[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: [Minios-devel] [UNIKRAFT/LWIP PATCH] uknetdev: Yield receive thread on full stack queue



Hi Simon,

Thanks for the fix!

Reviewed-by: Felipe Huici <felipe.huici@xxxxxxxxx>

On Thu, Feb 13, 2020 at 11:51 PM Simon Kuenzer <simon.kuenzer@xxxxxxxxx> wrote:
>
> When a too high rate of network traffic is received, the netdev's receive
> thread may never yield and only forwards packets to the lwip stack
> thread. This works as expected until the input queue runs full. If the
> the stack is never able to process them, the stack becomes completely
> unresponsive. Instead of dropping just a few packets all successive
> packets are dropped.
>
> This commit introduces a thread yield when this condition is met and
> gives the chance to process queued packets.
>
> Signed-off-by: Simon Kuenzer <simon.kuenzer@xxxxxxxxx>
> ---
>  uknetdev.c | 27 ++++++++++++++++++++++++---
>  1 file changed, 24 insertions(+), 3 deletions(-)
>
> diff --git a/uknetdev.c b/uknetdev.c
> index 47d2fb1..7047352 100644
> --- a/uknetdev.c
> +++ b/uknetdev.c
> @@ -193,6 +193,7 @@ static void uknetdev_input(struct uk_netdev *dev,
>         struct netif *nf = (struct netif *) argp;
>         struct uk_netbuf *nb;
>         struct pbuf *p;
> +       err_t err;
>         int ret;
>
>         UK_ASSERT(dev);
> @@ -243,12 +244,32 @@ static void uknetdev_input(struct uk_netdev *dev,
>                 p = lwip_netbuf_to_pbuf(nb);
>                 p->payload = nb->data;
>                 p->tot_len = p->len = nb->len;
> -               if (unlikely(nf->input(p, nf) != ERR_OK)) {
> +               err = nf->input(p, nf);
> +               if (unlikely(err != ERR_OK)) {
> +#if CONFIG_LWIP_THREADS && CONFIG_LIBUKNETDEV_DISPATCHERTHREADS
> +                       /* At this point it is possible that lwIP's input 
> queue
> +                        * is full or we run out of memory. In this case, we
> +                        * return to the scheduler and hope that lwIP's main
> +                        * thread is able to process some packets.
> +                        * Afterwards, we try it once again.
> +                        */
> +                       if (err == ERR_MEM) {
> +                               LWIP_DEBUGF(NETIF_DEBUG,
> +                                           ("%s: %c%c%u: lwIP's input queue 
> full: yielding and trying once again...\n",
> +                                            __func__, nf->name[0], 
> nf->name[1],
> +                                            nf->num));
> +                               uk_sched_yield();
> +                               err = nf->input(p, nf);
> +                               if (likely(err == ERR_OK))
> +                                       continue;
> +                       }
> +#endif
> +
>                         /*
>                          * Drop the packet that we could not send to the stack
>                          */
> -                       uk_pr_err("%c%c%u: Failed to forward packet to 
> lwIP\n",
> -                                 nf->name[0], nf->name[1], nf->num);
> +                       uk_pr_err("%c%c%u: Failed to forward packet to lwIP: 
> %d\n",
> +                                 nf->name[0], nf->name[1], nf->num, err);
>                         uk_netbuf_free_single(nb);
>                 }
>         } while (uk_netdev_status_more(ret));
> --
> 2.20.1
>
>
> _______________________________________________
> Minios-devel mailing list
> Minios-devel@xxxxxxxxxxxxxxxxxxxx
> https://lists.xenproject.org/mailman/listinfo/minios-devel

_______________________________________________
Minios-devel mailing list
Minios-devel@xxxxxxxxxxxxxxxxxxxx
https://lists.xenproject.org/mailman/listinfo/minios-devel

 


Rackspace

Lists.xenproject.org is hosted with RackSpace, monitoring our
servers 24x7x365 and backed by RackSpace's Fanatical Support®.