Skip to content

Commit

Permalink
Merge pull request #206 from etherfi-protocol/revert-102-revert-96-re…
Browse files Browse the repository at this point in the history
…vert-85-jtdev/feature/eip-5

Revert "[EFIP-5] {Permit Whitelist, Transfer Blacklist}"
  • Loading branch information
seongyun-ko authored Dec 5, 2024
2 parents 5460325 + 9c4a8db commit c5b51fb
Show file tree
Hide file tree
Showing 5 changed files with 5 additions and 223 deletions.
49 changes: 4 additions & 45 deletions src/EETH.sol
Original file line number Diff line number Diff line change
Expand Up @@ -15,18 +15,12 @@ import "./interfaces/ILiquidityPool.sol";

contract EETH is IERC20Upgradeable, UUPSUpgradeable, OwnableUpgradeable, IERC20PermitUpgradeable, IeETH {
using CountersUpgradeable for CountersUpgradeable.Counter;
//--------------------------------------------------------------------------------------
//--------------------------------- STATE-VARIABLES ----------------------------------
//--------------------------------------------------------------------------------------

ILiquidityPool public liquidityPool;

uint256 public totalShares;
mapping (address => uint256) public shares;
mapping (address => mapping (address => uint256)) public allowances;
mapping (address => CountersUpgradeable.Counter) private _nonces;
mapping (address => bool) public whitelistedSpender;
mapping (address => bool) public blacklistedRecipient;

bytes32 private constant _PERMIT_TYPEHASH = keccak256("Permit(address owner,address spender,uint256 value,uint256 nonce,uint256 deadline)");

Expand All @@ -40,16 +34,9 @@ contract EETH is IERC20Upgradeable, UUPSUpgradeable, OwnableUpgradeable, IERC20P
bytes32 private immutable _HASHED_VERSION;
bytes32 private immutable _TYPE_HASH;

//--------------------------------------------------------------------------------------
//------------------------------------ EVENTS ----------------------------------------
//--------------------------------------------------------------------------------------

event TransferShares( address indexed from, address indexed to, uint256 sharesValue);

//--------------------------------------------------------------------------------------
//---------------------------- STATE-CHANGING FUNCTIONS ------------------------------
//--------------------------------------------------------------------------------------

// TODO: Figure our what `name` and `version` are for
constructor() {
bytes32 hashedName = keccak256("EETH");
bytes32 hashedVersion = keccak256("1");
Expand Down Expand Up @@ -140,7 +127,6 @@ contract EETH is IERC20Upgradeable, UUPSUpgradeable, OwnableUpgradeable, IERC20P
bytes32 r,
bytes32 s
) public virtual override(IeETH, IERC20PermitUpgradeable) {
require(whitelistedSpender[spender], "eETH: spender not whitelisted");
require(block.timestamp <= deadline, "ERC20Permit: expired deadline");

bytes32 structHash = keccak256(abi.encode(_PERMIT_TYPEHASH, owner, spender, value, _useNonce(owner), deadline));
Expand All @@ -153,13 +139,8 @@ contract EETH is IERC20Upgradeable, UUPSUpgradeable, OwnableUpgradeable, IERC20P
_approve(owner, spender, value);
}

//--------------------------------------------------------------------------------------
//------------------------------- INTERNAL FUNCTIONS ---------------------------------
//--------------------------------------------------------------------------------------

// [INTERNAL FUNCTIONS]
function _transfer(address _sender, address _recipient, uint256 _amount) internal {
require(!blacklistedRecipient[_sender] && !blacklistedRecipient[_recipient], "eETH: blacklisted address");

uint256 _sharesToTransfer = liquidityPool.sharesForAmount(_amount);
_transferShares(_sender, _recipient, _sharesToTransfer);
emit Transfer(_sender, _recipient, _amount);
Expand Down Expand Up @@ -194,26 +175,7 @@ contract EETH is IERC20Upgradeable, UUPSUpgradeable, OwnableUpgradeable, IERC20P
nonce.increment();
}

//--------------------------------------------------------------------------------------
//------------------------------------ SETTERS ---------------------------------------
//--------------------------------------------------------------------------------------

function setWhitelistedSpender(address[] calldata _spenders, bool _isWhitelisted) external onlyOwner {
for (uint i = 0; i < _spenders.length; i++) {
whitelistedSpender[_spenders[i]] = _isWhitelisted;
}
}

function setBlacklistedRecipient(address[] calldata _recipients, bool _isBlacklisted) external onlyOwner {
for (uint i = 0; i < _recipients.length; i++) {
blacklistedRecipient[_recipients[i]] = _isBlacklisted;
}
}

//--------------------------------------------------------------------------------------
//------------------------------------ GETTERS ---------------------------------------
//--------------------------------------------------------------------------------------

// [GETTERS]
function name() public pure returns (string memory) { return "ether.fi ETH"; }
function symbol() public pure returns (string memory) { return "eETH"; }
function decimals() public pure returns (uint8) { return 18; }
Expand Down Expand Up @@ -258,10 +220,7 @@ contract EETH is IERC20Upgradeable, UUPSUpgradeable, OwnableUpgradeable, IERC20P
return ECDSAUpgradeable.toTypedDataHash(_domainSeparatorV4(), structHash);
}

