Hi, A user has reported an issue with not having a proper promiscuous mode on reddit a while back but as of now didn't manage to test the diff.
If somebody is running OpenBSD on Hyper-V, please test the diff below and see if there are any regressions (like increased CPU load) without running tcpdump and then try running 'tcpdump -nvvi hvn0' and see if that works: one indicator is the PROMISC flag in the ifconfig output that should get set when tcpdump is started and cleared once it's finished. I'm not certain if Hyper-V will allow you to sniff a whole lot of traffic on the virtual switch, however, one of the goals here is to instruct RNDIS to enter "all multicast capture" mode when one or more multicast addresses are configured. Therefore one of the goals is to attempt to support CARP operation on the virtual switch. commit 6e6b001dae79505e3e0fbca663c31f9eb6da285b Author: Mike Belopuhov <m...@belopuhov.com> Date: Sun Mar 11 13:38:21 2018 +0100 Add support for promisc mode diff --git sys/dev/pv/if_hvn.c sys/dev/pv/if_hvn.c index 3ca35165565..6d5e919b01c 100644 --- sys/dev/pv/if_hvn.c +++ sys/dev/pv/if_hvn.c @@ -134,11 +134,10 @@ struct hvn_softc { bus_dma_tag_t sc_dmat; struct arpcom sc_ac; struct ifmedia sc_media; int sc_link_state; - int sc_promisc; /* NVS protocol */ int sc_proto; uint32_t sc_nvstid; uint8_t sc_nvsrsp[HVN_NVS_MSGSIZE]; @@ -208,11 +207,10 @@ void hvn_rxeof(struct hvn_softc *, caddr_t, uint32_t, struct mbuf_list *); void hvn_rndis_complete(struct hvn_softc *, caddr_t, uint32_t); int hvn_rndis_output(struct hvn_softc *, struct hvn_tx_desc *); void hvn_rndis_status(struct hvn_softc *, caddr_t, uint32_t); int hvn_rndis_query(struct hvn_softc *, uint32_t, void *, size_t *); int hvn_rndis_set(struct hvn_softc *, uint32_t, void *, size_t); -int hvn_rndis_open(struct hvn_softc *); int hvn_rndis_close(struct hvn_softc *); void hvn_rndis_detach(struct hvn_softc *); struct cfdriver hvn_cd = { NULL, "hvn", DV_IFNET @@ -401,26 +399,44 @@ hvn_link_status(struct hvn_softc *sc) } int hvn_iff(struct hvn_softc *sc) { - /* XXX */ - sc->sc_promisc = 0; + struct ifnet *ifp = &sc->sc_ac.ac_if; + uint32_t filter = 0; + int rv; - return (0); + ifp->if_flags &= ~IFF_ALLMULTI; + + if ((ifp->if_flags & IFF_PROMISC) || sc->sc_ac.ac_multirangecnt > 0) { + ifp->if_flags |= IFF_ALLMULTI; + filter = NDIS_PACKET_TYPE_PROMISCUOUS; + } else { + filter = NDIS_PACKET_TYPE_BROADCAST | + NDIS_PACKET_TYPE_DIRECTED; + if (sc->sc_ac.ac_multicnt > 0) { + ifp->if_flags |= IFF_ALLMULTI; + filter |= NDIS_PACKET_TYPE_ALL_MULTICAST; + } + } + + rv = hvn_rndis_set(sc, OID_GEN_CURRENT_PACKET_FILTER, + &filter, sizeof(filter)); + if (rv) + DPRINTF("%s: failed to set RNDIS filter to %#x\n", + sc->sc_dev.dv_xname, filter); + return (rv); } void hvn_init(struct hvn_softc *sc) { struct ifnet *ifp = &sc->sc_ac.ac_if; hvn_stop(sc); - hvn_iff(sc); - - if (hvn_rndis_open(sc) == 0) { + if (hvn_iff(sc) == 0) { ifp->if_flags |= IFF_RUNNING; ifq_clr_oactive(&ifp->if_snd); } } @@ -1723,31 +1739,10 @@ hvn_rndis_set(struct hvn_softc *sc, uint32_t oid, void *data, size_t length) hvn_free_cmd(sc, rc); return (rv); } -int -hvn_rndis_open(struct hvn_softc *sc) -{ - uint32_t filter; - int rv; - - if (sc->sc_promisc) - filter = NDIS_PACKET_TYPE_PROMISCUOUS; - else - filter = NDIS_PACKET_TYPE_BROADCAST | - NDIS_PACKET_TYPE_ALL_MULTICAST | - NDIS_PACKET_TYPE_DIRECTED; - - rv = hvn_rndis_set(sc, OID_GEN_CURRENT_PACKET_FILTER, - &filter, sizeof(filter)); - if (rv) - DPRINTF("%s: failed to set RNDIS filter to %#x\n", - sc->sc_dev.dv_xname, filter); - return (rv); -} - int hvn_rndis_close(struct hvn_softc *sc) { uint32_t filter = 0; int rv;