@@ -3322,31 +3322,29 @@ static bool ML_DSA_SIGGEN(const Span<const uint8_t> args[],
33223322 const Span<const uint8_t > context = args[4 ];
33233323 const Span<const uint8_t > extmu = args[5 ];
33243324
3325- using SignFunc = int (*)(const uint8_t *, uint8_t *, size_t *,
3326- const uint8_t *, size_t , const uint8_t *, size_t );
33273325 using SignInternalFunc = int (*)(const uint8_t *, uint8_t *, size_t *,
33283326 const uint8_t *, size_t ,
33293327 const uint8_t *, size_t , const uint8_t *);
33303328
33313329 // Group all related functions for each variant
33323330 struct MLDSA_functions {
33333331 void (*params_init)(ml_dsa_params*);
3334- SignFunc sign;
33353332 SignInternalFunc sign_internal;
33363333 SignInternalFunc extmu_sign_internal;
33373334 };
33383335
3339- // Select function set based on NID
3336+ // Select function set based on NID. We must use |ml_dsa_*_sign_internal| here,
3337+ // to account for the random inputs (rnd).
33403338 MLDSA_functions mldsa_funcs;
33413339 if (nid == NID_MLDSA44) {
3342- mldsa_funcs = {ml_dsa_44_params_init, ml_dsa_44_sign ,
3343- ml_dsa_44_sign_internal, ml_dsa_extmu_44_sign_internal};
3340+ mldsa_funcs = {ml_dsa_44_params_init, ml_dsa_44_sign_internal ,
3341+ ml_dsa_extmu_44_sign_internal};
33443342 } else if (nid == NID_MLDSA65) {
3345- mldsa_funcs = {ml_dsa_65_params_init, ml_dsa_65_sign ,
3346- ml_dsa_65_sign_internal, ml_dsa_extmu_65_sign_internal};
3343+ mldsa_funcs = {ml_dsa_65_params_init, ml_dsa_65_sign_internal ,
3344+ ml_dsa_extmu_65_sign_internal};
33473345 } else if (nid == NID_MLDSA87) {
3348- mldsa_funcs = {ml_dsa_87_params_init, ml_dsa_87_sign ,
3349- ml_dsa_87_sign_internal, ml_dsa_extmu_87_sign_internal};
3346+ mldsa_funcs = {ml_dsa_87_params_init, ml_dsa_87_sign_internal ,
3347+ ml_dsa_extmu_87_sign_internal};
33503348 } else {
33513349 return false ;
33523350 }
@@ -3357,12 +3355,8 @@ static bool ML_DSA_SIGGEN(const Span<const uint8_t> args[],
33573355 size_t signature_len = params.bytes ;
33583356 std::vector<uint8_t > signature (signature_len);
33593357
3360- if (!context.empty ()) {
3361- if (!mldsa_funcs.sign (sk.data (), signature.data (), &signature_len,
3362- msg.data (), msg.size (), context.data (), context.size ())) {
3363- return false ;
3364- }
3365- } else {
3358+ if (!extmu.empty ()) {
3359+ // Only signatureInterface: internal contains the externalMu field.
33663360 if (extmu.data ()[0 ] == 0 ) {
33673361 // generate the signatures raw sign mode
33683362 if (!mldsa_funcs.sign_internal (sk.data (), signature.data (), &signature_len,
@@ -3376,6 +3370,20 @@ static bool ML_DSA_SIGGEN(const Span<const uint8_t> args[],
33763370 return false ;
33773371 }
33783372 }
3373+ } else {
3374+ // |context| is unique to signatureInterface: external.
3375+ //
3376+ // Prepare |pre| exactly how |ml_dsa_sign| is doing. The maximum |context| size
3377+ // for ML-DSA is 255 bytes. We append a 0 and the size as two additional bytes
3378+ // before |context| to become the prefix string.
3379+ uint8_t pre [257 ];
3380+ pre [0 ] = 0 ;
3381+ pre [1 ] = context.size ();
3382+ OPENSSL_memcpy (pre + 2 , context.data (), context.size ());
3383+ if (!mldsa_funcs.sign_internal (sk.data (), signature.data (), &signature_len,
3384+ msg.data (), msg.size (), pre , 2 + context.size (), rnd.data ())) {
3385+ return false ;
3386+ }
33793387 }
33803388
33813389 return write_reply ({Span<const uint8_t >(signature)});
@@ -3418,12 +3426,8 @@ static bool ML_DSA_SIGVER(const Span<const uint8_t> args[], ReplyCallback write_
34183426 }
34193427
34203428 uint8_t reply[1 ] = {0 };
3421- if (!context.empty ()) {
3422- if (mldsa_funcs.verify (pk.data (), sig.data (), sig.size (), msg.data (),
3423- msg.size (), context.data (), context.size ())) {
3424- reply[0 ] = 1 ;
3425- }
3426- } else {
3429+ if (!extmu.empty ()) {
3430+ // Only signatureInterface: internal contains the externalMu field.
34273431 if (extmu.data ()[0 ] == 0 ) {
34283432 // verify the signatures raw sign mode
34293433 if (mldsa_funcs.verify_internal (pk.data (), sig.data (), sig.size (), msg.data (),
@@ -3437,6 +3441,12 @@ static bool ML_DSA_SIGVER(const Span<const uint8_t> args[], ReplyCallback write_
34373441 reply[0 ] = 1 ;
34383442 }
34393443 }
3444+ } else {
3445+ // |context| is unique to signatureInterface: external.
3446+ if (mldsa_funcs.verify (pk.data (), sig.data (), sig.size (), msg.data (),
3447+ msg.size (), context.data (), context.size ())) {
3448+ reply[0 ] = 1 ;
3449+ }
34403450 }
34413451
34423452 return write_reply ({Span<const uint8_t >(reply)});
0 commit comments