summaryrefslogtreecommitdiffstats
path: root/sys/net
diff options
context:
space:
mode:
authormlaier <mlaier@FreeBSD.org>2004-06-13 17:29:10 +0000
committermlaier <mlaier@FreeBSD.org>2004-06-13 17:29:10 +0000
commit977d97b004a1ae5bbd9d42eae28386f8e2372068 (patch)
tree75b8601b85775d6a872ff81b3098fedeb53233af /sys/net
parent469e445f95c246a203c12198eff9932b25b49b12 (diff)
downloadFreeBSD-src-977d97b004a1ae5bbd9d42eae28386f8e2372068.zip
FreeBSD-src-977d97b004a1ae5bbd9d42eae28386f8e2372068.tar.gz
Link ALTQ to the build and break with ABI for struct ifnet. Please recompile
your (network) modules as well as any userland that might make sense of sizeof(struct ifnet). This does not change the queueing yet. These changes will follow in a seperate commit. Same with the driver changes, which need case by case evaluation. __FreeBSD_version bump will follow. Tested-by: (i386)LINT
Diffstat (limited to 'sys/net')
-rw-r--r--sys/net/if.c21
-rw-r--r--sys/net/if_ppp.c6
-rw-r--r--sys/net/if_sl.c2
-rw-r--r--sys/net/if_spppsubr.c4
-rw-r--r--sys/net/if_var.h207
5 files changed, 228 insertions, 12 deletions
diff --git a/sys/net/if.c b/sys/net/if.c
index 3830c18..c1d874a 100644
--- a/sys/net/if.c
+++ b/sys/net/if.c
@@ -82,7 +82,7 @@ static void if_grow(void);
static void if_init(void *);
static void if_check(void *);
static int if_findindex(struct ifnet *);
-static void if_qflush(struct ifqueue *);
+static void if_qflush(struct ifaltq *);
static void if_route(struct ifnet *, int flag, int fam);
static void if_slowtimo(void *);
static void if_unroute(struct ifnet *, int flag, int fam);
@@ -441,6 +441,13 @@ if_attach(struct ifnet *ifp)
ifa->ifa_refcnt = 1;
TAILQ_INSERT_HEAD(&ifp->if_addrhead, ifa, ifa_link);
ifp->if_broadcastaddr = 0; /* reliably crash if used uninitialized */
+#ifdef ALTQ
+ ifp->if_snd.altq_type = 0;
+ ifp->if_snd.altq_disc = NULL;
+ ifp->if_snd.altq_flags &= ALTQF_CANTCHANGE;
+ ifp->if_snd.altq_tbr = NULL;
+ ifp->if_snd.altq_ifp = ifp;
+#endif
if (domains)
if_attachdomain1(ifp);
@@ -519,6 +526,12 @@ if_detach(struct ifnet *ifp)
*/
s = splnet();
if_down(ifp);
+#ifdef ALTQ
+ if (ALTQ_IS_ENABLED(&ifp->if_snd))
+ altq_disable(&ifp->if_snd);
+ if (ALTQ_IS_ATTACHED(&ifp->if_snd))
+ altq_detach(&ifp->if_snd);
+#endif
for (ifa = TAILQ_FIRST(&ifp->if_addrhead); ifa; ifa = next) {
next = TAILQ_NEXT(ifa, ifa_link);
@@ -1189,10 +1202,14 @@ if_up(struct ifnet *ifp)
* Flush an interface queue.
*/
static void
-if_qflush(struct ifqueue *ifq)
+if_qflush(struct ifaltq *ifq)
{
struct mbuf *m, *n;
+#ifdef ALTQ
+ if (ALTQ_IS_ENABLED(ifq))
+ ALTQ_PURGE(ifq);
+#endif
n = ifq->ifq_head;
while ((m = n) != 0) {
n = m->m_act;
diff --git a/sys/net/if_ppp.c b/sys/net/if_ppp.c
index d7e007e..d0db17e 100644
--- a/sys/net/if_ppp.c
+++ b/sys/net/if_ppp.c
@@ -933,7 +933,8 @@ pppoutput(ifp, m0, dst, rtp)
sc->sc_npqtail = &m0->m_nextpkt;
} else {
/* fastq and if_snd are emptied at spl[soft]net now */
- ifq = (m0->m_flags & M_HIGHPRI)? &sc->sc_fastq: &ifp->if_snd;
+ ifq = (m0->m_flags & M_HIGHPRI)? &sc->sc_fastq:
+ (struct ifqueue *)&ifp->if_snd;
IF_LOCK(ifq);
if (_IF_QFULL(ifq) && dst->sa_family != AF_UNSPEC) {
_IF_DROP(ifq);
@@ -988,7 +989,8 @@ ppp_requeue(sc)
*/
*mpp = m->m_nextpkt;
m->m_nextpkt = NULL;
- ifq = (m->m_flags & M_HIGHPRI)? &sc->sc_fastq: &sc->sc_if.if_snd;
+ ifq = (m->m_flags & M_HIGHPRI)? &sc->sc_fastq:
+ (struct ifqueue *)&sc->sc_if.if_snd;
if (! IF_HANDOFF(ifq, m, NULL)) {
sc->sc_if.if_oerrors++;
sc->sc_stats.ppp_oerrors++;
diff --git a/sys/net/if_sl.c b/sys/net/if_sl.c
index 0d39973..bc35341 100644
--- a/sys/net/if_sl.c
+++ b/sys/net/if_sl.c
@@ -571,7 +571,7 @@ sloutput(ifp, m, dst, rtp)
m_freem(m);
return (EHOSTUNREACH);
}
- ifq = &sc->sc_if.if_snd;
+ ifq = (struct ifqueue *)&sc->sc_if.if_snd;
ip = mtod(m, struct ip *);
if (sc->sc_if.if_flags & SC_NOICMP && ip->ip_p == IPPROTO_ICMP) {
m_freem(m);
diff --git a/sys/net/if_spppsubr.c b/sys/net/if_spppsubr.c
index 83fb1fc..66b6412 100644
--- a/sys/net/if_spppsubr.c
+++ b/sys/net/if_spppsubr.c
@@ -781,7 +781,7 @@ sppp_output(struct ifnet *ifp, struct mbuf *m,
s = splimp();
}
- ifq = &ifp->if_snd;
+ ifq = (struct ifqueue *)&ifp->if_snd;
#ifdef INET
if (dst->sa_family == AF_INET) {
/* XXX Check mbuf length here? */
@@ -1038,7 +1038,7 @@ sppp_flush(struct ifnet *ifp)
{
struct sppp *sp = (struct sppp*) ifp;
- sppp_qflush (&sp->pp_if.if_snd);
+ sppp_qflush ((struct ifqueue *)&sp->pp_if.if_snd);
sppp_qflush (&sp->pp_fastq);
sppp_qflush (&sp->pp_cpq);
}
diff --git a/sys/net/if_var.h b/sys/net/if_var.h
index 541f214..02bcf1f 100644
--- a/sys/net/if_var.h
+++ b/sys/net/if_var.h
@@ -82,6 +82,10 @@ struct ether_header;
#define IF_DUNIT_NONE -1
+#if 1 /* ALTQ */
+#include <altq/if_altq.h>
+#endif
+
TAILQ_HEAD(ifnethead, ifnet); /* we use TAILQs so that the order of */
TAILQ_HEAD(ifaddrhead, ifaddr); /* instantiation is preserved in the list */
TAILQ_HEAD(ifprefixhead, ifprefix);
@@ -171,7 +175,11 @@ struct ifnet {
(void *);
int (*if_resolvemulti) /* validate/resolve multicast */
(struct ifnet *, struct sockaddr **, struct sockaddr *);
+#if 1 /* ALTQ */
+ struct ifaltq if_snd; /* output queue (includes altq) */
+#else
struct ifqueue if_snd; /* output queue */
+#endif
const u_int8_t *if_broadcastaddr; /* linklevel broadcast bytestring */
struct lltable *lltables; /* list of L3-L2 resolution tables */
@@ -228,6 +236,7 @@ typedef void if_init_f_t(void *);
*/
#define IF_LOCK(ifq) mtx_lock(&(ifq)->ifq_mtx)
#define IF_UNLOCK(ifq) mtx_unlock(&(ifq)->ifq_mtx)
+#define IF_LOCK_ASSERT(ifq) mtx_assert(&(ifq)->ifq_mtx, MA_OWNED)
#define _IF_QFULL(ifq) ((ifq)->ifq_len >= (ifq)->ifq_maxlen)
#define _IF_DROP(ifq) ((ifq)->ifq_drops++)
#define _IF_QLEN(ifq) ((ifq)->ifq_len)
@@ -278,18 +287,25 @@ typedef void if_init_f_t(void *);
IF_UNLOCK(ifq); \
} while (0)
-#define IF_DRAIN(ifq) do { \
+#define _IF_POLL(ifq, m) ((m) = (ifq)->ifq_head)
+#define IF_POLL(ifq, m) _IF_POLL(ifq, m)
+
+#define _IF_DRAIN(ifq) do { \
struct mbuf *m; \
- IF_LOCK(ifq); \
for (;;) { \
_IF_DEQUEUE(ifq, m); \
if (m == NULL) \
break; \
m_freem(m); \
} \
- IF_UNLOCK(ifq); \
} while (0)
+#define IF_DRAIN(ifq) do { \
+ IF_LOCK(ifq); \
+ _IF_DRAIN(ifq); \
+ IF_UNLOCK(ifq); \
+} while(0)
+
#ifdef _KERNEL
/* interface address change event */
typedef void (*ifaddr_event_handler_t)(void *, struct ifnet *);
@@ -311,8 +327,10 @@ EVENTHANDLER_DECLARE(if_clone_event, if_clone_event_handler_t);
#define IF_AFDATA_UNLOCK(ifp) mtx_unlock(&(ifp)->if_afdata_mtx)
#define IF_AFDATA_DESTROY(ifp) mtx_destroy(&(ifp)->if_afdata_mtx)
-#define IF_HANDOFF(ifq, m, ifp) if_handoff(ifq, m, ifp, 0)
-#define IF_HANDOFF_ADJ(ifq, m, ifp, adj) if_handoff(ifq, m, ifp, adj)
+#define IF_HANDOFF(ifq, m, ifp) \
+ if_handoff((struct ifqueue *)ifq, m, ifp, 0)
+#define IF_HANDOFF_ADJ(ifq, m, ifp, adj) \
+ if_handoff((struct ifqueue *)ifq, m, ifp, adj)
static __inline int
if_handoff(struct ifqueue *ifq, struct mbuf *m, struct ifnet *ifp, int adjust)
@@ -338,6 +356,185 @@ if_handoff(struct ifqueue *ifq, struct mbuf *m, struct ifnet *ifp, int adjust)
(*ifp->if_start)(ifp);
return (1);
}
+#if 1 /* ALTQ */
+#define IFQ_ENQUEUE(ifq, m, err) \
+do { \
+ IF_LOCK(ifq); \
+ if (ALTQ_IS_ENABLED(ifq)) \
+ ALTQ_ENQUEUE(ifq, m, NULL, err); \
+ else { \
+ if (_IF_QFULL(ifq)) { \
+ m_freem(m); \
+ (err) = ENOBUFS; \
+ } else { \
+ _IF_ENQUEUE(ifq, m); \
+ (err) = 0; \
+ } \
+ } \
+ if (err) \
+ (ifq)->ifq_drops++; \
+ IF_UNLOCK(ifq); \
+} while (0)
+
+#define IFQ_DEQUEUE_NOLOCK(ifq, m) \
+do { \
+ if (TBR_IS_ENABLED(ifq)) \
+ (m) = tbr_dequeue(ifq, ALTDQ_REMOVE); \
+ else if (ALTQ_IS_ENABLED(ifq)) \
+ ALTQ_DEQUEUE(ifq, m); \
+ else \
+ _IF_DEQUEUE(ifq, m); \
+} while (0)
+
+#define IFQ_DEQUEUE(ifq, m) \
+do { \
+ IF_LOCK(ifq); \
+ IFQ_DEQUEUE_NOLOCK(ifq, m); \
+ IF_UNLOCK(ifq); \
+} while (0)
+
+#define IFQ_POLL_NOLOCK(ifq, m) \
+do { \
+ if (TBR_IS_ENABLED(ifq)) \
+ (m) = tbr_dequeue(ifq, ALTDQ_POLL); \
+ else if (ALTQ_IS_ENABLED(ifq)) \
+ ALTQ_POLL(ifq, m); \
+ else \
+ _IF_POLL(ifq, m); \
+} while (0)
+
+#define IFQ_POLL(ifq, m) \
+do { \
+ IF_LOCK(ifq); \
+ IFQ_POLL_NOLOCK(ifq, m); \
+ IF_UNLOCK(ifq); \
+} while (0)
+
+#define IFQ_PURGE_NOLOCK(ifq) \
+do { \
+ if (ALTQ_IS_ENABLED(ifq)) { \
+ ALTQ_PURGE(ifq); \
+ } else \
+ _IF_DRAIN(ifq); \
+} while (0)
+
+#define IFQ_PURGE(ifq) \
+do { \
+ IF_LOCK(ifq); \
+ IFQ_PURGE_NOLOCK(ifq); \
+ IF_UNLOCK(ifq); \
+} while (0)
+
+#define IFQ_SET_READY(ifq) \
+ do { ((ifq)->altq_flags |= ALTQF_READY); } while (0)
+
+#else /* !ALTQ */
+#define IFQ_ENQUEUE(ifq, m, err) \
+do { \
+ IF_LOCK(ifq); \
+ if (_IF_QFULL(ifq)) { \
+ m_freem(m); \
+ (err) = ENOBUFS; \
+ } else { \
+ _IF_ENQUEUE(ifq, m); \
+ (err) = 0; \
+ } \
+ if (err) \
+ (ifq)->ifq_drops++; \
+ IF_UNLOCK(ifq); \
+} while (0)
+
+#define IFQ_DEQUEUE_NOLOCK(ifq, m) _IF_DEQUEUE(ifq, m)
+#define IFQ_DEQUEUE(ifq, m) IF_DEQUEUE(ifq, m)
+#define IFQ_POLL_NOLOCK(ifq, m) _IF_POLL(ifq, m)
+#define IFQ_POLL(ifq, m) IF_POLL(ifq, m)
+#define IFQ_PURGE_NOLOCK(ifq) _IF_DRAIN(ifq)
+#define IFQ_PURGE(ifq) IF_DRAIN(ifq)
+
+#define IFQ_SET_READY(ifq) /* nothing */
+
+#endif /* !ALTQ */
+
+#define IFQ_LOCK(ifq) IF_LOCK(ifq)
+#define IFQ_UNLOCK(ifq) IF_UNLOCK(ifq)
+#define IFQ_LOCK_ASSERT(ifq) IF_LOCK_ASSERT(ifq)
+#define IFQ_IS_EMPTY(ifq) ((ifq)->ifq_len == 0)
+#define IFQ_INC_LEN(ifq) ((ifq)->ifq_len++)
+#define IFQ_DEC_LEN(ifq) (--(ifq)->ifq_len)
+#define IFQ_INC_DROPS(ifq) ((ifq)->ifq_drops++)
+#define IFQ_SET_MAXLEN(ifq, len) ((ifq)->ifq_maxlen = (len))
+
+#define IFQ_HANDOFF_ADJ(ifp, m, adj, err) \
+do { \
+ int len; \
+ short mflags; \
+ \
+ len = (m)->m_pkthdr.len; \
+ mflags = (m)->m_flags; \
+ IFQ_ENQUEUE(&(ifp)->if_snd, m, err); \
+ if ((err) == 0) { \
+ (ifp)->if_obytes += len + (adj); \
+ if (mflags & M_MCAST) \
+ (ifp)->if_omcasts++; \
+ if (((ifp)->if_flags & IFF_OACTIVE) == 0) \
+ (*(ifp)->if_start)(ifp); \
+ } \
+} while (0)
+
+#define IFQ_HANDOFF(ifp, m, err) \
+ IFQ_HANDOFF_ADJ(ifq, m, 0, err)
+
+#define IFQ_DRV_DEQUEUE(ifq, m) \
+do { \
+ (m) = (ifq)->ifq_drv_head; \
+ if (m) { \
+ if (((ifq)->ifq_drv_head = (m)->m_nextpkt) == NULL) \
+ (ifq)->ifq_drv_tail = NULL; \
+ (m)->m_nextpkt = NULL; \
+ (ifq)->ifq_drv_len--; \
+ } else { \
+ IFQ_LOCK(ifq); \
+ IFQ_DEQUEUE_NOLOCK(ifq, m); \
+ while ((ifq)->ifq_drv_len < (ifq)->ifq_drv_maxlen) { \
+ struct mbuf *m0; \
+ IFQ_DEQUEUE_NOLOCK(ifq, m0); \
+ if (m0 == NULL) \
+ break; \
+ m0->m_nextpkt = NULL; \
+ if ((ifq)->ifq_drv_tail == NULL) \
+ (ifq)->ifq_drv_head = m0; \
+ else \
+ (ifq)->ifq_drv_tail->m_nextpkt = m0; \
+ (ifq)->ifq_drv_tail = m0; \
+ (ifq)->ifq_drv_len++; \
+ } \
+ IFQ_UNLOCK(ifq); \
+ } \
+} while (0)
+
+#define IFQ_DRV_PREPEND(ifq, m) \
+do { \
+ (m)->m_nextpkt = (ifq)->ifq_drv_head; \
+ if ((ifq)->ifq_tail == NULL) \
+ (ifq)->ifq_tail = (m); \
+ (ifq)->ifq_drv_head = (m); \
+ (ifq)->ifq_drv_len++; \
+} while (0)
+
+#define IFQ_DRV_IS_EMPTY(ifq) \
+ (((ifq)->ifq_drv_len == 0) && ((ifq)->ifq_len == 0))
+
+#define IFQ_DRV_PURGE(ifq) \
+do { \
+ struct mbuf *m = (ifq)->ifq_drv_head; \
+ while(m != NULL) { \
+ m = m->m_nextpkt; \
+ m_freem(m); \
+ } \
+ (ifq)->ifq_drv_head = (ifq)->ifq_drv_tail = NULL; \
+ (ifq)->ifq_drv_len = 0; \
+ IFQ_PURGE(ifq); \
+} while (0)
/*
* 72 was chosen below because it is the size of a TCP/IP
OpenPOWER on IntegriCloud