コード例 #1
0
        public static X509Certificate2 CopyWithPrivateKey(this X509Certificate2 certificate, Gost3410 privateKey)
        {
            if (certificate == null)
            {
                throw new ArgumentNullException(nameof(certificate));
            }
            if (privateKey == null)
            {
                throw new ArgumentNullException(nameof(privateKey));
            }

            if (certificate.HasPrivateKey)
            {
                throw new InvalidOperationException(SR.Cryptography_Cert_AlreadyHasPrivateKey);
            }

            using (Gost3410 publicKey = GetGost3410PublicKey(certificate))
            {
                if (publicKey == null)
                {
                    throw new ArgumentException(SR.Cryptography_PrivateKey_WrongAlgorithm);
                }

                //Gost3410Parameters currentParameters = publicKey.ExportParameters(false);
                //Gost3410Parameters newParameters = privateKey.ExportParameters(false);
            }

            ICertificatePal pal = certificate.Pal.CopyWithPrivateKey(privateKey);

            return(new X509Certificate2(pal));
        }
コード例 #2
0
 public void Encrypt2001()
 {
     using (Gost3410 gost = GetGostProvider())
     {
         Encrypt(gost);
     }
 }
コード例 #3
0
ファイル: GostSharedSecretTest.cs プロジェクト: Trivin/corefx
        // Шифрование тестового файла.
        static void EncryptTestFile(
            Gost3410 publicKey,
            Gost3410CryptoServiceProvider privateKey,
            string fileId = "2001")
        {
            // Создаем симметричный ключ.
            Gost28147 symmetric = Gost28147.Create();

            // Открываем ключ отправителя.
            Gost3410Parameters srcPublicKeyParameters = privateKey.ExportParameters(false);

            // Создаем agree ключ
            GostSharedSecretAlgorithm agree = privateKey.CreateAgree(
                publicKey.ExportParameters(false));

            // Зашифровываем симметричный ключ на agree ключе.
            byte[] WrappedKey = agree.Wrap(symmetric,
                                           GostKeyWrapMethod.CryptoPro12KeyWrap);

            // Создаем поток шифратора.
            ICryptoTransform transform = symmetric.CreateEncryptor();

            // Создаем зашифрованный файл.
            using (FileStream ofs = new FileStream(string.Format(EncryptedFileName, fileId), FileMode.Create))
            {
                BinaryWriter bw = new BinaryWriter(ofs);

                // Записываем зашифрованный симметричный ключ.
                bw.Write(WrappedKey.Length);
                bw.Write(WrappedKey);

                // Записываем синхропосылку
                bw.Write(symmetric.IV.Length);
                bw.Write(symmetric.IV);

                // Передаем открытый ключ.
                BinaryFormatter formatter = new BinaryFormatter();
                formatter.Serialize(ofs, srcPublicKeyParameters);

                // Создаем поток шифрования для записи в файл.
                using (CryptoStream cs = new CryptoStream(ofs, transform, CryptoStreamMode.Write))
                {
                    byte[] data = new byte[4096];
                    // Открываем входной файл.
                    using (FileStream ifs = new FileStream(string.Format(SourceFileName, fileId), FileMode.Open, FileAccess.Read))
                    {
                        // и переписываем содержимое в выходной поток.
                        int length = ifs.Read(data, 0, data.Length);
                        while (length > 0)
                        {
                            cs.Write(data, 0, length);
                            length = ifs.Read(data, 0, data.Length);
                        }
                    }
                }
            }
        }
コード例 #4
0
        // begin: gost
        public static X509SignatureGenerator CreateForGost(Gost3410 key)
        {
            if (key == null)
            {
                throw new ArgumentNullException(nameof(key));
            }

            return(new Gost3410SignatureGenerator(key));
        }
