Skip to content

Repository files navigation

Stellar PQC Migration Toolkit

Post-quantum readiness infrastructure for the Stellar network.

A developer toolkit that helps accounts, wallets, and enterprises assess their exposure to quantum-computing risk, simulate a migration to post-quantum cryptography, and eventually execute that migration on-chain — built in direct alignment with the Stellar Development Foundation's (SDF) published Quantum Preparedness Plan (QPP).

License Status Network Rust Soroban


Table of Contents


Why This Exists

Every Stellar account today is secured by classical Ed25519 signatures. Large-scale quantum computers, once available, would be capable of breaking that cryptography — meaning an attacker could forge signatures and drain any account whose public key has been exposed on-chain (which, on Stellar, is effectively every active account).

SDF has publicly committed to a phased transition of the network toward post-quantum cryptography. But a network-level upgrade path does not, by itself, migrate a single existing account, wallet, or institutional treasury. Someone still has to:

  1. Know how exposed they are today
  2. Understand what a migration actually looks like, safely, before touching real funds
  3. Execute that migration with tooling they can trust

No such tooling exists yet for Stellar. This project aims to be it.

The Threat Model, Precisely

It's worth being precise about the actual risk, since "quantum computers will break blockchains" is often stated too loosely.

What's actually at risk: Stellar accounts use Ed25519, an elliptic-curve signature scheme. A sufficiently large, fault-tolerant quantum computer running Shor's algorithm could derive a private key from its corresponding public key. On Stellar, an account's public key is visible on-chain the moment it transacts — meaning every account that has ever sent a transaction has already exposed the exact information a quantum attacker would need.

What's not at immediate risk: Funds in accounts that have never transacted (public key not yet revealed) are safer in the interim, though this is a fragile protection that disappears the moment the account is used.

The realistic timeline: Cryptographically-relevant quantum computers (CRQCs) capable of running Shor's algorithm at the scale needed to break Ed25519 do not exist today, and credible estimates for when they might vary widely — anywhere from the early 2030s to considerably later, with significant expert disagreement. This project does not assume an imminent break; it assumes migration takes years, so preparation should start now, matching SDF's own stated rationale for publishing the QPP well ahead of any concrete threat.

"Harvest now, decrypt later": The most urgent near-term risk isn't a sudden break — it's adversaries recording currently-public signatures and keys today, to be decrypted retroactively once quantum capability arrives. This is precisely why exposure scanning and early migration tooling has value now, even though no CRQC exists yet.

What this project does NOT attempt to solve:

  • It does not make Stellar's consensus or network layer quantum-safe — that is squarely SDF's and the validator community's responsibility, not an application-layer toolkit's.
  • It does not attempt to protect historical transaction data from retroactive decryption — once a signature is on-chain, it's on-chain permanently; this toolkit is about protecting future signing capability, not erasing past exposure.
  • It does not implement its own novel post-quantum cryptographic scheme — it uses established, publicly vetted PQC algorithms (see Algorithm Comparison), not experimental cryptography.

Alignment with SDF's Quantum Preparedness Plan

SDF's QPP is a three-stage roadmap:

Stage Target Description
Stage 1 2026 Post-quantum signature verification introduced as native host functions within Soroban smart contracts
Stage 2 2027 New quantum-safe signer types available via opt-in channels for existing accounts; account identity decoupled from signing keys
Stage 3 TBD Broader network-level enforcement / deprecation pathways for classical-only signing

This toolkit is designed to sit directly on top of Stage 1 and ahead of Stage 2 — providing the assessment and simulation tooling the ecosystem will need once native host function support lands, and serving as an early reference implementation while that support matures.

Note: This is an independent, community-built project. It is not officially affiliated with or endorsed by the Stellar Development Foundation. It is built in the spirit of, and in preparation for, SDF's publicly documented roadmap.

Glossary

