diff options
author | semenu <semenu@FreeBSD.org> | 2001-08-13 18:32:39 +0000 |
---|---|---|
committer | semenu <semenu@FreeBSD.org> | 2001-08-13 18:32:39 +0000 |
commit | 9fb458f8dfc6854b052a40956e1c4c7a06baff0a (patch) | |
tree | a7adb7d487d2ce4dadabeb5aa2883db9eae31c3a /sys | |
parent | c6c3284428a344414f008cb3282ac57379228bf8 (diff) | |
download | FreeBSD-src-9fb458f8dfc6854b052a40956e1c4c7a06baff0a.zip FreeBSD-src-9fb458f8dfc6854b052a40956e1c4c7a06baff0a.tar.gz |
Add support for 802.1Q VLAN and oversized ethernet frames.
PR: kern/29235
Submitted by: Peter Jeremy <peter.jeremy@alcatel.com.au>
Reviewed by: Yar Tikhiy <yar@FreeBSD.org>
MFC after: 1 week
Diffstat (limited to 'sys')
-rw-r--r-- | sys/dev/tx/if_tx.c | 34 | ||||
-rw-r--r-- | sys/dev/tx/if_txreg.h | 2 | ||||
-rw-r--r-- | sys/dev/tx/if_txvar.h | 2 | ||||
-rw-r--r-- | sys/modules/tx/Makefile | 6 | ||||
-rw-r--r-- | sys/pci/if_tx.c | 34 | ||||
-rw-r--r-- | sys/pci/if_txvar.h | 2 |
6 files changed, 71 insertions, 9 deletions
diff --git a/sys/dev/tx/if_tx.c b/sys/dev/tx/if_tx.c index 93c715b..f7610c7 100644 --- a/sys/dev/tx/if_tx.c +++ b/sys/dev/tx/if_tx.c @@ -54,6 +54,8 @@ #if defined(__FreeBSD__) #define NBPFILTER 1 +#include "vlan.h" + #include <net/if.h> #include <net/if_arp.h> #include <net/ethernet.h> @@ -61,6 +63,10 @@ #include <net/bpf.h> +#if NVLAN > 0 +#include <net/if_vlan_var.h> +#endif + #include <vm/vm.h> /* for vtophys */ #include <vm/pmap.h> /* for vtophys */ #include <machine/bus_memio.h> @@ -85,6 +91,8 @@ #else /* __OpenBSD__ */ #include "bpfilter.h" +#define NVLAN 0 /* not sure if/how OpenBSD supports VLANs */ + #include <sys/device.h> #include <net/if.h> @@ -555,6 +563,9 @@ epic_freebsd_attach(dev) /* Attach to OS's managers */ ether_ifattach(ifp, ETHER_BPF_SUPPORTED); +#if NVLAN > 0 + ifp->if_hdrlen = sizeof(struct ether_vlan_header); +#endif callout_handle_init(&sc->stat_ch); fail: @@ -642,9 +653,25 @@ epic_ifioctl(ifp, command, data) #if defined(__FreeBSD__) case SIOCSIFADDR: case SIOCGIFADDR: - case SIOCSIFMTU: error = ether_ioctl(ifp, command, data); break; + case SIOCSIFMTU: + if (ifp->if_mtu == ifr->ifr_mtu) + break; + + /* XXX Though the datasheet doesn't imply any + * limitations on RX and TX sizes beside max 64Kb + * DMA transfer, seems we can't send more then 1600 + * data bytes per ethernet packet. (Transmitter hangs + * up if more data is sent) + */ + if (ifr->ifr_mtu + ifp->if_hdrlen <= EPIC_MAX_MTU) { + ifp->if_mtu = ifr->ifr_mtu; + epic_stop(sc); + epic_init(sc); + } else + error = EINVAL; + break; #else /* __OpenBSD__ */ case SIOCSIFADDR: { struct ifaddr *ifa = (struct ifaddr *)data; @@ -1746,9 +1773,8 @@ epic_init_rings(sc) } desc->bufaddr = vtophys( mtod(buf->mbuf,caddr_t) ); - desc->buflength = ETHER_MAX_FRAME_LEN; - desc->status = 0x8000; /* Give to EPIC */ - + desc->buflength = MCLBYTES; /* Max RX buffer length */ + desc->status = 0x8000; /* Set owner bit to NIC */ } for (i = 0; i < TX_RING_SIZE; i++) { diff --git a/sys/dev/tx/if_txreg.h b/sys/dev/tx/if_txreg.h index a9ec762..7a5c82b 100644 --- a/sys/dev/tx/if_txreg.h +++ b/sys/dev/tx/if_txreg.h @@ -50,6 +50,8 @@ #define RX_RING_MASK (RX_RING_SIZE - 1) #define ETHER_MAX_FRAME_LEN (ETHER_MAX_LEN + ETHER_CRC_LEN) +#define EPIC_MAX_MTU 1600 /* This is experiment-derived value */ + /* PCI aux configuration registers */ #if defined(__FreeBSD__) #define PCIR_BASEIO (PCIR_MAPS + 0x0) /* Base IO Address */ diff --git a/sys/dev/tx/if_txvar.h b/sys/dev/tx/if_txvar.h index a9ec762..7a5c82b 100644 --- a/sys/dev/tx/if_txvar.h +++ b/sys/dev/tx/if_txvar.h @@ -50,6 +50,8 @@ #define RX_RING_MASK (RX_RING_SIZE - 1) #define ETHER_MAX_FRAME_LEN (ETHER_MAX_LEN + ETHER_CRC_LEN) +#define EPIC_MAX_MTU 1600 /* This is experiment-derived value */ + /* PCI aux configuration registers */ #if defined(__FreeBSD__) #define PCIR_BASEIO (PCIR_MAPS + 0x0) /* Base IO Address */ diff --git a/sys/modules/tx/Makefile b/sys/modules/tx/Makefile index c1c1dfa..b9fdd6d 100644 --- a/sys/modules/tx/Makefile +++ b/sys/modules/tx/Makefile @@ -4,6 +4,10 @@ KMOD= if_tx SRCS= if_tx.c opt_bdg.h device_if.h bus_if.h pci_if.h -SRCS+= miibus_if.h +SRCS+= miibus_if.h vlan.h +CLEANFILES = vlan.h + +vlan.h: + touch vlan.h .include <bsd.kmod.mk> diff --git a/sys/pci/if_tx.c b/sys/pci/if_tx.c index 93c715b..f7610c7 100644 --- a/sys/pci/if_tx.c +++ b/sys/pci/if_tx.c @@ -54,6 +54,8 @@ #if defined(__FreeBSD__) #define NBPFILTER 1 +#include "vlan.h" + #include <net/if.h> #include <net/if_arp.h> #include <net/ethernet.h> @@ -61,6 +63,10 @@ #include <net/bpf.h> +#if NVLAN > 0 +#include <net/if_vlan_var.h> +#endif + #include <vm/vm.h> /* for vtophys */ #include <vm/pmap.h> /* for vtophys */ #include <machine/bus_memio.h> @@ -85,6 +91,8 @@ #else /* __OpenBSD__ */ #include "bpfilter.h" +#define NVLAN 0 /* not sure if/how OpenBSD supports VLANs */ + #include <sys/device.h> #include <net/if.h> @@ -555,6 +563,9 @@ epic_freebsd_attach(dev) /* Attach to OS's managers */ ether_ifattach(ifp, ETHER_BPF_SUPPORTED); +#if NVLAN > 0 + ifp->if_hdrlen = sizeof(struct ether_vlan_header); +#endif callout_handle_init(&sc->stat_ch); fail: @@ -642,9 +653,25 @@ epic_ifioctl(ifp, command, data) #if defined(__FreeBSD__) case SIOCSIFADDR: case SIOCGIFADDR: - case SIOCSIFMTU: error = ether_ioctl(ifp, command, data); break; + case SIOCSIFMTU: + if (ifp->if_mtu == ifr->ifr_mtu) + break; + + /* XXX Though the datasheet doesn't imply any + * limitations on RX and TX sizes beside max 64Kb + * DMA transfer, seems we can't send more then 1600 + * data bytes per ethernet packet. (Transmitter hangs + * up if more data is sent) + */ + if (ifr->ifr_mtu + ifp->if_hdrlen <= EPIC_MAX_MTU) { + ifp->if_mtu = ifr->ifr_mtu; + epic_stop(sc); + epic_init(sc); + } else + error = EINVAL; + break; #else /* __OpenBSD__ */ case SIOCSIFADDR: { struct ifaddr *ifa = (struct ifaddr *)data; @@ -1746,9 +1773,8 @@ epic_init_rings(sc) } desc->bufaddr = vtophys( mtod(buf->mbuf,caddr_t) ); - desc->buflength = ETHER_MAX_FRAME_LEN; - desc->status = 0x8000; /* Give to EPIC */ - + desc->buflength = MCLBYTES; /* Max RX buffer length */ + desc->status = 0x8000; /* Set owner bit to NIC */ } for (i = 0; i < TX_RING_SIZE; i++) { diff --git a/sys/pci/if_txvar.h b/sys/pci/if_txvar.h index a9ec762..7a5c82b 100644 --- a/sys/pci/if_txvar.h +++ b/sys/pci/if_txvar.h @@ -50,6 +50,8 @@ #define RX_RING_MASK (RX_RING_SIZE - 1) #define ETHER_MAX_FRAME_LEN (ETHER_MAX_LEN + ETHER_CRC_LEN) +#define EPIC_MAX_MTU 1600 /* This is experiment-derived value */ + /* PCI aux configuration registers */ #if defined(__FreeBSD__) #define PCIR_BASEIO (PCIR_MAPS + 0x0) /* Base IO Address */ |