コード例 #5
0
        /// <summary>
        /// Create a self-signed certificate using the established subject, key, and optional
        /// extensions.
        /// </summary>
        /// <param name="notBefore">
        ///   The oldest date and time where this certificate is considered valid.
        ///   Typically <see cref="DateTimeOffset.UtcNow"/>, plus or minus a few seconds.
        /// </param>
        /// <param name="notAfter">
        ///   The date and time where this certificate is no longer considered valid.
        /// </param>
        /// <returns>
        ///   An <see cref="X509Certificate2"/> with the specified values. The returned object will
        ///   assert <see cref="X509Certificate2.HasPrivateKey" />.
        /// </returns>
        /// <exception cref="ArgumentException">
        ///   <paramref name="notAfter"/> represents a date and time before <paramref name="notAfter"/>.
        /// </exception>
        /// <exception cref="InvalidOperationException">
        ///   A constructor was used which did not accept a signing key.
        /// </exception>>
        /// <exception cref="CryptographicException">
        ///   Other errors during the certificate creation process.
        /// </exception>
        public X509Certificate2 CreateSelfSigned(DateTimeOffset notBefore, DateTimeOffset notAfter)
        {
            if (notAfter < notBefore)
            {
                throw new ArgumentException(SR.Cryptography_CertReq_DatesReversed);
            }
            if (_key == null)
            {
                throw new InvalidOperationException(SR.Cryptography_CertReq_NoKeyProvided);
            }

            Debug.Assert(_generator != null);

            byte[] serialNumber = new byte[8];
            RandomNumberGenerator.Fill(serialNumber);

            using (X509Certificate2 certificate = Create(
                       SubjectName,
                       _generator,
                       notBefore,
                       notAfter,
                       serialNumber))
            {
                RSA rsa = _key as RSA;

                if (rsa != null)
                {
                    return(certificate.CopyWithPrivateKey(rsa));
                }

                ECDsa ecdsa = _key as ECDsa;

                if (ecdsa != null)
                {
                    return(certificate.CopyWithPrivateKey(ecdsa));
                }

                Gost3410 gost3410 = _key as Gost3410;
                if (gost3410 != null)
                {
                    return(certificate.CopyWithPrivateKey(gost3410));
                }
                Gost3410_2012_256 gost3410_2012_256 = _key as Gost3410_2012_256;
                if (gost3410_2012_256 != null)
                {
                    return(certificate.CopyWithPrivateKey(gost3410_2012_256));
                }
                Gost3410_2012_512 gost3410_2012_512 = _key as Gost3410_2012_512;
                if (gost3410_2012_512 != null)
                {
                    return(certificate.CopyWithPrivateKey(gost3410_2012_512));
                }
            }

            Debug.Fail($"Key was of no known type: {_key?.GetType().FullName ?? "null"}");
            throw new CryptographicException();
        }
コード例 #6
0
        private static bool VerifySignature(Gost3410 publicKey, Stream dataStream, byte[] signature)
        {
            byte[] hash;

            using (var hashAlg = new Gost3411HashAlgorithm())
            {
                hash = hashAlg.ComputeHash(dataStream);
            }

            return(publicKey.VerifySignature(hash, signature));
        }
コード例 #7
0
        private static byte[] CreateSignature(Gost3410 privateKey, Stream dataStream)
        {
            byte[] hash;

            using (var hashAlg = new Gost3411HashAlgorithm())
            {
                hash = hashAlg.ComputeHash(dataStream);
            }

            return(privateKey.CreateSignature(hash));
        }
コード例 #8
0
        private static XmlDocument EncryptXmlDocument(XmlDocument xmlDocument, Gost3410 publicKey)
        {
            // Создание объекта для шифрации XML
            var encryptedXml = new GostEncryptedXml();

            // Поиск элементов для шифрации
            var elements = xmlDocument.SelectNodes("//SomeElement[@Encrypt='true']");

            if (elements != null)
            {
                var elementIndex = 0;

                foreach (XmlElement element in elements)
                {
                    // Создание случайного сессионного ключа
                    using (var sessionKey = new Gost28147SymmetricAlgorithm())
                    {
                        // Шифрация элемента
                        var encryptedData = encryptedXml.EncryptData(element, sessionKey, false);

                        // Шифрация сессионного ключа с использованием публичного асимметричного ключа
                        var encryptedSessionKeyData = GostEncryptedXml.EncryptKey(sessionKey, publicKey);

                        // Формирование элемента EncryptedData
                        var elementEncryptedData = new EncryptedData();
                        elementEncryptedData.Id                     = "EncryptedElement" + elementIndex++;
                        elementEncryptedData.Type                   = EncryptedXml.XmlEncElementUrl;
                        elementEncryptedData.EncryptionMethod       = new EncryptionMethod(GostEncryptedXml.XmlEncGost28147Url);
                        elementEncryptedData.CipherData.CipherValue = encryptedData;
                        elementEncryptedData.KeyInfo                = new KeyInfo();

                        // Формирование информации о зашифрованном сессионном ключе
                        var encryptedSessionKey = new EncryptedKey();
                        encryptedSessionKey.CipherData       = new CipherData(encryptedSessionKeyData);
                        encryptedSessionKey.EncryptionMethod = new EncryptionMethod(GostEncryptedXml.XmlEncGostKeyTransportUrl);
                        encryptedSessionKey.AddReference(new DataReference {
                            Uri = "#" + elementEncryptedData.Id
                        });
                        encryptedSessionKey.KeyInfo.AddClause(new KeyInfoName {
                            Value = "KeyName1"
                        });

                        // Добавление ссылки на зашифрованный ключ, используемый при шифровании данных
                        elementEncryptedData.KeyInfo.AddClause(new KeyInfoEncryptedKey(encryptedSessionKey));

                        // Замена элемента его зашифрованным представлением
                        GostEncryptedXml.ReplaceElement(element, elementEncryptedData, false);
                    }
                }
            }

            return(xmlDocument);
        }
