# How many nonce reuse before exposing your Musig2 private key?

**URL:** <https://delvingbitcoin.org/t/how-many-nonce-reuse-before-exposing-your-musig2-private-key/217>\
**Category:** Protocol Design\
**Tags:** musig2\
**Created:** [November 23, 2023, 3:02pm UTC](https://delvingbitcoin.org/t/how-many-nonce-reuse-before-exposing-your-musig2-private-key/217 "2023-11-23T15:02:56Z")\
**Posts on this page:** 5\
**Page:** 1

<div class="post-metadata">

**Author:** ![t-bast](https://delvingbitcoin.org/user_avatar/delvingbitcoin.org/t-bast/32/98_2.png) [@t-bast](https://delvingbitcoin.org/u/t-bast)\
**Post date:** [November 23, 2023, 3:02pm UTC](https://delvingbitcoin.org/t/how-many-nonce-reuse-before-exposing-your-musig2-private-key/217/1 "2023-11-23T15:02:56Z")

</div>

The [Musig2 BIP](https://github.com/bitcoin/bips/blob/e918b50731397872ad2922a1b08a5a4cd1d6d546/bip-0327.mediawiki) says that signing two distinct messages with the same `secnonce` exposes your private key. While I know we must absolutely not reuse `secnonces`, I wanted to check how the private key extraction worked and the difference with a standard schnorr sig.

And I couldn’t figure it out! It seems to me that an attacker would need **three** partial sigs for distinct messages using the same `secnonce`, **two** doesn’t seem to be enough?

Here is a simplified write-up of the equations, with a slightly different naming than the BIP to focus only on the important parts:

```auto
Alice has public key Pa = ka*G
Bob has public key Pb = kb*G
Q is the aggregated public key
R is the public aggregated nonce

b = H("noncecoef" || R || Q || m)
e = H("challenge" || R || Q || m)

=> implies that an attacker cannot choose (rb1', rb2') to influence b' thanks to H's preimage resistance

First signature for message m1:

  sa1 = ra1 + b1*ra2 + e1*a*ka
  sb1 = rb1 + b1*rb2 + e1*a*kb

Second signature for message m2 where Alice reuses ra1 and ra2:

  sa2 = ra1 + b2*ra2 + e2*a*ka
  sb2 = rb1' + b2*rb2' + e2*a*kb

The attacker ends up with:

  sa2 - sa1 = (b2 - b1)*ra2 + a*(e2 - e1)*ka

```

The attacker ends up with one equation but two unknowns (`ra2` and `ka`), so it’s not sufficient to extract `ka`? It needs a third signature to obtain a second equation and solve for both `ra2` and `ka`? What am I missing?

---

<div class="post-metadata">

**Author:** ![ajtowns](https://delvingbitcoin.org/user_avatar/delvingbitcoin.org/ajtowns/32/417_2.png) [@ajtowns](https://delvingbitcoin.org/u/ajtowns)\
**Post date:** [November 24, 2023, 1:33am UTC](https://delvingbitcoin.org/t/how-many-nonce-reuse-before-exposing-your-musig2-private-key/217/2 "2023-11-24T01:33:32Z")

</div>

I don’t think you’re missing anything; though perhaps some wagner-ish approach could also cause you to reveal your secret key if you sign many times while only using any single nonce pair twice. With musig2 you effectively have two nonces (ra\_1, ra\_2), so giving you three unknowns (ra\_1, ra\_2, ka) so needing three equations (signatures) to solve for three unknowns seems sensible.

---

<div class="post-metadata">

**Author:** ![conduition](https://delvingbitcoin.org/user_avatar/delvingbitcoin.org/conduition/32/384_2.png) [@conduition](https://delvingbitcoin.org/u/conduition)\
**Post date:** [November 24, 2023, 7:12am UTC](https://delvingbitcoin.org/t/how-many-nonce-reuse-before-exposing-your-musig2-private-key/217/3 "2023-11-24T07:12:11Z")

</div>

Neat point, i hadn’t thought of this till now.

I believe you are correct _for musig2._ But the older MuSig1 has no nonce coefficient b, and so reusing a nonce even once will expose your signing key the same way that reusing a Schnorr signing nonce will.

If you have three partial signatures under the same nonce, it is possible to extract the secret key, although the algebra involved is a bit overzealous.

Given:

- s\_1 = r\_1 + r\_2 b\_1 + e\_1 k a
- s\_2 = r\_1 + r\_2 b\_2 + e\_2 k a
- s\_3 = r\_1 + r\_2 b\_3 + e\_3 k a

You can solve for k as:

k = \frac{(s\_3-s\_1)(b\_2-b\_1) - (s\_2-s\_1)(b\_3-b\_1)}{a \left( (e\_3-e\_1)(b\_2-b\_1) + (e\_1-e\_2)(b\_3-b\_1) \right)}

I wrote a test to sanity check my math and indeed it does work: [add test to demonstrate computing secret keys from partial signatures… · conduition/musig2@778cc61 · GitHub](https://github.com/conduition/musig2/commit/778cc61d466d9cb418414bd2ff7692d2d6dba34d)

Also worth noting: Reusing nonces in musig is bad even if you are signing _the same message,_ because other signers can change their nonces and thus change the aggregated nonce, which changes e the same way that changing the message would.

---

<div class="post-metadata">

**Author:** ![real-or-random](https://delvingbitcoin.org/user_avatar/delvingbitcoin.org/real-or-random/32/413_2.png) [@real-or-random](https://delvingbitcoin.org/u/real-or-random)\
**Post date:** [March 7, 2024, 10:21am UTC](https://delvingbitcoin.org/t/how-many-nonce-reuse-before-exposing-your-musig2-private-key/217/4 "2024-03-07T10:21:47Z")

</div>

Indeed, you can’t extract the signing key from just two signatures with the same nonce. You’ll get two equations from the two signatures, but you have three unknowns.

But what’s also true is that security under concurrent sessions breaks down again. Assume the attacker can ask the honest signer for many concurrent signing sessions with limited reuse of nonces, i.e., each nonce (pair) may be used at most in two signing sessions. Then a forgery is possible.

The attack is very similar to the attack on “InsecureMuSig” descriped in the [MuSig2 paper](https://eprint.iacr.org/2020/1261.pdf) (pages 5 and 6). It just gets more hairy because we need to correct for b factors everywhere. Following the notation in the paper, the attacker opens \newcommand{\si}{k} \newcommand{\smax}{k\_{\mathrm{max}}} \newcommand{\Hsig}{\mathsf{H}\_{\mathrm{sig}}} \newcommand{\tX}{\widetilde{X}} \smax session _pairs_, where the user reuses the same nonce pair in the two sessions belonging to a session pair. That is, the user (signer index 1), responds with \smax nonce pairs (R\_{1,1}^{(\si)}, R\_{1,2}^{(\si)}). The adversary (signer index 2) chooses a targer message m^\*, computes R^\* = \prod\_{k=1}^{\smax} R\_{1,1}^{(\si)} and uses [Wagner’s algorithm](https://web.archive.org/web/20230507110001/https://people.eecs.berkeley.edu/~daw/papers/genbday-long.ps) or the recently discovered and much faster [BLLOR algorithm](https://eprint.iacr.org/2020/945.pdf) to find their nonce pairs (R\_{2,1}^{(k)}, R\_{2,2}^{(k)}) for each session pair such that

\sum\_{\si=1}^{\smax} \underbrace{ \frac{b^{(\si,2)} c^{(\si,1)} - b^{(\si,1)} c^{(\si,1)}}{b^{(\si,2)} - b^{(\si,1)}} }\_{=:\,c^{(\si)}} = \underbrace{\Hsig(\tX, R^\*, m^\*)}\_{=:\,c^\*},

where b^{(\si,1)}, b^{(\si,2)} are the two b values in the two sessions belonging to session pair k, and

c^{(\si,i)} := \Hsig\left(\tX, R\_{1,1}^{(\si)}\left(R\_{1,2}^{(\si)}\right)^{b^{(\si,i)}} R\_{2,1}^{(\si)} \left(R\_{2,2}^{(\si)}\right)^{b^{(\si,i)}}, m^{(\si)}\right), \qquad i \in \{1,2\}.

Having received (R\_{2,1}^{(k)}, R\_{2,2}^{(k)}) in the two sessions, the honest signer will reply with partial signatures

s\_1^{(\si,1)} = r\_{1,1}^{(\si)} + b^{(\si,1)} r\_{1,2} + c^{(\si,1)} \cdot a\_1x\_1, \\ s\_1^{(\si,2)} = r\_{1,1}^{(\si)} + b^{(\si,2)} r\_{1,2} + c^{(\si,2)} \cdot a\_1x\_1.

Multiplying the first equation with b^{(\si,2)}, and the second with -b^{(\si,1)}, and adding the two resulting equations yields

b^{(\si,2)} s\_1^{(\si,1)} - b^{(\si,1)} s\_1^{(\si,2)} = (b^{(\si,2)} - b^{(\si,1)}) r\_{1,1} ^{(\si)} + (b^{(\si,2)} c^{(\si,1)} - b^{(\si,1)} c^{(\si,1)}) \cdot a\_1x\_1.

By further dividing by b^{(\si,2)} - b^{(\si,1)} (which is non-zero with overwhelming probability), defining

s\_1^{(\si)} := \frac{ b^{(\si,2)} s\_1^{(\si,1)} - b^{(\si,1)} s\_1^{(\si,2)}}{b^{(\si,2)} - b^{(\si,1)}},

and substituting r\_1 := r\_{1,1}, we obtain

s\_1^{(\si)} = r\_1 ^{(\si)} + c^{(k)} \cdot a\_1x\_1

exactly as in the paper. The attack then proceeds as described in the paper.

_edit: If you see rendering errors in the equations, try to reload the page. I think Discourse here uses some optimizations where it loads the equations in the wrong order, and then they won’t work._

* * *

> [@t-bast](#):
>
> The [Musig2 BIP](https://github.com/bitcoin/bips/blob/e918b50731397872ad2922a1b08a5a4cd1d6d546/bip-0327.mediawiki) says that signing two distinct messages with the same `secnonce` exposes your private key.

Are you referring to the following statement from BIP327?

> The _Sign_ algorithm must **not** be executed twice with the same _secnonce_. Otherwise, it is possible to extract the secret signing key from the two partial signatures output by the two executions of _Sign_.’

Hm, yes, we should probably change the wording here.

---

<div class="post-metadata">

**Author:** ![t-bast](https://delvingbitcoin.org/user_avatar/delvingbitcoin.org/t-bast/32/98_2.png) [@t-bast](https://delvingbitcoin.org/u/t-bast)\
**Post date:** [March 7, 2024, 12:24pm UTC](https://delvingbitcoin.org/t/how-many-nonce-reuse-before-exposing-your-musig2-private-key/217/5 "2024-03-07T12:24:52Z")

</div>

Thanks for this detailed analysis @real-or-random, this is very instructive!
