Commit 49a9feaf authored by Johannes Berg's avatar Johannes Berg
Browse files

Merge tag 'rtw-next-2025-11-21-v2' of https://github.com/pkshih/rtw

Ping-Ke Shih says:
==================
rtw-next patches for v6.19

Main changes are about rtw89 USB support, which two USB devices are added
with proper TX status, and other notable items are listed below.

rtl8xxxu:

 - fix 40MHz bandwidth connection

rtw89:

 - support USB devices RTL8852AU and RTL8852CU

 - report TX status from air for USB devices

 - resolve racing between processes of TX and TX report

 - resolve racing of skb queue of C2H events

 - support injected packets with bandwidth and data rate

 - more materials for coming RTL8922DE
==================

Link: https://patch.msgid.link/45eed1763a354460acba15a8e69f9e3e@realtek.com


Signed-off-by: default avatarJohannes Berg <johannes.berg@intel.com>
parents b688a944 dbf9b7bb
Loading
Loading
Loading
Loading
+2 −7
Original line number Diff line number Diff line
@@ -1023,9 +1023,6 @@ static int rtl8180_init_rx_ring(struct ieee80211_hw *dev)
		dma_addr_t *mapping;
		entry = priv->rx_ring + priv->rx_ring_sz*i;
		if (!skb) {
			dma_free_coherent(&priv->pdev->dev,
					  priv->rx_ring_sz * 32,
					  priv->rx_ring, priv->rx_ring_dma);
			wiphy_err(dev->wiphy, "Cannot allocate RX skb\n");
			return -ENOMEM;
		}
@@ -1037,9 +1034,7 @@ static int rtl8180_init_rx_ring(struct ieee80211_hw *dev)

		if (dma_mapping_error(&priv->pdev->dev, *mapping)) {
			kfree_skb(skb);
			dma_free_coherent(&priv->pdev->dev,
					  priv->rx_ring_sz * 32,
					  priv->rx_ring, priv->rx_ring_dma);
			priv->rx_buf[i] = NULL;
			wiphy_err(dev->wiphy, "Cannot map DMA for RX skb\n");
			return -ENOMEM;
		}
@@ -1130,7 +1125,7 @@ static int rtl8180_start(struct ieee80211_hw *dev)

	ret = rtl8180_init_rx_ring(dev);
	if (ret)
		return ret;
		goto err_free_rings;

	for (i = 0; i < (dev->queues + 1); i++)
		if ((ret = rtl8180_init_tx_ring(dev, i, 16)))
