Re: pppac(4) move ifnet out of KERNEL_LOCK()

2020-08-08 Thread Vitaliy Makkoveev
Another update. 
The whole "while ((m = ifq_dequeue(ifq)) != NULL)" wrapped by netlock as
it was made for pppx(4). This is to exclude per-packet lock/unlock in
output path.


Index: sys/net/if_pppx.c
===
RCS file: /cvs/src/sys/net/if_pppx.c,v
retrieving revision 1.98
diff -u -p -r1.98 if_pppx.c
--- sys/net/if_pppx.c   28 Jul 2020 09:53:36 -  1.98
+++ sys/net/if_pppx.c   8 Aug 2020 13:28:04 -
@@ -1058,7 +1058,7 @@ static intpppac_ioctl(struct ifnet *, u
 
 static int pppac_output(struct ifnet *, struct mbuf *, struct sockaddr *,
struct rtentry *);
-static voidpppac_start(struct ifnet *);
+static voidpppac_qstart(struct ifqueue *);
 
 static inline struct pppac_softc *
 pppac_lookup(dev_t dev)
@@ -1107,13 +1107,11 @@ pppacopen(dev_t dev, int flags, int mode
ifp->if_hdrlen = sizeof(uint32_t); /* for BPF */;
ifp->if_mtu = MAXMCLBYTES - sizeof(uint32_t);
ifp->if_flags = IFF_SIMPLEX | IFF_BROADCAST;
-   ifp->if_xflags = IFXF_CLONED;
+   ifp->if_xflags = IFXF_CLONED | IFXF_MPSAFE;
ifp->if_rtrequest = p2p_rtrequest; /* XXX */
ifp->if_output = pppac_output;
-   ifp->if_start = pppac_start;
+   ifp->if_qstart = pppac_qstart;
ifp->if_ioctl = pppac_ioctl;
-   /* XXXSMP: be sure pppac_start() called under NET_LOCK() */
-   ifq_set_maxlen(&ifp->if_snd, 1);
 
if_counters_alloc(ifp);
if_attach(ifp);
@@ -1382,10 +1380,10 @@ pppacclose(dev_t dev, int flags, int mod
klist_invalidate(&sc->sc_wsel.si_note);
splx(s);
 
-   pipex_iface_fini(&sc->sc_pipex_iface);
-
if_detach(ifp);
 
+   pipex_iface_fini(&sc->sc_pipex_iface);
+
LIST_REMOVE(sc, sc_entry);
free(sc, M_DEVBUF, sizeof(*sc));
 
@@ -1459,15 +1457,14 @@ drop:
 }
 
 static void
-pppac_start(struct ifnet *ifp)
+pppac_qstart(struct ifqueue *ifq)
 {
+   struct ifnet *ifp = ifq->ifq_if;
struct pppac_softc *sc = ifp->if_softc;
struct mbuf *m;
 
-   if (!ISSET(ifp->if_flags, IFF_RUNNING))
-   return;
-
-   while ((m = ifq_dequeue(&ifp->if_snd)) != NULL) {
+   NET_LOCK();
+   while ((m = ifq_dequeue(ifq)) != NULL) {
 #if NBPFILTER > 0
if (ifp->if_bpf) {
bpf_mtap_af(ifp->if_bpf, m->m_pkthdr.ph_family, m,
@@ -1489,9 +1486,9 @@ pppac_start(struct ifnet *ifp)
 
mq_enqueue(&sc->sc_mq, m); /* qdrop */
}
+   NET_UNLOCK();
 
if (!mq_empty(&sc->sc_mq)) {
-   KERNEL_ASSERT_LOCKED();
wakeup(sc);
selwakeup(&sc->sc_rsel);
}



Re: pppac(4) move ifnet out of KERNEL_LOCK()

2020-08-05 Thread Vitaliy Makkoveev
A little update.

I use `ifq' passed to pppac_start() instead of `ifp->if_snd' for
consistency reason.

Index: sys/net/if_pppx.c
===
RCS file: /cvs/src/sys/net/if_pppx.c,v
retrieving revision 1.98
diff -u -p -r1.98 if_pppx.c
--- sys/net/if_pppx.c   28 Jul 2020 09:53:36 -  1.98
+++ sys/net/if_pppx.c   5 Aug 2020 20:09:19 -
@@ -1058,7 +1058,7 @@ static intpppac_ioctl(struct ifnet *, u
 
 static int pppac_output(struct ifnet *, struct mbuf *, struct sockaddr *,
struct rtentry *);
-static voidpppac_start(struct ifnet *);
+static voidpppac_qstart(struct ifqueue *);
 
 static inline struct pppac_softc *
 pppac_lookup(dev_t dev)
@@ -1107,13 +1107,11 @@ pppacopen(dev_t dev, int flags, int mode
ifp->if_hdrlen = sizeof(uint32_t); /* for BPF */;
ifp->if_mtu = MAXMCLBYTES - sizeof(uint32_t);
ifp->if_flags = IFF_SIMPLEX | IFF_BROADCAST;
-   ifp->if_xflags = IFXF_CLONED;
+   ifp->if_xflags = IFXF_CLONED | IFXF_MPSAFE;
ifp->if_rtrequest = p2p_rtrequest; /* XXX */
ifp->if_output = pppac_output;
-   ifp->if_start = pppac_start;
+   ifp->if_qstart = pppac_qstart;
ifp->if_ioctl = pppac_ioctl;
-   /* XXXSMP: be sure pppac_start() called under NET_LOCK() */
-   ifq_set_maxlen(&ifp->if_snd, 1);
 
if_counters_alloc(ifp);
if_attach(ifp);
@@ -1382,10 +1380,10 @@ pppacclose(dev_t dev, int flags, int mod
klist_invalidate(&sc->sc_wsel.si_note);
splx(s);
 
-   pipex_iface_fini(&sc->sc_pipex_iface);
-
if_detach(ifp);
 
+   pipex_iface_fini(&sc->sc_pipex_iface);
+
LIST_REMOVE(sc, sc_entry);
free(sc, M_DEVBUF, sizeof(*sc));
 
@@ -1459,15 +1457,13 @@ drop:
 }
 
 static void
-pppac_start(struct ifnet *ifp)
+pppac_qstart(struct ifqueue *ifq)
 {
+   struct ifnet *ifp = ifq->ifq_if;
struct pppac_softc *sc = ifp->if_softc;
struct mbuf *m;
 
-   if (!ISSET(ifp->if_flags, IFF_RUNNING))
-   return;
-
-   while ((m = ifq_dequeue(&ifp->if_snd)) != NULL) {
+   while ((m = ifq_dequeue(ifq)) != NULL) {
 #if NBPFILTER > 0
if (ifp->if_bpf) {
bpf_mtap_af(ifp->if_bpf, m->m_pkthdr.ph_family, m,
@@ -1475,8 +1471,10 @@ pppac_start(struct ifnet *ifp)
}
 #endif
 
+   NET_LOCK();
m = pipex_output(m, m->m_pkthdr.ph_family, 0,
&sc->sc_pipex_iface);
+   NET_UNLOCK();
if (m == NULL)
continue;
 
@@ -1491,7 +1489,6 @@ pppac_start(struct ifnet *ifp)
}
 
if (!mq_empty(&sc->sc_mq)) {
-   KERNEL_ASSERT_LOCKED();
wakeup(sc);
selwakeup(&sc->sc_rsel);
}



pppac(4) move ifnet out of KERNEL_LOCK()

2020-08-05 Thread Vitaliy Makkoveev
The same as for pppx(4).

pipex(4) and pppac(4) are ready to became a little bit more MP capable.
Diff below moves pppac(4) related `ifnet' out of KERNEL_LOCK().

The wakeup(9) and selwakeup() are not require KERNEL_LOCK() so this
assertion was wrong and can be dropped. Also we detach `ifnet' before
pipex_iface_fini().

Index: sys/net/if_pppx.c
===
RCS file: /cvs/src/sys/net/if_pppx.c,v
retrieving revision 1.98
diff -u -p -r1.98 if_pppx.c
--- sys/net/if_pppx.c   28 Jul 2020 09:53:36 -  1.98
+++ sys/net/if_pppx.c   5 Aug 2020 13:53:33 -
@@ -1058,7 +1058,7 @@ static intpppac_ioctl(struct ifnet *, u
 
 static int pppac_output(struct ifnet *, struct mbuf *, struct sockaddr *,
struct rtentry *);
-static voidpppac_start(struct ifnet *);
+static voidpppac_qstart(struct ifqueue *);
 
 static inline struct pppac_softc *
 pppac_lookup(dev_t dev)
@@ -1107,13 +1107,11 @@ pppacopen(dev_t dev, int flags, int mode
ifp->if_hdrlen = sizeof(uint32_t); /* for BPF */;
ifp->if_mtu = MAXMCLBYTES - sizeof(uint32_t);
ifp->if_flags = IFF_SIMPLEX | IFF_BROADCAST;
-   ifp->if_xflags = IFXF_CLONED;
+   ifp->if_xflags = IFXF_CLONED | IFXF_MPSAFE;
ifp->if_rtrequest = p2p_rtrequest; /* XXX */
ifp->if_output = pppac_output;
-   ifp->if_start = pppac_start;
+   ifp->if_qstart = pppac_qstart;
ifp->if_ioctl = pppac_ioctl;
-   /* XXXSMP: be sure pppac_start() called under NET_LOCK() */
-   ifq_set_maxlen(&ifp->if_snd, 1);
 
if_counters_alloc(ifp);
if_attach(ifp);
@@ -1382,10 +1380,10 @@ pppacclose(dev_t dev, int flags, int mod
klist_invalidate(&sc->sc_wsel.si_note);
splx(s);
 
-   pipex_iface_fini(&sc->sc_pipex_iface);
-
if_detach(ifp);
 
+   pipex_iface_fini(&sc->sc_pipex_iface);
+
LIST_REMOVE(sc, sc_entry);
free(sc, M_DEVBUF, sizeof(*sc));
 
@@ -1459,14 +1457,12 @@ drop:
 }
 
 static void
-pppac_start(struct ifnet *ifp)
+pppac_qstart(struct ifqueue *ifq)
 {
+   struct ifnet *ifp = ifq->ifq_if;
struct pppac_softc *sc = ifp->if_softc;
struct mbuf *m;
 
-   if (!ISSET(ifp->if_flags, IFF_RUNNING))
-   return;
-
while ((m = ifq_dequeue(&ifp->if_snd)) != NULL) {
 #if NBPFILTER > 0
if (ifp->if_bpf) {
@@ -1475,8 +1471,10 @@ pppac_start(struct ifnet *ifp)
}
 #endif
 
+   NET_LOCK();
m = pipex_output(m, m->m_pkthdr.ph_family, 0,
&sc->sc_pipex_iface);
+   NET_UNLOCK();
if (m == NULL)
continue;
 
@@ -1491,7 +1489,6 @@ pppac_start(struct ifnet *ifp)
}
 
if (!mq_empty(&sc->sc_mq)) {
-   KERNEL_ASSERT_LOCKED();
wakeup(sc);
selwakeup(&sc->sc_rsel);
}