Search Linux Wireless

Re: [PATCH 1/2] mac80211: use hardware flags for signal/noise units

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



hello!

is there any interrest in getting this merged? any problems?
am i wasting my time?

bruno


On Thursday 08 May 2008 19:15:40 Bruno Randolf wrote:
> trying to clean up the signal/noise code. the previous code in mac80211 had
> confusing names for the related variables, did not have much definition of
> what units of signal and noise were provided and used implicit mechanisms
> from the wireless extensions.
>
> this patch introduces hardware capability flags to let the hardware specify
> clearly if it can provide signal and noise level values and which units it
> can provide. this also anticipates possible new units like RCPI in the
> future.
>
> for signal:
>
>   IEEE80211_HW_SIGNAL_UNSPEC - unspecified, unknown, hw specific
>   IEEE80211_HW_SIGNAL_DB     - dB difference to unspecified reference point
>   IEEE80211_HW_SIGNAL_DBM    - dBm, difference to 1mW
>
> for noise we currently only have dBm:
>
>   IEEE80211_HW_NOISE_DBM     - dBm, difference to 1mW
>
> if IEEE80211_HW_SIGNAL_UNSPEC or IEEE80211_HW_SIGNAL_DB is used the driver
> has to provide the maximum value (max_signal) it reports in order for
> applications to make sense of the signal values.
>
> i tried my best to find out for each driver what it can provide and update
> it but i'm not sure (?) for some of them and used the more conservative
> guess in doubt. this can be fixed easily after this patch has been merged
> by changing the hardware flags of the driver.
>
> DRIVER          SIGNAL    MAX	NOISE   QUAL
> -----------------------------------------------------------------
> adm8211         unspec(?) 100   n/a     missing
> at76_usb        unspec(?) (?)   unused  missing
> ath5k           dBm             dBm     percent rssi
> b43legacy       dBm             dBm     percent jssi(?)
> b43             dBm             dBm     percent jssi(?)
> iwl-3945        dBm             dBm     percent snr+more
> iwl-4965        dBm             dBm     percent snr+more
> p54             unspec    127   n/a     missing
> rt2x00          dBm	        n/a     percent rssi+tx/rx frame success
>   rt2400        dBm             n/a
>   rt2500pci     dBm             n/a
>   rt2500usb     dBm             n/a
>   rt61pci       dBm             n/a
>   rt73usb       dBm             n/a
> rtl8180         unspec(?) 65    n/a     (?)
> rtl8187         unspec(?) 65    (?)     noise(?)
> zd1211          dB(?)     100   n/a     percent
>
> drivers/net/wireless/ath5k/base.c:      Changes-licensed-under:
> 3-Clause-BSD
>
> Signed-off-by: Bruno Randolf <br1@xxxxxxxxxxx>
> ---
>
>  drivers/net/wireless/adm8211.c              |    7 ++--
>  drivers/net/wireless/at76_usb.c             |    5 ++-
>  drivers/net/wireless/ath5k/base.c           |   23 +++----------
>  drivers/net/wireless/b43/main.c             |    8 ++---
>  drivers/net/wireless/b43/xmit.c             |    5 +--
>  drivers/net/wireless/b43legacy/main.c       |    7 ++--
>  drivers/net/wireless/b43legacy/xmit.c       |    4 +-
>  drivers/net/wireless/iwlwifi/iwl-3945.c     |   18 +++++-----
>  drivers/net/wireless/iwlwifi/iwl-4965.c     |   12 +++----
>  drivers/net/wireless/iwlwifi/iwl-core.c     |   16 ++-------
>  drivers/net/wireless/iwlwifi/iwl3945-base.c |   15 ++-------
>  drivers/net/wireless/p54/p54common.c        |    7 ++--
>  drivers/net/wireless/rt2x00/rt2400pci.c     |    5 +--
>  drivers/net/wireless/rt2x00/rt2500pci.c     |    6 ++-
>  drivers/net/wireless/rt2x00/rt2500usb.c     |    6 ++-
>  drivers/net/wireless/rt2x00/rt2x00dev.c     |    4 +-
>  drivers/net/wireless/rt2x00/rt61pci.c       |    5 +--
>  drivers/net/wireless/rt2x00/rt73usb.c       |    5 +--
>  drivers/net/wireless/rtl8180_dev.c          |    9 +++--
>  drivers/net/wireless/rtl8187_dev.c          |   10 +++---
>  drivers/net/wireless/zd1211rw/zd_mac.c      |   12 +++----
>  include/net/mac80211.h                      |   47
> ++++++++++++++++++++------- net/ieee80211/ieee80211_rx.c                |  
>  2 +
>  net/mac80211/debugfs_sta.c                  |    2 +
>  net/mac80211/ieee80211_i.h                  |    2 +
>  net/mac80211/main.c                         |   10 +++---
>  net/mac80211/mlme.c                         |   12 +++----
>  net/mac80211/rx.c                           |    4 +-
>  net/mac80211/sta_info.h                     |    2 +
>  net/mac80211/wext.c                         |   28 +++++++++++-----
>  30 files changed, 151 insertions(+), 147 deletions(-)
>
>
> diff --git a/drivers/net/wireless/adm8211.c
> b/drivers/net/wireless/adm8211.c index d93a1de..7af5d88 100644
> --- a/drivers/net/wireless/adm8211.c
> +++ b/drivers/net/wireless/adm8211.c
> @@ -445,9 +445,9 @@ static void adm8211_interrupt_rci(struct ieee80211_hw
> *dev) struct ieee80211_rx_status rx_status = {0};
>
>  			if (priv->pdev->revision < ADM8211_REV_CA)
> -				rx_status.ssi = rssi;
> +				rx_status.signal = rssi;
>  			else
> -				rx_status.ssi = 100 - rssi;
> +				rx_status.signal = 100 - rssi;
>
>  			rx_status.rate_idx = rate;
>
> @@ -1893,9 +1893,10 @@ static int __devinit adm8211_probe(struct pci_dev
> *pdev,
>
>  	dev->extra_tx_headroom = sizeof(struct adm8211_tx_hdr);
>  	/* dev->flags = IEEE80211_HW_RX_INCLUDES_FCS in promisc mode */
> +	dev->flags = IEEE80211_HW_SIGNAL_UNSPEC;
>
>  	dev->channel_change_time = 1000;
> -	dev->max_rssi = 100;	/* FIXME: find better value */
> +	dev->max_signal = 100;    /* FIXME: find better value */
>
>  	dev->queues = 1; /* ADM8211C supports more, maybe ADM8211B too */
>
> diff --git a/drivers/net/wireless/at76_usb.c
> b/drivers/net/wireless/at76_usb.c index 33fa026..009f8a7 100644
> --- a/drivers/net/wireless/at76_usb.c
> +++ b/drivers/net/wireless/at76_usb.c
> @@ -1599,7 +1599,7 @@ static void at76_rx_tasklet(unsigned long param)
>  	at76_dbg_dump(DBG_RX_DATA, priv->rx_skb->data,
>  		      priv->rx_skb->len, "RX: len=%d", priv->rx_skb->len);
>
> -	rx_status.ssi = buf->rssi;
> +	rx_status.signal = buf->rssi;
>  	rx_status.flag |= RX_FLAG_DECRYPTED;
>  	rx_status.flag |= RX_FLAG_IV_STRIPPED;
>
> @@ -2273,7 +2273,8 @@ static int at76_init_new_device(struct at76_priv
> *priv,
>
>  	/* mac80211 initialisation */
>  	priv->hw->wiphy->bands[IEEE80211_BAND_2GHZ] = &at76_supported_band;
> -	priv->hw->flags = IEEE80211_HW_RX_INCLUDES_FCS;
> +	priv->hw->flags = IEEE80211_HW_RX_INCLUDES_FCS |
> +			  IEEE80211_HW_SIGNAL_UNSPEC;
>
>  	SET_IEEE80211_DEV(priv->hw, &interface->dev);
>  	SET_IEEE80211_PERM_ADDR(priv->hw, priv->mac_addr);
> diff --git a/drivers/net/wireless/ath5k/base.c
> b/drivers/net/wireless/ath5k/base.c index 2b9ba34..c6b2fce 100644
> --- a/drivers/net/wireless/ath5k/base.c
> +++ b/drivers/net/wireless/ath5k/base.c
> @@ -462,13 +462,11 @@ ath5k_pci_probe(struct pci_dev *pdev,
>
>  	/* Initialize driver private data */
>  	SET_IEEE80211_DEV(hw, &pdev->dev);
> -	hw->flags = IEEE80211_HW_RX_INCLUDES_FCS;
> +	hw->flags = IEEE80211_HW_RX_INCLUDES_FCS |
> +		    IEEE80211_HW_SIGNAL_DBM |
> +		    IEEE80211_HW_NOISE_DBM;
>  	hw->extra_tx_headroom = 2;
>  	hw->channel_change_time = 5000;
> -	/* these names are misleading */
> -	hw->max_rssi = -110; /* signal in dBm */
> -	hw->max_noise = -110; /* noise in dBm */
> -	hw->max_signal = 100; /* we will provide a percentage based on rssi */
>  	sc = hw->priv;
>  	sc->hw = hw;
>  	sc->pdev = pdev;
> @@ -1897,20 +1895,9 @@ accept:
>  		rxs.freq = sc->curchan->center_freq;
>  		rxs.band = sc->curband->band;
>
> -		/*
> -		 * signal quality:
> -		 * the names here are misleading and the usage of these
> -		 * values by iwconfig makes it even worse
> -		 */
> -		/* noise floor in dBm, from the last noise calibration */
>  		rxs.noise = sc->ah->ah_noise_floor;
> -		/* signal level in dBm */
> -		rxs.ssi = rxs.noise + rs.rs_rssi;
> -		/*
> -		 * "signal" is actually displayed as Link Quality by iwconfig
> -		 * we provide a percentage based on rssi (assuming max rssi 64)
> -		 */
> -		rxs.signal = rs.rs_rssi * 100 / 64;
> +		rxs.signal = rxs.noise + rs.rs_rssi;
> +		rxs.qual = rs.rs_rssi * 100 / 64;
>
>  		rxs.antenna = rs.rs_antenna;
>  		rxs.rate_idx = ath5k_hw_to_driver_rix(sc, rs.rs_rate);
> diff --git a/drivers/net/wireless/b43/main.c
> b/drivers/net/wireless/b43/main.c index a37d7fa..d151d6a 100644
> --- a/drivers/net/wireless/b43/main.c
> +++ b/drivers/net/wireless/b43/main.c
> @@ -4466,10 +4466,10 @@ static int b43_wireless_init(struct ssb_device
> *dev)
>
>  	/* fill hw info */
>  	hw->flags = IEEE80211_HW_HOST_GEN_BEACON_TEMPLATE |
> -		    IEEE80211_HW_RX_INCLUDES_FCS;
> -	hw->max_signal = 100;
> -	hw->max_rssi = -110;
> -	hw->max_noise = -110;
> +		    IEEE80211_HW_RX_INCLUDES_FCS |
> +		    IEEE80211_HW_SIGNAL_DBM |
> +		    IEEE80211_HW_NOISE_DBM;
> +
>  	hw->queues = b43_modparam_qos ? 4 : 1;
>  	SET_IEEE80211_DEV(hw, dev->dev);
>  	if (is_valid_ether_addr(sprom->et1mac))
> diff --git a/drivers/net/wireless/b43/xmit.c
> b/drivers/net/wireless/b43/xmit.c index 8849194..afce933 100644
> --- a/drivers/net/wireless/b43/xmit.c
> +++ b/drivers/net/wireless/b43/xmit.c
> @@ -581,12 +581,11 @@ void b43_rx(struct b43_wldev *dev, struct sk_buff
> *skb, const void *_rxhdr) //      and also find out what the maximum
> possible value is.
>  		//      Fill status.ssi and status.signal fields.
>  	} else {
> -		status.ssi = b43_rssi_postprocess(dev, rxhdr->jssi,
> +		status.signal = b43_rssi_postprocess(dev, rxhdr->jssi,
>  						  (phystat0 & B43_RX_PHYST0_OFDM),
>  						  (phystat0 & B43_RX_PHYST0_GAINCTL),
>  						  (phystat3 & B43_RX_PHYST3_TRSTATE));
> -		/* the next line looks wrong, but is what mac80211 wants */
> -		status.signal = (rxhdr->jssi * 100) / B43_RX_MAX_SSI;
> +		status.qual = (rxhdr->jssi * 100) / B43_RX_MAX_SSI;
>  	}
>
>  	if (phystat0 & B43_RX_PHYST0_OFDM)
> diff --git a/drivers/net/wireless/b43legacy/main.c
> b/drivers/net/wireless/b43legacy/main.c index a353dae..4525660 100644
> --- a/drivers/net/wireless/b43legacy/main.c
> +++ b/drivers/net/wireless/b43legacy/main.c
> @@ -3718,10 +3718,9 @@ static int b43legacy_wireless_init(struct ssb_device
> *dev)
>
>  	/* fill hw info */
>  	hw->flags = IEEE80211_HW_HOST_GEN_BEACON_TEMPLATE |
> -		    IEEE80211_HW_RX_INCLUDES_FCS;
> -	hw->max_signal = 100;
> -	hw->max_rssi = -110;
> -	hw->max_noise = -110;
> +		    IEEE80211_HW_RX_INCLUDES_FCS |
> +		    IEEE80211_HW_SIGNAL_DBM |
> +		    IEEE80211_HW_NOISE_DBM;
>  	hw->queues = 1; /* FIXME: hardware has more queues */
>  	SET_IEEE80211_DEV(hw, dev->dev);
>  	if (is_valid_ether_addr(sprom->et1mac))
> diff --git a/drivers/net/wireless/b43legacy/xmit.c
> b/drivers/net/wireless/b43legacy/xmit.c index fc83dab..bed9e04 100644
> --- a/drivers/net/wireless/b43legacy/xmit.c
> +++ b/drivers/net/wireless/b43legacy/xmit.c
> @@ -532,12 +532,12 @@ void b43legacy_rx(struct b43legacy_wldev *dev,
>  		}
>  	}
>
> -	status.ssi = b43legacy_rssi_postprocess(dev, jssi,
> +	status.signal = b43legacy_rssi_postprocess(dev, jssi,
>  				      (phystat0 & B43legacy_RX_PHYST0_OFDM),
>  				      (phystat0 & B43legacy_RX_PHYST0_GAINCTL),
>  				      (phystat3 & B43legacy_RX_PHYST3_TRSTATE));
>  	status.noise = dev->stats.link_noise;
> -	status.signal = (jssi * 100) / B43legacy_RX_MAX_SSI;
> +	status.qual = (jssi * 100) / B43legacy_RX_MAX_SSI;
>  	/* change to support A PHY */
>  	if (phystat0 & B43legacy_RX_PHYST0_OFDM)
>  		status.rate_idx = b43legacy_plcp_get_bitrate_idx_ofdm(plcp, false);
> diff --git a/drivers/net/wireless/iwlwifi/iwl-3945.c
> b/drivers/net/wireless/iwlwifi/iwl-3945.c index 2869533..0bc062b 100644
> --- a/drivers/net/wireless/iwlwifi/iwl-3945.c
> +++ b/drivers/net/wireless/iwlwifi/iwl-3945.c
> @@ -520,7 +520,7 @@ static void iwl3945_add_radiotap(struct iwl3945_priv
> *priv, {
>  	/* First cache any information we need before we overwrite
>  	 * the information provided in the skb from the hardware */
> -	s8 signal = stats->ssi;
> +	s8 signal = stats->signal;
>  	s8 noise = 0;
>  	int rate = stats->rate_idx;
>  	u64 tsf = stats->mactime;
> @@ -697,7 +697,7 @@ static void iwl3945_rx_reply_rx(struct iwl3945_priv
> *priv, }
>
>  	/* Convert 3945's rssi indicator to dBm */
> -	rx_status.ssi = rx_stats->rssi - IWL_RSSI_OFFSET;
> +	rx_status.signal = rx_stats->rssi - IWL_RSSI_OFFSET;
>
>  	/* Set default noise value to -127 */
>  	if (priv->last_rx_noise == 0)
> @@ -716,21 +716,21 @@ static void iwl3945_rx_reply_rx(struct iwl3945_priv
> *priv, * Calculate rx_status.signal (quality indicator in %) based on SNR.
> */ if (rx_stats_noise_diff) {
>  		snr = rx_stats_sig_avg / rx_stats_noise_diff;
> -		rx_status.noise = rx_status.ssi -
> +		rx_status.noise = rx_status.signal -
>  					iwl3945_calc_db_from_ratio(snr);
> -		rx_status.signal = iwl3945_calc_sig_qual(rx_status.ssi,
> +		rx_status.qual = iwl3945_calc_sig_qual(rx_status.signal,
>  							 rx_status.noise);
>
>  	/* If noise info not available, calculate signal quality indicator (%)
>  	 *   using just the dBm signal level. */
>  	} else {
>  		rx_status.noise = priv->last_rx_noise;
> -		rx_status.signal = iwl3945_calc_sig_qual(rx_status.ssi, 0);
> +		rx_status.qual = iwl3945_calc_sig_qual(rx_status.signal, 0);
>  	}
>
>
>  	IWL_DEBUG_STATS("Rssi %d noise %d qual %d sig_avg %d noise_diff %d\n",
> -			rx_status.ssi, rx_status.noise, rx_status.signal,
> +			rx_status.signal, rx_status.noise, rx_status.qual,
>  			rx_stats_sig_avg, rx_stats_noise_diff);
>
>  	header = (struct ieee80211_hdr *)IWL_RX_DATA(pkt);
> @@ -740,8 +740,8 @@ static void iwl3945_rx_reply_rx(struct iwl3945_priv
> *priv, IWL_DEBUG_STATS_LIMIT("[%c] %d RSSI:%d Signal:%u, Noise:%u,
> Rate:%u\n", network_packet ? '*' : ' ',
>  			      le16_to_cpu(rx_hdr->channel),
> -			      rx_status.ssi, rx_status.ssi,
> -			      rx_status.ssi, rx_status.rate_idx);
> +			      rx_status.signal, rx_status.signal,
> +			      rx_status.noise, rx_status.rate_idx);
>
>  #ifdef CONFIG_IWL3945_DEBUG
>  	if (iwl3945_debug_level & (IWL_DL_RX))
> @@ -752,7 +752,7 @@ static void iwl3945_rx_reply_rx(struct iwl3945_priv
> *priv, if (network_packet) {
>  		priv->last_beacon_time = le32_to_cpu(rx_end->beacon_timestamp);
>  		priv->last_tsf = le64_to_cpu(rx_end->timestamp);
> -		priv->last_rx_rssi = rx_status.ssi;
> +		priv->last_rx_rssi = rx_status.signal;
>  		priv->last_rx_noise = rx_status.noise;
>  	}
>
> diff --git a/drivers/net/wireless/iwlwifi/iwl-4965.c
> b/drivers/net/wireless/iwlwifi/iwl-4965.c index 9546582..477f49d 100644
> --- a/drivers/net/wireless/iwlwifi/iwl-4965.c
> +++ b/drivers/net/wireless/iwlwifi/iwl-4965.c
> @@ -2588,7 +2588,7 @@ static void iwl4965_add_radiotap(struct iwl_priv
> *priv, struct ieee80211_rx_status *stats,
>  				 u32 ampdu_status)
>  {
> -	s8 signal = stats->ssi;
> +	s8 signal = stats->signal;
>  	s8 noise = 0;
>  	int rate = stats->rate_idx;
>  	u64 tsf = stats->mactime;
> @@ -3186,7 +3186,7 @@ static void iwl4965_rx_reply_rx(struct iwl_priv
> *priv, priv->ucode_beacon_time = le32_to_cpu(rx_start->beacon_time_stamp);
>
>  	/* Find max signal strength (dBm) among 3 antenna/receiver chains */
> -	rx_status.ssi = iwl4965_calc_rssi(rx_start);
> +	rx_status.signal = iwl4965_calc_rssi(rx_start);
>
>  	/* Meaningful noise values are available only from beacon statistics,
>  	 *   which are gathered only when associated, and indicate noise
> @@ -3195,11 +3195,11 @@ static void iwl4965_rx_reply_rx(struct iwl_priv
> *priv, if (iwl_is_associated(priv) &&
>  	    !test_bit(STATUS_SCANNING, &priv->status)) {
>  		rx_status.noise = priv->last_rx_noise;
> -		rx_status.signal = iwl4965_calc_sig_qual(rx_status.ssi,
> +		rx_status.qual = iwl4965_calc_sig_qual(rx_status.signal,
>  							 rx_status.noise);
>  	} else {
>  		rx_status.noise = IWL_NOISE_MEAS_NOT_AVAILABLE;
> -		rx_status.signal = iwl4965_calc_sig_qual(rx_status.ssi, 0);
> +		rx_status.qual = iwl4965_calc_sig_qual(rx_status.signal, 0);
>  	}
>
>  	/* Reset beacon noise level if not associated. */
> @@ -3211,12 +3211,12 @@ static void iwl4965_rx_reply_rx(struct iwl_priv
> *priv, iwl4965_dbg_report_frame(priv, pkt, header, 1);
>
>  	IWL_DEBUG_STATS_LIMIT("Rssi %d, noise %d, qual %d, TSF %llu\n",
> -			      rx_status.ssi, rx_status.noise, rx_status.signal,
> +			      rx_status.signal, rx_status.noise, rx_status.qual,
>  			      (unsigned long long)rx_status.mactime);
>
>  	network_packet = iwl4965_is_network_packet(priv, header);
>  	if (network_packet) {
> -		priv->last_rx_rssi = rx_status.ssi;
> +		priv->last_rx_rssi = rx_status.signal;
>  		priv->last_beacon_time =  priv->ucode_beacon_time;
>  		priv->last_tsf = le64_to_cpu(rx_start->timestamp);
>  	}
> diff --git a/drivers/net/wireless/iwlwifi/iwl-core.c
> b/drivers/net/wireless/iwlwifi/iwl-core.c index c4b5c1a..36ec156 100644
> --- a/drivers/net/wireless/iwlwifi/iwl-core.c
> +++ b/drivers/net/wireless/iwlwifi/iwl-core.c
> @@ -552,18 +552,10 @@ static void iwlcore_init_hw(struct iwl_priv *priv)
>  	struct ieee80211_hw *hw = priv->hw;
>  	hw->rate_control_algorithm = "iwl-4965-rs";
>
> -	/* Tell mac80211 and its clients (e.g. Wireless Extensions)
> -	 *	 the range of signal quality values that we'll provide.
> -	 * Negative values for level/noise indicate that we'll provide dBm.
> -	 * For WE, at least, non-0 values here *enable* display of values
> -	 *	 in app (iwconfig). */
> -	hw->max_rssi = -20; /* signal level, negative indicates dBm */
> -	hw->max_noise = -20;	/* noise level, negative indicates dBm */
> -	hw->max_signal = 100;	/* link quality indication (%) */
> -
> -	/* Tell mac80211 our Tx characteristics */
> -	hw->flags = IEEE80211_HW_HOST_GEN_BEACON_TEMPLATE;
> -
> +	/* Tell mac80211 our characteristics */
> +	hw->flags = IEEE80211_HW_HOST_GEN_BEACON_TEMPLATE |
> +		    IEEE80211_HW_SIGNAL_DBM |
> +		    IEEE80211_HW_NOISE_DBM;
>  	/* Default value; 4 EDCA QOS priorities */
>  	hw->queues = 4;
>  #ifdef CONFIG_IWL4965_HT
> diff --git a/drivers/net/wireless/iwlwifi/iwl3945-base.c
> b/drivers/net/wireless/iwlwifi/iwl3945-base.c index 7040cde..6a39850 100644
> --- a/drivers/net/wireless/iwlwifi/iwl3945-base.c
> +++ b/drivers/net/wireless/iwlwifi/iwl3945-base.c
> @@ -7994,17 +7994,10 @@ static int iwl3945_pci_probe(struct pci_dev *pdev,
> const struct pci_device_id *e
>
>  	priv->ibss_beacon = NULL;
>
> -	/* Tell mac80211 and its clients (e.g. Wireless Extensions)
> -	 *   the range of signal quality values that we'll provide.
> -	 * Negative values for level/noise indicate that we'll provide dBm.
> -	 * For WE, at least, non-0 values here *enable* display of values
> -	 *   in app (iwconfig). */
> -	hw->max_rssi = -20;	/* signal level, negative indicates dBm */
> -	hw->max_noise = -20;	/* noise level, negative indicates dBm */
> -	hw->max_signal = 100;	/* link quality indication (%) */
> -
> -	/* Tell mac80211 our Tx characteristics */
> -	hw->flags = IEEE80211_HW_HOST_GEN_BEACON_TEMPLATE;
> +	/* Tell mac80211 our characteristics */
> +	hw->flags = IEEE80211_HW_HOST_GEN_BEACON_TEMPLATE |
> +		    IEEE80211_HW_SIGNAL_DBM |
> +		    IEEE80211_HW_NOISE_DBM;
>
>  	/* 4 EDCA QOS priorities */
>  	hw->queues = 4;
> diff --git a/drivers/net/wireless/p54/p54common.c
> b/drivers/net/wireless/p54/p54common.c index 33d608a..9cbef5b 100644
> --- a/drivers/net/wireless/p54/p54common.c
> +++ b/drivers/net/wireless/p54/p54common.c
> @@ -355,7 +355,7 @@ static void p54_rx_data(struct ieee80211_hw *dev,
> struct sk_buff *skb) struct ieee80211_rx_status rx_status = {0};
>  	u16 freq = le16_to_cpu(hdr->freq);
>
> -	rx_status.ssi = hdr->rssi;
> +	rx_status.signal = hdr->rssi;
>  	/* XX correct? */
>  	rx_status.rate_idx = hdr->rate & 0xf;
>  	rx_status.freq = freq;
> @@ -1000,9 +1000,10 @@ struct ieee80211_hw *p54_init_common(size_t
> priv_data_len) skb_queue_head_init(&priv->tx_queue);
>  	dev->wiphy->bands[IEEE80211_BAND_2GHZ] = &band_2GHz;
>  	dev->flags = IEEE80211_HW_HOST_BROADCAST_PS_BUFFERING | /* not sure */
> -		    IEEE80211_HW_RX_INCLUDES_FCS;
> +		     IEEE80211_HW_RX_INCLUDES_FCS |
> +		     IEEE80211_HW_SIGNAL_UNSPEC;
>  	dev->channel_change_time = 1000;	/* TODO: find actual value */
> -	dev->max_rssi = 127;
> +	dev->max_signal = 127;
>
>  	priv->tx_stats[0].limit = 5;
>  	dev->queues = 1;
> diff --git a/drivers/net/wireless/rt2x00/rt2400pci.c
> b/drivers/net/wireless/rt2x00/rt2400pci.c index 247fbbf..afa565c 100644
> --- a/drivers/net/wireless/rt2x00/rt2400pci.c
> +++ b/drivers/net/wireless/rt2x00/rt2400pci.c
> @@ -1361,10 +1361,9 @@ static void rt2400pci_probe_hw_mode(struct
> rt2x00_dev *rt2x00dev) /*
>  	 * Initialize all hw fields.
>  	 */
> -	rt2x00dev->hw->flags = IEEE80211_HW_HOST_BROADCAST_PS_BUFFERING;
> +	rt2x00dev->hw->flags = IEEE80211_HW_HOST_BROADCAST_PS_BUFFERING |
> +			       IEEE80211_HW_SIGNAL_DBM;
>  	rt2x00dev->hw->extra_tx_headroom = 0;
> -	rt2x00dev->hw->max_signal = MAX_SIGNAL;
> -	rt2x00dev->hw->max_rssi = MAX_RX_SSI;
>  	rt2x00dev->hw->queues = 2;
>
>  	SET_IEEE80211_DEV(rt2x00dev->hw, &rt2x00dev_pci(rt2x00dev)->dev);
> diff --git a/drivers/net/wireless/rt2x00/rt2500pci.c
> b/drivers/net/wireless/rt2x00/rt2500pci.c index 0d53c75..c06f1b5 100644
> --- a/drivers/net/wireless/rt2x00/rt2500pci.c
> +++ b/drivers/net/wireless/rt2x00/rt2500pci.c
> @@ -1680,10 +1680,10 @@ static void rt2500pci_probe_hw_mode(struct
> rt2x00_dev *rt2x00dev) /*
>  	 * Initialize all hw fields.
>  	 */
> -	rt2x00dev->hw->flags = IEEE80211_HW_HOST_BROADCAST_PS_BUFFERING;
> +	rt2x00dev->hw->flags = IEEE80211_HW_HOST_BROADCAST_PS_BUFFERING |
> +			       IEEE80211_HW_SIGNAL_DBM;
> +
>  	rt2x00dev->hw->extra_tx_headroom = 0;
> -	rt2x00dev->hw->max_signal = MAX_SIGNAL;
> -	rt2x00dev->hw->max_rssi = MAX_RX_SSI;
>  	rt2x00dev->hw->queues = 2;
>
>  	SET_IEEE80211_DEV(rt2x00dev->hw, &rt2x00dev_pci(rt2x00dev)->dev);
> diff --git a/drivers/net/wireless/rt2x00/rt2500usb.c
> b/drivers/net/wireless/rt2x00/rt2500usb.c index 80b34d4..88bafdf 100644
> --- a/drivers/net/wireless/rt2x00/rt2500usb.c
> +++ b/drivers/net/wireless/rt2x00/rt2500usb.c
> @@ -1587,10 +1587,10 @@ static void rt2500usb_probe_hw_mode(struct
> rt2x00_dev *rt2x00dev) rt2x00dev->hw->flags =
>  	    IEEE80211_HW_HOST_GEN_BEACON_TEMPLATE |
>  	    IEEE80211_HW_RX_INCLUDES_FCS |
> -	    IEEE80211_HW_HOST_BROADCAST_PS_BUFFERING;
> +	    IEEE80211_HW_HOST_BROADCAST_PS_BUFFERING |
> +	    IEEE80211_HW_SIGNAL_DBM;
> +
>  	rt2x00dev->hw->extra_tx_headroom = TXD_DESC_SIZE;
> -	rt2x00dev->hw->max_signal = MAX_SIGNAL;
> -	rt2x00dev->hw->max_rssi = MAX_RX_SSI;
>  	rt2x00dev->hw->queues = 2;
>
>  	SET_IEEE80211_DEV(rt2x00dev->hw, &rt2x00dev_usb(rt2x00dev)->dev);
> diff --git a/drivers/net/wireless/rt2x00/rt2x00dev.c
> b/drivers/net/wireless/rt2x00/rt2x00dev.c index 9929b15..f51a50b 100644
> --- a/drivers/net/wireless/rt2x00/rt2x00dev.c
> +++ b/drivers/net/wireless/rt2x00/rt2x00dev.c
> @@ -600,9 +600,9 @@ void rt2x00lib_rxdone(struct queue_entry *entry,
>  	rt2x00dev->link.qual.rx_success++;
>
>  	rx_status->rate_idx = idx;
> -	rx_status->signal =
> +	rx_status->qual =
>  	    rt2x00lib_calculate_link_signal(rt2x00dev, rxdesc->rssi);
> -	rx_status->ssi = rxdesc->rssi;
> +	rx_status->signal = rxdesc->rssi;
>  	rx_status->flag = rxdesc->flags;
>  	rx_status->antenna = rt2x00dev->link.ant.active.rx;
>
> diff --git a/drivers/net/wireless/rt2x00/rt61pci.c
> b/drivers/net/wireless/rt2x00/rt61pci.c index 98af4d2..eaf23b9 100644
> --- a/drivers/net/wireless/rt2x00/rt61pci.c
> +++ b/drivers/net/wireless/rt2x00/rt61pci.c
> @@ -2245,10 +2245,9 @@ static void rt61pci_probe_hw_mode(struct rt2x00_dev
> *rt2x00dev) */
>  	rt2x00dev->hw->flags =
>  	    IEEE80211_HW_HOST_GEN_BEACON_TEMPLATE |
> -	    IEEE80211_HW_HOST_BROADCAST_PS_BUFFERING;
> +	    IEEE80211_HW_HOST_BROADCAST_PS_BUFFERING |
> +	    IEEE80211_HW_SIGNAL_DBM;
>  	rt2x00dev->hw->extra_tx_headroom = 0;
> -	rt2x00dev->hw->max_signal = MAX_SIGNAL;
> -	rt2x00dev->hw->max_rssi = MAX_RX_SSI;
>  	rt2x00dev->hw->queues = 4;
>
>  	SET_IEEE80211_DEV(rt2x00dev->hw, &rt2x00dev_pci(rt2x00dev)->dev);
> diff --git a/drivers/net/wireless/rt2x00/rt73usb.c
> b/drivers/net/wireless/rt2x00/rt73usb.c index 351d95c..51c5575 100644
> --- a/drivers/net/wireless/rt2x00/rt73usb.c
> +++ b/drivers/net/wireless/rt2x00/rt73usb.c
> @@ -1830,10 +1830,9 @@ static void rt73usb_probe_hw_mode(struct rt2x00_dev
> *rt2x00dev) */
>  	rt2x00dev->hw->flags =
>  	    IEEE80211_HW_HOST_GEN_BEACON_TEMPLATE |
> -	    IEEE80211_HW_HOST_BROADCAST_PS_BUFFERING;
> +	    IEEE80211_HW_HOST_BROADCAST_PS_BUFFERING |
> +	    IEEE80211_HW_SIGNAL_DBM;
>  	rt2x00dev->hw->extra_tx_headroom = TXD_DESC_SIZE;
> -	rt2x00dev->hw->max_signal = MAX_SIGNAL;
> -	rt2x00dev->hw->max_rssi = MAX_RX_SSI;
>  	rt2x00dev->hw->queues = 4;
>
>  	SET_IEEE80211_DEV(rt2x00dev->hw, &rt2x00dev_usb(rt2x00dev)->dev);
> diff --git a/drivers/net/wireless/rtl8180_dev.c
> b/drivers/net/wireless/rtl8180_dev.c index c181f23..c220998 100644
> --- a/drivers/net/wireless/rtl8180_dev.c
> +++ b/drivers/net/wireless/rtl8180_dev.c
> @@ -132,8 +132,8 @@ static void rtl8180_handle_rx(struct ieee80211_hw *dev)
>
>  			rx_status.antenna = (flags2 >> 15) & 1;
>  			/* TODO: improve signal/rssi reporting */
> -			rx_status.signal = flags2 & 0xFF;
> -			rx_status.ssi = (flags2 >> 8) & 0x7F;
> +			rx_status.qual = flags2 & 0xFF;
> +			rx_status.signal = (flags2 >> 8) & 0x7F;
>  			/* XXX: is this correct? */
>  			rx_status.rate_idx = (flags >> 20) & 0xF;
>  			rx_status.freq = dev->conf.channel->center_freq;
> @@ -894,9 +894,10 @@ static int __devinit rtl8180_probe(struct pci_dev
> *pdev, dev->wiphy->bands[IEEE80211_BAND_2GHZ] = &priv->band;
>
>  	dev->flags = IEEE80211_HW_HOST_BROADCAST_PS_BUFFERING |
> -		     IEEE80211_HW_RX_INCLUDES_FCS;
> +		     IEEE80211_HW_RX_INCLUDES_FCS |
> +		     IEEE80211_HW_SIGNAL_UNSPEC;
>  	dev->queues = 1;
> -	dev->max_rssi = 65;
> +	dev->max_signal = 65;
>
>  	reg = rtl818x_ioread32(priv, &priv->map->TX_CONF);
>  	reg &= RTL818X_TX_CONF_HWVER_MASK;
> diff --git a/drivers/net/wireless/rtl8187_dev.c
> b/drivers/net/wireless/rtl8187_dev.c index d5787b3..e14c842 100644
> --- a/drivers/net/wireless/rtl8187_dev.c
> +++ b/drivers/net/wireless/rtl8187_dev.c
> @@ -261,8 +261,8 @@ static void rtl8187_rx_cb(struct urb *urb)
>  	}
>
>  	rx_status.antenna = (hdr->signal >> 7) & 1;
> -	rx_status.signal = 64 - min(hdr->noise, (u8)64);
> -	rx_status.ssi = signal;
> +	rx_status.qual = 64 - min(hdr->noise, (u8)64);
> +	rx_status.signal = signal;
>  	rx_status.rate_idx = rate;
>  	rx_status.freq = dev->conf.channel->center_freq;
>  	rx_status.band = dev->conf.channel->band;
> @@ -740,11 +740,11 @@ static int __devinit rtl8187_probe(struct
> usb_interface *intf,
>
>  	priv->mode = IEEE80211_IF_TYPE_MNTR;
>  	dev->flags = IEEE80211_HW_HOST_BROADCAST_PS_BUFFERING |
> -		     IEEE80211_HW_RX_INCLUDES_FCS;
> +		     IEEE80211_HW_RX_INCLUDES_FCS |
> +		     IEEE80211_HW_SIGNAL_UNSPEC;
>  	dev->extra_tx_headroom = sizeof(struct rtl8187_tx_hdr);
>  	dev->queues = 1;
> -	dev->max_rssi = 65;
> -	dev->max_signal = 64;
> +	dev->max_signal = 65;
>
>  	eeprom.data = dev;
>  	eeprom.register_read = rtl8187_eeprom_register_read;
> diff --git a/drivers/net/wireless/zd1211rw/zd_mac.c
> b/drivers/net/wireless/zd1211rw/zd_mac.c index 69c45ca..6286eb2 100644
> --- a/drivers/net/wireless/zd1211rw/zd_mac.c
> +++ b/drivers/net/wireless/zd1211rw/zd_mac.c
> @@ -638,7 +638,7 @@ static int filter_ack(struct ieee80211_hw *hw, struct
> ieee80211_hdr *rx_hdr,
>
>  			memset(&status, 0, sizeof(status));
>  			status.flags = IEEE80211_TX_STATUS_ACK;
> -			status.ack_signal = stats->ssi;
> +			status.ack_signal = stats->signal;
>  			__skb_unlink(skb, q);
>  			tx_status(hw, skb, &status, 1);
>  			goto out;
> @@ -691,8 +691,8 @@ int zd_mac_rx(struct ieee80211_hw *hw, const u8
> *buffer, unsigned int length)
>
>  	stats.freq = zd_channels[_zd_chip_get_channel(&mac->chip) -
> 1].center_freq; stats.band = IEEE80211_BAND_2GHZ;
> -	stats.ssi = status->signal_strength;
> -	stats.signal = zd_rx_qual_percent(buffer,
> +	stats.signal = status->signal_strength;
> +	stats.qual = zd_rx_qual_percent(buffer,
>  		                          length - sizeof(struct rx_status),
>  		                          status);
>
> @@ -982,10 +982,10 @@ struct ieee80211_hw *zd_mac_alloc_hw(struct
> usb_interface *intf) hw->wiphy->bands[IEEE80211_BAND_2GHZ] = &mac->band;
>
>  	hw->flags = IEEE80211_HW_RX_INCLUDES_FCS |
> -		    IEEE80211_HW_HOST_GEN_BEACON_TEMPLATE;
> -	hw->max_rssi = 100;
> -	hw->max_signal = 100;
> +		    IEEE80211_HW_HOST_GEN_BEACON_TEMPLATE |
> +		    IEEE80211_HW_SIGNAL_DB;
>
> +	hw->max_signal = 100;
>  	hw->queues = 1;
>  	hw->extra_tx_headroom = sizeof(struct zd_ctrlset);
>
> diff --git a/include/net/mac80211.h b/include/net/mac80211.h
> index 75a3460..909956c 100644
> --- a/include/net/mac80211.h
> +++ b/include/net/mac80211.h
> @@ -336,13 +336,16 @@ enum mac80211_rx_flags {
>   * The low-level driver should provide this information (the subset
>   * supported by hardware) to the 802.11 code with each received
>   * frame.
> + *
>   * @mactime: value in microseconds of the 64-bit Time Synchronization
> Function * 	(TSF) timer when the first data symbol (MPDU) arrived at the
> hardware. * @band: the active band when this frame was received
>   * @freq: frequency the radio was tuned to when receiving this frame, in
> MHz - * @ssi: signal strength when receiving this frame
> - * @signal: used as 'qual' in statistics reporting
> - * @noise: PHY noise when receiving this frame
> + * @signal: signal strength when receiving this frame, either in dBm, in
> dB or + *	unspecified depending on the hardware capabilities flags
> + *	@IEEE80211_HW_SIGNAL_*
> + * @noise: noise when receiving this frame, in dBm.
> + * @qual: overall signal quality indication, in percent (0-100).
>   * @antenna: antenna used
>   * @rate_idx: index of data rate into band's supported rates
>   * @flag: %RX_FLAG_*
> @@ -351,9 +354,9 @@ struct ieee80211_rx_status {
>  	u64 mactime;
>  	enum ieee80211_band band;
>  	int freq;
> -	int ssi;
>  	int signal;
>  	int noise;
> +	int qual;
>  	int antenna;
>  	int rate_idx;
>  	int flag;
> @@ -392,7 +395,8 @@ enum ieee80211_tx_status_flags {
>   * 	relevant only if IEEE80211_TX_STATUS_AMPDU was set.
>   * @ampdu_ack_map: block ack bit map for the aggregation.
>   * 	relevant only if IEEE80211_TX_STATUS_AMPDU was set.
> - * @ack_signal: signal strength of the ACK frame
> + * @ack_signal: signal strength of the ACK frame either in dBm, dB or
> unspec + *	depending on hardware capabilites flags @IEEE80211_HW_SIGNAL_*
> */
>  struct ieee80211_tx_status {
>  	struct ieee80211_tx_control control;
> @@ -703,6 +707,25 @@ enum ieee80211_tkip_key_type {
>   * @IEEE80211_HW_2GHZ_SHORT_PREAMBLE_INCAPABLE:
>   *	Hardware is not capable of receiving frames with short preamble on
>   *	the 2.4 GHz band.
> + *
> + * @IEEE80211_HW_SIGNAL_UNSPEC:
> + *	Hardware can provide signal values but we don't know its units. We
> + *	expect values between 0 and @max_signal.
> + *	If possible please provide dB or dBm instead.
> + *
> + * @IEEE80211_HW_SIGNAL_DB:
> + *	Hardware gives signal values in dB, decibel difference from an
> + *	arbitrary, fixed reference. We expect values between 0 and @max_signal.
> + *	If possible please provide dBm instead.
> + *
> + * @IEEE80211_HW_SIGNAL_DBM:
> + *	Hardware gives signal values in dBm, decibel difference from
> + *	one milliwatt. This is the preferred method since it is standardized
> + *	between different devices. @max_signal does not need to be set.
> + *
> + * @IEEE80211_HW_NOISE_DBM:
> + *	Hardware can provide noise (radio interference) values in units dBm,
> + *      decibel difference from one milliwatt.
>   */
>  enum ieee80211_hw_flags {
>  	IEEE80211_HW_HOST_GEN_BEACON_TEMPLATE		= 1<<0,
> @@ -710,6 +733,10 @@ enum ieee80211_hw_flags {
>  	IEEE80211_HW_HOST_BROADCAST_PS_BUFFERING	= 1<<2,
>  	IEEE80211_HW_2GHZ_SHORT_SLOT_INCAPABLE		= 1<<3,
>  	IEEE80211_HW_2GHZ_SHORT_PREAMBLE_INCAPABLE	= 1<<4,
> +	IEEE80211_HW_SIGNAL_UNSPEC			= 1<<5,
> +	IEEE80211_HW_SIGNAL_DB				= 1<<6,
> +	IEEE80211_HW_SIGNAL_DBM				= 1<<7,
> +	IEEE80211_HW_NOISE_DBM				= 1<<8,
>  };
>
>  /**
> @@ -740,12 +767,8 @@ enum ieee80211_hw_flags {
>   *
>   * @channel_change_time: time (in microseconds) it takes to change
> channels. *
> - * @max_rssi: Maximum value for ssi in RX information, use
> - *	negative numbers for dBm and 0 to indicate no support.
> - *
> - * @max_signal: like @max_rssi, but for the signal value.
> - *
> - * @max_noise: like @max_rssi, but for the noise value.
> + * @max_signal: Maximum value for signal (rssi) in RX information, used
> + *     only when @IEEE80211_HW_SIGNAL_UNSPEC or @IEEE80211_HW_SIGNAL_DB
>   *
>   * @queues: number of available hardware transmit queues for
>   *	data packets. WMM/QoS requires at least four, these
> @@ -775,9 +798,7 @@ struct ieee80211_hw {
>  	int channel_change_time;
>  	int vif_data_size;
>  	u16 queues, ampdu_queues;
> -	s8 max_rssi;
>  	s8 max_signal;
> -	s8 max_noise;
>  };
>
>  /**
> diff --git a/net/ieee80211/ieee80211_rx.c b/net/ieee80211/ieee80211_rx.c
> index 200ee1e..69dbc34 100644
> --- a/net/ieee80211/ieee80211_rx.c
> +++ b/net/ieee80211/ieee80211_rx.c
> @@ -391,7 +391,7 @@ int ieee80211_rx(struct ieee80211_device *ieee, struct
> sk_buff *skb,
>
>  		wstats.updated = 0;
>  		if (rx_stats->mask & IEEE80211_STATMASK_RSSI) {
> -			wstats.level = rx_stats->rssi;
> +			wstats.level = rx_stats->signal;
>  			wstats.updated |= IW_QUAL_LEVEL_UPDATED;
>  		} else
>  			wstats.updated |= IW_QUAL_LEVEL_INVALID;
> diff --git a/net/mac80211/debugfs_sta.c b/net/mac80211/debugfs_sta.c
> index 676a932..c54c094 100644
> --- a/net/mac80211/debugfs_sta.c
> +++ b/net/mac80211/debugfs_sta.c
> @@ -63,8 +63,8 @@ STA_FILE(tx_fragments, tx_fragments, LU);
>  STA_FILE(tx_filtered, tx_filtered_count, LU);
>  STA_FILE(tx_retry_failed, tx_retry_failed, LU);
>  STA_FILE(tx_retry_count, tx_retry_count, LU);
> -STA_FILE(last_rssi, last_rssi, D);
>  STA_FILE(last_signal, last_signal, D);
> +STA_FILE(last_qual, last_qual, D);
>  STA_FILE(last_noise, last_noise, D);
>  STA_FILE(channel_use, channel_use, D);
>  STA_FILE(wep_weak_iv_count, wep_weak_iv_count, LU);
> diff --git a/net/mac80211/ieee80211_i.h b/net/mac80211/ieee80211_i.h
> index d82ed20..73b7ab3 100644
> --- a/net/mac80211/ieee80211_i.h
> +++ b/net/mac80211/ieee80211_i.h
> @@ -82,7 +82,7 @@ struct ieee80211_sta_bss {
>  	u16 capability; /* host byte order */
>  	enum ieee80211_band band;
>  	int freq;
> -	int rssi, signal, noise;
> +	int signal, noise, qual;
>  	u8 *wpa_ie;
>  	size_t wpa_ie_len;
>  	u8 *rsn_ie;
> diff --git a/net/mac80211/main.c b/net/mac80211/main.c
> index 55e7611..630ae31 100644
> --- a/net/mac80211/main.c
> +++ b/net/mac80211/main.c
> @@ -1701,13 +1701,13 @@ int ieee80211_register_hw(struct ieee80211_hw *hw)
>
>  	local->hw.conf.beacon_int = 1000;
>
> -	local->wstats_flags |= local->hw.max_rssi ?
> -			       IW_QUAL_LEVEL_UPDATED : IW_QUAL_LEVEL_INVALID;
> -	local->wstats_flags |= local->hw.max_signal ?
> +	local->wstats_flags |= local->hw.flags & (IEEE80211_HW_SIGNAL_UNSPEC |
> +						  IEEE80211_HW_SIGNAL_DB |
> +						  IEEE80211_HW_SIGNAL_DBM) ?
>  			       IW_QUAL_QUAL_UPDATED : IW_QUAL_QUAL_INVALID;
> -	local->wstats_flags |= local->hw.max_noise ?
> +	local->wstats_flags |= local->hw.flags & IEEE80211_HW_NOISE_DBM ?
>  			       IW_QUAL_NOISE_UPDATED : IW_QUAL_NOISE_INVALID;
> -	if (local->hw.max_rssi < 0 || local->hw.max_noise < 0)
> +	if (local->hw.flags & IEEE80211_HW_SIGNAL_DBM)
>  		local->wstats_flags |= IW_QUAL_DBM;
>
>  	result = sta_info_start(local);
> diff --git a/net/mac80211/mlme.c b/net/mac80211/mlme.c
> index cb01995..c671eb0 100644
> --- a/net/mac80211/mlme.c
> +++ b/net/mac80211/mlme.c
> @@ -1950,8 +1950,8 @@ static void ieee80211_rx_mgmt_assoc_resp(struct
> ieee80211_sub_if_data *sdata, local->hw.conf.channel->center_freq,
>  					   ifsta->ssid, ifsta->ssid_len);
>  		if (bss) {
> -			sta->last_rssi = bss->rssi;
>  			sta->last_signal = bss->signal;
> +			sta->last_qual = bss->qual;
>  			sta->last_noise = bss->noise;
>  			ieee80211_rx_bss_put(dev, bss);
>  		}
> @@ -2619,9 +2619,9 @@ static void ieee80211_rx_bss_info(struct net_device
> *dev,
>
>  	bss->timestamp = beacon_timestamp;
>  	bss->last_update = jiffies;
> -	bss->rssi = rx_status->ssi;
>  	bss->signal = rx_status->signal;
>  	bss->noise = rx_status->noise;
> +	bss->qual = rx_status->qual;
>  	if (!beacon && !bss->probe_resp)
>  		bss->probe_resp = true;
>
> @@ -3419,9 +3419,9 @@ static int ieee80211_sta_config_auth(struct
> net_device *dev, !ieee80211_sta_match_ssid(ifsta, bss->ssid,
> bss->ssid_len)) continue;
>
> -		if (!selected || top_rssi < bss->rssi) {
> +		if (!selected || top_rssi < bss->signal) {
>  			selected = bss;
> -			top_rssi = bss->rssi;
> +			top_rssi = bss->signal;
>  		}
>  	}
>  	if (selected)
> @@ -4052,8 +4052,8 @@ ieee80211_sta_scan_result(struct net_device *dev,
>
>  	memset(&iwe, 0, sizeof(iwe));
>  	iwe.cmd = IWEVQUAL;
> -	iwe.u.qual.qual = bss->signal;
> -	iwe.u.qual.level = bss->rssi;
> +	iwe.u.qual.qual = bss->qual;
> +	iwe.u.qual.level = bss->signal;
>  	iwe.u.qual.noise = bss->noise;
>  	iwe.u.qual.updated = local->wstats_flags;
>  	current_ev = iwe_stream_add_event(current_ev, end_buf, &iwe,
> diff --git a/net/mac80211/rx.c b/net/mac80211/rx.c
> index e8b89c8..3ea856f 100644
> --- a/net/mac80211/rx.c
> +++ b/net/mac80211/rx.c
> @@ -209,7 +209,7 @@ ieee80211_rx_monitor(struct ieee80211_local *local,
> struct sk_buff *origskb, cpu_to_le16(IEEE80211_CHAN_DYN |
>  					    IEEE80211_CHAN_2GHZ);
>
> -		rtfixed->antsignal = status->ssi;
> +		rtfixed->antsignal = status->signal;
>  		rthdr->it_len = cpu_to_le16(rtap_len);
>  	}
>
> @@ -720,8 +720,8 @@ ieee80211_rx_h_sta_process(struct ieee80211_rx_data
> *rx)
>
>  	sta->rx_fragments++;
>  	sta->rx_bytes += rx->skb->len;
> -	sta->last_rssi = rx->status->ssi;
>  	sta->last_signal = rx->status->signal;
> +	sta->last_qual = rx->status->qual;
>  	sta->last_noise = rx->status->noise;
>
>  	if (!(rx->fc & IEEE80211_FCTL_MOREFRAGS)) {
> diff --git a/net/mac80211/sta_info.h b/net/mac80211/sta_info.h
> index f8c95bc..9c5d0db 100644
> --- a/net/mac80211/sta_info.h
> +++ b/net/mac80211/sta_info.h
> @@ -217,8 +217,8 @@ struct sta_info {
>  				       * from this STA */
>  	unsigned long rx_fragments; /* number of received MPDUs */
>  	unsigned long rx_dropped; /* number of dropped MPDUs from this STA */
> -	int last_rssi; /* RSSI of last received frame from this STA */
>  	int last_signal; /* signal of last received frame from this STA */
> +	int last_qual;  /* qual of last received frame from this STA */
>  	int last_noise; /* noise of last received frame from this STA */
>  	/* last received seq/frag number from this STA (per RX queue) */
>  	__le16 last_seq_ctrl[NUM_RX_DATA_QUEUES];
> diff --git a/net/mac80211/wext.c b/net/mac80211/wext.c
> index 76e1de1..6a342a9 100644
> --- a/net/mac80211/wext.c
> +++ b/net/mac80211/wext.c
> @@ -169,14 +169,26 @@ static int ieee80211_ioctl_giwrange(struct net_device
> *dev, range->num_encoding_sizes = 2;
>  	range->max_encoding_tokens = NUM_DEFAULT_KEYS;
>
> -	range->max_qual.qual = local->hw.max_signal;
> -	range->max_qual.level = local->hw.max_rssi;
> -	range->max_qual.noise = local->hw.max_noise;
> +	if (local->hw.flags & IEEE80211_HW_SIGNAL_UNSPEC ||
> +	    local->hw.flags & IEEE80211_HW_SIGNAL_DB)
> +		range->max_qual.level = local->hw.max_signal;
> +	else if  (local->hw.flags & IEEE80211_HW_SIGNAL_DBM)
> +		range->max_qual.level = -110;
> +	else
> +		range->max_qual.level = 0;
> +
> +	if (local->hw.flags & IEEE80211_HW_NOISE_DBM)
> +		range->max_qual.noise = -110;
> +	else
> +		range->max_qual.noise = 0;
> +
> +	range->max_qual.qual = 100;
>  	range->max_qual.updated = local->wstats_flags;
>
> -	range->avg_qual.qual = local->hw.max_signal/2;
> -	range->avg_qual.level = 0;
> -	range->avg_qual.noise = 0;
> +	range->avg_qual.qual = 50;
> +	/* not always true but better than nothing */
> +	range->avg_qual.level = range->max_qual.level / 2;
> +	range->avg_qual.noise = range->max_qual.noise / 2;
>  	range->avg_qual.updated = local->wstats_flags;
>
>  	range->enc_capa = IW_ENC_CAPA_WPA | IW_ENC_CAPA_WPA2 |
> @@ -996,8 +1008,8 @@ static struct iw_statistics
> *ieee80211_get_wireless_stats(struct net_device *dev wstats->qual.noise =
> 0;
>  		wstats->qual.updated = IW_QUAL_ALL_INVALID;
>  	} else {
> -		wstats->qual.level = sta->last_rssi;
> -		wstats->qual.qual = sta->last_signal;
> +		wstats->qual.level = sta->last_signal;
> +		wstats->qual.qual = sta->last_qual;
>  		wstats->qual.noise = sta->last_noise;
>  		wstats->qual.updated = local->wstats_flags;
>  	}
>
> --
> To unsubscribe from this list: send the line "unsubscribe linux-wireless"
> in the body of a message to majordomo@xxxxxxxxxxxxxxx
> More majordomo info at  http://vger.kernel.org/majordomo-info.html


--
To unsubscribe from this list: send the line "unsubscribe linux-wireless" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at  http://vger.kernel.org/majordomo-info.html

[Index of Archives]     [Linux Host AP]     [ATH6KL]     [Linux Bluetooth]     [Linux Netdev]     [Kernel Newbies]     [Linux Kernel]     [IDE]     [Security]     [Git]     [Netfilter]     [Bugtraq]     [Yosemite News]     [MIPS Linux]     [ARM Linux]     [Linux Security]     [Linux RAID]     [Linux ATA RAID]     [Samba]     [Device Mapper]
  Powered by Linux