lsd0007

LSD0007: GNUnet communicators
Log | Files | Refs

commit af9b6d6479f2667375dfca9a9c949da37f9cadbf
parent b41ec1d897284983e79266bc998c6021ec082b19
Author: Pedram Fardzadeh <p.fardzadeh@protonmail.com>
Date:   Mon,  1 Jul 2024 22:56:34 +0200

Added Elligator key creation

Diffstat:
Mdraft-gnunet-communicators.xml | 55++++++++++++++++++++++++++++++++++++++++++-------------
1 file changed, 42 insertions(+), 13 deletions(-)

diff --git a/draft-gnunet-communicators.xml b/draft-gnunet-communicators.xml @@ -266,11 +266,13 @@ KDF(A,Z): Let G be the basepoint of Curve25519, EdToCurve() a function which converts Ed25519 points to their corresponding Curve25519 points, Enc() Elligator's encoding function, Dec() Elligator's decoding function, "X" the receiver's peer identity (a 256-bit EdDSA public key), - "x" the corresponding secret key, "a" a 256-bit ephemeral secret key. Observe that: + "x" the corresponding secret key, + "A" an ephemeral public key (256-bit Curve25519 public key) and + "a" the corresponding 256-bit ephemeral secret key. Observe that: </t> <artwork name="" type="" align="left" alt=""><![CDATA[ (x, X) := KeyGenEd25519() -(a, A) := KeyGenX25519() +(a, A) := ElligatorKeyCreate() Z := X25519(a, EdToCurve(X)) = X25519(x, A) ]]></artwork> <t> @@ -1401,15 +1403,42 @@ Enc(X): return REPR ]]></artwork> <t> - The encoding function is defined for the entire Curve25519. In modern cryptoghraphic systems, mostly public keys from the prime - subgroup of Curve25519 are used. The exclusive use of the prime subgroup is a recognizable property that an outside observer can - easily detect. To circumvent this issue, we need to randomly choose an curve point from the whole curve. (FIXME: Include our implementation). - By ensuring that the x-coordinate is from a randomly chosen curve point on the entire curve, the resulting representatives do not possess any - properties that could be used by an attacker to identify them as curve point coordinates anymore. + The encoding function is defined for the entire Curve25519. Most modern implementations of Curve25519 only generate points from its prime + subgroup to circumvent known attacks for which points not within the prime subgroup are susceptible. In our case, those attacks are not an + issue as we use the ephemeral secret key only once for computing key material. The exclusive use of the prime subgroup is a recognizable + property that an outside observer can easily detect, even in the case of using the encoding function. An attacker could decode the suspected + parts of packets to the corresponding Curve25519 points and check if the resulting points are always in the prime subgroup. To circumvent + this attack, we need to choose the ephemeral key pair randomly from the whole curve. One way to generate such a key pair is depicted below, + where G is the generator of the prime order group of Ed25519, H the generator of the low order subgroup of Ed25519 and EdToCurve() a function + which converts Ed25519 points to their corresponding Curve25519 points: </t> + <artwork name="" type="" align="left" alt=""><![CDATA[ +ElligatorGenerateKey(): + a := random(256) + ED_high := clamps(a).G + ED_low := (a mod 8).H + ED := ED_high + ED_low + A := EdToCurve(ED) + return (a, A) + ]]></artwork> +<t> +The general idea is to create both a random high-order curve point and a low-order curve point. Adding them together results in a curve point +that is evenly distributed on the whole Curve25519. Not all Curve25519 points are eligible to be used with Elligator for a key exchange. In +particular, not all points will have the property that the encoding and subsequent decoding result in the original point. The mathematical +reasoning will be explained later after looking into Elligator's decoding function. To create a valid Curve25519 point that can be used as an +ephemeral key, one needs to generate as many curve points until the property holds: +<artwork name="" type="" align="left" alt=""><![CDATA[ +ElligatorKeyCreate(): + VALID := 0 + while(VALID): + (a, A) := ElligatorGenerateKey() + if dec(enc(A)) == A: + VALID := 1 + return (a, A) + ]]></artwork> <t> The corresponding decoding function which is used by the elligator decapsulation function in <xref target="decaps"/> to recover the - x-coordinate is defined below: + x-coordinate from the representative is defined below: </t> <artwork name="" type="" align="left" alt=""><![CDATA[ Dec(REPR): @@ -1419,11 +1448,11 @@ Dec(REPR): return X ]]></artwork> <t> - Note that both for a value REPR and its negative counterpart -REPR (in the finite field), the decoding function will result in the - same x-coordinate. Moreover, for two different valid x-coordinates the resulting representatives are different. Conversely, - this means that we can't decode both representatives back to their original x-coordinate. This effectivly reduces the entropy of our - public keys by 1 bit, which is torelable. With this in mind, the sender need test that the generated ephemeral public key result in the - same public key after an encoding and subsequent decoding call. + Note that both for a value REPR and its negative counterpart -REPR (in the finite field), the decoding function will result in the same + x-coordinate. Moreover, for two different valid x-coordinates, the resulting representatives of the corresponding encoding calls are + different. Conversely, this means that we can't decode both representatives back to their original x-coordinate. This is why the sender + eventually makes multiple calls to ElligatorGenerateKey() in ElligatorKeyCreate() in order to create a valid public key that can be used + for a key exchange. Also note that this effectively reduces the entropy of our public keys by 1 bit, which is tolerable. </t> <t> In the original paper, Elligator's encoding function takes the sign of y-coordinate as an additional input parameter. Its value determines