【发布时间】:2014-04-29 19:08:34
【问题描述】:
客户端进行了一些ssl::stream<tcp_socket>::async_read_some()/ssl::stream<tcp_socket>::async_write() 调用,在某些时候需要退出,即需要关闭连接。
调用ssl::stream<tcp_socket>::lowest_layer().close() 有效,但(正如预期的那样)服务器(openssl s_server -state ... 命令)在关闭连接时报告错误。
看API的正确方法似乎是调用ssl::stream<tcp_socket>::async_shutdown()。
现在基本上有两种情况需要关机:
1) 客户端在async_read_some() 回调中,并对来自服务器的“退出”命令作出反应。从那里调用 async_shutdown() 在关闭回调中产生“短读”错误。
这令人惊讶,但在谷歌搜索后这似乎是正常行为 - 似乎必须检查它是否是一个真正的错误:
// const boost::system::error_code &ec
if (ec.category() == asio::error::get_ssl_category() &&
ec.value() == ERR_PACK(ERR_LIB_SSL, 0, SSL_R_SHORT_READ)) {
// -> not a real error, just a normal TLS shutdown
}
不过,TLS 服务器似乎很高兴 - 它报告:
DONE
shutting down SSL
CONNECTION CLOSED
2) async_read_some() 处于活动状态 - 但用户决定退出客户端(例如,通过标准输入的命令)。当从该上下文调用async_shutdown() 时,会发生以下情况:
-
async_read_some()回调执行时带有“短读”错误代码 - 现在是预期的 -
async_shutdown()回调执行时带有 decryption failed or bad record mac 错误代码 - 这是意料之外的
服务端不报错。
因此我的问题是如何使用 boost asio 正确关闭 TLS 客户端。
【问题讨论】:
标签: c++ ssl boost openssl boost-asio