Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
87 changes: 46 additions & 41 deletions build/deployments-1.json
Original file line number Diff line number Diff line change
@@ -1,42 +1,47 @@
{
"executions": {
"001_CoreMainnet": 1723685111,
"002_UpgradeMainnet": 1726812322,
"003_UpgradeLidoARMScript": 1729073099,
"004_UpdateCrossPriceScript": 1739872139,
"005_RegisterLidoWithdrawalsScript": 1743500783,
"006_ChangeFeeCollector": 1751894483,
"007_UpgradeLidoARMMorphoScript": 1754407511,
"008_DeployPendleAdaptor": 1755770279,
"009_UpgradeLidoARMSetBufferScript": 1755692363,
"010_UpgradeLidoARMAssetScript": 1764755147,
"011_DeployEtherFiARMScript": 1761812927,
"012_UpgradeEtherFiARMScript": 1763557643,
"014_DeployEthenaARMScript": 1764664655,
"015_UpgradeEthenaARMScript": 1766319523
},
"contracts": {
"ARM_ZAPPER": "0xE11EDbd5AE4Fa434Af7f8D7F03Da1742996e7Ab2",
"ETHENA_ARM": "0xCEDa2d856238aA0D12f6329de20B9115f07C366d",
"ETHENA_ARM_CAP_IMPL": "0x7073F39ae371962C2469D72f01f907375bB11E08",
"ETHENA_ARM_CAP_MAN": "0x687AFB5A52A15122fD5FC54A8B52cfd58346fb0C",
"ETHENA_ARM_IMPL": "0x11E6bEe1662a2E2B20A7163CC33334fa1cf19979",
"ETHERFI_ARM_IMPL": "0x69b98667134EeE3eBF75799dacBCd604E28709ab",
"ETHER_FI_ARM": "0xfB0A3CF9B019BFd8827443d131b235B3E0FC58d2",
"ETHER_FI_ARM_CAP_IMPL": "0xe27720Fc3f3707D47015e274D81a99e5B0800472",
"ETHER_FI_ARM_CAP_MAN": "0xf2A18F7330141Ec737EB73A0A5Ea8E4d7e9bE7ec",
"ETHER_FI_ARM_IMPL": "0x00B53CEE151c043CBe4bbFe4cfD2938Cb4fabCEB",
"LIDO_ARM": "0x85B78AcA6Deae198fBF201c82DAF6Ca21942acc6",
"LIDO_ARM_CAP_IMPL": "0x8506486813d025C5935dF481E450e27D2e483dc9",
"LIDO_ARM_CAP_MAN": "0xf54ebff575f699d281645c6F14Fe427dFFE629CF",
"LIDO_ARM_IMPL": "0xC0297a0E39031F09406F0987C9D9D41c5dfbc3df",
"LIDO_ARM_ZAPPER": "0x01F30B7358Ba51f637d1aa05D9b4A60f76DAD680",
"MORPHO_MARKET_ETHERFI": "0x8Cf42b82fFFa3E7714D62a2cA223acBeC1Eef095",
"MORPHO_MARKET_ETHERFI_IMPL": "0x2a1b59870f7806E60dF58415B0C220C096f57658",
"MORPHO_MARKET_MEVCAPITAL": "0x29c4Bb7B1eBcc53e8CBd16480B5bAe52C69806D3",
"MORPHO_MARKET_MEVCAPITAL_IMP": "0x90c7ABC962f96de171ee395A242D2Ff794D0a04c",
"OETH_ARM": "0x6bac785889A4127dB0e0CeFEE88E0a9F1Aaf3cC7",
"OETH_ARM_IMPL": "0x187FfF686a5f42ACaaF56469FcCF8e6Feca18248",
"PENDLE_ORIGIN_ARM_SY": "0xbcae2Eb1cc47F137D8B2D351B0E0ea8DdA4C6184"
}
}
"executions": {
"001_CoreMainnet": 1723685111,
"002_UpgradeMainnet": 1726812322,
"003_UpgradeLidoARMScript": 1729073099,
"004_UpdateCrossPriceScript": 1739872139,
"005_RegisterLidoWithdrawalsScript": 1743500783,
"006_ChangeFeeCollector": 1751894483,
"007_UpgradeLidoARMMorphoScript": 1754407511,
"008_DeployPendleAdaptor": 1755770279,
"009_UpgradeLidoARMSetBufferScript": 1755692363,
"010_UpgradeLidoARMAssetScript": 1764755147,
"011_DeployEtherFiARMScript": 1761812927,
"012_UpgradeEtherFiARMScript": 1763557643,
"013_UpgradeOETHARMScript": 1765353455,
"014_DeployEthenaARMScript": 1764664655,
"015_UpgradeEthenaARMScript": 1766319523,
"016_UpdateLidoARMCrossPriceScript": 1767616727,
"017_DeployNewMorphoMarketForEtherFiARM": 1770197063
},
"contracts": {
"ARM_ZAPPER": "0xE11EDbd5AE4Fa434Af7f8D7F03Da1742996e7Ab2",
"ETHENA_ARM": "0xCEDa2d856238aA0D12f6329de20B9115f07C366d",
"ETHENA_ARM_CAP_IMPL": "0x7073F39ae371962C2469D72f01f907375bB11E08",
"ETHENA_ARM_CAP_MAN": "0x687AFB5A52A15122fD5FC54A8B52cfd58346fb0C",
"ETHENA_ARM_IMPL": "0x11E6bEe1662a2E2B20A7163CC33334fa1cf19979",
"ETHERFI_ARM_IMPL": "0x69b98667134EeE3eBF75799dacBCd604E28709ab",
"ETHER_FI_ARM": "0xfB0A3CF9B019BFd8827443d131b235B3E0FC58d2",
"ETHER_FI_ARM_CAP_IMPL": "0xe27720Fc3f3707D47015e274D81a99e5B0800472",
"ETHER_FI_ARM_CAP_MAN": "0xf2A18F7330141Ec737EB73A0A5Ea8E4d7e9bE7ec",
"ETHER_FI_ARM_IMPL": "0x00B53CEE151c043CBe4bbFe4cfD2938Cb4fabCEB",
"LIDO_ARM": "0x85B78AcA6Deae198fBF201c82DAF6Ca21942acc6",
"LIDO_ARM_CAP_IMPL": "0x8506486813d025C5935dF481E450e27D2e483dc9",
"LIDO_ARM_CAP_MAN": "0xf54ebff575f699d281645c6F14Fe427dFFE629CF",
"LIDO_ARM_IMPL": "0xC0297a0E39031F09406F0987C9D9D41c5dfbc3df",
"LIDO_ARM_ZAPPER": "0x01F30B7358Ba51f637d1aa05D9b4A60f76DAD680",
"MORPHO_MARKET_ETHERFI": "0xe776485B4A12d50503aF40DBEa519671318472Ed",
"MORPHO_MARKET_ETHERFI_IMPL": "0x20DC48008D4CC8988C7027bbd38e5ad6766e1d5D",
"MORPHO_MARKET_MEVCAPITAL": "0x29c4Bb7B1eBcc53e8CBd16480B5bAe52C69806D3",
"MORPHO_MARKET_MEVCAPITAL_IMP": "0x90c7ABC962f96de171ee395A242D2Ff794D0a04c",
"MORPHO_MARKET_ORIGIN": "0x0ad39D67404aE36Fe476eFDDE1306a5414383544",
"MORPHO_MARKET_ORIGIN_IMPL": "0x2ea9D1827973813D77aA8f35BD23cb1F1311A648",
"OETH_ARM": "0x6bac785889A4127dB0e0CeFEE88E0a9F1Aaf3cC7",
"OETH_ARM_IMPL": "0x9A2be51E45Eec98F75b3e6e1b334246c94663641",
"PENDLE_ORIGIN_ARM_SY": "0xbcae2Eb1cc47F137D8B2D351B0E0ea8DdA4C6184"
}
}
2 changes: 2 additions & 0 deletions script/deploy/DeployManager.sol
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,7 @@ import {UpgradeOETHARMScript} from "./mainnet/013_UpgradeOETHARMScript.sol";
import {DeployEthenaARMScript} from "./mainnet/014_DeployEthenaARMScript.sol";
import {UpgradeEthenaARMScript} from "./mainnet/015_UpgradeEthenaARMScript.sol";
import {UpgradeLidoARMCrossPriceScript} from "./mainnet/016_UpdateLidoARMCrossPriceScript.sol";
import {DeployNewMorphoMarketForEtherFiARM} from "./mainnet/017_DeployNewMorphoMarketForEtherFiARM.sol";
import {EmptyScript} from "./mainnet/999_empty.sol";