Term Meaning
PQC Post-Quantum Cryptography — cryptographic algorithms believed to resist attacks from both classical and quantum computers
QPP SDF's Quantum Preparedness Plan — the three-stage roadmap this project aligns with
CRQC Cryptographically-Relevant Quantum Computer — a quantum computer powerful enough to break current elliptic-curve cryptography via Shor's algorithm
Soroban Stellar's smart contract platform; contracts are written in Rust and compiled to WebAssembly
Horizon Stellar's primary REST API for reading ledger and account data
Signer A public key (and associated weight) authorized to sign transactions for a Stellar account; accounts can have multiple weighted signers
Signer weight / threshold Stellar's multisig mechanism — each signer has a weight, and transactions require signatures totaling at least the relevant operation's threshold
Hybrid signing A transitional state where a transaction (or account) is protected by both a classical and a post-quantum signature simultaneously
Dilithium A lattice-based PQC digital signature scheme, one of the NIST-selected post-quantum standards (standardized as ML-DSA)
Falcon A lattice-based PQC signature scheme with smaller signatures than Dilithium but reliant on floating-point arithmetic
SPHINCS+ A hash-based, stateless PQC signature scheme; conservative security assumptions, larger signatures, slower verification
SAC Stellar Asset Contract — the built-in Soroban contract type that lets classic Stellar assets interoperate with smart contracts
Host function A function implemented natively by the Soroban host environment (as opposed to in contract WASM code) — typically far cheaper than the WASM equivalent
env.budget() The Soroban Rust SDK's test utility for measuring actual CPU instruction and memory consumption of contract execution

Architecture Overview

The toolkit is composed of three independently useful, progressively deeper layers.

┌─────────────────────────────────────────────────────────────┐
│                        Angular Frontend                      │
│        (Dashboard · Scan Reports · Migration Wizard)         │
└───────────────────────────┬───────────────────────────────────┘
                            │ REST / WebSocket
┌───────────────────────────▼───────────────────────────────────┐
│                        NestJS Backend                         │
│   ┌────────────┐   ┌──────────────┐   ┌────────────────────┐ │
│   │ Scanner     │   │ Simulator     │   │ Migration          │ │
│   │ Module      │   │ Module        │   │ Orchestrator       │ │
│   └─────┬──────┘   └──────┬───────┘   └─────────┬──────────┘ │
└─────────┼──────────────────┼─────────────────────┼────────────┘
          │                  │                     │
          ▼                  ▼                     ▼
   Horizon / RPC      Testnet Sandbox      Soroban Contracts
   (read accounts)    (Stellar Quickstart)  (Rust / WASM)
                                                    │
                                                    ▼
                                          PQC Signature Verification
                                          (Dilithium / Falcon primitives)

1. Assessment Layer (Quantum Exposure Scanner)

Purpose: Given a Stellar account or a set of accounts, produce a plain-language quantum-readiness report.

What it does:

  • Reads account signer configuration via Horizon (master weight, additional signers, thresholds)
  • Flags high-risk patterns, e.g.:
    • Single classical signer holding a large balance
    • Multisig setups with no quantum-safe signer present
    • Long-lived accounts whose public keys have had maximum on-chain exposure time
  • Produces a readiness score and a prioritized remediation list

Status: Buildable today, no dependency on native QPP host functions.

2. Simulation Layer (Safe Sandbox)

Purpose: Let a user rehearse a migration on a disposable testnet account before touching anything real.

What it does:

  • Spins up a funded testnet account (via Friendbot)
  • Adds a simulated post-quantum signer alongside the existing classical signer (hybrid state)
  • Walks through what a hybrid-signed transaction looks like — signed by both classical and PQC keys during a transition window, mirroring the pattern SDF's own two-stage plan implies
  • Visualizes signer weights and thresholds before/after in the Angular dashboard

Status: Requires a working Soroban contract (or local mock) to simulate signature checks against.

3. Migration Layer (On-Chain PQC)

Purpose: The real technical contribution — a Soroban smart contract capable of verifying a post-quantum signature, plus the orchestration logic to add a PQC signer to a live account and eventually retire the classical key.

What it does:

  • Implements PQC signature verification (Dilithium, primary candidate) as a Soroban contract function
  • Exposes a workflow to: generate a PQC keypair → register it as a new account signer → adjust threshold/weights → (later) drop the legacy classical signer
  • Benchmarks actual CPU instruction and memory cost of on-chain verification against Soroban's resource ceiling (see Feasibility Constraints)

Status: Active R&D. This is the layer most likely to be genuinely novel and the one most relevant to SDF's own engineering priorities.

User Journeys

Journey A — Individual account holder

1. User pastes their Stellar public key into the Scanner
2. Scanner reads signer config via Horizon, returns a readiness score
   (e.g., "High Exposure — single classical signer, 3-year-old key, no PQC signer present")
