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

# Signing schemes

> As CoW Protocol handles user's orders that were provided off-chain, the authenticity of a user's order needs to be asserted. Authenticity is asserted by the user  their order. A user may be an EOA or a smart contract.

## Order digest

The order digest is a `bytes32` that uniquely describes the parameters of an order. It is used as the input to the signing schemes. The digest is computed as described in the [`EIP-712`](https://eips.ethereum.org/EIPS/eip-712#specification).

### Replay protection

Replay protection for the signing schemes is achieved by using an [`EIP-712`](https://eips.ethereum.org/EIPS/eip-712#definition-of-domainseparator) domain separator. This domain separator is unique to each deployment of the CoW Protocol settlement contract on a particular chain.

When computing the domain separator, the following parameters are used:

```
{  name: "Gnosis Protocol",  version: "v2",  chainId: /* chain ID for the current network: e.g. 1 for mainnet */,  verifyingContract: "0x9008D19f58AAbD9eD0D60971565AA8510560ab41"}
```

<Note>
  CoW Protocol was formerly known as Gnosis Protocol v2. The domain separator is still named `Gnosis Protocol` as the change would have required a new deployment of the settlement contract.
</Note>

The actual domain separator is the result of hashing the previous `EIP712Domain` struct with the `EIP-712` defined [`hashStruct`](https://eips.ethereum.org/EIPS/eip-712#definition-of-hashstruct) function.

<Check>
  For convenience, the domain separator is exposed as a public view function in the settlement contract:

  [Arbitrum One](https://arbiscan.io/address/0x9008D19f58AAbD9eD0D60971565AA8510560ab41/#readContract#F2)[Avalanche](https://snowscan.xyz/address/0x9008D19f58AAbD9eD0D60971565AA8510560ab41/#readContract#F2)[Base](https://basescan.org/address/0x9008D19f58AAbD9eD0D60971565AA8510560ab41/#readContract#F2)[BNB](https://bscscan.com/address/0x9008D19f58AAbD9eD0D60971565AA8510560ab41/#readContract#F2)[Ethereum](https://etherscan.io/address/0x9008D19f58AAbD9eD0D60971565AA8510560ab41/#readContract#F2)[Gnosis](https://gnosisscan.io/address/0x9008D19f58AAbD9eD0D60971565AA8510560ab41/#readContract#F2)[Ink](https://explorer.inkonchain.com/address/0x9008D19f58AAbD9eD0D60971565AA8510560ab41/#readContract#F2)[Linea](https://lineascan.build/address/0x9008D19f58AAbD9eD0D60971565AA8510560ab41/#readContract#F2)[Plasma](https://plasmascan.to/address/0x9008D19f58AAbD9eD0D60971565AA8510560ab41/#readContract#F2)[Polygon](https://polygonscan.com/address/0x9008D19f58AAbD9eD0D60971565AA8510560ab41/#readContract#F2)[Sepolia](https://sepolia.etherscan.io/address/0x9008D19f58AAbD9eD0D60971565AA8510560ab41/#readContract#F2)
</Check>

### Encoding

To encode the order into the order digest, the [`EIP-712`](https://eips.ethereum.org/EIPS/eip-712#specification) specification is used:

```
orderDigest = keccak256("\x19\x01" ‖ domainSeparator ‖ hashStruct(orderStruct))
```

The components are:

* `keccak256`, the standard unpadded Ethereum hashing function
* `"\x19\x01"`, two bytes
* `‖`, the byte-concatenation function
* `domainSeparator`, the domain separator as mentioned in the previous section
* `hashStruct`, the [identically named function in the EIP-712 standard](https://eips.ethereum.org/EIPS/eip-712#definition-of-hashstruct)

<Accordion title="hashStruct pseudocode">
  ```
  hashStruct(typeHash, data) = keccak256(typeHash ‖ encodeData(data))
  ```

  The components are:

  * `keccak256`, the standard unpadded Ethereum hashing function
  * `‖`, the byte-concatenation function
  * `typeHash`, the hash of the struct type
  * `encodeData`, the [identically named function in the EIP-712 standard](https://eips.ethereum.org/EIPS/eip-712#definition-of-encodedata)
</Accordion>

The resulting order digest is a `bytes32` value that is used as the input to the signing schemes.

### JavaScript example

Phew, that was a lot of hashing! Feeling dizzy? Don't worry, we got you covered.

The [`@cowprotocol/contracts`](https://www.npmjs.com/package/@cowprotocol/contracts) package provides a function to compute the order digest for you:

```
import {  Order,  OrderBalance,  OrderKind,  domain,  hashOrder} from "@cowprotocol/contracts"// Define an orderconst order: Order = {  sellToken: "0x6b175474e89094c44da98b954eedeac495271d0f", // dai  buyToken: "0xdef1ca1fb7fbcdc777520aa7f396b4e015f497ab", // cow  sellAmount: "10000000000000000000000000", // 10m dai  buyAmount: "10000", // 10k cow  validTo: 1704067200,  appData: "0xc85ef7d79691fe79573b1a7064c19c1a9819ebdbd1faaab1a8ec92344438aaf4", // keccak256("cow")  feeAmount: "0",  kind: OrderKind.SELL,  partiallyFillable: false,  sellTokenBalance: OrderBalance.ERC20,  buyTokenBalance: OrderBalance.ERC20,};// hash the order to generate the order digestconst digest = hashOrder(domain(1, "0x9008D19f58AAbD9eD0D60971565AA8510560ab41"), order);// output the digestconsole.log(`Order digest: ${digest}`)
```

### Etherscan Example

For convenience, we also deployed a small helper contract that makes it easy to compute order uids as well as their full encoding for each chain using the Etherscan UI:

* [Ethereum](https://etherscan.io/address/0xe84dcd8587287b997f51299430a396ad03aaec06/#readContract#F1)
* [Gnosis](https://gnosisscan.io/address/0xCA51403B524dF7dA6f9D6BFc64895AD833b5d711/#readContract#F1)
* Base N/A
* Arbitrum N/A
* Avalanche N/A
* Polygon N/A
* BNB N/A
* Linea N/A
* Plasma N/A
* Ink N/A
* [Sepolia](https://sepolia.etherscan.io/address/0x59Ffd6c1823F212D49887230f155A35451FdDbfa/#readContract#F1)

## Supported schemes

CoW Protocol supports four different signing schemes. These signing schemes are summarized in the following table:

| **Signing Scheme**                                                            | **Gasless** | **EOA** | **Smart Contract** |
| ----------------------------------------------------------------------------- | ----------- | ------- | ------------------ |
| [`eth_sign`](https://ethereum.org/en/developers/docs/apis/json-rpc/#eth_sign) | ✅           | ✅       | ❌                  |
| [`EIP-712`](https://eips.ethereum.org/EIPS/eip-712)                           | ✅           | ✅       | ❌                  |
| [`ERC-1271`](https://eips.ethereum.org/EIPS/eip-1271)                         | ✅           | ❌       | ✅                  |
| `PreSign`                                                                     | ❌           | ✅       | ✅                  |

Except for the `PreSign` scheme, all signing schemes involve signing an *order digest* that is based on the message structure of `EIP-712`.

<Check>
  In the expanded detail sections below, `signature` refers to the value passed to `signature` in the [Order book API](/cow-protocol/reference/apis/orderbook).
</Check>

### `eth_sign`

This signature type is the most commonly supported signing mechanism for EOAs.

The signature is computed as:

```
signature = ethSign(orderDigest)
```

The components are:

* `ethSign`, using the user's private key to ECDSA-sign a message prefixed with `"\x19Ethereum signed message:\n"` and its length
* `orderDigest`, the order digest

Most Ethereum libraries support `ethSign` signatures ([ethers-js](https://docs.ethers.io/v5/api/signer/#Signer-signMessage), [web3py](https://web3py.readthedocs.io/en/stable/web3.eth.html?highlight=sign#web3.eth.Eth.sign)).

### `EIP-712`

This signing method, also known as typed structured data signing, is the recommended signing method for EOAs, since the user will be able to see the full order data that is being signed in most wallet implementations.

The signature is computed as:

```
signature = ecdsaSign(orderDigest)
```

The components are:

* `ecdsaSign`, using the user's private key to ECDSA-sign the message
* `orderDigest`, the order digest

Many Ethereum libraries have some degree of support for signing typed data without building the order digest by hand (for example [ethers-js](https://docs.ethers.io/v5/api/signer/#Signer-signTypedData), and [web3py](https://web3py.readthedocs.io/en/stable/web3.eth.html?highlight=sign_typed_data#web3.eth.Eth.sign_typed_data)).

In any case, you may want to read about the [domain separator](https://eips.ethereum.org/EIPS/eip-712#definition-of-domainseparator) and [encoding the order struct](#encoding).

### `ERC-1271`

This signing mechanism is the only option that can be used by smart contracts to provide off-chain signatures for orders.

In order to support smart-contract orders, the trading smart contract (the user) must implement the [EIP-1271](https://eips.ethereum.org/EIPS/eip-1271#specification) interface.

```
signature = eip1271Signature
```

<Check>
  When submitting an `ERC-1271` order to the API, the `from` field **MUST** be set to the address of the smart contract that will be signing the order. This is because the `ERC-1271` signature is not an Ethereum signature, and thus the `from` field cannot be inferred from the signature.
</Check>

The components are:

* `eip1271Signature`, any `bytes` that is a valid signature for the contract for the order. This signature is contract specific.

For an order to be accepted, the `eip1271Signature` must be valid for the `orderDigest` message, that is in Solidity:

```
isValidSignature(orderDigest, eip1271Signature) == MAGICVALUE
```

### `PreSign`

This is the only signing method that supports both EOA and smart-contract traders.

Together with submitting a `PreSign` order, the user must submit the order on-chain. This is done by calling the settlement contract `setPreSignature` function:

```
setPreSignature(orderUid, true);
```

The components are:

* `orderUid`, the unique identifier of the order
* `true`, whether the order is pre-signed or not (allows for cancelling pre-signed orders)

The signature is an empty `bytes` string:

```
signature = 0x
```

<Check>
  When submitting a `PreSign` order to the API, the `from` field **MUST** be set to the address of the order owner. This is because the `PreSign` signature is not an Ethereum signature, and thus the `from` field cannot be inferred from the signature.
</Check>

<Note>
  If an order was already filled, then pre-signing it does *not* make it tradable again.
</Note>
