summaryrefslogtreecommitdiffstats
path: root/sys
diff options
context:
space:
mode:
authorluigi <luigi@FreeBSD.org>2002-08-04 23:55:06 +0000
committerluigi <luigi@FreeBSD.org>2002-08-04 23:55:06 +0000
commita86f01c7176b2b4bc02ad8b92b300dec503849f2 (patch)
treea398d48b12396834afe00ee1a8595fee14457624 /sys
parenteab6aceed81b6fde781962b732f25806087a9cda (diff)
downloadFreeBSD-src-a86f01c7176b2b4bc02ad8b92b300dec503849f2.zip
FreeBSD-src-a86f01c7176b2b4bc02ad8b92b300dec503849f2.tar.gz
Extend the interface to ether_input(): a NULL eh pointer means that
the mbuf contains the ethernet header (eh) as well, which ether_input() will strip off as needed. This permits the removal (in a backward compatible way) of the header removal code which right now is replicated in all drivers, sometimes in an inconsistent way. Also, because many functions called after ether_input() require the eh in the mbuf, eventually we can propagate the interface and handle outdated drivers just in ether_input(). Individual driver changes to use the new interface will follow as we have a chance to touch them. NOTE THAT THIS CHANGE IS FULLY BACKWARD COMPATIBLE AND DOES NOT BREAK BINARY COMPATIBILITY FOR DRIVERS. MFC after: 3 days
Diffstat (limited to 'sys')
-rw-r--r--sys/net/if_ethersubr.c38
1 files changed, 26 insertions, 12 deletions
diff --git a/sys/net/if_ethersubr.c b/sys/net/if_ethersubr.c
index 693f184..53c744d 100644
--- a/sys/net/if_ethersubr.c
+++ b/sys/net/if_ethersubr.c
@@ -535,30 +535,44 @@ ether_ipfw_chk(struct mbuf **m0, struct ifnet *dst,
}
/*
- * Process a received Ethernet packet;
- * the packet is in the mbuf chain m without
- * the ether header, which is provided separately.
+ * Process a received Ethernet packet. We have two different interfaces:
+ * one (conventional) assumes the packet in the mbuf, with the ethernet
+ * header provided separately in *eh. The second one (new) has everything
+ * in the mbuf, and we can tell it because eh == NULL.
+ * The caller MUST MAKE SURE that there are at least
+ * sizeof(struct ether_header) bytes in the first mbuf.
+ *
+ * This allows us to concentrate in one place a bunch of code which
+ * is replicated in all device drivers. Also, many functions called
+ * from ether_input() try to put the eh back into the mbuf, so we
+ * can later propagate the 'contiguous packet' interface to them,
+ * and handle the old interface just here.
*
* NOTA BENE: for many drivers "eh" is a pointer into the first mbuf or
* cluster, right before m_data. So be very careful when working on m,
* as you could destroy *eh !!
- * A (probably) more convenient and efficient interface to ether_input
- * is to have the whole packet (with the ethernet header) into the mbuf:
- * modules which do not need the ethernet header can easily drop it, while
- * others (most noticeably bridge and ng_ether) do not need to do additional
- * work to put the ethernet header back into the mbuf.
*
* First we perform any link layer operations, then continue
* to the upper layers with ether_demux().
*/
void
-ether_input(ifp, eh, m)
- struct ifnet *ifp;
- struct ether_header *eh;
- struct mbuf *m;
+ether_input(struct ifnet *ifp, struct ether_header *eh, struct mbuf *m)
{
struct ether_header save_eh;
+ if (eh == NULL) {
+ if (m->m_len < sizeof(struct ether_header)) {
+ /* XXX error in the caller. */
+ m_freem(m);
+ return;
+ }
+ m->m_pkthdr.rcvif = ifp;
+ eh = mtod(m, struct ether_header *);
+ m->m_data += sizeof(struct ether_header);
+ m->m_len -= sizeof(struct ether_header);
+ m->m_pkthdr.len = m->m_len;
+ }
+
#ifdef MAC
mac_create_mbuf_from_ifnet(ifp, m);
#endif
OpenPOWER on IntegriCloud