- android - 多次调用 OnPrimaryClipChangedListener
- android - 无法更新 RecyclerView 中的 TextView 字段
- android.database.CursorIndexOutOfBoundsException : Index 0 requested, 光标大小为 0
- android - 使用 AppCompat 时,我们是否需要明确指定其 UI 组件(Spinner、EditText)颜色
几天来,我一直在努力解决这个问题,想弄清楚它们是如何工作的。我已经阅读了文档并查看了一些示例,但我仍然需要指导。
具体来说,当客户端调用 connect()
并成功连接到服务器主机时,我是否应该在它之后立即发出 SSL_connect()
以启动握手?然后,客户端尝试使用 SSL_write()
将一些字节写入套接字。
另一方面,服务器使用pselect()
监视任何准备好读取的读取fds,并为传入连接成功发出accept()
调用。我是否应该在 accept() 返回以完成握手后立即发出 SSL_accept()
调用?
我注意到 SSL_connect()
返回 SSL_ERROR_WANT_READ
(这是在 select() 调用之后发出 SSL_connect() 以监视写 fd 集和返回并根据 Openssl 文档)。
此处发出调用的正确程序是什么,顺序是什么?
编辑以添加代码片段 -
Client side :
err = connect(fd, addr, addrlen);
if ( err == -1 && errno == EINPROGRESS )
{
// check if this is a true error,
// or wait until connect times out
fd_set fdset;
FD_ZERO(&fdset);
FD_SET(sfd, &fdset);
timeval tv = {F_sockwaitconnect, 0}; TEMP_FAILURE_RETRY(err = select(fd + 1,\
NULL,\
&fdset,\
NULL,\
&tv));
// what happened?
if ( err == 1 )
{
connect was successful
}
else
return 0;
const SSL_METHOD *method;
SSL_CTX *cctx;
SSL *cssl;
FILE *fp;
fp = stdout;
ERR_clear_error();
method = TLSv1_client_method();
cctx = SSL_CTX_new(method);
if ( cctx == NULL )
{
ERR_print_errors_fp(stdout);
return 0;
}
SSL_CTX_set_verify(cctx, SSL_VERIFY_PEER, NULL);
SSL_CTX_set_verify_depth(cctx, 4);
if (SSL_CTX_load_verify_locations(cctx, "mycert.pem", NULL) == 0)
return 0;
SSL_CTX_set_options(cctx, SSL_OP_NO_SSLv2 | SSL_OP_NO_SSLv3 | SSL_OP_NO_TLSv1_1 | SSL_OP_NO_COMPRESSION);
ERR_clear_error();
cssl = SSL_new(cctx); /* create new SSL connection state */
SSL_set_fd(cssl, fd); * attach the socket descriptor */
ERR_clear_error();
int rconnect = SSL_ERROR_WANT_READ;
while ( rconnect == SSL_ERROR_WANT_READ || rconnect == SSL_ERROR_WANT_WRITE )
{
char *buf = (char *) malloc(124);
ERR_error_string(SSL_get_error(cssl, rconnect), buf);
ERR_clear_error();
if ( rconnect == SSL_ERROR_WANT_READ ) {
int err = 0;
fd_set fdset;
FD_ZERO(&fdset);
FD_SET(fd, &fdset);
timeval tv = {F_sockwaitconnect, 0};
TEMP_FAILURE_RETRY(err1 = select(fd + 1,\
&fdset,\
NULL,\
NULL,\
&tv));
// what happened?
if ( err == 1 )
{
rconnect = SSL_connect(cssl);
}
}
}
X509 *cert;
cert = SSL_get_peer_certificate(cssl);
char line[2000+1];
if ( cert != NULL )
{
X509_NAME_oneline(X509_get_subject_name(cert), line, MAX_SIZE);
X509_NAME_oneline(X509_get_issuer_name(cert), line1, MAX_SIZE);
X509_free(cert);
}
ERR_clear_error();
r = SSL_write(cssl, buffer, len);
< check error >
Server side :
int res = pselect(max_fd + 1, // host socket file descriptor
&fd_setw, // set of ds wait 4 incoming data
NULL, // no write operations
NULL, // no exception operations
&tm, // how much time to wait
&sig_set); // block all signals
if ( event on listening socket )
{
client = accept(sfd, &peer, &peerl);
}
else // incoming data to receive on existing connection
{
SSL *ssl;
FILE *fp = stdout;
if ( !ctx )
{
return 0;
}
ERR_clear_error();
ssl = SSL_new(ctx);
SSL_set_fd(ssl, soc);
int ret = SSL_accept(ssl);
while (ret <= 0) {
ERR_print_errors_fp(fp);
char *buf = (char *) malloc(124);
ERR_error_string(SSL_get_error(ssl, ret), buf);
ERR_clear_error();
ret = SSL_accept(ssl);
}
X509 *cert;
cert = SSL_get_peer_certificate(ssl);
char line[2000+1];
if ( cert != NULL )
{
X509_NAME_oneline(X509_get_subject_name(cert), line, MAX_SIZE);
X509_NAME_oneline(X509_get_issuer_name(cert), line1, MAX_SIZE);
X509_free(cert);
}
// get data and analyze result
int rc = 0;
bool recv_called = false;
rc = SSL_read(ssl, buffer, len);
< check error >
}
在上述所有操作之前,服务器打开、绑定(bind)并监听一个非阻塞套接字以获取任何新的传入客户端连接。
当我运行上面的代码时,客户端执行 connect() 而服务器执行 accept()。服务器现在在 pselect() 处等待任何 fd 准备好接收数据。另一方面,客户端位于 SSL_connect() 并不断收到 SSL_ERROR_WANT_READ 错误。 select() 返回套接字已准备好读取。我的猜测是客户端正在等待握手的 SSL_accept() 部分?我不知道为什么服务器在 pselect() 等待。 SSL_accept() 周围的代码是错误的,即它循环并且不查找 WANT_READ 和 WANT_WRITE 错误,但我没有在代码中达到这一点。
最佳答案
SSL_connect
可以在 connect
完成时调用。由于 connect
和 SSL_connect
都需要与对等方交换数据,因此在使用非阻塞套接字时它们可能不会立即成功。如果 SSL_connect
返回错误 SSL_WANT_READ
或 SSL_WANT_WRITE
您必须在新数据在套接字上可用后再次调用它 (SSL_WANT_READ
) 或套接字可写 (SSL_WANT_WRITE
)。您可以使用 select
、pselect
、poll
、epoll、kqueue 或您的操作系统为此提供的任何 API 检查或等待。
SSL_accept
和accept
类似,即 SSL_accept
可以在accept
成功后直接调用,不一定立即成功,因为需要与 SSL 客户端进行数据交换,因此如果它返回 SSL_WANT_READ
或 SSL_WANT_WRITE
错误,您必须再次调用它。
请注意,SSL_write
和 SSL_read
也可能导致此类错误。也就是说,对于这些功能,您还需要处理 SSL_WANT_READ
和 SSL_WANT_WRITE
,并且处理方式与 SSL_connect
和 SSL_accept
。 SSL_read
甚至可能导致 SSL_WANT_WRITE
,因为即使 SSL session 已经建立,SSL 重新协商也可能发生。
关于c++ - SSL_connect() 和 SSL_accept() 调用,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/53455592/
我使用非阻塞套接字。对于普通的 TCP 连接,我在这里执行: Non blocking socket - how to check if a connection was successful? 但是
我正在尝试使用 SSL 创建服务器-客户端程序。我在使用 SSL_connect() 时遇到了一些麻烦:当我调用它时,它不会再返回,它只是卡在那里,客户端程序一直在运行,服务器停止等待握手完成。一旦我
我目前正在将一些曾经使用 RSA Security 库的现有技术重写到 OpenSSL 中,但我开始遇到一些问题。目前,所有证书验证代码似乎都在顺利运行,直到我调用 SSL_connect()。 之前
这两天,当我尝试安装新的 gem 时,我的控制台上收到了这个错误: Gem::RemoteFetcher::FetchError: SSL_connect returned=1 errno=0 sta
我正在尝试通过 TLSv1.2 建立 https 连接。上下文创建和一切都很好,我没有包含在下面的代码中。 if(https) //block 1 { int ssl_err = 0;
我在使用 openssl 库时遇到问题。我在发送 EHLO 和 STARTTLS 后调用以下函数: SSL_CTX *ctx = NULL; SSL *ssl = NULL; void Cre
关闭。这个问题需要debugging details .它目前不接受答案。 编辑问题以包含 desired behavior, a specific problem or error, and t
我有一个非阻塞套接字,我正在使用 openssl 创建一个 ssl 连接。我的问题是 SSL_connect 的工作方式。在这些情况下,它返回 SSL_ERROR_WANT_READ 或 SSL_ER
你好,我有一个使用 openssl 和 winapi 套接字的 C++ 应用程序,代码如下所示: sock = socket(AF_INET, SOCK_STREAM, 0); if (con
SSL_connect() 是否支持 ssl v3?我问这个的原因是,在访问网站时: https://secure53.onlineaccess1.com 我得到 SSL_connect(ssl) 的
我们有基于 Cucumber 的 UI 自动化测试框架。最近我们已经从 Ruby 1.9.x 迁移到 2.2.0,之后我们在通过测试框架登录我们的应用程序时遇到了问题。它说 SSL 连接重置问题。 错
我刚刚开始学习 C 的 openssl。我在弄清楚 SSL_set_connect_state 之间的区别时遇到了一些麻烦。函数和 SSL_connect功能,因为他们似乎在我的系统上做同样的事情。有
几天来,我一直在努力解决这个问题,想弄清楚它们是如何工作的。我已经阅读了文档并查看了一些示例,但我仍然需要指导。 具体来说,当客户端调用 connect() 并成功连接到服务器主机时,我是否应该在它之
使用我的 SSLCLIENT 的 openssl SSLConnect 出现奇怪的连接失败。 我们正在尝试与服务器建立 ssl 连接。我们注意到 SSL_CONNECT 失败,错误代码为“SSL_ER
当用 openssl 编写的服务器不调用 SSL_accept 时,客户端的 SSL_connect 将永远阻塞。openssl -SSL_CTX_set_timeout 、 SSL_SESSION_
SSL_CTX_set_verify() 和 SSL_set_verify() 调用可用于为底层上下文和 ssl 设置 verify_callback() 函数,分别。以下是 verify_callb
以下代码将始终以 # 结尾错误信息。 它可能会在 5 秒后或 30 分钟后失败。 require 'net/https' http = Net::HTTP.new('newproduct.zendes
我有以下 Controller - courses-controller.rb: class CoursesController Searching for - Imag
我有以下代码,并且我收到了 SIGSEGV: if ( SSL_connect(ssl) == FAIL ) 我遇到的错误是: Program received signal SIGSEGV, Seg
我想在我的 C++ 服务器和客户端中使用 thrift 提供的 ssl 支持。我自己的 Thrift 客户端在通过“transport->open()”后总是卡在 SSL_connect 中.所以我建
我是一名优秀的程序员,十分优秀!