+19 −8
Original line number Diff line number Diff line
@@ -338,14 +338,16 @@ static void rtl8187_rx_cb(struct urb *urb)
	spin_unlock_irqrestore(&priv->rx_queue.lock, f);
	skb_put(skb, urb->actual_length);

	if (unlikely(urb->status)) {
		dev_kfree_skb_irq(skb);
		return;
	}
	if (unlikely(urb->status))
		goto free_skb;

	if (!priv->is_rtl8187b) {
		struct rtl8187_rx_hdr *hdr =
			(typeof(hdr))(skb_tail_pointer(skb) - sizeof(*hdr));
		struct rtl8187_rx_hdr *hdr;

		if (skb->len < sizeof(struct rtl8187_rx_hdr))
			goto free_skb;

		hdr = (typeof(hdr))(skb_tail_pointer(skb) - sizeof(*hdr));
		flags = le32_to_cpu(hdr->flags);
		/* As with the RTL8187B below, the AGC is used to calculate
		 * signal strength. In this case, the scaling
@@ -355,8 +357,12 @@ static void rtl8187_rx_cb(struct urb *urb)
		rx_status.antenna = (hdr->signal >> 7) & 1;
		rx_status.mactime = le64_to_cpu(hdr->mac_time);
	} else {
		struct rtl8187b_rx_hdr *hdr =
			(typeof(hdr))(skb_tail_pointer(skb) - sizeof(*hdr));
		struct rtl8187b_rx_hdr *hdr;

		if (skb->len < sizeof(struct rtl8187b_rx_hdr))
			goto free_skb;

		hdr = (typeof(hdr))(skb_tail_pointer(skb) - sizeof(*hdr));
		/* The Realtek datasheet for the RTL8187B shows that the RX
		 * header contains the following quantities: signal quality,
		 * RSSI, AGC, the received power in dB, and the measured SNR.
@@ -409,6 +415,11 @@ static void rtl8187_rx_cb(struct urb *urb)
		skb_unlink(skb, &priv->rx_queue);
		dev_kfree_skb_irq(skb);
	}
	return;

free_skb:
	dev_kfree_skb_irq(skb);
	return;
}

static int rtl8187_init_urbs(struct ieee80211_hw *dev)
+79 −1
Original line number Diff line number Diff line
@@ -593,6 +593,84 @@ static int rtl8192cu_power_on(struct rtl8xxxu_priv *priv)
	return 0;
}

static void rtl8192cu_power_off(struct rtl8xxxu_priv *priv)
{
	u32 val32;
	u16 val16;
	u8 val8;
	int i;

	/*
	 * Workaround for 8188RU LNA power leakage problem.
	 */
	if (priv->rtl_chip == RTL8188R) {
		val32 = rtl8xxxu_read32(priv, REG_FPGA0_XCD_RF_PARM);
		val32 |= BIT(1);
		rtl8xxxu_write32(priv, REG_FPGA0_XCD_RF_PARM, val32);
	}

	/* _DisableRFAFEAndResetBB */
	rtl8xxxu_write8(priv, REG_TXPAUSE, 0xff);
	rtl8xxxu_write_rfreg_mask(priv, RF_A, RF6052_REG_AC, 0xff, 0);

	rtl8xxxu_write8_set(priv, REG_APSD_CTRL, APSD_CTRL_OFF);
	rtl8xxxu_write32_set(priv, REG_FPGA0_XCD_RF_PARM, FPGA0_RF_PARM_CLK_GATE);

	rtl8xxxu_write8(priv, REG_SYS_FUNC,
			SYS_FUNC_USBA | SYS_FUNC_USBD | SYS_FUNC_BB_GLB_RSTN);
	rtl8xxxu_write8(priv, REG_SYS_FUNC, SYS_FUNC_USBA | SYS_FUNC_USBD);

	/* _ResetDigitalProcedure1 */
	if (rtl8xxxu_read8(priv, REG_MCU_FW_DL) & MCU_FW_DL_READY) {
		rtl8xxxu_write8(priv, REG_MCU_FW_DL, 0x00);

		rtl8xxxu_write8(priv, REG_FWIMR, 0x20);

		rtl8xxxu_write8(priv, REG_HMTFR + 3, 0x20);

		for (i = 0; i < 100; i++) {
			val16 = rtl8xxxu_read16(priv, REG_SYS_FUNC);
			if (!(val16 & SYS_FUNC_CPU_ENABLE))
				break;

			fsleep(50);
		}

		if (i == 100) {
			rtl8xxxu_write8(priv, REG_SYS_FUNC + 1,
					(SYS_FUNC_HWPDN | SYS_FUNC_ELDR) >> 8);
			msleep(10);
		}
	}

	val8 = (SYS_FUNC_HWPDN | SYS_FUNC_ELDR | SYS_FUNC_CPU_ENABLE) >> 8;
	rtl8xxxu_write8(priv, REG_SYS_FUNC + 1, val8);

	/* _DisableGPIO */
	rtl8xxxu_write16(priv, REG_GPIO_PIN_CTRL + 2, 0);
	val32 = rtl8xxxu_read32(priv, REG_GPIO_PIN_CTRL) & 0xffff00ff;
	val32 |= (val32 & 0xff) << 8;
	val32 |= 0x00ff0000;
	rtl8xxxu_write32(priv, REG_GPIO_PIN_CTRL, val32);

	rtl8xxxu_write8(priv, REG_GPIO_MUXCFG + 3, 0);
	val16 = rtl8xxxu_read16(priv, REG_GPIO_MUXCFG + 2) & 0xff0f;
	val16 |= (val16 & 0xf) << 4;
	val16 |= 0x0780;
	rtl8xxxu_write16(priv, REG_GPIO_MUXCFG + 2, val16);

	/* _DisableAnalog */
	val8 = 0x23;
	if (priv->vendor_umc && priv->chip_cut == 1)
		val8 |= BIT(3);
	rtl8xxxu_write8(priv, REG_SPS0_CTRL, val8);

	val16 = APS_FSMCO_HOST | APS_FSMCO_HW_SUSPEND | APS_FSMCO_PFM_ALDN;
	rtl8xxxu_write16(priv, REG_APS_FSMCO, val16);

	rtl8xxxu_write8(priv, REG_RSV_CTRL, 0x0e);
}