コード例 #9
0
        /// <summary>
        /// Зашифровать симметричный ключ
        /// </summary>
        /// <param name="symmKey"></param>
        /// <param name="recipientName"></param>
        /// <returns></returns>
        public byte[] EncryptSymmKey(Gost28147 symmKey, string recipientName)
        {
            Log.DssLogger.Debug($"Шифрование симметричного ключа на получателя {recipientName}");

            byte[] returnArray;

            try
            {
                X509Certificate2 cert = _certificateService.FindAddressBookCertificateBySubjectName(recipientName)
                                        .Result;

                // Если ничего не нашли - выходим
                if (cert == null)
                {
                    return(null);
                }

                // Открытый ключ получателя.
                AsymmetricAlgorithm pk        = cert.PublicKey.Key;
                Gost3410            recipient = pk as Gost3410;
                if (recipient == null)
                {
                    throw new CryptographicException("Not a gost certificate");
                }

                GostKeyExchangeFormatter keyFormatter = new GostKeyExchangeFormatter(recipient);

                byte[] transport = keyFormatter.CreateKeyExchangeData(symmKey);

                // Создаем зашифрованный файл.
                using (MemoryStream ms = new MemoryStream())
                {
                    // Записываем зашифрованный симметричный ключ в виде транспортного представления.
                    BinaryWriter bw = new BinaryWriter(ms);
                    bw.Write(transport.Length);
                    bw.Write(transport);

                    // Записываем синхропосылку
                    bw.Write(symmKey.IV.Length);
                    bw.Write(symmKey.IV);

                    returnArray = ms.ToArray();
                }
            }
            catch (Exception exp)
            {
                Log.DssLogger.Error($"Ошибка при зашифровании симметричного ключа: {exp}");
                returnArray = null;
            }

            return(returnArray);
        }
コード例 #10
0
        private static byte[] CreateSignature(Gost3410 privateKey, Stream dataStream)
        {
            byte[] hash;

            using (var hashAlg = new Gost3411HashAlgorithm())
            {
                hash = hashAlg.ComputeHash(dataStream);
            }

            var formatter = new GostSignatureFormatter(privateKey);

            return(formatter.CreateSignature(hash));
        }
コード例 #11
0
        public static byte[] EncryptKey(Gost28147 sessionKey, Gost3410 publicKey)
        {
            if (sessionKey == null)
            {
                throw ExceptionUtility.ArgumentNull("sessionKey");
            }

            if (publicKey == null)
            {
                throw ExceptionUtility.ArgumentNull("publicKey");
            }

            var formatter = new GostKeyExchangeFormatter(publicKey);

            return(formatter.CreateKeyExchangeData(sessionKey));
        }
コード例 #12
0
ファイル: Form1.cs プロジェクト: dmitriyzyuzin/CryptoPro
        private void Form1_Load(object sender, EventArgs e)
        {
            mode    = new byte[3];
            mode[0] = 0x01;
            mode[1] = 0x02;
            mode[2] = 0x03;

            cert = get_certificate_by_name("flex2424");
            CspParameters csp_params = new CspParameters(75, null, container_name);

            csp  = new Gost3410CryptoServiceProvider(csp_params);
            sign = cert.PublicKey.Key as Gost3410;

            foreach (StoreLocation storeLocation in (StoreLocation[])
                     Enum.GetValues(typeof(StoreLocation)))
            {
                if (storeLocation.ToString() == "CurrentUser")
                {
                    foreach (StoreName storeName in (StoreName[])
                             Enum.GetValues(typeof(StoreName)))
                    {
                        if (storeName.ToString() == "My")
                        {
                            // Выводим все сертификаты в /Текущий пользователь/Личное
                            X509Store store = new X509Store(storeName, storeLocation);

                            try
                            {
                                store.Open(OpenFlags.OpenExistingOnly);
                                foreach (X509Certificate2 certificate in store.Certificates)
                                {
                                    comboBox1.Items.Add(certificate.GetName());
                                }
                            }
                            catch (CryptographicException)
                            {
                                MessageBox.Show("Exception in comboBox");
                            }
                        }
                    }
                }
            }
        }
