构造函数缺失漏洞分析

一、前言

构造函数缺失漏洞自智能合约产生以来就一直出现,归根到底是由于新进开发者对 solidity 代码结构不熟悉造成的。BUGX.IO团队本次就来介绍一下漏洞的基本原理、表现形式以及对开发者的建议。

二、漏洞原理

1. 什么是构造函数

Solidity编写合约和面向对象编程语言非常相似,我们可以通过构造函数(constructor)来初始化合约对象。构造函数就是方法名和合约名字相同的函数,创建合约时会调用构造函数对状态变量进行数据初始化操作。

pragma solidity 0.4.21;

contract Foo {

  function Foo() public {

    // ...

  }

}

合约结构的规范化写作可以让其他人更好地阅读,并且 constructor 和 fallback 函数要放在前面以便更好地查看。官方建议以如下顺序写作:

* constructor

* fallback function (if exists)

* external

* public

* internal

* private

合约结构的规范写法如下:

contract A {
    constructor() public {
        ...
    }

    function() external {
        ...
    }

    // External functions
    // ...

    // External functions that are view
    // ...

    // External functions that are pure
    // ...

    // Public functions
    // ...

    // Internal functions
    // ...

    // Private functions
    // ...
}

2. 构造函数缺失与危害

构造函数缺失则是由于构造函数与合约名字不同,而又为 public 类型,就变成了一个公有函数了,可以被任何人调用,一般函数函数比较敏感,用于初始化合约时定义通证数量、管理员地址等基本变量状态,一时变成了公有函数,危害可想而知,权限控制、通证管理基本全线奔溃。

3. 版本升级后构造函数的变化

从 `0.4.22`版本开始,solidity 编译器引入了 constructors 关键字,以替代低版本的将合约名作为构造函数名的语法,避免程序员容易出现的编码错误。使用旧写法会出现 warning 信息。

新版本写法为:

contract Ownable {
    address public owner;
    address public admin;

    constructor() public {
        owner = msg.sender;
        admin = msg.sender;
    }

    // Other code
}

三、常见漏洞代码形式

1. 构造函数使用库合约名称,使得构造函数变成了公有函数,可被任意调用。

我们发现了不少这种错误写法的合约,在主合约中,构造函数写成了 Token() 或 ERC20Token() 。这样子的函数非构造函数,变成了普通函数了。

如 DealGuard 合约: 

https://etherscan.io//address/0xb47c5e8f389dc1fa8247c9a4b9e5dcdc79754152#code

2. 合约名与构造函数名不同,如大小写不同、拼写错误等,使得构造函数变成了公有函数,可被任意人调用。

只能说开发者太大意,对智能合约开发有什么误解吧。经常看到的漏洞形式是合约名与构造函数不同,只与 name 变量名相同,估计是开发者以为合约名相同就行了,却忽略了构造函数。

如 ReaperCoin11 合约: 

https://etherscan.io//address/0x1b7cd071187ec0b2995b96ee82296cfa639572f1#code

还有这个 Krypticoin 合约,乍一看看不出来,仔细瞅瞅,再仔细瞅瞅,原来 coin 拼错了 。

之前知道创宇发布了关于 `owned`大小写编码漏洞的文章。同时,我们也可以找一些类似的容易大小写错误的库合约,如 `ownable`。不过经过我们的分析,还是以 owned 大小写错误为主。

如 MORPH 合约:

https://etherscan.io//address/0x2ef27bf41236bd859a95209e17a43fbd26851f92#code

contract Owned {
    address public owner;

    function owned() public {
        owner = msg.sender;
    }

3. constructor 前加了function ,或者加了 fucntion 然后开头的 C写成了大写,即 `function Constructor()public {}`,使得构造函数变成了公有函数,可被任意人调用。

版本升级后的构造函数只需要单独使用 constructor 即可,但很多开发者却忽略了此细节。上面这个写法错误在于两点:

1) 加入了 function 变成了普通函数形式。但是这时编辑器中会报 warning 信息:

但是有开发者忽了此警告,写出了错误代码。

如 MDOT 合约: 

