[Libwebsockets] Event-Loop API

Brice Hamon brice at ydotm.com
Mon Sep 24 18:56:27 CEST 2018


Nicolas,

I have been using libwebsocket with an external event epoll loop for years
now.
It is quite straightforward and very stable.

I have the libwebsocket running inside a thread from my framework. That
thread has all the epolling mechanism build in.
I use the lws xxx_POLL_FD callbacks (in the http[0] protocol) to add,
modify and remove a file descriptor, like for a normal fd except that these
fds are created by lws.

The rest of the lws callback mechanism is working as it should, nothing
special to do here.

I hope it helps,

Andy, I hope this won't be removed for V3.0 ? Thanks.

Brice.







On Mon, Sep 24, 2018 at 12:30 PM Andy Green <andy at warmcat.com> wrote:

>
>
> On 24/09/2018 23:15, Nicolas Cornu wrote:
> > Hello,
> >
> > I'm trying to adapt libwebsockets to a new (barely unused) event-loop. I
> > read this page:
> > https://libwebsockets.org/git/libwebsockets/tree/lib/event-libs . I find
> > it difficult for two reasons.
>
> Well, at least you don't find it difficult because the event loop
> support - which by now supports libuv, libev, libevent and poll - is not
> neatly isolated into a nice "ops" callback struct.
>
> That's new for v3.0 - before that libevent support was contributed by a
> Samsung dude without that advantage, the event loop stuff was spread all
> over the code.  So since he found that possible - he just sent the patch
> one day out of the blue - the situation is actually a lot easier for you.
>
> > First, names of callbacks in lws_event_loop_ops are not clear
> > (wsi_logical_close, init_pt, destroy_context2, ...).
>
> If you look in the ops struct definition, there is a little more advice
>
> struct lws_event_loop_ops {
>         const char *name;
>         /* event loop-specific context init during context creation */
>         int (*init_context)(struct lws_context *context,
>                             const struct lws_context_creation_info *info);
>         /* called during lws_destroy_context */
>         int (*destroy_context1)(struct lws_context *context);
>         /* called during lws_destroy_context2 */
>         int (*destroy_context2)(struct lws_context *context);
>         /* init vhost listening wsi */
>         int (*init_vhost_listen_wsi)(struct lws *wsi);
>         /* init the event loop for a pt */
>         int (*init_pt)(struct lws_context *context, void *_loop, int tsi);
>         /* called at end of first phase of close_free_wsi()  */
>         int (*wsi_logical_close)(struct lws *wsi);
>         /* return nonzero if client connect not allowed  */
>         int (*check_client_connect_ok)(struct lws *wsi);
>         /* close handle manually  */
>         void (*close_handle_manually)(struct lws *wsi);
>         /* event loop accept processing  */
>         void (*accept)(struct lws *wsi);
>         /* control wsi active events  */
>         void (*io)(struct lws *wsi, int flags);
>         /* run the event loop for a pt */
>         void (*run_pt)(struct lws_context *context, int tsi);
>         /* called before pt is destroyed */
>         void (*destroy_pt)(struct lws_context *context, int tsi);
>         /* called just before wsi is freed  */
>         void (*destroy_wsi)(struct lws *wsi);
>
>         unsigned int periodic_events_available:1;
> };
>
> https://libwebsockets.org/git/libwebsockets/tree/lib/event-libs/private.h
>
> > Second, the callback of already existing event loops are not only here
> > to wrap event loop. For exemple, if we read init_context implementation
> > it does something else than wrapping event loop.
>
> ... this stuff is a) setting up event-loop specific signal handler and
> b) preparing the event-loop specific watcher struct with a runtime
> pointer to the context, so it can operate in signal context without
> globals.
>
> static int
> elops_init_context_uv(struct lws_context *context,
>                       const struct lws_context_creation_info *info)
> {
>         int n;
>
>         context->eventlib_signal_cb = info->signal_cb;
>
>         for (n = 0; n < context->count_threads; n++)
>                 context->pt[n].w_sigint.context = context;
>
>         return 0;
> }
>
>
> > So, is it possible to do better documentation about them to explain what
> > they should do?
>
> Sure, anything's possible.  But it's not exactly #1 on my todo list atm.
>
> If you have specific questions I will try to answer them, but the code
> calling the ops is all right there along with four example
> implementations.  You may find your event loop needs more ops, although
> libuv was probably the worst case for that already.
>
> Note that libuv is quite different from the other event loops because it
> requires asynchronous handle close later via the event loop.  So this
> has a lot of knock-ons to make it work properly, like having to
> reference-count anything with a handle so we know the moment when it's
> able to stop the event loop on exit; getting that wrong is catastrophic
> for memory leaks and clean integration with foreign loops.  Assuming
> your event loop is more along the lines of libevent, which doesn't have
> this requirement, cut-and-pasting the libevent support doesn't look that
> unmanageable or inexplicable:
>
>
> https://libwebsockets.org/git/libwebsockets/tree/lib/event-libs/libevent/libevent.c
>
> There are also three minimal examples that showcase various modes of
> using the event loop, that are easy to extend to more event loops
>
>
> https://libwebsockets.org/git/libwebsockets/tree/minimal-examples/http-server/minimal-http-server-eventlib
>
> https://libwebsockets.org/git/libwebsockets/tree/minimal-examples/http-server/minimal-http-server-eventlib-demos
>
> https://libwebsockets.org/git/libwebsockets/tree/minimal-examples/http-server/minimal-http-server-eventlib-foreign
>
> The "foreign" one is interesting because it proves lws can integrate
> cleanly with somebody else's existing event loop without perturbing it.
> Although again that was more of a challenge for libuv than anything else.
>
> -Andy
>
> > Regards,
> >
> > Nicolas
> >
> > _______________________________________________
> > Libwebsockets mailing list
> > Libwebsockets at ml.libwebsockets.org
> > https://libwebsockets.org/mailman/listinfo/libwebsockets
> >
> _______________________________________________
> Libwebsockets mailing list
> Libwebsockets at ml.libwebsockets.org
> https://libwebsockets.org/mailman/listinfo/libwebsockets
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <https://libwebsockets.org/pipermail/libwebsockets/attachments/20180924/53b29b86/attachment-0001.html>


More information about the Libwebsockets mailing list