Ver código fonte

rtl8187: make CTS-to-self protection work

CTS protection was not working properly because the HW needs
RTS flag to be asserted, and it need also RTS duration field to be
filled with CTS-to-self duration.

This patch makes the driver to do this.

Signed-off-by: Andrea Merello <andrea.merello@gmail.com>
Signed-off-by: John W. Linville <linville@tuxdriver.com>
Andrea Merello 11 anos atrás
pai
commit
d294d0286a
1 arquivos alterados com 8 adições e 1 exclusões
  1. 8 1
      drivers/net/wireless/rtl818x/rtl8187/dev.c

+ 8 - 1
drivers/net/wireless/rtl818x/rtl8187/dev.c

@@ -253,14 +253,21 @@ static void rtl8187_tx(struct ieee80211_hw *dev,
 	flags |= ieee80211_get_tx_rate(dev, info)->hw_value << 24;
 	flags |= ieee80211_get_tx_rate(dev, info)->hw_value << 24;
 	if (ieee80211_has_morefrags(tx_hdr->frame_control))
 	if (ieee80211_has_morefrags(tx_hdr->frame_control))
 		flags |= RTL818X_TX_DESC_FLAG_MOREFRAG;
 		flags |= RTL818X_TX_DESC_FLAG_MOREFRAG;
+
+	/* HW will perform RTS-CTS when only RTS flags is set.
+	 * HW will perform CTS-to-self when both RTS and CTS flags are set.
+	 * RTS rate and RTS duration will be used also for CTS-to-self.
+	 */
 	if (info->control.rates[0].flags & IEEE80211_TX_RC_USE_RTS_CTS) {
 	if (info->control.rates[0].flags & IEEE80211_TX_RC_USE_RTS_CTS) {
 		flags |= RTL818X_TX_DESC_FLAG_RTS;
 		flags |= RTL818X_TX_DESC_FLAG_RTS;
 		flags |= ieee80211_get_rts_cts_rate(dev, info)->hw_value << 19;
 		flags |= ieee80211_get_rts_cts_rate(dev, info)->hw_value << 19;
 		rts_dur = ieee80211_rts_duration(dev, priv->vif,
 		rts_dur = ieee80211_rts_duration(dev, priv->vif,
 						 skb->len, info);
 						 skb->len, info);
 	} else if (info->control.rates[0].flags & IEEE80211_TX_RC_USE_CTS_PROTECT) {
 	} else if (info->control.rates[0].flags & IEEE80211_TX_RC_USE_CTS_PROTECT) {
-		flags |= RTL818X_TX_DESC_FLAG_CTS;
+		flags |= RTL818X_TX_DESC_FLAG_RTS | RTL818X_TX_DESC_FLAG_CTS;
 		flags |= ieee80211_get_rts_cts_rate(dev, info)->hw_value << 19;
 		flags |= ieee80211_get_rts_cts_rate(dev, info)->hw_value << 19;
+		rts_dur = ieee80211_ctstoself_duration(dev, priv->vif,
+						 skb->len, info);
 	}
 	}
 
 
 	if (info->flags & IEEE80211_TX_CTL_ASSIGN_SEQ) {
 	if (info->flags & IEEE80211_TX_CTL_ASSIGN_SEQ) {