コード例 #13
0
ファイル: Form1.cs プロジェクト: alextrof94/GetElnList
        /// <summary>
        /// Получает ключ для расшифровки на основе зашифрованных данных (из примеров криптопро)
        /// </summary>
        /// <param name="exml"></param>
        /// <param name="encryptedData"></param>
        /// <returns>Алгоритм для расшифровки</returns>
        private SymmetricAlgorithm GetDecryptionKey(EncryptedXml exml, EncryptedData encryptedData)
        {
            IEnumerator encryptedKeyEnumerator = encryptedData.KeyInfo.GetEnumerator();

            // Проходим по всем KeyInfo
            while (encryptedKeyEnumerator.MoveNext())
            {
                // Пропускам все что неизвестно.
                KeyInfoEncryptedKey current = encryptedKeyEnumerator.Current as KeyInfoEncryptedKey;
                if (current == null)
                {
                    continue;
                }
                // До первого EncryptedKey
                EncryptedKey encryptedKey = current.EncryptedKey;
                if (encryptedKey == null)
                {
                    continue;
                }
                KeyInfo keyinfo = encryptedKey.KeyInfo;
                // Проходим по всем KeyInfo зашифрования ключа.
                IEnumerator srcKeyEnumerator = keyinfo.GetEnumerator();
                while (srcKeyEnumerator.MoveNext())
                {
                    // Пропускам все что неизвестно.
                    KeyInfoX509Data keyInfoCert = srcKeyEnumerator.Current
                                                  as KeyInfoX509Data;
                    if (keyInfoCert == null)
                    {
                        continue;
                    }
                    AsymmetricAlgorithm alg   = certOur.PrivateKey; // Приватный ключ, открытый ключ которого мы отправляли при шифровании запроса
                    Gost3410            myKey = alg as Gost3410;    // Преобразования
                    if (myKey == null)
                    {
                        continue;
                    }
                    // Получаем и возвращаем ключ для расшифровки
                    return(CPEncryptedXml.DecryptKeyClass(encryptedKey.CipherData.CipherValue, myKey, encryptedData.EncryptionMethod.KeyAlgorithm));
                }
            }
            return(null);
        }
コード例 #14
0
ファイル: GostKeyExchangeTests.cs プロジェクト: Trivin/corefx
        public void TestKeyExchange2001()
        {
            // Ассиметричный ключ получателя.
            Gost3410 AssymKey;

            // Синхропосылка.
            byte[] IV;

            // Создаем случайный открытый ключ.
            using (Gost3410 gkey = GetGostProvider2001())
            {
                AssymKey = gkey;

                // Создаем случайный секретный ключ, который необходимо передать.
                Gost28147 key = new Gost28147CryptoServiceProvider();
                // Синхропосылка не входит в GostKeyTransport и должна
                // передаваться отдельно.
                IV = key.IV;

                // Создаем форматтер, шифрующий на ассиметричном ключе получателя.
                GostKeyExchangeFormatter Formatter = new GostKeyExchangeFormatter(AssymKey);
                // GostKeyTransport - формат зашифрованной для безопасной передачи
                // ключевой информации.
                GostKeyTransport encKey = Formatter.CreateKeyExchange(key);

                // Шифруемая строка
                string message     = "012345678901234567890";
                byte[] sourceBytes = Encoding.ASCII.GetBytes(message);
                Console.WriteLine("** Строка до шифрования: " + message);

                // Шифруем строку на сессионном ключе
                byte[] encBytes = GostEncrypt(key, sourceBytes);
                Console.WriteLine("** Строка после шифрования: " +
                                  Encoding.ASCII.GetString(encBytes));

                // Получатель расшифровывает GostKeyTransport и само сообщение.
                byte[] decBytes = GostDecrypt(encKey, encBytes, IV, AssymKey);
                Console.WriteLine("** Строка после расшифрования: " +
                                  Encoding.ASCII.GetString(decBytes));

                Assert.Equal(sourceBytes, decBytes);
            }
        }