3. User clicks "Simulate Migration"
4. Simulator clones the account's signer config onto a funded testnet account
5. User walks through adding a PQC signer, adjusting thresholds, in a safe sandbox
6. User feels confident enough to click "Migrate on Mainnet" (Phase 4+ only)
7. Migration Orchestrator builds and submits the real transaction, confirms success,
   and updates the Scanner's readiness score for that account

Journey B — Institutional treasury team

1. Team uploads a CSV / connects via API a list of managed account public keys
2. Scanner batch-processes all accounts, ranks by exposure severity and balance size
3. Team exports a prioritized remediation report (PDF/CSV) for internal risk review
4. Team uses Simulator to test a proposed multisig reconfiguration against
   their actual signer/threshold setup before scheduling a real migration window
5. Migration Orchestrator supports scheduled/batched execution with
   pre-flight simulation checks (simulateTransaction) before submission

Journey C — Wallet / dApp developer

1. Developer imports the toolkit's client SDK (TypeScript) into their own wallet
2. Calls scanAccount() to surface a quantum-readiness badge/warning in their own UI
3. Optionally integrates the migration flow as a guided in-wallet feature,
   rather than sending users to a separate app

Data Model

Core entities used across the backend and database layer.

Account
├── publicKey: string (Stellar StrKey, e.g., "G...")
├── lastScannedAt: timestamp
├── readinessScore: enum { CRITICAL, HIGH, MEDIUM, LOW, MIGRATED }
├── balanceXLM: decimal
├── signers: Signer[]
└── scanHistory: ScanResult[]

Signer
├── key: string
├── weight: integer
├── type: enum { ED25519, PQC_DILITHIUM, PQC_FALCON, PRE_AUTH_TX, HASH_X }
└── addedAt: timestamp

ScanResult
├── id: uuid
├── accountId: FK -> Account
├── scannedAt: timestamp
├── score: enum
├── findings: Finding[]
└── rawSignerSnapshot: jsonb

Finding
├── code: string (e.g., "SINGLE_CLASSICAL_SIGNER", "NO_PQC_SIGNER_PRESENT")
├── severity: enum { CRITICAL, HIGH, MEDIUM, LOW, INFO }
└── message: string

MigrationPlan
├── id: uuid
├── accountId: FK -> Account
├── status: enum { DRAFT, SIMULATED, PENDING, SUBMITTED, CONFIRMED, FAILED }
├── proposedSigners: Signer[]
├── proposedThresholds: { low, medium, high: integer }
├── simulationResult: jsonb (nullable, populated after sandbox run)
└── submittedTxHash: string (nullable, populated after mainnet/testnet submission)

Contract Interfaces

Illustrative Soroban contract interfaces (Rust). Exact signatures will evolve as Phase 0 benchmarking informs real constraints.

pqc-verify contract — core signature verification:

#[contract]
pub struct PqcVerifyContract;

#[contractimpl]
impl PqcVerifyContract {
    /// Verifies a Dilithium signature against a message and public key.
    /// Returns true if valid, false otherwise. Panics on malformed input.
    pub fn verify_dilithium(
        env: Env,
        public_key: BytesN<1312>,   // Dilithium2 public key size, exact size TBD by variant
        signature: BytesN<2420>,   // Dilithium2 signature size, exact size TBD by variant
        message: Bytes,
    ) -> bool {
        // Implementation benchmarked in Phase 0 — see /benchmarks/results
        todo!()
    }
}

migration-registry contract — tracks per-account migration state:

#[contract]
pub struct MigrationRegistryContract;

#[contractimpl]
impl MigrationRegistryContract {
    /// Registers a new PQC signer as pending for the given account.
    pub fn propose_signer(env: Env, account: Address, pqc_public_key: BytesN<1312>) -> u64;

    /// Marks a previously proposed signer as confirmed, once added on-chain
    /// via a standard Stellar set_options operation.
    pub fn confirm_signer(env: Env, proposal_id: u64) -> bool;

    /// Returns the current migration status for an account.
    pub fn get_status(env: Env, account: Address) -> MigrationStatus;
}

#[contracttype]
pub enum MigrationStatus {
    NotStarted,
    PqcSignerProposed,
    PqcSignerConfirmed,
    ClassicalSignerRemoved,
}

These signatures are illustrative and will be finalized once Phase 0 benchmarking determines exact byte sizes and whether verification is feasible on-chain at all (see Feasibility Constraints).

API Reference (Backend)

Representative NestJS REST endpoints (subject to change as modules are implemented).

