From mboxrd@z Thu Jan 1 00:00:00 1970 Delivery-date: Mon, 04 May 2026 21:41:58 -0700 Received: from mail-ot1-f58.google.com ([209.85.210.58]) by mail.fairlystable.org with esmtps (TLS1.3) tls TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256 (Exim 4.94.2) (envelope-from ) id 1wK7bY-0003FJ-5i for bitcoindev@gnusha.org; Mon, 04 May 2026 21:41:58 -0700 Received: by mail-ot1-f58.google.com with SMTP id 46e09a7af769-7def9da8485sf856323a34.1 for ; Mon, 04 May 2026 21:41:55 -0700 (PDT) ARC-Seal: i=3; a=rsa-sha256; t=1777956110; cv=pass; d=google.com; s=arc-20240605; b=kwVLPRGxvz36Mq2vMKLu5eIEw56mn74aNL5aSrrVLKvH0GQNd2loRDZe1kalbzjUwp YC+J4UG8GYwniT9t3jRcKSW8VSI8vNW1MetkF8AQxDtylwEmGCoycrtwYQm461aRzcz2 8IopSJGvIrDYTkG8ELFoqTo0uuUgiOckZxRIgEkVIrR4X7+aRA17v7PoeuoS7mLXaJ/c LKl0xCGlnYtJYSEHmFjlyB9zasVgrS6C+60hTVHIh13WbCsjpdXjABMOHyH6ovTptD+p gnZa0bX3wuPm4TEKqvasmAjVaZ2awCQbXGbV+H463ooV7UuGqKJGK7c+cP8Y4m80G4J/ g6dg== ARC-Message-Signature: i=3; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20240605; h=list-unsubscribe:list-subscribe:list-archive:list-help:list-post :list-id:mailing-list:precedence:to:subject:message-id:date:from :mime-version:sender:dkim-signature:dkim-signature; bh=G2K1XxOci/8V8ZjLbXGzApftKr6e8zUwxGnAdUBtRqQ=; fh=NvQ3aoBv4Y7WittRlmoLmdHlrX1FVktasIo6anHBB7s=; b=BGL7Poqnk+zjZnCZvosF0hNkdKT5BUYcSIjZk+Pfxb0nwrCcOk9D2hkB6Eck6DbV1E QAoWaE4Zti0Fylf92P0KH8vxvDdN3IXj3iNlcuvLH4M8cxNiTVL61dSBpnXiyKwnd0vg li9ICsuQ3ZBt4rHRav8gGVbk1saHd9ZvujVagQnbE7XtTZ+BNO7GNGoM0hTTKQLMNOug GutYOHZdkGztxfn4wadM32BoIeBn6ehXBLzOHVHgEolLOdVewrQBRLIyIPAo/DmVeVV7 60uriVYnGUccFPE4/dBbT3uY4r888Z14Al700cKKNBQHaoIzy+u/63t/MaXOavtz2BI9 68hA==; darn=gnusha.org ARC-Authentication-Results: i=3; gmr-mx.google.com; dkim=pass header.i=@gmail.com header.s=20251104 header.b=Qur2bUvl; arc=pass (i=1); spf=pass (google.com: domain of laolu32@gmail.com designates 2607:f8b0:4864:20::b132 as permitted sender) smtp.mailfrom=laolu32@gmail.com; dmarc=pass (p=NONE sp=QUARANTINE dis=NONE) header.from=gmail.com; dara=pass header.i=@googlegroups.com DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=googlegroups.com; s=20251104; t=1777956110; x=1778560910; darn=gnusha.org; h=list-unsubscribe:list-subscribe:list-archive:list-help:list-post :list-id:mailing-list:precedence:x-original-authentication-results :x-original-sender:to:subject:message-id:date:from:mime-version :sender:from:to:cc:subject:date:message-id:reply-to; bh=G2K1XxOci/8V8ZjLbXGzApftKr6e8zUwxGnAdUBtRqQ=; b=Ri1HzZ9ATcF41eYZ/gqEXn6/rGKL99ET1O4472eRcYTAvW3SDoEwVFC14iD4vV20vB Er153xyf8XiVefNpCkdsBVgB1e/Cgz37ur1+s5EH+KNNZFuZlTNdVPY761zAzOTWi3VH WI7dcpYKzozvbAW8WlMvq0Aa/oMqAOJWq62HTKUEjPtjDDKJQTLCX7cFq19qCtYYf42O bM7huhYYtYyhl66JYEToWUwqW88+3zpQQszf4r4cxqaFjo8llNJVJ6epuIiUWP+gfxce Zw6YK5XxPtlUP63RqCwS83YVHuTPNA4IsW17HBhNys4QAz1w6WvvgKKQZtdpCJy93PnU iGiA== DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20251104; t=1777956110; x=1778560910; darn=gnusha.org; h=list-unsubscribe:list-subscribe:list-archive:list-help:list-post :list-id:mailing-list:precedence:x-original-authentication-results :x-original-sender:to:subject:message-id:date:from:mime-version:from :to:cc:subject:date:message-id:reply-to; bh=G2K1XxOci/8V8ZjLbXGzApftKr6e8zUwxGnAdUBtRqQ=; b=owiMnk048oyyUA+8eW4d/XdtvwabYhfyGAFrhZk40cM4aWA525iq+JxGEpXq0s6WKn KuqgY76CpMLkVScVbPjHFhTopjOJUT4gVjzhM4hq6N8fCNRSOxG4y+a/3reBSjJRKeum pVNrBRt+vyPD8qb34zagIWZxpHF+3+vLkHVHv1lO7l2MeXzMsTzBMxKVn0bIxCjrevyX mNNMgZ05QmiNujFoAD2z3yAmoRMO3JhR+W+bnYZCfPYcifMnfmDM46l9tu5ItrpTjTiH gV2JUxIt73tRWWvz9czKUPC2m13UBYvQVwRqSrQ3IWF2emcO/hn28C5QX+diNXpKt2sG F9/g== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20251104; t=1777956110; x=1778560910; h=list-unsubscribe:list-subscribe:list-archive:list-help:list-post :list-id:mailing-list:precedence:x-original-authentication-results :x-original-sender:to:subject:message-id:date:from:mime-version :x-gm-gg:x-beenthere:x-gm-message-state:sender:from:to:cc:subject :date:message-id:reply-to; bh=G2K1XxOci/8V8ZjLbXGzApftKr6e8zUwxGnAdUBtRqQ=; b=nUkScDKMZuCMGQJdDTioqdnOqsYU8pwXhAnNUk/7ukr2cs7vqEf925OyemK+AJQixC ir780Ds15si1442+ZTVaLQsXxogPiEW2xyS3aSsWs/2gWit9sMpQf4E+67ds7YDI+mY7 4kLIJQBmEX7+O14DhJFSADhEx25Q0lcxEykhfUREv1MOtSQ+t4xFa72ZSiibG4CJnZGu eKc8otAxOiIT5yrcK4yzjXLFiWcy4Q1Ep3g/M4Qx2Kjl4YUuyKV8ioXO+QUP3g93qOtG ECs8/Jjf1NfZMDaY5B9+ACqWvaiLwKXcUXm5FFVPlG+VTlkVqR7AAOgZx3pI50+gxtbo yBgA== Sender: bitcoindev@googlegroups.com X-Forwarded-Encrypted: i=3; AFNElJ/pHzTa9878Za1JRQ1qcOJFRXtwP+798tFagZYpV3AIjwhhAmYU2JePXKe3xrCymQBWUVYMY8YDlR0r@gnusha.org X-Gm-Message-State: AOJu0YyV+e3V+9lDAKtMtkc9NL205EuTqbLnRUDno+ATQamzXKeut4tB 8pVrl6NxmYJANmJHIf8ha49G6MhAMD2Wg6Eg/oEMoI+7L/LyUqKR5yTh X-Received: by 2002:a05:6870:3118:b0:42f:b835:9aa8 with SMTP id 586e51a60fabf-434761ae52dmr3619700fac.4.1777956109717; Mon, 04 May 2026 21:41:49 -0700 (PDT) X-BeenThere: bitcoindev@googlegroups.com; h="AUV6zMMTWpdL+ZCY7yUied1/p2dt95hbSiBKDOvmvxhOLKvgbA==" Received: by 2002:a05:6870:6488:b0:41c:64c3:46be with SMTP id 586e51a60fabf-43430002b17ls2860297fac.1.-pod-prod-07-us; Mon, 04 May 2026 21:41:43 -0700 (PDT) X-Received: by 2002:a05:6808:180a:b0:47b:c2a2:1c79 with SMTP id 5614622812f47-47c88fdb93cmr6231470b6e.1.1777956103670; Mon, 04 May 2026 21:41:43 -0700 (PDT) Received: by 2002:a05:6808:32ca:b0:47c:339e:add7 with SMTP id 5614622812f47-47c88e7fea0msb6e; Mon, 4 May 2026 21:40:56 -0700 (PDT) X-Received: by 2002:a17:90b:562d:b0:35d:a843:6b1f with SMTP id 98e67ed59e1d1-3650cd9871emr12426299a91.11.1777956055773; Mon, 04 May 2026 21:40:55 -0700 (PDT) ARC-Seal: i=2; a=rsa-sha256; t=1777956055; cv=pass; d=google.com; s=arc-20240605; b=BKoYTyz7FjpdyZ9heEdEmbawB3syV0+H3RrgLrW3MXOsKen9cUnbvLHf8LF6UGpvxg dxqhGqjobfWTZ/NE9zzTxPVZWaRRHLN7FZ66C3bFLR9xvVdbExOOcc42Q2XxjKPPA7Z9 1/hRz8bnQWVG3/f6jemiAuWWCYOibzRBkGHWOAjno5EFpVpqR6jN9Vt+Gs3edWzuxOXT Ys/25YdS5pjf2B1fsARhY88qdZ4gNtBNyxST1Nzx6Vxg7cmhCivmLyGdCc1f3Y5xuLCG IUnVA08/9RxVRUnq4BhAsh7Z+hD7dnr7JGQQpKZqvWfu5BrAzeOYHjCDFiLJRWeMmv0b Iywg== ARC-Message-Signature: i=2; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20240605; h=to:subject:message-id:date:from:mime-version:dkim-signature; bh=qEEuIQArHnnFM/VsvXVi6x+09W9a7LKBGfNNmX5YBZ4=; fh=DMP0F9ULS1guKiqimntQRCN8ZraraesEgQuVcn7F0Z0=; b=aPwjE1gm6Y1b38buGcW+l+eVeZoAX3R3pxOC1ZnB8vH7m6le/gVOvSHE/xhuVm/wXC s+W3U83NE19K+6GwFrUuEik0Y+osQPkT/rx0M70HTVoTfh5LlHpqd28uK8pzqsNs1EG+ ptsrWtCroB7TkzvaeJ5BzFjKdlBDEeCaxC0nCkwCExtRVEgIDF3ZykPSAJp9Y984lsj1 RSZLUkC9oTe4mXZi534dz7kX5wVAIpAg0VTHzC9Q6328f8bQuY7G5ZCYWyJJ/MtUAqjW bF20nyCrIKrNIJWDW2dkgoUUQPmVIG7ZXLjX/JvcofdjTwufn7XgOR78W6t0clpbtgfJ xpKw==; dara=google.com ARC-Authentication-Results: i=2; gmr-mx.google.com; dkim=pass header.i=@gmail.com header.s=20251104 header.b=Qur2bUvl; arc=pass (i=1); spf=pass (google.com: domain of laolu32@gmail.com designates 2607:f8b0:4864:20::b132 as permitted sender) smtp.mailfrom=laolu32@gmail.com; dmarc=pass (p=NONE sp=QUARANTINE dis=NONE) header.from=gmail.com; dara=pass header.i=@googlegroups.com Received: from mail-yx1-xb132.google.com (mail-yx1-xb132.google.com. [2607:f8b0:4864:20::b132]) by gmr-mx.google.com with ESMTPS id 98e67ed59e1d1-365782b18c2si30062a91.2.2026.05.04.21.40.55 for (version=TLS1_3 cipher=TLS_AES_128_GCM_SHA256 bits=128/128); Mon, 04 May 2026 21:40:55 -0700 (PDT) Received-SPF: pass (google.com: domain of laolu32@gmail.com designates 2607:f8b0:4864:20::b132 as permitted sender) client-ip=2607:f8b0:4864:20::b132; Received: by mail-yx1-xb132.google.com with SMTP id 956f58d0204a3-651c5d525f6so4407167d50.3 for ; Mon, 04 May 2026 21:40:55 -0700 (PDT) ARC-Seal: i=1; a=rsa-sha256; t=1777956054; cv=none; d=google.com; s=arc-20240605; b=AhCVmRxK1y0VkkgYOQYgsO171cFFvgbpwJotIgYR3f0aCYKiIMHVTF2t2nZJ8cI6kV S8Huc7L5LLgsqpqykx3dk+P5svk/i8srZzkAtwe3ku2nIpnuat8GS50lKm/VlN1MoV/F ldBkg04+BEQaHf1ptPbDX7P/0rWmT413/KKxNTZDMv2ekPuA1y9l5p40nMKqr81LUXdj dUZ4gJUr9pBcgPhs7vEZYMj4EG8fme6Bzh5oL5P7LMe3dhxGSqBGVVTt/bWYnY6iEokL xhI2b2gA0Rim4lQ8ca2hKHnkzrLDyHR7ynl54RPK7DeXuozCfTxKUe1B4qn0714ryXtb pnZQ== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20240605; h=to:subject:message-id:date:from:mime-version:dkim-signature; bh=qEEuIQArHnnFM/VsvXVi6x+09W9a7LKBGfNNmX5YBZ4=; fh=DMP0F9ULS1guKiqimntQRCN8ZraraesEgQuVcn7F0Z0=; b=HMeIWB3xmH76aEKuXlX3Fp2+5OdN1FqFn5jX4eF1dXQzLaBotJT2C2OZs+xHLXhR9Y Oem0GntFg9vfM/+GiNWVz6XHr1t1Rrb/dhTjhWU5AQgKzTEpbNvLrVKdyZzNS5wjwJn3 S+HrmxDm1Ax4n1SNceDAVYXYa7Onj3zuyU6FYcPP/RyogKMMVBrAPMSR2f8tzGWIVTXq L3mU1TXo41A2pgEzCisLmeM+uRHeb/oAtBkkhC/QjPdASKBbbUEQinTjRSUkHPAQTxXR hnPmt9N8dC3r7qNF6xla6ZlhgCVSht9sxSois/xfa/LYZwiQmcgOgWtguH3xAV+tJckt RuWg==; dara=google.com ARC-Authentication-Results: i=1; mx.google.com; arc=none X-Gm-Gg: AeBDieuZXdzVBKxc9WPZOoURpqPiv4GUYOy+gHaAVhzUnruJmMgDN4ZDmvuQ1ama8kJ QFNdOLT978c1YUe5c5a+IPDfGtqUzFa0tG04p6FF7lsHudq5fqs3b0pxB9vTePLiH/kstoBgdCr dhxch0PrXuQHxSu6NetDJH0Qjc/5c9Vl685PPGvpu6hHLXF2WKM4MyMrr/wVgRId1PcEy4M+DjC 0tq0TNvHeKJ21WZAC0rVoPwJLcv87Ep6GwZLH6HJRaOql0rCWMcg7EfNJI2JoXH+TKj1NEROXiG cEXX9lpRhmhNmzzNovOk6/kobYBgCG7ACxVnJRiHETEN9RJ0WO6YehFAdg/gKw3JFVO2PqmemVu BNDW40aqCRujX4DfpxA== X-Received: by 2002:a05:690e:43d0:b0:65c:30fc:6a7f with SMTP id 956f58d0204a3-65c3dae9dc4mr10098673d50.37.1777956054236; Mon, 04 May 2026 21:40:54 -0700 (PDT) MIME-Version: 1.0 From: Olaoluwa Osuntokun Date: Mon, 4 May 2026 23:40:42 -0500 X-Gm-Features: AVHnY4I6DSEIo7Lh2LzV6u6ZDAXG08BSj6w_LkM-vqx9k8GnRySQcKEKVQi-_ts Message-ID: Subject: [bitcoindev] A Post-Quantum Path for BIP 324 To: Bitcoin Development Mailing List Content-Type: multipart/alternative; boundary="0000000000000a02ad06510aa7e3" X-Original-Sender: laolu32@gmail.com X-Original-Authentication-Results: gmr-mx.google.com; dkim=pass header.i=@gmail.com header.s=20251104 header.b=Qur2bUvl; arc=pass (i=1); spf=pass (google.com: domain of laolu32@gmail.com designates 2607:f8b0:4864:20::b132 as permitted sender) smtp.mailfrom=laolu32@gmail.com; dmarc=pass (p=NONE sp=QUARANTINE dis=NONE) header.from=gmail.com; dara=pass header.i=@googlegroups.com Precedence: list Mailing-list: list bitcoindev@googlegroups.com; contact bitcoindev+owners@googlegroups.com List-ID: X-Google-Group-Id: 786775582512 List-Post: , List-Help: , List-Archive: , List-Unsubscribe: , X-Spam-Score: -0.5 (/) --0000000000000a02ad06510aa7e3 Content-Type: text/plain; charset="UTF-8" Hi y'all, In case you weren't already tired of all the recent dev list chatter re post quantum cryptography, here's another! When the topic of Bitcoin transitioning to a post quantum world is brought up, the discussion typically focuses on the consensus layer re swapping out vulnerable signature schemes. However, the consensus layer isn't the only area of Bitcoin that relies in cryptography that would be broken in the face of a powerful quantum computer! That's right, I'm talking about BIP 324, the peer to peer encryption BIP for Bitcoin. Like everything else on the Internet today, BIP 324 uses ECDH to allow two connecting peers to derive a shared secret known only to them, which is then used to encrypt all traffic between them. As ECDH relies on Elliptic Curve cryptography, a future quantum computer would be able to eavesdrop on a p2p handshake transcript, then derive the underlying private keys to the ephemeral ECDH public key, permitting it to decrypt all traffic. It's actually worse than that, as today adversaries can collect all encrypted p2p Bitcoin traffic, with the hope of being able to decrypt it all at a future date. This is commonly referred to as the: "harvest, decrypt later" (HNDL) strategy [11]. Compared to a consensus change, which requires widespread market agreement, and coordination to achieve, upgrading BIP 324 to be post quantum resistant is a much lower hanging fruit worthy of pursing immediately. Last week I starting thinking a bit about this topic, brushing up on the latest literature/techniques, and stumbled onto a few key design questions. The goal of this post isn't to propose a new concrete p2p encryption BIP, instead I want to start discussion on the various design tradeoffs that came up as I was researching this p2p encryption transition. ## PQ BIP 324 Design Questions 1. Do we want to pursue a hybrid KEM (key encapsulation mechanism), or go with a pure PQ KEM? 2. Is it still a key requirement that the initial handshake be indistinguishable from a random byte string? 2a. If yes to the above, then should we go with classical-then-pq-upgrade, or a one shot hybrid oblivious KEM. ## A Brief Intro to KEMs + ML-KEM First, let's introduce the new primitive we have to work with: ML-KEM (Module-Lattice-Based Key-Encapsulation Mechanism) [1][2]. As it says on the tin, ML-KEM is a lattice based Key-Encapsulation Mechanism. The phrase KEM might sound unfamiliar with those comfortable with ECDH, but ECDH is actually a KEM itself. A KEM has 3 algorithms: * KeyGen() -> {sk, pk} * Generates a public/private secret key pair * Encaps(pub) -> {secret, capsule} * Generates a new secret value, and a "capsule", which only the holder of pub can use to obtain the secret value. * Decaps(priv, capsule) -> secret * Uses the private key to extract the secret from the capsule If you squint a bit, then you'll see that ECDH is a KEM, and a rather elegant one at that: * KeyGen() -> {k, k*G} * Normal EC key generation. * Encaps(pub) -> {capsule = x*G, secret = pub*x} * The core ECDH routine. The ephemeral public key is actually the "capsule". The resulting secret is the ECDH output with the remote party's KEM public key and the local secret. * Decaps(priv, capsule) -> secret = priv * capsule * The receiver completes the key exchange using the ephemeral public key and their own private key. ECIES is another flavor of EC based KEM. One thing worth noting is that AFAICT, so far in the NIST PQC world [4], there is no known non-interactive key exchange protocol like we enjoy today with ECDH. IIUC, the reason is that lattice based schemes derived from the LWE [3] problem, whose security is predicated on using "noise" to hide a secret value. For these cryptosystems, usually a type of "hint" is sent to make everything work out nicely like in ECDH. However, in the stricter non-interactive setting (no messages sent), this doesn't map cleanly. As a result, ML-KEM looks more like a hybrid encryption protocol (Alice encrypts a shared secret to bob using asymmetric lattice crypto). ## To Hybrid KEM, Or Not to Hybrid KEM This brings us to our first design question.... Should we use a hybrid KEM or a pure post quantum one? A hybrid KEM would keep the existing ECDH, _also_ do ML-KEM, then securely combine (there's some subtlety there, see [6][7]) the resulting in a final secret value for encryption. A hybrid KEM is attractive as an encryption channel derived from such a KEM is secure if _any_ of the combined schemes are secure. This permits schemes to hedge a bit, as hey, maybe the PQ stuff is actually broken in the future but ECDH isn't. If it's the other way around, then your encryption scheme is still secure. ### Pure ML-KEM P2P Encrypted Handshake If we opt to not use a hybrid scheme, then the Elligator layer can be dropped all together. Instead, the 1.1 KB (ML-KEM-768) encapsulation keys are sent, keeping the trailing garbage+terminator in tact. The initial handshake would look something like: * Alice -> Bob: alice_encaps || initiator_garbage * Alice derives an encapsulation key, and sends it to Bob. * Bob -> Alice: ml_kem_capsule || responder_garbage || responder_garbage_terminator || first_encrypted_packet * Bob uses Alice's encapsulation key to encapsulate a random secret, and sends it over to Alice. He can also encrypt the first message at this point. * Alice -> Bob: initiator_garbage_terminator || first_encrypted_packet * Alice de-encapsulates the shared secret, and can now also start to encrypt messages. We'd then replace `v2_ecdh` with something like a `v3_mlkem` that derives the final shared secret based on the sent/received transcript up until that point: * `sha256_tagged("bip324_ml_kem", ml_kem_secret, alice_encaps, ml_kem_capsule)` ### Hybrid ML-KEM P2P Encrypted Handshake If we want to use a hybrid combiner, then along side the normal ellswift keys, the ML-KEM-768 encap key is also sent: * Alice -> Bob: ellswift_alice || alice_encaps || initiator_garbage * Bob -> Alice: ellswift_bob || ml_kem_capsule || responder_garbage || responder_garbage_terminator || first_encrypted_packet * Alice -> Bob: initiator_garbage_terminator || first_encrypted_packet Then following guidelines of [7], we'd then replace `v2_ecdh` with something like `v3_hybrid_shared_secret`: * `sha256_tagged("bip324_ellswift_xonly_ecdh_mlkem_768", ml_kem_ss, ecdh_point_x32, alice_encaps, ml_kem_capsule, ellswift_alice, ellswift_bob)` ## PQ/Hybrid Obfuscated KEMs At this point, those that are familiar with BIP 324 will recognize that both the pure PQ and hybrid versions renders the ElligatorSwift usage pretty much useless. ElligatorSwift encodes a 32-byte public key as a 64-byte value which is indistinguishable from a uniformly distributed bitstream. In a bubble, this means that the initial BIP 324 handshake to a 3rd party observer just looks like random bytes. However, with the introduction of ML-KEM, the ML-KEM encapsulation key is sent in plaintext over the wire. An ML-KEM key has identifiable structure, as it's a giant vector of polynomial coefficients mod 3329, which is easily recognizable over the wire. Luckily, there's an ML-KEM analogue to ElligatorSwift, called Kemeleon [8][9][10]! In a similar fashion to ElligatorSwift, it takes an ML-KEM public key, then encodes it as one giant integer, utilizing rejection sampling. Kemeleon applies this mapping both to the encapsulation keys, and also the capsule ciphertext that encrypts the shared secrets. The ML-KEM keys end up being a bit smaller, while the ciphertexts map to a larger value. Another tradeoff is that the Kemeleon key generation is ~3x slower than normal ML-KEM generation. One thing to note here is that Kemeleon's "looks random" property isn't quite on the same footing as ElligatorSwift's. ElligatorSwift is statistically indistinguishable from random, since every 512-bit string is a valid encoding. Kemeleon's indistinguishability is computational, resting on a Module-LWE style assumption. So if you naively concatenate an ElligatorSwift key and a Kemeleon key, the pair is only as obfuscated as the weakest visible half. This asymmetry is what motivates the OEINC construction discussed below. This brings us to our second design question.... Do we still want to ensure that the BIP-324 handshake looks identical to a pseudorandom bytestream from the very first message? Assuming yes, then AFAICT, we have two classes of options here: 1. Retain the existing BIP-324 outer ElligatorSwift handshake, but use ML-KEM within that initial encrypted transport to upgrade to a PQ shared secret. 2. Use the Outer Encrypts Inner Nested Combiner (OEINC - "OINK") combiner from [8]. 3. Attempt to adapt Drivel from [8] into the Bitcoin p2p setting. ### Classical Encrypted Channel Upgrades to PQ With the first option, we simply use one KEM right after the other. So BIP 324 v2 would be mostly unchanged, then we _upgrade_ to BIP 324 v3 within v2. A sketch of this would be something like: * Phase 0: normal BIP 324 handshake * Phase 1: negotiation of PQ KEM scheme over the encrypted handshake * Can be optional, if we just pick a set PQ KEM scheme. * Before this point, no Bitcoin p2p message should be sent, as the channel isn't PQC protected yet. * Phase 2: do normal ML-KEM within the ElligatorSwift derived encrypted transport 1. Alice sends the encapsulation key 2. Bob derives a secrets, encrypts it using the encapsulation key 3. Both sides then derive a PQ shared secret, ss_PQ * Phase 3: both sides use a hybrid combiner like sketched out above to derive a new set of transport keys * Phase 4: both sides rekey, switching over to a new the transport keys The upside of this option is that the outer part of BIP 324 remains unchanged, then with another round trip, we're able to upgrade the encryption keys to PQ hybrid security. The downside is that the very first messages sent aren't PQ from the start, but a PQ adversary wouldn't be able to decrypt the actual Bitcoin p2p messages (as we wait to send those until the upgrade). The handshake still looks like just random bytes. ### Outer Encrypts Inner Nested Combiner For the second option, [8] (with talk video [9] and slides [10]) describes an OEINC scheme where the outer KEM encrypts the inner KEM, wherein the KEM ciphertext of an inner KEM is encrypted using a shared secret derived from the outer KEM. The two KEM ciphertexts and the two derived keys are then used alongside a hybrid combiner to derive a final shared secret. Unlike the classical-then-pq-upgrade that establishes a classical channel, then uses that to upgrade to pq channel, OEINC is a special hybrid combiner that achieves a similar output but in one swoop. It defines a special KEM, which can then be used as the KEM in the very first handshake I sketched out. A sketch of this KEM looks something like: * Setup: * The outer KEM is BIP 324's ElligatorSwift-encoded secp256k1 DHKEM. * It serves as the outer KEM because its on-wire encoding is statistically indistinguishable from random. * The inner KEM is ML-Kemeleon. * KeyGen(): * (kem_secret_outer, kem_pubkey_outer) = outKEM.Gen() * (kem_secret_inner, kem_pubkey_inner) = inKEM.Gen() * combined_pubkey = (kem_pubkey_outer, kem_pubkey_inner) * combined_secret = (kem_secret_outer, kem_secret_inner) * Encaps(combined_pubkey): * (shared_secret_outer, capsule_outer) = outKEM.Encap(kem_pubkey_outer) * (encrypt_key_1, encrypt_key_2) = KDF(shared_secret_outer) * (shared_secret_inner, capsule_inner) = inKEM.Encap(kem_pubkey_inner) * encrypted_capsule_inner = encrypt(encrypt_key_1, capsule_inner) * combined_capsule = capsule_outer || encrypted_capsule_inner * combined_shared_secret = combine(encrypt_key_2, shared_secret_inner, combined_capsule) * Decaps(combined_secret, combined_capsule): * (capsule_outer, encrypted_capsule_inner) = combined_capsule * shared_secret_outer = outKEM.Decaps(kem_secret_outer, capsule_outer) * (encrypt_key_1, encrypt_key_2) = KDF(shared_secret_outer) * capsule_inner = decrypt(encrypt_key_1, encrypted_capsule_inner) * shared_secret_inner = inKEM.Decaps(kem_secret_inner, capsule_inner) * combined_shared_secret = combine(encrypt_key_2, shared_secret_inner, combined_capsule) This is done over just sending the two encapsulated secrets plainly as I outlined above in order to achieve a stronger security notion. The issue with this though is that though ciphertext uniformity (the encapsulated secrets) is achieved, the two public keys sent are randomly looking, but not in a uniform manner. In practice, this might not really matter much AFAICT (a theoretical adversary would be able to distinguish the Elligator half from the Kemeleon half). ### Drivel: PQ-Obfuscated Authentication The biggest issue with Drivel as a fit for BIP 324 is that it expects the initiator to already know a long term static public key for the responder. In the case of BIP 324, only ephemeral keys are exchanged, so there's no long term public keys known to either side. To get around this, we could extend BIP 155 (or make a new one likely, given size limits) to include a signed OKEM key. However then that would introduce authentication into the combined set, which explicitly wasn't a design goal of BIP 324. With that caveat in mind, here's the construction itself. Drivel [8] combines the OEINC scheme with another layer that out-of-the-box assumes an asymmetric protocol within a set client and server. The client uses an existing OEINC KEM public key published by the server to then encrypt a fresh new ephemeral KEM. ----- So there we have it. Before drafting a concrete v3 transport, we need to decide if we want a hybrid KEM, or are fine with a pure PQ KEM. Then we need to decide if we want to attempt to maintain the current quality where the p2p handshake transcript is indistinguishable from random. If yes, then that forces another series of decisions re how to construct/compose an oblivious KEM from available primitives. At a glance, the route of classical-then-pq-upgrade seems to be the simplest. BIP 324 stays as is, then we run ML-KEM within that. The ML-KEM keys are encrypted, so there's no need to sprinkle in the layer of Kemeleon. If we want a nice combined protocol, then we should investigate the OEINC route. It's more data to send as part of the initial handshake, but we still keep ElligatorSwift and use that as the outer KEM. If for some reason we're concerned with a future adversary gaining a distinguisher for Kemeleon, then maybe we need to bite the bullet and also roll out a full blown PQ authentication protocol along side everything. One thing worth flagging for any of the byte-0 designs (where PQ material is sent in the clear on the very first flight, like the hybrid and OEINC sketches above): ML-KEM-768 makes the responder do real work before it can decide if a connection is even legit. Today, the responder only needs the first 64 bytes of an ElligatorSwift share before it can derive the shared secret. With ML-KEM-768, the responder has to read and validate a 1184 byte encapsulation key before running Encaps, and FIPS 203 mandates input checks on every Encaps and Decaps. In a permissionless P2P network, that's a meaningful change in inbound DoS surface, and probably calls for stricter handshake byte limits, tighter timeouts, and possibly some form of stateless cookie/puzzle if handshake floods become a real problem. The classical-then-pq-upgrade path sidesteps most of this since the PQ material only shows up after the v2 channel is up. With all that said, after the above design decisions are addressed, there aren't too many concrete blockers here w.r.t rolling this out. Of course the development (eg: selecting/creating a library for ML-KEM and maybe ML-Kemeleon), and upgrade will take some time. But unlike the consensus layer, p2p encryption doesn't require the widespread market agreement that an actual soft fork does. BIP 324 is a much shorter walk to PQ than the consensus layer, and serves as a sort of PQ warm up before the bigger soft fork is tackled. -- Laolu [1]: https://en.wikipedia.org/wiki/ML-KEM [2]: https://csrc.nist.gov/pubs/fips/203/final [3]: https://en.wikipedia.org/wiki/Learning_with_errors [4]: This statement ignores Isogeny based crypto, and also SWOOSH [5] as it requires 200 KB pubkeys [5]: https://eprint.iacr.org/2023/271 [6]: https://eprint.iacr.org/2018/024 [7]: https://eprint.iacr.org/2020/1364 [8]: https://eprint.iacr.org/2024/1086 [9]: https://www.youtube.com/watch?v=CvFCYUq5rGg [10]: https://csrc.nist.gov/csrc/media/Presentations/2025/kemeleon/images-media/kemeleon.pdf [11]: https://en.wikipedia.org/wiki/Harvest_now,_decrypt_later -- You received this message because you are subscribed to the Google Groups "Bitcoin Development Mailing List" group. To unsubscribe from this group and stop receiving emails from it, send an email to bitcoindev+unsubscribe@googlegroups.com. To view this discussion visit https://groups.google.com/d/msgid/bitcoindev/CAO3Pvs9U3prZJiDs0Ns7LSA07R8hM-GQou_FcTZZz-JUQpUYHw%40mail.gmail.com. --0000000000000a02ad06510aa7e3 Content-Type: text/html; charset="UTF-8" Content-Transfer-Encoding: quoted-printable
Hi y'all,

