creamfi / balancer-core Goto Github PK
View Code? Open in Web Editor NEWLicense: GNU General Public License v3.0
License: GNU General Public License v3.0
https://hackmd.io/mm0PhJ-YR8euWs6vSGinAQ#Reserves-and-balance-mismatch-ERC20balanceOf
_records[token].balance = IERC20(token).balanceOf(address(this)) - totalReserves[token]
Error messages are removed to let us have more space to add new functions. Find out a way to add some messages back.
#18 中 slither failed。在這 PR 中,我們在 gulp
中對 IERC20(token).balanceOf(address(this))
的結果運算,在看似無關的地方觸發了 slither 的 incorrect-equality 錯誤。
Error message
$ slither . --filter-paths "test" --exclude=naming-convention,unused-state,solc-version,constable-states,external-function,reentrancy-events
...
INFO:Detectors:
BNum.bdiv(uint256,uint256) (BNum.sol#75-86) uses a dangerous strict equality:
- require(bool)(a == 0 || c0 / a == BONE) (BNum.sol#81)
BNum.bmul(uint256,uint256) (BNum.sol#63-73) uses a dangerous strict equality:
- require(bool)(a == 0 || c0 / a == b) (BNum.sol#68)
BNum.bpow(uint256,uint256) (BNum.sol#108-126) uses a dangerous strict equality:
- remain == 0 (BNum.sol#120)
BNum.bpowApprox(uint256,uint256,uint256) (BNum.sol#128-161) uses a dangerous strict equality:
- term == 0 (BNum.sol#149)
Reference: https://github.com/crytic/slither/wiki/Detector-Documentation#dangerous-strict-equalities
INFO:Slither:. analyzed (16 contracts with 40 detectors), 4 result(s) found
INFO:Slither:Use https://crytic.io/ to get access to additional detectors and Github integration
...
試著 debug 後發現 slither 會偵測「有沒有 balance 在 require 中被用 ==
比較」,因此我猜測有被丟到 BNum.bdiv
、 BNum.bmul
、 BNum.bpow
、及 BNum.bpowApprox
的參數,在這 PR 後被標記為是 balance。因為這些函數會對這些參數做像是 BNum.bmul
中 require(a == 0 || c0 / a == b)
這種違反 incorrect-equality 的行為。
目前我傾向先讓 slither 忽略 incorrect-equality
不檢查,因為要 debug 需要滿多時間的,然後感覺問題很可能是在 slither。
In #1 , we have totalReserves
storing all reserved fees. Eventually, we transfer all these tokens in all pools back to an address provided by BFactory
.
BFactory
contract BFactory {
...
function getReservesAddress() returns (address);
// Can only be called by the admin who deployed this contract.
function setReservesAddress(address reservesAddress);
// Transfer the reserves tokens in `pool` to the `reservesAddress`.
function collectTokens(BPool pool);
}
BPool
contract BPool {
...
function withdrawReserves(address reserveAddress) {
require(msg.sender == _factory);
for (t in _tokens) {
// transfer reserves tokens to `reserveAddress`
...
}
}
}
Don't call BFactory.collect(BPool pool)
because
BPool.drainTotalReserves
should be secure in most of the condition thanks to the guard at
balancer-core/contracts/BPool.sol
Line 819 in 9f194f3
BFactory
call another malicious contract and then this contract calls BPool.drainTotalReserves
through a delegate call. This way, msg.sender
in BPool.drainTotalReserves
will be _factory
and require
is bypassed. Thus, we should prevent BFactory
from calling any contract we don't know. Currently, BFactory
calls other contracts in the following snippets:
BFactory.newBPool
balancer-core/contracts/BFactory.sol
Line 59 in f571d8f
This is fine because bpool
is created by BFactory
and the code is known to us.
BFactory.collect
balancer-core/contracts/BFactory.sol
Lines 123 to 124 in f571d8f
This is possibly manipulated if pool
is a contract with malicious/malformed balanceOf
or transfer
. If it calls any pool's drainTotalReserves
with delegatecall
, totalReserves
can be withdrawn to attackers address.
BFactory.collectTokenReserves
balancer-core/contracts/BFactory.sol
Line 133 in f571d8f
This is fine because we have require(_isBPool[address(pool)])
guarding us, which is only passed through when pool
is one of our pools.
A declarative, efficient, and flexible JavaScript library for building user interfaces.
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google ❤️ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.