0

Boost Beast TLS 客户端(主要基于)未连接到 Microsoft Azure azurewebsites 托管的 Web 应用程序。查看 Wireshark 输出,在客户端发送 Client hello 消息后,服务器似乎正在发送 RST,该消息详细说明了可用的密码。客户端与其他 websocket 服务器一起工作,运行 Java Jetty 和让我们加密证书。

默认情况下, firefox 在连接到域时使用的首选密码出现TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384在主机上的密码列表和客户端在客户端问候消息中发送的数据包中。

我尝试了其他方法,例如禁用客户端证书身份验证,这在过去已经解决了其他证书问题。我已经能够使用 openssl 库和 native_handle 修改密码套件。但这并没有解决问题,我发现了一个堆栈溢出问题,答案表明密码存在兼容性问题。

在客户端打招呼后谷歌搜索 RST 消息,似乎主要返回与 IIS 和 Windows 服务器有关的问题。

有谁知道这可能是什么?

4

2 回答 2

1

我认为密码不仅是 RST 数据包的原因。由于您已经验证了两个地方都存在密码,也许我强烈建议确认签名算法,然后它可能是您应该考虑检查的证书绑定类型。

如果证书使用 SNI 绑定,我已经看到基于 JAVA 的服务器抛出 RST 数据包。

试一试并检查证书绑定并确认,否则建议更新客户端,因为服务器是 Azure 网站,这是 PAAS 提供的,并且在 azure 网站部署服务器内没有任何更改的范围。

您还可以使用带有 -showcerts 开关的 openssl 命令来比较证书及其密码和签名算法

于 2021-12-01T16:52:47.323 回答
0

所以我只是碰巧尝试了同步的例子,它是连接的。在客户端 hello 数据包中,它与我们的代码之间的少量差异之一是 SNI / 服务器名称字符串;Server Name: xxx.azurewebsites.net:443Server Name: xxx.azurewebsites.net

它碰巧在我们的嵌入式代码中包含了该端口,但不是来自该示例。我们的代码恰好基于异步客户端示例。

异步示例有;

    // Update the host_ string. This will provide the value of the
    // Host HTTP header during the WebSocket handshake.
    // See https://tools.ietf.org/html/rfc7230#section-5.4
    host_ += ':' + std::to_string(ep.port());

    // Set a timeout on the operation
    beast::get_lowest_layer(ws_).expires_after(std::chrono::seconds(30));

    // Set SNI Hostname (many hosts need this to handshake successfully)
    if(! SSL_set_tlsext_host_name(
            ws_.next_layer().native_handle(),
            host_.c_str()))
    {
        ec = beast::error_code(static_cast<int>(::ERR_get_error()),
            net::error::get_ssl_category());
        return fail(ec, "connect");
    }

同步示例有;

    // Set SNI Hostname (many hosts need this to handshake successfully)
    if(! SSL_set_tlsext_host_name(ws.next_layer().native_handle(), host.c_str()))
        throw beast::system_error(
            beast::error_code(
                static_cast<int>(::ERR_get_error()),
                net::error::get_ssl_category()),
            "Failed to set SNI Hostname");

    // Update the host_ string. This will provide the value of the
    // Host HTTP header during the WebSocket handshake.
    // See https://tools.ietf.org/html/rfc7230#section-5.4
    host += ':' + std::to_string(ep.port());

所以基本上,这些示例的工作方式不同,无论是否将端口添加到 SNI。在 github 上查找 boost beast,表明异步示例已在develop中修复;他们选择不包括端口号。

于 2021-12-02T16:28:49.903 回答