Возможно ли переполнение в этом смарт-контракте?

function mint(address beneficiary) public payable {
    uint256 MTCToken = (msg.value/10000) * (10 ** uint256(18));
    uint256 teamToken = (MTCToken/100) * (5);
    balances[owner] += teamToken;
    balances[beneficiary] = balances[beneficiary] + (MTCToken - teamToken);
    totalSupply_ = totalSupply_ + (MTCToken);
}

Я немного запутался с точной длиной предела переполнения. Можно ли пересечь предел в вышеуказанной функции?

Ответы (2)

Возможно переполнение, но мы не можем сказать об этом, если не знаем, что такое тип сальдо и totalSupply_. Это может быть uint8, и тогда будет очень легко переполнить балансы[владелец] или балансы[бенефициар] или totalSupply_

Если это uint256, то это все еще возможно, но для этого потребуется отправить много ETH. Это не имеет никакого смысла.

Я не знаю ваших требований, поэтому не могу сказать, почему вы умножаете на 10 ** 18.

uint256 MTCToken = (msg.value/10000) * (10 ** uint256(18));

msg.value находится в Wei, поэтому я предполагаю, что у вас здесь ошибка. Также лучше сначала сделать умножение, а потом деление.

Я немного запутался с точной длиной предела переполнения.

Ответ: Предел переполнения зависит от типа переменной назначения. Если вы сохраняете результаты в типе uint8, то максимальное значение равно 255.

Итак, в этом примере:

pragma solidity 0.4.24;

  contract Overflow {
    uint8 iWantToBeCrossed;

    function OverflowMe() public
    {
        iWantToBeCrossed = 100;
        iWantToBeCrossed += 200;

    }

    function ShowMeTheValue () public   view returns (uint8){
        return iWantToBeCrossed;
    }
}

Функция ShowMeTheValue вернет 44 после вызова функции OverflowMe.

введите описание изображения здесьДля uint256 вам нужны большие значения. Так что теоретически переполнение возможно, но практически это не имеет никакого смысла, потому что вам нужно будет отправить много ETH на свой контракт.

Переполнение технически возможно, но маловероятно. Максимально возможное число в uint256 равно (2^256)-1. Если бы кто-то отправил весь существующий эфир в эту функцию, значение MTCToken все равно было бы всего 9,7330305e+39, что составляет всего ~133 из 256 бит.

Обратите внимание, что msg.value уже находится в wei, поэтому умножение на 10**18 не даст вам, сколько там wei. Кроме того, я бы предложил выполнить умножение перед делением, так как при делении десятичные дроби будут отброшены. например 12345/100*5 = 615 против 617.