我需要一个用Boost Asio SSL
编写的程序的代码片段。我有一个由两个客户组成的系统,互相连接。我要求他们进行相互身份验证,这样,在handshake()
命令的末尾,两个客户端都可以确定另一个客户端拥有他们提供的证书的私钥。两个客户端都有一个context
对象,让我们称它们为ctx1
和ctx2
,每个客户端都有一个公共证书和一个私钥。
是否可以设置上下文对象,以便当我调用socket.handshake()
时,客户端将进行双向身份验证。如果没有,那么实现我的目标的正确方法是什么?
发布于 2014-08-17 08:06:06
看起来boost只是使用OpenSSL接口。我不太了解boost,但是我为Perl实现了很多OpenSSL内部程序,并在阅读了boost源代码的相关部分之后得出了以下结论:
要与OpenSSL进行相互身份验证,您必须在客户端使用SSL_VERIFY_PEER
,在服务器端使用SSL_VERIFY_PEER|SSL_VERIFY_FAIL_IF_NO_PEER_CERT
。如果您只在服务器端使用SSL_VERIFY_PEER
,它将只向客户端发送证书请求,但如果客户端没有发回证书,则默默接受。
有了助推,这很可能是:
ctx.set_verify_mode(ssl::verify_peer); // client side
ctx.set_verify_mode(ssl::verify_peer|ssl::verify_fail_if_no_peer_cert); // server side
如果以这种方式设置verify_mode,它将根据配置的受信任CA(用ctx.load_verify_file
或ctx.load_verify_path
设置)验证证书。
如果您完全控制签署证书的CA (即您自己的CA),那么接受由此CA签名的任何证书就足够了。但是,如果您使用的CA也签署了您不希望接受的证书(通常是针对公共CA的情况),则还需要验证证书的内容。详细的操作方法取决于您的协议,但是对于通常的internet协议,如HTTP或SMTP,则需要检查证书的commonName和/或subjectAltNames。通配符处理之类的详细信息在协议之间有所不同。
Boost提供了验证来帮助您进行HTTP风格的验证,尽管从阅读代码中我认为实现略有错误(接受多个通配符,允许IDN通配符--有关需求请参阅RFC6125 )。
我不知道有什么标准来验证客户证书。通常,由特定(私有) CA签署的任何证书都将被接受。其他时候,来自公共CA的证书与特定的电子邮件模式相匹配。在本例中,boost似乎对您没有多大帮助,因此您可能需要使用OpenSSL SSL*
句柄处理sock.native_handle()
,然后使用OpenSSL函数提取证书(SSL_get_peer_certificate
)并检查证书的内容(各种X509_*
函数)。
至少,如果涉及公共CA,您还应该检查证书的吊销状态。看起来boost并没有提供到CRL (证书吊销列表)的直接接口,所以您必须使用ctx.native_handle()
和适当的OpenSSL函数(X509_STORE_add_crl
等)。使用OCSP (联机状态撤销协议)要复杂得多,相关的OpenSSL函数大多没有文档记录,这意味着您必须阅读OpenSSL源代码才能使用它们:(
发布于 2014-08-16 19:10:56
一方不能强迫另一方对你进行认证,这取决于协议,每一方只对另一方进行认证。只需遵循asio/概述/ssl.html格式的手册即可
ssl::context ctx(ssl::context::sslv23);
ctx.set_verify_mode(ssl::verify_peer);
ctx.load_verify_file("ca.pem");
https://stackoverflow.com/questions/25342971
复制相似问题