用于客户端 TLS 连接的 OpenSSL 或 LibreSSL C++ 示例

OpenSSL or LibreSSL C++ sample for client TLS connection

我正在搜索 C++ 中的客户端 TLS 连接示例。最适合 Visual Studio,但老实说它可以是任何编译器。我找到了几个 C 样本。但是没有人工作。我从 C 中的这个示例开始: https://wiki.openssl.org/index.php/SSL/TLS_Client

但是失败了

    res = BIO_do_connect(web);

with "system library" 如果我想连接到我自己的 node.js 服务器(使用直接 ip 地址)或 "bad hostname lookup" 使用 encrypted.google.com 作为 url. 与 libressl 和 Visual Studio 2013.

下一站:http://fm4dd.com/openssl/sslconnect.htm

至此程序运行成功。但是任何尝试在末尾写入 SSL 连接:

std::string json = "{'test':'huhu'}";

char buff[1024];
sprintf(buff, "POST /test.de HTTP/1.1 \nHost: test.de\nContent-Type: application/json\nContent-Length: %d\n\n", json.length());
std::string post = buff;

int snd = SSL_write(ssl, post.data(), post.length());
snd = SSL_write(ssl, json.data(), json.length());

强制服务器关闭连接(我不知道到底发生了什么,因为我现在不知道如何告诉 node.js 告诉我更多信息)。

所以我在 C++

中搜索工作示例或如何使用自己的证书 运行 获得 TLS 连接

I am searching for a client TLS connection example in C++.

我认为有几个 OpenSSL 到 C++ 的端口。他们尝试做完整的 class 包装器。请参阅 Google 上的 openssl++ class

当我在 C++ 中使用它时,我使用唯一指针进行清理。例如,参见 How to properly print RSA* as string in C++?. I use it primarily to ensure cleanup. I think its similar to Resource Acquisition Is Initialization 模式。

OpenSSL 还为类似的库和框架提供了一个页面。请参阅 OpenSSL wiki 上的 Related Links 页面。


But it fails on

res = BIO_do_connect(web);

with "system library" if I want to connect to my own node.js server (using the > direct ip address) or with "bad hostname lookup"

我的猜测是证书中的名称与 URL 连接中使用的名称不匹配。

您可以通过在 host 文件中添加一个条目来使名称起作用。实际上,这是您的本地 DNS 覆盖。参见 Microsoft TCP/IP Host Name Resolution Order

或者,您可以生成包含所有必需名称的证书。为此,请参阅 How to create a self-signed certificate with openssl?


forces the server to close the connection (I do not see exactly what happend as I do not now how I can tell node.js to tell me more).

 "POST /test.de HTTP/1.1 \nHost: test.de\nContent-Type: 
     application/json\nContent-Length: %d\n\n"

由于您缺少 Connection: close 请求header,服务器可能正在跟踪 RFC 7230, HTTP/1.1 Message Syntax and Routing, Section 6.1:

A server that does not support persistent connections MUST send the "close" connection option in every response message that does not have a 1xx (Informational) status code.

另外,应该是:

 "POST /test.de HTTP/1.1\r\nHost: test.de\r\nContent-Type: 
     application/json\r\nContent-Length:%d\r\n\r\n"

\r\n 用作新行,而不是 \r\n。双 \r\n 用于终止 header。您可以快速验证是否在标准中搜索 "CRLF"。您将参与 ABNF 语法的讨论。


So I search for a working sample or how to get a TLS connection with own certificate running in C++

这里的技巧是创建一个 well-formed 证书。为此,请参阅 How to create a self-signed certificate with openssl?

这是使用固定证书包的 LibreSSL 的更新示例:C++ libtls example on github