mldsa: implement function for deriving public key from secret key
authorFelix Fietkau <nbd@nbd.name>
Fri, 11 Jul 2025 09:25:56 +0000 (11:25 +0200)
committerFelix Fietkau <nbd@nbd.name>
Sat, 12 Jul 2025 08:33:56 +0000 (10:33 +0200)
Signed-off-by: Felix Fietkau <nbd@nbd.name>
mldsa.c
mldsa.h

diff --git a/mldsa.c b/mldsa.c
index b302712fe63d2092122d2f91d7aa3b4019eca25b..9db701c110ff0954e0bce2853800c1cf69cab14c 100644 (file)
--- a/mldsa.c
+++ b/mldsa.c
@@ -1862,6 +1862,36 @@ crypto_sign_keypair_internal(uint8_t *pk, uint8_t *sk,
   return 0;
 }
 
+int MLD_44_ref_pubkey(uint8_t *pk, const uint8_t *sk)
+{
+  uint8_t rho[MLDSA_SEEDBYTES];
+  uint8_t key[MLDSA_SEEDBYTES];
+  uint8_t tr[MLDSA_TRBYTES];
+  polyvecl mat[MLDSA_K];
+  polyvecl s1;
+  polyveck s2, t2, t1, t0;
+
+  unpack_sk(rho, tr, key, &t0, &s1, &s2, sk);
+
+  /* Expand matrix */
+  polyvec_matrix_expand(mat, rho);
+
+  /* Matrix-vector multiplication */
+  polyvecl_ntt(&s1);
+  polyvec_matrix_pointwise_montgomery(&t1, mat, &s1);
+  polyveck_reduce(&t1);
+  polyveck_invntt_tomont(&t1);
+
+  /* Add error vector s2 */
+  polyveck_add(&t1, &s2);
+
+  /* Extract t1 and write public key */
+  polyveck_caddq(&t1);
+  polyveck_power2round(&t2, &t0, &t1);
+  pack_pk(pk, rho, &t2);
+  return 0;
+}
+
 int MLD_44_ref_keypair(uint8_t *pk, uint8_t *sk)
 {
   uint8_t seed[MLDSA_SEEDBYTES];
diff --git a/mldsa.h b/mldsa.h
index 7c41d2b104e21138f366cae79f3b29e44bf8ffca..e451dff94f4b22451ae73c1053fee6852395016e 100644 (file)
--- a/mldsa.h
+++ b/mldsa.h
@@ -17,6 +17,7 @@
 #define MLD_44_ref_BYTES MLD_44_BYTES
 
 int MLD_44_ref_keypair(uint8_t *pk, uint8_t *sk);
+int MLD_44_ref_pubkey(uint8_t *pk, const uint8_t *sk);
 
 int MLD_44_ref_signature(uint8_t *sig, size_t *siglen, const uint8_t *m,
                          size_t mlen, const uint8_t *ctx, size_t ctxlen,