https://etherscan.io//address/0xef7d906fd1c0eb5234df32f40c6a1cb0328d7279#code

   function constructor() public {
        totalSupply = 5000000000000;       // Set the total supply (in base units)
        balances[0xbfC729007CE9CBBE54132Fb9BFa097D80AAC791C] = 5000000000000;    // Initially assign the entire supply to the specified account
    }

2) 但是如果将 `constructor`错写成了 `Constructor`,使得编辑器识别其为普通函数名,没有任何 warning 信息。

如 TOGToken 合约: 

https://etherscan.io//address/0xb9d5c2548266428795fd8b1f12aedbdeb417fe54#code

四、常见漏洞代码形式

使用新版本写法,并且检查句式、拼写的正确性。

五、漏洞影响范围

通过我们对以太坊上的合约进行整体监测,发现有此漏洞的竟达两千多份,大小写编码错误的约有20 份。其中不乏正在使用中的合约。

六、资料

https://solidity.readthedocs.io/en/latest/contracts.html?highlight=constructor#creating-contracts

https://solidity.readthedocs.io/en/latest/style-guide.html?highlight=constructor#order-of-functions

https://ethereum.stackexchange.com/questions/30223/should-the-constructor-function-be-public

http://solidity.readthedocs.io/en/develop/contracts.html?highlight=private#visibility-and-getters

七、公司介绍 

BUGX.IO是一家致力于区块链领域的安全公司。核心团队组建于2014年,我们在区块链生态安全、行业解决方案、安全建设、红蓝对抗等方面有深厚积累与过硬专业素养。

 

深度学习是机器学习的一个子领域,它基于人工神经网络的研究,特别是利用多层次的神经网络来进行学习和模式识别。深度学习模型能够学习数据的高层次特征,这些特征对于图像和语音识别、自然语言处理、医学图像分析等应用至关重要。以下是深度学习的一些关键概念和组成部分: 1. **神经网络(Neural Networks)**:深度学习的基础是人工神经网络,它是由多个层组成的网络结构,包括输入层、隐藏层和输出层。每个层由多个神经元组成,神经元之间通过权重连接。 2. **前馈神经网络(Feedforward Neural Networks)**:这是最常见的神经网络类型,信息从输入层流向隐藏层,最终到达输出层。 3. **卷积神经网络(Convolutional Neural Networks, CNNs)**:这种网络特别适合处理具有网格结构的数据,如图像。它们使用卷积层来提取图像的特征。 4. **循环神经网络(Recurrent Neural Networks, RNNs)**:这种网络能够处理序列数据,如时间序列或自然语言,因为它们具有记忆功能,能够捕捉数据中的时间依赖性。 5. **长短期记忆网络(Long Short-Term Memory, LSTM)**:LSTM 是一种特殊的 RNN,它能够学习长期依赖关系,非常适合复杂的序列预测任务。 6. **生成对抗网络(Generative Adversarial Networks, GANs)**:由两个网络组成,一个生成器和一个判别器,它们相互竞争,生成器生成数据,判别器评估数据的真实性。 7. **深度学习框架**:如 TensorFlow、Keras、PyTorch 等,这些框架提供了构建、训练和部署深度学习模型的工具和库。 8. **激活函数(Activation Functions)**:如 ReLU、Sigmoid、Tanh 等,它们在神经网络中用于添加非线性,使得网络能够学习复杂的函数。 9. **损失函数(Loss Functions)**:用于评估模型的预测与真实值之间的差异,常见的损失函数包括均方误差(MSE)、交叉熵(Cross-Entropy)等。 10. **优化算法(Optimization Algorithms)**:如梯度下降(Gradient Descent)、随机梯度下降(SGD)、Adam 等,用于更新网络权重,以最小化损失函数。 11. **正则化(Regularization)**:技术如 Dropout、L1/L2 正则化等,用于防止模型过拟合。 12. **迁移学习(Transfer Learning)**:利用在一个任务上训练好的模型来提高另一个相关任务的性能。 深度学习在许多领域都取得了显著的成就,但它也面临着一些挑战,如对大量数据的依赖、模型的解释性差、计算资源消耗大等。研究人员正在不断探索新的方法来解决这些问题。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值