void smsc_setmulti(struct smsc_softc *sc) { struct ifnet *ifp = &sc->sc_ec.ec_if; struct ether_multi *enm; struct ether_multistep step; uint32_t hashtbl[2] = { 0, 0 }; uint32_t hash; if (sc->sc_dying) return; if (ifp->if_flags & (IFF_ALLMULTI | IFF_PROMISC)) { allmulti: smsc_dbg_printf(sc, "receive all multicast enabled\n"); sc->sc_mac_csr |= SMSC_MAC_CSR_MCPAS; sc->sc_mac_csr &= ~SMSC_MAC_CSR_HPFILT; smsc_write_reg(sc, SMSC_MAC_CSR, sc->sc_mac_csr); return; } else { sc->sc_mac_csr |= SMSC_MAC_CSR_HPFILT; sc->sc_mac_csr &= ~(SMSC_MAC_CSR_PRMS | SMSC_MAC_CSR_MCPAS); } ETHER_FIRST_MULTI(step, &sc->sc_ec, enm); while (enm != NULL) { if (memcmp(enm->enm_addrlo, enm->enm_addrhi, ETHER_ADDR_LEN) != 0) goto allmulti; hash = smsc_hash(enm->enm_addrlo); hashtbl[hash >> 5] |= 1 << (hash & 0x1F); ETHER_NEXT_MULTI(step, enm); } /* Debug */ if (sc->sc_mac_csr & SMSC_MAC_CSR_HPFILT) { smsc_dbg_printf(sc, "receive select group of macs\n"); } else { smsc_dbg_printf(sc, "receive own packets only\n"); } /* Write the hash table and mac control registers */ ifp->if_flags &= ~IFF_ALLMULTI; smsc_write_reg(sc, SMSC_HASHH, hashtbl[1]); smsc_write_reg(sc, SMSC_HASHL, hashtbl[0]); smsc_write_reg(sc, SMSC_MAC_CSR, sc->sc_mac_csr); }
void smsc_iff(struct smsc_softc *sc) { struct ifnet *ifp = &sc->sc_ac.ac_if; struct arpcom *ac = &sc->sc_ac; struct ether_multi *enm; struct ether_multistep step; uint32_t hashtbl[2] = { 0, 0 }; uint32_t hash; if (usbd_is_dying(sc->sc_udev)) return; sc->sc_mac_csr &= ~(SMSC_MAC_CSR_HPFILT | SMSC_MAC_CSR_MCPAS | SMSC_MAC_CSR_PRMS); ifp->if_flags &= ~IFF_ALLMULTI; if (ifp->if_flags & IFF_PROMISC || ac->ac_multirangecnt > 0) { ifp->if_flags |= IFF_ALLMULTI; sc->sc_mac_csr |= SMSC_MAC_CSR_MCPAS; if (ifp->if_flags & IFF_PROMISC) sc->sc_mac_csr |= SMSC_MAC_CSR_PRMS; } else { sc->sc_mac_csr |= SMSC_MAC_CSR_HPFILT; ETHER_FIRST_MULTI(step, ac, enm); while (enm != NULL) { hash = smsc_hash(enm->enm_addrlo); hashtbl[hash >> 5] |= 1 << (hash & 0x1F); ETHER_NEXT_MULTI(step, enm); } } /* Debug */ if (sc->sc_mac_csr & SMSC_MAC_CSR_MCPAS) smsc_dbg_printf(sc, "receive all multicast enabled\n"); else if (sc->sc_mac_csr & SMSC_MAC_CSR_HPFILT) smsc_dbg_printf(sc, "receive select group of macs\n"); /* Write the hash table and mac control registers */ smsc_write_reg(sc, SMSC_HASHH, hashtbl[1]); smsc_write_reg(sc, SMSC_HASHL, hashtbl[0]); smsc_write_reg(sc, SMSC_MAC_CSR, sc->sc_mac_csr); }