> ## Documentation Index
> Fetch the complete documentation index at: https://docs.eco.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Vaults & resource locks

> Every intent has its own deterministic vault. Funds are non-custodial, released only by cryptographic proof of fulfillment, or refunded automatically on expiry.

A **Vault** is a per-intent escrow contract that holds reward tokens until execution is proven. Every intent gets its own vault, deployed deterministically via CREATE2. There is no shared protocol account. There are no admin keys.

## Why per-intent vaults

Two consequences make the design useful:

**Funding is just a transfer.** The vault address can be computed offchain from the intent hash. Cold wallets, hardware devices, multisigs, exchanges, and PSPs can fund an intent with a standard ERC-20 `transfer` to the vault, no EIP-712 signature, no permit, no contract interaction.

**Funds release only on proof.** No private key controls withdrawal. The source-chain Portal will only release funds after a registered prover confirms fulfillment. If the deadline passes without fulfillment, a permissionless refund service returns the funds to the depositor.

## Resource locks vs escrow

The vault model is sometimes called a **resource lock**: instead of escrowing funds in a shared protocol account, each operation reserves its own resource container. This eliminates protocol-level risk concentration and lets the funding flow look exactly like a payment.

| Pooled escrow                                  | Per-intent vault                     |
| ---------------------------------------------- | ------------------------------------ |
| One contract holds all reward tokens           | One vault per intent                 |
| Trust the protocol's accounting                | Trust the proof                      |
| Funding requires interaction with the protocol | Funding is a vanilla ERC-20 transfer |
| Bug in escrow contract → all users affected    | Bug in vault → bounded to one intent |

## Determinism in practice

```
vaultAddress = CREATE2(
  portalAddress,
  intentHash,           // salt
  keccak256(initCode)
)
```

Because the vault address is a deterministic function of the intent hash, an application can:

* Display "Send USDC to `0xVaultAddr`" before the intent is even published
* Pre-fund a vault, then publish the intent later when ready
* Verify funding by checking onchain balance, with no protocol coupling
