Skip to content

Commit

Permalink
fix: ensure scaling for different reserveAsset token decimals (#551)
Browse files Browse the repository at this point in the history
### Description

This PR adds scaling to the reserve balance read in
mintUBIFromReserveBalance in Case the token has less than 18 decimals.

### Other changes



### Tested

- added test verifying expected behavior for token with 6 decimals

### Related issues


### Backwards compatibility


### Documentation
  • Loading branch information
philbow61 authored Nov 26, 2024
1 parent 161ec08 commit e840fa3
Show file tree
Hide file tree
Showing 2 changed files with 36 additions and 1 deletion.
5 changes: 4 additions & 1 deletion contracts/goodDollar/GoodDollarExpansionController.sol
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ import { IGoodDollarExpansionController } from "contracts/interfaces/IGoodDollar
import { IGoodDollarExchangeProvider } from "contracts/interfaces/IGoodDollarExchangeProvider.sol";
import { IBancorExchangeProvider } from "contracts/interfaces/IBancorExchangeProvider.sol";
import { IERC20 } from "openzeppelin-contracts-next/contracts/token/ERC20/IERC20.sol";
import { IERC20Metadata } from "openzeppelin-contracts-next/contracts/token/ERC20/extensions/IERC20Metadata.sol";
import { IGoodDollar } from "contracts/goodDollar/interfaces/IGoodProtocol.sol";
import { IDistributionHelper } from "contracts/goodDollar/interfaces/IGoodProtocol.sol";

Expand Down Expand Up @@ -152,7 +153,9 @@ contract GoodDollarExpansionController is IGoodDollarExpansionController, Ownabl
IBancorExchangeProvider.PoolExchange memory exchange = IBancorExchangeProvider(address(goodDollarExchangeProvider))
.getPoolExchange(exchangeId);

uint256 contractReserveBalance = IERC20(exchange.reserveAsset).balanceOf(reserve);
uint256 contractReserveBalance = IERC20(exchange.reserveAsset).balanceOf(reserve) *
(10 ** (18 - IERC20Metadata(exchange.reserveAsset).decimals()));

uint256 additionalReserveBalance = contractReserveBalance - exchange.reserveBalance;
if (additionalReserveBalance > 0) {
amountMinted = goodDollarExchangeProvider.mintFromInterest(exchangeId, additionalReserveBalance);
Expand Down
32 changes: 32 additions & 0 deletions test/unit/goodDollar/GoodDollarExpansionController.t.sol
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ pragma solidity 0.8.18;

import { Test } from "forge-std/Test.sol";
import { ERC20Mock } from "openzeppelin-contracts-next/contracts/mocks/ERC20Mock.sol";
import { ERC20DecimalsMock } from "openzeppelin-contracts-next/contracts/mocks/ERC20DecimalsMock.sol";
import { GoodDollarExpansionController } from "contracts/goodDollar/GoodDollarExpansionController.sol";

import { IGoodDollarExpansionController } from "contracts/interfaces/IGoodDollarExpansionController.sol";
Expand Down Expand Up @@ -326,6 +327,37 @@ contract GoodDollarExpansionControllerTest_mintUBIFromReserveBalance is GoodDoll
assertEq(amountMinted, 0);
}

function test_mintUBIFromReserveBalance_whenReserveAssetDecimalsIsLessThan18_shouldScaleCorrectly() public {
ERC20DecimalsMock reserveToken6DecimalsMock = new ERC20DecimalsMock("Reserve Token", "RES", 6);
IBancorExchangeProvider.PoolExchange memory pool2 = IBancorExchangeProvider.PoolExchange({
reserveAsset: address(reserveToken6DecimalsMock),
tokenAddress: address(token),
tokenSupply: 7 * 1e9 * 1e18,
reserveBalance: 200_000 * 1e18, // internally scaled to 18 decimals
reserveRatio: 0.2 * 1e8, // 20%
exitContribution: 0.1 * 1e8 // 10%
});

uint256 reserveInterest = 1000e6;
deal(address(reserveToken6DecimalsMock), reserveAddress, 200_000 * 1e6 + reserveInterest);

vm.mockCall(
address(exchangeProvider),
abi.encodeWithSelector(IBancorExchangeProvider(exchangeProvider).getPoolExchange.selector, exchangeId),
abi.encode(pool2)
);

vm.expectCall(
address(exchangeProvider),
abi.encodeWithSelector(
IGoodDollarExchangeProvider(exchangeProvider).mintFromInterest.selector,
exchangeId,
reserveInterest * 1e12
)
);
expansionController.mintUBIFromReserveBalance(exchangeId);
}

function test_mintUBIFromReserveBalance_whenAdditionalReserveBalanceIsLargerThan0_shouldMintAndEmit() public {
uint256 amountToMint = 1000e18;
uint256 additionalReserveBalance = 1000e18;
Expand Down

0 comments on commit e840fa3

Please sign in to comment.