[Libwebsockets] 'Close' frame with external message loop issue
andrejs.hanins at ubnt.com
Tue Nov 3 15:46:09 CET 2015
On 11/02/2015 09:21 PM, Andy Green wrote:
> On 3 November 2015 02:49:15 GMT+08:00, Andrejs Hanins <andrejs.hanins at ubnt.com> wrote:
>> On 11/02/2015 08:25 PM, Andy Green wrote:
>>> On 2 November 2015 22:52:59 GMT+08:00, Andrejs Hanins
>> <andrejs.hanins at ubnt.com> wrote:
>>>> I'm using LWS in server mode with external message loop (i.e. I
>>>> libwebsocket_service_fd by myself based on poll events reported by
>>>> external mechanism). Everything works absolutely fine, except when
>>>> client sends a 'Close' frame to the sever. The frame is successfully
>>>> received by server (server log has 'server sees client close
>>>> but the client doesn't receive a response to 'Close' frame. I see
>>>> server requests 'writable' state with the intention to respond back
>>>> the client (POLLOUT added to the events), 'writable' state is indeed
>>>> acquired as per message 'lws_calllback_as_writeable: 0xb39910
>>>> (user=0xb99a50)' followed only by a single user callback
>>>> LWS_CALLBACK_SERVER_WRITEABLE. The actual sending of 'Close'
>>>> doesn't happedn.
>>>> I have a suspicion that this situation is not handled properly by
>>>> code. Instead of sending an internal frame ('Close' response), the
>>>> library just calls LWS_CALLBACK_SERVER_WRITEABLE *as if* user had
>>>> requested a write, but this is not the case. User code doesn't have
>>>> anything to write. As a result, system ends up in hanged state -
>>>> wait for 'Close' response, but server does nothing.
>>> Is your lws older than a couple of weeks? This patch was aimed at
>> solving that:
>> I'm using latest stable tag v1.5-chrome47-firefox41 which includes
>> mentioned fix. But yes, the
>> issue seems to be somewhat similar, because I also get unexpected
>> writable cb.
> Might be worth dumping wsi->state at the place that's patched, in case it's a slightly different close-related state than is checked for atm.
Did that and got the following log:
written 66 bytes to client
spill on uh-ws-proto
server sees client close packet
lws_handle_POLLOUT_event 7 <--- 7 is WSI_STATE_RETURNED_CLOSE_ALREADY
lws_calllback_as_writeable: 0x9e9bf0 (user=0x9e9680)
There is nothing else follows in the log.
So, the state 7 is already handled by the patch, but the connection is still not closed and user writable callback is called.
Although, I'm struggling to understand how writable callback *is not* supposed to be called in state 7 if the last line of
lws_handle_POLLOUT_event() method is exactly lws_calllback_as_writeable().
Any other ideas to try?
>>>> I tried to call libwebsocket_service(ctx, 0) each time I receive
>>>> LWS_CALLBACK_SERVER_WRITEABLE, but it also doesn't help for some
>>>> reason. I just got additional callback to LWS_CALLBACK_GET_THREAD_ID
>>>> for which I always return 0.
>>>> BR, Andrey
>>>> Libwebsockets mailing list
>>>> Libwebsockets at ml.libwebsockets.org
More information about the Libwebsockets