Closed carlossampol closed 5 years ago
Auditing time 1 day
@MrCrambo assigned
My report is finished
Auditing time: 1 day
@RideSolo assigned
Auditing time: 1 day.
My report is finished.
@danbogd assigned
Tether USD (USDT) smart contract security audit report performed by Callisto Security Audit Department
In total, 7 issues were reported including:
3 low severity issues.
4 owner privileges (the ability of an owner to manipulate contract, may be risky for investors).
No critical security issues were found.
transfer
and transferFrom
.transfer
and transferFrom
through addBlackList
and removeBlackList
. And burn blacklisted users assets (please note that the assets are supposed to be backed in a 1:1 ratio) using destroyBlackFunds
function.deprecate
and implement any logic in the new contract. And even if the new contract will be audited, at any time possible to change the address of the new contract again to not audited and insecure.transfer
and transferFrom
allow the destination address to be equal to zero, meaning that users fund can be lost if sent to it by mistake.
function transfer(address _to, uint _value) public onlyPayloadSize(2 * 32) {
uint fee = (_value.mul(basisPointsRate)).div(10000);
if (fee > maximumFee) {
fee = maximumFee;
}
uint sendAmount = _value.sub(fee);
balances[msg.sender] = balances[msg.sender].sub(_value);
balances[_to] = balances[_to].add(sendAmount);
if (fee > 0) {
balances[owner] = balances[owner].add(fee);
Transfer(msg.sender, owner, fee);
}
Transfer(msg.sender, _to, sendAmount);
}
function transferFrom(address _from, address _to, uint _value) public onlyPayloadSize(3 * 32) {
var _allowance = allowed[_from][msg.sender];
uint fee = (_value.mul(basisPointsRate)).div(10000);
if (fee > maximumFee) {
fee = maximumFee;
}
if (_allowance < MAX_UINT) {
allowed[_from][msg.sender] = _allowance.sub(_value);
}
uint sendAmount = _value.sub(fee);
balances[_from] = balances[_from].sub(_value);
balances[_to] = balances[_to].add(sendAmount);
if (fee > 0) {
balances[owner] = balances[owner].add(fee);
Transfer(_from, owner, fee);
}
Transfer(_from, _to, sendAmount);
}
When issuing or redeeming tokens a transfer event should be emitted back and forth to address(0). ERC20 standard: "A token contract which creates new tokens SHOULD trigger a Transfer event with the _from address set to 0x0 when tokens are created". the same can be deducted when redeeming or burning tokens.
Same issue is applicable for TetherToken
constructor.
https://gist.github.com/RideSolo/24c79eb34b565ade477ec89c2af49a5b#file-usdt-sol-L406
https://gist.github.com/RideSolo/24c79eb34b565ade477ec89c2af49a5b#file-usdt-sol-L420
Add into the function transfer(address _to, ... )
and transferFrom
the following code, to avoid transfers to the contract address:
require( _to != address(this) );
The audited smart contract can be deployed. Only low severity issues were found during the audit.
https://gist.github.com/yuriy77k/49b74a164bccac9b2554de9b25ffae8b
https://gist.github.com/yuriy77k/476b9556f4895d32867890af4e4199ba
https://gist.github.com/yuriy77k/d75e9365b6ec7eefd46a237d09e673bc
0xdac17f958d2ee523a2206206994597c13d831ec7 - this smart contract has stolen my 50k USDT funds from Trust Wallet!
@HawaiiToastNo1 were you ever able to get it back?
Audit request
Audit Top 200 CoinMarketCap tokens.
Tether USD (USDT) Ethereum Token
Deployed at https://etherscan.io/address/0xdac17f958d2ee523a2206206994597c13d831ec7#contracts
Source code
https://etherscan.io/address/0xdac17f958d2ee523a2206206994597c13d831ec7#contracts
Disclosure policy
public
Platform
Ethereum
Number of lines:
252