Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
30 commits
Select commit Hold shift + click to select a range
686b3b5
Implement VedaAdapter
MoMannn Mar 2, 2026
89e74c4
basic boring on chain queue implementation
MoMannn Mar 6, 2026
7dc2245
Move to arbitrum mainnet tests, implement new deposit function, remov…
MoMannn Mar 30, 2026
b0a56ed
Clean up docs, add batch events
MoMannn Mar 30, 2026
5af6309
add arbitrum rpc to tests
MoMannn Mar 30, 2026
0f8ee51
set API key in tests
MoMannn Mar 30, 2026
25a8c19
add veda deployment script
MoMannn Mar 30, 2026
7b3fb1d
Remove NotLeafDelegator check and add security consideration
MoMannn Mar 31, 2026
c022400
optimize inputs and add docs regarding senity check inputs
MoMannn Apr 2, 2026
57120d5
additional tests and code optimization
MoMannn Apr 2, 2026
4deb901
linter + fetching from latest block
MoMannn Apr 2, 2026
d3338bb
Merge branch 'main' into chore-veda-adapter
MoMannn Apr 2, 2026
57b5b88
move deploy script to .env variables
MoMannn Apr 5, 2026
e412baf
fix teller docs
MoMannn Apr 5, 2026
801ab0d
remove unnecesarry caller variable
MoMannn Apr 5, 2026
16edf2a
update docs
MoMannn Apr 5, 2026
51f1654
Update approval logic to unlimited
MoMannn Apr 5, 2026
01be197
Merge branch 'chore-veda-adapter' of https://github.com/MetaMask/dele…
MoMannn Apr 5, 2026
1f1182e
Use calldata instead of memory for external function array parameters
MoMannn Apr 9, 2026
adb6c64
Eliminate single-use encodedTransfer_ local variable
MoMannn Apr 9, 2026
231e1de
Fix _ensureAllowance
MoMannn Apr 9, 2026
aba8aa5
fixate veda adapter deposit / withdrawal token in constructor
MoMannn Apr 9, 2026
6301f8c
Merge branch 'main' of https://github.com/MetaMask/delegation-framewo…
MoMannn Apr 20, 2026
077acc4
add veda adapter audit
MoMannn Apr 21, 2026
edf55c3
gas optimization - max approve in constructor
MoMannn Apr 21, 2026
f0c77d1
add monad specific deployment changes
MoMannn May 4, 2026
ede87fa
Merge branch 'main' into chore-veda-adapter
MoMannn May 19, 2026
972d2c9
remove unnecessary parameter from event
MoMannn May 20, 2026
d6fe82a
Merge branch 'chore-veda-adapter' of https://github.com/MetaMask/dele…
MoMannn May 20, 2026
e2227ef
Veda adapter deployment
MoMannn May 29, 2026
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
4 changes: 4 additions & 0 deletions .env.example
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,10 @@ META_SWAP_ADAPTER_OWNER_ADDRESS=
METASWAP_ADDRESS=
SWAPS_API_SIGNER_ADDRESS=
ARGS_EQUALITY_CHECK_ENFORCER_ADDRESS=
VEDA_ADAPTER_OWNER_ADDRESS=
VEDA_BORING_VAULT_ADDRESS=
VEDA_TELLER_ADDRESS=
VEDA_DEPOSIT_TOKEN_ADDRESS=

# Required for verifying contracts
ETHERSCAN_API_KEY=
Expand Down
2 changes: 2 additions & 0 deletions .github/workflows/test.yml
Original file line number Diff line number Diff line change
Expand Up @@ -51,3 +51,5 @@ jobs:
run: forge test -vvv
env:
LINEA_RPC_URL: ${{ secrets.LINEA_RPC_URL }}
ARBITRUM_RPC_URL: ${{ secrets.ARBITRUM_RPC_URL }}
RPC_API_KEY: ${{ secrets.RPC_API_KEY }}
Binary file added audits/cyfrin/cyfrin-4-26.pdf
Binary file not shown.
85 changes: 85 additions & 0 deletions broadcast/DeployVedaAdapter.s.sol/143/run-1780040823916.json

Large diffs are not rendered by default.

85 changes: 85 additions & 0 deletions broadcast/DeployVedaAdapter.s.sol/143/run-latest.json

Large diffs are not rendered by default.

63 changes: 63 additions & 0 deletions script/DeployVedaAdapter.s.sol
Original file line number Diff line number Diff line change
@@ -0,0 +1,63 @@
// SPDX-License-Identifier: MIT AND Apache-2.0
pragma solidity 0.8.23;

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

import { VedaAdapter } from "../src/helpers/VedaAdapter.sol";

