提升 asio 崩溃

Boost asio crashes

我有一个程序使用 cpprestsdk 进行 http 查询并使用 websocketpp 订阅数据流。该程序将立即崩溃(它说 Process finished with exit code 139 (interrupted by signal 11: SIGSEGV))。但是如果我评论http查询或订阅数据流,程序不会崩溃。

#include <websocketpp/config/asio_client.hpp>
#include <websocketpp/client.hpp>
#include "json.hpp"
#include <iostream>
#include <ctime>
#include <iostream>
#include <cpprest/http_client.h>
#include <cpprest/filestream.h>
#include <vector>
#include <string>


using std::string;
using namespace web;
using std::cout, std::endl;
using std::vector;
using websocketpp::lib::placeholders::_1;
using websocketpp::lib::placeholders::_2;
using websocketpp::lib::bind;

typedef websocketpp::client<websocketpp::config::asio_tls_client> client;
typedef websocketpp::config::asio_client::message_type::ptr message_ptr;


void on_stream_data(websocketpp::connection_hdl hdl, message_ptr msg) {
}

class OrderBook {
public:
    void initialize() {
        web::http::client::http_client_config cfg;
        std::string uri = string("https://fapi.binance.com/fapi/v1/depth?symbol=btcusdt&limit=1000");
        web::http::client::http_client client(U(uri), cfg);
        web::http::http_request request(web::http::methods::GET);
        request.headers().add("Content-Type", "application/x-www-form-urlencoded");
        web::http::http_response response = client.request(request).get();
    }

    int start_stream() {
        client c;
        std::string uri = string("wss://fstream.binance.com/ws/btcusdt@depth@100ms");
        try {
            c.set_access_channels(websocketpp::log::alevel::all);
            c.clear_access_channels(websocketpp::log::alevel::frame_payload);
            c.init_asio();
            c.set_message_handler(bind(on_stream_data, ::_1, ::_2));
            websocketpp::lib::error_code ec;
            client::connection_ptr con = c.get_connection(uri, ec);
            if (ec) {
                std::cout << "could not create connection because: " << ec.message() << std::endl;
                return 0;
            }
            c.connect(con);
            c.run();
        } catch (websocketpp::exception const &e) {
            std::cout << e.what() << std::endl;
        }
    }
};

int main(int argc, char *argv[]) {
    OrderBook ob;
    ob.initialize();  // comment either of these two lines, the program won't crash, otherwise the program will crash once start
    std::this_thread::sleep_for(std::chrono::milliseconds(10000000));
    ob.start_stream();  // comment either of these two lines, the program won't crash, otherwise the program will crash once start
}

当我 运行 这个程序处于 Clion 调试模式时,Clion 显示崩溃来自 /opt/homebrew/Cellar/boost/1.76.0/include/boost/asio/ssl/detail/impl/engine.ipp

中的函数
int engine::do_connect(void*, std::size_t)
{
  return ::SSL_connect(ssl_);
}

它说 Exception: EXC_BAD_ACCESS (code=1, address=0xf000000000)

有什么问题吗?是不是因为我 运行 两段代码使用了 boost::asio,有些东西不应该被初始化两次?

我可以编译这个 运行 没问题。

我最好的选择是您可能正在混合版本,尤其是增强版本。当 ODR violations lead to Undefined Behaviour.

时会导致常见的故障模式

请注意,这些 header-only 库依赖于一些非 header-only 的提升库(例如 Boost System、Thread and/or Chrono)。您需要针对与您 link.

库相同的版本进行编译

如果您使用任何库的分发包版本(cpprestsdk、websocketpp 或您正在使用的任何 json 库),那么使用 Boost 的分发包版本也是最安全的。

我个人会通过使用 Boost([=28= 的野兽],Json 的,你猜对了)来简化情况。

运行 全部在测试 Ubuntu 18.04 OS Boost 1.65 版本中,start_stream 序列触发此信息性错误:

[2022-05-22 13:42:11] [fatal] Required tls_init handler not present.
could not create connection because: Connection creation attempt failed

同时 UBSAN/ASAN 干净。一旦您找出导致程序崩溃的配置问题,也许该错误对您有所帮助。