Exemplo n.º 1
0
 /// <summary>
 ///     This function checks the magic value in the key blob header
 /// </summary>
 /// <param name="magic">The expected magic number.</param>
 /// <param name="includePrivateParameters">Private blob if true else public key blob</param>
 private static void CheckMagicValueOfKey(KeyBlobMagicNumber magic, bool includePrivateParameters)
 {
     if (includePrivateParameters)
     {
         if (magic != KeyBlobMagicNumber.BCRYPT_DSA_PRIVATE_MAGIC && magic != KeyBlobMagicNumber.BCRYPT_DSA_PRIVATE_MAGIC_V2)
         {
             throw new CryptographicException(SR.Cryptography_NotValidPrivateKey);
         }
     }
     else
     {
         if (magic != KeyBlobMagicNumber.BCRYPT_DSA_PUBLIC_MAGIC && magic != KeyBlobMagicNumber.BCRYPT_DSA_PUBLIC_MAGIC_V2)
         {
             throw new CryptographicException(SR.Cryptography_NotValidPublicOrPrivateKey);
         }
     }
 }
Exemplo n.º 2
0
        public override DSAParameters ExportParameters(bool includePrivateParameters)
        {
            byte[] dsaBlob = ExportKeyBlob(includePrivateParameters);

            KeyBlobMagicNumber magic = (KeyBlobMagicNumber)BitConverter.ToInt32(dsaBlob, 0);

            // Check the magic value in the key blob header. If the blob does not have the required magic,
            // then throw a CryptographicException.
            CheckMagicValueOfKey(magic, includePrivateParameters);

            unsafe
            {
                DSAParameters dsaParams = default;

                fixed(byte *pDsaBlob = dsaBlob)
                {
                    int offset;

                    if (magic == KeyBlobMagicNumber.BCRYPT_DSA_PUBLIC_MAGIC || magic == KeyBlobMagicNumber.BCRYPT_DSA_PRIVATE_MAGIC)
                    {
                        if (dsaBlob.Length < sizeof(BCRYPT_DSA_KEY_BLOB))
                        {
                            throw ErrorCode.E_FAIL.ToCryptographicException();
                        }

                        BCRYPT_DSA_KEY_BLOB *pBcryptBlob = (BCRYPT_DSA_KEY_BLOB *)pDsaBlob;
                        // We now have a buffer laid out as follows:
                        //     BCRYPT_DSA_KEY_BLOB  header
                        //     byte[cbKey]               P
                        //     byte[cbKey]               G
                        //     byte[cbKey]               Y
                        //     -- Private only --
                        //     byte[Sha1HashOutputSize]  X

                        offset = sizeof(KeyBlobMagicNumber) + sizeof(int); // skip Magic and cbKey

                        // Read out a (V1) BCRYPT_DSA_KEY_BLOB structure.
                        dsaParams.Counter = BinaryPrimitives.ReadInt32BigEndian(Interop.BCrypt.Consume(dsaBlob, ref offset, 4));
                        dsaParams.Seed    = Interop.BCrypt.Consume(dsaBlob, ref offset, Sha1HashOutputSize);
                        dsaParams.Q       = Interop.BCrypt.Consume(dsaBlob, ref offset, Sha1HashOutputSize);

                        Debug.Assert(offset == sizeof(BCRYPT_DSA_KEY_BLOB), $"Expected offset = sizeof(BCRYPT_DSA_KEY_BLOB), got {offset} != {sizeof(BCRYPT_DSA_KEY_BLOB)}");
                        dsaParams.P = Interop.BCrypt.Consume(dsaBlob, ref offset, pBcryptBlob->cbKey);
                        dsaParams.G = Interop.BCrypt.Consume(dsaBlob, ref offset, pBcryptBlob->cbKey);
                        dsaParams.Y = Interop.BCrypt.Consume(dsaBlob, ref offset, pBcryptBlob->cbKey);
                        if (includePrivateParameters)
                        {
                            dsaParams.X = Interop.BCrypt.Consume(dsaBlob, ref offset, Sha1HashOutputSize);
                        }
                    }
                    else
                    {
                        Debug.Assert(magic == KeyBlobMagicNumber.BCRYPT_DSA_PUBLIC_MAGIC_V2 || magic == KeyBlobMagicNumber.BCRYPT_DSA_PRIVATE_MAGIC_V2);

                        if (dsaBlob.Length < sizeof(BCRYPT_DSA_KEY_BLOB_V2))
                        {
                            throw ErrorCode.E_FAIL.ToCryptographicException();
                        }

                        BCRYPT_DSA_KEY_BLOB_V2 *pBcryptBlob = (BCRYPT_DSA_KEY_BLOB_V2 *)pDsaBlob;
                        // We now have a buffer laid out as follows:
                        //     BCRYPT_DSA_KEY_BLOB_V2  header
                        //     byte[cbSeedLength]      Seed
                        //     byte[cbGroupSize]       Q
                        //     byte[cbKey]             P
                        //     byte[cbKey]             G
                        //     byte[cbKey]             Y
                        //     -- Private only --
                        //     byte[cbGroupSize]       X

                        offset = sizeof(BCRYPT_DSA_KEY_BLOB_V2) - 4; //skip to Count[4]

                        // Read out a BCRYPT_DSA_KEY_BLOB_V2 structure.
                        dsaParams.Counter = BinaryPrimitives.ReadInt32BigEndian(Interop.BCrypt.Consume(dsaBlob, ref offset, 4));

                        Debug.Assert(offset == sizeof(BCRYPT_DSA_KEY_BLOB_V2), $"Expected offset = sizeof(BCRYPT_DSA_KEY_BLOB_V2), got {offset} != {sizeof(BCRYPT_DSA_KEY_BLOB_V2)}");

                        dsaParams.Seed = Interop.BCrypt.Consume(dsaBlob, ref offset, pBcryptBlob->cbSeedLength);
                        dsaParams.Q    = Interop.BCrypt.Consume(dsaBlob, ref offset, pBcryptBlob->cbGroupSize);
                        dsaParams.P    = Interop.BCrypt.Consume(dsaBlob, ref offset, pBcryptBlob->cbKey);
                        dsaParams.G    = Interop.BCrypt.Consume(dsaBlob, ref offset, pBcryptBlob->cbKey);
                        dsaParams.Y    = Interop.BCrypt.Consume(dsaBlob, ref offset, pBcryptBlob->cbKey);
                        if (includePrivateParameters)
                        {
                            dsaParams.X = Interop.BCrypt.Consume(dsaBlob, ref offset, pBcryptBlob->cbGroupSize);
                        }
                    }

                    // If no counter/seed information is present, normalize Counter and Seed to 0/null to maintain parity with the CAPI version of DSA.
                    if (dsaParams.Counter == -1)
                    {
                        dsaParams.Counter = 0;
                        dsaParams.Seed    = null;
                    }

                    Debug.Assert(offset == dsaBlob.Length, $"Expected offset = dsaBlob.Length, got {offset} != {dsaBlob.Length}");

                    return(dsaParams);
                }
            }
        }
Exemplo n.º 3
0
 /// <summary>
 ///     This function checks the magic value in the key blob header
 /// </summary>
 /// <param name="includePrivateParameters">Private blob if true else public key blob</param>
 private static void CheckMagicValueOfKey(KeyBlobMagicNumber magic, bool includePrivateParameters)
 {
     if (includePrivateParameters)
     {
         if (magic != KeyBlobMagicNumber.BCRYPT_DSA_PRIVATE_MAGIC && magic != KeyBlobMagicNumber.BCRYPT_DSA_PRIVATE_MAGIC_V2)
             throw new CryptographicException(SR.Cryptography_NotValidPrivateKey);
     }
     else
     {
         if (magic != KeyBlobMagicNumber.BCRYPT_DSA_PUBLIC_MAGIC && magic != KeyBlobMagicNumber.BCRYPT_DSA_PUBLIC_MAGIC_V2)
             throw new CryptographicException(SR.Cryptography_NotValidPublicOrPrivateKey);
     }
 }