<li>BLS12_381Aggregation.aggregateVerifyHashed previously fed the per-signer (pk_i, H(msg_i)) pairs straight into the multi-pairing, omitting the per-message public-key aggregation and identity-rejection step required by draft-irtf-cfrg-bls-signature §2.9 lines 12-13. An attacker who controlled pk_a and pk_b = -pk_a (each with a valid PoP, since they hold both secret keys) could publish an aggregate over (pk_a, m), (pk_b, m), (pk_c, m') whose pk_a / pk_b contributions cancelled in the pairing equation, reducing it to a check of pk_c on m' while the aggregate still ostensibly claimed contributions from pk_a and pk_b. BLS12_381BasicScheme.aggregateVerify pre-screened by rejecting duplicate messages and BLS12_381MessageAugmentation folded the public key into the hash input so the spec grouping was trivial, but BLS12_381ProofOfPossession.aggregateVerify took the unmodified helper path. The shared helper now groups signers by hashed message, sums the public keys per group, and rejects the aggregate when any per-group key equals the G1 identity (the spec form for §2.9); all three schemes inherit the check.</li>
0 commit comments