Skip to content

EVVM-org/ZkVaultService-contracts

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

3 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

ZkVaultService Contracts

Zero-knowledge vault service for shielded transfers on EVVM.

Overview

ShieldedPool enables privacy-preserving deposits and withdrawals using zkSNARK proofs. Users can deposit tokens into the pool to receive a commitment, then withdraw to any address using zero-knowledge proofs that verify the note exists without revealing the source.

Key Features

  • Deposit: Lock tokens into the pool, receive a shielded commitment
  • Transfer: Move funds between commitments privately
  • Split: Split one commitment into up to four new commitments
  • Withdraw: Withdraw to any address using zk proofs

Architecture

User -> [Deposit] -> ShieldedPool -> Commitment
                         |
                    [Transfer/Split]
                         |
User <- [Withdraw] <- ShieldedPool

Contracts

Contract Purpose
ShieldedPool Main vault contract
WithdrawFromPoolVerifier Verifier for withdrawal proofs
SplitNoteVerifier Verifier for split proofs

Function Reference

deposit

Deposit tokens into the pool, creating a shielded commitment.

function deposit(
    address from,          // Token sender
    uint256 amount,       // Deposit amount
    bytes32 commitment,   // Shielded commitment (secret)
    address senderExecutor,  // EVVM executor for sender
    address originExecutor,   // EVVM executor for origin
    uint256 nonce,        // Nonce for authorization
    bytes signature,     // EIP-712 signature from sender
    uint256 priorityFeePay,   // Priority fee for payment
    uint256 noncePay,    // Nonce for payment tx
    bytes signaturePay   // EIP-712 signature for payment
)

Requirements:

  • amount > 0
  • commitment must be unique (not previously used)
  • Both signatures must be valid

Events: Emits Deposit(sender, commitment, amount)


transferIntent

Transfer between shielded commitments.

function transferIntent(
    address from,
    bytes32 expectedRoot,    // Merkle tree root to verify against
    bytes proof,             // ZK proof
    bytes32 nullifierIn,    // Nullifier for input note
    uint32 merkleProofLength, // Depth of merkle proof (1-10)
    bytes32 newCommitment,  // New shielded commitment
    address senderExecutor,
    address originExecutor,
    uint256 nonce,
    bytes signature
)

Requirements:

  • expectedRoot must be registered
  • nullifierIn must not be spent
  • merkleProofLength must be 1-10

Events: Emits TransferIntent(root, nullifier, newCommitment)


split

Split one commitment into up to four new commitments.

function split(
    address from,
    bytes32 expectedRoot,
    bytes32 nullifierIn,
    uint32 merkleProofLength,
    bytes32 newCommitment1,
    bytes32 newCommitment2,
    bytes32 newCommitment3,
    bytes32 newCommitment4,
    bytes proof,
    address senderExecutor,
    address originExecutor,
    uint256 nonce,
    bytes signature
)

Requirements:

  • Split verifier must be configured (address(0) check)
  • All other requirements same as transferIntent

Events: Emits SplitIntent(root, nullifier, newCommitment1-4)


withdraw

Withdraw funds to any address using zk proof.

function withdraw(
    address from,
    bytes proof,                    // ZK proof
    bytes32[] publicInputs,        // 6 public inputs
    bytes32 ciphertext,            // Encrypted amount
    address senderExecutor,
    address originExecutor,
    uint256 nonce,
    bytes signature
)

Public Inputs (6):

[0] nullifierIn
[1] merkleProofLength
[2] expectedRoot
[3] recipient (cast to bytes32)
[4] padding
[5] decrypted amount

Requirements:

  • Withdraw verifier must be configured
  • publicInputs.length == 6
  • merkleProofLength must be 1-10
  • Root must be registered
  • Nullifier must not be spent
  • Recipient cannot be zero address
  • Amount must be > 0

Events: Emits Withdraw(recipient, nullifier)


setRootRelayer

Configure which addresses can register new Merkle roots.

function setRootRelayer(address relayer, bool allowed)

Access: Owner only


registerRoot

Register a new Merkle root for proof verification.

function registerRoot(bytes32 root)

Access: Registered root relayers only


Error Codes

Error Description
"not owner" Caller is not contract owner
"not root relayer" Caller is not registered relayer
"amount must be > 0" Deposit/withdraw amount is zero
"commitment already used" Commitment was already deposited
"root already known" Root is already registered
"unknown root" Root is not registered
"nullifier used" Nullifier was already spent
"invalid merkle depth" Merkle proof depth out of range
"invalid proof" ZK proof verification failed
"invalid recipient" Recipient is zero address
"invalid withdraw amount" Withdrawn amount is zero
"amount mismatch" Public amount doesn't match decrypted
"split not enabled" Split verifier not configured
"withdraw not enabled" Withdraw verifier not configured

Deployment

Prerequisites

  • Foundry installed
  • .env file configured

Environment Variables

# Required
DEPLOYER_PRIVATE_KEY=
EVVM_CORE_ADDRESS=
EVVM_STAKING_ADDRESS=
EVVM_USDC_TOKEN_ADDRESS=
ROOT_RELAYER_ADDRESS=
SEPOLIA_RPC_URL=

Deploy to Sepolia

forge script script/Deploy.s.sol:DeployScript --broadcast --rpc-url sepolia

Deploy to Other Networks

  1. Add RPC endpoint to foundry.toml:
[rpc_endpoints]
mainnet = "${MAINNET_RPC_URL}"
  1. Add to Deploy.s.sol or create network-specific script

  2. Run:

forge script script/Deploy.s.sol:DeployScript --broadcast --rpc-url mainnet

Post-Deployment

  1. Verify contracts on Etherscan:
forge verify-contract --compiler-version <version> <contract-address> <contract-name> --ETHERSCAN-API-KEY <key>
  1. Update deployment records (off-repo)

Building

# Install dependencies
npm install
cd noir && npm install

# Build contracts
npm run build

# Build Noir circuits
npm run noir:compile

# Export circuit artifacts
npm run noir:export

Testing

npm run test

License

EVVM Noncommercial License - See LICENSE for details.

About

No description, website, or topics provided.

Resources

Stars

Watchers

Forks

Releases

No releases published

Packages

 
 
 

Contributors