# In-band secret distribution

## Overview

To ensure a recipient receives the secret information required to spend their commitment, the sender encrypts the secrets (salt, value, tokenId, ercAddress) of the commitment sent to the recipient and proves using zkp that they encrypted this correctly with the recipient's public key. We use the KEM-DEM hybrid encryption paradigm.

## KEM-DEM Hybrid Encryption

### Key Creation

Use Elliptic curve (here we use Baby Jubjub curve) `E` over a finite field `Fp` where `p` is a large prime and `G` is the generator.

Alice generates a random ephemeral asymmetric key-pair $$(x\_e, Q\_e)$$:\
$$x\_e ; \leftarrow; {0, 1}^{256} \qquad Q\_e \coloneqq x\_eG$$

These keys are only used once, and are unique to this transaction.

### Encryption

The encryption process involves 2 steps: a KEM step to derive a symmetric encryption key from a shared secret, and a DEM step to encrypt the plaintexts using the encryption key.

### Key Encapsulation Method (Encryption)

Using the previously generated asymmetric private key, we obtain a shared secret, $$key\_{DH}$$, using standard Diffie-Hellman. This is hashed alongside the ephemeral public key to obtain the encryption key. $$key\_{DH} \coloneqq x\_eQ\_r \qquad key\_{enc} \coloneqq H\_{K}(key\_{DH} ; + ;Q\_e)$$

where:\
$$Q\_r$$ is the recipient's public key\
$$H\_{K}(x) \coloneqq \text{Poseidon}(Domain\_{K}, x)$$\
$$Domain\_{K} \coloneqq \text{to\_field}(\text{SHA256}(\text{'nightfall-kem'}))$$

### Data Encapsulation Method (Encryption)

For circuit efficiency, the encryption used is a block cipher in counter mode where the cipher algorithm is a mimc hash. Given the ephemeral keys are unique to each transaction, there is no need for a nonce to be included. The encryption of the $$i^{th}$$ message is as follows:

$$c\_i \coloneqq H\_{D}(key\_{enc} + i) + p\_i$$

where:\
$$H\_{D}(x) \coloneqq \text{Poseidon}(Domain\_{D}, x)$$\
$$Domain\_{D} \coloneqq \text{to\_field}(\text{SHA256}(\text{'nightfall-dem'}))$$

The sender then provides the recipient with $$(Q\_e, \text{ciphertexts})$$. These are included as part of the transaction struct sent on-chain.

### Decryption

In order to decrypt, the recipient performs a slightly modified version of the KEM-DEM steps.

### Key Encapsulation Method (Decryption)

Given $$Q\_e$$, the recipient is able to calculate the encryption key locally by performing the following steps.

$$key\_{DH} \coloneqq x\_rQ\_e \qquad key\_{enc} \coloneqq H\_{K}(key\_{DH} ; + ;Q\_e)$$

where:\
$$Q\_e$$is the ephemeral public key\
$$H\_{K}(x) \coloneqq \text{Poseidon}(Domain\_{K}, x)$$\
$$Domain\_{K} \coloneqq \text{to\_field}(\text{SHA256}(\text{'nightfall-kem'}))$$

### Data Encapsulation Method (Decryption)

With $$key\_{enc}$$ and an array of ciphertexts, the $$i\_{th}$$ plaintext can be recovered with the following:

$$p\_i \coloneqq c\_i - H\_{D}(key\_{enc} + i)$$

where:\
$$H\_{D}(x) \coloneqq \text{Poseidon}(Domain\_{D}, x)$$\
$$Domain\_{D} \coloneqq \text{to\_field}(SHA256(\text{'nightfall-dem'}))$$

## Derivation and generation of the various keys involved in encryption, ownership of commitments and spending

Using BIP39 generate a 12 word `mnemonic` and from this generate a `seed` by calling `mnemonicToSeedSync`. Then following the standards of BIP32 and BIP44, generate a `rootKey` based on this `seed` and `path`.

```
zkpPrivateKey = Poseidon(rootKey, 2708019456231621178814538244712057499818649907582893776052749473028258908910)
where 2708019456231621178814538244712057499818649907582893776052749473028258908910 is keccak256(`zkpPrivateKey`) % BN128_GROUP_ORDER

nullifierKey = Poseidon(rootKey, 7805187439118198468809896822299973897593108379494079213870562208229492109015n)
where 7805187439118198468809896822299973897593108379494079213870562208229492109015n is keccak256(`nullifierKey`) % BN128_GROUP_ORDER

zkpPublicKey = zkpPrivateKey * G
```

The apps which will use the `ZkpKeys` to generate these keys can store the `rootKey` in different devices by splitting this into shares using Shamir Secret Sharing. If either `rootKey` or `mnemonic` is compromised, then the adversary can calculate the `zkpPrivateKey` and `nullifierKey`. The `zkpPrivateKey` can be used to decrypt secrets of a commitment whilst the `nullifierKey` can be used to spend the commitment. Hence `rootKey` and `mnemonic` must be stored very securely. It is also recommended to store `zkpPrivateKey` and `nullifierKey` separately to avoid theft of commitments in case one of these is compromised.


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://westlad.gitbook.io/nightfall_3/in-band-secret-distribution.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
