if_lagg.c (172020) | if_lagg.c (172554) |
---|---|
1/* $OpenBSD: if_trunk.c,v 1.30 2007/01/31 06:20:19 reyk Exp $ */ 2 3/* 4 * Copyright (c) 2005, 2006 Reyk Floeter <reyk@openbsd.org> 5 * 6 * Permission to use, copy, modify, and distribute this software for any 7 * purpose with or without fee is hereby granted, provided that the above 8 * copyright notice and this permission notice appear in all copies. 9 * 10 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 11 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 12 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 13 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 14 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 15 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 16 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 17 */ 18 19#include <sys/cdefs.h> | 1/* $OpenBSD: if_trunk.c,v 1.30 2007/01/31 06:20:19 reyk Exp $ */ 2 3/* 4 * Copyright (c) 2005, 2006 Reyk Floeter <reyk@openbsd.org> 5 * 6 * Permission to use, copy, modify, and distribute this software for any 7 * purpose with or without fee is hereby granted, provided that the above 8 * copyright notice and this permission notice appear in all copies. 9 * 10 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 11 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 12 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 13 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 14 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 15 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 16 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 17 */ 18 19#include <sys/cdefs.h> |
20__FBSDID("$FreeBSD: head/sys/net/if_lagg.c 172020 2007-08-30 19:12:10Z thompsa $"); | 20__FBSDID("$FreeBSD: head/sys/net/if_lagg.c 172554 2007-10-12 03:03:16Z thompsa $"); |
21 22#include "opt_inet.h" 23#include "opt_inet6.h" 24 25#include <sys/param.h> 26#include <sys/kernel.h> 27#include <sys/malloc.h> 28#include <sys/mbuf.h> --- 81 unchanged lines hidden (view full) --- 110 struct lagg_port *); 111static const void *lagg_gethdr(struct mbuf *, u_int, u_int, void *); 112 113IFC_SIMPLE_DECLARE(lagg, 0); 114 115/* Simple round robin */ 116static int lagg_rr_attach(struct lagg_softc *); 117static int lagg_rr_detach(struct lagg_softc *); | 21 22#include "opt_inet.h" 23#include "opt_inet6.h" 24 25#include <sys/param.h> 26#include <sys/kernel.h> 27#include <sys/malloc.h> 28#include <sys/mbuf.h> --- 81 unchanged lines hidden (view full) --- 110 struct lagg_port *); 111static const void *lagg_gethdr(struct mbuf *, u_int, u_int, void *); 112 113IFC_SIMPLE_DECLARE(lagg, 0); 114 115/* Simple round robin */ 116static int lagg_rr_attach(struct lagg_softc *); 117static int lagg_rr_detach(struct lagg_softc *); |
118static void lagg_rr_port_destroy(struct lagg_port *); | |
119static int lagg_rr_start(struct lagg_softc *, struct mbuf *); 120static struct mbuf *lagg_rr_input(struct lagg_softc *, struct lagg_port *, 121 struct mbuf *); 122 123/* Active failover */ 124static int lagg_fail_attach(struct lagg_softc *); 125static int lagg_fail_detach(struct lagg_softc *); 126static int lagg_fail_start(struct lagg_softc *, struct mbuf *); --- 141 unchanged lines hidden (view full) --- 268 269 lagg_stop(sc); 270 ifp->if_flags &= ~IFF_UP; 271 272 /* Shutdown and remove lagg ports */ 273 while ((lp = SLIST_FIRST(&sc->sc_ports)) != NULL) 274 lagg_port_destroy(lp, 1); 275 /* Unhook the aggregation protocol */ | 118static int lagg_rr_start(struct lagg_softc *, struct mbuf *); 119static struct mbuf *lagg_rr_input(struct lagg_softc *, struct lagg_port *, 120 struct mbuf *); 121 122/* Active failover */ 123static int lagg_fail_attach(struct lagg_softc *); 124static int lagg_fail_detach(struct lagg_softc *); 125static int lagg_fail_start(struct lagg_softc *, struct mbuf *); --- 141 unchanged lines hidden (view full) --- 267 268 lagg_stop(sc); 269 ifp->if_flags &= ~IFF_UP; 270 271 /* Shutdown and remove lagg ports */ 272 while ((lp = SLIST_FIRST(&sc->sc_ports)) != NULL) 273 lagg_port_destroy(lp, 1); 274 /* Unhook the aggregation protocol */ |
276 if (sc->sc_detach != NULL) 277 (*sc->sc_detach)(sc); | 275 (*sc->sc_detach)(sc); |
278 279 LAGG_WUNLOCK(sc); 280 281 ifmedia_removeall(&sc->sc_media); 282 ether_ifdetach(ifp); 283 if_free_type(ifp, IFT_ETHER); 284 285 mtx_lock(&lagg_list_mtx); --- 833 unchanged lines hidden (view full) --- 1119 1120 if (sc->sc_proto != LAGG_PROTO_NONE) 1121 error = (*sc->sc_start)(sc, m); 1122 else 1123 m_freem(m); 1124 1125 if (error == 0) 1126 ifp->if_opackets++; | 276 277 LAGG_WUNLOCK(sc); 278 279 ifmedia_removeall(&sc->sc_media); 280 ether_ifdetach(ifp); 281 if_free_type(ifp, IFT_ETHER); 282 283 mtx_lock(&lagg_list_mtx); --- 833 unchanged lines hidden (view full) --- 1117 1118 if (sc->sc_proto != LAGG_PROTO_NONE) 1119 error = (*sc->sc_start)(sc, m); 1120 else 1121 m_freem(m); 1122 1123 if (error == 0) 1124 ifp->if_opackets++; |
1127 else { 1128 m_freem(m); /* sc_start failed */ | 1125 else |
1129 ifp->if_oerrors++; | 1126 ifp->if_oerrors++; |
1130 } | |
1131 } 1132 LAGG_RUNLOCK(sc); 1133 1134 return; 1135} 1136 1137static struct mbuf * 1138lagg_input(struct ifnet *ifp, struct mbuf *m) --- 202 unchanged lines hidden (view full) --- 1341} 1342 1343int 1344lagg_enqueue(struct ifnet *ifp, struct mbuf *m) 1345{ 1346 int error = 0; 1347 1348 IFQ_HANDOFF(ifp, m, error); | 1127 } 1128 LAGG_RUNLOCK(sc); 1129 1130 return; 1131} 1132 1133static struct mbuf * 1134lagg_input(struct ifnet *ifp, struct mbuf *m) --- 202 unchanged lines hidden (view full) --- 1337} 1338 1339int 1340lagg_enqueue(struct ifnet *ifp, struct mbuf *m) 1341{ 1342 int error = 0; 1343 1344 IFQ_HANDOFF(ifp, m, error); |
1345 if (error) 1346 ifp->if_oerrors++; |
|
1349 return (error); 1350} 1351 1352/* 1353 * Simple round robin aggregation 1354 */ 1355 1356static int 1357lagg_rr_attach(struct lagg_softc *sc) 1358{ | 1347 return (error); 1348} 1349 1350/* 1351 * Simple round robin aggregation 1352 */ 1353 1354static int 1355lagg_rr_attach(struct lagg_softc *sc) 1356{ |
1359 struct lagg_port *lp; 1360 | |
1361 sc->sc_detach = lagg_rr_detach; 1362 sc->sc_start = lagg_rr_start; 1363 sc->sc_input = lagg_rr_input; 1364 sc->sc_port_create = NULL; | 1357 sc->sc_detach = lagg_rr_detach; 1358 sc->sc_start = lagg_rr_start; 1359 sc->sc_input = lagg_rr_input; 1360 sc->sc_port_create = NULL; |
1365 sc->sc_port_destroy = lagg_rr_port_destroy; | |
1366 sc->sc_capabilities = IFCAP_LAGG_FULLDUPLEX; | 1361 sc->sc_capabilities = IFCAP_LAGG_FULLDUPLEX; |
1362 sc->sc_seq = 0; |
|
1367 | 1363 |
1368 lp = SLIST_FIRST(&sc->sc_ports); 1369 sc->sc_psc = (caddr_t)lp; 1370 | |
1371 return (0); 1372} 1373 1374static int 1375lagg_rr_detach(struct lagg_softc *sc) 1376{ | 1364 return (0); 1365} 1366 1367static int 1368lagg_rr_detach(struct lagg_softc *sc) 1369{ |
1377 sc->sc_psc = NULL; | |
1378 return (0); 1379} 1380 | 1370 return (0); 1371} 1372 |
1381static void 1382lagg_rr_port_destroy(struct lagg_port *lp) 1383{ 1384 struct lagg_softc *sc = lp->lp_softc; 1385 1386 if (lp == (struct lagg_port *)sc->sc_psc) 1387 sc->sc_psc = NULL; 1388} 1389 | |
1390static int 1391lagg_rr_start(struct lagg_softc *sc, struct mbuf *m) 1392{ | 1373static int 1374lagg_rr_start(struct lagg_softc *sc, struct mbuf *m) 1375{ |
1393 struct lagg_port *lp = (struct lagg_port *)sc->sc_psc, *lp_next; 1394 int error = 0; | 1376 struct lagg_port *lp; 1377 uint32_t p; |
1395 | 1378 |
1396 if (lp == NULL && (lp = lagg_link_active(sc, NULL)) == NULL) | 1379 p = atomic_fetchadd_32(&sc->sc_seq, 1); 1380 p %= sc->sc_count; 1381 lp = SLIST_FIRST(&sc->sc_ports); 1382 while (p--) 1383 lp = SLIST_NEXT(lp, lp_entries); 1384 1385 /* 1386 * Check the port's link state. This will return the next active 1387 * port if the link is down or the port is NULL. 1388 */ 1389 if ((lp = lagg_link_active(sc, lp)) == NULL) { 1390 m_freem(m); |
1397 return (ENOENT); | 1391 return (ENOENT); |
1392 } |
|
1398 1399 /* Send mbuf */ | 1393 1394 /* Send mbuf */ |
1400 error = lagg_enqueue(lp->lp_ifp, m); 1401 1402 /* Get next active port */ 1403 lp_next = lagg_link_active(sc, SLIST_NEXT(lp, lp_entries)); 1404 sc->sc_psc = (caddr_t)lp_next; 1405 1406 return (error); | 1395 return (lagg_enqueue(lp->lp_ifp, m)); |
1407} 1408 1409static struct mbuf * 1410lagg_rr_input(struct lagg_softc *sc, struct lagg_port *lp, struct mbuf *m) 1411{ 1412 struct ifnet *ifp = sc->sc_ifp; 1413 1414 /* Just pass in the packet to our lagg device */ --- 25 unchanged lines hidden (view full) --- 1440} 1441 1442static int 1443lagg_fail_start(struct lagg_softc *sc, struct mbuf *m) 1444{ 1445 struct lagg_port *lp; 1446 1447 /* Use the master port if active or the next available port */ | 1396} 1397 1398static struct mbuf * 1399lagg_rr_input(struct lagg_softc *sc, struct lagg_port *lp, struct mbuf *m) 1400{ 1401 struct ifnet *ifp = sc->sc_ifp; 1402 1403 /* Just pass in the packet to our lagg device */ --- 25 unchanged lines hidden (view full) --- 1429} 1430 1431static int 1432lagg_fail_start(struct lagg_softc *sc, struct mbuf *m) 1433{ 1434 struct lagg_port *lp; 1435 1436 /* Use the master port if active or the next available port */ |
1448 if ((lp = lagg_link_active(sc, sc->sc_primary)) == NULL) | 1437 if ((lp = lagg_link_active(sc, sc->sc_primary)) == NULL) { 1438 m_freem(m); |
1449 return (ENOENT); | 1439 return (ENOENT); |
1440 } |
|
1450 1451 /* Send mbuf */ 1452 return (lagg_enqueue(lp->lp_ifp, m)); 1453} 1454 1455static struct mbuf * 1456lagg_fail_input(struct lagg_softc *sc, struct lagg_port *lp, struct mbuf *m) 1457{ --- 100 unchanged lines hidden (view full) --- 1558lagg_lb_start(struct lagg_softc *sc, struct mbuf *m) 1559{ 1560 struct lagg_lb *lb = (struct lagg_lb *)sc->sc_psc; 1561 struct lagg_port *lp = NULL; 1562 uint32_t p = 0; 1563 int idx; 1564 1565 p = lagg_hashmbuf(m, lb->lb_key); | 1441 1442 /* Send mbuf */ 1443 return (lagg_enqueue(lp->lp_ifp, m)); 1444} 1445 1446static struct mbuf * 1447lagg_fail_input(struct lagg_softc *sc, struct lagg_port *lp, struct mbuf *m) 1448{ --- 100 unchanged lines hidden (view full) --- 1549lagg_lb_start(struct lagg_softc *sc, struct mbuf *m) 1550{ 1551 struct lagg_lb *lb = (struct lagg_lb *)sc->sc_psc; 1552 struct lagg_port *lp = NULL; 1553 uint32_t p = 0; 1554 int idx; 1555 1556 p = lagg_hashmbuf(m, lb->lb_key); |
1566 if ((idx = p % sc->sc_count) >= LAGG_MAX_PORTS) | 1557 if ((idx = p % sc->sc_count) >= LAGG_MAX_PORTS) { 1558 m_freem(m); |
1567 return (EINVAL); | 1559 return (EINVAL); |
1560 } |
|
1568 lp = lb->lb_ports[idx]; 1569 1570 /* 1571 * Check the port's link state. This will return the next active 1572 * port if the link is down or the port is NULL. 1573 */ | 1561 lp = lb->lb_ports[idx]; 1562 1563 /* 1564 * Check the port's link state. This will return the next active 1565 * port if the link is down or the port is NULL. 1566 */ |
1574 if ((lp = lagg_link_active(sc, lp)) == NULL) | 1567 if ((lp = lagg_link_active(sc, lp)) == NULL) { 1568 m_freem(m); |
1575 return (ENOENT); | 1569 return (ENOENT); |
1570 } |
|
1576 1577 /* Send mbuf */ 1578 return (lagg_enqueue(lp->lp_ifp, m)); 1579} 1580 1581static struct mbuf * 1582lagg_lb_input(struct lagg_softc *sc, struct lagg_port *lp, struct mbuf *m) 1583{ --- 69 unchanged lines hidden (view full) --- 1653} 1654 1655static int 1656lagg_lacp_start(struct lagg_softc *sc, struct mbuf *m) 1657{ 1658 struct lagg_port *lp; 1659 1660 lp = lacp_select_tx_port(sc, m); | 1571 1572 /* Send mbuf */ 1573 return (lagg_enqueue(lp->lp_ifp, m)); 1574} 1575 1576static struct mbuf * 1577lagg_lb_input(struct lagg_softc *sc, struct lagg_port *lp, struct mbuf *m) 1578{ --- 69 unchanged lines hidden (view full) --- 1648} 1649 1650static int 1651lagg_lacp_start(struct lagg_softc *sc, struct mbuf *m) 1652{ 1653 struct lagg_port *lp; 1654 1655 lp = lacp_select_tx_port(sc, m); |
1661 if (lp == NULL) | 1656 if (lp == NULL) { 1657 m_freem(m); |
1662 return (EBUSY); | 1658 return (EBUSY); |
1659 } |
|
1663 1664 /* Send mbuf */ 1665 return (lagg_enqueue(lp->lp_ifp, m)); 1666} 1667 1668static struct mbuf * 1669lagg_lacp_input(struct lagg_softc *sc, struct lagg_port *lp, struct mbuf *m) 1670{ --- 26 unchanged lines hidden --- | 1660 1661 /* Send mbuf */ 1662 return (lagg_enqueue(lp->lp_ifp, m)); 1663} 1664 1665static struct mbuf * 1666lagg_lacp_input(struct lagg_softc *sc, struct lagg_port *lp, struct mbuf *m) 1667{ --- 26 unchanged lines hidden --- |