Method Endpoint Description
POST /scanner/scan Scans a single account by public key, returns a ScanResult
POST /scanner/batch-scan Scans multiple accounts (institutional use case)
GET /scanner/history/:publicKey Returns historical scan results for an account
POST /simulator/sandbox Creates a funded testnet account cloned from a real account's signer config
POST /simulator/hybrid-sign Simulates a hybrid classical+PQC signed transaction
POST /migration/plan Creates a draft MigrationPlan for an account
POST /migration/plan/:id/simulate Runs the plan against simulateTransaction for a dry-run cost/feasibility check
POST /migration/plan/:id/submit Submits the real migration transaction (testnet first; mainnet gated behind Phase 6)
GET /migration/plan/:id Returns current status of a migration plan

Example request/response:

POST /scanner/scan
Content-Type: application/json

{ "publicKey": "GABC...XYZ" }
{
  "accountId": "GABC...XYZ",
  "readinessScore": "HIGH",
  "findings": [
    {
      "code": "SINGLE_CLASSICAL_SIGNER",
      "severity": "HIGH",
      "message": "This account has a single Ed25519 signer with no post-quantum signer configured."
    },
    {
      "code": "LARGE_BALANCE_SINGLE_SIGNER",
      "severity": "CRITICAL",
      "message": "Balance exceeds risk threshold with no multisig or PQC protection."
    }
  ],
  "scannedAt": "2026-07-05T12:00:00Z"
}

Tech Stack

Layer Technology Notes
Frontend Angular, ngx-charts / Chart.js Signer visualization, scan reports, migration wizard
Backend NestJS, TypeScript Orchestration, scanning logic, Stellar SDK integration
Blockchain SDK @stellar/stellar-sdk Account reads, transaction construction, multisig handling
Data layer PostgreSQL (or SQLite for local/MVP) Cache of scanned accounts and historical reports
Smart contracts Rust, soroban-sdk Core PQC verification logic
Target wasm32-unknown-unknown Soroban's compilation target
PQC primitives pqcrypto-dilithium (candidate) / evaluating pure-Rust alternatives See open questions below
Local dev network Stellar Quickstart (Docker) Local Horizon + Soroban RPC + Friendbot
Contract tooling stellar-cli (formerly soroban-cli) Build, deploy, invoke, test contracts
Optimization wasm-opt (Binaryen) WASM size/performance optimization
Testing Jest (Nest/Angular), soroban-sdk native test harness (Rust)
CI GitHub Actions Contract build + test automation

Feasibility Constraints

Soroban transactions are bound by a network-defined resource budget, most notably a CPU instruction ceiling on the order of 100 million instructions per transaction, alongside separately metered ledger I/O, transaction size, and events/return value size.

This matters because post-quantum signature schemes are meaningfully heavier than the Ed25519 verification Stellar uses today:

  • Dilithium — larger public keys and signatures (~1.3KB / ~2.4KB for Dilithium2) than Ed25519 (32/64 bytes); verification involves lattice/polynomial-ring arithmetic rather than a single elliptic-curve operation
  • Falcon — smaller signatures than Dilithium, but implementations typically rely on floating-point arithmetic, which is a known complication in no_std / WASM environments like Soroban

Before committing to an architecture, this project benchmarks actual on-chain verification cost using env.budget() in Soroban's Rust test harness. Two outcomes are planned for:

  1. On-chain verification fits comfortably within the instruction budget alongside real contract logic → PQC verification becomes a first-class Soroban contract capability.
  2. On-chain verification is too expensive → pivot to an off-chain-verify, on-chain-attest pattern, where a relayer performs PQC verification off-chain and submits a lightweight cryptographic proof or hash commitment on-chain.

Either outcome is a legitimate, documentable engineering result — this README will be updated with real benchmark numbers once Phase 1 (below) is complete.

Algorithm Comparison

A working comparison of the candidate PQC signature schemes, to be validated empirically in Phase 0.