static int rtl8192cu_led_brightness_set(struct led_classdev *led_cdev,
					enum led_brightness brightness)
{
@@ -618,7 +696,7 @@ struct rtl8xxxu_fileops rtl8192cu_fops = {
	.parse_efuse = rtl8192cu_parse_efuse,
	.load_firmware = rtl8192cu_load_firmware,
	.power_on = rtl8192cu_power_on,
	.power_off = rtl8xxxu_power_off,
	.power_off = rtl8192cu_power_off,
	.read_efuse = rtl8xxxu_read_efuse,
	.reset_8051 = rtl8xxxu_reset_8051,
	.llt_init = rtl8xxxu_init_llt_table,
+114 −1
Original line number Diff line number Diff line
@@ -411,6 +411,119 @@ static int rtl8723au_power_on(struct rtl8xxxu_priv *priv)
	return ret;
}

static int rtl8723au_active_to_emu(struct rtl8xxxu_priv *priv)
{
	u8 val8;
	int count, ret = 0;

	/* Start of rtl8723AU_card_enable_flow */
	/* Act to Cardemu sequence*/
	/* Turn off RF */
	rtl8xxxu_write8(priv, REG_RF_CTRL, 0);

	/* 0x004E[7] = 0, switch DPDT_SEL_P output from register 0x0065[2] */
	val8 = rtl8xxxu_read8(priv, REG_LEDCFG2);
	val8 &= ~LEDCFG2_DPDT_SELECT;
	rtl8xxxu_write8(priv, REG_LEDCFG2, val8);

	/* 0x0005[1] = 1 turn off MAC by HW state machine*/
	val8 = rtl8xxxu_read8(priv, REG_APS_FSMCO + 1);
	val8 |= BIT(1);
	rtl8xxxu_write8(priv, REG_APS_FSMCO + 1, val8);

	for (count = RTL8XXXU_MAX_REG_POLL; count; count--) {
		val8 = rtl8xxxu_read8(priv, REG_APS_FSMCO + 1);
		if ((val8 & BIT(1)) == 0)
			break;
		udelay(10);
	}

	if (!count) {
		dev_warn(&priv->udev->dev, "%s: Disabling MAC timed out\n",
			 __func__);
		ret = -EBUSY;
		goto exit;
	}

	/* 0x0000[5] = 1 analog Ips to digital, 1:isolation */
	val8 = rtl8xxxu_read8(priv, REG_SYS_ISO_CTRL);
	val8 |= SYS_ISO_ANALOG_IPS;
	rtl8xxxu_write8(priv, REG_SYS_ISO_CTRL, val8);

	/* 0x0020[0] = 0 disable LDOA12 MACRO block*/
	val8 = rtl8xxxu_read8(priv, REG_LDOA15_CTRL);
	val8 &= ~LDOA15_ENABLE;
	rtl8xxxu_write8(priv, REG_LDOA15_CTRL, val8);

exit:
	return ret;
}

static int rtl8723au_emu_to_disabled(struct rtl8xxxu_priv *priv)
{
	u8 val8;

	/* 0x0007[7:0] = 0x20 SOP option to disable BG/MB */
	rtl8xxxu_write8(priv, REG_APS_FSMCO + 3, 0x20);

	/* 0x04[12:11] = 01 enable WL suspend */
	val8 = rtl8xxxu_read8(priv, REG_APS_FSMCO + 1);
	val8 &= ~BIT(4);
	val8 |= BIT(3);
	rtl8xxxu_write8(priv, REG_APS_FSMCO + 1, val8);

	val8 = rtl8xxxu_read8(priv, REG_APS_FSMCO + 1);
	val8 |= BIT(7);
	rtl8xxxu_write8(priv, REG_APS_FSMCO + 1, val8);

	/* 0x48[16] = 1 to enable GPIO9 as EXT wakeup */
	val8 = rtl8xxxu_read8(priv, REG_GPIO_INTM + 2);
	val8 |= BIT(0);
	rtl8xxxu_write8(priv, REG_GPIO_INTM + 2, val8);

	return 0;
}

static void rtl8723au_power_off(struct rtl8xxxu_priv *priv)
{
	u8 val8;
	u16 val16;

	rtl8xxxu_flush_fifo(priv);

	rtl8xxxu_active_to_lps(priv);

	/* Turn off RF */
	rtl8xxxu_write8(priv, REG_RF_CTRL, 0x00);

	/* Reset Firmware if running in RAM */
	if (rtl8xxxu_read8(priv, REG_MCU_FW_DL) & MCU_FW_RAM_SEL)
		rtl8xxxu_firmware_self_reset(priv);

	/* Reset MCU */
	val16 = rtl8xxxu_read16(priv, REG_SYS_FUNC);
	val16 &= ~SYS_FUNC_CPU_ENABLE;
	rtl8xxxu_write16(priv, REG_SYS_FUNC, val16);

	/* Reset MCU ready status */
	rtl8xxxu_write8(priv, REG_MCU_FW_DL, 0x00);

	rtl8723au_active_to_emu(priv);
	rtl8723au_emu_to_disabled(priv);

	/* Reset MCU IO Wrapper */
	val8 = rtl8xxxu_read8(priv, REG_RSV_CTRL + 1);
	val8 &= ~BIT(0);
	rtl8xxxu_write8(priv, REG_RSV_CTRL + 1, val8);

	val8 = rtl8xxxu_read8(priv, REG_RSV_CTRL + 1);
	val8 |= BIT(0);
	rtl8xxxu_write8(priv, REG_RSV_CTRL + 1, val8);

	/* RSV_CTRL 0x1C[7:0] = 0x0e  lock ISO/CLK/Power control register */
	rtl8xxxu_write8(priv, REG_RSV_CTRL, 0x0e);
}

#define XTAL1	GENMASK(23, 18)
#define XTAL0	GENMASK(17, 12)

@@ -492,7 +605,7 @@ struct rtl8xxxu_fileops rtl8723au_fops = {
	.parse_efuse = rtl8723au_parse_efuse,
	.load_firmware = rtl8723au_load_firmware,
	.power_on = rtl8723au_power_on,
	.power_off = rtl8xxxu_power_off,
	.power_off = rtl8723au_power_off,
	.read_efuse = rtl8xxxu_read_efuse,
	.reset_8051 = rtl8xxxu_reset_8051,
	.llt_init = rtl8xxxu_init_llt_table,
+41 −147
Original line number Diff line number Diff line
@@ -20,7 +20,6 @@
#define DRIVER_NAME "rtl8xxxu"

int rtl8xxxu_debug;
static bool rtl8xxxu_ht40_2g;
static bool rtl8xxxu_dma_aggregation;
static int rtl8xxxu_dma_agg_timeout = -1;
static int rtl8xxxu_dma_agg_pages = -1;
@@ -45,8 +44,6 @@ MODULE_FIRMWARE("rtlwifi/rtl8192fufw.bin");

module_param_named(debug, rtl8xxxu_debug, int, 0600);
MODULE_PARM_DESC(debug, "Set debug mask");
module_param_named(ht40_2g, rtl8xxxu_ht40_2g, bool, 0600);
MODULE_PARM_DESC(ht40_2g, "Enable HT40 support on the 2.4GHz band");
module_param_named(dma_aggregation, rtl8xxxu_dma_aggregation, bool, 0600);
MODULE_PARM_DESC(dma_aggregation, "Enable DMA packet aggregation");
module_param_named(dma_agg_timeout, rtl8xxxu_dma_agg_timeout, int, 0600);
@@ -1252,7 +1249,7 @@ void rtl8xxxu_gen1_config_channel(struct ieee80211_hw *hw)
		opmode &= ~BW_OPMODE_20MHZ;
		rtl8xxxu_write8(priv, REG_BW_OPMODE, opmode);
		rsr &= ~RSR_RSC_BANDWIDTH_40M;
		if (sec_ch_above)
		if (!sec_ch_above)
			rsr |= RSR_RSC_UPPER_SUB_CHANNEL;
		else
			rsr |= RSR_RSC_LOWER_SUB_CHANNEL;
@@ -1321,9 +1318,8 @@ void rtl8xxxu_gen1_config_channel(struct ieee80211_hw *hw)

	for (i = RF_A; i < priv->rf_paths; i++) {
		val32 = rtl8xxxu_read_rfreg(priv, i, RF6052_REG_MODE_AG);
		if (hw->conf.chandef.width == NL80211_CHAN_WIDTH_40)
			val32 &= ~MODE_AG_CHANNEL_20MHZ;
		else
		val32 &= ~MODE_AG_BW_MASK;
		if (hw->conf.chandef.width != NL80211_CHAN_WIDTH_40)
			val32 |= MODE_AG_CHANNEL_20MHZ;
		rtl8xxxu_write_rfreg(priv, i, RF6052_REG_MODE_AG, val32);
	}
@@ -1374,9 +1370,11 @@ void rtl8xxxu_gen2_config_channel(struct ieee80211_hw *hw)
		    hw->conf.chandef.chan->center_freq) {
			sec_ch_above = 1;
			channel += 2;
			subchannel = 2;
		} else {
			sec_ch_above = 0;
			channel -= 2;
			subchannel = 1;
		}