コード例 #15
0
        /// <summary>
        /// Create a CertificateRequest for the specified subject name, GOST3410 key, and hash algorithm.
        /// </summary>
        /// <param name="subjectName">
        ///   The parsed representation of the subject name for the certificate or certificate request.
        /// </param>
        /// <param name="key">
        ///   n GOST3410 key whose public key material will be included in the certificate or certificate request.
        ///   This key will be used as a private key if <see cref="CreateSelfSigned" /> is called.
        /// </param>
        /// <param name="hashAlgorithm">
        ///   The hash algorithm to use when signing the certificate or certificate request.
        /// </param>
        public CertificateRequest(X500DistinguishedName subjectName, Gost3410 key, HashAlgorithmName hashAlgorithm)
        {
            if (subjectName == null)
            {
                throw new ArgumentNullException(nameof(subjectName));
            }
            if (key == null)
            {
                throw new ArgumentNullException(nameof(key));
            }
            if (string.IsNullOrEmpty(hashAlgorithm.Name))
            {
                throw new ArgumentException(SR.Cryptography_HashAlgorithmNameNullOrEmpty, nameof(hashAlgorithm));
            }

            SubjectName = subjectName;

            _key          = key;
            _generator    = X509SignatureGenerator.CreateForGost(key);
            PublicKey     = _generator.PublicKey;
            HashAlgorithm = hashAlgorithm;
        }
コード例 #16
0
        private static XmlDocument SignXmlDocument(XmlDocument xmlDocument, Gost3410 signingKey)
        {
            // Создание подписчика XML-документа
            var signedXml = new SignedXml(xmlDocument);

            // Установка ключа для создания подписи
            signedXml.SigningKey = signingKey;
            signedXml.SignedInfo.CanonicalizationMethod = SignedXml.XmlDsigExcC14NTransformUrl;
            signedXml.SignedInfo.SignatureMethod        = SignedXml.XmlDsigGost3410Url;

            // Ссылка на узел, который нужно подписать, с указанием алгоритма хэширования
            //var dataReference = new Reference { Uri = "#Id1", DigestMethod = GostSignedXml.XmlDsigGost3411Url };
            var dataReference = new Reference();

            dataReference.AddTransform(new XmlDsigEnvelopedSignatureTransform());
            dataReference.AddTransform(new XmlDsigExcC14NTransform());
            dataReference.DigestMethod = SignedXml.XmlDsigGost3411Url;
            dataReference.Uri          = "";

            // Установка ссылки на узел
            signedXml.AddReference(dataReference);

            // Установка информации о ключе, который использовался для создания подписи
            var keyInfo = new KeyInfo();

            keyInfo.AddClause(new GostKeyValue(signingKey));
            signedXml.KeyInfo = keyInfo;

            // Вычисление подписи
            signedXml.ComputeSignature();

            // Получение XML-представления подписи
            var signatureXml = signedXml.GetXml();

            // Добавление подписи в исходный документ
            xmlDocument.DocumentElement.AppendChild(xmlDocument.ImportNode(signatureXml, true));

            return(xmlDocument);
        }
コード例 #17
0
ファイル: GostKeyValue.cs プロジェクト: dprotopopov/corefx
 /// <summary>
 /// Инициализирует новый экземпляр класса <c>GostKeyValue</c> с новым,
 /// сгенерированным случайным образом открытым ключом ГОСТ 34.10-2001.
 /// </summary>
 /// <remarks>При создании нового ключа ГОСТ 34.10-2001 этот конструктор
 /// использует реализацию <see cref="Gost3410"/> по
 /// умолчанию, как определено классом
 /// <see cref="System.Security.Cryptography.CryptoConfig"/>.</remarks>
 public GostKeyValue()
 {
     _key = (Gost3410)Gost3410.Create();
 }