Scheme Type Public Key Size Signature Size Verify Speed (general) WASM/no_std Friendliness NIST Status
Ed25519 (current baseline) Elliptic curve 32 bytes 64 bytes Very fast Excellent (already in production on Stellar) Not post-quantum
Dilithium2/3 (ML-DSA) Lattice-based ~1.3–1.9 KB ~2.4–3.3 KB Fast, integer-only arithmetic Good — pure-Rust implementations exist, main risk is crate maturity for wasm32-unknown-unknown NIST-standardized (FIPS 204)
Falcon Lattice-based (NTRU) ~0.9–1.8 KB ~0.6–1.3 KB (smallest of the candidates) Fast, but relies on floating-point arithmetic Poor-to-moderate — floating-point in no_std WASM is a known friction point NIST-standardized (FIPS 206, pending)
SPHINCS+ (SLH-DSA) Hash-based ~32–64 bytes (small) Large — several KB to tens of KB Slower verification, especially for smaller-signature parameter sets Good — purely hash-based, no exotic arithmetic NIST-standardized (FIPS 205)

Working hypothesis (to be validated in Phase 0): Dilithium is the most likely first candidate for on-chain Soroban verification due to integer-only arithmetic and reasonable signature sizes, with SPHINCS+ as a conservative fallback if Dilithium's crate ecosystem proves difficult to compile to wasm32-unknown-unknown, and Falcon deprioritized specifically because of its floating-point dependency in a no_std context.

Repository Structure

stellar-pqc-toolkit/
├── contracts/                  # Rust / Soroban smart contracts
│   ├── pqc-verify/              # Core PQC signature verification contract
│   ├── migration-registry/      # Tracks signer migration state per account
│   └── shared/                  # Shared Rust types/utilities across contracts
├── backend/                    # NestJS application
│   ├── src/
│   │   ├── scanner/              # Assessment layer module
│   │   ├── simulator/            # Simulation layer module
│   │   ├── migration/            # Migration orchestration module
│   │   └── stellar/              # Shared Stellar SDK / Horizon integration
│   └── test/
├── frontend/                    # Angular application
│   ├── src/app/
│   │   ├── dashboard/
│   │   ├── scan-report/
│   │   └── migration-wizard/
├── benchmarks/                  # CPU/memory benchmark scripts and results
│   └── results/                  # Recorded env.budget() output per PQC scheme
├── docker/                      # Stellar Quickstart local network config
├── docs/                        # Architecture decision records, design notes
└── README.md

Getting Started

Prerequisites

  • Rust (stable) + wasm32-unknown-unknown target
  • stellar-cli
  • Node.js (LTS) + npm/yarn
  • Docker (for Stellar Quickstart local network)

Local network setup

docker run --rm -it \
  -p 8000:8000 \
  --name stellar-quickstart \
  stellar/quickstart:latest \
  --local --enable-soroban-rpc

Build and test the core contract

cd contracts/pqc-verify
rustup target add wasm32-unknown-unknown
cargo build --target wasm32-unknown-unknown --release
cargo test -- --nocapture   # prints env.budget() CPU/memory usage

Run the backend

cd backend
npm install
npm run start:dev

Run the frontend

cd frontend
npm install
ng serve

(Detailed setup docs and contract deployment scripts to be added as each module is built out.)

Configuration & Environment Variables

Backend (.env in /backend):

# Stellar network
HORIZON_URL=https://horizon-testnet.stellar.org
SOROBAN_RPC_URL=http://localhost:8000/soroban/rpc
NETWORK_PASSPHRASE="Test SDF Network ; September 2015"

# Database
DATABASE_URL=postgresql://user:password@localhost:5432/pqc_toolkit

# App
PORT=3000
LOG_LEVEL=debug

# Friendbot (testnet funding)
FRIENDBOT_URL=https://friendbot.stellar.org

Frontend (environment.ts in /frontend):

export const environment = {
  production: false,
  apiBaseUrl: 'http://localhost:3000',
  horizonUrl: 'https://horizon-testnet.stellar.org',
};

Contracts (contracts/pqc-verify/.cargo/config.toml or equivalent build config):

[build]
target = "wasm32-unknown-unknown"

Never commit real secret keys, mainnet signing keys, or .env files to the repository. All examples above use testnet-safe defaults. See Security.

Testing Strategy