		val32 = rtl8xxxu_read32(priv, REG_FPGA0_RF_MODE);
@@ -3637,54 +3635,6 @@ static void rtl8xxxu_set_ampdu_min_space(struct rtl8xxxu_priv *priv, u8 density)
	rtl8xxxu_write8(priv, REG_AMPDU_MIN_SPACE, val8);
}

static int rtl8xxxu_active_to_emu(struct rtl8xxxu_priv *priv)
{
	u8 val8;
	int count, ret = 0;

	/* Start of rtl8723AU_card_enable_flow */
	/* Act to Cardemu sequence*/
	/* Turn off RF */
	rtl8xxxu_write8(priv, REG_RF_CTRL, 0);

	/* 0x004E[7] = 0, switch DPDT_SEL_P output from register 0x0065[2] */
	val8 = rtl8xxxu_read8(priv, REG_LEDCFG2);
	val8 &= ~LEDCFG2_DPDT_SELECT;
	rtl8xxxu_write8(priv, REG_LEDCFG2, val8);

	/* 0x0005[1] = 1 turn off MAC by HW state machine*/
	val8 = rtl8xxxu_read8(priv, REG_APS_FSMCO + 1);
	val8 |= BIT(1);
	rtl8xxxu_write8(priv, REG_APS_FSMCO + 1, val8);

	for (count = RTL8XXXU_MAX_REG_POLL; count; count--) {
		val8 = rtl8xxxu_read8(priv, REG_APS_FSMCO + 1);
		if ((val8 & BIT(1)) == 0)
			break;
		udelay(10);
	}

	if (!count) {
		dev_warn(&priv->udev->dev, "%s: Disabling MAC timed out\n",
			 __func__);
		ret = -EBUSY;
		goto exit;
	}

	/* 0x0000[5] = 1 analog Ips to digital, 1:isolation */
	val8 = rtl8xxxu_read8(priv, REG_SYS_ISO_CTRL);
	val8 |= SYS_ISO_ANALOG_IPS;
	rtl8xxxu_write8(priv, REG_SYS_ISO_CTRL, val8);

	/* 0x0020[0] = 0 disable LDOA12 MACRO block*/
	val8 = rtl8xxxu_read8(priv, REG_LDOA15_CTRL);
	val8 &= ~LDOA15_ENABLE;
	rtl8xxxu_write8(priv, REG_LDOA15_CTRL, val8);

exit:
	return ret;
}

