On Sat, Sep 26, 2015 at 03:37:22PM +0200, Stefan Sperling wrote: > This diff fixes the issue for me.
Same diff, + my uncommitted mac context diff from http://marc.info/?l=openbsd-tech&m=144294310002198&w=2 Also adds a tweak to the ioctl handler which finally fixes ifconfig iwm0 lladdr random This depends on the etheranyaddr changes of the bsd.rd fix diff. ok? Index: dev/pci/if_iwm.c =================================================================== RCS file: /cvs/src/sys/dev/pci/if_iwm.c,v retrieving revision 1.49 diff -u -p -r1.49 if_iwm.c --- dev/pci/if_iwm.c 26 Sep 2015 10:52:09 -0000 1.49 +++ dev/pci/if_iwm.c 26 Sep 2015 15:06:42 -0000 @@ -2803,8 +2803,10 @@ iwm_run_init_mvm_ucode(struct iwm_softc printf("%s: failed to read nvm\n", DEVNAME(sc)); return error; } - memcpy(&sc->sc_ic.ic_myaddr, - &sc->sc_nvm.hw_addr, ETHER_ADDR_LEN); + + if (IEEE80211_ADDR_EQ(etheranyaddr, sc->sc_ic.ic_myaddr)) + IEEE80211_ADDR_COPY(sc->sc_ic.ic_myaddr, + sc->sc_nvm.hw_addr); sc->sc_scan_cmd_len = sizeof(struct iwm_scan_cmd) + sc->sc_capa_max_probe_len @@ -4634,7 +4636,8 @@ iwm_mvm_ack_rates(struct iwm_softc *sc, uint8_t ofdm = 0; int i; - if (IEEE80211_IS_CHAN_2GHZ(ni->ni_chan)) { + if (ni->ni_chan == IEEE80211_CHAN_ANYC || + IEEE80211_IS_CHAN_2GHZ(ni->ni_chan)) { for (i = 0; i <= IWM_LAST_CCK_RATE; i++) { cck |= (1 << i); if (lowest_present_cck > i) @@ -4998,11 +5001,6 @@ iwm_auth(struct iwm_softc *sc) if (error) return error; - if ((error = iwm_mvm_mac_ctxt_add(sc, in)) != 0) { - DPRINTF(("%s: failed to add MAC\n", DEVNAME(sc))); - return error; - } - if ((error = iwm_mvm_phy_ctxt_changed(sc, &sc->sc_phyctxt[0], in->in_ni.ni_chan, 1, 1)) != 0) { DPRINTF(("%s: failed add phy ctxt\n", DEVNAME(sc))); @@ -5455,6 +5453,7 @@ int iwm_init_hw(struct iwm_softc *sc) { struct ieee80211com *ic = &sc->sc_ic; + struct iwm_node *in = (struct iwm_node *)ic->ic_bss; int error, i, qid; if ((error = iwm_preinit(sc)) != 0) @@ -5518,6 +5517,12 @@ iwm_init_hw(struct iwm_softc *sc) iwm_enable_txq(sc, qid, qid); } + /* Add the MAC context. */ + if ((error = iwm_mvm_mac_ctxt_add(sc, in)) != 0) { + printf("%s: failed to add MAC\n", DEVNAME(sc)); + goto error; + } + return 0; error: @@ -5754,6 +5759,11 @@ iwm_ioctl(struct ifnet *ifp, u_long cmd, error = 0; break; + case SIOCSIFLLADDR: + IEEE80211_ADDR_COPY(sc->sc_ic.ic_myaddr, + ((struct arpcom *)ifp)->ac_enaddr); + break; + default: error = ieee80211_ioctl(ifp, cmd, data); } @@ -6370,9 +6380,14 @@ iwm_preinit(struct iwm_softc *sc) memset(&ic->ic_sup_rates[IEEE80211_MODE_11A], 0, sizeof(ic->ic_sup_rates[IEEE80211_MODE_11A])); - /* Reattach net80211 so MAC address and channel map are picked up. */ - ieee80211_ifdetach(ifp); - ieee80211_ifattach(ifp); + /* Configure channel information obtained from firmware. */ + ieee80211_channel_init(ifp); + + /* Configure MAC address. */ + error = if_setlladdr(ifp, ic->ic_myaddr); + if (error) + printf("%s: could not set MAC address (error %d)\n", + DEVNAME(sc), error); ic->ic_node_alloc = iwm_node_alloc; Index: net/if.c =================================================================== RCS file: /cvs/src/sys/net/if.c,v retrieving revision 1.380 diff -u -p -r1.380 if.c --- net/if.c 13 Sep 2015 18:15:03 -0000 1.380 +++ net/if.c 26 Sep 2015 13:41:27 -0000 @@ -1568,6 +1568,22 @@ if_put(struct ifnet *ifp) atomic_dec_int(&ifp->if_refcnt); } +int +if_setlladdr(struct ifnet *ifp, caddr_t lladdr) +{ + struct sockaddr_dl *sdl; + + sdl = (struct sockaddr_dl *)ifp->if_sadl; + if (sdl == NULL) + return (EINVAL); + + bcopy(lladdr, (caddr_t)((struct arpcom *)ifp)->ac_enaddr, + ETHER_ADDR_LEN); + bcopy(lladdr, LLADDR(sdl), ETHER_ADDR_LEN); + + return (0); +} + /* * Interface ioctls. */ @@ -1969,11 +1985,7 @@ ifioctl(struct socket *so, u_long cmd, c case IFT_CARP: case IFT_XETHER: case IFT_ISO88025: - bcopy((caddr_t)ifr->ifr_addr.sa_data, - (caddr_t)((struct arpcom *)ifp)->ac_enaddr, - ETHER_ADDR_LEN); - bcopy((caddr_t)ifr->ifr_addr.sa_data, - LLADDR(sdl), ETHER_ADDR_LEN); + if_setlladdr(ifp, (caddr_t)ifr->ifr_addr.sa_data); error = (*ifp->if_ioctl)(ifp, cmd, data); if (error == ENOTTY) error = 0; Index: net/if.h =================================================================== RCS file: /cvs/src/sys/net/if.h,v retrieving revision 1.167 diff -u -p -r1.167 if.h --- net/if.h 11 Sep 2015 13:02:28 -0000 1.167 +++ net/if.h 26 Sep 2015 13:41:27 -0000 @@ -469,6 +469,7 @@ void ifnewlladdr(struct ifnet *); void if_congestion(void); int if_congested(void); __dead void unhandled_af(int); +int if_setlladdr(struct ifnet *, caddr_t); #endif /* _KERNEL */ Index: net/if_ethersubr.c =================================================================== RCS file: /cvs/src/sys/net/if_ethersubr.c,v retrieving revision 1.226 diff -u -p -r1.226 if_ethersubr.c --- net/if_ethersubr.c 17 Sep 2015 04:53:27 -0000 1.226 +++ net/if_ethersubr.c 26 Sep 2015 13:41:28 -0000 @@ -121,8 +121,10 @@ didn't get a copy, you may request one f #include <netmpls/mpls.h> #endif /* MPLS */ -u_char etherbroadcastaddr[ETHER_ADDR_LEN] = +u_int8_t etherbroadcastaddr[ETHER_ADDR_LEN] = { 0xff, 0xff, 0xff, 0xff, 0xff, 0xff }; +u_int8_t etheranyaddr[ETHER_ADDR_LEN] = + { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 }; #define senderr(e) { error = (e); goto bad;} int Index: net80211/ieee80211.c =================================================================== RCS file: /cvs/src/sys/net80211/ieee80211.c,v retrieving revision 1.45 diff -u -p -r1.45 ieee80211.c --- net80211/ieee80211.c 11 Sep 2015 13:02:28 -0000 1.45 +++ net80211/ieee80211.c 26 Sep 2015 13:41:28 -0000 @@ -72,24 +72,12 @@ void ieee80211_setbasicrates(struct ieee int ieee80211_findrate(struct ieee80211com *, enum ieee80211_phymode, int); void -ieee80211_ifattach(struct ifnet *ifp) +ieee80211_channel_init(struct ifnet *ifp) { struct ieee80211com *ic = (void *)ifp; struct ieee80211_channel *c; int i; - memcpy(((struct arpcom *)ifp)->ac_enaddr, ic->ic_myaddr, - ETHER_ADDR_LEN); - ether_ifattach(ifp); - - ifp->if_output = ieee80211_output; - -#if NBPFILTER > 0 - bpfattach(&ic->ic_rawbpf, ifp, DLT_IEEE802_11, - sizeof(struct ieee80211_frame_addr4)); -#endif - ieee80211_crypto_attach(ifp); - /* * Fill in 802.11 available channel set, mark * all available channels as active, and pick @@ -130,6 +118,26 @@ ieee80211_ifattach(struct ifnet *ifp) ic->ic_curmode = IEEE80211_MODE_AUTO; ic->ic_des_chan = IEEE80211_CHAN_ANYC; /* any channel is ok */ ic->ic_scan_lock = IEEE80211_SCAN_UNLOCKED; +} + +void +ieee80211_ifattach(struct ifnet *ifp) +{ + struct ieee80211com *ic = (void *)ifp; + + memcpy(((struct arpcom *)ifp)->ac_enaddr, ic->ic_myaddr, + ETHER_ADDR_LEN); + ether_ifattach(ifp); + + ifp->if_output = ieee80211_output; + +#if NBPFILTER > 0 + bpfattach(&ic->ic_rawbpf, ifp, DLT_IEEE802_11, + sizeof(struct ieee80211_frame_addr4)); +#endif + ieee80211_crypto_attach(ifp); + + ieee80211_channel_init(ifp); /* IEEE 802.11 defines a MTU >= 2290 */ ifp->if_capabilities |= IFCAP_VLAN_MTU; Index: net80211/ieee80211_var.h =================================================================== RCS file: /cvs/src/sys/net80211/ieee80211_var.h,v retrieving revision 1.63 diff -u -p -r1.63 ieee80211_var.h --- net80211/ieee80211_var.h 11 Sep 2015 13:02:28 -0000 1.63 +++ net80211/ieee80211_var.h 26 Sep 2015 13:41:28 -0000 @@ -380,6 +380,7 @@ extern struct ieee80211com_head ieee8021 void ieee80211_ifattach(struct ifnet *); void ieee80211_ifdetach(struct ifnet *); +void ieee80211_channel_init(struct ifnet *); void ieee80211_media_init(struct ifnet *, ifm_change_cb_t, ifm_stat_cb_t); int ieee80211_media_change(struct ifnet *); void ieee80211_media_status(struct ifnet *, struct ifmediareq *); Index: netinet/if_ether.h =================================================================== RCS file: /cvs/src/sys/netinet/if_ether.h,v retrieving revision 1.59 diff -u -p -r1.59 if_ether.h --- netinet/if_ether.h 13 Sep 2015 10:42:32 -0000 1.59 +++ netinet/if_ether.h 26 Sep 2015 13:41:28 -0000 @@ -186,6 +186,7 @@ struct sockaddr_inarp { #ifdef _KERNEL extern u_int8_t etherbroadcastaddr[ETHER_ADDR_LEN]; +extern u_int8_t etheranyaddr[ETHER_ADDR_LEN]; extern u_int8_t ether_ipmulticast_min[ETHER_ADDR_LEN]; extern u_int8_t ether_ipmulticast_max[ETHER_ADDR_LEN]; extern struct niqueue arpintrq;