aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--drivers/net/wireless/rt2x00/rt2x00dev.c11
-rw-r--r--drivers/net/wireless/rt2x00/rt2x00lib.h4
-rw-r--r--drivers/net/wireless/rt2x00/rt2x00mac.c5
-rw-r--r--drivers/net/wireless/rt2x00/rt2x00queue.c6
-rw-r--r--drivers/net/wireless/rt2x00/rt2x00queue.h5
-rw-r--r--include/net/mac80211.h2
-rw-r--r--net/mac80211/tx.c4
7 files changed, 23 insertions, 14 deletions
diff --git a/drivers/net/wireless/rt2x00/rt2x00dev.c b/drivers/net/wireless/rt2x00/rt2x00dev.c
index 6c6d0ac3554..4a4b7e42fe6 100644
--- a/drivers/net/wireless/rt2x00/rt2x00dev.c
+++ b/drivers/net/wireless/rt2x00/rt2x00dev.c
@@ -205,6 +205,7 @@ void rt2x00lib_txdone(struct queue_entry *entry,
enum data_queue_qid qid = skb_get_queue_mapping(entry->skb);
unsigned int header_length = ieee80211_get_hdrlen_from_skb(entry->skb);
u8 rate_idx, rate_flags, retry_rates;
+ u8 skbdesc_flags = skbdesc->flags;
unsigned int i;
bool success;
@@ -287,12 +288,12 @@ void rt2x00lib_txdone(struct queue_entry *entry,
}
/*
- * Only send the status report to mac80211 when TX status was
- * requested by it. If this was a extra frame coming through
- * a mac80211 library call (RTS/CTS) then we should not send the
- * status report back.
+ * Only send the status report to mac80211 when it's a frame
+ * that originated in mac80211. If this was a extra frame coming
+ * through a mac80211 library call (RTS/CTS) then we should not
+ * send the status report back.
*/
- if (tx_info->flags & IEEE80211_TX_CTL_REQ_TX_STATUS)
+ if (!(skbdesc_flags & SKBDESC_NOT_MAC80211))
ieee80211_tx_status_irqsafe(rt2x00dev->hw, entry->skb);
else
dev_kfree_skb_irq(entry->skb);
diff --git a/drivers/net/wireless/rt2x00/rt2x00lib.h b/drivers/net/wireless/rt2x00/rt2x00lib.h
index c1f48acaee4..be2e37fb407 100644
--- a/drivers/net/wireless/rt2x00/rt2x00lib.h
+++ b/drivers/net/wireless/rt2x00/rt2x00lib.h
@@ -162,8 +162,10 @@ void rt2x00queue_remove_l2pad(struct sk_buff *skb, unsigned int header_length);
* rt2x00queue_write_tx_frame - Write TX frame to hardware
* @queue: Queue over which the frame should be send
* @skb: The skb to send
+ * @local: frame is not from mac80211
*/
-int rt2x00queue_write_tx_frame(struct data_queue *queue, struct sk_buff *skb);
+int rt2x00queue_write_tx_frame(struct data_queue *queue, struct sk_buff *skb,
+ bool local);
/**
* rt2x00queue_update_beacon - Send new beacon from mac80211 to hardware
diff --git a/drivers/net/wireless/rt2x00/rt2x00mac.c b/drivers/net/wireless/rt2x00/rt2x00mac.c
index eed093d3453..9c90ceb0ffc 100644
--- a/drivers/net/wireless/rt2x00/rt2x00mac.c
+++ b/drivers/net/wireless/rt2x00/rt2x00mac.c
@@ -66,7 +66,6 @@ static int rt2x00mac_tx_rts_cts(struct rt2x00_dev *rt2x00dev,
rts_info = IEEE80211_SKB_CB(skb);
rts_info->control.rates[0].flags &= ~IEEE80211_TX_RC_USE_RTS_CTS;
rts_info->control.rates[0].flags &= ~IEEE80211_TX_RC_USE_CTS_PROTECT;
- rts_info->flags &= ~IEEE80211_TX_CTL_REQ_TX_STATUS;
if (tx_info->control.rates[0].flags & IEEE80211_TX_RC_USE_CTS_PROTECT)
rts_info->flags |= IEEE80211_TX_CTL_NO_ACK;
@@ -91,7 +90,7 @@ static int rt2x00mac_tx_rts_cts(struct rt2x00_dev *rt2x00dev,
frag_skb->data, data_length, tx_info,
(struct ieee80211_rts *)(skb->data));
- retval = rt2x00queue_write_tx_frame(queue, skb);
+ retval = rt2x00queue_write_tx_frame(queue, skb, true);
if (retval) {
dev_kfree_skb_any(skb);
WARNING(rt2x00dev, "Failed to send RTS/CTS frame.\n");
@@ -153,7 +152,7 @@ int rt2x00mac_tx(struct ieee80211_hw *hw, struct sk_buff *skb)
goto exit_fail;
}
- if (rt2x00queue_write_tx_frame(queue, skb))
+ if (rt2x00queue_write_tx_frame(queue, skb, false))
goto exit_fail;
if (rt2x00queue_threshold(queue))
diff --git a/drivers/net/wireless/rt2x00/rt2x00queue.c b/drivers/net/wireless/rt2x00/rt2x00queue.c
index 02972a036bc..eaedee8c05c 100644
--- a/drivers/net/wireless/rt2x00/rt2x00queue.c
+++ b/drivers/net/wireless/rt2x00/rt2x00queue.c
@@ -454,7 +454,8 @@ static void rt2x00queue_write_tx_descriptor(struct queue_entry *entry,
rt2x00dev->ops->lib->kick_tx_queue(rt2x00dev, queue->qid);
}
-int rt2x00queue_write_tx_frame(struct data_queue *queue, struct sk_buff *skb)
+int rt2x00queue_write_tx_frame(struct data_queue *queue, struct sk_buff *skb,
+ bool local)
{
struct ieee80211_tx_info *tx_info;
struct queue_entry *entry = rt2x00queue_get_entry(queue, Q_INDEX);
@@ -495,6 +496,9 @@ int rt2x00queue_write_tx_frame(struct data_queue *queue, struct sk_buff *skb)
skbdesc->tx_rate_idx = rate_idx;
skbdesc->tx_rate_flags = rate_flags;
+ if (local)
+ skbdesc->flags |= SKBDESC_NOT_MAC80211;
+
/*
* When hardware encryption is supported, and this frame
* is to be encrypted, we should strip the IV/EIV data from
diff --git a/drivers/net/wireless/rt2x00/rt2x00queue.h b/drivers/net/wireless/rt2x00/rt2x00queue.h
index 97c7895c0ec..70775e5ba1a 100644
--- a/drivers/net/wireless/rt2x00/rt2x00queue.h
+++ b/drivers/net/wireless/rt2x00/rt2x00queue.h
@@ -94,12 +94,15 @@ enum data_queue_qid {
* mac80211 but was stripped for processing by the driver.
* @SKBDESC_L2_PADDED: Payload has been padded for 4-byte alignment,
* the padded bytes are located between header and payload.
+ * @SKBDESC_NOT_MAC80211: Frame didn't originate from mac80211,
+ * don't try to pass it back.
*/
enum skb_frame_desc_flags {
SKBDESC_DMA_MAPPED_RX = 1 << 0,
SKBDESC_DMA_MAPPED_TX = 1 << 1,
SKBDESC_IV_STRIPPED = 1 << 2,
- SKBDESC_L2_PADDED = 1 << 3
+ SKBDESC_L2_PADDED = 1 << 3,
+ SKBDESC_NOT_MAC80211 = 1 << 4,
};
/**
diff --git a/include/net/mac80211.h b/include/net/mac80211.h
index f34f4ca7016..3754ea405c8 100644
--- a/include/net/mac80211.h
+++ b/include/net/mac80211.h
@@ -219,7 +219,7 @@ struct ieee80211_bss_conf {
*
* These flags are used with the @flags member of &ieee80211_tx_info.
*
- * @IEEE80211_TX_CTL_REQ_TX_STATUS: request TX status callback for this frame.
+ * @IEEE80211_TX_CTL_REQ_TX_STATUS: require TX status callback for this frame.
* @IEEE80211_TX_CTL_ASSIGN_SEQ: The driver has to assign a sequence
* number to this frame, taking care of not overwriting the fragment
* number and increasing the sequence number only when the
diff --git a/net/mac80211/tx.c b/net/mac80211/tx.c
index 5af2f40ea4d..943def2b07d 100644
--- a/net/mac80211/tx.c
+++ b/net/mac80211/tx.c
@@ -1443,8 +1443,6 @@ static void ieee80211_xmit(struct ieee80211_sub_if_data *sdata,
msecs_to_jiffies(local->hw.conf.dynamic_ps_timeout));
}
- info->flags |= IEEE80211_TX_CTL_REQ_TX_STATUS;
-
rcu_read_lock();
if (unlikely(sdata->vif.type == NL80211_IFTYPE_MONITOR)) {
@@ -1575,6 +1573,8 @@ netdev_tx_t ieee80211_monitor_start_xmit(struct sk_buff *skb,
memset(info, 0, sizeof(*info));
+ info->flags |= IEEE80211_TX_CTL_REQ_TX_STATUS;
+
/* pass the radiotap header up to xmit */
ieee80211_xmit(IEEE80211_DEV_TO_SUB_IF(dev), skb);
return NETDEV_TX_OK;