Elk*_*vis 13 .net c# sockets ssl client-certificates
我无法获得使用我的SslStream项目的客户端证书.无论我做什么,我都无法让它实际使用客户端证书,尽管所有证书都是有效且值得信赖的,并且我已经为我自己生成的证书导入了CA证书,但它没有工作.我必须遗漏一些东西,但我已经过了几十次,审查了文档,示例和谷歌搜索的时间,我只是无法让它工作.我究竟做错了什么?
客户端:
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Net.Security;
using System.Net.Sockets;
using System.Reflection;
using System.Security.Cryptography.X509Certificates;
using System.Text;
namespace SslClient
{
class SslClientProgram
{
static void Main(string[] args)
{
TcpClient client = new TcpClient("localhost", 443);
SslStream stream = new SslStream(client.GetStream(), false, VerifyServerCertificate, null);
Assembly assembly = System.Reflection.Assembly.GetExecutingAssembly();
string location = assembly.Location;
int pos = location.LastIndexOf('\\');
location = location.Substring(0, pos);
X509Certificate2 certificate = new X509Certificate2(location + "\\my.client.certificate.pfx", "password");
stream.AuthenticateAsClient("my.host.name", new X509Certificate2Collection(certificate), System.Security.Authentication.SslProtocols.Tls, false);
StreamReader reader = new StreamReader(stream);
StreamWriter writer = new StreamWriter(stream);
while (true)
{
string line = System.Console.ReadLine();
writer.WriteLine(line);
writer.Flush();
if (line == "close") break;
line = reader.ReadLine();
System.Console.WriteLine("Received: {0}", line);
}
stream.Close();
}
private static bool VerifyServerCertificate(object sender, X509Certificate certificate, X509Chain chain, SslPolicyErrors sslPolicyErrors)
{
return true;
}
}
}
Run Code Online (Sandbox Code Playgroud)
服务器:
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Net.Security;
using System.Net.Sockets;
using System.Reflection;
using System.Security.Cryptography.X509Certificates;
using System.Text;
namespace SslServer
{
class SslServerProgram
{
static void Main(string[] args)
{
TcpListener server = new TcpListener(System.Net.IPAddress.Loopback, 443);
server.Start();
TcpClient client = server.AcceptTcpClient();
SslStream stream = new SslStream(client.GetStream(), false, VerifyClientCertificate, null);
Assembly assembly = System.Reflection.Assembly.GetExecutingAssembly();
string location = assembly.Location;
int pos = location.LastIndexOf('\\');
location = location.Substring(0, pos);
X509Certificate2 certificate = new X509Certificate2(location + "\\my.server.certificate.pfx", "password");
stream.AuthenticateAsServer(certificate, false, System.Security.Authentication.SslProtocols.Tls, false);
if (stream.RemoteCertificate != null)
{
System.Console.WriteLine(stream.RemoteCertificate.Subject);
}
else
{
System.Console.WriteLine("No client certificate.");
}
StreamReader reader = new StreamReader(stream);
StreamWriter writer = new StreamWriter(stream);
bool clientClose = false;
while (!System.Console.KeyAvailable)
{
System.Console.WriteLine("Waiting for data...");
string line = reader.ReadLine();
System.Console.WriteLine("Received: {0}", line);
if (line == "close")
{
clientClose = true;
break;
}
writer.WriteLine(line);
writer.Flush();
}
if (!clientClose) System.Console.ReadKey();
stream.Close();
server.Stop();
}
private static bool VerifyClientCertificate(object sender, X509Certificate certificate, X509Chain chain, SslPolicyErrors sslPolicyErrors)
{
return true;
}
}
}
Run Code Online (Sandbox Code Playgroud)
无论我尝试什么,服务器总是说"没有客户端证书".
事实证明,这AuthenticateAsServer
是关键 - 更具体地说,是第二个参数.
如果clientCertificateRequired
是false
,它将完全忽略客户端证书,即使客户端证书由客户端指定,但如果是true
,则允许它们,但如果未指定客户端证书,则不会抛出异常.
愚蠢的我 - 我认为clientCertificateRequired
设置为true意味着它实际上是必需的,因为.Net文档将其描述为:
"一个布尔值,指定客户端是否必须提供证书以进行身份验证."*(强调我的)
我的期望是,如果是true
,并且我没有发送客户证书,那么它将失败.这是一个明显的案例,微软的文档不完全准确.
更新:最新文档的clientCertificateRequired
参数包括短语"请注意,这只是一个请求-如果没有提供证书,服务器仍然接受连接请求."
归档时间: |
|
查看次数: |
11157 次 |
最近记录: |