2012-02-12 59 views
1

这里是我的WCF服务代码:如何使用BouncyCastle生成可用于WCF验证的X509Certificate2?

 ServiceHost svh = new ServiceHost(typeof(MyClass)); 

     var tcpbinding = new NetTcpBinding(SecurityMode.TransportWithMessageCredential, true); 
     //security 

     tcpbinding.Security.Message.ClientCredentialType = MessageCredentialType.UserName; 
     svh.Credentials.UserNameAuthentication.CustomUserNamePasswordValidator = new BWUserNamePasswordValidator(); 
     svh.Credentials.UserNameAuthentication.UserNamePasswordValidationMode =UserNamePasswordValidationMode.Custom; 
     svh.Credentials.ServiceCertificate.Certificate = GenerateCertificate(myCert); 

     svh.AddServiceEndpoint(typeof(IMyClass), tcpbinding, location);    

     svh.Open(); 

而这里的代码,我使用生成证书,其中:

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); 

     gen.AddExtension(X509Extensions.SubjectKeyIdentifier, false, 
        new SubjectKeyIdentifierStructure(keypair.Public));   

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

     return new X509Certificate2(DotNetUtilities.ToX509Certificate((Org.BouncyCastle.X509.X509Certificate)newCert)); 
    } 

当我开始它与下面的异常崩溃的服务器:

ArgumentException: It is likely that certificate 'CN=MyCert' may not 
have a private key that is capable of key exchange or the process may not have 
access rights for the private key. Please see inner exception for detail. 

内部异常为空。

我做错了什么?

回答

2

需要为此目的明确创建用于证书交换的密钥对。我想你只需要另一部分添加到您的证书生成这样的:

如果
gen.AddExtension(
    X509Extensions.KeyUsage, 
    true, 
    new KeyUsage(KeyUsage.keyCertSign)); 

不知道,语法是完全正确的,但是这样的想法:你需要的证书中的密钥作为对证书签名,如果有的话,这是一个“关键”延伸。

+0

增加了参数。该服务仍然不会从它开始。 我正在试验用makecert创建一个可用的证书,并且正确的命令序列是 makecert -n“CN = mfcertificate”-cy权限-a sha1 -sv“nick_ca.pvk”-r“nick_ca.cer” makecert -pe -n“CN = my Dev”-a sha1 -sky exchange -eku 1.3.6.1.5.5.7.3.1 -ic“nick_ca.cer”-iv“nick_ca.pvk”-sp“Microsoft RSA SChannel Cryptographic提供者“-sy 12 -sv”nick_dev.pvk“”nick_dev.cer“ pvk2pfx -pvk”nick_dev.pvk“-spc”nick_dev.cer“-pfx”nick_dev.pfx“ 我不知道如何在BouncyCastle中做到这一点虽然 – 2012-02-12 19:26:14

+0

你得到的错误将使用makecert与“-sky exchange”参数解决,我只是不知道BouncyCastle API足够知道如何做到这一点。抱歉。 – 2012-02-12 19:34:48

+0

实际上,它没有解决,我试过了)) – 2012-02-12 19:36:04