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

# C# / .NET quickstart

> Encrypt files client-side in C# through the Everabyte Crypto SDK C ABI (P/Invoke) — a complete zero-knowledge round trip.

C# integrates through the SDK's **C ABI** via **P/Invoke** (`DllImport`/`LibraryImport`). The native library is `evb_e2ee_ffi.dll` / `libevb_e2ee_ffi.so` (built from `bindings/dart/rust` of [everabyte/crypto-sdk](https://github.com/everabyte/crypto-sdk), or fetched from GitHub Releases).

## 1. Install

```bash theme={null}
git clone https://github.com/everabyte/crypto-sdk.git
cd crypto-sdk/bindings/dart/rust && cargo build --release
# → evb_e2ee_ffi.dll (Windows) / libevb_e2ee_ffi.so (Linux) / .dylib (macOS)
```

Declare the imports (a subset — full list in the [C ABI reference](https://docs.everabyte.com/sdk/c-abi-reference.md)):

```csharp theme={null}
internal static partial class EvbE2ee
{
    private const string Lib = "evb_e2ee_ffi";

    [LibraryImport(Lib)]
    private static partial int evb_generate_umk(byte[] umk, ulong cap, out ulong len);

    [LibraryImport(Lib)]
    private static partial int evb_umk_public_keys(byte[] sk, byte[] seed,
        byte[] outJson, ulong cap);

    [LibraryImport(Lib, StringMarshalling = StringMarshalling.Utf8)]
    private static partial int evb_wrap_umk_with_mnemonic(byte[] sk, byte[] seed,
        string mnemonic, byte[] salt, byte[] nonce, byte[] blob, ulong cap);

    [LibraryImport(Lib)]
    private static partial int evb_wrap_dek_to_umk(byte[] dek,
        byte[] publicKeyX25519, byte[] publicKeyMlkem, byte[] outJson, ulong cap);

    [LibraryImport(Lib)]
    private static partial int evb_unwrap_dek_from_umk(byte[] envelopeJson,
        byte[] sk, byte[] seed, byte[] dekOut, ulong cap, out ulong len);

    [LibraryImport(Lib)]
    private static partial int evb1_seal_all(byte[] dek, byte[] fileNonce,
        byte[] plaintext, ulong plaintextLen, byte[] outBuf, ulong cap, out ulong len);

    [LibraryImport(Lib)]
    private static partial int evb1_open_all(byte[] dek, byte[] payload,
        ulong payloadLen, byte[] outBuf, ulong cap, out ulong len);

    [LibraryImport(Lib, StringMarshalling = StringMarshalling.Utf8)]
    private static partial int evb_derive_wire_alias(byte[] sk, byte[] seed,
        string realName, byte[] alias, ulong cap);

    [LibraryImport(Lib, StringMarshalling = StringMarshalling.Utf8)]
    private static partial int evb_encrypt_file_name(byte[] dek, string realName,
        byte[] nonce, byte[] blob, ulong cap);

    [LibraryImport(Lib, StringMarshalling = StringMarshalling.Utf8)]
    private static partial int evb_decrypt_file_name(byte[] dek, string blob,
        byte[] outName, ulong cap, out ulong len);

    [LibraryImport(Lib)]
    private static partial int evb_random(ulong len, byte[] outBuf, ulong cap, out ulong outLen);
}
```

## 2. Account key (UMK) — once, kept in your secret store

```csharp theme={null}
var umk = new byte[96];
EvbE2ee.evb_generate_umk(umk, 96, out _);

var jsonBuf = new byte[2048];
EvbE2ee.evb_umk_public_keys(umk.AsSpan(0, 32).ToArray(), umk.AsSpan(32).ToArray(), jsonBuf, (ulong)jsonBuf.Length);
var publics = JsonSerializer.Deserialize<PublicKeys>(jsonBuf, JsonOpts.TrimNulls);

var mnemonic = /* fresh 12-word BIP-39 phrase, shown to the user once */;
var blob = new byte[8192];
var salt = RandomNumberGenerator.GetBytes(16);
var nonce = RandomNumberGenerator.GetBytes(12);
EvbE2ee.evb_wrap_umk_with_mnemonic(umk, umk.AsSpan(32).ToArray(), mnemonic, salt, nonce, blob, (ulong)blob.Length);
// POST /e2ee/keys/register { publics, wraps:[{wrapKind:"mnemonic", wrappedBlob}], stepUpToken }
```

Keep the 96 UMK bytes in **your** secret store (Azure Key Vault, DPAPI-protected file, HSM). Everabyte receives only public keys and wrapped blobs.

## 3. Encrypt → upload → attach envelope

```csharp theme={null}
var plaintext = await File.ReadAllBytesAsync("contract.pdf");
var dek = RandomNumberGenerator.GetBytes(32);
var fileNonce = RandomNumberGenerator.GetBytes(12);

var payload = new byte[plaintext.Length + 65536 + 16];
EvbE2ee.evb1_seal_all(dek, fileNonce, plaintext, (ulong)plaintext.Length, payload, (ulong)payload.Length, out var ctLen);

var wireName = new byte[128];
EvbE2ee.evb_derive_wire_alias(umk.AsSpan(0, 32).ToArray(), umk.AsSpan(32).ToArray(), "contract.pdf", wireName, (ulong)wireName.Length);
var encryptedName = new byte[512];
EvbE2ee.evb_encrypt_file_name(dek, "contract.pdf", RandomNumberGenerator.GetBytes(12), encryptedName, (ulong)encryptedName.Length);

var envelopeJson = new byte[4096];
var pkX = Convert.FromBase64String(publics.PublicKeyX25519);
var pkK = Convert.FromBase64String(publics.PublicKeyMlkem);
EvbE2ee.evb_wrap_dek_to_umk(dek, pkX, pkK, envelopeJson, (ulong)envelopeJson.Length);

// 1) POST /files/upload/{bucketId}  (multipart, filename = wireName = "evb-<hex64>")
// 2) POST /e2ee/files/by-path/envelope { bucketId, fileName: wireName, encryptedName, envelope }
// Check both responses. On timeout, reconcile by file ID before cleanup. After a
// confirmed failure, resolve the row by bucket + wireName, confirm no envelope,
// and hard-delete through the file API as required by the E2EE upload contract.
// Handle retention blocks explicitly.
```

## 4. Download → decrypt

```csharp theme={null}
// GET /e2ee/files/{id}/envelope → envelope JSON
// GET /files/{id}/stream?download=true → stored ciphertext
var dek = new byte[32];
EvbE2ee.evb_unwrap_dek_from_umk(envelopeJsonBytes, umk.AsSpan(0, 32).ToArray(), umk.AsSpan(32).ToArray(), dek, 32, out _);

var original = new byte[storedCiphertext.Length];
EvbE2ee.evb1_open_all(dek, storedCiphertext, (ulong)storedCiphertext.Length, original, (ulong)original.Length, out var ptLen);
// original[0..ptLen] === the exact plaintext, decrypted on your machine
```

Error handling: every call returns `0` on success, negative otherwise; `evb_last_error(buf, cap)` reads the secret-free message (call with `cap = 0` first to get the required size).

## Next

* [C ABI reference](https://docs.everabyte.com/sdk/c-abi-reference.md) — every symbol and convention.
* [Node.js quickstart](https://docs.everabyte.com/sdk/quickstart-nodejs.md) — same round trip, no native library.


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.