aboutsummaryrefslogtreecommitdiff
path: root/sys/dev/sis
diff options
context:
space:
mode:
authorGleb Smirnoff <glebius@FreeBSD.org>2019-10-21 18:07:44 +0000
committerGleb Smirnoff <glebius@FreeBSD.org>2019-10-21 18:07:44 +0000
commit33253a3794ed611364f90d9b3fc0ce0589697a23 (patch)
tree0c1b2cf596d8c9a391d9b9011e75353c82d3a737 /sys/dev/sis
parent9c0d67282381cb4fb4ddae9a11801367795ed442 (diff)
downloadsrc-33253a3794ed611364f90d9b3fc0ce0589697a23.tar.gz
src-33253a3794ed611364f90d9b3fc0ce0589697a23.zip
Convert to if_foreach_llmaddr() KPI.
Notes
Notes: svn path=/head/; revision=353826
Diffstat (limited to 'sys/dev/sis')
-rw-r--r--sys/dev/sis/if_sis.c82
1 files changed, 45 insertions, 37 deletions
diff --git a/sys/dev/sis/if_sis.c b/sys/dev/sis/if_sis.c
index 017033488565..b4cc9e38a653 100644
--- a/sys/dev/sis/if_sis.c
+++ b/sys/dev/sis/if_sis.c
@@ -694,13 +694,29 @@ sis_rxfilter(struct sis_softc *sc)
sis_rxfilter_sis(sc);
}
+static u_int
+sis_write_maddr(void *arg, struct sockaddr_dl *sdl, u_int cnt)
+{
+ struct sis_softc *sc = arg;
+ uint32_t h;
+ int bit, index;
+
+ h = sis_mchash(sc, LLADDR(sdl));
+ index = h >> 3;
+ bit = h & 0x1F;
+ CSR_WRITE_4(sc, SIS_RXFILT_CTL, NS_FILTADDR_FMEM_LO + index);
+ if (bit > 0xF)
+ bit -= 0x10;
+ SIS_SETBIT(sc, SIS_RXFILT_DATA, (1 << bit));
+
+ return (1);
+}
+
static void
sis_rxfilter_ns(struct sis_softc *sc)
{
struct ifnet *ifp;
- struct ifmultiaddr *ifma;
- uint32_t h, i, filter;
- int bit, index;
+ uint32_t i, filter;
ifp = sc->sis_ifp;
filter = CSR_READ_4(sc, SIS_RXFILT_CTL);
@@ -743,21 +759,7 @@ sis_rxfilter_ns(struct sis_softc *sc)
CSR_WRITE_4(sc, SIS_RXFILT_DATA, 0);
}
- if_maddr_rlock(ifp);
- CK_STAILQ_FOREACH(ifma, &ifp->if_multiaddrs, ifma_link) {
- if (ifma->ifma_addr->sa_family != AF_LINK)
- continue;
- h = sis_mchash(sc,
- LLADDR((struct sockaddr_dl *)ifma->ifma_addr));
- index = h >> 3;
- bit = h & 0x1F;
- CSR_WRITE_4(sc, SIS_RXFILT_CTL, NS_FILTADDR_FMEM_LO +
- index);
- if (bit > 0xF)
- bit -= 0x10;
- SIS_SETBIT(sc, SIS_RXFILT_DATA, (1 << bit));
- }
- if_maddr_runlock(ifp);
+ if_foreach_llmaddr(ifp, sis_write_maddr, sc);
}
/* Turn the receive filter on */
@@ -765,13 +767,29 @@ sis_rxfilter_ns(struct sis_softc *sc)
CSR_READ_4(sc, SIS_RXFILT_CTL);
}
+struct sis_hash_maddr_ctx {
+ struct sis_softc *sc;
+ uint16_t hashes[16];
+};
+
+static u_int
+sis_hash_maddr(void *arg, struct sockaddr_dl *sdl, u_int cnt)
+{
+ struct sis_hash_maddr_ctx *ctx = arg;
+ uint32_t h;
+
+ h = sis_mchash(ctx->sc, LLADDR(sdl));
+ ctx->hashes[h >> 4] |= 1 << (h & 0xf);
+
+ return (1);
+}
+
static void
sis_rxfilter_sis(struct sis_softc *sc)
{
struct ifnet *ifp;
- struct ifmultiaddr *ifma;
- uint32_t filter, h, i, n;
- uint16_t hashes[16];
+ struct sis_hash_maddr_ctx ctx;
+ uint32_t filter, i, n;
ifp = sc->sis_ifp;
@@ -796,31 +814,21 @@ sis_rxfilter_sis(struct sis_softc *sc)
if (ifp->if_flags & IFF_PROMISC)
filter |= SIS_RXFILTCTL_ALLPHYS;
for (i = 0; i < n; i++)
- hashes[i] = ~0;
+ ctx.hashes[i] = ~0;
} else {
for (i = 0; i < n; i++)
- hashes[i] = 0;
- i = 0;
- if_maddr_rlock(ifp);
- CK_STAILQ_FOREACH(ifma, &ifp->if_multiaddrs, ifma_link) {
- if (ifma->ifma_addr->sa_family != AF_LINK)
- continue;
- h = sis_mchash(sc,
- LLADDR((struct sockaddr_dl *)ifma->ifma_addr));
- hashes[h >> 4] |= 1 << (h & 0xf);
- i++;
- }
- if_maddr_runlock(ifp);
- if (i > n) {
+ ctx.hashes[i] = 0;
+ ctx.sc = sc;
+ if (if_foreach_llmaddr(ifp, sis_hash_maddr, &ctx) > n) {
filter |= SIS_RXFILTCTL_ALLMULTI;
for (i = 0; i < n; i++)
- hashes[i] = ~0;
+ ctx.hashes[i] = ~0;
}
}
for (i = 0; i < n; i++) {
CSR_WRITE_4(sc, SIS_RXFILT_CTL, (4 + i) << 16);
- CSR_WRITE_4(sc, SIS_RXFILT_DATA, hashes[i]);
+ CSR_WRITE_4(sc, SIS_RXFILT_DATA, ctx.hashes[i]);
}
/* Turn the receive filter on */