[Libwebsockets] Ways to send multiple client request on the same wsi

Andy Green andy at warmcat.com
Wed Aug 22 23:15:38 CEST 2018

On 08/23/2018 02:38 AM, Xi Chen wrote:
> Thanks for your reply Andy.
> I have a few comments:
> 1. I quickly went thru the code (H2 client role specifically). For 
> POLLIN, the h2n->swsi will be set by received stream id (sid), then 
> corresponding h2 child wsi will be used.
> For POLLOUT, it seems doing a round-robin manner to go thru all child 
> list of nwsi. Do I understand correctly?

That's right... the round-robin action is formed because when a child 
wsi gets some time and bandwidth on the shared nwsi, the child wsi is 
sent to the end of the sibling linked-list.  So he's last to be checked 
for wanting write access next time the nwsi is writable.

> 2. I have already went thru the minimum-http-client-multi example. 
> However, from the debug log, I found that each client created its own 
> socket (i.e., a nwsi and a child wsi). It seems the example creates 
> multiple sockets rather than reusing the same socket. What I need is one 
> nwsi (one socket) opened with multiple child wsi, each has its own sid 
> value representing a different H2 stream. I do not see such API 
> existing. Can you help confirm?
> To achieve this, seems I need to i) create new wsi; ii) add it in to 
> nwsi's child list; iii) lws_h2_client_handshake(new wsi). Correct?

Yes, but... no, all this is already implemented and working.

By default it acts as individual connections for backward compatibility.

You need to use the flag LCCSCF_PIPELINE on the client connection info 
.ssl_connection to indicate you want either h1 pipelining or h2 broadsiding.


It is documented at the top of minimal-http-client-multi.c

  * By default the connections happen all together at the beginning and 
  * concurrently, which is fast.  However this is resource-intenstive, 
there are
  * 8 tcp connections, 8 tls tunnels on both the client and server.  You can
  * instead opt to have the connections happen one after the other inside a
  * single tcp connection and tls tunnel, using HTTP/1.1 pipelining.  To be
  * eligible to be pipelined on another existing connection to the same 
  * the client connection must have the LCCSCF_PIPELINE flag on its
  * info.ssl_connection member (this is independent of whether the 
  * is in ssl mode or not).
  * HTTP/1.0: Pipelining only possible if Keep-Alive: yes sent by server
  * HTTP/1.1: always possible... serializes requests
  * HTTP/2:   always possible... all requests sent as individual streams 
in parallel

and the flag has some documentation in libwebsockets.h

	LCCSCF_PIPELINE				= (1 << 16),
		/**< Serialize / pipeline multiple client connections
		 * on a single connection where possible.
		 * HTTP/1.0: possible if Keep-Alive: yes sent by server
		 * HTTP/1.1: always possible... uses pipelining
		 * HTTP/2:   always possible... uses parallel streams
		 * */

although I would agree it needs a document detailing all this new stuff 
in one place.

If you give the -p flag to the -multi minimal example, adding 
LCCSCF_PIPELINE, you will see in debug stuff like this

[2018/08/23 05:06:15:7180] INFO: lws_h2_dump_waiting_children: 0xe9b3e0: 
children waiting for POLLOUT service:
[2018/08/23 05:06:15:7180] INFO:   * 0xea40a0 h2 http
[2018/08/23 05:06:15:7180] INFO:   * 0xea5960 h2 http
[2018/08/23 05:06:15:7180] INFO:   * 0xea7220 h2 http
[2018/08/23 05:06:15:7180] INFO:   * 0xea8ae0 h2 http
[2018/08/23 05:06:15:7180] INFO:   * 0xeaa3a0 h2 http
[2018/08/23 05:06:15:7180] INFO:   * 0xeabc60 h2 http
[2018/08/23 05:06:15:7180] INFO:   * 0xead520 h2 http
[2018/08/23 05:06:15:7180] INFO:     0xebfba0 h2 http

which is pretty clear that they are all using a single nwsi.


> Thanks
> -Xi
> On Tue, Aug 21, 2018 at 11:28 PM, Andy Green <andy at warmcat.com 
> <mailto:andy at warmcat.com>> wrote:
>     On 08/21/2018 12:09 AM, Xi Chen wrote:
>         Hi,
>         I have two issues (maybe observations) which needs some
>         clarifications:
>           1.
>              Currently I send one H2 client request vis
>              lws_client_connect_via_info(), it creates one network wsi
>         (nwsi) and
>              then one h2 child wsi (h2_wsi). When I return -1 in the
>         callback, it
>              frees h2_wsi only. Why nwsi is not close?
>     (I must say I am gratified to hear someone talk about nwsi.  After
>     spending many months working on h2 support it's the first time
>     someone read the code AFAIK.)
>     It stays open for some time in case you have more client connections
>     to the same host coming.
>     Since v3.0 lws has a pretty sophisticated transparent queuing for
>     multi client connection to the same vhost, that works on http/1.1
>     pipelining if that's what you got or h2, broadsiding the connections
>     concurrently on a single TLS / tcp "nwsi".
>           2.
>              If I want to send the same request again, seems I need to call
>              lws_client_connect_via_info() again which creates nwsi and
>         h2_wsi
>              again (i.e., SSL handshake again), is there a way I can
>         reuse the
>              previous allocated nwsi and h2_wsi?
>     If the nwsi is still up, it should use it.
>     Have a play with:
>     https://libwebsockets.org/git/libwebsockets/tree/minimal-examples/http-client/minimal-http-client-multi
>     <https://libwebsockets.org/git/libwebsockets/tree/minimal-examples/http-client/minimal-http-client-multi>
>     this has switches that let you test multiple client connections
>     simultaneously or with with staggered delays (to stress the queuing
>     algorithm) in h1, h1 with pipelining and h2.  Various combinations
>     of this run as part of the CI testing on travis against both a local
>     server and libwebsockets.org <http://libwebsockets.org>.
>     If there are problems coming, talking about how to reproduce them
>     with that + whatever hack patch is needed will make it much easier
>     to look at it.
>     -Andy
>         Thanks
>         -Xi
>         _______________________________________________
>         Libwebsockets mailing list
>         Libwebsockets at ml.libwebsockets.org
>         <mailto:Libwebsockets at ml.libwebsockets.org>
>         https://libwebsockets.org/mailman/listinfo/libwebsockets
>         <https://libwebsockets.org/mailman/listinfo/libwebsockets>

More information about the Libwebsockets mailing list