如何在.net中创建全新的x509Certificate2?

如何在.net中创建全新的x509Certificate2?,.net,x509certificate2,.net,X509certificate2,我在网上搜索了一下,找到了许多从.net中的文件生成新x509Certificate2的示例,但没有一个示例演示如何从.net中一开始就生成一个全新的x509Certificate2 有没有人能告诉我如何在.net中做这件事 非常感谢。我认为您无法使用该API完成此操作。但是你可以使用Bouncy Castle创建一个(http://www.bouncycastle.org)然后将该对象转换为X509Certificate2对象(BC有一些实用程序类用于此操作) -编辑- 看看这些BC类:X50

我在网上搜索了一下,找到了许多从.net中的文件生成新x509Certificate2的示例,但没有一个示例演示如何从.net中一开始就生成一个全新的x509Certificate2

有没有人能告诉我如何在.net中做这件事


非常感谢。

我认为您无法使用该API完成此操作。但是你可以使用Bouncy Castle创建一个(http://www.bouncycastle.org)然后将该对象转换为X509Certificate2对象(BC有一些实用程序类用于此操作)

-编辑- 看看这些BC类:X509V3CertificateGenerator和X509Certificate


稍后将BC X509Certificate对象转换为常规X509Certificate2对象的BC实用程序类是:DotNetUtilities

您可以使用PINVOKE调用Crypt32来实现。有一些可用的工具将生成一个并将其放入证书存储中

还有Keith Brown的,它是用托管代码编写的,并且具有

或者,您可以使用
Org.BouncyCastle.X509.X509V3CertificateGenerator
使用BouncyCastle.Security.DotNetUtilities中的实用程序方法,并调用
ToX509Certificate()


如果您想创建一个请求并让CA对其进行签名,那么在.NET中实际上更容易,因为这些类中的大多数都可以作为COM互操作DLL导入。但这是一个完全不同的问题。

这里有一个您可以使用的代码:

    static X509Certificate2 GenerateCertificate(string certName)
    {
        var keypairgen = new RsaKeyPairGenerator();
        keypairgen.Init(new KeyGenerationParameters(new SecureRandom(new CryptoApiRandomGenerator()), 1024));

        var keypair = keypairgen.GenerateKeyPair();

        var gen = new X509V3CertificateGenerator();

        var CN = new X509Name("CN=" + certName);
        var SN = BigInteger.ProbablePrime(120, new Random());

        gen.SetSerialNumber(SN);
        gen.SetSubjectDN(CN);
        gen.SetIssuerDN(CN);
        gen.SetNotAfter(DateTime.MaxValue);
        gen.SetNotBefore(DateTime.Now.Subtract(new TimeSpan(7, 0, 0, 0)));
        gen.SetSignatureAlgorithm("MD5WithRSA");
        gen.SetPublicKey(keypair.Public);           

        var newCert = gen.Generate(keypair.Private);

        return new X509Certificate2(DotNetUtilities.ToX509Certificate((Org.BouncyCastle.X509.X509Certificate)newCert));
    }
为此,请不要忘记添加对

Open ssl的引用,以创建x509证书 1.从以下链接下载Win64 Openssl。(Win64 Openssl v1.1.0j-37mb安装程序) URL-

2.安装后,设置系统路径环境变量。(path=C:\OpenSSL-Win64\bin)

3.打开命令提示符并将目录更改为桌面

4.创建密钥的命令: 私钥:
openssl-req-x509-days 365-newkey rsa:2048-keyout cert-Key.pem-out cert.pem
输入命令并按照说明进行操作

5.现在我们在桌面上有两个名为cert-key.pem和cert.pem的文件。要创建.pfx文件,请运行以下命令
openssl pkcs12-导出-输入cert.pem-inkey cert-key.pem-输出x509-cert.pfx
然后按照说明操作(输入相同的密码)

6.创建公钥的命令:
openssl pkcs12-in-x509-cert.pfx-clcerts-nokeys-out-x509-cert-public.pem
然后按照指示去做

7.将证书注册到mmc。

签出(名称空间:System.Security.Cryptography.X509Certificates)

public X509Certificate2 GetCertificate()
{
    var config = InitConfiguration();
    var certificateSubject = "X509Subject";
    var certificateStoreName = "X509StoreName";
    var certificateStoreLocation = "X509StoreLocation";
    var thumbPrint = "ThumbPrint";

    var storeName = (StoreName)Enum.Parse(typeof(StoreName), certificateStoreName, true);
    var storeLocation = (StoreLocation)Enum.Parse(typeof(StoreLocation), certificateStoreLocation, true);

    var certificateStore = new X509Store(storeName, storeLocation);
    certificateStore.Open(OpenFlags.ReadOnly);

    foreach (var storeCertificate in certificateStore.Certificates)
    {
        if (storeCertificate.Thumbprint.ToLower(System.Globalization.CultureInfo.CurrentCulture) == thumbPrint.ToLower(System.Globalization.CultureInfo.CurrentCulture))
        {return storeCertificate;
        }
    }
certificateStore.Close();
    return null;
}

似乎没有人知道这一点。似乎.net中的x509Certificate2只用于读取x509Certificate2证书,而不是生成证书,对吗?是的,使用x509Certificate2拥有的方法和构造函数,我们只能导入并获取其属性。实际上,Keith Brown的代码也只对Crypt32方法使用了P/Invoke。它很好地包装了它,因此您不必太担心。因为Crypt-32对pinvoke不友好:)与基思·布朗的资料的链接已经失效。有人有当前链接吗?我可能错了,但是新的Random()不应该是静态只读随机实例吗?如果每次创建一个新实例,它每次都会返回相同的随机数ProbablePrime。我通过VeraCode运行了BouncyCastle(1.7.1),发现它的BigInteger实现没有提供足够的熵。这就对图书馆使用的质数生成的有效性提出了质疑。@Young先生,如果您愿意,我非常有兴趣通过私人信息了解与您上述评论相关的更多细节。BigInteger不是密钥生成器使用的任何熵的来源;我们有一个安全的随机类。在我们最新的代码中,这本质上是转发给系统RNG,但可能是早期版本不太理想。在BigInteger中,Random类仅用于选择Miller-Rabin随机基来测试可能的素数。欢迎使用SO。虽然您的代码看起来是合法的,但如果您在答案中添加一些文本来解释重要的位或链接到官方文档,那就太好了。
InitConfiguration()
这将枚举系统存储中的证书。它不会创建新的证书
 public static X509Certificate2 GenerateSelfSignedCertificate()
    {
        string secp256r1Oid = "1.2.840.10045.3.1.7";  //oid for prime256v1(7)  other identifier: secp256r1
        
        string subjectName = "Self-Signed-Cert-Example";

        var ecdsa = ECDsa.Create(ECCurve.CreateFromValue(secp256r1Oid));

        var certRequest = new CertificateRequest($"CN={subjectName}", ecdsa, HashAlgorithmName.SHA256);

        //add extensions to the request (just as an example)
        //add keyUsage
        certRequest.CertificateExtensions.Add(new X509KeyUsageExtension(X509KeyUsageFlags.DigitalSignature, true));

        X509Certificate2 generatedCert = certRequest.CreateSelfSigned(DateTimeOffset.Now.AddDays(-1), DateTimeOffset.Now.AddYears(10)); // generate the cert and sign!

        X509Certificate2 pfxGeneratedCert = new X509Certificate2(generatedCert.Export(X509ContentType.Pfx)); //has to be turned into pfx or Windows at least throws a security credentials not found during sslStream.connectAsClient or HttpClient request...

     return pfxGeneratedCert;
}