//--------------------------------------------------------------------------------------
//------------------------------------ MODIFIER --------------------------------------
//--------------------------------------------------------------------------------------

// [MODIFIERS]
modifier onlyPoolContract() {
require(msg.sender == address(liquidityPool), "Only pool contract function");
_;
Expand Down
61 changes: 1 addition & 60 deletions src/WeETH.sol
Original file line number Diff line number Diff line change
Expand Up @@ -17,9 +17,6 @@ contract WeETH is ERC20Upgradeable, UUPSUpgradeable, OwnableUpgradeable, ERC20Pe
IeETH public eETH;
ILiquidityPool public liquidityPool;

mapping (address => bool) public whitelistedSpender;
mapping (address => bool) public blacklistedRecipient;

//--------------------------------------------------------------------------------------
//---------------------------- STATE-CHANGING FUNCTIONS ------------------------------
//--------------------------------------------------------------------------------------
Expand All @@ -29,9 +26,6 @@ contract WeETH is ERC20Upgradeable, UUPSUpgradeable, OwnableUpgradeable, ERC20Pe
_disableInitializers();
}

/// @notice Initializes the contract with the specified liquidity pool and eETH addresses
/// @param _liquidityPool The address of the liquidity pool
/// @param _eETH The address of the eETH contract
function initialize(address _liquidityPool, address _eETH) external initializer {
require(_liquidityPool != address(0), "No zero addresses");
require(_eETH != address(0), "No zero addresses");
Expand Down Expand Up @@ -82,64 +76,14 @@ contract WeETH is ERC20Upgradeable, UUPSUpgradeable, OwnableUpgradeable, ERC20Pe
return eETHAmount;
}

/// @notice Requires the spender to be whitelisted before calling {ERC20PermitUpgradeable-permit}
function permit(
address owner,
address spender,
uint256 value,
uint256 deadline,
uint8 v,
bytes32 r,
bytes32 s
) public override {
require(whitelistedSpender[spender], "weETH: spender not whitelisted");

super.permit(owner, spender, value, deadline, v, r, s);
}

//--------------------------------------------------------------------------------------
//------------------------------- INTERNAL FUNCTIONS ---------------------------------
//--------------------------------------------------------------------------------------

/// @dev Authorizes the upgrade of the contract to a new implementation by the owner
/// @param newImplementation The address of the new contract implementation
function _authorizeUpgrade(
address newImplementation
) internal override onlyOwner {}


/// @notice Require the recipient to not be blacklisted before calling {ERC20Upgradeable-_transfer}
function _transfer(
address from,
address to,
uint256 amount
) internal override {
require(!blacklistedRecipient[from] && !blacklistedRecipient[to], "weETH: blacklisted address");
super._transfer(from, to, amount);
}

//--------------------------------------------------------------------------------------
//------------------------------------ SETTERS ---------------------------------------
//--------------------------------------------------------------------------------------

/// @notice Sets the whitelisted status for a list of addresses
/// @param _spenders An array of spender addresses
/// @param _isWhitelisted Boolean value to set the whitelisted status
function setWhitelistedSpender(address[] calldata _spenders, bool _isWhitelisted) external onlyOwner {
for (uint i = 0; i < _spenders.length; i++) {
whitelistedSpender[_spenders[i]] = _isWhitelisted;
}
}

/// @notice Sets the blacklisted status for a list of addresses
/// @param _recipients An array of recipient addresses
/// @param _isBlacklisted Boolean value to set the blacklisted status
function setBlacklistedRecipient(address[] calldata _recipients, bool _isBlacklisted) external onlyOwner {
for (uint i = 0; i < _recipients.length; i++) {
blacklistedRecipient[_recipients[i]] = _isBlacklisted;
}
}

//--------------------------------------------------------------------------------------
//------------------------------------ GETTERS ---------------------------------------
//--------------------------------------------------------------------------------------
Expand All @@ -158,14 +102,11 @@ contract WeETH is ERC20Upgradeable, UUPSUpgradeable, OwnableUpgradeable, ERC20Pe
return liquidityPool.amountForShare(_weETHAmount);
}

/// @notice Fetches the exchange rate of eETH for 1 weETH
/// @return The amount of eETH for 1 weETH
// Amount of eETH for 1 weETH
function getRate() external view returns (uint256) {
return getEETHByWeETH(1 ether);
}

/// @notice Fetches the address of the current contract implementation
/// @return The address of the current implementation
function getImplementation() external view returns (address) {
return _getImplementation();
}
Expand Down
55 changes: 0 additions & 55 deletions test/EETH.t.sol
Original file line number Diff line number Diff line change
Expand Up @@ -300,59 +300,4 @@ contract EETHTest is TestSetup {
assertEq(eETHInstance.allowance(alice, bob), 0.5 ether);
}

