Index: ifq.c =================================================================== RCS file: /cvs/src/sys/net/ifq.c,v retrieving revision 1.9 diff -u -p -r1.9 ifq.c --- ifq.c 7 Mar 2017 15:42:02 -0000 1.9 +++ ifq.c 8 Mar 2017 06:35:51 -0000 @@ -70,6 +70,7 @@ void ifq_barrier_task(void *); void ifq_serialize(struct ifqueue *ifq, struct task *t) { + struct mbuf_list ml = MBUF_LIST_INITIALIZER(); struct task work; if (ISSET(t->t_flags, TASK_ONQUEUE)) @@ -96,9 +97,20 @@ ifq_serialize(struct ifqueue *ifq, struc mtx_enter(&ifq->ifq_task_mtx); } + /* + * ifq->ifq_free is only modified by dequeue, which + * is only called from within this serialization + * context. it is therefore safe to access and modify + * here without taking ifq->ifq_mtx. + */ + ml = ifq->ifq_free; + ml_init(&ifq->ifq_free); + ifq->ifq_serializer = NULL; } mtx_leave(&ifq->ifq_task_mtx); + + ml_purge(&ml); } int @@ -177,6 +189,7 @@ ifq_init(struct ifqueue *ifq, struct ifn ifq->ifq_ops = &priq_ops; ifq->ifq_q = priq_ops.ifqop_alloc(idx, NULL); + ml_init(&ifq->ifq_free); ifq->ifq_len = 0; ifq->ifq_packets = 0; Index: ifq.h =================================================================== RCS file: /cvs/src/sys/net/ifq.h,v retrieving revision 1.10 diff -u -p -r1.10 ifq.h --- ifq.h 7 Mar 2017 01:29:53 -0000 1.10 +++ ifq.h 8 Mar 2017 06:35:51 -0000 @@ -42,6 +42,7 @@ struct ifqueue { struct mutex ifq_mtx; const struct ifq_ops *ifq_ops; void *ifq_q; + struct mbuf_list ifq_free; unsigned int ifq_len; unsigned int ifq_oactive;