コード例 #18
0
        /// <summary>
        /// Create a certificate using the established subject, key, and optional extensions using
        /// the provided certificate as the issuer.
        /// </summary>
        /// <param name="issuerCertificate">
        ///   An X509Certificate2 instance representing the issuing Certificate Authority (CA).
        /// </param>
        /// <param name="notBefore">
        ///   The oldest date and time where this certificate is considered valid.
        ///   Typically <see cref="DateTimeOffset.UtcNow"/>, plus or minus a few seconds.
        /// </param>
        /// <param name="notAfter">
        ///   The date and time where this certificate is no longer considered valid.
        /// </param>
        /// <param name="serialNumber">
        ///   The serial number to use for the new certificate. This value should be unique per issuer.
        ///   The value is interpreted as an unsigned (big) integer in big endian byte ordering.
        /// </param>
        /// <returns>
        ///   An <see cref="X509Certificate2"/> with the specified values. The returned object will
        ///   not assert <see cref="X509Certificate2.HasPrivateKey" />.
        /// </returns>
        /// <exception cref="ArgumentNullException"><paramref name="issuerCertificate"/> is null.</exception>
        /// <exception cref="ArgumentException">
        ///   The <see cref="X509Certificate2.HasPrivateKey"/> value for <paramref name="issuerCertificate"/> is false.
        /// </exception>
        /// <exception cref="ArgumentException">
        ///   The type of signing key represented by <paramref name="issuerCertificate"/> could not be determined.
        /// </exception>
        /// <exception cref="ArgumentException">
        ///   <paramref name="notAfter"/> represents a date and time before <paramref name="notBefore"/>.
        /// </exception>
        /// <exception cref="ArgumentException"><paramref name="serialNumber"/> is null or has length 0.</exception>
        /// <exception cref="ArgumentException">
        ///   <paramref name="issuerCertificate"/> has a different key algorithm than the requested certificate.
        /// </exception>
        /// <exception cref="InvalidOperationException">
        ///   <paramref name="issuerCertificate"/> is an RSA certificate and this object was created via a constructor
        ///   which does not accept a <see cref="RSASignaturePadding"/> value.
        /// </exception>
        public X509Certificate2 Create(
            X509Certificate2 issuerCertificate,
            DateTimeOffset notBefore,
            DateTimeOffset notAfter,
            byte[] serialNumber)
        {
            if (issuerCertificate == null)
            {
                throw new ArgumentNullException(nameof(issuerCertificate));
            }
            if (!issuerCertificate.HasPrivateKey)
            {
                throw new ArgumentException(SR.Cryptography_CertReq_IssuerRequiresPrivateKey, nameof(issuerCertificate));
            }
            if (notAfter < notBefore)
            {
                throw new ArgumentException(SR.Cryptography_CertReq_DatesReversed);
            }
            if (serialNumber == null || serialNumber.Length < 1)
            {
                throw new ArgumentException(SR.Arg_EmptyOrNullArray, nameof(serialNumber));
            }

            if (issuerCertificate.PublicKey.Oid.Value != PublicKey.Oid.Value)
            {
                throw new ArgumentException(
                          SR.Format(
                              SR.Cryptography_CertReq_AlgorithmMustMatch,
                              issuerCertificate.PublicKey.Oid.Value,
                              PublicKey.Oid.Value),
                          nameof(issuerCertificate));
            }

            DateTime notBeforeLocal = notBefore.LocalDateTime;

            if (notBeforeLocal < issuerCertificate.NotBefore)
            {
                throw new ArgumentException(
                          SR.Format(
                              SR.Cryptography_CertReq_NotBeforeNotNested,
                              notBeforeLocal,
                              issuerCertificate.NotBefore),
                          nameof(notBefore));
            }

            DateTime notAfterLocal = notAfter.LocalDateTime;

            // Round down to the second, since that's the cert accuracy.
            // This makes one method which uses the same DateTimeOffset for chained notAfters
            // not need to do the rounding locally.
            long notAfterLocalTicks = notAfterLocal.Ticks;
            long fractionalSeconds  = notAfterLocalTicks % TimeSpan.TicksPerSecond;

            notAfterLocalTicks -= fractionalSeconds;
            notAfterLocal       = new DateTime(notAfterLocalTicks, notAfterLocal.Kind);

            if (notAfterLocal > issuerCertificate.NotAfter)
            {
                throw new ArgumentException(
                          SR.Format(
                              SR.Cryptography_CertReq_NotAfterNotNested,
                              notAfterLocal,
                              issuerCertificate.NotAfter),
                          nameof(notAfter));
            }

            // Check the Basic Constraints and Key Usage extensions to help identify inappropriate certificates.
            // Note that this is not a security check. The system library backing X509Chain will use these same criteria
            // to determine if a chain is valid; and a user can easily call the X509SignatureGenerator overload to
            // bypass this validation.  We're simply helping them at signing time understand that they've
            // chosen the wrong cert.
            var basicConstraints = (X509BasicConstraintsExtension)issuerCertificate.Extensions[Oids.BasicConstraints2];
            var keyUsage         = (X509KeyUsageExtension)issuerCertificate.Extensions[Oids.KeyUsage];

            if (basicConstraints == null)
            {
                throw new ArgumentException(SR.Cryptography_CertReq_BasicConstraintsRequired, nameof(issuerCertificate));
            }
            if (!basicConstraints.CertificateAuthority)
            {
                throw new ArgumentException(SR.Cryptography_CertReq_IssuerBasicConstraintsInvalid, nameof(issuerCertificate));
            }
            if (keyUsage != null && (keyUsage.KeyUsages & X509KeyUsageFlags.KeyCertSign) == 0)
            {
                throw new ArgumentException(SR.Cryptography_CertReq_IssuerKeyUsageInvalid, nameof(issuerCertificate));
            }

            AsymmetricAlgorithm key = null;
            string keyAlgorithm     = issuerCertificate.GetKeyAlgorithm();
            X509SignatureGenerator generator;

            try
            {
                switch (keyAlgorithm)
                {
                case Oids.Rsa:
                    if (_rsaPadding == null)
                    {
                        throw new InvalidOperationException(SR.Cryptography_CertReq_RSAPaddingRequired);
                    }

                    RSA rsa = issuerCertificate.GetRSAPrivateKey();
                    key       = rsa;
                    generator = X509SignatureGenerator.CreateForRSA(rsa, _rsaPadding);
                    break;

                case Oids.EcPublicKey:
                    ECDsa ecdsa = issuerCertificate.GetECDsaPrivateKey();
                    key       = ecdsa;
                    generator = X509SignatureGenerator.CreateForECDsa(ecdsa);
                    break;

                //begin: gost
                case Oids.Gost3410EL:
                    Gost3410 gost3410 = issuerCertificate.GetGost3410PrivateKey();
                    key       = gost3410;
                    generator = X509SignatureGenerator.CreateForGost(gost3410);
                    break;

                case Oids.Gost3410_2012_256:
                    Gost3410_2012_256 gost3410_2012_256 = issuerCertificate.GetGost3410_2012_256PrivateKey();
                    key       = gost3410_2012_256;
                    generator = X509SignatureGenerator.CreateForGost(gost3410_2012_256);
                    break;

                case Oids.Gost3410_2012_512:
                    Gost3410_2012_512 gost3410_2012_512 = issuerCertificate.GetGost3410_2012_512PrivateKey();
                    key       = gost3410_2012_512;
                    generator = X509SignatureGenerator.CreateForGost(gost3410_2012_512);
                    break;

                //end: gost
                default:
                    throw new ArgumentException(
                              SR.Format(SR.Cryptography_UnknownKeyAlgorithm, keyAlgorithm),
                              nameof(issuerCertificate));
                }

                return(Create(issuerCertificate.SubjectName, generator, notBefore, notAfter, serialNumber));
            }
            finally
            {
                key?.Dispose();
            }
        }
