瀏覽代碼

iwlwifi: report the rate index as an MCS rate number

If transmit in HT rate, report the rate index as an MCS rate number
instead of an index. so "iw" can display correct BitRate

Signed-off-by: Wey-Yi Guy <wey-yi.w.guy@intel.com>
Signed-off-by: Reinette Chatre <reinette.chatre@intel.com>
Signed-off-by: John W. Linville <linville@tuxdriver.com>
Wey-Yi Guy 16 年之前
父節點
當前提交
a9c146b369
共有 1 個文件被更改,包括 27 次插入4 次删除
  1. 27 4
      drivers/net/wireless/iwlwifi/iwl-agn-rs.c

+ 27 - 4
drivers/net/wireless/iwlwifi/iwl-agn-rs.c

@@ -270,6 +270,8 @@ const static struct iwl_rate_mcs_info iwl_rate_mcs[IWL_RATE_COUNT] = {
   {"60", "64QAM 5/6"}
   {"60", "64QAM 5/6"}
 };
 };
 
 
+#define MCS_INDEX_PER_STREAM	(8)
+
 static inline u8 rs_extract_rate(u32 rate_n_flags)
 static inline u8 rs_extract_rate(u32 rate_n_flags)
 {
 {
 	return (u8)(rate_n_flags & 0xFF);
 	return (u8)(rate_n_flags & 0xFF);
@@ -2518,12 +2520,33 @@ static void rs_get_rate(void *priv_r, struct ieee80211_sta *sta, void *priv_sta,
 		}
 		}
 	}
 	}
 
 
-	if (rate_idx < 0 || rate_idx > IWL_RATE_COUNT)
-		rate_idx = rate_lowest_index(sband, sta);
-	else if (sband->band == IEEE80211_BAND_5GHZ)
+	if (lq_sta->last_rate_n_flags & RATE_MCS_HT_MSK) {
 		rate_idx -= IWL_FIRST_OFDM_RATE;
 		rate_idx -= IWL_FIRST_OFDM_RATE;
-
+		/* 6M and 9M shared same MCS index */
+		rate_idx = (rate_idx > 0) ? (rate_idx - 1) : 0;
+		if (rs_extract_rate(lq_sta->last_rate_n_flags) >=
+		    IWL_RATE_MIMO3_6M_PLCP)
+			rate_idx = rate_idx + (2 * MCS_INDEX_PER_STREAM);
+		else if (rs_extract_rate(lq_sta->last_rate_n_flags) >=
+			 IWL_RATE_MIMO2_6M_PLCP)
+			rate_idx = rate_idx + MCS_INDEX_PER_STREAM;
+		info->control.rates[0].flags = IEEE80211_TX_RC_MCS;
+		if (lq_sta->last_rate_n_flags & RATE_MCS_SGI_MSK)
+			info->control.rates[0].flags |= IEEE80211_TX_RC_SHORT_GI;
+		if (lq_sta->last_rate_n_flags & RATE_MCS_DUP_MSK)
+			info->control.rates[0].flags |= IEEE80211_TX_RC_DUP_DATA;
+		if (lq_sta->last_rate_n_flags & RATE_MCS_FAT_MSK)
+			info->control.rates[0].flags |= IEEE80211_TX_RC_40_MHZ_WIDTH;
+		if (lq_sta->last_rate_n_flags & RATE_MCS_GF_MSK)
+			info->control.rates[0].flags |= IEEE80211_TX_RC_GREEN_FIELD;
+	} else {
+		if (rate_idx < 0 || rate_idx > IWL_RATE_COUNT)
+			rate_idx = rate_lowest_index(sband, sta);
+		else if (sband->band == IEEE80211_BAND_5GHZ)
+			rate_idx -= IWL_FIRST_OFDM_RATE;
+	}
 	info->control.rates[0].idx = rate_idx;
 	info->control.rates[0].idx = rate_idx;
+
 }
 }
 
 
 static void *rs_alloc_sta(void *priv_rate, struct ieee80211_sta *sta,
 static void *rs_alloc_sta(void *priv_rate, struct ieee80211_sta *sta,