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

# EVM

> Implement atomic swaps on EVM-compatible blockchains using smart contracts

## Contract architecture

Garden uses Hashed Time Lock Contracts (HTLCs) to implement atomic swap functionality on EVM chains. The contract manages the lifecycle of a swap through four main operations with enhanced signature support and flexible initiation methods:

<CardGroup cols={4}>
  <Card title="Initiate" icon="play" href="#initiate" />

  <Card title="Redeem" icon="check" href="#redeem" />

  <Card title="Refund" icon="rotate-left" href="#refund" />

  <Card title="Instant refund" icon="bolt" href="#instant-refund" />
</CardGroup>

## Core functions

### Initiate

The initiate function creates a new HTLC by locking tokens in the contract. EVM provides different implementations for ERC20 tokens vs. native ETH:

#### Basic initiation

<CodeGroup>
  ```solidity ERC20 theme={null}
  function initiate(
      address redeemer,
      uint256 timelock,
      uint256 amount,
      bytes32 secretHash
  ) external
  ```

  ```solidity Native ETH theme={null}
  function initiate(
      address payable redeemer,
      uint256 timelock,
      uint256 amount,
      bytes32 secretHash
  ) external payable
  ```
</CodeGroup>

#### Initiation on behalf

<CodeGroup>
  ```solidity ERC20 theme={null}
  function initiateOnBehalf(
      address initiator,
      address redeemer,
      uint256 timelock,
      uint256 amount,
      bytes32 secretHash
  ) external
  ```

  ```solidity Native ETH theme={null}
  function initiateOnBehalf(
      address payable initiator,
      address payable redeemer,
      uint256 timelock,
      uint256 amount,
      bytes32 secretHash
  ) external payable
  ```
</CodeGroup>

#### Signature-based initiation (ERC20 only)

```solidity theme={null}
function initiateWithSignature(
    address initiator,
    address redeemer,
    uint256 timelock,
    uint256 amount,
    bytes32 secretHash,
    bytes calldata signature
) external
```

<Note>
  Uses EIP712 signatures for off-chain authorization, enabling gasless transactions where authorized third parties can initiate swaps on behalf of users.
</Note>

### Redeem

The redeem function allows the redeemer to claim the locked tokens by providing the secret that hashes to the stored secret hash.

<CodeGroup>
  ```solidity ERC20 theme={null}
  function redeem(
      bytes32 orderID,
      bytes calldata secret
  ) external
  ```

  ```solidity Native ETH theme={null}
  function redeem(
      bytes32 orderID,
      bytes calldata secret
  ) external
  ```
</CodeGroup>

<Info>
  The secret must hash to the exact value stored during initiation using SHA256. Once revealed, this secret enables the counterparty to claim funds on the other chain. No signature required - anyone can execute if they know the secret.
</Info>

### Refund

The refund function allows the initiator to reclaim their tokens after the timelock has expired and the redeemer has not claimed the funds.

<CodeGroup>
  ```solidity ERC20 theme={null}
  function refund(bytes32 orderID) external
  ```

  ```solidity Native ETH theme={null}
  function refund(bytes32 orderID) external
  ```
</CodeGroup>

<Note>
  Uses absolute block numbers for timelock, which provides predictable settlement windows based on consistent block production times.
</Note>

### Instant refund

The instant refund function provides a way for the redeemer to consent to canceling the swap before the timelock expires using EIP712 signatures.

<CodeGroup>
  ```solidity ERC20 theme={null}
  function instantRefund(
      bytes32 orderID,
      bytes calldata signature
  ) external
  ```

  ```solidity Native ETH theme={null}
  function instantRefund(
      bytes32 orderID,
      bytes calldata signature
  ) external
  ```
</CodeGroup>

<Note>
  This requires the redeemer's EIP712 signature to prevent unauthorized instant refunds. This ensures mutual consent before the settlement window expires.
</Note>

## EVM-specific features

### Order state management

Both contracts use a struct to store swap state with different address types for native vs. ERC20 handling:

<CodeGroup>
  ```solidity ERC20 theme={null}
  struct Order {
      address initiator;
      address redeemer;
      uint256 initiatedAt;
      uint256 timelock;
      uint256 amount;
      uint256 fulfilledAt;
  }
  ```

  ```solidity Native ETH theme={null}
  struct Order {
      address payable initiator;
      address payable redeemer;
      uint256 initiatedAt;
      uint256 timelock;
      uint256 amount;
      uint256 fulfilledAt;
  }
  ```
</CodeGroup>

### Token handling differences

**ERC20 implementation:**

* Uses SafeERC20 for secure token transfers.
* Requires token approval before initiation.
* Transfers tokens via `transferFrom` and `transfer`.

**Native ETH implementation:**

* Uses `payable` functions and `msg.value`.
* Direct ETH transfers via `.transfer()`.
* No approval required.

<Tip>
  The native ETH version simplifies the user experience by eliminating the need for token approvals, while the ERC20 version provides compatibility with all standard tokens.
</Tip>

### EIP712 signature support

Both contracts implement EIP712 for secure off-chain message signing:

```solidity theme={null}
bytes32 private constant _REFUND_TYPEHASH = keccak256("Refund(bytes32 orderId)");

function instantRefundDigest(bytes32 orderID) public view returns (bytes32) {
    return _hashTypedDataV4(keccak256(abi.encode(_REFUND_TYPEHASH, orderID)));
}
```

### Event logging

Both contracts emit identical events for each state transition to enable efficient off-chain monitoring:

```solidity theme={null}
event Initiated(bytes32 indexed orderID);
event Redeemed(bytes32 indexed orderID, bytes secret);
event Refunded(bytes32 indexed orderID);
```

### Order ID generation

Unique order identifiers are generated using SHA256 hashing with chain-specific parameters:

```solidity theme={null}
bytes32 orderID = sha256(abi.encode(
    block.chainid, 
    secretHash, 
    initiator, 
    redeemer, 
    timelock, 
    amount
));
```

<Check>
  Chain ID inclusion prevents cross-chain replay attacks, while the parameter combination ensures each order is uniquely identifiable across the network.
</Check>