Layer Approach Tooling
Smart contracts Unit tests via Soroban's native Rust test harness; resource usage assertions via env.budget() soroban-sdk test utilities, cargo test
Contract fuzz/property testing Property-based tests for signature verification edge cases (malformed keys, wrong-length inputs, replay attempts) proptest or soroban-sdk fuzzing hooks
Backend unit tests Isolated tests for scanner logic, risk scoring, migration state machine Jest
Backend integration tests Full request/response cycle against a local Soroban Quickstart network Jest + Docker Compose (Quickstart container)
Frontend unit tests Component-level tests for dashboard, scan report, migration wizard Jest + Angular Testing Library
End-to-end tests Full user journey — scan → simulate → migrate — run against local testnet Playwright or Cypress
Security-focused tests Verify contract behavior under adversarial inputs (signature malleability, replay, wrong network passphrase) Manual + automated adversarial test suite (contracts/*/tests/security/)

Testing philosophy: Given this project eventually touches real account signer configuration, testnet-first and simulation-first testing is non-negotiable at every layer — no code path that mutates account signers should be exercised against mainnet without first passing the full test suite against testnet.

CI/CD

GitHub Actions workflows (.github/workflows/):

  • contracts.yml — builds all Soroban contracts for wasm32-unknown-unknown, runs cargo test, records env.budget() output as a build artifact for tracking resource cost over time
  • backend.yml — installs dependencies, runs lint + unit + integration tests against a Dockerized Quickstart network spun up as a CI service container
  • frontend.yml — installs dependencies, runs lint + unit tests, builds production bundle
  • e2e.yml — runs full Playwright/Cypress suite against a CI-provisioned local network (nightly or on-demand, given cost/time)

All contract changes require CI-verified benchmark results attached to the PR before merge, since resource cost regressions are a first-class concern for this project.

Roadmap

  • Phase 0 — Feasibility spike: Minimal Soroban contract with a single Dilithium verify function; benchmark CPU instructions and memory via env.budget(); document results in benchmarks/results/
  • Phase 1 — Scanner MVP: NestJS + Angular quantum-exposure scanner for individual Stellar accounts, no contract dependency
  • Phase 2 — Simulation sandbox: Testnet-based hybrid signer simulation with visual before/after dashboard
  • Phase 3 — Migration contract: Production-quality Soroban contract for PQC signer registration and management
  • Phase 4 — End-to-end migration flow: Full user journey from scan → simulate → migrate on testnet
  • Phase 5 — Stellar Community Fund submission: Package Phase 0–4 results for SCF Build Award application
  • Phase 6 — Mainnet readiness: Security review, audit considerations, and mainnet deployment path once SDF's native QPP host functions ship

Risk Register

Tracked openly so the project's assumptions and failure modes are visible, not discovered late.

Risk Likelihood Impact Mitigation
PQC verification exceeds Soroban's CPU instruction budget Medium High — forces off-chain architecture pivot Phase 0 benchmarking spike before any further build-out; off-chain-attest fallback design already sketched
No pure-Rust, no_std-compatible PQC crate available Medium High — blocks on-chain approach entirely Evaluate multiple crates early; contribute upstream fixes if close but not quite compatible; fallback to hand-rolled minimal implementation of core verify logic if needed
SDF ships native QPP host functions before this project reaches Phase 3 Medium Low/Positive — reduces required scope, this project can adapt to consume native functions instead of implementing its own Design migration-registry contract to be swappable/forward-compatible with native host functions from the start
Users migrate real mainnet funds using early, unaudited tooling Low (if guardrails respected) Critical Hard testnet-only gate in code until Phase 6 security review; explicit UI warnings; no mainnet submission path exists until then
PQC key/signature sizes make transactions expensive or hit transaction size limits Medium Medium Benchmark transaction size costs alongside CPU costs in Phase 0; consider off-chain storage of large keys with on-chain hash commitments if needed
Scope creep — the toolkit tries to do too much before anything is solid Medium Medium Phased roadmap explicitly sequences scanner (low-risk, high-value) before migration (high-risk, high-value)
SDF's actual QPP implementation diverges from public roadmap assumptions used here Low Medium Treat SDF's public QPP posts/docs as living documents; revisit design assumptions each time SDF publishes updates

Design Decisions & Open Questions

These are tracked openly rather than hidden, since they materially affect architecture:

  • Dilithium vs. Falcon vs. SPHINCS+: Dilithium is the current leading candidate due to (relatively) simpler integer-only arithmetic vs. Falcon's floating-point dependency. SPHINCS+ is stateless and conservative but has larger signatures and slower verification — under evaluation as a fallback.
  • Pure-Rust vs. FFI-wrapped crates: Many available PQC crates (e.g., those wrapping liboqs) are C-dependent and may not compile cleanly to wasm32-unknown-unknown, which is a no_std target with no libc. Identifying or building a pure-Rust, no_std-compatible implementation is a near-term blocker to resolve.
  • On-chain vs. off-chain verification: Pending Phase 0 benchmark results (see Feasibility Constraints).
  • Identity/key decoupling: SDF's Stage 2 plan decouples account identity from signing keys. This project's migration-registry contract is designed to be forward-compatible with that model rather than inventing a competing one.

FAQ

Is this an official Stellar Development Foundation project? No. This is an independent, community-built project developed in preparation for and alignment with SDF's publicly published Quantum Preparedness Plan. It is not endorsed by SDF unless/until stated otherwise.

Can I use this on mainnet today? No. Until Phase 6 (security review) is complete, mainnet submission paths are intentionally not implemented. The Scanner (read-only) is the only component safe to point at real mainnet accounts today, since it makes no changes to account state.

Why not just wait for SDF to ship native PQC host functions? Native host functions handle the cryptographic primitive efficiently at the protocol level, but they don't solve the migration problem — someone still needs tooling to assess exposure, simulate changes, and safely execute a transition for a specific account. This project is designed to consume native host functions once available rather than compete with them.

What happens if Dilithium verification simply doesn't fit in Soroban's resource budget? The project pivots to an off-chain-verify, on-chain-attest architecture (see Feasibility Constraints) — this is a planned fallback, not a project-ending outcome.

Does this project implement its own cryptography? No. It uses established, independently vetted post-quantum algorithms (Dilithium, Falcon, SPHINCS+ — all NIST-standardized or NIST-track schemes). This project's novel contribution is the integration and migration tooling, not new cryptographic primitives.

How is this different from a general-purpose Stellar wallet? Wallets manage keys and sign transactions. This toolkit specifically assesses and migrates cryptographic posture — it's closer to a security auditing and migration tool than a wallet, though it's designed to be integrated into wallets via its client SDK.

Contributing

This project is in early, active development. Issues, discussion, and PRs are welcome — particularly around:

  • Pure-Rust PQC crate evaluation for no_std / WASM compatibility
  • Soroban resource benchmarking methodology
  • UX for the migration wizard (making a genuinely high-stakes action feel safe and reversible)
  • Threat-model review and adversarial test case design

Please open an issue before submitting large PRs so design direction can be discussed first. When contributing to contract code, include env.budget() output in your PR description so resource cost changes are visible to reviewers.

Code style

  • Rust: rustfmt + clippy clean, no warnings suppressed without a documented reason
  • TypeScript (backend/frontend): ESLint + Prettier, shared config at the repo root
  • Commits: Conventional Commits style (feat:, fix:, docs:, chore:) to keep changelog generation clean

Security

This toolkit will, by design, eventually touch real account signer configurations. Until the Migration Layer has been reviewed and tested extensively on testnet, it should not be used against mainnet accounts holding real value. A formal security review is planned ahead of any mainnet-facing release (see Roadmap, Phase 6).

Specific safeguards built into the design:

  • No mainnet transaction-submission code path exists until Phase 6
  • All migration actions require an explicit simulate-then-confirm step — no one-click mainnet mutation of signer configuration will ever be offered
  • Private keys are never persisted server-side; all signing happens client-side, and the backend only ever handles public keys and unsigned transaction envelopes
  • Contract code is designed to reject malformed, wrong-length, or replayed signatures explicitly, with adversarial test coverage tracked in contracts/*/tests/security/

If you discover a security issue, please report it privately rather than via a public issue — a dedicated security contact and disclosure policy will be published before any testnet-to-mainnet transition work begins.

License

(To be finalized — MIT or Apache 2.0 recommended for maximum compatibility with the Stellar/Soroban ecosystem's existing open-source norms.)

References

(Links to be replaced with archived/versioned references as the project matures, since SDF documentation URLs and content evolve over time.)

Acknowledgments

  • The Stellar Development Foundation, for publishing the Quantum Preparedness Plan and the broader Stellar/Soroban documentation this project builds on
  • The Open Quantum Safe project and the broader post-quantum cryptography research community
  • The NIST Post-Quantum Cryptography Standardization project, whose selected algorithms form the cryptographic foundation of this toolkit

About

A developer toolkit that helps accounts, wallets, and enterprises assess their exposure to quantum-computing risk, simulate a migration to post-quantum cryptography, and eventually execute that migration on-chain

Resources

Contributing

Stars

Watchers

Forks

Releases

Packages

Contributors

Languages