int rtl8xxxu_active_to_lps(struct rtl8xxxu_priv *priv)
{
	u8 val8;
@@ -3761,31 +3711,6 @@ void rtl8xxxu_disabled_to_emu(struct rtl8xxxu_priv *priv)
	rtl8xxxu_write8(priv, REG_APS_FSMCO + 1, val8);
}

static int rtl8xxxu_emu_to_disabled(struct rtl8xxxu_priv *priv)
{
	u8 val8;

	/* 0x0007[7:0] = 0x20 SOP option to disable BG/MB */
	rtl8xxxu_write8(priv, REG_APS_FSMCO + 3, 0x20);

	/* 0x04[12:11] = 01 enable WL suspend */
	val8 = rtl8xxxu_read8(priv, REG_APS_FSMCO + 1);
	val8 &= ~BIT(4);
	val8 |= BIT(3);
	rtl8xxxu_write8(priv, REG_APS_FSMCO + 1, val8);

	val8 = rtl8xxxu_read8(priv, REG_APS_FSMCO + 1);
	val8 |= BIT(7);
	rtl8xxxu_write8(priv, REG_APS_FSMCO + 1, val8);

	/* 0x48[16] = 1 to enable GPIO9 as EXT wakeup */
	val8 = rtl8xxxu_read8(priv, REG_GPIO_INTM + 2);
	val8 |= BIT(0);
	rtl8xxxu_write8(priv, REG_GPIO_INTM + 2, val8);

	return 0;
}

