Skip to content

Commit

Permalink
Merge branch 'main' into alp/PDE-198
Browse files Browse the repository at this point in the history
  • Loading branch information
ungaro committed Dec 11, 2024
2 parents 691b704 + 1b4ab43 commit 09d2333
Show file tree
Hide file tree
Showing 8 changed files with 601 additions and 90 deletions.
10 changes: 5 additions & 5 deletions nest/script/DeployNestContracts.s.sol
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.25;

import { ERC1967Proxy } from "@openzeppelin/contracts/proxy/ERC1967/ERC1967Proxy.sol";
import { IERC20 } from "@openzeppelin/contracts/token/ERC20/IERC20.sol";
import { Script } from "forge-std/Script.sol";
import { Test } from "forge-std/Test.sol";
Expand All @@ -13,6 +12,8 @@ import { NestStaking } from "../src/NestStaking.sol";
import { IComponentToken } from "../src/interfaces/IComponentToken.sol";
import { AggregateTokenProxy } from "../src/proxy/AggregateTokenProxy.sol";
import { NestStakingProxy } from "../src/proxy/NestStakingProxy.sol";

import { pUSDProxy } from "../src/proxy/pUSDProxy.sol";
import { pUSD } from "../src/token/pUSD.sol";

// Concrete implementation of ComponentToken
Expand Down Expand Up @@ -43,7 +44,6 @@ contract DeployNestContracts is Script, Test {

function run() external {
vm.startBroadcast(NEST_ADMIN_ADDRESS);
ERC1967Proxy pUSDProxy = ERC1967Proxy(payable(PUSD_ADDRESS));

AggregateToken aggregateToken = new AggregateToken();
AggregateTokenProxy aggregateTokenProxy = new AggregateTokenProxy(
Expand All @@ -52,9 +52,9 @@ contract DeployNestContracts is Script, Test {
AggregateToken.initialize,
(
NEST_ADMIN_ADDRESS,
"Nest Insto Vault",
"NIV",
IComponentToken(address(pUSDProxy)),
"Nest RWA Vault",
"nRWA",
IComponentToken(PUSD_ADDRESS),
1e17, // ask price
1e17 // bid price
)
Expand Down
4 changes: 3 additions & 1 deletion nest/script/UpgradeNestContracts.s.sol
Original file line number Diff line number Diff line change
Expand Up @@ -14,11 +14,13 @@ import { AggregateTokenProxy } from "../src/proxy/AggregateTokenProxy.sol";
contract UpgradeNestContracts is Script, Test {

address private constant NEST_ADMIN_ADDRESS = 0xb015762405De8fD24d29A6e0799c12e0Ea81c1Ff;
address private constant BORING_VAULT_ADDRESS = 0xe644F07B1316f28a7F134998e021eA9f7135F351;

UUPSUpgradeable private constant AGGREGATE_TOKEN_PROXY =
UUPSUpgradeable(payable(0x659619AEdf381c3739B0375082C2d61eC1fD8835));

// Add the component token addresses
address private constant ASSET_TOKEN = 0xF66DFD0A9304D3D6ba76Ac578c31C84Dc0bd4A00;
address private constant ASSET_TOKEN = 0x2DEc3B6AdFCCC094C31a2DCc83a43b5042220Ea2;

// LiquidContinuousMultiTokenVault - Credbull
address private constant COMPONENT_TOKEN = 0x4B1fC984F324D2A0fDD5cD83925124b61175f5C6;
Expand Down
11 changes: 7 additions & 4 deletions nest/script/UpgradepUSD.s.sol
Original file line number Diff line number Diff line change
Expand Up @@ -5,15 +5,14 @@ import { UUPSUpgradeable } from "@openzeppelin/contracts-upgradeable/proxy/utils
import { ERC1967Utils } from "@openzeppelin/contracts/proxy/ERC1967/ERC1967Utils.sol";

import { Script } from "forge-std/Script.sol";
import { Test } from "forge-std/Test.sol";
import { console2 } from "forge-std/console2.sol";

import { pUSDProxy } from "../src/proxy/pUSDProxy.sol";
import { pUSD } from "../src/token/pUSD.sol";

import { IERC20 } from "@openzeppelin/contracts/interfaces/IERC20.sol";

contract UpgradePUSD is Script, Test {
contract UpgradePUSD is Script {

// Constants
address private constant ADMIN_ADDRESS = 0xb015762405De8fD24d29A6e0799c12e0Ea81c1Ff;
Expand All @@ -35,6 +34,9 @@ contract UpgradePUSD is Script, Test {
uint256 public currentTotalSupply;
bool public isConnected;

// small hack to be excluded from coverage report
function test() public { }

function setUp() public {
// Try to read implementation slot from proxy, this only works with RPC
try vm.load(PUSD_PROXY, ERC1967Utils.IMPLEMENTATION_SLOT) returns (bytes32 implementation) {
Expand All @@ -56,12 +58,13 @@ contract UpgradePUSD is Script, Test {
console2.log("Vault:", currentVault);
console2.log("Total Supply:", currentTotalSupply);
} else {
vm.skip(true);
//TODO: Check this again
vm.skip(false);
isConnected = false;
}
} catch {
console2.log("No implementation found - skipping");
vm.skip(true);
vm.skip(false);
isConnected = false;
}
}
Expand Down
101 changes: 98 additions & 3 deletions nest/src/AggregateToken.sol
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.25;

import { ERC4626Upgradeable } from "@openzeppelin/contracts-upgradeable/token/ERC20/extensions/ERC4626Upgradeable.sol";
import { IERC20 } from "@openzeppelin/contracts/interfaces/IERC20.sol";
import { IERC4626 } from "@openzeppelin/contracts/interfaces/IERC4626.sol";
import { ERC1155Holder } from "@openzeppelin/contracts/token/ERC1155/utils/ERC1155Holder.sol";
Expand Down Expand Up @@ -55,6 +56,9 @@ contract AggregateToken is ComponentToken, IAggregateToken, ERC1155Holder {
/// @notice Emitted when the AggregateToken contract is unpaused for deposits
event Unpaused();

/// @notice Emitted when the asset token is updated
event AssetTokenUpdated(IERC20 indexed oldAsset, IERC20 indexed newAsset);

// Errors

/**
Expand All @@ -63,6 +67,9 @@ contract AggregateToken is ComponentToken, IAggregateToken, ERC1155Holder {
*/
error ComponentTokenAlreadyListed(IComponentToken componentToken);

/// @notice Emitted when a ComponentToken is removed from the component token list
event ComponentTokenRemoved(IComponentToken indexed componentToken);

/**
* @notice Indicates a failure because the ComponentToken is not in the component token list
* @param componentToken ComponentToken that is not in the component token list
Expand Down Expand Up @@ -124,7 +131,7 @@ contract AggregateToken is ComponentToken, IAggregateToken, ERC1155Holder {
uint256 askPrice,
uint256 bidPrice
) public initializer {
super.initialize(owner, name, symbol, IERC20(address(asset_)), false, false);
super.initialize(owner, name, symbol, IERC20(address(asset_)), false, true);

AggregateTokenStorage storage $ = _getAggregateTokenStorage();
$.componentTokenList.push(asset_);
Expand Down Expand Up @@ -166,19 +173,72 @@ contract AggregateToken is ComponentToken, IAggregateToken, ERC1155Holder {
uint256 assets,
address receiver,
address controller
) public override(ComponentToken, IComponentToken) returns (uint256 shares) {
) public override(ComponentToken, IComponentToken) nonReentrant returns (uint256 shares) {
if (_getAggregateTokenStorage().paused) {
revert DepositPaused();
}
return super.deposit(assets, receiver, controller);
}

/**
* @inheritdoc ERC4626Upgradeable
* @dev Overridden to add pause check before deposit
* @param assets Amount of assets to deposit
* @param receiver Address that will receive the shares
* @return shares Amount of shares minted
*/
function deposit(
uint256 assets,
address receiver
) public override(ERC4626Upgradeable, IERC4626) nonReentrant returns (uint256 shares) {
if (_getAggregateTokenStorage().paused) {
revert DepositPaused();
}
return super.deposit(assets, receiver);
}

/**
* @inheritdoc ComponentToken
* @dev Overridden to add pause check before minting
* @param shares Amount of shares to mint
* @param receiver Address that will receive the shares
* @param controller Address that controls the minting
* @return assets Amount of assets deposited
*/
function mint(
uint256 shares,
address receiver,
address controller
) public override(ComponentToken) nonReentrant returns (uint256 assets) {
if (_getAggregateTokenStorage().paused) {
revert DepositPaused();
}
return super.mint(shares, receiver, controller);
}

/**
* @inheritdoc ERC4626Upgradeable
* @dev Overridden to add pause check before minting
* @param shares Amount of shares to mint
* @param receiver Address that will receive the shares
* @return assets Amount of assets deposited
*/
function mint(
uint256 shares,
address receiver
) public override(ERC4626Upgradeable, IERC4626) nonReentrant returns (uint256 assets) {
if (_getAggregateTokenStorage().paused) {
revert DepositPaused();
}
return super.mint(shares, receiver);
}

/// @inheritdoc IComponentToken
function redeem(
uint256 shares,
address receiver,
address controller
) public override(ComponentToken, IComponentToken) returns (uint256 assets) {
) public override(ComponentToken, IComponentToken) nonReentrant returns (uint256 assets) {
return super.redeem(shares, receiver, controller);
}

Expand Down Expand Up @@ -223,6 +283,41 @@ contract AggregateToken is ComponentToken, IAggregateToken, ERC1155Holder {
emit ComponentTokenListed(componentToken);
}

/**
* @notice Remove a ComponentToken from the component token list
* @dev Only the owner can call this function. The ComponentToken must have zero balance to be removed.
* @param componentToken ComponentToken to remove
*/
function removeComponentToken(
IComponentToken componentToken
) external nonReentrant onlyRole(ADMIN_ROLE) {
AggregateTokenStorage storage $ = _getAggregateTokenStorage();

// Check if component token exists
if (!$.componentTokenMap[componentToken]) {
revert ComponentTokenNotListed(componentToken);
}

// Check if it's the current asset
if (address(componentToken) == asset()) {
revert ComponentTokenIsAsset(componentToken);
}

// Remove from mapping
$.componentTokenMap[componentToken] = false;

// Remove from array by finding and replacing with last element
for (uint256 i = 0; i < $.componentTokenList.length; i++) {
if ($.componentTokenList[i] == componentToken) {
$.componentTokenList[i] = $.componentTokenList[$.componentTokenList.length - 1];
$.componentTokenList.pop();
break;
}
}

emit ComponentTokenUnlisted(componentToken);
}

/**
* @notice Buy ComponentToken using `asset`
* @dev Only the owner can call this function, will revert if
Expand Down
Loading

0 comments on commit 09d2333

Please sign in to comment.