借鉴的 https://blog.csdn.net/qq_19004627/article/details/88737411
坑1:openssl报错:ip address mismatch(preverify_ok=0;err=64;depth=0),不确定是不是自己生成的证书在无网情况下是不是不可用(开发电脑无法连互联网),暂时屏蔽了openssl相关的代码。
坑2:这个文章的client的代码中的发送代码有中文“你好”,导致服务器解析异常,进而断链(这个问题,困扰了我几乎一整天)。暂时修改成非中文,如果一定要中文,需要转utf-8。
坑3:服务器的回显代码可以做下优化。如下所示,当data->len非零时再传输。
case LWS_CALLBACK_SERVER_WRITEABLE: // 当此连接可写时 { if (data->len != 0) { lws_write(wsi, &data->buf[LWS_PRE], data->len, LWS_WRITE_TEXT); data->len = 0; } }
坑4:接收字符串打印乱码(直接打印in),可以在长度后面增加\0。
case LWS_CALLBACK_RECEIVE: // 当接收到客户端发来的帧以后 // 判断是否最后一帧 data->fin = lws_is_final_fragment(wsi); // 判断是否二进制消息 data->bin = lws_frame_is_binary(wsi); // 对服务器的接收端进行流量控制,如果来不及处理,可以控制之 // 下面的调用禁止在此连接上接收数据 //lws_rx_flow_control(wsi, 0); // 业务处理部分,为了实现Echo服务器,把客户端数据保存起来 memcpy(&data->buf[LWS_PRE], in, len); data->len = len; data->buf[LWS_PRE + data->len] = 0; lwsl_notice("recvied message:%s,len=%d\n", (char*)&data->buf[LWS_PRE], data->len); // 需要给客户端应答时,触发一次写回调 lws_callback_on_writable(wsi); break;
其他今天搜寻了一天的资料的心得:
1、lws_write前面一定要预留LWS_PRE的空间,给lws内部使用,否则会崩溃。
2、如果报文很长,需要分片,需要判断lws_is_final_fragment,可以使用类似下面的代码:
case LWS_CALLBACK_RECEIVE: { Client * const client = (Client *)user; const size_t remaining = lws_remaining_packet_payload(wsi); if (!remaining && lws_is_final_fragment(wsi)) { if (client->HasFragments()) { client->AppendMessageFragment(in, len, 0); in = (void *)client->GetMessage(); len = client->GetMessageLength(); } client->ProcessMessage((char *)in, len, wsi); client->ResetMessage(); } else client->AppendMessageFragment(in, len, remaining); } break;
3、客户端支持多连接到不同服务器,需要开多个线程去处理。
其他的一些可以参考https://blog.csdn.net/yetyongjin/article/details/131082375
标签:遇到,wsi,demo,len,LWS,client,libwebsocket,lws,data From: https://www.cnblogs.com/xuhuajie/p/18387490