简介

对应的代码TimeLock.sol

TimeLock.sol 直译为时间锁。其实是一个在solidity中实现的队列。
可以将代码加入队列,从队列中执行。执行方式为call调用。不支持重复调用,相同的地址和参数作为一个任务,重复添加无效,调用时只会调用一次,后续调用会失败,调用后再次加入队列可以调用成功。

代码解析

  • uint public constant GRACE_PERIOD = 14 days; 宽限时间

  • uint public constant MINIMUM_DELAY = 0; 最小延期时间

  • uint public constant MAXIMUM_DELAY = 30 days;最大延期时间

  • address public admin; 管理员

  • address public pendingAdmin; 待定管理员

  • uint public delay; 延期时间

  • mapping (bytes32 => bool) public queuedTransactions; 交易队列

  • constructor(address admin_, uint delay_) 构造方法
    传入 管理员的地址和延期时间,延期时间需要大于等于 MINIMUM_DELAY且小于等于MAXIMUM_DELAY。
    管理员地址不能是0地址。

    constructor(address admin_, uint delay_) public {require(delay_ >= MINIMUM_DELAY, "Timelock: Delay must exceed minimum delay.");require(delay_ <= MAXIMUM_DELAY, "Timelock: Delay must not exceed maximum delay.");require(admin_ != address(0), "Timelock: Admin must not be 0 address");admin = admin_;delay = delay_;}
  • receive() external payable { }
    合约最多可以具有一个receive函数。这个函数不能有参数,不能返回任何参数,并且必须具有receive可见性和payable状态可变性。当向合约发送 Ether 且未指定调用任何函数(calldata 为空)时执行。这是在普通的以太坊转账上执行的函数(例如,通过.send()或.transfer()转账)。
    如果 receive 函数不存在,但是有payable的 fallback 回退函数,那么在进行纯以太转账时,fallback 函数会调用。
    如果两个函数都没有,这个合约就没法通过常规的转账交易接收以太(会抛出异常)。

  • function setDelay(uint delay_)
    设置新的延期时间,只有管理员能进行设置,延期时间需要大于等于MINIMUM_DELAY且小于等于MAXIMUM_DELAY

    function setDelay(uint delay_) public {require(msg.sender == address(this), "Timelock: Call must come from Timelock.");require(delay_ >= MINIMUM_DELAY, "Timelock: Delay must exceed minimum delay.");require(delay_ <= MAXIMUM_DELAY, "Timelock: Delay must not exceed maximum delay.");delay = delay_;emit NewDelay(delay);}
  • function acceptAdmin() 任职管理员
    待定管理员转正,由待定管理员调用,并将其设置为管理员,待定管理员设置为0地址。
    function acceptAdmin() public {require(msg.sender == pendingAdmin, "Timelock: Call must come from pendingAdmin.");admin = msg.sender;pendingAdmin = address(0);emit NewAdmin(admin);}
  • function setPendingAdmin(address pendingAdmin_) 设置待定管理员
    由管理员调用,将某人设置为待定管理员
    function setPendingAdmin(address pendingAdmin_) public {require(msg.sender == address(this), "Timelock: Call must come from Timelock.");pendingAdmin = pendingAdmin_;emit NewPendingAdmin(pendingAdmin);}
  • function queueTransaction
    加入队列
    由管理员调用 当 eta>=当前区块时间+延期时间时可以调用,将某提案的target, value, signature, data, eta存入队列,并设置状态为true,代表队列等待执行
    function queueTransaction(address target, uint value, string memory signature, bytes memory data, uint eta) public returns (bytes32) {require(msg.sender == admin, "Timelock: Call must come from admin.");require(eta >= getBlockTimestamp().add(delay), "Timelock: Estimated execution block must satisfy delay.");bytes32 txHash = keccak256(abi.encode(target, value, signature, data, eta));queuedTransactions[txHash] = true;emit QueueTransaction(txHash, target, value, signature, data, eta);return txHash;}
  • function cancelTransaction
    取消队列由管理员调用 将target, value, signature, data, eta的提案状态设置为false
    function cancelTransaction(address target, uint value, string memory signature, bytes memory data, uint eta) public {require(msg.sender == admin, "Timelock: Call must come from admin.");bytes32 txHash = keccak256(abi.encode(target, value, signature, data, eta));queuedTransactions[txHash] = false;emit CancelTransaction(txHash, target, value, signature, data, eta);}
  • function executeTransaction 执行队列
    由管理员执行。
    根据target, value, signature, data, eta取出队列,如果是待执行状态,则执行该队列。
    只有区块在eta及之后,eta+宽限时间之前才能执行。
    队列使用call的方式进行执行。
    function executeTransaction(address target, uint value, string memory signature, bytes memory data, uint eta) public payable returns (bytes memory) {require(msg.sender == admin, "Timelock: Call must come from admin.");bytes32 txHash = keccak256(abi.encode(target, value, signature, data, eta));require(queuedTransactions[txHash], "Timelock: Transaction hasn't been queued.");require(getBlockTimestamp() >= eta, "Timelock: Transaction hasn't surpassed time lock.");require(getBlockTimestamp() <= eta.add(GRACE_PERIOD), "Timelock: Transaction is stale.");queuedTransactions[txHash] = false;bytes memory callData;if (bytes(signature).length == 0) {callData = data;} else {callData = abi.encodePacked(bytes4(keccak256(bytes(signature))), data);}// solhint-disable-next-line avoid-low-level-calls(bool success, bytes memory returnData) = target.call{value: value}(callData); //solhint-disable avoid-call-valuerequire(success, "Timelock: Transaction execution reverted.");emit ExecuteTransaction(txHash, target, value, signature, data, eta);return returnData;}
  • getBlockTimestamp()获取当前区块的时间戳
    function getBlockTimestamp() internal view returns (uint) {// solhint-disable-next-line not-rely-on-timereturn block.timestamp;}

Compound 治理——执行队列 TimeLock相关推荐

  1. Compound 治理——提案

    GovernorAlpha是社区治理投票的智能合约,包含提案部分和投票结果部分. GovernorAlpha.sol 代码解析 function quorumVotes() public pure r ...

  2. 【Linux 内核】实时调度类 ⑦ ( 实时调度类核心函数源码分析 | dequeue_task_rt 函数 | 从执行队列中移除进程 )

    文章目录 一.dequeue_task_rt 函数 ( 从执行队列中移除进程 ) 二.update_curr_rt 函数 ( 更新调度信息 ) 本篇博客中 , 开始分析 struct sched_cl ...

  3. 【Linux 内核】实时调度类 ⑥ ( 实时调度类核心函数源码分析 | 插入进程到执行队列 | 从执行队列中选择优先级最高的进程 )

    文章目录 一.enqueue_task_rt 函数 ( 插入进程到执行队列 ) 二.pick_next_task_rt 函数 ( 从执行队列中选择优先级最高的进程 ) 本篇博客中 , 开始分析 str ...

  4. linux队列运行任务查看,Linux环境下批量执行队列任务的优雅方案

    设想我们有一个程序,需要在不同的参数下执行很多次,我们希望能够批量进行提交. 但是程序对系统的资源消耗比较大,而系统的资源是有限. 我们希望这些任务是按照队列排队提交的,每次只执行3个. 只有当队列中 ...

  5. hive指定hadoop执行队列

    指定队列的命令: 有三种: set mapred.job.queue.name=queue3; SET mapreduce.job.queuename=queue3; set mapred.queue ...

  6. PHP队列服务打不开,执行队列服务问题

    #### 1.运行queue队列服务的php配置必须启用proc\_open和proc\_get\_status函数,宝塔默认是禁用的:还有pcntl开头的函数也记得删除,不要禁用.如果有pcntl开 ...

  7. php导出excel执行队列,php导出大量数据到excel时,有哪些比较好的处理方法?

    导出csv就行 $columns = ['你导出的字段','你导出的字段','你导出的字段',..........]; $csvFileName = 'test.csv'; header('Conte ...

  8. # JavaScript中的执行上下文和队列(栈)的关系?

    原文:What is the Execution Context & Stack in JavaScript? git地址:JavaScript中的执行上下文和队列(栈)的关系? 导读:以前总 ...

  9. js 延迟几秒执行_深入研究 Node.js 的回调队列

    队列是 Node.js 中用于有效处理异步操作的一项重要技术. 在本文中,我们将深入研究 Node.js 中的队列:它们是什么,它们如何工作(通过事件循环)以及它们的类型. Node.js 中的队列是 ...

最新文章

  1. Verilog 中输入输出信号的类型?
  2. Linux Graphic DRI Wayland 显示子系统
  3. KineticJS教程(3)
  4. 关于跨域,以及跨域的几种方式
  5. 端到端测试_端到端测试的滥用–测试技术2
  6. Java学习笔记—生产者和消费者模式
  7. 阿里巴巴中间件在 Serverless 技术领域的探索
  8. 浅析 JNDI / DataSource / ConnectionPool 三者
  9. android4.0 底部菜单,Android自定义控件系列(四)—底部菜单(下)
  10. poj-3034 Whac-a-Mole
  11. team网卡配置_Linux中多个网卡配置(team的配置方式)
  12. 哪些版本linux支持arm,腾讯QQ Linux版本正式回归 支持x64 ARM64 MIPS64架构
  13. sqldbx连接db2数据库
  14. 仿脉脉PHP源码,php,mysql_如何实现类似脉脉网的二维人际关系,php,mysql,算法,社区,社交 - phpStudy...
  15. 安卓设备门禁识别开发_基于android手机的视频通话门禁控制系统
  16. Unity用Mesh画多边形、圆形
  17. Java入门视频教程(三)4 Java基本语法------分支流程
  18. libserial_port.so免费下载,包含所有库版本
  19. 2021年全球GigE相机收入大约721.2百万美元,预计2028年达到1293.9百万美元
  20. 新版火狐浏览器安装xpath插件

热门文章

  1. 谷歌chrome安卓版_Chrome+Android能摩擦出怎样的火花?Fyde OS深入体验笔记
  2. asp.net小说网站案例
  3. mysql给定两个时间段 获取两个时间段的所有日期
  4. 前端入门 1| HTML基本结构
  5. 拼图、jquery拼图、javascript拼图
  6. VMware打开虚拟机,会立即导致宿主机重启
  7. 一个JavaScript变量应用实例
  8. 『计组』CPU 如何区分指令和数据
  9. 解决springboot引入JSONObject包报错
  10. Mybatis层次结构图