/**
* @title DeployVedaAdapter
* @notice Deploys the VedaAdapter contract.
* @dev Fill the required variables in the .env file
* @dev run the script with:
* forge script script/DeployVedaAdapter.s.sol --rpc-url <your_rpc_url> --private-key $PRIVATE_KEY --broadcast
* For deploying on monad add --skip-simulation, because of how monad works the simulation fails because the token is not activated.
*/
contract DeployVedaAdapter is Script {
bytes32 salt;
address deployer;
address vedaAdapterOwner;
address delegationManager;
address boringVault;
address vedaTeller;
address depositToken;

function setUp() public {
salt = bytes32(abi.encodePacked(vm.envString("SALT")));
vedaAdapterOwner = vm.envAddress("VEDA_ADAPTER_OWNER_ADDRESS");
delegationManager = vm.envAddress("DELEGATION_MANAGER_ADDRESS");
boringVault = vm.envAddress("VEDA_BORING_VAULT_ADDRESS");
vedaTeller = vm.envAddress("VEDA_TELLER_ADDRESS");
depositToken = vm.envAddress("VEDA_DEPOSIT_TOKEN_ADDRESS");
deployer = msg.sender;
console2.log("~~~");
console2.log("Owner: %s", vedaAdapterOwner);
console2.log("DelegationManager: %s", delegationManager);
console2.log("BoringVault: %s", boringVault);
console2.log("VedaTeller: %s", vedaTeller);
console2.log("DepositToken: %s", depositToken);
console2.log("Deployer: %s", deployer);
console2.log("Salt:");
console2.logBytes32(salt);
}

function run() public {
console2.log("~~~");

// Foundry's fork mode cannot interact with mUSD on Monad (NotActivated in revm).
// Mock the approve call so simulation passes; the real broadcast executes the
// actual constructor on-chain where the token works correctly.
// vm.mockCall(depositToken, abi.encodeWithSelector(bytes4(keccak256("approve(address,uint256)"))), abi.encode(true));

vm.startBroadcast();

address vedaAdapter =
address(new VedaAdapter{ salt: salt }(vedaAdapterOwner, delegationManager, boringVault, vedaTeller, depositToken));
console2.log("VedaAdapter: %s", vedaAdapter);

vm.stopBroadcast();

// vm.clearMockedCalls();
}
}
399 changes: 399 additions & 0 deletions src/helpers/VedaAdapter.sol

Large diffs are not rendered by default.

74 changes: 74 additions & 0 deletions src/helpers/interfaces/IVedaTeller.sol
Original file line number Diff line number Diff line change
@@ -0,0 +1,74 @@
// Based on:
// https://github.com/Se7en-Seas/boring-vault/blob/main/src/base/Roles/TellerWithMultiAssetSupport.sol
// https://github.com/Veda-Labs/boring-vault/blob/dev/oct-2025/src/base/Roles/TellerWithYieldStreaming.sol

// SPDX-License-Identifier: MIT AND Apache-2.0
pragma solidity 0.8.23;

/**
* @title IVedaTeller
* @notice Interface for the user-facing functions of Veda's TellerWithMultiAssetSupport.
* @dev Uses `address` for asset parameters to avoid importing Solmate's ERC20.
* The Teller is the entry/exit point for the BoringVault. All functions use `requiresAuth`,
* so callers must be authorized on the Teller's Authority.
*/
interface IVedaTeller {
/**
* @notice Allows users to deposit into the BoringVault, if the contract is not paused.
* @dev Shares are minted to `msg.sender`. A share lock period may apply.
* @param depositAsset The ERC20 token to deposit
* @param depositAmount The amount to deposit
* @param minimumMint The minimum shares the user expects to receive
* @param referralAddress Address used for referral tracking
* @return shares The number of vault shares minted
*/
function deposit(
address depositAsset,
uint256 depositAmount,
uint256 minimumMint,
address referralAddress
)
external
payable
returns (uint256 shares);

/**
* @notice Allows an authorized caller to deposit into the BoringVault for another address, if this contract is not paused.
Comment thread
MoMannn marked this conversation as resolved.
* @dev Intended for router-like integrations; this selector should remain role-gated.
* @param depositAsset The ERC20 token to deposit
* @param depositAmount The amount to deposit
* @param minimumMint The minimum shares the user expects to receive
* @param to The address that will receive the minted vault shares
* @param referralAddress Address used for referral tracking
* @return shares The number of vault shares minted
*/
function deposit(
address depositAsset,
uint256 depositAmount,
uint256 minimumMint,
address to,
address referralAddress
)
external
payable
returns (uint256 shares);

/**
* @notice Allows users to withdraw from the BoringVault.
* @dev Available on TellerWithYieldStreaming. Burns shares from `msg.sender` and sends
* underlying assets to `to`. Updates vested yield before withdrawal.
* @param withdrawAsset The ERC20 token to receive
* @param shareAmount The amount of vault shares to burn
* @param minimumAssets The minimum underlying assets expected
* @param to The address that will receive the underlying assets
* @return assetsOut The amount of underlying assets sent
*/
function withdraw(
address withdrawAsset,
uint256 shareAmount,
uint256 minimumAssets,
address to
)
external
returns (uint256 assetsOut);
}
Loading
Loading