Skip to main content

Split-Key Architecture

The split-key architecture is the mechanism that makes Phantom Identity secure at rest. The secp256k1 private key — the identity's signing authority — is never stored in one place. It is split into two parts using XOR encryption. One part lives offline in the PNG bearer object. The other lives on-chain in the PersistentKeyVault. Neither part alone reveals anything about the private key. An attacker must compromise both to recover the identity.

XOR Split-Key Encryption

The split is a one-time pad construction:

encKeyPartA = random(256 bits)
encKeyPartB = privateKey XOR encKeyPartA

Recovery is the inverse:

privateKey = encKeyPartA XOR encKeyPartB

Why XOR?

XOR split is information-theoretically secure when one part is uniformly random (which encKeyPartA is, by construction). This means:

  • encKeyPartA alone is indistinguishable from random noise. It reveals nothing about the private key.
  • encKeyPartB alone is also indistinguishable from random noise, because it is the XOR of a random value with the private key.
  • Both together recover the private key with a single XOR operation — no key derivation, no decryption rounds, no computational overhead.

This is not a threshold scheme or a Shamir split. It is a 2-of-2 XOR split — both parts are required, and each is exactly 256 bits. The simplicity is intentional. There are no parameters to misconfigure, no threshold to choose, and no reconstruction algorithm that could introduce implementation bugs.

Storage Locations

PartLocationAccess ControlPersistence
encKeyPartAPNG tEXt chunk (offline, user-held)Physical possession of the file + optional passphraseIndefinite (file on disk)
encKeyPartBPersistentKeyVault smart contract (on-chain)Valid Access Proof (Groth16) + quantum commitment preimageUntil explicit revocation

The two storage locations have fundamentally different threat models:

  • The PNG is vulnerable to local threats: device compromise, malware, physical theft, accidental deletion.
  • The on-chain vault is vulnerable to cryptographic threats: ZK proof forgery, smart contract bugs, quantum attacks on the proving system.

An attacker must succeed against both threat models simultaneously to compromise the identity.

On-Chain Access Control

The encKeyPartB stored on-chain is not freely readable. The PersistentKeyVault enforces three layers of access control before returning key material:

Layer 1: Zero-Knowledge Proof

The caller must provide a valid Groth16 Access Proof with 4 public inputs (root, dataHash, sessionNonce, accessTag). The on-chain verifier checks the proof against the trusted verification key. This proves the caller knows the commitment preimage — the secrets embedded in the PNG — without revealing them.

An attacker without the PNG cannot generate a valid proof. The proof requires knowledge of secret, nullifierSecret, and blinding, which are private inputs to the circuit.

Layer 2: Anti-Replay (accessTag)

Each access must include a unique accessTag:

accessTag=Poseidon2(nullifierSecret,  sessionNonce)\text{accessTag} = \text{Poseidon}_2(\text{nullifierSecret},\; \text{sessionNonce})

The vault records every accessTag it has seen. If the same accessTag is submitted twice, the transaction reverts. This prevents an attacker from replaying a previously observed proof.

The sessionNonce is a fresh random value for each session. Because nullifierSecret is private (known only to the PNG holder), an attacker cannot compute a valid accessTag for a new session nonce without knowing the secret.

Layer 3: Quantum-Resistant Commitment

Each access requires the caller to provide the quantumSecret — the preimage of the currently stored quantumCommitment:

keccak256(quantumSecret)=?stored quantumCommitment\text{keccak256}(\text{quantumSecret}) \stackrel{?}{=} \text{stored quantumCommitment}

If the check passes, the vault replaces the stored quantum commitment with a new one provided by the caller (newQuantumCommitment). This rotation means that even if an attacker somehow compromises the Groth16 proving system (e.g., via a future quantum computer that can forge BN254 proofs), they would also need to provide a valid keccak256 preimage — which requires breaking keccak256, a fundamentally different and harder problem.

The rotation also means that each valid quantum secret is single-use. After a successful access, the previous quantum secret is no longer valid, and only the current holder (who chose the new quantum commitment) knows the next valid preimage.

Passphrase Protection

The PNG metadata can be optionally encrypted with a user-chosen passphrase, adding a knowledge factor to the possession factor.

Encryption Scheme

ParameterValue
AlgorithmAES-256-GCM
Key derivationPBKDF2-SHA256
Iterations100,000
SaltRandom 16 bytes (stored in PNG metadata, unencrypted)
IVRandom 12 bytes (stored in PNG metadata, unencrypted)
Auth tag128 bits (appended to ciphertext)

The passphrase is processed through PBKDF2 to produce a 256-bit AES key. All sensitive metadata fields (encKeyPartA, secret, nullifierSecret, blinding, dataHash, quantumSecret) are encrypted as a single AES-256-GCM payload. The salt and IV are stored in the clear alongside the ciphertext — they do not need to be secret.

Security Analysis

Without the passphrase, an attacker who obtains the PNG has:

  • An encrypted blob that is indistinguishable from random data (AES-256-GCM provides IND-CCA2 security).
  • The salt and IV, which do not help without the passphrase.
  • No way to generate a valid Access Proof (they cannot extract the commitment secrets).
  • No access to encKeyPartA (they cannot recover the private key even if they somehow obtain encKeyPartB).

PBKDF2 with 100,000 iterations provides reasonable resistance against offline brute-force attacks on the passphrase. For high-security use cases, users should choose strong passphrases (high entropy).

caution

Passphrase protection does not encrypt the PNG image itself — only the metadata. The visual content of the PNG is unchanged. Do not embed sensitive visual information in the image.

Threat Model

ThreatAttacker HasResult
PNG stolen, no passphraseencKeyPartA + all secretsAttacker can generate Access Proofs and recover the private key. Identity compromised.
PNG stolen, passphrase setEncrypted blobAttacker must brute-force the passphrase. With a strong passphrase, this is infeasible.
On-chain vault compromisedencKeyPartBUseless without encKeyPartA. Cannot reconstruct private key. Cannot generate Access Proofs (no secrets).
Both PNG + vault compromisedencKeyPartA + encKeyPartBPrivate key recovered via XOR. Identity compromised. (Requires simultaneous compromise of offline file and on-chain access control.)
Proof system broken (quantum)Ability to forge Groth16 proofsStill needs keccak256 preimage (quantum commitment). Still needs encKeyPartA from PNG. Attack mitigated by quantum rotation.
Proof replayedPreviously valid proofaccessTag already recorded. Transaction reverts.
PNG lostNothingIdentity is permanently inaccessible. No recovery mechanism. This is a feature of bearer instruments.
Observer watches vault accessAccess transaction metadataSees the keyId and accessTag, but cannot link to the holder's real identity. Cannot recover the private key from the encrypted key parts.

Comparison with Other Approaches

ApproachKey StorageTrust AssumptionRecovery
MetaMask / Browser walletSingle location (browser storage)Browser securitySeed phrase (centralized backup)
Hardware walletSingle location (secure element)Hardware integritySeed phrase
MPC walletDistributed across partiesThreshold of parties honestDistributed recovery
Specter Split-KeyXOR split: offline PNG + on-chain vaultNeither location alone is sufficientNo recovery. Bearer instrument.

The split-key model has no recovery mechanism by design. If the PNG is lost, the identity is gone. This is the same security philosophy as physical bearer instruments (cash, bearer bonds) — possession is control, and loss is final.