On Sun, Mar 22, 2015 at 09:16:08AM +0100, Stefan Sperling wrote: > On Sun, Mar 22, 2015 at 01:45:45PM +1100, Jonathan Gray wrote: > > Try the following. > > This diff re-introduces an unrelated problem fixed in r1.7. > > Interface attachment is moved back to the attach-hook, and the driver > tries to load the firmware from disk before creating an interface. > > If the firmare image is not present at boot, no interface is created. > After installing the firmware with fw_update (which succeeds because > it looks for "iwm" in dmesg not ifconfig) there is no way to recover > the interface without a reboot because 'ifconfig iwm0' doesn't work. > > # ifconfig iwm0 down up > ifconfig: SIOCGIFFLAGS: Device not configured > # ifconfig iwm0 > iwm0: no such interface > > The only other driver I'm aware of that does this is athn(4) on USB. > However, in that case the USB device can simply be re-plugged to force > the entire attach procedure to run again.
Plenty of drivers do the interface attach in the hook. zyd(4), otus(4), atu(4), upgt(4), kue(4), ral(4), bnx(4), myx(4), txp(4)... I can't think of anything that tries to detach/reattach the interface so it can be used to load firmware on interface up. If the mac address and the supported 802.11 modes depend on having the firmware loaded, is it really worth adding a interface that allows invalid parameters to be set? > > > diff --git sys/dev/pci/if_iwm.c sys/dev/pci/if_iwm.c > > index 6072e6a..3bec032 100644 > > --- sys/dev/pci/if_iwm.c > > +++ sys/dev/pci/if_iwm.c > > @@ -6410,8 +6410,38 @@ iwm_preinit(struct iwm_softc *sc) > > IWM_UCODE_API(sc->sc_fwver), > > ether_sprintf(sc->sc_nvm.hw_addr)); > > > > - /* Reattach net80211 so MAC address and channel map are picked up. */ > > - ieee80211_ifdetach(ifp); > > + ic->ic_phytype = IEEE80211_T_OFDM; /* not only, but not used */ > > + ic->ic_opmode = IEEE80211_M_STA; /* default to BSS mode */ > > + ic->ic_state = IEEE80211_S_INIT; > > + > > + /* Set device capabilities. */ > > + ic->ic_caps = > > + IEEE80211_C_WEP | /* WEP */ > > + IEEE80211_C_RSN | /* WPA/RSN */ > > + IEEE80211_C_SCANALL | /* device scans all channels at once */ > > + IEEE80211_C_SHSLOT | /* short slot time supported */ > > + IEEE80211_C_SHPREAMBLE; /* short preamble supported */ > > + > > + if (sc->sc_nvm.sku_cap_band_52GHz_enable) > > + ic->ic_sup_rates[IEEE80211_MODE_11A] = > > ieee80211_std_rateset_11a; > > + ic->ic_sup_rates[IEEE80211_MODE_11B] = ieee80211_std_rateset_11b; > > + ic->ic_sup_rates[IEEE80211_MODE_11G] = ieee80211_std_rateset_11g; > > + > > + /* IBSS channel undefined for now. */ > > + ic->ic_ibss_chan = &ic->ic_channels[1]; > > + > > + /* Max RSSI */ > > + ic->ic_max_rssi = IWM_MAX_DBM - IWM_MIN_DBM; > > + > > + ifp->if_softc = sc; > > + ifp->if_flags = IFF_BROADCAST | IFF_SIMPLEX | IFF_MULTICAST; > > + ifp->if_ioctl = iwm_ioctl; > > + ifp->if_start = iwm_start; > > + ifp->if_watchdog = iwm_watchdog; > > + IFQ_SET_READY(&ifp->if_snd); > > + memcpy(ifp->if_xname, DEVNAME(sc), IFNAMSIZ); > > + > > + if_attach(ifp); > > ieee80211_ifattach(ifp); > > > > ic->ic_node_alloc = iwm_node_alloc; > > @@ -6421,6 +6451,12 @@ iwm_preinit(struct iwm_softc *sc) > > ic->ic_newstate = iwm_newstate; > > ieee80211_media_init(ifp, iwm_media_change, ieee80211_media_status); > > > > +#if NBPFILTER > 0 > > + iwm_radiotap_attach(sc); > > +#endif > > + timeout_set(&sc->sc_calib_to, iwm_calib_timeout, sc); > > + task_set(&sc->init_task, iwm_init_task, sc); > > + > > return 0; > > } > > > > @@ -6441,8 +6477,6 @@ iwm_attach(struct device *parent, struct device > > *self, void *aux) > > struct pci_attach_args *pa = aux; > > pci_intr_handle_t ih; > > pcireg_t reg, memtype; > > - struct ieee80211com *ic = &sc->sc_ic; > > - struct ifnet *ifp = &ic->ic_if; > > const char *intrstr; > > int error; > > int txq_i, i; > > @@ -6592,22 +6626,6 @@ iwm_attach(struct device *parent, struct device > > *self, void *aux) > > /* Clear pending interrupts. */ > > IWM_WRITE(sc, IWM_CSR_INT, 0xffffffff); > > > > - ic->ic_phytype = IEEE80211_T_OFDM; /* not only, but not used */ > > - ic->ic_opmode = IEEE80211_M_STA; /* default to BSS mode */ > > - ic->ic_state = IEEE80211_S_INIT; > > - > > - /* Set device capabilities. */ > > - ic->ic_caps = > > - IEEE80211_C_WEP | /* WEP */ > > - IEEE80211_C_RSN | /* WPA/RSN */ > > - IEEE80211_C_SCANALL | /* device scans all channels at once */ > > - IEEE80211_C_SHSLOT | /* short slot time supported */ > > - IEEE80211_C_SHPREAMBLE; /* short preamble supported */ > > - > > - ic->ic_sup_rates[IEEE80211_MODE_11A] = ieee80211_std_rateset_11a; > > - ic->ic_sup_rates[IEEE80211_MODE_11B] = ieee80211_std_rateset_11b; > > - ic->ic_sup_rates[IEEE80211_MODE_11G] = ieee80211_std_rateset_11g; > > - > > for (i = 0; i < nitems(sc->sc_phyctxt); i++) { > > sc->sc_phyctxt[i].id = i; > > } > > @@ -6615,30 +6633,6 @@ iwm_attach(struct device *parent, struct device > > *self, void *aux) > > sc->sc_amrr.amrr_min_success_threshold = 1; > > sc->sc_amrr.amrr_max_success_threshold = 15; > > > > - /* IBSS channel undefined for now. */ > > - ic->ic_ibss_chan = &ic->ic_channels[1]; > > - > > - /* Max RSSI */ > > - ic->ic_max_rssi = IWM_MAX_DBM - IWM_MIN_DBM; > > - > > - ifp->if_softc = sc; > > - ifp->if_flags = IFF_BROADCAST | IFF_SIMPLEX | IFF_MULTICAST; > > - ifp->if_ioctl = iwm_ioctl; > > - ifp->if_start = iwm_start; > > - ifp->if_watchdog = iwm_watchdog; > > - IFQ_SET_READY(&ifp->if_snd); > > - memcpy(ifp->if_xname, DEVNAME(sc), IFNAMSIZ); > > - > > - if_attach(ifp); > > - ieee80211_ifattach(ifp); > > - ieee80211_media_init(ifp, iwm_media_change, ieee80211_media_status); > > - > > -#if NBPFILTER > 0 > > - iwm_radiotap_attach(sc); > > -#endif > > - timeout_set(&sc->sc_calib_to, iwm_calib_timeout, sc); > > - task_set(&sc->init_task, iwm_init_task, sc); > > - > > /* > > * We cannot read the MAC address without loading the > > * firmware from disk. Postpone until mountroot is done.