コード例 #19
0
ファイル: GostKeyValue.cs プロジェクト: dprotopopov/corefx
 /// <summary>
 /// Инициализирует новый экземпляр класса <c>GostKeyValue</c> с заданным
 /// открытым ключом ГОСТ 34.10-2001.
 /// </summary>
 ///
 /// <param name="key">Экземпляр реализации класса
 /// <see cref="Gost3410"/>, в котором содержится открытый
 /// ключ.</param>
 public GostKeyValue(Gost3410 key)
 {
     _key = key;
 }
コード例 #20
0
 // begin: gost
 public ICertificatePal CopyWithPrivateKey(Gost3410 gost)
 {
     return(CopyWithPersistedCapiKey(((Gost3410CryptoServiceProvider)gost).CspKeyContainerInfo));
 }
コード例 #21
0
        /// <summary>
        /// Формирование сигнатуры для серверной подписи
        /// </summary>
        /// <param name="alg"></param>
        /// <param name="data"></param>
        /// <param name="detached"></param>
        /// <returns></returns>
        public static byte[] ComputeSignature(Gost3410 alg, byte[] data, bool detached = true)
        {
            var certBytes = alg.ContainerCertificateRaw;

            var _x509CertificateParser = new BCX509.X509CertificateParser();
            var bcCert = _x509CertificateParser.ReadCertificate(certBytes);

            ICollection <BCX509.X509Certificate> certPath = new List <BCX509.X509Certificate>();

            certPath.Add(bcCert);

            IDigest digest;
            string  hashOid;
            string  signOid;

            if (GostCryptoConfig.ProviderType == ProviderTypes.CryptoPro256)
            {
                digest  = new GOST3411_2012_256Digest();
                signOid = Constants.OID_GR3410_12_256;
                hashOid = Constants.OID_GR3411_12_256;
            }
            else if (GostCryptoConfig.ProviderType == ProviderTypes.CryptoPro512)
            {
                digest  = new GOST3411_2012_512Digest();
                signOid = Constants.OID_GR3410_12_512;
                hashOid = Constants.OID_GR3411_12_512;
            }
            else
            {
                digest  = new Gost3411Digest();
                signOid = Constants.OID_GR3410_2001;
                hashOid = Constants.OID_GR3411_2001;
            }

            byte[] dataHash = ComputeDigest(digest, data);

            // Construct SignerInfo.signedAttrs
            Asn1EncodableVector signedAttributesVector = new Asn1EncodableVector();

            // Add PKCS#9 contentType signed attribute
            signedAttributesVector.Add(
                new Org.BouncyCastle.Asn1.Cms.Attribute(
                    new DerObjectIdentifier(Constants.szOID_RSA_contentType),
                    new DerSet(new DerObjectIdentifier(Constants.szOID_RSA_data))));

            // Add PKCS#9 messageDigest signed attribute
            signedAttributesVector.Add(
                new Org.BouncyCastle.Asn1.Cms.Attribute(
                    new DerObjectIdentifier(Constants.szOID_RSA_messageDigest),
                    new DerSet(new DerOctetString(dataHash))));

            // Add PKCS#9 signingTime signed attribute
            signedAttributesVector.Add(
                new Org.BouncyCastle.Asn1.Cms.Attribute(
                    new DerObjectIdentifier(Constants.szOID_RSA_signingTime),
                    new DerSet(new Org.BouncyCastle.Asn1.Cms.Time(new DerUtcTime(DateTime.UtcNow)))));

            DerSet signedAttributes = new DerSet(signedAttributesVector);

            byte[] pkcs1Digest = ComputeDigest(digest, signedAttributes.GetDerEncoded());
            //byte[] pkcs1DigestInfo = CreateDigestInfo(pkcs1Digest, hashOid);

            var formatter = new GostSignatureFormatter(alg);
            var signature = formatter.CreateSignature(pkcs1Digest);

            // Construct SignerInfo
            SignerInfo signerInfo = new SignerInfo(
                new SignerIdentifier(new IssuerAndSerialNumber(bcCert.IssuerDN, bcCert.SerialNumber)),
                new AlgorithmIdentifier(new DerObjectIdentifier(hashOid), null),
                signedAttributes,
                new AlgorithmIdentifier(new DerObjectIdentifier(signOid), null),
                new DerOctetString(signature),
                null);

            // Construct SignedData.digestAlgorithms
            Asn1EncodableVector digestAlgorithmsVector = new Asn1EncodableVector();

            digestAlgorithmsVector.Add(new AlgorithmIdentifier(new DerObjectIdentifier(hashOid), null));

            // Construct SignedData.encapContentInfo
            ContentInfo encapContentInfo = new ContentInfo(
                new DerObjectIdentifier(Constants.szOID_RSA_data),
                (detached) ? null : new DerOctetString(data));

            // Construct SignedData.certificates
            Asn1EncodableVector certificatesVector = new Asn1EncodableVector();

            foreach (BCX509.X509Certificate cert in certPath)
            {
                certificatesVector.Add(X509CertificateStructure.GetInstance(Asn1Object.FromByteArray(cert.GetEncoded())));
            }

            // Construct SignedData.signerInfos
            Asn1EncodableVector signerInfosVector = new Asn1EncodableVector();

            signerInfosVector.Add(signerInfo.ToAsn1Object());

            // Construct SignedData
            SignedData signedData = new SignedData(
                new DerSet(digestAlgorithmsVector),
                encapContentInfo,
                new BerSet(certificatesVector),
                null,
                new DerSet(signerInfosVector));

            // Construct top level ContentInfo
            ContentInfo contentInfo = new ContentInfo(
                new DerObjectIdentifier(Constants.szOID_RSA_signedData),
                signedData);

            return(contentInfo.GetDerEncoded());
        }
