客户端对BIO_do_connect返回-1

Client returns -1 on BIO_do_connect

本文关键字:返回 connect do BIO 客户端      更新时间:2023-10-16

我试图使用OpenSSL及其BIOs创建一个基本的服务器和客户端,但BIO_do_connect返回-1。ERR_get_error在此之后返回0。我试图通过写//check [condition]来最小化下面的代码。在我的实际代码中,我用if检查做同样的事情,然后打印出ERR_get_error返回的错误。(因此,如果条件为真,我打印一个错误消息)

这是我的服务器代码:
// init OpenSSL
SSL_load_error_strings();
ERR_load_BIO_strings();
SSL_library_init();
OpenSSL_add_all_algorithms();
SSL_CTX *ctx = SSL_CTX_new(SSLv23_server_method());
SSL_CTX_set_default_passwd_cb(ctx, &myPasswordCallback);
int certState = SSL_CTX_use_certificate_file(ctx, "../certs/cert.pem", SSL_FILETYPE_PEM);
// check certState < 0
int keyState = SSL_CTX_use_PrivateKey_file(ctx, "../certs/key.pem", SSL_FILETYPE_PEM);
// check keyState < 0
BIO *serverBio = BIO_new_ssl(ctx, 0);
// check serverBio == nullptr
SSL *serverSsl = nullptr;
BIO_get_ssl(serverBio, &serverSsl);
// check serverSsl == nullptr
SSL_set_mode(serverSsl, SSL_MODE_AUTO_RETRY);
BIO *acceptBio = BIO_new_accept("6672");
// check acceptBio == nullptr
int setupAcceptResult = BIO_do_accept(acceptBio);
// check setupAcceptResult <= 0
int acceptResult = BIO_do_accept(acceptBio);
// check acceptResult <= 0
BIO *clientBio = BIO_pop(acceptBio);
// check clientBio == nullptr
BIO_free_all(clientBio);
BIO_free_all(acceptBio);
BIO_free_all(serverBio);
// cleanup OpenSSL
SSL_CTX_free(ctx);
EVP_cleanup();
ERR_free_strings();

此服务器运行正常,但我的客户端无法连接到它:

// init OpenSSL
SSL_load_error_strings();
ERR_load_BIO_strings();
SSL_library_init();
OpenSSL_add_all_algorithms();
SSL_CTX *ctx = SSL_CTX_new(SSLv23_client_method());
SSL_CTX_set_default_passwd_cb(ctx, &myPasswordCallback);
int certState = SSL_CTX_use_certificate_file(ctx, "../certs/cert.pem", SSL_FILETYPE_PEM);
// check certState < 0
int keyState = SSL_CTX_use_PrivateKey_file(ctx, "../certs/key.pem", SSL_FILETYPE_PEM);
// check keyState < 0
BIO *clientBio = BIO_new_ssl_connect(ctx);
SSL *clientSsl = nullptr;
BIO_get_ssl(clientBio, &clientSsl);
// check clientSsl == nullptr
SSL_set_mode(clientSsl, SSL_MODE_AUTO_RETRY);
BIO_set_conn_hostname(clientBio, "localhost:6672");
long connectionState = BIO_do_connect(clientBio);
// check connectionState <= 0
// here it fails; connectionState is -1
long sslState = SSL_get_verify_result(clientSsl);
// check sslState != X509_V_OK
BIO_free_all(clientBio);
SSL_CTX_free(ctx);
EVP_cleanup();
ERR_free_strings();
我很抱歉发了这么多代码。我没有找到一个完整的OpenSSL服务器/客户端使用BIOs的例子。

您的服务器代码基本上是这样的:

  1. 设置serverBio为SSL
  2. 创建一个没有SSL的新BIO acceptBio
  3. 接受连接connection -> clientBio
  4. 自由一切

服务器没有进行任何SSL握手,因为serverBio没有被用于新创建的TCP连接clientBio.

除此之外,我建议您首先针对已知的良好客户端和服务器测试您的服务器和客户端,以便您可以更快地找出问题所在。openssl s_clientopenssl s_server提供这样的测试客户端和服务器。此外,包捕获(wireshark)有助于发现服务器和客户端之间发生了什么。