Re: Looking for iwn testers (was: Re: add MCS support to radiotap)

2016-11-19 Thread Stefan Sperling
On Sat, Oct 29, 2016 at 01:13:47PM +0200, Stefan Sperling wrote:
> On Sat, Oct 08, 2016 at 07:34:55PM +0200, Mark Kettenis wrote:
> > > The addition might need to be tested on a 1TR1 and 2T3R setups.  I can
> > > test the latter, but I have no hardware to test the former.
> > 
> > FWIW, this seems to cause no regressions on:
> > 
> > iwn0 at pci2 dev 0 function 0 "Intel WiFi Link 5300" rev 0x00: msi, MIMO 
> > 3T3R, MoW, address 00:21:6a:13:67:82
> 
> The 1T1R devices listed in the man page are:
> 
>   Intel Centrino Wireless-N 135
>   Intel Centrino Wireless-N 105 
> 
> Does anybody have either of these devices?

Nobody seems to have these devices.
I am going to proceed soon and just hope that I won't break them.

> If so, please test the diff below during regular usage,
> and with these commands:
> 
>   ifconfig iwn0 mediaopt monitor up
>   tcpdump -n -i iwn0 -y IEEE802_11_RADIO
> 
> The expected behaviour is that tcpdump displays some frames
> (at least beacons from APs on the current channel).
> 
> Index: if_iwn.c
> ===
> RCS file: /cvs/src/sys/dev/pci/if_iwn.c,v
> retrieving revision 1.175
> diff -u -p -r1.175 if_iwn.c
> --- if_iwn.c  28 Oct 2016 10:11:22 -  1.175
> +++ if_iwn.c  29 Oct 2016 10:10:19 -
> @@ -4504,13 +4504,18 @@ iwn_config(struct iwn_softc *sc)
>   sc->rxon.ht_triple_mask = 0xff;
>   rxchain =
>   IWN_RXCHAIN_VALID(sc->rxchainmask) |
> - IWN_RXCHAIN_MIMO_COUNT(2) |
> - IWN_RXCHAIN_IDLE_COUNT(2);
> + IWN_RXCHAIN_MIMO_COUNT(sc->nrxchains) |
> + IWN_RXCHAIN_IDLE_COUNT(sc->nrxchains);
> + if (ic->ic_opmode == IEEE80211_M_MONITOR) {
> + rxchain |= IWN_RXCHAIN_FORCE_SEL(sc->rxchainmask);
> + rxchain |= IWN_RXCHAIN_FORCE_MIMO_SEL(sc->rxchainmask);
> + rxchain |= (IWN_RXCHAIN_DRIVER_FORCE | IWN_RXCHAIN_MIMO_FORCE);
> + }
>   sc->rxon.rxchain = htole16(rxchain);
>   DPRINTF(("setting configuration\n"));
> - DPRINTF(("%s: rxon chan %d flags %x cck %x ofdm %x\n", __func__,
> - sc->rxon.chan, le32toh(sc->rxon.flags), sc->rxon.cck_mask,
> - sc->rxon.ofdm_mask));
> + DPRINTF(("%s: rxon chan %d flags %x cck %x ofdm %x rxchain %x\n",
> + __func__, sc->rxon.chan, le32toh(sc->rxon.flags), sc->rxon.cck_mask,
> + sc->rxon.ofdm_mask, sc->rxon.rxchain));
>   error = iwn_cmd(sc, IWN_CMD_RXON, &sc->rxon, sc->rxonsz, 0);
>   if (error != 0) {
>   printf("%s: RXON command failed\n", sc->sc_dev.dv_xname);
> 



Looking for iwn testers (was: Re: add MCS support to radiotap)

2016-10-29 Thread Stefan Sperling
On Sat, Oct 08, 2016 at 07:34:55PM +0200, Mark Kettenis wrote:
> > The addition might need to be tested on a 1TR1 and 2T3R setups.  I can
> > test the latter, but I have no hardware to test the former.
> 
> FWIW, this seems to cause no regressions on:
> 
> iwn0 at pci2 dev 0 function 0 "Intel WiFi Link 5300" rev 0x00: msi, MIMO 
> 3T3R, MoW, address 00:21:6a:13:67:82

The 1T1R devices listed in the man page are:

  Intel Centrino Wireless-N 135
  Intel Centrino Wireless-N 105 

Does anybody have either of these devices?

If so, please test the diff below during regular usage,
and with these commands:

  ifconfig iwn0 mediaopt monitor up
  tcpdump -n -i iwn0 -y IEEE802_11_RADIO

The expected behaviour is that tcpdump displays some frames
(at least beacons from APs on the current channel).

Index: if_iwn.c
===
RCS file: /cvs/src/sys/dev/pci/if_iwn.c,v
retrieving revision 1.175
diff -u -p -r1.175 if_iwn.c
--- if_iwn.c28 Oct 2016 10:11:22 -  1.175
+++ if_iwn.c29 Oct 2016 10:10:19 -
@@ -4504,13 +4504,18 @@ iwn_config(struct iwn_softc *sc)
sc->rxon.ht_triple_mask = 0xff;
rxchain =
IWN_RXCHAIN_VALID(sc->rxchainmask) |
-   IWN_RXCHAIN_MIMO_COUNT(2) |
-   IWN_RXCHAIN_IDLE_COUNT(2);
+   IWN_RXCHAIN_MIMO_COUNT(sc->nrxchains) |
+   IWN_RXCHAIN_IDLE_COUNT(sc->nrxchains);
+   if (ic->ic_opmode == IEEE80211_M_MONITOR) {
+   rxchain |= IWN_RXCHAIN_FORCE_SEL(sc->rxchainmask);
+   rxchain |= IWN_RXCHAIN_FORCE_MIMO_SEL(sc->rxchainmask);
+   rxchain |= (IWN_RXCHAIN_DRIVER_FORCE | IWN_RXCHAIN_MIMO_FORCE);
+   }
sc->rxon.rxchain = htole16(rxchain);
DPRINTF(("setting configuration\n"));
-   DPRINTF(("%s: rxon chan %d flags %x cck %x ofdm %x\n", __func__,
-   sc->rxon.chan, le32toh(sc->rxon.flags), sc->rxon.cck_mask,
-   sc->rxon.ofdm_mask));
+   DPRINTF(("%s: rxon chan %d flags %x cck %x ofdm %x rxchain %x\n",
+   __func__, sc->rxon.chan, le32toh(sc->rxon.flags), sc->rxon.cck_mask,
+   sc->rxon.ofdm_mask, sc->rxon.rxchain));
error = iwn_cmd(sc, IWN_CMD_RXON, &sc->rxon, sc->rxonsz, 0);
if (error != 0) {
printf("%s: RXON command failed\n", sc->sc_dev.dv_xname);



Re: add MCS support to radiotap

2016-10-08 Thread Mark Kettenis
> Date: Sat, 8 Oct 2016 13:06:53 +0200 (CEST)
> From: Mark Kettenis 
> 
> > Date: Fri, 7 Oct 2016 18:59:52 +0200
> > From: Stefan Sperling 
> > 
> > On Fri, Oct 07, 2016 at 03:28:19PM +0200, Stefan Sperling wrote:
> > > Currently tcpdump shows "0 Mbit/s" for any frame sent with 11n HT MCS.
> > > To make progress easier, I'd like to see which MCS are used on the air,
> > > by any device.
> > > 
> > > The change below matches what FreeBSD did to pass an MCS index via 
> > > radiotap.
> > > This simply writes the MCS index into a previously unused range of rate 
> > > values.
> > > This format is already recognized by third party tools such as wireshark
> > > so let's just do it the same way.
> > > 
> > > The diff below updates the radiotap docs, makes iwn pass the MCS index,
> > > shows it in tcpdump. I can now see MCS with iwn in monitor mode.
> > > 
> > > ok?
> > 
> > Same diff, plus iwn now captures MIMO frames in monitor mode.
> 
> The addition might need to be tested on a 1TR1 and 2T3R setups.  I can
> test the latter, but I have no hardware to test the former.

FWIW, this seems to cause no regressions on:

iwn0 at pci2 dev 0 function 0 "Intel WiFi Link 5300" rev 0x00: msi, MIMO 3T3R, 
MoW, address 00:21:6a:13:67:82

Cheers,

Mark

> > Index: sys/net80211/ieee80211_radiotap.h
> > ===
> > RCS file: /cvs/src/sys/net80211/ieee80211_radiotap.h,v
> > retrieving revision 1.13
> > diff -u -p -r1.13 ieee80211_radiotap.h
> > --- sys/net80211/ieee80211_radiotap.h   12 Jan 2016 09:28:09 -  
> > 1.13
> > +++ sys/net80211/ieee80211_radiotap.h   7 Oct 2016 13:15:59 -
> > @@ -90,9 +90,10 @@ struct ieee80211_radiotap_header {
> >   *  For frequency-hopping radios, the hop set (first byte)
> >   *  and pattern (second byte).
> >   *
> > - * IEEE80211_RADIOTAP_RATE  u_int8_t500kb/s
> > + * IEEE80211_RADIOTAP_RATE  u_int8_t500kb/s or MCS 
> > index
> >   *
> > - *  Tx/Rx data rate
> > + *  Tx/Rx data rate in units of 500kb/s. If the high bit (0x80) is set
> > + *  the remaining bits contain an MCS index instead of a date rate.
> >   *
> >   * IEEE80211_RADIOTAP_DBM_ANTSIGNAL int8_t  decibels from
> >   *  one milliwatt (dBm)
> > Index: sys/dev/pci/if_iwn.c
> > ===
> > RCS file: /cvs/src/sys/dev/pci/if_iwn.c,v
> > retrieving revision 1.172
> > diff -u -p -r1.172 if_iwn.c
> > --- sys/dev/pci/if_iwn.c5 Sep 2016 08:18:18 -   1.172
> > +++ sys/dev/pci/if_iwn.c7 Oct 2016 16:33:39 -
> > @@ -2131,23 +2131,27 @@ iwn_rx_done(struct iwn_softc *sc, struct
> > tap->wr_dbm_antsignal = (int8_t)rssi;
> > tap->wr_dbm_antnoise = (int8_t)sc->noise;
> > tap->wr_tsft = stat->tstamp;
> > -   switch (stat->rate) {
> > -   /* CCK rates. */
> > -   case  10: tap->wr_rate =   2; break;
> > -   case  20: tap->wr_rate =   4; break;
> > -   case  55: tap->wr_rate =  11; break;
> > -   case 110: tap->wr_rate =  22; break;
> > -   /* OFDM rates. */
> > -   case 0xd: tap->wr_rate =  12; break;
> > -   case 0xf: tap->wr_rate =  18; break;
> > -   case 0x5: tap->wr_rate =  24; break;
> > -   case 0x7: tap->wr_rate =  36; break;
> > -   case 0x9: tap->wr_rate =  48; break;
> > -   case 0xb: tap->wr_rate =  72; break;
> > -   case 0x1: tap->wr_rate =  96; break;
> > -   case 0x3: tap->wr_rate = 108; break;
> > -   /* Unknown rate: should not happen. */
> > -   default:  tap->wr_rate =   0;
> > +   if (stat->rflags & IWN_RFLAG_MCS) {
> > +   tap->wr_rate = (0x80 | stat->rate); /* HT MCS index */
> > +   } else {
> > +   switch (stat->rate) {
> > +   /* CCK rates. */
> > +   case  10: tap->wr_rate =   2; break;
> > +   case  20: tap->wr_rate =   4; break;
> > +   case  55: tap->wr_rate =  11; break;
> > +   case 110: tap->wr_rate =  22; break;
> > +   /* OFDM rates. */
> > +   case 0xd: tap->wr_rate =  12; break;
> > +   case 0xf: tap->wr_rate =  18; break;
> > +   case 0x5: tap->wr_rate =  24; break;
> > +   case 0x7: tap->wr_rate =  36; break;
> > +   case 0x9: tap->wr_rate =  48; break;
> > +   case 0xb: tap->wr_rate =  72; break;
> > +   case 0x1: tap->wr_rate =  96; break;
> > +   case 0x3: tap->wr_rate = 108; break;
> > +   /* Unknown rate: should not happen. */
> > +   default:  tap->wr_rate =  0;
> > +   }
> > }
> >  
> > mb.m_data = (caddr_t)tap;
> > @@ -287

Re: add MCS support to radiotap

2016-10-08 Thread Mark Kettenis
> Date: Fri, 7 Oct 2016 18:59:52 +0200
> From: Stefan Sperling 
> 
> On Fri, Oct 07, 2016 at 03:28:19PM +0200, Stefan Sperling wrote:
> > Currently tcpdump shows "0 Mbit/s" for any frame sent with 11n HT MCS.
> > To make progress easier, I'd like to see which MCS are used on the air,
> > by any device.
> > 
> > The change below matches what FreeBSD did to pass an MCS index via radiotap.
> > This simply writes the MCS index into a previously unused range of rate 
> > values.
> > This format is already recognized by third party tools such as wireshark
> > so let's just do it the same way.
> > 
> > The diff below updates the radiotap docs, makes iwn pass the MCS index,
> > shows it in tcpdump. I can now see MCS with iwn in monitor mode.
> > 
> > ok?
> 
> Same diff, plus iwn now captures MIMO frames in monitor mode.

The addition might need to be tested on a 1TR1 and 2T3R setups.  I can
test the latter, but I have no hardware to test the former.

> Index: sys/net80211/ieee80211_radiotap.h
> ===
> RCS file: /cvs/src/sys/net80211/ieee80211_radiotap.h,v
> retrieving revision 1.13
> diff -u -p -r1.13 ieee80211_radiotap.h
> --- sys/net80211/ieee80211_radiotap.h 12 Jan 2016 09:28:09 -  1.13
> +++ sys/net80211/ieee80211_radiotap.h 7 Oct 2016 13:15:59 -
> @@ -90,9 +90,10 @@ struct ieee80211_radiotap_header {
>   *  For frequency-hopping radios, the hop set (first byte)
>   *  and pattern (second byte).
>   *
> - * IEEE80211_RADIOTAP_RATE  u_int8_t500kb/s
> + * IEEE80211_RADIOTAP_RATE  u_int8_t500kb/s or MCS index
>   *
> - *  Tx/Rx data rate
> + *  Tx/Rx data rate in units of 500kb/s. If the high bit (0x80) is set
> + *  the remaining bits contain an MCS index instead of a date rate.
>   *
>   * IEEE80211_RADIOTAP_DBM_ANTSIGNAL int8_t  decibels from
>   *  one milliwatt (dBm)
> Index: sys/dev/pci/if_iwn.c
> ===
> RCS file: /cvs/src/sys/dev/pci/if_iwn.c,v
> retrieving revision 1.172
> diff -u -p -r1.172 if_iwn.c
> --- sys/dev/pci/if_iwn.c  5 Sep 2016 08:18:18 -   1.172
> +++ sys/dev/pci/if_iwn.c  7 Oct 2016 16:33:39 -
> @@ -2131,23 +2131,27 @@ iwn_rx_done(struct iwn_softc *sc, struct
>   tap->wr_dbm_antsignal = (int8_t)rssi;
>   tap->wr_dbm_antnoise = (int8_t)sc->noise;
>   tap->wr_tsft = stat->tstamp;
> - switch (stat->rate) {
> - /* CCK rates. */
> - case  10: tap->wr_rate =   2; break;
> - case  20: tap->wr_rate =   4; break;
> - case  55: tap->wr_rate =  11; break;
> - case 110: tap->wr_rate =  22; break;
> - /* OFDM rates. */
> - case 0xd: tap->wr_rate =  12; break;
> - case 0xf: tap->wr_rate =  18; break;
> - case 0x5: tap->wr_rate =  24; break;
> - case 0x7: tap->wr_rate =  36; break;
> - case 0x9: tap->wr_rate =  48; break;
> - case 0xb: tap->wr_rate =  72; break;
> - case 0x1: tap->wr_rate =  96; break;
> - case 0x3: tap->wr_rate = 108; break;
> - /* Unknown rate: should not happen. */
> - default:  tap->wr_rate =   0;
> + if (stat->rflags & IWN_RFLAG_MCS) {
> + tap->wr_rate = (0x80 | stat->rate); /* HT MCS index */
> + } else {
> + switch (stat->rate) {
> + /* CCK rates. */
> + case  10: tap->wr_rate =   2; break;
> + case  20: tap->wr_rate =   4; break;
> + case  55: tap->wr_rate =  11; break;
> + case 110: tap->wr_rate =  22; break;
> + /* OFDM rates. */
> + case 0xd: tap->wr_rate =  12; break;
> + case 0xf: tap->wr_rate =  18; break;
> + case 0x5: tap->wr_rate =  24; break;
> + case 0x7: tap->wr_rate =  36; break;
> + case 0x9: tap->wr_rate =  48; break;
> + case 0xb: tap->wr_rate =  72; break;
> + case 0x1: tap->wr_rate =  96; break;
> + case 0x3: tap->wr_rate = 108; break;
> + /* Unknown rate: should not happen. */
> + default:  tap->wr_rate =  0;
> + }
>   }
>  
>   mb.m_data = (caddr_t)tap;
> @@ -2876,8 +2880,7 @@ iwn_tx(struct iwn_softc *sc, struct mbuf
>   if ((ni->ni_flags & IEEE80211_NODE_HT) &&
>   !IEEE80211_IS_MULTICAST(wh->i_addr1) &&
>   type == IEEE80211_FC0_TYPE_DATA) {
> - /* XXX need a way to pass current MCS in 11n mode */
> - tap->wt_rate = 0;
> + tap-

Re: add MCS support to radiotap

2016-10-08 Thread Mark Kettenis
> Date: Fri, 7 Oct 2016 15:28:19 +0200
> From: Stefan Sperling 
> 
> Currently tcpdump shows "0 Mbit/s" for any frame sent with 11n HT MCS.
> To make progress easier, I'd like to see which MCS are used on the air,
> by any device.
> 
> The change below matches what FreeBSD did to pass an MCS index via radiotap.
> This simply writes the MCS index into a previously unused range of rate 
> values.
> This format is already recognized by third party tools such as wireshark
> so let's just do it the same way.
> 
> The diff below updates the radiotap docs, makes iwn pass the MCS index,
> shows it in tcpdump. I can now see MCS with iwn in monitor mode.
> 
> ok?

ok kettenis@

> Index: sys/net80211/ieee80211_radiotap.h
> ===
> RCS file: /cvs/src/sys/net80211/ieee80211_radiotap.h,v
> retrieving revision 1.13
> diff -u -p -r1.13 ieee80211_radiotap.h
> --- sys/net80211/ieee80211_radiotap.h 12 Jan 2016 09:28:09 -  1.13
> +++ sys/net80211/ieee80211_radiotap.h 7 Oct 2016 13:15:59 -
> @@ -90,9 +90,10 @@ struct ieee80211_radiotap_header {
>   *  For frequency-hopping radios, the hop set (first byte)
>   *  and pattern (second byte).
>   *
> - * IEEE80211_RADIOTAP_RATE  u_int8_t500kb/s
> + * IEEE80211_RADIOTAP_RATE  u_int8_t500kb/s or MCS index
>   *
> - *  Tx/Rx data rate
> + *  Tx/Rx data rate in units of 500kb/s. If the high bit (0x80) is set
> + *  the remaining bits contain an MCS index instead of a date rate.
>   *
>   * IEEE80211_RADIOTAP_DBM_ANTSIGNAL int8_t  decibels from
>   *  one milliwatt (dBm)
> Index: sys/dev/pci/if_iwn.c
> ===
> RCS file: /cvs/src/sys/dev/pci/if_iwn.c,v
> retrieving revision 1.172
> diff -u -p -r1.172 if_iwn.c
> --- sys/dev/pci/if_iwn.c  5 Sep 2016 08:18:18 -   1.172
> +++ sys/dev/pci/if_iwn.c  7 Oct 2016 13:10:42 -
> @@ -2131,23 +2131,27 @@ iwn_rx_done(struct iwn_softc *sc, struct
>   tap->wr_dbm_antsignal = (int8_t)rssi;
>   tap->wr_dbm_antnoise = (int8_t)sc->noise;
>   tap->wr_tsft = stat->tstamp;
> - switch (stat->rate) {
> - /* CCK rates. */
> - case  10: tap->wr_rate =   2; break;
> - case  20: tap->wr_rate =   4; break;
> - case  55: tap->wr_rate =  11; break;
> - case 110: tap->wr_rate =  22; break;
> - /* OFDM rates. */
> - case 0xd: tap->wr_rate =  12; break;
> - case 0xf: tap->wr_rate =  18; break;
> - case 0x5: tap->wr_rate =  24; break;
> - case 0x7: tap->wr_rate =  36; break;
> - case 0x9: tap->wr_rate =  48; break;
> - case 0xb: tap->wr_rate =  72; break;
> - case 0x1: tap->wr_rate =  96; break;
> - case 0x3: tap->wr_rate = 108; break;
> - /* Unknown rate: should not happen. */
> - default:  tap->wr_rate =   0;
> + if (stat->rflags & IWN_RFLAG_MCS) {
> + tap->wr_rate = (0x80 | stat->rate); /* HT MCS index */
> + } else {
> + switch (stat->rate) {
> + /* CCK rates. */
> + case  10: tap->wr_rate =   2; break;
> + case  20: tap->wr_rate =   4; break;
> + case  55: tap->wr_rate =  11; break;
> + case 110: tap->wr_rate =  22; break;
> + /* OFDM rates. */
> + case 0xd: tap->wr_rate =  12; break;
> + case 0xf: tap->wr_rate =  18; break;
> + case 0x5: tap->wr_rate =  24; break;
> + case 0x7: tap->wr_rate =  36; break;
> + case 0x9: tap->wr_rate =  48; break;
> + case 0xb: tap->wr_rate =  72; break;
> + case 0x1: tap->wr_rate =  96; break;
> + case 0x3: tap->wr_rate = 108; break;
> + /* Unknown rate: should not happen. */
> + default:  tap->wr_rate =  0;
> + }
>   }
>  
>   mb.m_data = (caddr_t)tap;
> @@ -2876,8 +2880,7 @@ iwn_tx(struct iwn_softc *sc, struct mbuf
>   if ((ni->ni_flags & IEEE80211_NODE_HT) &&
>   !IEEE80211_IS_MULTICAST(wh->i_addr1) &&
>   type == IEEE80211_FC0_TYPE_DATA) {
> - /* XXX need a way to pass current MCS in 11n mode */
> - tap->wt_rate = 0;
> + tap->wt_rate = (0x80 | ni->ni_txmcs);
>   } else
>   tap->wt_rate = rinfo->rate;
>   tap->wt_hwqueue = ac;
> Index: usr.sbin/tcpdump/print-802_11.c
> ===
> RCS file: /cvs/src/u

Re: add MCS support to radiotap

2016-10-07 Thread Stefan Sperling
On Fri, Oct 07, 2016 at 03:28:19PM +0200, Stefan Sperling wrote:
> Currently tcpdump shows "0 Mbit/s" for any frame sent with 11n HT MCS.
> To make progress easier, I'd like to see which MCS are used on the air,
> by any device.
> 
> The change below matches what FreeBSD did to pass an MCS index via radiotap.
> This simply writes the MCS index into a previously unused range of rate 
> values.
> This format is already recognized by third party tools such as wireshark
> so let's just do it the same way.
> 
> The diff below updates the radiotap docs, makes iwn pass the MCS index,
> shows it in tcpdump. I can now see MCS with iwn in monitor mode.
> 
> ok?

Same diff, plus iwn now captures MIMO frames in monitor mode.

Index: sys/net80211/ieee80211_radiotap.h
===
RCS file: /cvs/src/sys/net80211/ieee80211_radiotap.h,v
retrieving revision 1.13
diff -u -p -r1.13 ieee80211_radiotap.h
--- sys/net80211/ieee80211_radiotap.h   12 Jan 2016 09:28:09 -  1.13
+++ sys/net80211/ieee80211_radiotap.h   7 Oct 2016 13:15:59 -
@@ -90,9 +90,10 @@ struct ieee80211_radiotap_header {
  *  For frequency-hopping radios, the hop set (first byte)
  *  and pattern (second byte).
  *
- * IEEE80211_RADIOTAP_RATE  u_int8_t500kb/s
+ * IEEE80211_RADIOTAP_RATE  u_int8_t500kb/s or MCS index
  *
- *  Tx/Rx data rate
+ *  Tx/Rx data rate in units of 500kb/s. If the high bit (0x80) is set
+ *  the remaining bits contain an MCS index instead of a date rate.
  *
  * IEEE80211_RADIOTAP_DBM_ANTSIGNAL int8_t  decibels from
  *  one milliwatt (dBm)
Index: sys/dev/pci/if_iwn.c
===
RCS file: /cvs/src/sys/dev/pci/if_iwn.c,v
retrieving revision 1.172
diff -u -p -r1.172 if_iwn.c
--- sys/dev/pci/if_iwn.c5 Sep 2016 08:18:18 -   1.172
+++ sys/dev/pci/if_iwn.c7 Oct 2016 16:33:39 -
@@ -2131,23 +2131,27 @@ iwn_rx_done(struct iwn_softc *sc, struct
tap->wr_dbm_antsignal = (int8_t)rssi;
tap->wr_dbm_antnoise = (int8_t)sc->noise;
tap->wr_tsft = stat->tstamp;
-   switch (stat->rate) {
-   /* CCK rates. */
-   case  10: tap->wr_rate =   2; break;
-   case  20: tap->wr_rate =   4; break;
-   case  55: tap->wr_rate =  11; break;
-   case 110: tap->wr_rate =  22; break;
-   /* OFDM rates. */
-   case 0xd: tap->wr_rate =  12; break;
-   case 0xf: tap->wr_rate =  18; break;
-   case 0x5: tap->wr_rate =  24; break;
-   case 0x7: tap->wr_rate =  36; break;
-   case 0x9: tap->wr_rate =  48; break;
-   case 0xb: tap->wr_rate =  72; break;
-   case 0x1: tap->wr_rate =  96; break;
-   case 0x3: tap->wr_rate = 108; break;
-   /* Unknown rate: should not happen. */
-   default:  tap->wr_rate =   0;
+   if (stat->rflags & IWN_RFLAG_MCS) {
+   tap->wr_rate = (0x80 | stat->rate); /* HT MCS index */
+   } else {
+   switch (stat->rate) {
+   /* CCK rates. */
+   case  10: tap->wr_rate =   2; break;
+   case  20: tap->wr_rate =   4; break;
+   case  55: tap->wr_rate =  11; break;
+   case 110: tap->wr_rate =  22; break;
+   /* OFDM rates. */
+   case 0xd: tap->wr_rate =  12; break;
+   case 0xf: tap->wr_rate =  18; break;
+   case 0x5: tap->wr_rate =  24; break;
+   case 0x7: tap->wr_rate =  36; break;
+   case 0x9: tap->wr_rate =  48; break;
+   case 0xb: tap->wr_rate =  72; break;
+   case 0x1: tap->wr_rate =  96; break;
+   case 0x3: tap->wr_rate = 108; break;
+   /* Unknown rate: should not happen. */
+   default:  tap->wr_rate =  0;
+   }
}
 
mb.m_data = (caddr_t)tap;
@@ -2876,8 +2880,7 @@ iwn_tx(struct iwn_softc *sc, struct mbuf
if ((ni->ni_flags & IEEE80211_NODE_HT) &&
!IEEE80211_IS_MULTICAST(wh->i_addr1) &&
type == IEEE80211_FC0_TYPE_DATA) {
-   /* XXX need a way to pass current MCS in 11n mode */
-   tap->wt_rate = 0;
+   tap->wt_rate = (0x80 | ni->ni_txmcs);
} else
tap->wt_rate = rinfo->rate;
tap->wt_hwqueue = ac;
@@ -4498,13 +4501,18 @@ iwn_config(struct iwn_softc *sc)
sc->rxon.ht_triple_mask = 0xff;
rxchain =
IWN_RXCHAIN

add MCS support to radiotap

2016-10-07 Thread Stefan Sperling
Currently tcpdump shows "0 Mbit/s" for any frame sent with 11n HT MCS.
To make progress easier, I'd like to see which MCS are used on the air,
by any device.

The change below matches what FreeBSD did to pass an MCS index via radiotap.
This simply writes the MCS index into a previously unused range of rate values.
This format is already recognized by third party tools such as wireshark
so let's just do it the same way.

The diff below updates the radiotap docs, makes iwn pass the MCS index,
shows it in tcpdump. I can now see MCS with iwn in monitor mode.

ok?

Index: sys/net80211/ieee80211_radiotap.h
===
RCS file: /cvs/src/sys/net80211/ieee80211_radiotap.h,v
retrieving revision 1.13
diff -u -p -r1.13 ieee80211_radiotap.h
--- sys/net80211/ieee80211_radiotap.h   12 Jan 2016 09:28:09 -  1.13
+++ sys/net80211/ieee80211_radiotap.h   7 Oct 2016 13:15:59 -
@@ -90,9 +90,10 @@ struct ieee80211_radiotap_header {
  *  For frequency-hopping radios, the hop set (first byte)
  *  and pattern (second byte).
  *
- * IEEE80211_RADIOTAP_RATE  u_int8_t500kb/s
+ * IEEE80211_RADIOTAP_RATE  u_int8_t500kb/s or MCS index
  *
- *  Tx/Rx data rate
+ *  Tx/Rx data rate in units of 500kb/s. If the high bit (0x80) is set
+ *  the remaining bits contain an MCS index instead of a date rate.
  *
  * IEEE80211_RADIOTAP_DBM_ANTSIGNAL int8_t  decibels from
  *  one milliwatt (dBm)
Index: sys/dev/pci/if_iwn.c
===
RCS file: /cvs/src/sys/dev/pci/if_iwn.c,v
retrieving revision 1.172
diff -u -p -r1.172 if_iwn.c
--- sys/dev/pci/if_iwn.c5 Sep 2016 08:18:18 -   1.172
+++ sys/dev/pci/if_iwn.c7 Oct 2016 13:10:42 -
@@ -2131,23 +2131,27 @@ iwn_rx_done(struct iwn_softc *sc, struct
tap->wr_dbm_antsignal = (int8_t)rssi;
tap->wr_dbm_antnoise = (int8_t)sc->noise;
tap->wr_tsft = stat->tstamp;
-   switch (stat->rate) {
-   /* CCK rates. */
-   case  10: tap->wr_rate =   2; break;
-   case  20: tap->wr_rate =   4; break;
-   case  55: tap->wr_rate =  11; break;
-   case 110: tap->wr_rate =  22; break;
-   /* OFDM rates. */
-   case 0xd: tap->wr_rate =  12; break;
-   case 0xf: tap->wr_rate =  18; break;
-   case 0x5: tap->wr_rate =  24; break;
-   case 0x7: tap->wr_rate =  36; break;
-   case 0x9: tap->wr_rate =  48; break;
-   case 0xb: tap->wr_rate =  72; break;
-   case 0x1: tap->wr_rate =  96; break;
-   case 0x3: tap->wr_rate = 108; break;
-   /* Unknown rate: should not happen. */
-   default:  tap->wr_rate =   0;
+   if (stat->rflags & IWN_RFLAG_MCS) {
+   tap->wr_rate = (0x80 | stat->rate); /* HT MCS index */
+   } else {
+   switch (stat->rate) {
+   /* CCK rates. */
+   case  10: tap->wr_rate =   2; break;
+   case  20: tap->wr_rate =   4; break;
+   case  55: tap->wr_rate =  11; break;
+   case 110: tap->wr_rate =  22; break;
+   /* OFDM rates. */
+   case 0xd: tap->wr_rate =  12; break;
+   case 0xf: tap->wr_rate =  18; break;
+   case 0x5: tap->wr_rate =  24; break;
+   case 0x7: tap->wr_rate =  36; break;
+   case 0x9: tap->wr_rate =  48; break;
+   case 0xb: tap->wr_rate =  72; break;
+   case 0x1: tap->wr_rate =  96; break;
+   case 0x3: tap->wr_rate = 108; break;
+   /* Unknown rate: should not happen. */
+   default:  tap->wr_rate =  0;
+   }
}
 
mb.m_data = (caddr_t)tap;
@@ -2876,8 +2880,7 @@ iwn_tx(struct iwn_softc *sc, struct mbuf
if ((ni->ni_flags & IEEE80211_NODE_HT) &&
!IEEE80211_IS_MULTICAST(wh->i_addr1) &&
type == IEEE80211_FC0_TYPE_DATA) {
-   /* XXX need a way to pass current MCS in 11n mode */
-   tap->wt_rate = 0;
+   tap->wt_rate = (0x80 | ni->ni_txmcs);
} else
tap->wt_rate = rinfo->rate;
tap->wt_hwqueue = ac;
Index: usr.sbin/tcpdump/print-802_11.c
===
RCS file: /cvs/src/usr.sbin/tcpdump/print-802_11.c,v
retrieving revision 1.33
diff -u -p -r1.33 print-802_11.c
--- usr.sbin/tcpdump/print-802_11.c 2 Sep 2016 17:11:46 -   1.33