int rtl8xxxu_flush_fifo(struct rtl8xxxu_priv *priv)
{
	struct device *dev = &priv->udev->dev;
@@ -3863,56 +3788,6 @@ void rtl8xxxu_gen2_usb_quirks(struct rtl8xxxu_priv *priv)
	rtl8xxxu_write32(priv, REG_TXDMA_OFFSET_CHK, val32);
}

void rtl8xxxu_power_off(struct rtl8xxxu_priv *priv)
{
	u8 val8;
	u16 val16;
	u32 val32;

	/*
	 * Workaround for 8188RU LNA power leakage problem.
	 */
	if (priv->rtl_chip == RTL8188R) {
		val32 = rtl8xxxu_read32(priv, REG_FPGA0_XCD_RF_PARM);
		val32 |= BIT(1);
		rtl8xxxu_write32(priv, REG_FPGA0_XCD_RF_PARM, val32);
	}

	rtl8xxxu_flush_fifo(priv);

	rtl8xxxu_active_to_lps(priv);

	/* Turn off RF */
	rtl8xxxu_write8(priv, REG_RF_CTRL, 0x00);

	/* Reset Firmware if running in RAM */
	if (rtl8xxxu_read8(priv, REG_MCU_FW_DL) & MCU_FW_RAM_SEL)
		rtl8xxxu_firmware_self_reset(priv);

	/* Reset MCU */
	val16 = rtl8xxxu_read16(priv, REG_SYS_FUNC);
	val16 &= ~SYS_FUNC_CPU_ENABLE;
	rtl8xxxu_write16(priv, REG_SYS_FUNC, val16);

	/* Reset MCU ready status */
	rtl8xxxu_write8(priv, REG_MCU_FW_DL, 0x00);

	rtl8xxxu_active_to_emu(priv);
	rtl8xxxu_emu_to_disabled(priv);

	/* Reset MCU IO Wrapper */
	val8 = rtl8xxxu_read8(priv, REG_RSV_CTRL + 1);
	val8 &= ~BIT(0);
	rtl8xxxu_write8(priv, REG_RSV_CTRL + 1, val8);

	val8 = rtl8xxxu_read8(priv, REG_RSV_CTRL + 1);
	val8 |= BIT(0);
	rtl8xxxu_write8(priv, REG_RSV_CTRL + 1, val8);

	/* RSV_CTRL 0x1C[7:0] = 0x0e  lock ISO/CLK/Power control register */
	rtl8xxxu_write8(priv, REG_RSV_CTRL, 0x0e);
}