コード例 #22
0
        private static XmlDocument DecryptXmlDocument(XmlDocument encryptedXmlDocument, Gost3410 privateKey)
        {
            // Создание объекта для дешифрации XML
            var encryptedXml = new GostEncryptedXml(encryptedXmlDocument);

            // Добавление ссылки на приватный асимметричный ключ
            encryptedXml.AddKeyNameMapping("KeyName1", privateKey);

            // Расшифровка зашифрованных элементов документа
            encryptedXml.DecryptDocument();

            return(encryptedXmlDocument);
        }
コード例 #23
0
        internal Gost3410SignatureGenerator(Gost3410 key)
        {
            Debug.Assert(key != null);

            _key = key;
        }
コード例 #24
0
 /// <summary>
 /// Шифрует сессионный ключ с помощью указанного асимметричного ключа ГОСТ Р 34.10.
 /// </summary>
 /// <param name="sessionKey">Шифруемый сессионный ключ.</param>
 /// <param name="publicKey">Открытый ключ ГОСТ Р 34.10 для шифрования сессионного ключа.</param>
 /// <returns>Массив байт, содержащий зашифрованный сессионный ключ.</returns>
 /// <remarks>Как правило сессионный ключ используется для шифрования данных и в свою очередь так же шифруется.</remarks>
 public static byte[] EncryptKey(Gost28147 sessionKey, Gost3410 publicKey)
 {
     return(GostEncryptedXmlImpl.EncryptKey(sessionKey, publicKey));
 }