-
Notifications
You must be signed in to change notification settings - Fork 11.9k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Reduce reliance on underlying decimals in ERC4626 #3549
Comments
This is a good point, we can't assume
This is also a very good point. I agree with adding a function like |
From the ERC:
It would be easy to just do that, but then what if someone overrides our 4626 with a custom decimal that doesn't not match the underlying asset. Should we make the decimal in 4626 "non-virtual override" ? |
So we could do
and no possibility to override decimal ... or
That way devs can still override |
I don't understand the second option, can you explain it in words? We can add the implementation of decimals based on ERC20Wrapper, but I think we should also add |
maybe this then: function decimals() public view override(IERC20Metadata, ERC20) returns (uint8) {
try IERC20Metadata(address(_asset)).decimals() returns (uint8 value) {
return value;
} catch {
return super.decimals();
}
}
function _initialConvertToShares(uint256 assets, Math.Rounding rounding) internal view virtual returns (uint256 shares) {
shares = assets;
}
function _convertToShares(uint256 assets, Math.Rounding rounding) internal view virtual returns (uint256 shares) {
uint256 supply = totalSupply();
return
(assets == 0 || supply == 0)
? _initialConvertToShares(assets, rounding)
: assets.mulDiv(supply, totalAssets(), rounding);
}
function _initialConvertToAssets(uint256 shares, Math.Rounding rounding) internal view virtual returns (uint256 assets) {
assets = shares;
}
function _convertToAssets(uint256 shares, Math.Rounding rounding) internal view virtual returns (uint256 assets) {
uint256 supply = totalSupply();
return
(supply == 0)
? _initialConvertToAssets(shares, rounding)
: shares.mulDiv(totalAssets(), supply, rounding);
}
``` |
What are the |
The second option is:
If the decimals are not overridden, then If the decimals are overridden, then IMO this is the most elegant approach. EDIT: it could be rewritten as
|
Also, any approach that makes |
Really like the first option @Amxx |
4626 uses
_asset.decimals()
to calculate initial share/asset conversionshttps://github.com/OpenZeppelin/openzeppelin-contracts/blob/master/contracts/token/ERC20/extensions/ERC4626.sol#L167
EIP4626 states:
But EIP20 states for
decimals
:So even if the vault exposes
decimals
for shares, the 20 spec says not to expect assets to exposedecimals
.Even if both tokens expose
decimals
the method is for usability, not for onchain calculations.Maybe a virtual
_initialShareRatio()
function could be exposed that implementing contracts can override without needing to override the entire conversion processThe text was updated successfully, but these errors were encountered: