예제 #1
0
    /// <summary>
    /// Creates a self signed application instance certificate.
    /// </summary>
    /// <param name="storeType">Type of certificate store (Directory) <see cref="CertificateStoreType"/>.</param>
    /// <param name="storePath">The store path (syntax depends on storeType).</param>
    /// <param name="password">The password to use to protect the certificate.</param>
    /// <param name="applicationUri">The application uri (created if not specified).</param>
    /// <param name="applicationName">Name of the application (optional if subjectName is specified).</param>
    /// <param name="subjectName">The subject used to create the certificate (optional if applicationName is specified).</param>
    /// <param name="domainNames">The domain names that can be used to access the server machine (defaults to local computer name if not specified).</param>
    /// <param name="keySize">Size of the key (1024, 2048 or 4096).</param>
    /// <param name="startTime">The start time.</param>
    /// <param name="lifetimeInMonths">The lifetime of the key in months.</param>
    /// <param name="hashSizeInBits">The hash size in bits.</param>
    /// <param name="isCA">if set to <c>true</c> then a CA certificate is created.</param>
    /// <param name="issuerCAKeyCert">The CA cert with the CA private key.</param>
    /// <returns>The certificate with a private key.</returns>
    public static X509Certificate2 CreateCertificate(
        string storeType,
        string storePath,
        string password,
        string applicationUri,
        string applicationName,
        string subjectName,
        IList <String> domainNames,
        ushort keySize,
        DateTime startTime,
        ushort lifetimeInMonths,
        ushort hashSizeInBits,
        bool isCA,
        X509Certificate2 issuerCAKeyCert)
    {
        if (issuerCAKeyCert != null)
        {
            if (!issuerCAKeyCert.HasPrivateKey)
            {
                throw new NotSupportedException("Cannot sign with a CA certificate without a private key.");
            }
        }

        // set default values.
        X509Name subjectDN = SetSuitableDefaults(
            ref applicationUri,
            ref applicationName,
            ref subjectName,
            ref domainNames,
            ref keySize,
            ref lifetimeInMonths,
            isCA);

        using (var cfrg = new CertificateFactoryRandomGenerator())
        {
            // cert generators
            SecureRandom random           = new SecureRandom(cfrg);
            X509V3CertificateGenerator cg = new X509V3CertificateGenerator();

            // Serial Number
            BigInteger serialNumber = BigIntegers.CreateRandomInRange(BigInteger.One, BigInteger.ValueOf(Int64.MaxValue), random);
            cg.SetSerialNumber(serialNumber);

            X509Name issuerDN = null;
            if (issuerCAKeyCert != null)
            {
                issuerDN = new X509Name(true, issuerCAKeyCert.Subject.Replace("S=", "ST="));
            }
            else
            {
                // self signed
                issuerDN = subjectDN;
            }

            cg.SetIssuerDN(issuerDN);
            cg.SetSubjectDN(subjectDN);

            // valid for
            cg.SetNotBefore(startTime);
            cg.SetNotAfter(startTime.AddMonths(lifetimeInMonths));

            // Private/Public Key
            AsymmetricCipherKeyPair subjectKeyPair;
            var keyGenerationParameters = new KeyGenerationParameters(random, keySize);
            var keyPairGenerator        = new RsaKeyPairGenerator();
            keyPairGenerator.Init(keyGenerationParameters);
            subjectKeyPair = keyPairGenerator.GenerateKeyPair();
            cg.SetPublicKey(subjectKeyPair.Public);

            // add extensions
            // Subject key identifier
            cg.AddExtension(X509Extensions.SubjectKeyIdentifier.Id, false,
                            new SubjectKeyIdentifier(SubjectPublicKeyInfoFactory.CreateSubjectPublicKeyInfo(subjectKeyPair.Public)));

            // Basic constraints
            cg.AddExtension(X509Extensions.BasicConstraints.Id, true, new BasicConstraints(isCA));

            // Authority Key identifier
            var issuerKeyPair      = subjectKeyPair;
            var issuerSerialNumber = serialNumber;
            cg.AddExtension(X509Extensions.AuthorityKeyIdentifier.Id, false,
                            new AuthorityKeyIdentifier(SubjectPublicKeyInfoFactory.CreateSubjectPublicKeyInfo(subjectKeyPair.Public),
                                                       new GeneralNames(new GeneralName(issuerDN)), issuerSerialNumber));

            if (!isCA)
            {
                // Key usage
                cg.AddExtension(X509Extensions.KeyUsage, true,
                                new KeyUsage(KeyUsage.DataEncipherment | KeyUsage.DigitalSignature |
                                             KeyUsage.NonRepudiation | KeyUsage.KeyCertSign | KeyUsage.KeyEncipherment));

                // Extended Key usage
                cg.AddExtension(X509Extensions.ExtendedKeyUsage, true,
                                new ExtendedKeyUsage(new List <DerObjectIdentifier>()
                {
                    new DerObjectIdentifier("1.3.6.1.5.5.7.3.1"), // server auth
                    new DerObjectIdentifier("1.3.6.1.5.5.7.3.2"), // client auth
                }));

                // subject alternate name
                cg.AddExtension(X509Extensions.SubjectAlternativeName, false,
                                new GeneralNames(new GeneralName[] {
                    new GeneralName(GeneralName.UniformResourceIdentifier, applicationUri),
                    new GeneralName(GeneralName.DnsName, domainNames[0])
                }));
            }
            else
            {
                // Key usage CA
                cg.AddExtension(X509Extensions.KeyUsage, true,
                                new KeyUsage(KeyUsage.CrlSign | KeyUsage.DigitalSignature | KeyUsage.KeyCertSign));
            }

            // sign certificate
            AsymmetricKeyParameter privateKey = null;
            if (issuerCAKeyCert != null)
            {
                using (RSA rsa = issuerCAKeyCert.GetRSAPrivateKey())
                {
                    RSAParameters rsaParams = rsa.ExportParameters(true);
                    RsaPrivateCrtKeyParameters keyParams = new RsaPrivateCrtKeyParameters(
                        new BigInteger(1, rsaParams.Modulus),
                        new BigInteger(1, rsaParams.Exponent),
                        new BigInteger(1, rsaParams.D),
                        new BigInteger(1, rsaParams.P),
                        new BigInteger(1, rsaParams.Q),
                        new BigInteger(1, rsaParams.DP),
                        new BigInteger(1, rsaParams.DQ),
                        new BigInteger(1, rsaParams.InverseQ));
                    privateKey = keyParams;
                }
            }
            else
            {
                privateKey = subjectKeyPair.Private;
            }

            ISignatureFactory signatureFactory =
                new Asn1SignatureFactory((hashSizeInBits < 256) ? "SHA1WITHRSA" : "SHA256WITHRSA", privateKey, random);

            Org.BouncyCastle.X509.X509Certificate x509 = cg.Generate(signatureFactory);

            // create pkcs12 store for cert and private key
            X509Certificate2 certificate = null;
            using (MemoryStream pfxData = new MemoryStream())
            {
                Pkcs12Store            pkcsStore = new Pkcs12StoreBuilder().Build();
                X509CertificateEntry[] chain     = new X509CertificateEntry[1];
                string passcode = Guid.NewGuid().ToString();
                chain[0] = new X509CertificateEntry(x509);
                pkcsStore.SetKeyEntry(applicationName, new AsymmetricKeyEntry(subjectKeyPair.Private), chain);
                pkcsStore.Save(pfxData, passcode.ToCharArray(), random);

                // merge into X509Certificate2
                certificate = CreateCertificateFromPKCS12(pfxData.ToArray(), passcode);
            }

            Utils.Trace(Utils.TraceMasks.Security, "Created new certificate: {0}", certificate.Thumbprint);

            // add cert to the store.
            if (!String.IsNullOrEmpty(storePath))
            {
                ICertificateStore store = null;
                if (storeType == CertificateStoreType.X509Store)
                {
                    store = new X509CertificateStore();
                }
                else if (storeType == CertificateStoreType.Directory)
                {
                    store = new DirectoryCertificateStore();
                }
                else
                {
                    throw new ArgumentException("Invalid store type");
                }

                store.Open(storePath);
                store.Add(certificate, password);
                store.Close();
                store.Dispose();
            }

            // note: this cert has a private key!
            return(certificate);
        }
    }
예제 #2
0
        private static X509Certificate2 GenerateSelfSignedCertificate(string subjectName, string issuerName, AsymmetricKeyParameter issuerPrivKey)
        {
            const int keyStrength = 2048;

            // Generating Random Numbers
            var randomGenerator = new CryptoApiRandomGenerator();
            var random          = new SecureRandom(randomGenerator);

            // The Certificate Generator
            var certificateGenerator = new X509V3CertificateGenerator();

            // Serial Number
            var serialNumber = BigIntegers.CreateRandomInRange(BigInteger.One, BigInteger.ValueOf(Int64.MaxValue), random);

            certificateGenerator.SetSerialNumber(serialNumber);

            // Signature Algorithm
            const string signatureAlgorithm = "SHA256WithRSA";

            certificateGenerator.SetSignatureAlgorithm(signatureAlgorithm);

            // Issuer and Subject Name
            var subjectDN = new X509Name(subjectName);
            var issuerDN  = new X509Name(issuerName);

            certificateGenerator.SetIssuerDN(issuerDN);
            certificateGenerator.SetSubjectDN(subjectDN);

            // Valid For
            var notBefore = DateTime.UtcNow.Date;
            var notAfter  = notBefore.AddYears(2);

            certificateGenerator.SetNotBefore(notBefore);
            certificateGenerator.SetNotAfter(notAfter);

            // Subject Public Key
            AsymmetricCipherKeyPair subjectKeyPair;
            var keyGenerationParameters = new KeyGenerationParameters(random, keyStrength);
            var keyPairGenerator        = new RsaKeyPairGenerator();

            keyPairGenerator.Init(keyGenerationParameters);
            subjectKeyPair = keyPairGenerator.GenerateKeyPair();

            certificateGenerator.SetPublicKey(subjectKeyPair.Public);
            // self-sign certificate
            var certificate = certificateGenerator.Generate(issuerPrivKey, random);


            // corresponding private key
            var info = PrivateKeyInfoFactory.CreatePrivateKeyInfo(subjectKeyPair.Private);


            // merge into X509Certificate2
            var x509 = new X509Certificate2(certificate.GetEncoded());

            var seq = (Asn1Sequence)Asn1Object.FromByteArray(info.PrivateKey.GetDerEncoded());

            if (seq.Count != 9)
            {
                //throw new PemException("malformed sequence in RSA private key");
            }

            var rsa       = RsaPrivateKeyStructure.GetInstance(seq);
            var rsaparams = new RsaPrivateCrtKeyParameters(
                rsa.Modulus, rsa.PublicExponent, rsa.PrivateExponent, rsa.Prime1, rsa.Prime2, rsa.Exponent1, rsa.Exponent2, rsa.Coefficient);

            x509.PrivateKey = ToDotNetKey(rsaparams);
            return(x509);
        }
예제 #3
0
        /// <summary>
        /// Static method used to create a certificate and return as a .net object
        /// </summary>
        public static X509Certificate2 Create(string name, DateTime start, DateTime end, string userPassword,
                                              bool addtoStore = false)
        {
            // generate a key pair using RSA
            var generator = new RsaKeyPairGenerator();

            // keys have to be a minimum of 2048 bits for Azure
            generator.Init(new KeyGenerationParameters(new SecureRandom(new CryptoApiRandomGenerator()), 2048));
            AsymmetricCipherKeyPair cerKp = generator.GenerateKeyPair();
            // get a copy of the private key
            AsymmetricKeyParameter privateKey = cerKp.Private;

            // create the CN using the name passed in and create a unique serial number for the cert
            var        certName = new X509Name("CN=" + name);
            BigInteger serialNo = BigInteger.ProbablePrime(120, new Random());

            // start the generator and set CN/DN and serial number and valid period
            var x509Generator = new X509V3CertificateGenerator();

            x509Generator.SetSerialNumber(serialNo);
            x509Generator.SetSubjectDN(certName);
            x509Generator.SetIssuerDN(certName);
            x509Generator.SetNotBefore(start);
            x509Generator.SetNotAfter(end);
            // add the server authentication key usage
            var keyUsage = new KeyUsage(KeyUsage.KeyEncipherment);

            x509Generator.AddExtension(X509Extensions.KeyUsage, false, keyUsage.ToAsn1Object());
            var extendedKeyUsage = new ExtendedKeyUsage(new[] { KeyPurposeID.IdKPServerAuth });

            x509Generator.AddExtension(X509Extensions.ExtendedKeyUsage, true, extendedKeyUsage.ToAsn1Object());
            // algorithm can only be SHA1 ??
            x509Generator.SetSignatureAlgorithm("sha1WithRSA");
            // Set the key pair
            x509Generator.SetPublicKey(cerKp.Public);
            X509Certificate certificate = x509Generator.Generate(cerKp.Private);

            // export the certificate bytes
            byte[] certStream = DotNetUtilities.ToX509Certificate(certificate).Export(X509ContentType.Pkcs12,
                                                                                      userPassword);

            // build the key parameter and the certificate entry
            var keyEntry = new AsymmetricKeyEntry(privateKey);
            var entry    = new X509CertificateEntry(certificate);
            // build the PKCS#12 store to encapsulate the certificate
            var builder = new Pkcs12StoreBuilder();

            builder.SetUseDerEncoding(true);
            builder.SetCertAlgorithm(PkcsObjectIdentifiers.Sha1WithRsaEncryption);
            builder.SetKeyAlgorithm(PkcsObjectIdentifiers.Sha1WithRsaEncryption);
            builder.Build();
            // create a memorystream to hold the output
            var stream = new MemoryStream(2000);
            // create the individual store and set two entries for cert and key
            var store = new Pkcs12Store();

            store.SetCertificateEntry("Elastacloud Test Certificate", entry);
            store.SetKeyEntry("Elastacloud Test Certificate", keyEntry, new[] { entry });
            store.Save(stream, userPassword.ToCharArray(), new SecureRandom());

            // Create the equivalent C# representation
            var cert = new X509Certificate2(stream.GetBuffer(), userPassword, X509KeyStorageFlags.Exportable);

            // if specified then this add this certificate to the store
            if (addtoStore)
            {
                AddToMyStore(cert);
            }

            return(cert);
        }
예제 #4
0
        public void TestCreationECDSA()
        {
            BigInteger ECParraGX = new BigInteger(Base64.Decode("D/qWPNyogWzMM7hkK+35BcPTWFc9Pyf7vTs8uaqv"));
            BigInteger ECParraGY = new BigInteger(Base64.Decode("AhQXGxb1olGRv6s1LPRfuatMF+cx3ZTGgzSE/Q5R"));
            BigInteger ECParraH  = new BigInteger(Base64.Decode("AQ=="));
            BigInteger ECParraN  = new BigInteger(Base64.Decode("f///////////////f///nl6an12QcfvRUiaIkJ0L"));
            BigInteger ECPubQX   = new BigInteger(Base64.Decode("HWWi17Yb+Bm3PYr/DMjLOYNFhyOwX1QY7ZvqqM+l"));
            BigInteger ECPubQY   = new BigInteger(Base64.Decode("JrlJfxu3WGhqwtL/55BOs/wsUeiDFsvXcGhB8DGx"));
            BigInteger ECPrivD   = new BigInteger(Base64.Decode("GYQmd/NF1B+He1iMkWt3by2Az6Eu07t0ynJ4YCAo"));

            X9ECParameters     x9       = ECNamedCurveTable.GetByName("prime239v1");
            ECCurve            curve    = x9.Curve;
            ECDomainParameters ecDomain = new ECDomainParameters(curve, curve.ValidatePoint(ECParraGX, ECParraGY), ECParraN, ECParraH);

            ECPublicKeyParameters ecPub = new ECPublicKeyParameters("ECDSA",
                                                                    curve.ValidatePoint(ECPubQX, ECPubQY), ecDomain);
            ECPrivateKeyParameters ecPriv = new ECPrivateKeyParameters("ECDSA", ECPrivD, ecDomain);

            IDictionary attrs = new Hashtable();

            attrs[X509Name.C]  = "AU";
            attrs[X509Name.O]  = "The Legion of the Bouncy Castle";
            attrs[X509Name.L]  = "Melbourne";
            attrs[X509Name.ST] = "Victoria";
            attrs[X509Name.E]  = "*****@*****.**";

            IList ord = new ArrayList();

            ord.Add(X509Name.C);
            ord.Add(X509Name.O);
            ord.Add(X509Name.L);
            ord.Add(X509Name.ST);
            ord.Add(X509Name.E);

            IList values = new ArrayList();

            values.Add("AU");
            values.Add("The Legion of the Bouncy Castle");
            values.Add("Melbourne");
            values.Add("Victoria");
            values.Add("*****@*****.**");

            X509V3CertificateGenerator certGen = new X509V3CertificateGenerator();

            certGen.SetSerialNumber(BigInteger.One);

            certGen.SetIssuerDN(new X509Name(ord, attrs));
            certGen.SetNotBefore(DateTime.Today.Subtract(new TimeSpan(1, 0, 0, 0)));
            certGen.SetNotAfter(DateTime.Today.AddDays(1));
            certGen.SetSubjectDN(new X509Name(ord, attrs));
            certGen.SetPublicKey(ecPub);
            certGen.SetSignatureAlgorithm("SHA1WITHECDSA");

            certGen.AddExtension(X509Extensions.BasicConstraints, true, new BasicConstraints(false));

            X509Certificate cert = certGen.Generate(ecPriv);

//            Assert.IsTrue((cert.IsValidNow && cert.Verify(ecPub)), "Certificate failed to be valid (ECDSA)");
            cert.CheckValidity();
            cert.Verify(ecPub);

            ISet extOidSet = cert.GetCriticalExtensionOids();

            if (extOidSet.Count != 1)
            {
                Fail("wrong number of oids");
            }
            //if (dummySet != null)
            //{
            //    foreach (string key in dummySet)
            //    {
            //        Console.WriteLine("\t{0}:\t{1}", key);
            //    }
            //}

            //Console.WriteLine();

            //dummySet = cert.GetNonCriticalExtensionOids();

            //if (dummySet != null)
            //{
            //    foreach (string key in dummySet)
            //    {
            //        Console.WriteLine("\t{0}:\t{1}", key);
            //    }
            //}

            //Console.WriteLine();
        }
예제 #5
0
        /// <summary>
        /// Creates the certificate based on the subject name
        /// </summary>
        /// <param name="certificate">The certificate object with custom values for the certificate</param>
        /// <returns></returns>
        public static bool GeneratePfx(CertificateAttributes certificate)
        {
            var isCertificateCreated = false;

            try
            {
                var keyPairGenerator = new RsaKeyPairGenerator();
                keyPairGenerator.Init(new KeyGenerationParameters(new SecureRandom(new CryptoApiRandomGenerator()), 1024));
                var kp = keyPairGenerator.GenerateKeyPair();
                var signatureFactory = new Asn1SignatureFactory(certificate.Algorithm.GetDescription(), kp.Private);
                var gen      = new X509V3CertificateGenerator();
                var certName = new X509Name("CN=" + certificate.SubjectName);
                var serialNo = BigInteger.ProbablePrime(120, new Random());
                //sets the serial no for the certificate : add a custom serial no if you have one
                gen.SetSerialNumber(serialNo);
                //set the subject name : can be custom here
                gen.SetSubjectDN(certName);
                //sets the issuer name
                gen.SetIssuerDN(certName);
                gen.SetNotAfter(DateTime.Now.AddYears(100));
                gen.SetNotBefore(DateTime.Now.Subtract(new TimeSpan(7, 0, 0, 0)));
                //set the public key for the certificate
                gen.SetPublicKey(kp.Public);

                gen.AddExtension(
                    X509Extensions.AuthorityKeyIdentifier.Id,
                    false,
                    new AuthorityKeyIdentifier(
                        SubjectPublicKeyInfoFactory.CreateSubjectPublicKeyInfo(kp.Public),
                        new GeneralNames(new GeneralName(certName)),
                        serialNo));

                gen.AddExtension(
                    X509Extensions.ExtendedKeyUsage.Id,
                    false,
                    new ExtendedKeyUsage(new List <object> {
                    new DerObjectIdentifier("1.3.6.1.5.5.7.3.1")
                }));

                var newCert            = gen.Generate(signatureFactory);
                var createdCertificate = DotNetUtilities.ToX509Certificate(newCert);
                var byteArray          = createdCertificate.Export(X509ContentType.Pkcs12, certificate.Password);
                var byteArray1         = createdCertificate.Export(X509ContentType.Cert, certificate.Password);

                //Save the pfx file here
                Helper.WriteAllBytes("C:\\certs\\" + certificate.SubjectName + ".pfx", byteArray);

                //save the cert here
                if (certificate.SaveCerFile)
                {
                    Helper.WriteAllBytes("C:\\certs\\" + certificate.SubjectName + ".cer", byteArray1);
                }

                isCertificateCreated = true;
            }
            catch (Exception exception)
            {
                var logger = new Logger.FileLogger();
                logger.Log(exception);
            }

            return(isCertificateCreated);
        }
        /// <summary>
        ///     Generates the certificate.
        /// </summary>
        /// <param name="subjectName">Name of the subject.</param>
        /// <param name="issuerName">Name of the issuer.</param>
        /// <param name="validFrom">The valid from.</param>
        /// <param name="validTo">The valid to.</param>
        /// <param name="subjectKeyPair">The key pair.</param>
        /// <param name="signatureAlgorithm">The signature algorithm.</param>
        /// <param name="issuerPrivateKey">The issuer private key.</param>
        /// <param name="hostName">The host name</param>
        /// <returns>X509Certificate2 instance.</returns>
        /// <exception cref="PemException">Malformed sequence in RSA private key</exception>
        private static X509Certificate2 generateCertificate(string?hostName,
                                                            string subjectName,
                                                            string issuerName, DateTime validFrom,
                                                            DateTime validTo, AsymmetricCipherKeyPair subjectKeyPair,
                                                            string signatureAlgorithm = "SHA256WithRSA",
                                                            AsymmetricKeyParameter?issuerPrivateKey = null)
        {
            // Generating Random Numbers
            var randomGenerator = new CryptoApiRandomGenerator();
            var secureRandom    = new SecureRandom(randomGenerator);

            // The Certificate Generator
            var certificateGenerator = new X509V3CertificateGenerator();

            // Serial Number
            var serialNumber =
                BigIntegers.CreateRandomInRange(BigInteger.One, BigInteger.ValueOf(long.MaxValue), secureRandom);

            certificateGenerator.SetSerialNumber(serialNumber);

            // Issuer and Subject Name
            var subjectDn = new X509Name(subjectName);
            var issuerDn  = new X509Name(issuerName);

            certificateGenerator.SetIssuerDN(issuerDn);
            certificateGenerator.SetSubjectDN(subjectDn);

            certificateGenerator.SetNotBefore(validFrom);
            certificateGenerator.SetNotAfter(validTo);

            if (hostName != null)
            {
                // add subject alternative names
                var nameType = GeneralName.DnsName;
                if (IPAddress.TryParse(hostName, out _))
                {
                    nameType = GeneralName.IPAddress;
                }

                var subjectAlternativeNames = new Asn1Encodable[] { new GeneralName(nameType, hostName) };

                var subjectAlternativeNamesExtension = new DerSequence(subjectAlternativeNames);
                certificateGenerator.AddExtension(X509Extensions.SubjectAlternativeName.Id, false,
                                                  subjectAlternativeNamesExtension);
            }

            // Subject Public Key
            certificateGenerator.SetPublicKey(subjectKeyPair.Public);

            // Set certificate intended purposes to only Server Authentication
            certificateGenerator.AddExtension(X509Extensions.ExtendedKeyUsage.Id, false,
                                              new ExtendedKeyUsage(KeyPurposeID.IdKPServerAuth));
            if (issuerPrivateKey == null)
            {
                certificateGenerator.AddExtension(X509Extensions.BasicConstraints.Id, true, new BasicConstraints(true));
            }

            var signatureFactory = new Asn1SignatureFactory(signatureAlgorithm,
                                                            issuerPrivateKey ?? subjectKeyPair.Private, secureRandom);

            // Self-sign the certificate
            var certificate = certificateGenerator.Generate(signatureFactory);

            // Corresponding private key
            var privateKeyInfo = PrivateKeyInfoFactory.CreatePrivateKeyInfo(subjectKeyPair.Private);

            var seq = (Asn1Sequence)Asn1Object.FromByteArray(privateKeyInfo.ParsePrivateKey().GetDerEncoded());

            if (seq.Count != 9)
            {
                throw new PemException("Malformed sequence in RSA private key");
            }

            var rsa       = RsaPrivateKeyStructure.GetInstance(seq);
            var rsaparams = new RsaPrivateCrtKeyParameters(rsa.Modulus, rsa.PublicExponent, rsa.PrivateExponent,
                                                           rsa.Prime1, rsa.Prime2, rsa.Exponent1,
                                                           rsa.Exponent2, rsa.Coefficient);

            // Set private key onto certificate instance
            var x509Certificate = withPrivateKey(certificate, rsaparams);

            if (!doNotSetFriendlyName)
            {
                try
                {
                    x509Certificate.FriendlyName = ProxyConstants.CNRemoverRegex.Replace(subjectName, string.Empty);
                }
                catch (PlatformNotSupportedException)
                {
                    doNotSetFriendlyName = true;
                }
            }

            return(x509Certificate);
        }
        /// <inheritdoc/>
        public async Task <(X509Certificate?Certificate, RsaKeyParameters?Key)> GetLocalCertificateAsync(ApplicationDescription applicationDescription, ILogger?logger = null, CancellationToken token = default)
        {
            if (applicationDescription == null)
            {
                throw new ArgumentNullException(nameof(applicationDescription));
            }

            string?applicationUri = applicationDescription.ApplicationUri;

            if (string.IsNullOrEmpty(applicationUri))
            {
                throw new ArgumentOutOfRangeException(nameof(applicationDescription), "Expecting ApplicationUri in the form of 'http://{hostname}/{appname}' -or- 'urn:{hostname}:{appname}'.");
            }

            string?subjectName = null;
            string?hostName    = null;
            string?appName     = null;

            UriBuilder appUri = new UriBuilder(applicationUri);

            if (appUri.Scheme == "http" && !string.IsNullOrEmpty(appUri.Host))
            {
                var path = appUri.Path.Trim('/');
                if (!string.IsNullOrEmpty(path))
                {
                    hostName    = appUri.Host;
                    appName     = path;
                    subjectName = $"CN={appName},DC={hostName}";
                }
            }

            if (appUri.Scheme == "urn")
            {
                var parts = appUri.Path.Split(new[] { ':' }, 2);
                if (parts.Length == 2)
                {
                    hostName    = parts[0];
                    appName     = parts[1];
                    subjectName = $"CN={appName},DC={hostName}";
                }
            }

            if (subjectName == null)
            {
                throw new ArgumentOutOfRangeException(nameof(applicationDescription), "Expecting ApplicationUri in the form of 'http://{hostname}/{appname}' -or- 'urn:{hostname}:{appname}'.");
            }

            var crt = default(X509Certificate);
            var key = default(RsaKeyParameters);

            // Build 'own/certs' certificate store.
            var ownCerts     = new Org.BouncyCastle.Utilities.Collections.HashSet();
            var ownCertsInfo = new DirectoryInfo(Path.Combine(_pkiPath, "own", "certs"));

            if (ownCertsInfo.Exists)
            {
                foreach (var info in ownCertsInfo.EnumerateFiles())
                {
                    using (var crtStream = info.OpenRead())
                    {
                        var c = _certParser.ReadCertificate(crtStream);
                        if (c != null)
                        {
                            ownCerts.Add(c);
                        }
                    }
                }
            }

            IX509Store ownCertStore = X509StoreFactory.Create("Certificate/Collection", new X509CollectionStoreParameters(ownCerts));

            // Select the newest certificate that matches by subject name.
            var selector = new X509CertStoreSelector()
            {
                Subject = new X509Name(subjectName)
            };

            crt = ownCertStore.GetMatches(selector).OfType <X509Certificate>().OrderBy(c => c.NotBefore).LastOrDefault();
            if (crt != null)
            {
                // If certificate found, verify alt-name, and retrieve private key.
                var asn1OctetString = crt.GetExtensionValue(X509Extensions.SubjectAlternativeName);
                if (asn1OctetString != null)
                {
                    var          asn1Object = X509ExtensionUtilities.FromExtensionValue(asn1OctetString);
                    GeneralNames gns        = GeneralNames.GetInstance(asn1Object);
                    if (gns.GetNames().Any(n => n.TagNo == GeneralName.UniformResourceIdentifier && n.Name.ToString() == applicationUri))
                    {
                        var ki = new FileInfo(Path.Combine(_pkiPath, "own", "private", $"{crt.SerialNumber}.key"));
                        if (ki.Exists)
                        {
                            using (var keyStream = new StreamReader(ki.OpenRead()))
                            {
                                var keyReader = new PemReader(keyStream);
                                var keyPair   = keyReader.ReadObject() as AsymmetricCipherKeyPair;
                                if (keyPair != null)
                                {
                                    key = keyPair.Private as RsaKeyParameters;
                                }
                            }
                        }
                    }
                }
            }

            // If certificate and key are found, return to caller.
            if (crt != null && key != null)
            {
                logger?.LogTrace($"Found certificate with subject alt name '{applicationUri}'.");
                return(crt, key);
            }

            if (!CreateLocalCertificateIfNotExist)
            {
                return(null, null);
            }

            // Create new certificate
            var subjectDN = new X509Name(subjectName);

            // Create a keypair.
            var kp = await Task.Run <AsymmetricCipherKeyPair>(() =>
            {
                RsaKeyPairGenerator kg = new RsaKeyPairGenerator();
                kg.Init(new KeyGenerationParameters(_rng, 2048));
                return(kg.GenerateKeyPair());
            });

            key = kp.Private as RsaPrivateCrtKeyParameters;

            // Create a certificate.
            X509V3CertificateGenerator cg = new X509V3CertificateGenerator();
            var subjectSN = BigInteger.ProbablePrime(120, _rng);

            cg.SetSerialNumber(subjectSN);
            cg.SetSubjectDN(subjectDN);
            cg.SetIssuerDN(subjectDN);
            cg.SetNotBefore(DateTime.Now.Date.ToUniversalTime());
            cg.SetNotAfter(DateTime.Now.Date.ToUniversalTime().AddYears(25));
            cg.SetPublicKey(kp.Public);

            cg.AddExtension(
                X509Extensions.BasicConstraints.Id,
                true,
                new BasicConstraints(false));

            cg.AddExtension(
                X509Extensions.SubjectKeyIdentifier.Id,
                false,
                new SubjectKeyIdentifier(SubjectPublicKeyInfoFactory.CreateSubjectPublicKeyInfo(kp.Public)));

            cg.AddExtension(
                X509Extensions.AuthorityKeyIdentifier.Id,
                false,
                new AuthorityKeyIdentifier(SubjectPublicKeyInfoFactory.CreateSubjectPublicKeyInfo(kp.Public), new GeneralNames(new GeneralName(subjectDN)), subjectSN));

            cg.AddExtension(
                X509Extensions.SubjectAlternativeName,
                false,
                new GeneralNames(new[] { new GeneralName(GeneralName.UniformResourceIdentifier, applicationUri), new GeneralName(GeneralName.DnsName, hostName) }));

            cg.AddExtension(
                X509Extensions.KeyUsage,
                true,
                new KeyUsage(KeyUsage.DataEncipherment | KeyUsage.DigitalSignature | KeyUsage.NonRepudiation | KeyUsage.KeyCertSign | KeyUsage.KeyEncipherment));

            cg.AddExtension(
                X509Extensions.ExtendedKeyUsage,
                true,
                new ExtendedKeyUsage(KeyPurposeID.IdKPClientAuth, KeyPurposeID.IdKPServerAuth));

            crt = cg.Generate(new Asn1SignatureFactory("SHA256WITHRSA", key, _rng));

            logger?.LogTrace($"Created certificate with subject alt name '{applicationUri}'.");

            var keyInfo = new FileInfo(Path.Combine(_pkiPath, "own", "private", $"{crt.SerialNumber}.key"));

            if (!keyInfo.Directory.Exists)
            {
                Directory.CreateDirectory(keyInfo.DirectoryName);
            }
            else if (keyInfo.Exists)
            {
                keyInfo.Delete();
            }

            using (var keystream = new StreamWriter(keyInfo.OpenWrite()))
            {
                var pemwriter = new PemWriter(keystream);
                pemwriter.WriteObject(key);
            }

            var crtInfo = new FileInfo(Path.Combine(_pkiPath, "own", "certs", $"{crt.SerialNumber}.crt"));

            if (!crtInfo.Directory.Exists)
            {
                Directory.CreateDirectory(crtInfo.DirectoryName);
            }
            else if (crtInfo.Exists)
            {
                crtInfo.Delete();
            }

            using (var crtstream = new StreamWriter(crtInfo.OpenWrite()))
            {
                var pemwriter = new PemWriter(crtstream);
                pemwriter.WriteObject(crt);
            }

            return(crt, key);
        }
        /// <summary>
        /// 生成X509 V3证书
        /// </summary>
        /// <param name="certPath">Cert证书路径</param>
        /// <param name="endDate">证书失效时间</param>
        /// <param name="keySize">密钥长度</param>
        /// <param name="password">证书密码</param>
        /// <param name="signatureAlgorithm">设置将用于签署此证书的签名算法</param>
        /// <param name="issuer">设置此证书颁发者的DN</param>
        /// <param name="subject">设置此证书使用者的DN</param>
        /// <param name="pfxPath">Pfx证书路径</param>
        /// <param name="friendlyName">设置证书友好名称(可选)</param>
        /// <param name="startDate">证书生效时间</param>
        /// <param name="algorithm">加密算法</param>
        public static void X509V3(string algorithm, int keySize, string password, string signatureAlgorithm,
                                  DateTime startDate, DateTime endDate, X509Name issuer, X509Name subject, string certPath, string pfxPath,
                                  string friendlyName = "")
        {
            //generate Random Numbers
            CryptoApiRandomGenerator randomGenerator = new CryptoApiRandomGenerator();
            SecureRandom             random          = new SecureRandom(randomGenerator);

            var keyGenerator = GeneratorUtilities.GetKeyPairGenerator(algorithm);

            keyGenerator.Init(new KeyGenerationParameters(new SecureRandom(), keySize));

            var keyPair = keyGenerator.GenerateKeyPair();

            var v3CertGen    = new X509V3CertificateGenerator();
            var serialNumber = BigIntegers.CreateRandomInRange(BigInteger.One, BigInteger.ValueOf(long.MaxValue), random);

            v3CertGen.SetSerialNumber(serialNumber);                                                   //设置证书的序列号

            v3CertGen.SetIssuerDN(issuer);                                                             //设置颁发者信息
            v3CertGen.SetSubjectDN(subject);                                                           //设置使用者信息

            v3CertGen.SetNotBefore(startDate);                                                         //设置证书的生效日期
            v3CertGen.SetNotAfter(endDate);                                                            //设置证书失效的日期
            v3CertGen.SetPublicKey(keyPair.Public);                                                    //设置此证书的公钥

            ISignatureFactory sigFact = new Asn1SignatureFactory(signatureAlgorithm, keyPair.Private); //签名算法&设置此证书的私钥

            var spki = SubjectPublicKeyInfoFactory.CreateSubjectPublicKeyInfo(keyPair.Public);

            //设置一些扩展字段
            //基本约束
            v3CertGen.AddExtension(X509Extensions.BasicConstraints, true, new BasicConstraints(true));
            //使用者密钥标识符
            v3CertGen.AddExtension(X509Extensions.SubjectKeyIdentifier, false, new SubjectKeyIdentifier(spki));
            //授权密钥标识符
            v3CertGen.AddExtension(X509Extensions.AuthorityKeyIdentifier, false, new AuthorityKeyIdentifier(spki));

            var x509Certificate = v3CertGen.Generate(sigFact); //生成证书

            x509Certificate.CheckValidity();                   //检查当前日期是否在证书的有效期内
            x509Certificate.Verify(keyPair.Public);            //使用公钥验证证书的签名

            var certificate2 = new X509Certificate2(DotNetUtilities.ToX509Certificate(x509Certificate))
            {
                FriendlyName = friendlyName, //设置友好名称
            };

            //cer公钥文件
            var bytes = certificate2.Export(X509ContentType.Cert);

            using (var fs = new FileStream(certPath, FileMode.Create))
            {
                fs.Write(bytes, 0, bytes.Length);
            }

            //pfx证书,包含公钥私钥
            //CopyWithPrivateKey netstandard2.1支持
            certificate2 =
                certificate2.CopyWithPrivateKey(DotNetUtilities.ToRSA((RsaPrivateCrtKeyParameters)keyPair.Private));

            var bytes2 = certificate2.Export(X509ContentType.Pfx, password);

            using (var fs = new FileStream(pfxPath, FileMode.Create))
            {
                fs.Write(bytes2, 0, bytes2.Length);
            }


            //如果使用 netstandard2.0 请使用下面的代码
#if NETSTANDARD2_0
            var certEntry = new X509CertificateEntry(x509Certificate);
            var store     = new Pkcs12StoreBuilder().Build();
            store.SetCertificateEntry(friendlyName, certEntry);   //设置证书
            var chain = new X509CertificateEntry[1];
            chain[0] = certEntry;
            store.SetKeyEntry(friendlyName, new AsymmetricKeyEntry(keyPair.Private), chain);   //设置私钥
            using (var fs = File.Create(pfxPath))
            {
                store.Save(fs, password.ToCharArray(), new SecureRandom()); //保存
            }
#endif
        }
예제 #9
0
        //[Obsolete("Use CreateSelfSignedTlsCert instead.")]
        public static X509Certificate2 CreateSelfSignedCert(string subjectName, string issuerName, AsymmetricKeyParameter privateKey)
        {
            const int keyStrength = DEFAULT_KEY_SIZE;

            if (privateKey == null)
            {
                privateKey = CreatePrivateKeyResource(issuerName);
            }
            var issuerPrivKey = privateKey;

            // Generating Random Numbers
            var randomGenerator = new CryptoApiRandomGenerator();
            var random          = new SecureRandom(randomGenerator);
            ISignatureFactory signatureFactory = new Asn1SignatureFactory("SHA256WITHRSA", issuerPrivKey, random);

            // The Certificate Generator
            var certificateGenerator = new X509V3CertificateGenerator();

            certificateGenerator.AddExtension(X509Extensions.SubjectAlternativeName, false, new GeneralNames(new GeneralName[] { new GeneralName(GeneralName.DnsName, "localhost"), new GeneralName(GeneralName.DnsName, "127.0.0.1") }));
            certificateGenerator.AddExtension(X509Extensions.ExtendedKeyUsage, true, new ExtendedKeyUsage(new List <DerObjectIdentifier>()
            {
                new DerObjectIdentifier("1.3.6.1.5.5.7.3.1")
            }));

            // Serial Number
            var serialNumber = BigIntegers.CreateRandomInRange(BigInteger.One, BigInteger.ValueOf(Int64.MaxValue), random);

            certificateGenerator.SetSerialNumber(serialNumber);

            // Issuer and Subject Name
            var subjectDn = new X509Name(subjectName);
            var issuerDn  = new X509Name(issuerName);

            certificateGenerator.SetIssuerDN(issuerDn);
            certificateGenerator.SetSubjectDN(subjectDn);

            // Valid For
            var notBefore = DateTime.UtcNow.Date;
            var notAfter  = notBefore.AddYears(70);

            certificateGenerator.SetNotBefore(notBefore);
            certificateGenerator.SetNotAfter(notAfter);

            // Subject Public Key
            var keyGenerationParameters = new KeyGenerationParameters(random, keyStrength);
            var keyPairGenerator        = new RsaKeyPairGenerator();

            keyPairGenerator.Init(keyGenerationParameters);
            var subjectKeyPair = keyPairGenerator.GenerateKeyPair();

            certificateGenerator.SetPublicKey(subjectKeyPair.Public);

            // self sign certificate
            var certificate = certificateGenerator.Generate(signatureFactory);

            // Originally pre-processor defines were used to try and pick the supported way to get from a Bouncy Castle
            // certificate and private key to a .NET certificate. The problem is that setting the private key on a .NET
            // X509 certificate is possible in .NET Framework but NOT in .NET Core. To complicate matters even further
            // the workaround in the CovertBouncyCert method of saving a cert + pvt key to a .pfx stream and then
            // reloading does not work on macOS or Unity (and possibly elsewhere) due to .pfx serialisation not being
            // compatible. This is the exception from Unity:
            //
            // Mono.Security.ASN1..ctor (System.Byte[] data) (at <6a66fe237d4242c9924192d3c28dd540>:0)
            // Mono.Security.X509.X509Certificate.Parse(System.Byte[] data)(at < 6a66fe237d4242c9924192d3c28dd540 >:0)
            //
            // Summary:
            // .NET Framework (including Mono on Linux, macOS and WSL)
            //  - Set x509.PrivateKey works.
            // .NET Standard:
            //  - Set x509.PrivateKey for a .NET Framework application.
            //  - Set x509.PrivateKey for a .NET Core application FAILS.
            // .NET Core:
            //  - Set x509.PrivateKey for a .NET Core application FAILS.
            //  - PFX serialisation works on Windows.
            //  - PFX serialisation works on WSL and Linux.
            //  - PFX serialisation FAILS on macOS.
            //
            // For same issue see https://github.com/dotnet/runtime/issues/23635.
            // For fix in net5 see https://github.com/dotnet/corefx/pull/42226.
            try
            {
                // corresponding private key
                var info = Org.BouncyCastle.Pkcs.PrivateKeyInfoFactory.CreatePrivateKeyInfo(subjectKeyPair.Private);

                // merge into X509Certificate2
                var x509 = new X509Certificate2(certificate.GetEncoded());

                var seq = (Asn1Sequence)Asn1Object.FromByteArray(info.ParsePrivateKey().GetDerEncoded());
                if (seq.Count != 9)
                {
                    throw new Org.BouncyCastle.OpenSsl.PemException("malformed sequence in RSA private key");
                }

                var rsa       = RsaPrivateKeyStructure.GetInstance(seq); //new RsaPrivateKeyStructure(seq);
                var rsaparams = new RsaPrivateCrtKeyParameters(
                    rsa.Modulus, rsa.PublicExponent, rsa.PrivateExponent, rsa.Prime1, rsa.Prime2, rsa.Exponent1, rsa.Exponent2, rsa.Coefficient);

                x509.PrivateKey = ToRSA(rsaparams);
                return(x509);
            }
            catch
            {
                return(ConvertBouncyCert(certificate, subjectKeyPair));
            }
        }
        /// <summary>
        /// Creates a cert with the connectionstring (token) and stores it in the given cert store.
        /// </summary>
        public async static Task WriteAsync(string name, string connectionString, string storeType, string storePath)
        {
            if (string.IsNullOrEmpty(connectionString))
            {
                throw new ArgumentException("Token not found in X509Store and no new token provided!");
            }

            SecureRandom            random = new SecureRandom();
            KeyGenerationParameters keyGenerationParameters = new KeyGenerationParameters(random, 2048);
            RsaKeyPairGenerator     keyPairGenerator        = new RsaKeyPairGenerator();

            keyPairGenerator.Init(keyGenerationParameters);
            AsymmetricCipherKeyPair keys = keyPairGenerator.GenerateKeyPair();

            ArrayList nameOids = new ArrayList();

            nameOids.Add(X509Name.CN);
            ArrayList nameValues = new ArrayList();

            nameValues.Add(name);
            X509Name subjectDN = new X509Name(nameOids, nameValues);
            X509Name issuerDN  = subjectDN;

            X509V3CertificateGenerator cg = new X509V3CertificateGenerator();

            cg.SetSerialNumber(BigIntegers.CreateRandomInRange(BigInteger.One, BigInteger.ValueOf(Int64.MaxValue), random));
            cg.SetIssuerDN(issuerDN);
            cg.SetSubjectDN(subjectDN);
            cg.SetNotBefore(DateTime.Now);
            cg.SetNotAfter(DateTime.Now.AddMonths(12));
            cg.SetPublicKey(keys.Public);
            cg.AddExtension(X509Extensions.KeyUsage, true, new KeyUsage(KeyUsage.DataEncipherment));

            // encrypt the token with the public key so only the owner of the assoc. private key can decrypt it and
            // "hide" it in the instruction code cert extension
            RSA              rsa       = RSA.Create();
            RSAParameters    rsaParams = new RSAParameters();
            RsaKeyParameters keyParams = (RsaKeyParameters)keys.Public;

            rsaParams.Modulus = new byte[keyParams.Modulus.ToByteArrayUnsigned().Length];
            keyParams.Modulus.ToByteArrayUnsigned().CopyTo(rsaParams.Modulus, 0);

            rsaParams.Exponent = new byte[keyParams.Exponent.ToByteArrayUnsigned().Length];
            keyParams.Exponent.ToByteArrayUnsigned().CopyTo(rsaParams.Exponent, 0);

            rsa.ImportParameters(rsaParams);
            if (rsa != null)
            {
                byte[] bytes = rsa.Encrypt(Encoding.ASCII.GetBytes(connectionString), RSAEncryptionPadding.OaepSHA1);
                if (bytes != null)
                {
                    cg.AddExtension(X509Extensions.InstructionCode, false, bytes);
                }
                else
                {
                    RsaUtils.RSADispose(rsa);
                    throw new CryptographicException("Can not encrypt IoTHub security token using generated public key!");
                }
            }
            RsaUtils.RSADispose(rsa);

            // sign the cert with the private key
            ISignatureFactory signatureFactory = new Asn1SignatureFactory("SHA256WITHRSA", keys.Private, random);

            Org.BouncyCastle.X509.X509Certificate x509 = cg.Generate(signatureFactory);

            // create a PKCS12 store for the cert and its private key
            X509Certificate2 certificate = null;

            using (MemoryStream pfxData = new MemoryStream())
            {
                Pkcs12StoreBuilder builder = new Pkcs12StoreBuilder();
                builder.SetUseDerEncoding(true);
                Pkcs12Store            pkcsStore = builder.Build();
                X509CertificateEntry[] chain     = new X509CertificateEntry[1];
                string passcode = Guid.NewGuid().ToString();
                chain[0] = new X509CertificateEntry(x509);
                pkcsStore.SetKeyEntry(name, new AsymmetricKeyEntry(keys.Private), chain);
                pkcsStore.Save(pfxData, passcode.ToCharArray(), random);

                // create X509Certificate2 object from PKCS12 file
                certificate = CertificateFactory.CreateCertificateFromPKCS12(pfxData.ToArray(), passcode);

                // handle each store type differently
                switch (storeType)
                {
                case CertificateStoreType.Directory:
                {
                    // Add to DirectoryStore
                    using (DirectoryCertificateStore store = new DirectoryCertificateStore())
                    {
                        store.Open(storePath);
                        X509CertificateCollection certificates = await store.Enumerate();

                        // remove any existing cert with our name from the store
                        foreach (X509Certificate2 cert in certificates)
                        {
                            if (cert.SubjectName.Decode(X500DistinguishedNameFlags.None | X500DistinguishedNameFlags.DoNotUseQuotes).Equals("CN=" + name, StringComparison.OrdinalIgnoreCase))
                            {
                                await store.Delete(cert.Thumbprint);
                            }
                        }

                        // add new one
                        await store.Add(certificate);
                    }
                    break;
                }

                case CertificateStoreType.X509Store:
                {
                    // Add to X509Store
                    using (X509Store store = new X509Store(storePath, StoreLocation.CurrentUser))
                    {
                        store.Open(OpenFlags.ReadWrite);

                        // remove any existing cert with our name from the store
                        foreach (X509Certificate2 cert in store.Certificates)
                        {
                            if (cert.SubjectName.Decode(X500DistinguishedNameFlags.None | X500DistinguishedNameFlags.DoNotUseQuotes).Equals("CN=" + name, StringComparison.OrdinalIgnoreCase))
                            {
                                store.Remove(cert);
                            }
                        }

                        // add new cert to store
                        try
                        {
                            store.Add(certificate);
                        }
                        catch (Exception e)
                        {
                            throw new Exception($"Not able to add cert to the requested store type '{storeType}' (exception message: '{e.Message}'.");
                        }
                    }
                    break;
                }

                default:
                {
                    throw new Exception($"The requested store type '{storeType}' is not supported. Please change.");
                }
                }
                return;
            }
        }
예제 #11
0
        public static (CertPrivateKey, BcCertificate) GenerateRsaCACertificate(string subjectName, int keyStrength = 2048)
        {
            // Generating Random Numbers
            var randomGenerator = new CryptoApiRandomGenerator();
            var random          = new SecureRandom(randomGenerator);

            // The Certificate Generator
            var certificateGenerator = new X509V3CertificateGenerator();

            // Serial Number
            var serialNumber = BigIntegers.CreateRandomInRange(BigInteger.One, BigInteger.ValueOf(Int64.MaxValue), random);

            certificateGenerator.SetSerialNumber(serialNumber);

            // Signature Algorithm
            const string signatureAlgorithm = "SHA256WithRSA";

#pragma warning disable CS0618 // Type or member is obsolete
            certificateGenerator.SetSignatureAlgorithm(signatureAlgorithm);
#pragma warning restore CS0618 // Type or member is obsolete

            // Issuer and Subject Name
            var subjectDN = new X509Name(subjectName);
            var issuerDN  = subjectDN;
            certificateGenerator.SetIssuerDN(issuerDN);
            certificateGenerator.SetSubjectDN(subjectDN);

            // Valid For
            var notBefore = DateTime.UtcNow.Date;
            var notAfter  = notBefore.AddYears(2);

            certificateGenerator.SetNotBefore(notBefore);
            certificateGenerator.SetNotAfter(notAfter);

            // Subject Public Key
            AsymmetricCipherKeyPair subjectKeyPair;
            var keyGenerationParameters = new KeyGenerationParameters(random, keyStrength);
            var keyPairGenerator        = new RsaKeyPairGenerator();
            keyPairGenerator.Init(keyGenerationParameters);
            subjectKeyPair = keyPairGenerator.GenerateKeyPair();

            certificateGenerator.SetPublicKey(subjectKeyPair.Public);

            // Generating the Certificate
            var issuerKeyPair = subjectKeyPair;

            // selfsign certificate
#pragma warning disable CS0618 // Type or member is obsolete
            var certificate = certificateGenerator.Generate(issuerKeyPair.Private, random);
#pragma warning restore CS0618 // Type or member is obsolete

            // var x509 = new System.Security.Cryptography.X509Certificates.X509Certificate2(certificate.GetEncoded());
            // // Add CA certificate to Root store
            // addCertToStore(cert, StoreName.Root, StoreLocation.CurrentUser);

            var key = new CertPrivateKey
            {
                KeyPair = issuerKeyPair,
            };

            return(key, certificate);
        }
예제 #12
0
 public virtual X509CertificateBuilder SetNotBefore(DateTime notBefore)
 {
     X509V3CertificateGenerator.SetNotBefore(notBefore);
     return(this);
 }
예제 #13
0
 public ICertificateBuilder SetNotBefore(DateTimeOffset notBefore)
 {
     certificateGenerator.SetNotBefore(notBefore.UtcDateTime);
     return(this);
 }
        public void TestCreationECDSA()
        {
            IBigInteger ECParraGX = new BigInteger(Base64.Decode("D/qWPNyogWzMM7hkK+35BcPTWFc9Pyf7vTs8uaqv"));
            IBigInteger ECParraGY = new BigInteger(Base64.Decode("AhQXGxb1olGRv6s1LPRfuatMF+cx3ZTGgzSE/Q5R"));
            IBigInteger ECParraH = new BigInteger(Base64.Decode("AQ=="));
            IBigInteger ECParraN = new BigInteger(Base64.Decode("f///////////////f///nl6an12QcfvRUiaIkJ0L"));
            IBigInteger ECPubQX = new BigInteger(Base64.Decode("HWWi17Yb+Bm3PYr/DMjLOYNFhyOwX1QY7ZvqqM+l"));
            IBigInteger ECPubQY = new BigInteger(Base64.Decode("JrlJfxu3WGhqwtL/55BOs/wsUeiDFsvXcGhB8DGx"));
            IBigInteger ECPrivD = new BigInteger(Base64.Decode("GYQmd/NF1B+He1iMkWt3by2Az6Eu07t0ynJ4YCAo"));
            FPCurve curve = new FPCurve(
               new BigInteger("883423532389192164791648750360308885314476597252960362792450860609699839"), // q
                new BigInteger("7fffffffffffffffffffffff7fffffffffff8000000000007ffffffffffc", 16), // a
                new BigInteger("6b016c3bdcf18941d0d654921475ca71a9db2fb27d1d37796185c2942c0a", 16)); // b
            ECDomainParameters ecDomain =
                new ECDomainParameters(curve, new FPPoint(curve, curve.FromBigInteger(ECParraGX), curve.FromBigInteger(ECParraGY)), ECParraN);
            ECPublicKeyParameters ecPub = new ECPublicKeyParameters(
                "ECDSA",
                new FPPoint(curve,
                    curve.FromBigInteger(ECPubQX),
                    curve.FromBigInteger(ECPubQY)),
                ecDomain);
            ECPrivateKeyParameters ecPriv = new ECPrivateKeyParameters("ECDSA", ECPrivD, ecDomain);

            IDictionary attrs = new Hashtable();
            attrs[X509Name.C] = "AU";
            attrs[X509Name.O] = "The Legion of the Bouncy Castle";
            attrs[X509Name.L] = "Melbourne";
            attrs[X509Name.ST] = "Victoria";
            attrs[X509Name.E] = "*****@*****.**";

            IList ord = new ArrayList();
            ord.Add(X509Name.C);
            ord.Add(X509Name.O);
            ord.Add(X509Name.L);
            ord.Add(X509Name.ST);
            ord.Add(X509Name.E);

            IList values = new ArrayList();
            values.Add("AU");
            values.Add("The Legion of the Bouncy Castle");
            values.Add("Melbourne");
            values.Add("Victoria");
            values.Add("*****@*****.**");

            X509V3CertificateGenerator certGen = new X509V3CertificateGenerator();

            certGen.SetSerialNumber(BigInteger.One);

            certGen.SetIssuerDN(new X509Name(ord, attrs));
            certGen.SetNotBefore(DateTime.Today.Subtract(new TimeSpan(1, 0, 0, 0)));
            certGen.SetNotAfter(DateTime.Today.AddDays(1));
            certGen.SetSubjectDN(new X509Name(ord, attrs));
            certGen.SetPublicKey(ecPub);
            certGen.SetSignatureAlgorithm("SHA1WITHECDSA");

            X509Certificate cert = certGen.Generate(ecPriv);

            //            Assert.IsTrue((cert.IsValidNow && cert.Verify(ecPub)), "Certificate failed to be valid (ECDSA)");
            cert.CheckValidity();
            cert.Verify(ecPub);

            ISet dummySet = cert.GetNonCriticalExtensionOids();

            if (dummySet != null)
            {
                foreach (string key in dummySet)
                {
                    Console.WriteLine("\t{0}:\t{1}", key);
                }
            }

            Console.WriteLine();

            dummySet = cert.GetNonCriticalExtensionOids();

            if (dummySet != null)
            {
                foreach (string key in dummySet)
                {
                    Console.WriteLine("\t{0}:\t{1}", key);
                }
            }

            Console.WriteLine();
        }
예제 #15
0
파일: mkcert.cs 프로젝트: ywscr/MimeKit
        public static void Main(string[] args)
        {
            var x509NameOids = CreateX509NameOidMapping();
            var oids         = new List <DerObjectIdentifier> ();
            var values       = new List <string> ();
            var privateKey   = new PrivateKeyOptions();
            var options      = new GeneratorOptions();
            AsymmetricCipherKeyPair key;
            string section = null;
            string alias   = null;

            options.Output = Path.ChangeExtension(args[0], ".pfx");

            using (var reader = File.OpenText(args[0])) {
                string line;

                while ((line = reader.ReadLine()) != null)
                {
                    if (line.Length == 0 || line[0] == '#')
                    {
                        continue;
                    }

                    if (line[0] == '[')
                    {
                        int endIndex = line.IndexOf(']');

                        if (endIndex == -1)
                        {
                            Console.Error.WriteLine("Incomplete section: ", line);
                            return;
                        }

                        section = line.Substring(1, endIndex - 1);
                        continue;
                    }

                    var kvp      = line.Split(new char[] { '=' }, 2);
                    var property = kvp[0].ToLowerInvariant().Trim();
                    var value    = kvp[1].Trim();

                    switch (section.ToLowerInvariant())
                    {
                    case "privatekey":
                        switch (property)
                        {
                        case "algorithm":
                            privateKey.Algorithm = value;
                            break;

                        case "bitlength":
                            if (int.TryParse(value, out int bitLength))
                            {
                                privateKey.BitLength = bitLength;
                            }
                            else
                            {
                                Console.Error.WriteLine("Invalid [PrivateKey] BitLength: {0}", value);
                                return;
                            }
                            break;

                        case "filename":
                            privateKey.FileName = value;
                            break;

                        default:
                            Console.Error.WriteLine("Unknown [PrivateKey] property: {0}", kvp[0]);
                            return;
                        }
                        break;

                    case "subject":
                        if (x509NameOids.TryGetValue(property, out DerObjectIdentifier oid))
                        {
                            if (oid == X509Name.CN)
                            {
                                alias = value;
                            }
                            else if (alias == null && oid == X509Name.E)
                            {
                                alias = value;
                            }

                            values.Add(value);
                            oids.Add(oid);
                        }
                        else
                        {
                            Console.Error.WriteLine("Unknown [Subject] property: {0}", kvp[0]);
                            return;
                        }
                        break;

                    case "generator":
                        switch (property)
                        {
                        case "basicconstraints":
                            options.BasicConstraints = value;
                            break;

                        case "daysvalid":
                            if (int.TryParse(value, out int days))
                            {
                                options.DaysValid = days;
                            }
                            else
                            {
                                Console.Error.WriteLine("Invalid [Generator] DaysValid: {0}", value);
                                return;
                            }
                            break;

                        case "issuer":
                            options.Issuer = value;
                            break;

                        case "issuerpassword":
                            options.IssuerPassword = value;
                            break;

                        case "keyusage":
                            options.KeyUsage = value;
                            break;

                        case "output":
                            options.Output = value;
                            break;

                        case "password":
                            options.Password = value;
                            break;

                        case "signaturealgorithm":
                            options.SignatureAlgorithm = value;
                            break;

                        default:
                            Console.Error.WriteLine("Unknown [Generator] property: {0}", kvp[0]);
                            return;
                        }
                        break;

                    default:
                        Console.Error.WriteLine("Unknown section: {0}", section);
                        break;
                    }
                }
            }

            // Sanity Checks
            if (!string.IsNullOrEmpty(privateKey.FileName) && !File.Exists(privateKey.FileName))
            {
                Console.Error.WriteLine("[PrivateKey] FileName `{0}' does not exist!", privateKey.FileName);
                return;
            }

            if (oids.Count == 0)
            {
                Console.Error.WriteLine("No [Subject] specified.");
                return;
            }

            if (string.IsNullOrEmpty(options.Issuer))
            {
                Console.Error.WriteLine("[Generator] Issuer property cannot be empty!");
                return;
            }
            else if (options.Issuer != "this" && !File.Exists(options.Issuer))
            {
                Console.Error.WriteLine("[Generator] Issuer `{0}' does not exist!", options.Issuer);
                return;
            }

            if (string.IsNullOrEmpty(options.Output))
            {
                Console.Error.WriteLine("[Generator] Output property cannot be empty!");
                return;
            }

            var randomGenerator = new CryptoApiRandomGenerator();
            var random          = new SecureRandom(randomGenerator);
            var subject         = new X509Name(oids, values);

            if (string.IsNullOrEmpty(privateKey.FileName))
            {
                var keyGenerationParameters = new KeyGenerationParameters(random, privateKey.BitLength);
                IAsymmetricCipherKeyPairGenerator keyPairGenerator;

                switch (privateKey.Algorithm.ToLowerInvariant())
                {
                case "rsa": keyPairGenerator = new RsaKeyPairGenerator(); break;

                case "ecdsa": keyPairGenerator = new ECKeyPairGenerator("ECDSA"); break;

                default: Console.Error.WriteLine("Unsupported PrivateKey algorithm: {0}", privateKey.Algorithm); return;
                }
                keyPairGenerator.Init(keyGenerationParameters);
                key = keyPairGenerator.GenerateKeyPair();
            }
            else
            {
                try {
                    key = LoadAsymmetricCipherKeyPair(privateKey.FileName);
                } catch (Exception ex) {
                    Console.Error.WriteLine("[PrivateKey] Failed to load `{0}': {1}", privateKey.FileName, ex.Message);
                    return;
                }
            }

            AsymmetricKeyParameter signingKey;
            X509Certificate        issuerCertificate;

            X509Certificate[] chain;
            X509Name          issuer;

            if (options.Issuer != "this")
            {
                try {
                    chain             = LoadPkcs12CertificateChain(options.Issuer, options.IssuerPassword, out signingKey);
                    issuerCertificate = chain[0];
                    issuer            = chain[0].SubjectDN;
                } catch (Exception ex) {
                    Console.Error.WriteLine("[Generator] failed to load `{0}': {1}", options.Issuer, ex.Message);
                    return;
                }
            }
            else
            {
                chain             = new X509Certificate[0];
                issuerCertificate = null;
                signingKey        = key.Private;
                issuer            = subject;
            }

            string signatureAlgorithm;

            if (string.IsNullOrEmpty(options.SignatureAlgorithm))
            {
                if (signingKey is RsaPrivateCrtKeyParameters)
                {
                    signatureAlgorithm = "SHA256WithRSA";
                }
                else if (signingKey is ECPrivateKeyParameters ec)
                {
                    if (ec.AlgorithmName == "ECGOST3410")
                    {
                        signatureAlgorithm = "GOST3411WithECGOST3410";
                    }
                    else
                    {
                        signatureAlgorithm = "SHA256withECDSA";
                    }
                }
                else
                {
                    signatureAlgorithm = "GOST3411WithGOST3410";
                }
            }
            else
            {
                signatureAlgorithm = options.SignatureAlgorithm;
            }

            int        serialNumberIndex = oids.IndexOf(X509Name.SerialNumber);
            BigInteger serialNumber;

            if (serialNumberIndex == -1)
            {
                serialNumber = BigIntegers.CreateRandomInRange(BigInteger.One, BigInteger.ValueOf(long.MaxValue), random);
            }
            else
            {
                try {
                    serialNumber = new BigInteger(values[serialNumberIndex]);
                } catch {
                    Console.Error.WriteLine("Invalid [Subject] SerialNumber: {0}", values[serialNumberIndex]);
                    return;
                }
            }

            var notBefore = DateTime.UtcNow;
            var notAfter  = notBefore.AddDays(options.DaysValid);

            var signatureFactory = new Asn1SignatureFactory(signatureAlgorithm, signingKey, random);
            var generator        = new X509V3CertificateGenerator();

            generator.SetSerialNumber(serialNumber);
            generator.SetPublicKey(key.Public);
            generator.SetNotBefore(notBefore);
            generator.SetNotAfter(notAfter);
            generator.SetSubjectDN(subject);
            generator.SetIssuerDN(issuer);

            generator.AddExtension(X509Extensions.SubjectKeyIdentifier, false, new SubjectKeyIdentifierStructure(key.Public));

            if (issuerCertificate != null)
            {
                generator.AddExtension(X509Extensions.AuthorityKeyIdentifier, false, new AuthorityKeyIdentifierStructure(issuerCertificate));
            }

            if (!string.IsNullOrEmpty(options.BasicConstraints))
            {
                var  basicConstraints = options.BasicConstraints.Split(new char[] { ',' }, StringSplitOptions.RemoveEmptyEntries);
                bool critical         = false;
                bool ca = false;

                foreach (var constraint in basicConstraints)
                {
                    switch (constraint.Trim().ToLowerInvariant())
                    {
                    case "critical": critical = true; break;

                    case "ca:false": ca = false; break;

                    case "ca:true": ca = true; break;
                    }
                }

                generator.AddExtension(X509Extensions.BasicConstraints, critical, new BasicConstraints(ca));
            }

            if (!string.IsNullOrEmpty(options.KeyUsage))
            {
                var  keyUsages = options.KeyUsage.Split(new char[] { ',' }, StringSplitOptions.RemoveEmptyEntries);
                bool critical  = false;
                int  keyUsage  = 0;

                foreach (var usage in keyUsages)
                {
                    switch (usage.Trim().ToLowerInvariant())
                    {
                    case "critical": critical = true; break;

                    case "digitalsignature": keyUsage |= X509KeyUsage.DigitalSignature; break;

                    case "nonrepudiation": keyUsage |= X509KeyUsage.NonRepudiation; break;

                    case "keyencipherment": keyUsage |= X509KeyUsage.KeyEncipherment; break;

                    case "dataencipherment": keyUsage |= X509KeyUsage.DataEncipherment; break;

                    case "keyagreement": keyUsage |= X509KeyUsage.KeyAgreement; break;

                    case "keycertsign": keyUsage |= X509KeyUsage.KeyCertSign; break;

                    case "crlsign": keyUsage |= X509KeyUsage.CrlSign; break;

                    case "encipheronly": keyUsage |= X509KeyUsage.EncipherOnly; break;

                    case "decipheronly": keyUsage |= X509KeyUsage.DecipherOnly; break;
                    }
                }

                generator.AddExtension(X509Extensions.KeyUsage, critical, new KeyUsage(keyUsage));
            }

            var certificate = generator.Generate(signatureFactory);
            var keyEntry    = new AsymmetricKeyEntry(key.Private);

            var chainEntries = new X509CertificateEntry[chain.Length + 1];

            chainEntries[0] = new X509CertificateEntry(certificate);
            for (int i = 0; i < chain.Length; i++)
            {
                chainEntries[i + 1] = new X509CertificateEntry(chain[i]);
            }

            var pkcs12 = new Pkcs12Store();

            pkcs12.SetKeyEntry(alias ?? string.Empty, keyEntry, chainEntries);

            using (var stream = File.Create(options.Output))
                pkcs12.Save(stream, options.Password.ToCharArray(), random);

            Console.WriteLine("{0} {1}", options.Output, GetFingerprint(certificate));
        }
예제 #16
0
        public Org.BouncyCastle.X509.X509Certificate GenerateCertificate(SecureRandom random,
                                                                         string subjectName,
                                                                         AsymmetricCipherKeyPair subjectKeyPair,
                                                                         BigInteger subjectSerialNumber,
                                                                         string[] subjectAlternativeNames,
                                                                         string issuerName,
                                                                         AsymmetricCipherKeyPair issuerKeyPair,
                                                                         BigInteger issuerSerialNumber,
                                                                         bool isCertificateAuthority,
                                                                         KeyPurposeID[] usages)
        {
            var certificateGenerator = new X509V3CertificateGenerator();

            certificateGenerator.SetSerialNumber(subjectSerialNumber);

            // Set the signature algorithm. This is used to generate the thumbprint which is then signed
            // with the issuer's private key. We'll use SHA-256, which is (currently) considered fairly strong.
            const string signatureAlgorithm = "SHA256WithRSA";

            certificateGenerator.SetSignatureAlgorithm(signatureAlgorithm);

            var issuerDN = new X509Name(issuerName);

            certificateGenerator.SetIssuerDN(issuerDN);

            // Note: The subject can be omitted if you specify a subject alternative name (SAN).
            var subjectDN = new X509Name(subjectName);

            certificateGenerator.SetSubjectDN(subjectDN);

            // Our certificate needs valid from/to values.
            var notBefore = DateTime.UtcNow.Date;
            var notAfter  = notBefore.AddYears(20);

            certificateGenerator.SetNotBefore(notBefore);
            certificateGenerator.SetNotAfter(notAfter);

            // The subject's public key goes in the certificate.
            certificateGenerator.SetPublicKey(subjectKeyPair.Public);

            AddAuthorityKeyIdentifier(certificateGenerator, issuerDN, issuerKeyPair, issuerSerialNumber);
            AddSubjectKeyIdentifier(certificateGenerator, subjectKeyPair);
            AddBasicConstraints(certificateGenerator, isCertificateAuthority);

            if (usages != null && usages.Any())
            {
                AddExtendedKeyUsage(certificateGenerator, usages);
            }

            if (subjectAlternativeNames != null && subjectAlternativeNames.Any())
            {
                AddSubjectAlternativeNames(certificateGenerator, subjectAlternativeNames);
            }



            // The certificate is signed with the issuer's private key.
            var certificate = certificateGenerator.Generate(issuerKeyPair.Private, random);

            return(certificate);
        }
예제 #17
0
        public string CreateAndStoreNewClientCertificate(string subjectName, string pvkPass, X509Certificate2 issuer)
        {
            X509V3CertificateGenerator generator = new X509V3CertificateGenerator();

            // Generate pseudo random number
            var randomGen = new CryptoApiRandomGenerator();
            var random    = new SecureRandom(randomGen);

            // Set certificate serial number
            var serialNumber =
                BigIntegers.CreateRandomInRange(BigInteger.One, BigInteger.ValueOf(Int64.MaxValue), random);

            generator.SetSerialNumber(serialNumber);

            // Set certificate subject name
            var subjectDN = new X509Name(subjectName);

            generator.SetSubjectDN(subjectDN);

            // Set issuer subject name
            var issuerDN = new X509Name(issuer.Subject);

            generator.SetIssuerDN(issuerDN);

            // Set certificate validity
            var notBefore = DateTime.UtcNow.Date;

            generator.SetNotBefore(notBefore);
            generator.SetNotAfter(notBefore.AddYears(2));

            // Generate new RSA key pair for certificate
            var keyGeneratorParameters = new KeyGenerationParameters(random, RSAKeyStrength);
            var keyPairGenerator       = new RsaKeyPairGenerator();

            keyPairGenerator.Init(keyGeneratorParameters);
            var subjectKeyPair = keyPairGenerator.GenerateKeyPair();

            // Import public key into generator
            generator.SetPublicKey(subjectKeyPair.Public);

            var issuerKeyPair = DotNetUtilities.GetKeyPair(issuer.PrivateKey);

            // Get key pair from .net issuer certificate
            //var issuerKeyPair = DotNetUtilities.GetKeyPair(issuer.PrivateKey);
            var issuerSerialNumber = new BigInteger(issuer.GetSerialNumber());

            // Sign CA key with serial
            var caKeyIdentifier = new AuthorityKeyIdentifier(
                SubjectPublicKeyInfoFactory.CreateSubjectPublicKeyInfo(issuerKeyPair.Public),
                new GeneralNames(new GeneralName(issuerDN)),
                issuerSerialNumber);

            generator.AddExtension(
                X509Extensions.AuthorityKeyIdentifier.Id,
                false,
                caKeyIdentifier);

            // Create signature factory to sign new cert
            ISignatureFactory signatureFactory = new Asn1SignatureFactory(SignatureAlgorithm, issuerKeyPair.Private);

            // Generate new bouncy castle certificate signed by issuer
            var newCertificate = generator.Generate(signatureFactory);

            var    store        = new Pkcs12Store();
            string friendlyName = newCertificate.SubjectDN.ToString().Split('=')[1];

            var certificateEntry = new X509CertificateEntry(newCertificate);

            // Set certificate
            store.SetCertificateEntry(friendlyName, certificateEntry);
            // Set private key
            store.SetKeyEntry(
                friendlyName,
                new AsymmetricKeyEntry(subjectKeyPair.Private),
                new X509CertificateEntry[] { certificateEntry });

            var privatePath = @".\certs\" + $"{friendlyName}.pfx";
            var publicPath  = @".\certs\" + $"{friendlyName}.cer";

            using (var stream = new MemoryStream())
            {
                // Convert bouncy castle cert => .net cert
                store.Save(stream, pvkPass.ToCharArray(), random);
                var dotNetCertificate = new X509Certificate2(
                    stream.ToArray(),
                    pvkPass,
                    X509KeyStorageFlags.Exportable | X509KeyStorageFlags.PersistKeySet);

                // Extract public part to store in server storage
                var publicCert = dotNetCertificate.Export(X509ContentType.Cert);
                // Extract private parameters to export into .pfx for distribution
                var privateCert = dotNetCertificate.Export(X509ContentType.Pfx, pvkPass);

                dotNetCertificate.Reset();
                dotNetCertificate.Import(publicCert);

                // Store public cert info in storage
                using (var storage = new X509Store(StoreName.My, StoreLocation.LocalMachine))
                {
                    storage.Open(OpenFlags.ReadWrite);
                    storage.Add(dotNetCertificate);
                    storage.Close();
                }

                dotNetCertificate.Dispose();

                // Write private parameters to .pfx file to install at client
                File.WriteAllBytes(privatePath, privateCert);
                File.WriteAllBytes(publicPath, publicCert);
            }

            return(privatePath);
        }
예제 #18
0
        public static X509Certificate2 CreateSelfSignedCertificateBasedOnPrivateKey(string commonNameValue,
                                                                                    X509Name issuer,
                                                                                    AsymmetricKeyParameter issuerPrivKey,
                                                                                    bool isClientCertificate,
                                                                                    bool isCaCertificate,
                                                                                    int yearsUntilExpiration)
        {
            const int keyStrength = 2048;

            // Generating Random Numbers
            var random = GetSeededSecureRandom();
            ISignatureFactory signatureFactory = new Asn1SignatureFactory("SHA512WITHRSA", issuerPrivKey, random);

            // The Certificate Generator
            X509V3CertificateGenerator certificateGenerator = new X509V3CertificateGenerator();

            if (isClientCertificate)
            {
                certificateGenerator.AddExtension(X509Extensions.ExtendedKeyUsage.Id, true, new ExtendedKeyUsage(KeyPurposeID.IdKPClientAuth));
            }
            else
            {
                certificateGenerator.AddExtension(X509Extensions.ExtendedKeyUsage.Id, true,
                                                  new ExtendedKeyUsage(KeyPurposeID.IdKPServerAuth, KeyPurposeID.IdKPClientAuth));
            }

            if (isCaCertificate)
            {
                certificateGenerator.AddExtension(X509Extensions.BasicConstraints.Id, true, new BasicConstraints(0));
                certificateGenerator.AddExtension(X509Extensions.KeyUsage.Id, false,
                                                  new X509KeyUsage(X509KeyUsage.KeyCertSign | X509KeyUsage.CrlSign));
            }

            // Serial Number
            BigInteger serialNumber = BigIntegers.CreateRandomInRange(BigInteger.One, BigInteger.ValueOf(Int64.MaxValue), random);

            certificateGenerator.SetSerialNumber(serialNumber);

            // Issuer and Subject Name

            X509Name subjectDN = new X509Name("CN=" + commonNameValue);

            certificateGenerator.SetIssuerDN(issuer);
            certificateGenerator.SetSubjectDN(subjectDN);

            // Valid For
            DateTime notBefore = DateTime.UtcNow.Date.AddDays(-7);
            DateTime notAfter  = notBefore.AddYears(yearsUntilExpiration);

            certificateGenerator.SetNotBefore(notBefore);
            certificateGenerator.SetNotAfter(notAfter);

            // Subject Public Key
            var keyGenerationParameters = new KeyGenerationParameters(random, keyStrength);
            var keyPairGenerator        = new RsaKeyPairGenerator();

            keyPairGenerator.Init(keyGenerationParameters);
            var subjectKeyPair = keyPairGenerator.GenerateKeyPair();

            certificateGenerator.SetPublicKey(subjectKeyPair.Public);

            X509Certificate certificate      = certificateGenerator.Generate(signatureFactory);
            var             store            = new Pkcs12Store();
            string          friendlyName     = certificate.SubjectDN.ToString();
            var             certificateEntry = new X509CertificateEntry(certificate);

            store.SetCertificateEntry(friendlyName, certificateEntry);
            store.SetKeyEntry(friendlyName, new AsymmetricKeyEntry(subjectKeyPair.Private), new[] { certificateEntry });
            var stream = new MemoryStream();

            store.Save(stream, new char[0], random);
            var convertedCertificate =
                new X509Certificate2(
                    stream.ToArray(), (string)null,
                    X509KeyStorageFlags.PersistKeySet | X509KeyStorageFlags.Exportable);

            stream.Position = 0;

            return(convertedCertificate);
        }
예제 #19
0
        internal PkiCertificate Create(X509Name issuerName, PkiKey issuerPrivateKey,
                                       X509Name subjectName, DateTimeOffset notBefore, DateTimeOffset notAfter,
                                       byte[] serialNumber, X509KeyUsage keyUsage = null, KeyPurposeID[] extKeyUsage = null)
        {
            // Based on:
            //    https://stackoverflow.com/a/39456955/5428506
            //    https://github.com/bcgit/bc-csharp/blob/master/crypto/test/src/test/CertTest.cs

            var pubKey = _keyPair?.PublicKey.NativeKey ?? PublicKey.NativeKey;

            var sigFactory = ComputeSignatureAlgorithm(issuerPrivateKey.NativeKey);
            var certGen    = new X509V3CertificateGenerator();

            certGen.SetSerialNumber(new BigInteger(serialNumber));
            certGen.SetIssuerDN(issuerName);
            certGen.SetSubjectDN(subjectName);
            certGen.SetNotBefore(notBefore.UtcDateTime);
            certGen.SetNotAfter(notAfter.UtcDateTime);
            certGen.SetPublicKey(pubKey);

            if (keyUsage == null)
            {
                keyUsage = new X509KeyUsage(X509KeyUsage.KeyEncipherment |
                                            X509KeyUsage.DigitalSignature);
            }
            if (extKeyUsage == null)
            {
                extKeyUsage = new[] {
                    KeyPurposeID.IdKPClientAuth,
                    KeyPurposeID.IdKPServerAuth
                }
            }
            ;

            certGen.AddExtension("2.5.29.15", true, keyUsage);
            certGen.AddExtension("2.5.29.37", true, new DerSequence(extKeyUsage));

            // Based on:
            //    https://boredwookie.net/blog/bouncy-castle-add-a-subject-alternative-name-when-creating-a-cer

            foreach (var ext in CertificateExtensions)
            {
                // certGen.AddExtension(ext.Identifier, ext.Value.IsCritical, ext.Value.Value);
                certGen.AddExtension(ext.Identifier, ext.IsCritical, ext.Value);
            }

            var bcCert = certGen.Generate(sigFactory);

            return(new PkiCertificate
            {
                NativeCertificate = bcCert,
            });

            // Compare to LE-issued Certs:
            //    Enhanced Key Usage:
            //        Server Authentication (1.3.6.1.5.5.7.3.1)
            //        Client Authentication (1.3.6.1.5.5.7.3.2)
            //    Subject Key Identifier:
            //        e05bf2ba81d8d3845ff45b5638551e64ca19133d
            //    Authority Key Identifier:
            //        KeyID=a84a6a63047dddbae6d139b7a64565eff3a8eca1
            //    Authority Information Access:
            //        [1]Authority Info Access
            //            Access Method=On-line Certificate Status Protocol (1.3.6.1.5.5.7.48.1)
            //            Alternative Name:
            //                URL=http://ocsp.int-x3.letsencrypt.org
            //        [2]Authority Info Access
            //            Access Method=Certification Authority Issuer (1.3.6.1.5.5.7.48.2)
            //            Alternative Name:
            //                URL=http://cert.int-x3.letsencrypt.org/
            //    Certificate Policies:
            //        ...
            //    SCT List:
            //        ...
            //    Key Usage:
            //        Digital Signature, Key Encipherment (a0)
            //    Basic Constraints:
            //        Subject Type=End Entity
            //        Path Length Constraint=None

            // CA:
            //    Key Usage:
            //        Digital Signature, Certificate Signing, Off-line CRL Signing, CRL Signing (86)
        }
예제 #20
0
        /// <summary>
        /// Create a self signed certificate with bouncy castle.
        /// </summary>
        public static X509Certificate2 GenerateCertificate(
            string subjectName,
            Action <X509V3CertificateGenerator> modifyGenerator,
            string signatureAlgorithm = "SHA256WITHRSA",
            int publicKeyLength       = 2048,
            ChainCertificateRequest chainCertificateRequest = null)
        {
            if (string.IsNullOrEmpty(subjectName))
            {
                subjectName = "NuGetTest";
            }

            var random  = new SecureRandom();
            var keyPair = GenerateKeyPair(publicKeyLength);

            // Create cert
            var subjectDN = $"CN={subjectName}";
            var certGen   = new X509V3CertificateGenerator();

            certGen.SetSubjectDN(new X509Name(subjectDN));

            // default to new key pair
            var issuerPrivateKey = keyPair.Private;
            var keyUsage         = KeyUsage.DigitalSignature;
            var issuerDN         = chainCertificateRequest?.IssuerDN ?? subjectDN;

            certGen.SetIssuerDN(new X509Name(issuerDN));

#if IS_DESKTOP
            if (chainCertificateRequest != null)
            {
                if (chainCertificateRequest.Issuer != null)
                {
                    // for a certificate with an issuer assign Authority Key Identifier
                    var issuer   = chainCertificateRequest?.Issuer;
                    var bcIssuer = DotNetUtilities.FromX509Certificate(issuer);
                    var authorityKeyIdentifier = new AuthorityKeyIdentifierStructure(bcIssuer);
                    issuerPrivateKey = DotNetUtilities.GetKeyPair(issuer.PrivateKey).Private;
                    certGen.AddExtension(X509Extensions.AuthorityKeyIdentifier.Id, false, authorityKeyIdentifier);
                }

                if (chainCertificateRequest.ConfigureCrl)
                {
                    // for a certificate in a chain create CRL distribution point extension
                    var crlServerUri  = $"{chainCertificateRequest.CrlServerBaseUri}{issuerDN}.crl";
                    var generalName   = new Org.BouncyCastle.Asn1.X509.GeneralName(Org.BouncyCastle.Asn1.X509.GeneralName.UniformResourceIdentifier, new DerIA5String(crlServerUri));
                    var distPointName = new DistributionPointName(new GeneralNames(generalName));
                    var distPoint     = new DistributionPoint(distPointName, null, null);

                    certGen.AddExtension(X509Extensions.CrlDistributionPoints, critical: false, extensionValue: new DerSequence(distPoint));
                }

                if (chainCertificateRequest.IsCA)
                {
                    // update key usage with CA cert sign and crl sign attributes
                    keyUsage |= KeyUsage.CrlSign | KeyUsage.KeyCertSign;
                }
            }
#endif
            certGen.SetNotAfter(DateTime.UtcNow.Add(TimeSpan.FromHours(1)));
            certGen.SetNotBefore(DateTime.UtcNow.Subtract(TimeSpan.FromHours(1)));
            certGen.SetPublicKey(keyPair.Public);

            var serialNumber = BigIntegers.CreateRandomInRange(BigInteger.One, BigInteger.ValueOf(long.MaxValue), random);
            certGen.SetSerialNumber(serialNumber);

            var subjectKeyIdentifier = new SubjectKeyIdentifier(SubjectPublicKeyInfoFactory.CreateSubjectPublicKeyInfo(keyPair.Public));
            certGen.AddExtension(X509Extensions.SubjectKeyIdentifier.Id, false, subjectKeyIdentifier);

            certGen.AddExtension(X509Extensions.KeyUsage.Id, false, new KeyUsage(keyUsage));
            certGen.AddExtension(X509Extensions.BasicConstraints.Id, true, new BasicConstraints(chainCertificateRequest?.IsCA ?? false));

            // Allow changes
            modifyGenerator?.Invoke(certGen);

            var signatureFactory = new Asn1SignatureFactory(signatureAlgorithm, issuerPrivateKey, random);
            var certificate      = certGen.Generate(signatureFactory);
            var certResult       = new X509Certificate2(certificate.GetEncoded());

#if IS_DESKTOP
            certResult.PrivateKey = DotNetUtilities.ToRSA(keyPair.Private as RsaPrivateCrtKeyParameters);
#endif

            return(certResult);
        }
예제 #21
0
        private static X509Certificate2 CreateSelfSignedCertificate(string agentGuid, string logAnalyticsWorkspaceId)
        {
            var random = new SecureRandom();

            var certificateGenerator = new X509V3CertificateGenerator();

            var serialNumber = BigIntegers.CreateRandomInRange(BigInteger.One, BigInteger.ValueOf(Int64.MaxValue), random);

            certificateGenerator.SetSerialNumber(serialNumber);

            var dirName = string.Format("CN={0}, CN={1}, OU=Linux Monitoring Agent, O=Microsoft", logAnalyticsWorkspaceId, agentGuid);

            X509Name certName = new X509Name(dirName);

            certificateGenerator.SetIssuerDN(certName);

            certificateGenerator.SetSubjectDN(certName);

            certificateGenerator.SetNotBefore(DateTime.UtcNow.Date);

            certificateGenerator.SetNotAfter(DateTime.UtcNow.Date.AddYears(1));

            const int strength = 2048;

            var keyGenerationParameters = new KeyGenerationParameters(random, strength);

            var keyPairGenerator = new RsaKeyPairGenerator();

            keyPairGenerator.Init(keyGenerationParameters);

            var subjectKeyPair = keyPairGenerator.GenerateKeyPair();

            certificateGenerator.SetPublicKey(subjectKeyPair.Public);


            // Get Private key for the Certificate
            TextWriter textWriter = new StringWriter();
            PemWriter  pemWriter  = new PemWriter(textWriter);

            pemWriter.WriteObject(subjectKeyPair.Private);
            pemWriter.Writer.Flush();

            string privateKeyString = textWriter.ToString();


            // The magic extension that on commenting made the certificate work with ODS!!!!!

            //certificateGenerator.AddExtension(X509Extensions.ExtendedKeyUsage.Id, false,
            //  new ExtendedKeyUsage(new[] { KeyPurposeID.IdKPServerAuth, KeyPurposeID.IdKPClientAuth }));

            //certificateGenerator.AddExtension(X509Extensions.ExtendedKeyUsage.Id, false,
            //  new AuthorityKeyIdentifier(
            //      new GeneralNames(new GeneralName(certName)), serialNumber));


            //certificateGenerator.AddExtension(X509Extensions.ExtendedKeyUsage.Id, false,
            //   new AuthorityKeyIdentifier(
            //       SubjectPublicKeyInfoFactory.CreateSubjectPublicKeyInfo(subjectKeyPair.Public),
            //       new GeneralNames(new GeneralName(certName)), serialNumber));


            var issuerKeyPair    = subjectKeyPair;
            var signatureFactory = new Asn1SignatureFactory(Constants.DEFAULT_SIGNATURE_ALOGIRTHM, issuerKeyPair.Private);
            var bouncyCert       = certificateGenerator.Generate(signatureFactory);

            // Lets convert it to X509Certificate2
            X509Certificate2 certificate;

            Pkcs12Store store = new Pkcs12StoreBuilder().Build();

            store.SetKeyEntry($"{agentGuid}_key", new AsymmetricKeyEntry(subjectKeyPair.Private), new[] { new X509CertificateEntry(bouncyCert) });

            string exportpw = Guid.NewGuid().ToString("x");

            using (var ms = new MemoryStream())
            {
                store.Save(ms, exportpw.ToCharArray(), random);
                certificate = new X509Certificate2(ms.ToArray(), exportpw, X509KeyStorageFlags.Exportable);
            }

            // Get the value.
            string resultsTrue = certificate.ToString(true);

            // Display the value to the console.
            Console.WriteLine(resultsTrue);

            //Get Certificate in PEM format
            StringBuilder builder = new StringBuilder();

            builder.AppendLine("-----BEGIN CERTIFICATE-----");
            builder.AppendLine(
                Convert.ToBase64String(certificate.RawData, Base64FormattingOptions.InsertLineBreaks));
            builder.AppendLine("-----END CERTIFICATE-----");

            Console.WriteLine("Writing certificate and key to two files");

            string crt_location = "C://oms.crt";
            string key_location = "C://oms.key";

            try
            {
                if (!String.IsNullOrEmpty(Environment.GetEnvironmentVariable("CI_CRT_LOCATION")))
                {
                    crt_location = Environment.GetEnvironmentVariable("CI_CRT_LOCATION");
                }
            }
            catch (Exception ex)
            {
                Console.WriteLine("Reading env variables (CI_CRT_LOCATION) is too much to ask for " + ex.Message);
            }

            try
            {
                if (!String.IsNullOrEmpty(Environment.GetEnvironmentVariable("CI_KEY_LOCATION")))
                {
                    key_location = Environment.GetEnvironmentVariable("CI_KEY_LOCATION");
                }
            }
            catch (Exception ex)
            {
                Console.WriteLine("Reading env variables (CI_KEY_LOCATION) is too much to ask for " + ex.Message);
            }


            File.WriteAllText(crt_location, builder.ToString());
            File.WriteAllText(key_location, privateKeyString);

            // Saving certificate in the store
            // SaveCertificate(certificate);

            // For local testing : reading a random cert
            //string newcer = "E://oms.crt";
            //X509Certificate2 cert1 = new X509Certificate2(newcer);

            return(certificate);
        }
예제 #22
0
        public X509Certificate2 GenerateSelfSignedCertificate(string name)
        {
            var randomGenerator = new CryptoApiRandomGenerator();
            var random          = new SecureRandom(randomGenerator);

            var certificateGenerator = new X509V3CertificateGenerator();

            var serialNumber = BigIntegers.CreateRandomInRange(BigInteger.One, BigInteger.ValueOf(long.MaxValue), random);

            certificateGenerator.SetSerialNumber(serialNumber);

            var subjectDN = new X509Name(name);
            var issuerDN  = subjectDN;

            certificateGenerator.SetIssuerDN(issuerDN);
            certificateGenerator.SetSubjectDN(subjectDN);

            var notBefore = DateTime.UtcNow.Date;
            var notAfter  = notBefore.AddYears(ExpireTimeInYears);

            certificateGenerator.SetNotBefore(notBefore);
            certificateGenerator.SetNotAfter(notAfter);

            var keyGenerationParameters = new KeyGenerationParameters(random, KeyStrength);
            var keyPairGenerator        = new RsaKeyPairGenerator();

            keyPairGenerator.Init(keyGenerationParameters);

            var subjectKeyPair = keyPairGenerator.GenerateKeyPair();

            certificateGenerator.SetPublicKey(subjectKeyPair.Public);

            var issuerKeyPair = subjectKeyPair;

            var signatureFactory = new Asn1SignatureFactory("SHA512WITHRSA", issuerKeyPair.Private, random);
            var certificate      = certificateGenerator.Generate(signatureFactory);

            var info = PrivateKeyInfoFactory.CreatePrivateKeyInfo(subjectKeyPair.Private);

            var x509 = new X509Certificate2(certificate.GetEncoded());

            var privateKey = info.ParsePrivateKey();
            var sequence   = (Asn1Sequence)Asn1Object.FromByteArray(privateKey.GetDerEncoded());

            if (sequence.Count != 9)
            {
                throw new PemException("Malformed sequence in RSA private key.");
            }

            var rsa           = RsaPrivateKeyStructure.GetInstance(sequence);
            var rsaParameters = new RsaPrivateCrtKeyParameters(
                rsa.Modulus,
                rsa.PublicExponent,
                rsa.PrivateExponent,
                rsa.Prime1,
                rsa.Prime2,
                rsa.Exponent1,
                rsa.Exponent2,
                rsa.Coefficient);

            var privateKeyRSA = DotNetUtilities.ToRSA(rsaParameters);

            var csp = new CspParameters
            {
                KeyContainerName = "Shapeshifter"
            };

            var rsaPrivate = new RSACryptoServiceProvider(csp);

            rsaPrivate.ImportParameters(privateKeyRSA.ExportParameters(true));
            x509.PrivateKey = rsaPrivate;

            return(x509);
        }
        static void Main(string[] args)
        {
            string subjectName = "testsubject";

            var randomGenerator = new CryptoApiRandomGenerator();

            var random = new SecureRandom(randomGenerator);
            var certificateGenerator = new X509V3CertificateGenerator();

            var serialNumber =
                BigIntegers.CreateRandomInRange(
                    BigInteger.One, BigInteger.ValueOf(Int64.MaxValue), random);

            certificateGenerator.SetSerialNumber(serialNumber);

            const string signatureAlgorithm = "SHA256WithRSA";

            certificateGenerator.SetSignatureAlgorithm(signatureAlgorithm);

            var subjectDN = new Org.BouncyCastle.Asn1.X509.X509Name(subjectName);
            var issuerDN  = subjectDN;

            certificateGenerator.SetIssuerDN(issuerDN);
            certificateGenerator.SetSubjectDN(subjectDN);

            var notBefore = DateTime.UtcNow.Date;
            var notAfter  = notBefore.AddYears(2);

            certificateGenerator.SetNotBefore(notBefore);
            certificateGenerator.SetNotAfter(notAfter);

            const int strength = 2048;
            var       keyGenerationParameters = new KeyGenerationParameters(random, strength);

            var keyPairGenerator = new RsaKeyPairGenerator();

            keyPairGenerator.Init(keyGenerationParameters);
            var subjectKeyPair = keyPairGenerator.GenerateKeyPair();

            certificateGenerator.SetPublicKey(subjectKeyPair.Public);

            var issuerKeyPair = subjectKeyPair;
            var certificate   = certificateGenerator.Generate(issuerKeyPair.Private, random);


            PdfReader reader = new PdfReader(this.inputPDF);

            ////var kpgen = new RsaKeyPairGenerator();

            ////kpgen.Init(new KeyGenerationParameters(new SecureRandom(new CryptoApiRandomGenerator()), 1024));

            ////var kp = kpgen.GenerateKeyPair();

            ////var gen = new X509V3CertificateGenerator();

            ////var certName = new Org.BouncyCastle.Asn1.X509.X509Name("CN=" + subjectName);
            ////var serialNo = BigInteger.ProbablePrime(120, new Random());

            ////gen.SetSerialNumber(serialNo);
            ////gen.SetSubjectDN(certName);
            ////gen.SetIssuerDN(certName);
            ////gen.SetNotAfter(DateTime.Now.AddYears(100));
            ////gen.SetNotBefore(DateTime.Now.Subtract(new TimeSpan(7, 0, 0, 0)));
            ////gen.SetSignatureAlgorithm("MD5WithRSA");
            ////gen.SetPublicKey(kp.Public);

            ////gen.AddExtension(
            ////    X509Extensions.AuthorityKeyIdentifier.Id,
            ////    false,
            ////    new AuthorityKeyIdentifier(
            ////        SubjectPublicKeyInfoFactory.CreateSubjectPublicKeyInfo(kp.Public),
            ////        new GeneralNames(new GeneralName(certName)),
            ////        serialNo));

            ////gen.AddExtension(
            ////    X509Extensions.ExtendedKeyUsage.Id,
            ////    false,
            ////    new ExtendedKeyUsage(new ArrayList() { new DerObjectIdentifier("1.3.6.1.5.5.7.3.1") }));

            ////var newCert = gen.Generate(kp.Private);

            ////DotNetUtilities.ToX509Certificate(newCert).Export(System.Security.Cryptography.X509Certificates.X509ContentType.Pkcs12, "password");
        }
예제 #24
0
        public void TestCreationDSA()
        {
            BigInteger DSAParaG    = new BigInteger(Base64.Decode("AL0fxOTq10OHFbCf8YldyGembqEu08EDVzxyLL29Zn/t4It661YNol1rnhPIs+cirw+yf9zeCe+KL1IbZ/qIMZM="));
            BigInteger DSAParaP    = new BigInteger(Base64.Decode("AM2b/UeQA+ovv3dL05wlDHEKJ+qhnJBsRT5OB9WuyRC830G79y0R8wuq8jyIYWCYcTn1TeqVPWqiTv6oAoiEeOs="));
            BigInteger DSAParaQ    = new BigInteger(Base64.Decode("AIlJT7mcKL6SUBMmvm24zX1EvjNx"));
            BigInteger DSAPublicY  = new BigInteger(Base64.Decode("TtWy2GuT9yGBWOHi1/EpCDa/bWJCk2+yAdr56rAcqP0eHGkMnA9s9GJD2nGU8sFjNHm55swpn6JQb8q0agrCfw=="));
            BigInteger DsaPrivateX = new BigInteger(Base64.Decode("MMpBAxNlv7eYfxLTZ2BItJeD31A="));

            DsaParameters           para    = new DsaParameters(DSAParaP, DSAParaQ, DSAParaG);
            DsaPrivateKeyParameters dsaPriv = new DsaPrivateKeyParameters(DsaPrivateX, para);
            DsaPublicKeyParameters  dsaPub  = new DsaPublicKeyParameters(DSAPublicY, para);

            IDictionary attrs = new Hashtable();

            attrs[X509Name.C]  = "AU";
            attrs[X509Name.O]  = "The Legion of the Bouncy Castle";
            attrs[X509Name.L]  = "Melbourne";
            attrs[X509Name.ST] = "Victoria";
            attrs[X509Name.E]  = "*****@*****.**";

            IList ord = new ArrayList();

            ord.Add(X509Name.C);
            ord.Add(X509Name.O);
            ord.Add(X509Name.L);
            ord.Add(X509Name.ST);
            ord.Add(X509Name.E);

            IList values = new ArrayList();

            values.Add("AU");
            values.Add("The Legion of the Bouncy Castle");
            values.Add("Melbourne");
            values.Add("Victoria");
            values.Add("*****@*****.**");

            X509V3CertificateGenerator certGen = new X509V3CertificateGenerator();

            certGen.SetSerialNumber(BigInteger.One);

            certGen.SetIssuerDN(new X509Name(ord, attrs));
            certGen.SetNotBefore(DateTime.UtcNow.AddDays(-1));
            certGen.SetNotAfter(DateTime.UtcNow.AddDays(1));
            certGen.SetSubjectDN(new X509Name(ord, attrs));
            certGen.SetPublicKey(dsaPub);
            certGen.SetSignatureAlgorithm("SHA1WITHDSA");

            X509Certificate cert = certGen.Generate(dsaPriv);

//			Assert.IsTrue((cert.IsValidNow && cert.Verify(dsaPub)), "Certificate failed to be valid (DSA Test)");
            cert.CheckValidity();
            cert.Verify(dsaPub);

            //ISet dummySet = cert.GetNonCriticalExtensionOids();

            //if (dummySet != null)
            //{
            //    foreach (string key in dummySet)
            //    {
            //        Console.WriteLine("\t{0}:\t{1}", key);
            //    }
            //}

            //Console.WriteLine();

            //dummySet = cert.GetNonCriticalExtensionOids();
            //if (dummySet != null)
            //{
            //    foreach (string key in dummySet)
            //    {
            //        Console.WriteLine("\t{0}:\t{1}", key);
            //    }
            //}

            //Console.WriteLine();
        }
        public void TestCreationECDSA()
        {
            IBigInteger ECParraGX = new BigInteger(Base64.Decode("D/qWPNyogWzMM7hkK+35BcPTWFc9Pyf7vTs8uaqv"));
            IBigInteger ECParraGY = new BigInteger(Base64.Decode("AhQXGxb1olGRv6s1LPRfuatMF+cx3ZTGgzSE/Q5R"));
            IBigInteger ECParraH  = new BigInteger(Base64.Decode("AQ=="));
            IBigInteger ECParraN  = new BigInteger(Base64.Decode("f///////////////f///nl6an12QcfvRUiaIkJ0L"));
            IBigInteger ECPubQX   = new BigInteger(Base64.Decode("HWWi17Yb+Bm3PYr/DMjLOYNFhyOwX1QY7ZvqqM+l"));
            IBigInteger ECPubQY   = new BigInteger(Base64.Decode("JrlJfxu3WGhqwtL/55BOs/wsUeiDFsvXcGhB8DGx"));
            IBigInteger ECPrivD   = new BigInteger(Base64.Decode("GYQmd/NF1B+He1iMkWt3by2Az6Eu07t0ynJ4YCAo"));
            FPCurve     curve     = new FPCurve(
                new BigInteger("883423532389192164791648750360308885314476597252960362792450860609699839"), // q
                new BigInteger("7fffffffffffffffffffffff7fffffffffff8000000000007ffffffffffc", 16),         // a
                new BigInteger("6b016c3bdcf18941d0d654921475ca71a9db2fb27d1d37796185c2942c0a", 16));        // b
            ECDomainParameters ecDomain =
                new ECDomainParameters(curve, new FPPoint(curve, curve.FromBigInteger(ECParraGX), curve.FromBigInteger(ECParraGY)), ECParraN);
            ECPublicKeyParameters ecPub = new ECPublicKeyParameters(
                "ECDSA",
                new FPPoint(curve,
                            curve.FromBigInteger(ECPubQX),
                            curve.FromBigInteger(ECPubQY)),
                ecDomain);
            ECPrivateKeyParameters ecPriv = new ECPrivateKeyParameters("ECDSA", ECPrivD, ecDomain);


            IDictionary attrs = new Hashtable();

            attrs[X509Name.C]  = "AU";
            attrs[X509Name.O]  = "The Legion of the Bouncy Castle";
            attrs[X509Name.L]  = "Melbourne";
            attrs[X509Name.ST] = "Victoria";
            attrs[X509Name.E]  = "*****@*****.**";

            IList ord = new ArrayList();

            ord.Add(X509Name.C);
            ord.Add(X509Name.O);
            ord.Add(X509Name.L);
            ord.Add(X509Name.ST);
            ord.Add(X509Name.E);

            IList values = new ArrayList();

            values.Add("AU");
            values.Add("The Legion of the Bouncy Castle");
            values.Add("Melbourne");
            values.Add("Victoria");
            values.Add("*****@*****.**");

            X509V3CertificateGenerator certGen = new X509V3CertificateGenerator();

            certGen.SetSerialNumber(BigInteger.One);

            certGen.SetIssuerDN(new X509Name(ord, attrs));
            certGen.SetNotBefore(DateTime.Today.Subtract(new TimeSpan(1, 0, 0, 0)));
            certGen.SetNotAfter(DateTime.Today.AddDays(1));
            certGen.SetSubjectDN(new X509Name(ord, attrs));
            certGen.SetPublicKey(ecPub);
            certGen.SetSignatureAlgorithm("SHA1WITHECDSA");


            X509Certificate cert = certGen.Generate(ecPriv);

//            Assert.IsTrue((cert.IsValidNow && cert.Verify(ecPub)), "Certificate failed to be valid (ECDSA)");
            cert.CheckValidity();
            cert.Verify(ecPub);

            ISet dummySet = cert.GetNonCriticalExtensionOids();

            if (dummySet != null)
            {
                foreach (string key in dummySet)
                {
                    Console.WriteLine("\t{0}:\t{1}", key);
                }
            }

            Console.WriteLine();

            dummySet = cert.GetNonCriticalExtensionOids();

            if (dummySet != null)
            {
                foreach (string key in dummySet)
                {
                    Console.WriteLine("\t{0}:\t{1}", key);
                }
            }

            Console.WriteLine();
        }
예제 #26
0
        public void TestCreationRSA()
        {
            BigInteger                 rsaPubMod   = new BigInteger(Base64.Decode("AIASoe2PQb1IP7bTyC9usjHP7FvnUMVpKW49iuFtrw/dMpYlsMMoIU2jupfifDpdFxIktSB4P+6Ymg5WjvHKTIrvQ7SR4zV4jaPTu56Ys0pZ9EDA6gb3HLjtU+8Bb1mfWM+yjKxcPDuFjwEtjGlPHg1Vq+CA9HNcMSKNn2+tW6qt"));
            BigInteger                 rsaPubExp   = new BigInteger(Base64.Decode("EQ=="));
            BigInteger                 rsaPrivMod  = new BigInteger(Base64.Decode("AIASoe2PQb1IP7bTyC9usjHP7FvnUMVpKW49iuFtrw/dMpYlsMMoIU2jupfifDpdFxIktSB4P+6Ymg5WjvHKTIrvQ7SR4zV4jaPTu56Ys0pZ9EDA6gb3HLjtU+8Bb1mfWM+yjKxcPDuFjwEtjGlPHg1Vq+CA9HNcMSKNn2+tW6qt"));
            BigInteger                 rsaPrivDP   = new BigInteger(Base64.Decode("JXzfzG5v+HtLJIZqYMUefJfFLu8DPuJGaLD6lI3cZ0babWZ/oPGoJa5iHpX4Ul/7l3s1PFsuy1GhzCdOdlfRcQ=="));
            BigInteger                 rsaPrivDQ   = new BigInteger(Base64.Decode("YNdJhw3cn0gBoVmMIFRZzflPDNthBiWy/dUMSRfJCxoZjSnr1gysZHK01HteV1YYNGcwPdr3j4FbOfri5c6DUQ=="));
            BigInteger                 rsaPrivExp  = new BigInteger(Base64.Decode("DxFAOhDajr00rBjqX+7nyZ/9sHWRCCp9WEN5wCsFiWVRPtdB+NeLcou7mWXwf1Y+8xNgmmh//fPV45G2dsyBeZbXeJwB7bzx9NMEAfedchyOwjR8PYdjK3NpTLKtZlEJ6Jkh4QihrXpZMO4fKZWUm9bid3+lmiq43FwW+Hof8/E="));
            BigInteger                 rsaPrivP    = new BigInteger(Base64.Decode("AJ9StyTVW+AL/1s7RBtFwZGFBgd3zctBqzzwKPda6LbtIFDznmwDCqAlIQH9X14X7UPLokCDhuAa76OnDXb1OiE="));
            BigInteger                 rsaPrivQ    = new BigInteger(Base64.Decode("AM3JfD79dNJ5A3beScSzPtWxx/tSLi0QHFtkuhtSizeXdkv5FSba7lVzwEOGKHmW829bRoNxThDy4ds1IihW1w0="));
            BigInteger                 rsaPrivQinv = new BigInteger(Base64.Decode("Lt0g7wrsNsQxuDdB8q/rH8fSFeBXMGLtCIqfOec1j7FEIuYA/ACiRDgXkHa0WgN7nLXSjHoy630wC5Toq8vvUg=="));
            RsaKeyParameters           rsaPublic   = new RsaKeyParameters(false, rsaPubMod, rsaPubExp);
            RsaPrivateCrtKeyParameters rsaPrivate  = new RsaPrivateCrtKeyParameters(rsaPrivMod, rsaPubExp, rsaPrivExp, rsaPrivP, rsaPrivQ, rsaPrivDP, rsaPrivDQ, rsaPrivQinv);

            IDictionary attrs = new Hashtable();

            attrs[X509Name.C]  = "AU";
            attrs[X509Name.O]  = "The Legion of the Bouncy Castle";
            attrs[X509Name.L]  = "Melbourne";
            attrs[X509Name.ST] = "Victoria";
            attrs[X509Name.E]  = "*****@*****.**";

            IList ord = new ArrayList();

            ord.Add(X509Name.C);
            ord.Add(X509Name.O);
            ord.Add(X509Name.L);
            ord.Add(X509Name.ST);
            ord.Add(X509Name.E);

            IList values = new ArrayList();

            values.Add("AU");
            values.Add("The Legion of the Bouncy Castle");
            values.Add("Melbourne");
            values.Add("Victoria");
            values.Add("*****@*****.**");

            X509V3CertificateGenerator certGen = new X509V3CertificateGenerator();

            certGen.SetSerialNumber(BigInteger.One);

            certGen.SetIssuerDN(new X509Name(ord, attrs));
            certGen.SetNotBefore(DateTime.UtcNow.AddDays(-1));
            certGen.SetNotAfter(DateTime.UtcNow.AddDays(1));
            certGen.SetSubjectDN(new X509Name(ord, attrs));
            certGen.SetPublicKey(rsaPublic);
            certGen.SetSignatureAlgorithm("MD5WithRSAEncryption");

            X509Certificate cert = certGen.Generate(rsaPrivate);

//			Assert.IsTrue((cert.IsValidNow && cert.Verify(rsaPublic)),"Certificate failed to be valid (RSA)");
            cert.CheckValidity();
            cert.Verify(rsaPublic);

            //Console.WriteLine(ASN1Dump.DumpAsString(cert.ToAsn1Object()));

            //ISet dummySet = cert.GetNonCriticalExtensionOids();

            //if (dummySet != null)
            //{
            //    foreach (string key in dummySet)
            //    {
            //        Console.WriteLine("\t{0}:\t{1}", key);
            //    }
            //}

            //Console.WriteLine();

            //dummySet = cert.GetNonCriticalExtensionOids();
            //if (dummySet != null)
            //{
            //    foreach (string key in dummySet)
            //    {
            //        Console.WriteLine("\t{0}:\t{1}", key);
            //    }
            //}

            //Console.WriteLine();
        }
예제 #27
0
        // Only the ctor should be calling with isAuthority = true
        // if isAuthority, value for isMachineCert doesn't matter
        private X509CertificateContainer CreateCertificate(bool isAuthority, bool isMachineCert, X509Certificate signingCertificate, CertificateCreationSettings certificateCreationSettings)
        {
            if (certificateCreationSettings == null)
            {
                if (isAuthority)
                {
                    certificateCreationSettings = new CertificateCreationSettings();
                }
                else
                {
                    throw new Exception("Parameter certificateCreationSettings cannot be null when isAuthority is false");
                }
            }

            // Set to default cert creation settings if not set
            if (certificateCreationSettings.ValidityNotBefore == default(DateTime))
            {
                certificateCreationSettings.ValidityNotBefore = _defaultValidityNotBefore;
            }
            if (certificateCreationSettings.ValidityNotAfter == default(DateTime))
            {
                certificateCreationSettings.ValidityNotAfter = _defaultValidityNotAfter;
            }

            if (!isAuthority ^ (signingCertificate != null))
            {
                throw new ArgumentException("Either isAuthority == true or signingCertificate is not null");
            }
            string subject = certificateCreationSettings.Subject;

            // If certificateCreationSettings.SubjectAlternativeNames == null, then we should add exactly one SubjectAlternativeName == Subject
            // so that the default certificate generated is compatible with mainline scenarios
            // However, if certificateCreationSettings.SubjectAlternativeNames == string[0], then allow this as this is a legit scenario we want to test out
            if (certificateCreationSettings.SubjectAlternativeNames == null)
            {
                certificateCreationSettings.SubjectAlternativeNames = new string[1] {
                    subject
                };
            }

            string[] subjectAlternativeNames = certificateCreationSettings.SubjectAlternativeNames;

            if (!isAuthority && string.IsNullOrWhiteSpace(subject))
            {
                throw new ArgumentException("Certificate Subject must not be an empty string or only whitespace", "creationSettings.Subject");
            }

            EnsureInitialized();

            s_certGenerator.Reset();
            s_certGenerator.SetSignatureAlgorithm(_signatureAlthorithm);

            X509Name authorityX509Name = CreateX509Name(_authorityCanonicalName);
            var      serialNum         = new BigInteger(64 /*sizeInBits*/, _random).Abs();

            var keyPair = isAuthority ? _authorityKeyPair : _keyPairGenerator.GenerateKeyPair();

            if (isAuthority)
            {
                s_certGenerator.SetIssuerDN(authorityX509Name);
                s_certGenerator.SetSubjectDN(authorityX509Name);

                var authorityKeyIdentifier = new AuthorityKeyIdentifier(
                    SubjectPublicKeyInfoFactory.CreateSubjectPublicKeyInfo(_authorityKeyPair.Public),
                    new GeneralNames(new GeneralName(authorityX509Name)),
                    serialNum);

                s_certGenerator.AddExtension(X509Extensions.AuthorityKeyIdentifier, false, authorityKeyIdentifier);
                s_certGenerator.AddExtension(X509Extensions.KeyUsage, false, new KeyUsage(X509KeyUsage.DigitalSignature | X509KeyUsage.KeyAgreement | X509KeyUsage.KeyCertSign | X509KeyUsage.KeyEncipherment | X509KeyUsage.CrlSign));
            }
            else
            {
                X509Name subjectName = CreateX509Name(subject);
                s_certGenerator.SetIssuerDN(PrincipalUtilities.GetSubjectX509Principal(signingCertificate));
                s_certGenerator.SetSubjectDN(subjectName);

                s_certGenerator.AddExtension(X509Extensions.AuthorityKeyIdentifier, false, new AuthorityKeyIdentifierStructure(_authorityKeyPair.Public));
                s_certGenerator.AddExtension(X509Extensions.KeyUsage, false, new KeyUsage(X509KeyUsage.DigitalSignature | X509KeyUsage.KeyAgreement | X509KeyUsage.KeyEncipherment));
            }

            s_certGenerator.AddExtension(X509Extensions.SubjectKeyIdentifier, false, new SubjectKeyIdentifierStructure(keyPair.Public));

            s_certGenerator.SetSerialNumber(serialNum);
            s_certGenerator.SetNotBefore(certificateCreationSettings.ValidityNotBefore);
            s_certGenerator.SetNotAfter(certificateCreationSettings.ValidityNotAfter);
            s_certGenerator.SetPublicKey(keyPair.Public);

            s_certGenerator.AddExtension(X509Extensions.BasicConstraints, true, new BasicConstraints(isAuthority));
            s_certGenerator.AddExtension(X509Extensions.ExtendedKeyUsage, false, new ExtendedKeyUsage(KeyPurposeID.IdKPServerAuth, KeyPurposeID.IdKPClientAuth));

            if (!isAuthority)
            {
                if (isMachineCert)
                {
                    List <Asn1Encodable> subjectAlternativeNamesAsAsn1EncodableList = new List <Asn1Encodable>();

                    // All endpoints should also be in the Subject Alt Names
                    for (int i = 0; i < subjectAlternativeNames.Length; i++)
                    {
                        if (!string.IsNullOrWhiteSpace(subjectAlternativeNames[i]))
                        {
                            // Machine certs can have additional DNS names
                            subjectAlternativeNamesAsAsn1EncodableList.Add(new GeneralName(GeneralName.DnsName, subjectAlternativeNames[i]));
                        }
                    }

                    s_certGenerator.AddExtension(X509Extensions.SubjectAlternativeName, true, new DerSequence(subjectAlternativeNamesAsAsn1EncodableList.ToArray()));
                }
                else
                {
                    if (subjectAlternativeNames.Length > 1)
                    {
                        var subjectAlternativeNamesAsAsn1EncodableList = new Asn1EncodableVector();

                        // Only add a SAN for the user if there are any
                        for (int i = 1; i < subjectAlternativeNames.Length; i++)
                        {
                            if (!string.IsNullOrWhiteSpace(subjectAlternativeNames[i]))
                            {
                                Asn1EncodableVector otherNames = new Asn1EncodableVector();
                                otherNames.Add(new DerObjectIdentifier(_upnObjectId));
                                otherNames.Add(new DerTaggedObject(true, 0, new DerUtf8String(subjectAlternativeNames[i])));

                                Asn1Object genName = new DerTaggedObject(false, 0, new DerSequence(otherNames));

                                subjectAlternativeNamesAsAsn1EncodableList.Add(genName);
                            }
                        }
                        s_certGenerator.AddExtension(X509Extensions.SubjectAlternativeName, true, new DerSequence(subjectAlternativeNamesAsAsn1EncodableList));
                    }
                }
            }

            // Our CRL Distribution Point has the serial number in the query string to fool Windows into doing a fresh query
            // rather than using a cached copy of the CRL in the case where the CRL has been previously accessed before
            var crlDistributionPoints = new DistributionPoint[2] {
                new DistributionPoint(new DistributionPointName(
                                          new GeneralNames(new GeneralName(
                                                               GeneralName.UniformResourceIdentifier, string.Format("{0}?serialNum={1}", _crlUri, serialNum.ToString(radix: 16))))),
                                      null,
                                      null),
                new DistributionPoint(new DistributionPointName(
                                          new GeneralNames(new GeneralName(
                                                               GeneralName.UniformResourceIdentifier, string.Format("{0}?serialNum={1}", _crlUri, serialNum.ToString(radix: 16))))),
                                      null,
                                      new GeneralNames(new GeneralName(authorityX509Name)))
            };
            var revocationListExtension = new CrlDistPoint(crlDistributionPoints);

            s_certGenerator.AddExtension(X509Extensions.CrlDistributionPoints, false, revocationListExtension);

            X509Certificate cert = s_certGenerator.Generate(_authorityKeyPair.Private, _random);

            switch (certificateCreationSettings.ValidityType)
            {
            case CertificateValidityType.Revoked:
                RevokeCertificateBySerialNumber(serialNum.ToString(radix: 16));
                break;

            case CertificateValidityType.Expired:
                break;

            default:
                EnsureCertificateIsValid(cert);
                break;
            }

            // For now, given that we don't know what format to return it in, preserve the formats so we have
            // the flexibility to do what we need to

            X509CertificateContainer container = new X509CertificateContainer();

            X509CertificateEntry[] chain = new X509CertificateEntry[1];
            chain[0] = new X509CertificateEntry(cert);

            Pkcs12Store store = new Pkcs12StoreBuilder().Build();

            store.SetKeyEntry(
                certificateCreationSettings.FriendlyName != null ? certificateCreationSettings.FriendlyName : string.Empty,
                new AsymmetricKeyEntry(keyPair.Private),
                chain);

            using (MemoryStream stream = new MemoryStream())
            {
                store.Save(stream, _password.ToCharArray(), _random);
                container.Pfx = stream.ToArray();
            }

            X509Certificate2 outputCert;

            if (isAuthority)
            {
                // don't hand out the private key for the cert when it's the authority
                outputCert = new X509Certificate2(cert.GetEncoded());
            }
            else
            {
                // Otherwise, allow encode with the private key. note that X509Certificate2.RawData will not provide the private key
                // you will have to re-export this cert if needed
                outputCert = new X509Certificate2(container.Pfx, _password, X509KeyStorageFlags.MachineKeySet | X509KeyStorageFlags.Exportable | X509KeyStorageFlags.PersistKeySet);
            }

            container.Subject             = subject;
            container.InternalCertificate = cert;
            container.Certificate         = outputCert;
            container.Thumbprint          = outputCert.Thumbprint;

            Trace.WriteLine("[CertificateGenerator] generated a certificate:");
            Trace.WriteLine(string.Format("    {0} = {1}", "isAuthority", isAuthority));
            if (!isAuthority)
            {
                Trace.WriteLine(string.Format("    {0} = {1}", "Signed by", signingCertificate.SubjectDN));
                Trace.WriteLine(string.Format("    {0} = {1}", "Subject (CN) ", subject));
                Trace.WriteLine(string.Format("    {0} = {1}", "Subject Alt names ", string.Join(", ", subjectAlternativeNames)));
                Trace.WriteLine(string.Format("    {0} = {1}", "Friendly Name ", certificateCreationSettings.FriendlyName));
            }
            Trace.WriteLine(string.Format("    {0} = {1}", "HasPrivateKey:", outputCert.HasPrivateKey));
            Trace.WriteLine(string.Format("    {0} = {1}", "Thumbprint", outputCert.Thumbprint));
            Trace.WriteLine(string.Format("    {0} = {1}", "CertificateValidityType", certificateCreationSettings.ValidityType));

            return(container);
        }
        public async Task ValidateMergeCertificate()
        {
            string serverCertificateName = Recording.GenerateId();

            // Generate the request.
            CertificatePolicy policy = new CertificatePolicy(WellKnownIssuerNames.Unknown, "CN=Azure SDK")
            {
                CertificateTransparency = false,
                ContentType             = CertificateContentType.Pkcs12,
            };

            CertificateOperation operation = await Client.StartCreateCertificateAsync(serverCertificateName, policy);

            RegisterForCleanup(serverCertificateName);
            await using IAsyncDisposable disposableOperation = EnsureDeleted(operation);

            // Read the CA.
            byte[]           caCertificateBytes = Convert.FromBase64String(CaPublicKeyBase64);
            X509Certificate2 caCertificate      = new X509Certificate2(caCertificateBytes);

            // Read CA private key since getting it from caCertificate above throws.
            AsymmetricCipherKeyPair caPrivateKey;

            using (StringReader caPrivateKeyReader = new StringReader(CaPrivateKeyPem))
            {
                Org.BouncyCastle.OpenSsl.PemReader reader = new Org.BouncyCastle.OpenSsl.PemReader(caPrivateKeyReader);
                caPrivateKey = (AsymmetricCipherKeyPair)reader.ReadObject();
            }

            // Read the CSR.
            Pkcs10CertificationRequest csr     = new Pkcs10CertificationRequest(operation.Properties.Csr);
            CertificationRequestInfo   csrInfo = csr.GetCertificationRequestInfo();

            // Parse the issuer subject name.
            Hashtable oidLookup = new Hashtable(X509Name.DefaultLookup)
            {
                { "s", new DerObjectIdentifier("2.5.4.8") },
            };

            X509Name issuerName = new X509Name(true, oidLookup, caCertificate.Subject);

            // Sign the request.
            X509V3CertificateGenerator generator = new X509V3CertificateGenerator();

            generator.SetIssuerDN(issuerName);
            generator.SetSerialNumber(BigInteger.One);
            generator.SetNotBefore(DateTime.Now);
            generator.SetNotAfter(DateTime.Now.AddDays(1));
            generator.SetSubjectDN(csrInfo.Subject);
            generator.SetPublicKey(csr.GetPublicKey());

            Asn1SignatureFactory signatureFactory      = new Asn1SignatureFactory("SHA256WITHRSA", caPrivateKey.Private);
            X509Certificate      serverSignedPublicKey = generator.Generate(signatureFactory);

            // Merge the certificate chain.
            MergeCertificateOptions       options = new MergeCertificateOptions(serverCertificateName, new[] { serverSignedPublicKey.GetEncoded(), caCertificateBytes });
            KeyVaultCertificateWithPolicy mergedServerCertificate = await Client.MergeCertificateAsync(options);

            X509Certificate2 serverCertificate = new X509Certificate2(mergedServerCertificate.Cer);

            Assert.AreEqual(csrInfo.Subject.ToString(), serverCertificate.Subject);
            Assert.AreEqual(serverCertificateName, mergedServerCertificate.Name);

            KeyVaultCertificateWithPolicy completedServerCertificate = await operation.WaitForCompletionAsync(DefaultCertificateOperationPollingInterval, default);

            Assert.AreEqual(mergedServerCertificate.Name, completedServerCertificate.Name);
            CollectionAssert.AreEqual(mergedServerCertificate.Cer, completedServerCertificate.Cer);
        }
        private X509Certificate MakeCertificate(AsymmetricCipherKeyPair subjectKeyPair, X509Name certificateSubject, AsymmetricCipherKeyPair rootKeyPair, X509Name rootSubject, bool isRootCertificate, bool addAuthorityKeyIdentifier)
        {
            X509Certificate x509Certificate;

            try
            {
                AsymmetricKeyParameter     @public  = subjectKeyPair.Public;
                AsymmetricKeyParameter     @private = rootKeyPair.Private;
                AsymmetricKeyParameter     asymmetricKeyParameter     = rootKeyPair.Public;
                X509V3CertificateGenerator x509V3CertificateGenerator = new X509V3CertificateGenerator();
                x509V3CertificateGenerator.Reset();
                if (this.SerialNumber != -9223372036854775808L)
                {
                    x509V3CertificateGenerator.SetSerialNumber(new BigInteger(this.SerialNumber.ToString()));
                }
                else
                {
                    DateTime now = DateTime.Now;
                    x509V3CertificateGenerator.SetSerialNumber(new BigInteger(128, new Random(now.Millisecond + Environment.TickCount)));
                }
                x509V3CertificateGenerator.SetIssuerDN(rootSubject);
                x509V3CertificateGenerator.SetNotBefore(this.ValidFrom.ToUniversalTime());
                x509V3CertificateGenerator.SetNotAfter(this.ValidTo.ToUniversalTime());
                x509V3CertificateGenerator.SetSubjectDN(certificateSubject);
                x509V3CertificateGenerator.SetPublicKey(@public);
                x509V3CertificateGenerator.SetSignatureAlgorithm(string.Concat(this.SignatureAlgorithm.ToString(), "Encryption"));
                int extensionType = 0;
                Asn1EncodableVector asn1EncodableVectors = new Asn1EncodableVector(new Asn1Encodable[0]);
                foreach (ExtensionInfo extension in this.Extensions.extensionInfo)
                {
                    if (!extension.ExtendedKeyUsage)
                    {
                        extensionType |= (int)extension.ExtensionType;
                    }
                    if (!extension.ExtendedKeyUsage)
                    {
                        continue;
                    }
                    asn1EncodableVectors.Add(new Asn1Encodable[] { (Asn1Encodable)extension.ExtensionType });
                }
                bool keyUsageIsCritical = this.Extensions.KeyUsageIsCritical;
                if (isRootCertificate)
                {
                    x509V3CertificateGenerator.AddExtension(X509Extensions.BasicConstraints, true, new BasicConstraints(true));
                    extensionType     |= 6;
                    keyUsageIsCritical = true;
                }
                if (extensionType != 0)
                {
                    x509V3CertificateGenerator.AddExtension(X509Extensions.KeyUsage, keyUsageIsCritical, new KeyUsage(extensionType));
                }
                if (asn1EncodableVectors.Count > 0)
                {
                    x509V3CertificateGenerator.AddExtension(X509Extensions.ExtendedKeyUsage, this.Extensions.EnhancedKeyUsageIsCritical, ExtendedKeyUsage.GetInstance(new DerSequence(asn1EncodableVectors)));
                }
                x509V3CertificateGenerator.AddExtension(X509Extensions.SubjectKeyIdentifier, false, new SubjectKeyIdentifier(SubjectPublicKeyInfoFactory.CreateSubjectPublicKeyInfo(@public)));
                if (addAuthorityKeyIdentifier)
                {
                    x509V3CertificateGenerator.AddExtension(X509Extensions.AuthorityKeyIdentifier, false, new AuthorityKeyIdentifier(SubjectPublicKeyInfoFactory.CreateSubjectPublicKeyInfo(asymmetricKeyParameter)));
                }
                X509Certificate x509Certificate1 = x509V3CertificateGenerator.Generate(@private, this.GetSecureRandom());
                x509Certificate1.Verify(asymmetricKeyParameter);
                x509Certificate = x509Certificate1;
            }
            catch
            {
                throw;
            }
            return(x509Certificate);
        }
        public void TestCreationDSA()
        {
            IBigInteger DSAParaG = new BigInteger(Base64.Decode("AL0fxOTq10OHFbCf8YldyGembqEu08EDVzxyLL29Zn/t4It661YNol1rnhPIs+cirw+yf9zeCe+KL1IbZ/qIMZM="));
            IBigInteger DSAParaP = new BigInteger(Base64.Decode("AM2b/UeQA+ovv3dL05wlDHEKJ+qhnJBsRT5OB9WuyRC830G79y0R8wuq8jyIYWCYcTn1TeqVPWqiTv6oAoiEeOs="));
            IBigInteger DSAParaQ = new BigInteger(Base64.Decode("AIlJT7mcKL6SUBMmvm24zX1EvjNx"));
            IBigInteger DSAPublicY = new BigInteger(Base64.Decode("TtWy2GuT9yGBWOHi1/EpCDa/bWJCk2+yAdr56rAcqP0eHGkMnA9s9GJD2nGU8sFjNHm55swpn6JQb8q0agrCfw=="));
            IBigInteger DsaPrivateX = new BigInteger(Base64.Decode("MMpBAxNlv7eYfxLTZ2BItJeD31A="));

            DsaParameters para = new DsaParameters(DSAParaP, DSAParaQ, DSAParaG);
            DsaPrivateKeyParameters dsaPriv = new DsaPrivateKeyParameters(DsaPrivateX, para);
            DsaPublicKeyParameters dsaPub = new DsaPublicKeyParameters(DSAPublicY, para);

            IDictionary attrs = new Hashtable();
            attrs[X509Name.C] = "AU";
            attrs[X509Name.O] = "The Legion of the Bouncy Castle";
            attrs[X509Name.L] = "Melbourne";
            attrs[X509Name.ST] = "Victoria";
            attrs[X509Name.E] = "*****@*****.**";

            IList ord = new ArrayList();
            ord.Add(X509Name.C);
            ord.Add(X509Name.O);
            ord.Add(X509Name.L);
            ord.Add(X509Name.ST);
            ord.Add(X509Name.E);

            IList values = new ArrayList();
            values.Add("AU");
            values.Add("The Legion of the Bouncy Castle");
            values.Add("Melbourne");
            values.Add("Victoria");
            values.Add("*****@*****.**");

            X509V3CertificateGenerator certGen = new X509V3CertificateGenerator();

            certGen.SetSerialNumber(BigInteger.One);

            certGen.SetIssuerDN(new X509Name(ord, attrs));
            certGen.SetNotBefore(DateTime.UtcNow.AddDays(-1));
            certGen.SetNotAfter(DateTime.UtcNow.AddDays(1));
            certGen.SetSubjectDN(new X509Name(ord, attrs));
            certGen.SetPublicKey(dsaPub);
            certGen.SetSignatureAlgorithm("SHA1WITHDSA");

            X509Certificate cert = certGen.Generate(dsaPriv);

            //			Assert.IsTrue((cert.IsValidNow && cert.Verify(dsaPub)), "Certificate failed to be valid (DSA Test)");
            cert.CheckValidity();
            cert.Verify(dsaPub);

            ISet dummySet = cert.GetNonCriticalExtensionOids();

            if (dummySet != null)
            {
                foreach (string key in dummySet)
                {
                    Console.WriteLine("\t{0}:\t{1}", key);
                }
            }

            Console.WriteLine();

            dummySet = cert.GetNonCriticalExtensionOids();
            if (dummySet != null)
            {
                foreach (string key in dummySet)
                {
                    Console.WriteLine("\t{0}:\t{1}", key);
                }
            }

            Console.WriteLine();
        }
        public static X509Certificate2 GenerateSelfSignedCertificate(X509Name issuer, X509Name subject, AsymmetricKeyParameter issuerPrivKey)
        {
            const int keyStrength = 2048;

            //generate random numbers
            CryptoApiRandomGenerator randomGenerator  = new CryptoApiRandomGenerator();
            SecureRandom             random           = new SecureRandom(randomGenerator);
            ISignatureFactory        signatureFactory = new Asn1SignatureFactory("SHA256WITHRSA", issuerPrivKey, random);

            //the certificate generator
            X509V3CertificateGenerator certificateGenerator = new X509V3CertificateGenerator();

            certificateGenerator.AddExtension(X509Extensions.ExtendedKeyUsage.Id, true, new ExtendedKeyUsage(KeyPurposeID.IdKPServerAuth));

            //serial number
            BigInteger serialNumber = BigIntegers.CreateRandomInRange(BigInteger.One, BigInteger.ValueOf(long.MaxValue), random);

            certificateGenerator.SetSerialNumber(serialNumber);

            // Issuer and Subject Name
            //X509Name subjectDN = new X509Name("CN=" + subjectName);
            //X509Name issuerDN = new X509Name("CN=" + issuerName);
            certificateGenerator.SetIssuerDN(issuer);
            certificateGenerator.SetSubjectDN(subject);

            //valid For
            DateTime notBefore = DateTime.Now.AddDays(-1);
            DateTime notAfter  = notBefore.AddYears(2);

            certificateGenerator.SetNotBefore(notBefore);
            certificateGenerator.SetNotAfter(notAfter);

            //Subject Public Key
            var keyGenerationParameters = new KeyGenerationParameters(random, keyStrength);
            var keyPairGenerator        = new RsaKeyPairGenerator();

            keyPairGenerator.Init(keyGenerationParameters);
            var subjectKeyPair = keyPairGenerator.GenerateKeyPair();

            certificateGenerator.SetPublicKey(subjectKeyPair.Public);

            //selfSign certificate
            Org.BouncyCastle.X509.X509Certificate certificate = certificateGenerator.Generate(signatureFactory);
            //var dotNetPrivateKey = ToDotNetKey((RsaPrivateCrtKeyParameters)subjectKeyPair.Private);

            //merge into X509Certificate2

            var certificate2 = new X509Certificate2(DotNetUtilities.ToX509Certificate(certificate))
            {
                FriendlyName = "fulu sso", //设置友好名称
            };

            certificate2 = certificate2.CopyWithPrivateKey(DotNetUtilities.ToRSA((RsaPrivateCrtKeyParameters)subjectKeyPair.Private));

            certificate2.FriendlyName = "fulu sso";

            var bytes2 = certificate2.Export(X509ContentType.Pfx, "123456");

            using (var fs = new FileStream("mypfx2.pfx", FileMode.Create))
            {
                fs.Write(bytes2, 0, bytes2.Length);
            }


            //var x509 = new X509Certificate2(DotNetUtilities.ToX509Certificate(certificate))
            //{
            //    PrivateKey = dotNetPrivateKey,
            //    FriendlyName = "fulu sso"
            //};

            return(certificate2);
        }
        public void TestCreationRSA()
        {
            IBigInteger rsaPubMod = new BigInteger(Base64.Decode("AIASoe2PQb1IP7bTyC9usjHP7FvnUMVpKW49iuFtrw/dMpYlsMMoIU2jupfifDpdFxIktSB4P+6Ymg5WjvHKTIrvQ7SR4zV4jaPTu56Ys0pZ9EDA6gb3HLjtU+8Bb1mfWM+yjKxcPDuFjwEtjGlPHg1Vq+CA9HNcMSKNn2+tW6qt"));
            IBigInteger rsaPubExp = new BigInteger(Base64.Decode("EQ=="));
            IBigInteger rsaPrivMod = new BigInteger(Base64.Decode("AIASoe2PQb1IP7bTyC9usjHP7FvnUMVpKW49iuFtrw/dMpYlsMMoIU2jupfifDpdFxIktSB4P+6Ymg5WjvHKTIrvQ7SR4zV4jaPTu56Ys0pZ9EDA6gb3HLjtU+8Bb1mfWM+yjKxcPDuFjwEtjGlPHg1Vq+CA9HNcMSKNn2+tW6qt"));
            IBigInteger rsaPrivDP = new BigInteger(Base64.Decode("JXzfzG5v+HtLJIZqYMUefJfFLu8DPuJGaLD6lI3cZ0babWZ/oPGoJa5iHpX4Ul/7l3s1PFsuy1GhzCdOdlfRcQ=="));
            IBigInteger rsaPrivDQ = new BigInteger(Base64.Decode("YNdJhw3cn0gBoVmMIFRZzflPDNthBiWy/dUMSRfJCxoZjSnr1gysZHK01HteV1YYNGcwPdr3j4FbOfri5c6DUQ=="));
            IBigInteger rsaPrivExp = new BigInteger(Base64.Decode("DxFAOhDajr00rBjqX+7nyZ/9sHWRCCp9WEN5wCsFiWVRPtdB+NeLcou7mWXwf1Y+8xNgmmh//fPV45G2dsyBeZbXeJwB7bzx9NMEAfedchyOwjR8PYdjK3NpTLKtZlEJ6Jkh4QihrXpZMO4fKZWUm9bid3+lmiq43FwW+Hof8/E="));
            IBigInteger rsaPrivP = new BigInteger(Base64.Decode("AJ9StyTVW+AL/1s7RBtFwZGFBgd3zctBqzzwKPda6LbtIFDznmwDCqAlIQH9X14X7UPLokCDhuAa76OnDXb1OiE="));
            IBigInteger rsaPrivQ = new BigInteger(Base64.Decode("AM3JfD79dNJ5A3beScSzPtWxx/tSLi0QHFtkuhtSizeXdkv5FSba7lVzwEOGKHmW829bRoNxThDy4ds1IihW1w0="));
            IBigInteger rsaPrivQinv = new BigInteger(Base64.Decode("Lt0g7wrsNsQxuDdB8q/rH8fSFeBXMGLtCIqfOec1j7FEIuYA/ACiRDgXkHa0WgN7nLXSjHoy630wC5Toq8vvUg=="));
            RsaKeyParameters rsaPublic = new RsaKeyParameters(false, rsaPubMod, rsaPubExp);
            RsaPrivateCrtKeyParameters rsaPrivate = new RsaPrivateCrtKeyParameters(rsaPrivMod, rsaPubExp, rsaPrivExp, rsaPrivP, rsaPrivQ, rsaPrivDP, rsaPrivDQ, rsaPrivQinv);

            IDictionary attrs = new Hashtable();
            attrs[X509Name.C] = "AU";
            attrs[X509Name.O] = "The Legion of the Bouncy Castle";
            attrs[X509Name.L] = "Melbourne";
            attrs[X509Name.ST] = "Victoria";
            attrs[X509Name.E] = "*****@*****.**";

            IList ord = new ArrayList();
            ord.Add(X509Name.C);
            ord.Add(X509Name.O);
            ord.Add(X509Name.L);
            ord.Add(X509Name.ST);
            ord.Add(X509Name.E);

            IList values = new ArrayList();
            values.Add("AU");
            values.Add("The Legion of the Bouncy Castle");
            values.Add("Melbourne");
            values.Add("Victoria");
            values.Add("*****@*****.**");

            X509V3CertificateGenerator certGen = new X509V3CertificateGenerator();

            certGen.SetSerialNumber(BigInteger.One);

            certGen.SetIssuerDN(new X509Name(ord, attrs));
            certGen.SetNotBefore(DateTime.UtcNow.AddDays(-1));
            certGen.SetNotAfter(DateTime.UtcNow.AddDays(1));
            certGen.SetSubjectDN(new X509Name(ord, attrs));
            certGen.SetPublicKey(rsaPublic);
            certGen.SetSignatureAlgorithm("MD5WithRSAEncryption");

            X509Certificate cert = certGen.Generate(rsaPrivate);

            //			Assert.IsTrue((cert.IsValidNow && cert.Verify(rsaPublic)),"Certificate failed to be valid (RSA)");
            cert.CheckValidity();
            cert.Verify(rsaPublic);

            //Console.WriteLine(ASN1Dump.DumpAsString(cert.ToAsn1Object()));

            ISet dummySet = cert.GetNonCriticalExtensionOids();

            if (dummySet != null)
            {
                foreach (string key in dummySet)
                {
                    Console.WriteLine("\t{0}:\t{1}", key);
                }
            }

            Console.WriteLine();

            dummySet = cert.GetNonCriticalExtensionOids();
            if (dummySet != null)
            {
                foreach (string key in dummySet)
                {
                    Console.WriteLine("\t{0}:\t{1}", key);
                }
            }

            Console.WriteLine();
        }
예제 #33
0
        public static (Certificate crtificate, AsymmetricKeyParameter privateKey) CreateSelfSignedTlsCert(
            string subjectName, string issuerName, AsymmetricKeyParameter issuerPrivateKey)
        {
            const int keyStrength = DEFAULT_KEY_SIZE;

            if (issuerPrivateKey == null)
            {
                issuerPrivateKey = CreatePrivateKeyResource(issuerName);
            }

            // Generating Random Numbers
            var randomGenerator = new CryptoApiRandomGenerator();
            var random          = new SecureRandom(randomGenerator);
            ISignatureFactory signatureFactory = new Asn1SignatureFactory("SHA256WITHRSA", issuerPrivateKey, random);

            // The Certificate Generator
            var certificateGenerator = new X509V3CertificateGenerator();

            certificateGenerator.AddExtension(X509Extensions.SubjectAlternativeName, false,
                                              new GeneralNames(new GeneralName[]
            {
                new GeneralName(GeneralName.DnsName, "localhost"), new GeneralName(GeneralName.DnsName, "127.0.0.1")
            }));
            certificateGenerator.AddExtension(X509Extensions.ExtendedKeyUsage, true,
                                              new ExtendedKeyUsage(new List <DerObjectIdentifier>()
            {
                new DerObjectIdentifier("1.3.6.1.5.5.7.3.1")
            }));

            // Serial Number
            var serialNumber =
                BigIntegers.CreateRandomInRange(BigInteger.One, BigInteger.ValueOf(Int64.MaxValue), random);

            certificateGenerator.SetSerialNumber(serialNumber);

            // Issuer and Subject Name
            var subjectDn = new X509Name(subjectName);
            var issuerDn  = new X509Name(issuerName);

            certificateGenerator.SetIssuerDN(issuerDn);
            certificateGenerator.SetSubjectDN(subjectDn);

            // Valid For
            var notBefore = DateTime.UtcNow.Date;
            var notAfter  = notBefore.AddYears(70);

            certificateGenerator.SetNotBefore(notBefore);
            certificateGenerator.SetNotAfter(notAfter);

            // Subject Public Key
            var keyGenerationParameters = new KeyGenerationParameters(random, keyStrength);
            var keyPairGenerator        = new RsaKeyPairGenerator();

            keyPairGenerator.Init(keyGenerationParameters);
            var subjectKeyPair = keyPairGenerator.GenerateKeyPair();

            certificateGenerator.SetPublicKey(subjectKeyPair.Public);

            // self sign certificate
            var certificate = certificateGenerator.Generate(signatureFactory);

            var chain          = new X509CertificateStructure[] { X509CertificateStructure.GetInstance(certificate.GetEncoded()) };
            var tlsCertificate = new Certificate(chain);

            return(tlsCertificate, subjectKeyPair.Private);
        }