In case you weren't already tire= d of all the recent dev list chatter re post
quantum cryptography, here&= #39;s another!

When the topic of Bitcoin transitioning to a post qua= ntum world is brought up,
the discussion typically focuses on the consen= sus layer re swapping out
vulnerable signature schemes. However, the con= sensus layer isn't the only area
of Bitcoin that relies in cryptogra= phy that would be broken in the face of a
powerful quantum computer! Tha= t's right, I'm talking about BIP 324, the peer to
peer encryptio= n BIP for Bitcoin.

Like everything else on the Internet today, BIP 3= 24 uses ECDH to allow two
connecting peers to derive a shared secret kno= wn only to them, which is then
used to encrypt all traffic between them.= As ECDH relies on Elliptic Curve
cryptography, a future quantum compute= r would be able to eavesdrop on a p2p
handshake transcript, then derive = the underlying private keys to the ephemeral
ECDH public key, permitting= it to decrypt all traffic. It's actually worse than
that, as today = adversaries can collect all encrypted p2p Bitcoin traffic, with
the hope= of being able to decrypt it all at a future date. This is commonly
refe= rred to as the: "harvest, decrypt later" (HNDL) strategy [11].
Compared to a consensus change, which requires widespread market agree= ment, and
coordination to achieve, upgrading BIP 324 to be post quantum = resistant is a
much lower hanging fruit worthy of pursing immediately.
Last week I starting thinking a bit about this topic, brushing up on = the latest
literature/techniques, and stumbled onto a few key design que= stions. The goal
of this post isn't to propose a new concrete p2p en= cryption BIP, instead I want
to start discussion on the various design t= radeoffs that came up as I was
researching this p2p encryption transitio= n.

## PQ BIP 324 Design Questions

1. Do we want to pursue a h= ybrid KEM (key encapsulation mechanism), or go with
=C2=A0 =C2=A0a pure = PQ KEM?

2. Is it still a key requirement that the initial handshake = be
=C2=A0 =C2=A0indistinguishable from a random byte string?

=C2= =A0 =C2=A02a. If yes to the above, then should we go with classical-then-pq= -upgrade,
=C2=A0 =C2=A0or a one shot hybrid oblivious KEM.


##= A Brief Intro to KEMs + ML-KEM

First, let's introduce the new p= rimitive we have to work with: ML-KEM
(Module-Lattice-Based Key-Encapsul= ation Mechanism) [1][2]. As it says on the
tin, ML-KEM is a lattice base= d Key-Encapsulation Mechanism. The phrase KEM
might sound unfamiliar wit= h those comfortable with ECDH, but ECDH is actually a
KEM itself.
A KEM has 3 algorithms:
=C2=A0 * KeyGen() -> {sk, pk}
=C2=A0 =C2= =A0 =C2=A0* Generates a public/private secret key pair

=C2=A0 * Enca= ps(pub) -> {secret, capsule}
=C2=A0 =C2=A0 =C2=A0* Generates a new se= cret value, and a "capsule", which only the holder of
=C2=A0 = =C2=A0 =C2=A0 =C2=A0pub can use to obtain the secret value.

=C2=A0 *= Decaps(priv, capsule) -> secret
=C2=A0 =C2=A0 =C2=A0* Uses the priva= te key to extract the secret from the capsule


If you squint a bi= t, then you'll see that ECDH is a KEM, and a rather elegant
one at t= hat:
=C2=A0 * KeyGen() -> {k, k*G}
=C2=A0 =C2=A0 =C2=A0 * Normal E= C key generation.

=C2=A0 * Encaps(pub) -> {capsule =3D x*G, secr= et =3D pub*x}
=C2=A0 =C2=A0 =C2=A0 * The core ECDH routine. The ephemera= l public key is actually the
=C2=A0 =C2=A0 =C2=A0 =C2=A0 "capsule&q= uot;. The resulting secret is the ECDH output with the remote
=C2=A0 =C2= =A0 =C2=A0 =C2=A0 party's KEM public key and the local secret.

= =C2=A0 * Decaps(priv, capsule) -> secret =3D priv * capsule
=C2=A0 = =C2=A0 =C2=A0 * The receiver completes the key exchange using the ephemeral= public key
=C2=A0 =C2=A0 =C2=A0 =C2=A0 and their own private key.
ECIES is another flavor of EC based KEM.

One thing worth noting is= that AFAICT, so far in the NIST PQC world [4], there is
no known non-in= teractive key exchange protocol like we enjoy today with ECDH.
IIUC, the= reason is that lattice based schemes derived from the LWE [3]
problem, = whose security is predicated on using "noise" to hide a secret va= lue.
For these cryptosystems, usually a type of "hint" is sent= to make everything
work out nicely like in ECDH. However, in the strict= er non-interactive setting
(no messages sent), this doesn't map clea= nly.