function test_PermitWhitelistEETH() public {
startHoax(alice);
liquidityPoolInstance.deposit{value: 1 ether}();
vm.stopPrank();

// alice approves bob to spend 1 ether of eETH
bytes32 permitHash = keccak256(
abi.encodePacked(
"\x19\x01",
eETHInstance.DOMAIN_SEPARATOR(),
keccak256(abi.encode(
keccak256("Permit(address owner,address spender,uint256 value,uint256 nonce,uint256 deadline)"),
alice,
address(bob),
1 ether,
eETHInstance.nonces(alice),
block.timestamp
))
)
);
(uint8 v, bytes32 r, bytes32 s) = vm.sign(2, permitHash);

vm.expectRevert("eETH: spender not whitelisted");
eETHInstance.permit(alice, bob, 1 ether, block.timestamp, v, r, s);

address[] memory whitelist = new address[](1);
whitelist[0] = bob;
vm.prank(owner);
eETHInstance.setWhitelistedSpender(whitelist, true);

eETHInstance.permit(alice, bob, 1 ether, block.timestamp, v, r, s);
vm.prank(bob);
eETHInstance.transferFrom(alice, bob, 1 ether);
}

function test_TransferBlacklistEETH() public {
startHoax(alice);
liquidityPoolInstance.deposit{value: 2 ether}();

eETHInstance.transfer(bob, 1 ether);
vm.stopPrank();

vm.prank(owner);
address[] memory blacklist = new address[](1);
blacklist[0] = bob;
eETHInstance.setBlacklistedRecipient(blacklist, true);

vm.prank(alice);
vm.expectRevert("eETH: blacklisted address");
eETHInstance.transfer(bob, 1 ether);

vm.prank(bob);
vm.expectRevert("eETH: blacklisted address");
eETHInstance.transfer(alice, 1 ether);
}
}
7 changes: 0 additions & 7 deletions test/TestSetup.sol
Original file line number Diff line number Diff line change
Expand Up @@ -733,13 +733,6 @@ contract TestSetup is Test {
_initializeEtherFiAdmin();

admin = alice;

// weETH and Liquidity Pool must be on eETH to function as expected
vm.prank(owner);
address[] memory whitelist = new address[](2);
whitelist[0] = address(weEthInstance);
whitelist[1] = address(liquidityPoolInstance);
eETHInstance.setWhitelistedSpender(whitelist, true);
}

function _initOracleReportsforTesting() internal {
Expand Down
56 changes: 0 additions & 56 deletions test/WeETH.t.sol
Original file line number Diff line number Diff line change
Expand Up @@ -42,7 +42,6 @@ contract WeETHTest is TestSetup {
//Approve the wrapped eth contract to spend 100 eEth
eETHInstance.approve(address(weEthInstance), 100 ether);
weEthInstance.wrap(5 ether);
vm.stopPrank();

assertEq(weEthInstance.balanceOf(alice), 5 ether);
assertEq(eETHInstance.balanceOf(alice), 5 ether);
Expand Down Expand Up @@ -290,59 +289,4 @@ contract WeETHTest is TestSetup {
weEthInstance.unwrap(1 ether);
assertEq(eETHInstance.balanceOf(bob), 1.333333333333333332 ether);
}

function test_PermitWhitelistWeETH() public {
// allocationg weETH to alice
test_WrapWorksCorrectly();

// alice approves bob to spend 1 ether of weETH
bytes32 permitHash = keccak256(
abi.encodePacked(
"\x19\x01",
weEthInstance.DOMAIN_SEPARATOR(),
keccak256(abi.encode(
keccak256("Permit(address owner,address spender,uint256 value,uint256 nonce,uint256 deadline)"),
alice,
address(bob),
1 ether,
weEthInstance.nonces(alice),
block.timestamp
))
)
);
(uint8 v, bytes32 r, bytes32 s) = vm.sign(2, permitHash);

vm.expectRevert("weETH: spender not whitelisted");
weEthInstance.permit(alice, bob, 1 ether, block.timestamp, v, r, s);

address[] memory whitelist = new address[](1);
whitelist[0] = bob;
vm.prank(owner);
weEthInstance.setWhitelistedSpender(whitelist, true);

weEthInstance.permit(alice, bob, 1 ether, block.timestamp, v, r, s);
vm.prank(bob);
weEthInstance.transferFrom(alice, bob, 1 ether);
}

function test_TransferBlacklistWeETH() public {
// allocationg weETH to alice
test_WrapWorksCorrectly();

vm.prank(alice);
weEthInstance.transfer(bob, 1 ether);

vm.prank(owner);
address[] memory blacklist = new address[](1);
blacklist[0] = bob;
weEthInstance.setBlacklistedRecipient(blacklist, true);

vm.prank(alice);
vm.expectRevert("weETH: blacklisted address");
weEthInstance.transfer(bob, 1 ether);

vm.prank(bob);
vm.expectRevert("weETH: blacklisted address");
weEthInstance.transfer(alice, 1 ether);
}
}

0 comments on commit c5b51fb

Please sign in to comment.