contract DeployManager is Script {
Expand Down Expand Up @@ -89,6 +90,7 @@ contract DeployManager is Script {
_runDeployFile(new DeployEthenaARMScript());
_runDeployFile(new UpgradeEthenaARMScript());
_runDeployFile(new UpgradeLidoARMCrossPriceScript());
_runDeployFile(new DeployNewMorphoMarketForEtherFiARM());
_runDeployFile(new EmptyScript());
} else if (block.chainid == 17000) {
// Holesky
Expand Down
47 changes: 47 additions & 0 deletions script/deploy/mainnet/017_DeployNewMorphoMarketForEtherFiARM.sol
Original file line number Diff line number Diff line change
@@ -0,0 +1,47 @@
// SPDX-License-Identifier: MIT
pragma solidity 0.8.23;

// Foundry imports
import {console} from "forge-std/console.sol";

// Contract imports
import {Proxy} from "contracts/Proxy.sol";
import {Mainnet} from "contracts/utils/Addresses.sol";
import {MorphoMarket} from "contracts/markets/MorphoMarket.sol";
import {Abstract4626MarketWrapper} from "contracts/markets/Abstract4626MarketWrapper.sol";

// Deployment imports
import {GovProposal, GovSixHelper} from "contracts/utils/GovSixHelper.sol";
import {AbstractDeployScript} from "../AbstractDeployScript.sol";

contract DeployNewMorphoMarketForEtherFiARM is AbstractDeployScript {
using GovSixHelper for GovProposal;

GovProposal public govProposal;

string public constant override DEPLOY_NAME = "017_DeployNewMorphoMarketForEtherFiARM";
bool public constant override proposalExecuted = false;

Proxy morphoMarketProxy;
MorphoMarket morphoMarket;

function _execute() internal override {
console.log("Deploy:", DEPLOY_NAME);
console.log("------------");

// 1. Deploy MorphoMarket proxy
morphoMarketProxy = new Proxy();
_recordDeploy("MORPHO_MARKET_ETHERFI", address(morphoMarketProxy));

// 2. Deploy MorphoMarket
morphoMarket = new MorphoMarket(Mainnet.ETHERFI_ARM, Mainnet.MORPHO_MARKET_OETH_VAULT);
_recordDeploy("MORPHO_MARKET_ETHERFI_IMPL", address(morphoMarket));
// 3. Initialize MorphoMarket proxy with the implementation, Timelock as owner
bytes memory data = abi.encodeWithSelector(
Abstract4626MarketWrapper.initialize.selector, Mainnet.STRATEGIST, Mainnet.MERKLE_DISTRIBUTOR
);
morphoMarketProxy.initialize(address(morphoMarket), Mainnet.TIMELOCK, data);

console.log("Finished deploying", DEPLOY_NAME);
}
}
1 change: 1 addition & 0 deletions src/contracts/utils/Addresses.sol
Original file line number Diff line number Diff line change
Expand Up @@ -60,6 +60,7 @@ library Mainnet {
address public constant MORPHO_MARKET_MEVCAPITAL = 0x9a8bC3B04b7f3D87cfC09ba407dCED575f2d61D8;
address public constant MORPHO_MARKET_ETHERFI = 0x4881Ef0BF6d2365D3dd6499ccd7532bcdBCE0658;
address public constant MORPHO_MARKET_YEARN_OG = 0xE89371eAaAC6D46d4C3ED23453241987916224FC;
address public constant MORPHO_MARKET_OETH_VAULT = 0x3Dfe70B05657949A5dB340754aD664810ac63b21;
// Apostro Ethena USDe is currently the only curated Morpho market that takes USDe
address public constant MORPHO_MARKET_ETHENA = 0x4EDfaB296F8Eb15aC0907CF9eCb7079b1679Da57;

Expand Down
3 changes: 3 additions & 0 deletions test/smoke/EthenaARMSmokeTest.t.sol
Original file line number Diff line number Diff line change
Expand Up @@ -212,6 +212,7 @@ contract Fork_EthenaARM_Smoke_Test is AbstractSmokeTest {
_swapExactTokensForTokens(susde, usde, 0.998e36, 100 ether);

// Operator requests an Ethena withdrawal
skip(ethenaARM.DELAY_REQUEST() + 1);
vm.prank(Mainnet.ARM_RELAYER);
ethenaARM.requestBaseWithdrawal(10 ether);
}
Expand All @@ -221,6 +222,7 @@ contract Fork_EthenaARM_Smoke_Test is AbstractSmokeTest {
_swapExactTokensForTokens(susde, usde, 0.998e36, 100 ether);

// Owner requests an Ethena withdrawal
skip(ethenaARM.DELAY_REQUEST() + 1);
vm.prank(Mainnet.TIMELOCK);
ethenaARM.requestBaseWithdrawal(10 ether);
}
Expand All @@ -231,6 +233,7 @@ contract Fork_EthenaARM_Smoke_Test is AbstractSmokeTest {

// Owner requests an Ethena withdrawal
uint256 nextUnstakerIndex = ethenaARM.nextUnstakerIndex();
skip(ethenaARM.DELAY_REQUEST() + 1);
vm.prank(Mainnet.TIMELOCK);
ethenaARM.requestBaseWithdrawal(10 ether);

Expand Down
78 changes: 77 additions & 1 deletion test/smoke/EtherFiARMSmokeTest.t.sol
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ pragma solidity ^0.8.23;

import {AbstractSmokeTest} from "./AbstractSmokeTest.sol";

import {IERC20, IEETHWithdrawalNFT} from "contracts/Interfaces.sol";
import {IERC20, IERC4626, IEETHWithdrawalNFT} from "contracts/Interfaces.sol";
import {EtherFiARM} from "contracts/EtherFiARM.sol";
import {CapManager} from "contracts/CapManager.sol";
import {Proxy} from "contracts/Proxy.sol";
Expand All @@ -19,6 +19,7 @@ contract Fork_EtherFiARM_Smoke_Test is AbstractSmokeTest {
EtherFiARM etherFiARM;
CapManager capManager;
IEETHWithdrawalNFT etherfiWithdrawalNFT;
IERC4626 morphoMarket;
address operator;

function setUp() public {
Expand All @@ -34,6 +35,7 @@ contract Fork_EtherFiARM_Smoke_Test is AbstractSmokeTest {
etherFiARM = EtherFiARM(payable(deployManager.getDeployment("ETHER_FI_ARM")));
capManager = CapManager(deployManager.getDeployment("ETHER_FI_ARM_CAP_MAN"));
etherfiWithdrawalNFT = IEETHWithdrawalNFT(Mainnet.ETHERFI_WITHDRAWAL_NFT);
morphoMarket = IERC4626(deployManager.getDeployment("MORPHO_MARKET_ETHERFI"));

vm.prank(etherFiARM.owner());
etherFiARM.setOwner(Mainnet.TIMELOCK);
Expand Down Expand Up @@ -253,4 +255,78 @@ contract Fork_EtherFiARM_Smoke_Test is AbstractSmokeTest {
requestIdArray[0] = requestId;
etherFiARM.claimEtherFiWithdrawals(requestIdArray);
}

/* Lending Market Allocation Tests */

function test_allocate_to_lending_market() external {
// Add and set the active market to the Morpho market
vm.startPrank(Mainnet.TIMELOCK);
if (!etherFiARM.supportedMarkets(address(morphoMarket))) {
address[] memory markets = new address[](1);
markets[0] = address(morphoMarket);
etherFiARM.addMarkets(markets);
}
etherFiARM.setActiveMarket(address(morphoMarket));
vm.stopPrank();

// Deal WETH to the ARM
deal(address(weth), address(etherFiARM), 100 ether);

uint256 armWethBefore = weth.balanceOf(address(etherFiARM));
uint256 marketBalanceBefore = morphoMarket.maxWithdraw(address(etherFiARM));

// Set buffer to 0% so all liquidity goes to the lending market
vm.prank(Mainnet.ARM_RELAYER);
etherFiARM.setARMBuffer(0);

// Allocate liquidity to the lending market
vm.prank(Mainnet.ARM_RELAYER);
(, int256 actualDelta) = etherFiARM.allocate();

uint256 armWethAfter = weth.balanceOf(address(etherFiARM));
uint256 marketBalanceAfter = morphoMarket.maxWithdraw(address(etherFiARM));

// Verify liquidity moved to the lending market
assertGt(actualDelta, 0, "Actual delta should be positive (deposited to market)");
assertLt(armWethAfter, armWethBefore, "ARM WETH balance should decrease");
assertGt(marketBalanceAfter, marketBalanceBefore, "Market balance should increase");
}

function test_allocate_from_lending_market() external {
// Add and set the active market to the Morpho market
vm.startPrank(Mainnet.TIMELOCK);
if (!etherFiARM.supportedMarkets(address(morphoMarket))) {
address[] memory markets = new address[](1);
markets[0] = address(morphoMarket);
etherFiARM.addMarkets(markets);
}
etherFiARM.setActiveMarket(address(morphoMarket));
vm.stopPrank();

// Deal WETH to the ARM and allocate to market with buffer at 0%
deal(address(weth), address(etherFiARM), 100 ether);
vm.prank(Mainnet.ARM_RELAYER);
etherFiARM.setARMBuffer(0);
vm.prank(Mainnet.ARM_RELAYER);
etherFiARM.allocate();

uint256 armWethBefore = weth.balanceOf(address(etherFiARM));
uint256 marketBalanceBefore = morphoMarket.maxWithdraw(address(etherFiARM));

// Set buffer to 100% so liquidity comes back from the lending market
vm.prank(Mainnet.ARM_RELAYER);
etherFiARM.setARMBuffer(1e18);

// Allocate liquidity from the lending market
vm.prank(Mainnet.ARM_RELAYER);
(, int256 actualDelta) = etherFiARM.allocate();

uint256 armWethAfter = weth.balanceOf(address(etherFiARM));
uint256 marketBalanceAfter = morphoMarket.maxWithdraw(address(etherFiARM));

// Verify liquidity moved from the lending market (as much as available)
assertLt(actualDelta, 0, "Actual delta should be negative (withdrawn from market)");
assertGt(armWethAfter, armWethBefore, "ARM WETH balance should increase");
assertLe(marketBalanceAfter, marketBalanceBefore, "Market balance should decrease or stay same");
}
}
78 changes: 77 additions & 1 deletion test/smoke/LidoARMSmokeTest.t.sol
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ pragma solidity ^0.8.23;

import {AbstractSmokeTest} from "./AbstractSmokeTest.sol";

import {IERC20, IStETHWithdrawal} from "contracts/Interfaces.sol";
import {IERC20, IERC4626, IStETHWithdrawal} from "contracts/Interfaces.sol";
import {LidoARM} from "contracts/LidoARM.sol";
import {CapManager} from "contracts/CapManager.sol";
import {Proxy} from "contracts/Proxy.sol";
Expand All @@ -18,6 +18,7 @@ contract Fork_LidoARM_Smoke_Test is AbstractSmokeTest {
Proxy proxy;
LidoARM lidoARM;
CapManager capManager;
IERC4626 morphoMarket;
address operator;

function setUp() public {
Expand All @@ -32,6 +33,7 @@ contract Fork_LidoARM_Smoke_Test is AbstractSmokeTest {
proxy = Proxy(payable(deployManager.getDeployment("LIDO_ARM")));
lidoARM = LidoARM(payable(deployManager.getDeployment("LIDO_ARM")));
capManager = CapManager(deployManager.getDeployment("LIDO_ARM_CAP_MAN"));
morphoMarket = IERC4626(deployManager.getDeployment("MORPHO_MARKET_MEVCAPITAL"));

// Only fuzz from this address. Big speedup on fork.
targetSender(address(this));
Expand Down Expand Up @@ -229,4 +231,78 @@ contract Fork_LidoARM_Smoke_Test is AbstractSmokeTest {

assertEq(totalAmountRequested, lidoARM.lidoWithdrawalQueueAmount());
}

/* Lending Market Allocation Tests */

function test_allocate_to_lending_market() external {
// Add and set the active market to the Morpho market
vm.startPrank(Mainnet.TIMELOCK);
if (!lidoARM.supportedMarkets(address(morphoMarket))) {
address[] memory markets = new address[](1);
markets[0] = address(morphoMarket);
lidoARM.addMarkets(markets);
}
lidoARM.setActiveMarket(address(morphoMarket));
vm.stopPrank();

// Deal WETH to the ARM
deal(address(weth), address(lidoARM), 100 ether);

uint256 armWethBefore = weth.balanceOf(address(lidoARM));
uint256 marketBalanceBefore = morphoMarket.maxWithdraw(address(lidoARM));

// Set buffer to 0% so all liquidity goes to the lending market
vm.prank(Mainnet.ARM_RELAYER);
lidoARM.setARMBuffer(0);

// Allocate liquidity to the lending market
vm.prank(Mainnet.ARM_RELAYER);
(, int256 actualDelta) = lidoARM.allocate();

uint256 armWethAfter = weth.balanceOf(address(lidoARM));
uint256 marketBalanceAfter = morphoMarket.maxWithdraw(address(lidoARM));

// Verify liquidity moved to the lending market
assertGt(actualDelta, 0, "Actual delta should be positive (deposited to market)");
assertLt(armWethAfter, armWethBefore, "ARM WETH balance should decrease");
assertGt(marketBalanceAfter, marketBalanceBefore, "Market balance should increase");
}

function test_allocate_from_lending_market() external {
// Add and set the active market to the Morpho market
vm.startPrank(Mainnet.TIMELOCK);
if (!lidoARM.supportedMarkets(address(morphoMarket))) {
address[] memory markets = new address[](1);
markets[0] = address(morphoMarket);
lidoARM.addMarkets(markets);
}
lidoARM.setActiveMarket(address(morphoMarket));
vm.stopPrank();

// Deal WETH to the ARM and allocate to market with buffer at 0%
deal(address(weth), address(lidoARM), 100 ether);
vm.prank(Mainnet.ARM_RELAYER);
lidoARM.setARMBuffer(0);
vm.prank(Mainnet.ARM_RELAYER);
lidoARM.allocate();

uint256 armWethBefore = weth.balanceOf(address(lidoARM));
uint256 marketBalanceBefore = morphoMarket.maxWithdraw(address(lidoARM));

// Set buffer to 100% so liquidity comes back from the lending market
vm.prank(Mainnet.ARM_RELAYER);
lidoARM.setARMBuffer(1e18);

// Allocate liquidity from the lending market
vm.prank(Mainnet.ARM_RELAYER);
(, int256 actualDelta) = lidoARM.allocate();

uint256 armWethAfter = weth.balanceOf(address(lidoARM));
uint256 marketBalanceAfter = morphoMarket.maxWithdraw(address(lidoARM));

// Verify liquidity moved from the lending market (as much as available)
assertLt(actualDelta, 0, "Actual delta should be negative (withdrawn from market)");
assertGt(armWethAfter, armWethBefore, "ARM WETH balance should increase");
assertLe(marketBalanceAfter, marketBalanceBefore, "Market balance should decrease or stay same");
}
}
Loading
Loading