As a result, ML-KEM looks more like a hybrid encryption protoco= l (Alice
encrypts a shared secret to bob using asymmetric lattice crypto= ).

## To Hybrid KEM, Or Not to Hybrid KEM

This brings us to o= ur first design question....

Should we use a hybrid KEM or a pure po= st quantum one?

A hybrid KEM would keep the existing ECDH, _also_ d= o ML-KEM, then securely
combine (there's some subtlety there, see [6= ][7]) the resulting in a
final secret value for encryption. A hybrid KEM= is attractive as an encryption
channel derived from such a KEM is secur= e if _any_ of the combined schemes are
secure. This permits schemes to h= edge a bit, as hey, maybe the PQ stuff is
actually broken in the future = but ECDH isn't. If it's the other way around,
then your encrypti= on scheme is still secure.

### Pure ML-KEM P2P Encrypted Handshake
If we opt to not use a hybrid scheme, then the Elligator layer can be= dropped
all together. Instead, the 1.1 KB (ML-KEM-768) encapsulation ke= ys are sent,
keeping the trailing garbage+terminator in tact.

Th= e initial handshake would look something like:
=C2=A0* Alice -> Bob:= alice_encaps || initiator_garbage
=C2=A0 =C2=A0 * Alice derives an enca= psulation key, and sends it to Bob.

=C2=A0* Bob -> Alice: ml_kem_= capsule || responder_garbage || responder_garbage_terminator || first_encry= pted_packet
=C2=A0 =C2=A0* Bob uses Alice's encapsulation key to enc= apsulate a random secret, and
=C2=A0 =C2=A0 =C2=A0sends it over to Alice= . He can also encrypt the first message at this
=C2=A0 =C2=A0 =C2=A0poin= t.

=C2=A0* Alice -> Bob: initiator_garbage_terminator || first_en= crypted_packet
=C2=A0 =C2=A0* Alice de-encapsulates the shared secret, a= nd can now also start to encrypt
=C2=A0 =C2=A0 =C2=A0messages.

We= 'd then replace `v2_ecdh` with something like a `v3_mlkem` that derives= the
final shared secret based on the sent/received transcript up until = that point:
=C2=A0 * `sha256_tagged("bip324_ml_kem", ml_kem_se= cret, alice_encaps, ml_kem_capsule)`

### Hybrid ML-KEM P2P Encrypted= Handshake

If we want to use a hybrid combiner, then along side the = normal ellswift keys,
the ML-KEM-768 encap key is also sent:

=C2= =A0* Alice -> Bob: ellswift_alice || alice_encaps || initiator_garbage=C2=A0* Bob -> Alice: ellswift_bob || ml_kem_capsule || responder_garb= age || responder_garbage_terminator || first_encrypted_packet
=C2=A0* Al= ice -> Bob: initiator_garbage_terminator || first_encrypted_packet
Then following guidelines of [7], we'd then replace `v2_ecdh` with so= mething
like `v3_hybrid_shared_secret`:
=C2=A0 * `sha256_tagged("= ;bip324_ellswift_xonly_ecdh_mlkem_768", ml_kem_ss, ecdh_point_x32, ali= ce_encaps, ml_kem_capsule, ellswift_alice, ellswift_bob)`

## PQ/Hybr= id Obfuscated KEMs

At this point, those that are familiar with BIP 3= 24 will recognize that both
the pure PQ and hybrid versions renders the = ElligatorSwift usage pretty much
useless. ElligatorSwift encodes a 32-by= te public key as a 64-byte value which
is indistinguishable from a unifo= rmly distributed bitstream. In a bubble, this
means that the initial BIP= 324 handshake to a 3rd party observer just looks
like random bytes. How= ever, with the introduction of ML-KEM, the ML-KEM
encapsulation key is s= ent in plaintext over the wire. An ML-KEM key has
identifiable structure= , as it's a giant vector of polynomial coefficients mod
3329, which = is easily recognizable over the wire.

Luckily, there's an ML-KEM= analogue to ElligatorSwift, called Kemeleon
[8][9][10]! In a similar fa= shion to ElligatorSwift, it takes an ML-KEM public
key, then encodes it = as one giant integer, utilizing rejection sampling.
Kemeleon applies thi= s mapping both to the encapsulation keys, and also the
capsule ciphertex= t that encrypts the shared secrets. The ML-KEM keys end up
being a bit s= maller, while the ciphertexts map to a larger value. Another
tradeoff is= that the Kemeleon key generation is ~3x slower than normal ML-KEM
gener= ation.

One thing to note here is that Kemeleon's "looks ran= dom" property isn't quite
on the same footing as ElligatorSwift= 's. ElligatorSwift is statistically
indistinguishable from random, s= ince every 512-bit string is a valid encoding.
Kemeleon's indistingu= ishability is computational, resting on a Module-LWE
style assumption. S= o if you naively concatenate an ElligatorSwift key and a
Kemeleon key, t= he pair is only as obfuscated as the weakest visible half. This
asymmetr= y is what motivates the OEINC construction discussed below.

This bri= ngs us to our second design question....

Do we still want to ensure = that the BIP-324 handshake looks identical to a
pseudorandom bytestream = from the very first message?

Assuming yes, then AFAICT, we have two = classes of options here:
=C2=A0 1. Retain the existing BIP-324 outer El= ligatorSwift handshake, but use ML-KEM
=C2=A0 =C2=A0 =C2=A0within that i= nitial encrypted transport to upgrade to a PQ shared secret.

=C2=A0 = 2. Use the Outer Encrypts Inner Nested Combiner (OEINC - "OINK") = combiner
=C2=A0 =C2=A0 =C2=A0from [8].

=C2=A0 3. Attempt to adapt= Drivel from [8] into the Bitcoin p2p setting.

### Classical Encrypt= ed Channel Upgrades to PQ

With the first option, we simply use one K= EM right after the other. So BIP 324
v2 would be mostly unchanged, then = we _upgrade_ to BIP 324 v3 within v2.

A sketch of this would be som= ething like:
=C2=A0 * Phase 0: normal BIP 324 handshake
=C2=A0 * Phas= e 1: negotiation of PQ KEM scheme over the encrypted handshake
=C2=A0 = =C2=A0 =C2=A0* Can be optional, if we just pick a set PQ KEM scheme.
=C2= =A0 =C2=A0 =C2=A0* Before this point, no Bitcoin p2p message should be sent= , as the channel
=C2=A0 =C2=A0 =C2=A0 =C2=A0isn't PQC protected yet.=
=C2=A0 * Phase 2: do normal ML-KEM within the ElligatorSwift derived en= crypted
=C2=A0 =C2=A0 transport
=C2=A0 =C2=A0 =C2=A01. Alice sends th= e encapsulation key
=C2=A0 =C2=A0 =C2=A02. Bob derives a secrets, encryp= ts it using the encapsulation key
=C2=A0 =C2=A0 =C2=A03. Both sides then= derive a PQ shared secret, ss_PQ
=C2=A0 * Phase 3: both sides use a hyb= rid combiner like sketched out above to derive
=C2=A0 =C2=A0 a new set o= f transport keys
=C2=A0 * Phase 4: both sides rekey, switching over to a= new the transport keys

The upside of this option is that the outer = part of BIP 324 remains unchanged,
then with another round trip, we'= re able to upgrade the encryption keys to PQ
hybrid security. The downsi= de is that the very first messages sent aren't PQ
from the start, bu= t a PQ adversary wouldn't be able to decrypt the actual
Bitcoin p2p = messages (as we wait to send those until the upgrade). The
handshake sti= ll looks like just random bytes.

### Outer Encrypts Inner Nested Com= biner

For the second option, [8] (with talk video [9] and slides [10= ]) describes an
OEINC scheme where the outer KEM
encrypts the inner K= EM, wherein the KEM ciphertext of an inner KEM is encrypted
using a shar= ed secret derived from the outer KEM. The two KEM ciphertexts and
the tw= o derived keys are then used alongside a hybrid combiner to derive a
fin= al shared secret.

Unlike the classical-then-pq-upgrade that establi= shes a classical channel, then
uses that to upgrade to pq channel, OEINC= is a special hybrid combiner that
achieves a similar output but in one = swoop. It defines a special KEM, which can
then be used as the KEM in th= e very first handshake I sketched out.

A sketch of this KEM looks so= mething like:
=C2=A0 * Setup:
=C2=A0 =C2=A0 * The outer KEM is BIP 32= 4's ElligatorSwift-encoded secp256k1 DHKEM.
=C2=A0 =C2=A0 =C2=A0 =C2= =A0* It serves as the outer KEM because its on-wire encoding is
=C2=A0 = =C2=A0 =C2=A0 =C2=A0 =C2=A0statistically indistinguishable from random.
= =C2=A0 =C2=A0 * The inner KEM is ML-Kemeleon.

=C2=A0 * KeyGen():
= =C2=A0 =C2=A0 * (kem_secret_outer, kem_pubkey_outer) =3D outKEM.Gen()
= =C2=A0 =C2=A0 * (kem_secret_inner, kem_pubkey_inner) =3D inKEM.Gen()
=C2= =A0 =C2=A0 * combined_pubkey =3D (kem_pubkey_outer, kem_pubkey_inner)
= =C2=A0 =C2=A0 * combined_secret =3D (kem_secret_outer, kem_secret_inner)
=C2=A0 * Encaps(combined_pubkey):
=C2=A0 =C2=A0 * (shared_secret_ou= ter, capsule_outer) =3D outKEM.Encap(kem_pubkey_outer)
=C2=A0 =C2=A0 * (= encrypt_key_1, encrypt_key_2) =3D KDF(shared_secret_outer)
=C2=A0 =C2=A0= * (shared_secret_inner, capsule_inner) =3D inKEM.Encap(kem_pubkey_inner)=C2=A0 =C2=A0 * encrypted_capsule_inner =3D encrypt(encrypt_key_1, capsul= e_inner)
=C2=A0 =C2=A0 * combined_capsule =3D capsule_outer || encrypted= _capsule_inner
=C2=A0 =C2=A0 * combined_shared_secret =3D combine(encryp= t_key_2, shared_secret_inner, combined_capsule)

=C2=A0 * Decaps(comb= ined_secret, combined_capsule):
=C2=A0 =C2=A0 * (capsule_outer, encrypte= d_capsule_inner) =3D combined_capsule
=C2=A0 =C2=A0 * shared_secret_oute= r =3D outKEM.Decaps(kem_secret_outer, capsule_outer)
=C2=A0 =C2=A0 * (en= crypt_key_1, encrypt_key_2) =3D KDF(shared_secret_outer)
=C2=A0 =C2=A0 *= capsule_inner =3D decrypt(encrypt_key_1, encrypted_capsule_inner)
=C2= =A0 =C2=A0 * shared_secret_inner =3D inKEM.Decaps(kem_secret_inner, capsule= _inner)
=C2=A0 =C2=A0 * combined_shared_secret =3D combine(encrypt_key_2= , shared_secret_inner, combined_capsule)


This is done over just = sending the two encapsulated secrets plainly as I
outlined above in orde= r to achieve a stronger security notion. The issue with
this though is t= hat though ciphertext uniformity (the encapsulated secrets) is
achieved,= the two public keys sent are randomly looking, but not in a uniform
man= ner. In practice, this might not really matter much AFAICT (a theoreticaladversary would be able to distinguish the Elligator half from the Kemele= on
half).

### Drivel: PQ-Obfuscated Authentication

The big= gest issue with Drivel as a fit for BIP 324 is that it expects the
initi= ator to already know a long term static public key for the responder. Inthe case of BIP 324, only ephemeral keys are exchanged, so there's no = long
term public keys known to either side.

To get around this, w= e could extend BIP 155 (or make a new one likely, given
size limits) to = include a signed OKEM key. However then that would introduce
authenticat= ion into the combined set, which explicitly wasn't a design goal
of = BIP 324.

With that caveat in mind, here's the construction itsel= f. Drivel [8] combines
the OEINC scheme with another layer that out-of-t= he-box assumes an asymmetric
protocol within a set client and server. Th= e client uses an existing OEINC
KEM public key published by the server t= o then encrypt a fresh new ephemeral
KEM.

-----

So there = we have it. Before drafting a concrete v3 transport, we need to
decide i= f we want a hybrid KEM, or are fine with a pure PQ KEM. Then we need to
= decide if we want to attempt to maintain the current quality where the p2p<= br>handshake transcript is indistinguishable from random. If yes, then that= forces
another series of decisions re how to construct/compose an obliv= ious KEM from
available primitives.

At a glance, the route of cla= ssical-then-pq-upgrade seems to be the simplest.
BIP 324 stays as is, th= en we run ML-KEM within that. The ML-KEM keys are
encrypted, so there= 9;s no need to sprinkle in the layer of Kemeleon.

If we want a nice = combined protocol, then we should investigate the OEINC
route. It's = more data to send as part of the initial handshake, but we still
keep El= ligatorSwift and use that as the outer KEM.

If for some reason we= 9;re concerned with a future adversary gaining a
distinguisher for Kemel= eon, then maybe we need to bite the bullet and also
roll out a full blow= n PQ authentication protocol along side everything.

One thing worth = flagging for any of the byte-0 designs (where PQ material is
sent in the= clear on the very first flight, like the hybrid and OEINC sketches
abov= e): ML-KEM-768 makes the responder do real work before it can decide if aconnection is even legit. Today, the responder only needs the first 64 by= tes
of an ElligatorSwift share before it can derive the shared secret. W= ith
ML-KEM-768, the responder has to read and validate a 1184 byte encap= sulation
key before running Encaps, and FIPS 203 mandates input checks o= n every Encaps
and Decaps. In a permissionless P2P network, that's a= meaningful change in
inbound DoS surface, and probably calls for strict= er handshake byte limits,
tighter timeouts, and possibly some form of st= ateless cookie/puzzle if
handshake floods become a real problem. The cla= ssical-then-pq-upgrade path
sidesteps most of this since the PQ material= only shows up after the v2
channel is up.

With all that said, af= ter the above design decisions are addressed, there
aren't too many = concrete blockers here w.r.t rolling this out. Of course the
development= (eg: selecting/creating a library for ML-KEM and maybe
ML-Kemeleon), an= d upgrade will take some time. But unlike the consensus
layer, p2p encry= ption doesn't require the widespread market agreement that an
actual= soft fork does. BIP 324 is a much shorter walk to PQ than the consensuslayer, and serves as a sort of PQ warm up before the bigger soft fork istackled.=C2=A0


-- Laolu

[1]: https://en.wikipedia.org/wiki/ML-KEM
[2]: https://csrc.nist.gov/pu= bs/fips/203/final
[3]: https://en.wikipedia.org/wiki/Learning_with_errors[4]: This statement ignores Isogeny based crypto, and also SWOOSH [5] as i= t requires 200 KB pubkeys
[5]: https://eprint.iacr.org/2023/271
[6]: https://eprint.iacr.org/2018/024
[7]: https://eprint.iacr.org/2020/1364[8]: https://eprint.iacr.org= /2024/1086
[9]: https://www.youtube.com/watch?v=3DCvFCYUq5rGg
[10]: https://csrc.nist.gov/csrc/media/Presentations/2025/kemeleon/= images-media/kemeleon.pdf
[11]: https://en.wikipedia.org/wiki/Harvest_now,= _decrypt_later

--
You received this message because you are subscribed to the Google Groups &= quot;Bitcoin Development Mailing List" group.
To unsubscribe from this group and stop receiving emails from it, send an e= mail to bitcoind= ev+unsubscribe@googlegroups.com.
To view this discussion visit https://groups.google.com/d/ms= gid/bitcoindev/CAO3Pvs9U3prZJiDs0Ns7LSA07R8hM-GQou_FcTZZz-JUQpUYHw%40mail.g= mail.com.
--0000000000000a02ad06510aa7e3--