void rtl8723bu_set_ps_tdma(struct rtl8xxxu_priv *priv,
			   u8 arg1, u8 arg2, u8 arg3, u8 arg4, u8 arg5)
{
@@ -5018,8 +4893,7 @@ rtl8xxxu_bss_info_changed(struct ieee80211_hw *hw, struct ieee80211_vif *vif,
				sgi = 1;

			highest_rate = fls(ramask) - 1;
			if (rtl8xxxu_ht40_2g &&
			    (sta->deflink.ht_cap.cap & IEEE80211_HT_CAP_SUP_WIDTH_20_40))
			if (sta->deflink.ht_cap.cap & IEEE80211_HT_CAP_SUP_WIDTH_20_40)
				bw = RATE_INFO_BW_40;
			else
				bw = RATE_INFO_BW_20;
@@ -5345,9 +5219,19 @@ rtl8xxxu_fill_txdesc_v1(struct ieee80211_hw *hw, struct ieee80211_hdr *hdr,
		tx_desc->txdw5 |= cpu_to_le32(TXDESC32_RETRY_LIMIT_ENABLE);
	}

	if (ieee80211_is_data_qos(hdr->frame_control))
	if (ieee80211_is_data_qos(hdr->frame_control)) {
		tx_desc->txdw4 |= cpu_to_le32(TXDESC32_QOS);

		if (conf_is_ht40(&hw->conf)) {
			tx_desc->txdw4 |= cpu_to_le32(TXDESC_DATA_BW);

			if (conf_is_ht40_minus(&hw->conf))
				tx_desc->txdw4 |= cpu_to_le32(TXDESC_PRIME_CH_OFF_UPPER);
			else
				tx_desc->txdw4 |= cpu_to_le32(TXDESC_PRIME_CH_OFF_LOWER);
		}
	}

	if (short_preamble)
		tx_desc->txdw4 |= cpu_to_le32(TXDESC32_SHORT_PREAMBLE);

@@ -5813,7 +5697,7 @@ static void jaguar2_rx_parse_phystats_type1(struct rtl8xxxu_priv *priv,
			 !rtl8xxxu_is_sta_sta(priv) &&
			 (rtl8xxxu_is_packet_match_bssid(priv, hdr, 0) ||
			  rtl8xxxu_is_packet_match_bssid(priv, hdr, 1));
	u8 pwdb_max = 0;
	u8 pwdb_max = 0, rxsc;
	int rx_path;

	if (parse_cfo) {
@@ -5828,6 +5712,16 @@ static void jaguar2_rx_parse_phystats_type1(struct rtl8xxxu_priv *priv,
		pwdb_max = max(pwdb_max, phy_stats1->pwdb[rx_path]);

	rx_status->signal = pwdb_max - 110;

	if (rxmcs >= DESC_RATE_6M && rxmcs <= DESC_RATE_54M)
		rxsc = phy_stats1->l_rxsc;
	else
		rxsc = phy_stats1->ht_rxsc;

	if (phy_stats1->rf_mode == 0 || rxsc == 1 || rxsc == 2)
		rx_status->bw = RATE_INFO_BW_20;
	else
		rx_status->bw = RATE_INFO_BW_40;
}

static void jaguar2_rx_parse_phystats_type2(struct rtl8xxxu_priv *priv,
@@ -6454,6 +6348,8 @@ int rtl8xxxu_parse_rxdesc16(struct rtl8xxxu_priv *priv, struct sk_buff *skb)
					rtl8xxxu_rx_update_rssi(priv,
								rx_status,
								hdr);
			} else {
				rx_status->flag |= RX_FLAG_NO_SIGNAL_VAL;
			}

			rx_status->mactime = rx_desc->tsfl;
@@ -6560,6 +6456,8 @@ int rtl8xxxu_parse_rxdesc24(struct rtl8xxxu_priv *priv, struct sk_buff *skb)
					rtl8xxxu_rx_update_rssi(priv,
								rx_status,
								hdr);
			} else {
				rx_status->flag |= RX_FLAG_NO_SIGNAL_VAL;
			}

			rx_status->mactime = rx_desc->tsfl;
@@ -7906,15 +7804,15 @@ static int rtl8xxxu_probe(struct usb_interface *interface,
		goto err_set_intfdata;
	}

	if (rtl8xxxu_debug & RTL8XXXU_DEBUG_EFUSE)
		rtl8xxxu_dump_efuse(priv);

	ret = priv->fops->parse_efuse(priv);
	if (ret) {
		dev_err(&udev->dev, "Fatal - failed to parse EFuse\n");
		goto err_set_intfdata;
	}

	if (rtl8xxxu_debug & RTL8XXXU_DEBUG_EFUSE)
		rtl8xxxu_dump_efuse(priv);

	rtl8xxxu_print_chipinfo(priv);

	ret = priv->fops->load_firmware(priv);
@@ -7949,7 +7847,8 @@ static int rtl8xxxu_probe(struct usb_interface *interface,
	sband->ht_cap.ht_supported = true;
	sband->ht_cap.ampdu_factor = IEEE80211_HT_MAX_AMPDU_64K;
	sband->ht_cap.ampdu_density = IEEE80211_HT_MPDU_DENSITY_16;
	sband->ht_cap.cap = IEEE80211_HT_CAP_SGI_20 | IEEE80211_HT_CAP_SGI_40;
	sband->ht_cap.cap = IEEE80211_HT_CAP_SGI_20 | IEEE80211_HT_CAP_SGI_40 |
			    IEEE80211_HT_CAP_SUP_WIDTH_20_40;
	memset(&sband->ht_cap.mcs, 0, sizeof(sband->ht_cap.mcs));
	sband->ht_cap.mcs.rx_mask[0] = 0xff;
	sband->ht_cap.mcs.rx_mask[4] = 0x01;
@@ -7958,15 +7857,7 @@ static int rtl8xxxu_probe(struct usb_interface *interface,
		sband->ht_cap.cap |= IEEE80211_HT_CAP_SGI_40;
	}
	sband->ht_cap.mcs.tx_params = IEEE80211_HT_MCS_TX_DEFINED;
	/*
	 * Some APs will negotiate HT20_40 in a noisy environment leading
	 * to miserable performance. Rather than defaulting to this, only
	 * enable it if explicitly requested at module load time.
	 */
	if (rtl8xxxu_ht40_2g) {
		dev_info(&udev->dev, "Enabling HT_20_40 on the 2.4GHz band\n");
		sband->ht_cap.cap |= IEEE80211_HT_CAP_SUP_WIDTH_20_40;
	}

	hw->wiphy->bands[NL80211_BAND_2GHZ] = sband;

	hw->wiphy->rts_threshold = 2347;
@@ -8136,6 +8027,9 @@ static const struct usb_device_id dev_table[] = {
/* TP-Link TL-WN823N V2 */
{USB_DEVICE_AND_INTERFACE_INFO(0x2357, 0x0135, 0xff, 0xff, 0xff),
	.driver_info = (unsigned long)&rtl8192fu_fops},
/* D-Link AN3U rev. A1 */
{USB_DEVICE_AND_INTERFACE_INFO(0x2001, 0x3328, 0xff, 0xff, 0xff),
	.driver_info = (unsigned long)&rtl8192fu_fops},
#ifdef CONFIG_RTL8XXXU_UNTESTED
/* Still supported by rtlwifi */
{USB_DEVICE_AND_INTERFACE_INFO(USB_VENDOR_ID_REALTEK, 0x8176, 0xff, 0xff, 0xff),
Loading