Fix GOST 2012 SPKI algorithm OID for legacy CryptoPro parameter sets - #709
Open
danielbarsh wants to merge 1 commit into
Open
Fix GOST 2012 SPKI algorithm OID for legacy CryptoPro parameter sets#709danielbarsh wants to merge 1 commit into
danielbarsh wants to merge 1 commit into
Conversation
… update GOST parameter check; add unit test for GOST R 34.10-2012 encoding
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Problem
SubjectPublicKeyInfoFactory.CreateSubjectPublicKeyInfochose between the GOST R 34.10-2001 algorithmOID (
id-GostR3410-2001) and the GOST R 34.10-2012 OIDs (id-tc26-gost3410-12-256/512) based solelyon whether the key's
PublicKeyParamSet(curve) was one of the legacy CryptoPro sets(A/B/C/XchA/XchB), ignoring
DigestParamSetentirely:Per RFC 9215's backward-compatibility rules, a legacy CryptoPro curve can legitimately be paired with a
GOST R 34.11-2012 digest — that's a valid GOST 2012 key and must be encoded with a 2012 algorithm OID,
not 2001. The curve alone doesn't determine the algorithm version.
Spec reference
RFC 9215 ("Using GOST R 34.10-2012 and GOST R 34.11-2012 Algorithms with the Internet X.509 Public Key
Infrastructure"), Section 4.2 ("Public Key Parameters"):
and, further in the same section:
So the outer algorithm OID identifies the signature scheme version (2001 vs 2012);
publicKeyParamSetonly selects the curve, independently of that — and the RFC's own compatibility rule requires exactly
the CryptoPro-curve + 2012-digest combination this fix handles.
Fix
SubjectPublicKeyInfoFactorynow branches onDigestParamSet(legacy GOST R 34.11-94 CryptoPro paramset vs a 2012 digest) instead of on the curve. The 256/512 sub-selection within the 2012 branch is
unchanged (still based on field size, which is curve-derived and unaffected by this change). The
now-unused
cryptoProOidsset (and theSystem.Collections.Genericimport it needed) was removed.Note: bc-java's
SubjectPublicKeyInfoFactoryhas the identical curve-only check today, so this isn't aC#-specific mis-port — happy to raise the equivalent issue there if useful.
Testing
Added
Gost2012CryptoProSpkiTest:This generates a key on a legacy CryptoPro curve (
GostR3410x2001CryptoProA) with a GOST 2012 digestOID and asserts the encoded
SubjectPublicKeyInfocarries the 2012 algorithm OID rather than the 2001one. Also re-ran
ECGOST3410_2012TestandGost3410Testto confirm no regression on thenative-2012-curve and pure-2001-key paths — all pass.