Merge android12-gs-pixel-5.10-sc-qpr3 into android13-gs-pixel-5.10-gs101-tm
Signed-off-by: Robin Peng <robinpeng@google.com>
Change-Id: I022dea5af7c2e4c3b5f7f7124c7053cbb25ad42c
diff --git a/BUILD.bazel b/BUILD.bazel
new file mode 100644
index 0000000..6a7b6dd
--- /dev/null
+++ b/BUILD.bazel
@@ -0,0 +1,20 @@
+# NOTE: THIS FILE IS EXPERIMENTAL FOR THE BAZEL MIGRATION AND NOT USED FOR
+# YOUR BUILDS CURRENTLY.
+#
+# It is not yet the source of truth for your build. If you're looking to modify
+# the build file, modify the Android.bp file instead. Do *not* modify this file
+# unless you have coordinated with the team managing the Soong to Bazel
+# migration.
+
+load("//build/kleaf:kernel.bzl", "kernel_module")
+
+kernel_module(
+ name = "bcmdhd4389.cloudripper",
+ outs = [
+ "bcmdhd4389.ko",
+ ],
+ kernel_build = "//private/gs-google:cloudripper",
+ visibility = [
+ "//private/gs-google:__pkg__",
+ ],
+)
diff --git a/Kbuild b/Kbuild
old mode 100755
new mode 100644
index d7534b6..8ed311c
--- a/Kbuild
+++ b/Kbuild
@@ -1,6 +1,6 @@
# bcmdhd
#
-# Copyright (C) 2021, Broadcom.
+# Copyright (C) 2022, Broadcom.
#
# Unless you and Broadcom execute a separate written software license
# agreement governing use of this software, this software is licensed to you
@@ -133,6 +133,11 @@
# Enable inband device wake feature
DHDCFLAGS += -DPCIE_INB_DW
+# Enable DS ack extended wait
+DHDCFLAGS += -DPCIE_INB_DSACK_EXT_WAIT
+
+# Prioritize ARP
+DHDCFLAGS += -DPRIORITIZE_ARP
# Debug check for PCIe read latency
#DHDCFLAGS += -DDBG_DW_CHK_PCIE_READ_LATENCY
@@ -238,8 +243,9 @@
DHDCFLAGS += -DAFFINITY_UPDATE_MIN_PERIOD_SEC=6
DHDCFLAGS += -DRESCHED_STREAK_MAX_HIGH=10
DHDCFLAGS += -DRESCHED_STREAK_MAX_LOW=2
- DHDCFLAGS += -DIRQ_AFFINITY_BIG_CORE=5
- DHDCFLAGS += -DIRQ_AFFINITY_SMALL_CORE=1
+ DHDCFLAGS += -DCLEAN_IRQ_AFFINITY_HINT
+ DHDCFLAGS += -DIRQ_AFFINITY_BIG_CORE=4
+ DHDCFLAGS += -DIRQ_AFFINITY_SMALL_CORE=4
endif
# Memory consumed by DHD
@@ -274,17 +280,28 @@
DHDCFLAGS += -DWL_MONITOR
# WLBR Regon coordinator
DHDCFLAGS += -DWBRC
+# DPC bounds
+ DHDCFLAGS += -DDHD_TX_CPL_BOUND=64
+ DHDCFLAGS += -DDHD_TX_POST_BOUND=128
+ DHDCFLAGS += -DDHD_RX_CPL_POST_BOUND=156
+ DHDCFLAGS += -DDHD_CTRL_CPL_POST_BOUND=64
endif
ifneq ($(CONFIG_FIB_RULES),)
# Debugability
# HAL File dump is supported only for iptable builds(brcm_wlan_iptables_defconfig)
ifneq ($(CONFIG_SOC_GOOGLE),)
-DHDCFLAGS += -DDHD_DEBUGABILITY_DEBUG_DUMP
+DHDCFLAGS += -DDHD_FILE_DUMP_EVENT
+DHDCFLAGS += -DDHD_HAL_RING_DUMP
+DHDCFLAGS += -DDHD_HAL_RING_DUMP_MEMDUMP
# Pixel platform only, to support ring data flushing properly
DHDCFLAGS += -DDHD_DUMP_START_COMMAND
+# Enable pktid logging
+DHDCFLAGS += -DDHD_MAP_PKTID_LOGGING
else
DHDCFLAGS += -DDHD_FILE_DUMP_EVENT
+# The debug dump file path is blank in DHD, it is defined in HAL.
+DHDCFLAGS += -DDHD_COMMON_DUMP_PATH="\"/\""
endif
DHDCFLAGS := $(filter-out -DDHD_DUMP_FILE_WRITE_FROM_KERNEL ,$(DHDCFLAGS))
endif
@@ -367,7 +384,9 @@
#Custom Mapping of DSCP to User Priority
DHDCFLAGS += -DWL_CUSTOM_MAPPING_OF_DSCP
# Enable below define for production
+ifneq ($(CONFIG_SOC_GOOGLE),)
DHDCFLAGS += -DMACADDR_PROVISION_ENFORCED
+endif
ifneq ($(CONFIG_BCMDHD_PCIE),)
DHDCFLAGS += -DDHD_WAKE_STATUS
endif
@@ -394,7 +413,6 @@
DHDCFLAGS += -DSET_SSID_FAIL_CUSTOM_RC=100
DHDCFLAGS += -DDHD_EVENT_LOG_FILTER
DHDCFLAGS += -DWL_CFGVENDOR_SEND_HANG_EVENT
-DHDCFLAGS += -DDHD_MAP_PKTID_LOGGING
# Packet
DHDCFLAGS += -DBLOCK_IPV6_PACKET
#DHDCFLAGS += -DDHD_DONOT_FORWARD_BCMEVENT_AS_NETWORK_PKT # NAN test failure
@@ -587,7 +605,9 @@
DHDCFLAGS += -DDUAL_ESCAN_RESULT_BUFFER
# NAN
-DHDCFLAGS += -DWL_NAN -DWL_NAN_DISC_CACHE -DWL_NANP2P
+DHDCFLAGS += -DWL_NAN -DWL_NAN_DISC_CACHE -DWL_NANP2P -DWL_NAN_INSTANT_MODE
+
+DHDCFLAGS += -DQOS_MAP_SET
# Thermal mitigation flag
DHDCFLAGS += -DWL_THERMAL_MITIGATION
@@ -680,6 +700,12 @@
# debug code to identify root cause of scan timeout due to syncid mismatch
DHDCFLAGS += -DSYNCID_MISMATCH_DEBUG
+# MSCS OFFLOAD
+DHDCFLAGS += -DWL_RAV_MSCS_NEG_IN_ASSOC
+
+# MAX_PFN_LIST_COUNT is defined as 64 in wlioctl_defs.h
+DHDCFLAGS += -DMAX_PFN_LIST_COUNT=16
+
##########################
# driver type
# m: module type driver
@@ -694,6 +720,10 @@
ifneq ($(filter y, $(CONFIG_BCM4389)),)
#6GHz support
DHDCFLAGS += -DWL_6G_BAND
+ # UNII4 channel support
+ DHDCFLAGS += -DWL_5P9G
+ # UNII-4 channel filter for non-sta roles
+ DHDCFLAGS += -DWL_UNII4_CHAN
endif
# For 4389 and 43752
@@ -882,6 +912,10 @@
DHDCFLAGS += -DBCM4389_CHIP_DEF -DSUPPORT_MULTIPLE_REVISION -DSUPPORT_MULTIPLE_REVISION_MAP
DHDCFLAGS += -DSUPPORT_MIXED_MODULES -DUSE_CID_CHECK -DSUPPORT_MULTIPLE_CHIPS
DHDCFLAGS += -DCONCAT_DEF_REV_FOR_NOMATCH_VID
+ # Detect NON DMA M2M corruption (MFG only)
+ DHDCFLAGS += -DDHD_NON_DMA_M2M_CORRUPTION
+ # Detect FW Memory Corruption (MFG only)
+ DHDCFLAGS += -DDHD_FW_MEM_CORRUPTION
endif
ifneq ($(CONFIG_BCMDHD_PCIE),)
DHDCFLAGS += -DDHD_LINUX_STD_FW_API
@@ -899,6 +933,10 @@
DHDCFLAGS += -DDHD_SUPPORT_VFS_CALL
# Skip pktlogging of data packets
DHDCFLAGS += -DDHD_SKIP_PKTLOGGING_FOR_DATA_PKTS
+
+ # Allow wl event forwarding as network packet
+ DHDCFLAGS += -DWL_EVENT_ENAB
+
ifneq ($(CONFIG_BCMDHD_PCIE),)
# LB RXP Flow control to avoid OOM
DHDCFLAGS += -DLB_RXP_STOP_THR=200 -DLB_RXP_STRT_THR=199
@@ -911,8 +949,6 @@
DHDCFLAGS += -DDHD_CAP_PLATFORM="\"hikey \""
# Dongle init fail
DHDCFLAGS += -DPOWERUP_MAX_RETRY=3
- # UNII4 channel support
- DHDCFLAGS += -DWL_5P9G
DHDCFLAGS := $(filter-out -DSIMPLE_MAC_PRINT ,$(DHDCFLAGS))
endif
diff --git a/Kconfig b/Kconfig
index 525be73..1c44bed 100644
--- a/Kconfig
+++ b/Kconfig
@@ -1,5 +1,5 @@
#
-# Copyright (C) 2021, Broadcom.
+# Copyright (C) 2022, Broadcom.
#
# Unless you and Broadcom execute a separate written software license
# agreement governing use of this software, this software is licensed to you
diff --git a/Makefile b/Makefile
index 4bde8f6..09fdc4e 100644
--- a/Makefile
+++ b/Makefile
@@ -1,5 +1,5 @@
#
-# Copyright (C) 2021, Broadcom.
+# Copyright (C) 2022, Broadcom.
#
# Unless you and Broadcom execute a separate written software license
# agreement governing use of this software, this software is licensed to you
diff --git a/aiutils.c b/aiutils.c
index f14f570..af2355d 100644
--- a/aiutils.c
+++ b/aiutils.c
@@ -2,7 +2,7 @@
* Misc utility routines for accessing chip-specific features
* of the SiliconBackplane-based Broadcom chips.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/bcm_app_utils.c b/bcm_app_utils.c
index f9a8716..ff26779 100644
--- a/bcm_app_utils.c
+++ b/bcm_app_utils.c
@@ -3,7 +3,7 @@
* Contents are wifi-specific, used by any kernel or app-level
* software that might want wifi things as it grows.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -109,33 +109,7 @@
static uint8
spec_to_chan(chanspec_t chspec)
{
- uint8 center_ch, edge, primary, sb;
-
- center_ch = CHSPEC_CHANNEL(chspec);
-
- if (CHSPEC_IS20(chspec)) {
- return center_ch;
- } else {
- /* the lower edge of the wide channel is half the bw from
- * the center channel.
- */
- if (CHSPEC_IS40(chspec)) {
- edge = center_ch - CH_20MHZ_APART;
- } else {
- /* must be 80MHz (until we support more) */
- ASSERT(CHSPEC_IS80(chspec));
- edge = center_ch - CH_40MHZ_APART;
- }
-
- /* find the channel number of the lowest 20MHz primary channel */
- primary = edge + CH_10MHZ_APART;
-
- /* select the actual subband */
- sb = (chspec & WL_CHANSPEC_CTL_SB_MASK) >> WL_CHANSPEC_CTL_SB_SHIFT;
- primary = primary + sb * CH_20MHZ_APART;
-
- return primary;
- }
+ return wf_chspec_primary20_chan(chspec);
}
/*
diff --git a/bcm_l2_filter.c b/bcm_l2_filter.c
index 1fc884f..f5b4ac9 100644
--- a/bcm_l2_filter.c
+++ b/bcm_l2_filter.c
@@ -1,7 +1,7 @@
/*
* L2 Filter handling functions
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -102,6 +102,7 @@
{
MFREE(osh, ptable, sizeof(arp_table_t));
}
+
/* returns 0 if gratuitous ARP or unsolicited neighbour advertisement */
int
bcm_l2_filter_gratuitous_arp(osl_t *osh, void *pktbuf)
@@ -167,6 +168,7 @@
return BCME_ERROR;
}
+
int
get_pkt_ether_type(osl_t *osh, void *pktbuf,
uint8 **data_ptr, int *len_ptr, uint16 *et_ptr, bool *snap_ptr)
@@ -336,6 +338,7 @@
*mac_addr = dhcp + DHCP_CHADDR_OFFSET;
return BCME_OK;
}
+
/* modify the mac address for IP, in arp table */
int
bcm_l2_filter_parp_modifyentry(arp_table_t* arp_tbl, struct ether_addr *ea,
@@ -590,6 +593,7 @@
}
}
}
+
/* create 42 byte ARP packet for ARP response, aligned the Buffer */
void *
bcm_l2_filter_proxyarp_alloc_reply(osl_t* osh, uint16 pktlen, struct ether_addr *src_ea,
@@ -622,21 +626,25 @@
*p = (void *)(frame + ETHER_HDR_LEN + (snap ? SNAP_HDR_LEN + ETHER_TYPE_LEN : 0));
return pkt;
}
+
/* copy the smac entry from parp_table */
void bcm_l2_filter_parp_get_smac(arp_table_t* ptable, void* smac)
{
bcopy(ptable->parp_smac, smac, ETHER_ADDR_LEN);
}
+
/* copy the cmac entry from parp_table */
void bcm_l2_filter_parp_get_cmac(arp_table_t* ptable, void* cmac)
{
bcopy(ptable->parp_cmac, cmac, ETHER_ADDR_LEN);
}
+
/* copy the smac entry to smac entry in parp_table */
void bcm_l2_filter_parp_set_smac(arp_table_t* ptable, void* smac)
{
bcopy(smac, ptable->parp_smac, ETHER_ADDR_LEN);
}
+
/* copy the cmac entry to cmac entry in parp_table */
void bcm_l2_filter_parp_set_cmac(arp_table_t* ptable, void* cmac)
{
@@ -689,6 +697,7 @@
return answer;
}
+
/*
* The length of the option including
* the type and length fields in units of 8 octets
diff --git a/bcmbloom.c b/bcmbloom.c
index 3e2e051..a2abbb2 100644
--- a/bcmbloom.c
+++ b/bcmbloom.c
@@ -1,7 +1,7 @@
/*
* Bloom filter support
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/bcmevent.c b/bcmevent.c
index 32e66e0..e0700d0 100644
--- a/bcmevent.c
+++ b/bcmevent.c
@@ -1,7 +1,7 @@
/*
* bcmevent read-only data shared by kernel or app layers
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -186,9 +186,6 @@
#ifdef WLBSSLOAD_REPORT
BCMEVENT_NAME(WLC_E_BSS_LOAD),
#endif
-#if defined(BT_WIFI_HANDOVER) || defined(WL_TBOW)
- BCMEVENT_NAME(WLC_E_BT_WIFI_HANDOVER_REQ),
-#endif
#ifdef WLFBT
BCMEVENT_NAME(WLC_E_FBT),
#endif /* WLFBT */
@@ -234,8 +231,22 @@
#ifdef WL_TWT
BCMEVENT_NAME(WLC_E_TWT),
#endif /* WL_TWT */
-
+ BCMEVENT_NAME(WLC_E_AMT),
+ BCMEVENT_NAME(WLC_E_ROAM_SCAN_RESULT),
+#if defined(XRAPI)
+ BCMEVENT_NAME(WLC_E_XR_SOFTAP_PSMODE),
+#endif /* XRAPI */
+#ifdef WL_SIB_COEX
+ BCMEVENT_NAME(WLC_E_SIB),
+#endif /* WL_SIB_COEX */
BCMEVENT_NAME(WLC_E_MSCS),
+ BCMEVENT_NAME(WLC_E_RXDMA_RECOVERY_ATMPT),
+#ifdef WL_SCHED_SCAN
+ BCMEVENT_NAME(WLC_E_PFN_PARTIAL_RESULT),
+#endif /* WL_SCHED_SCAN */
+ BCMEVENT_NAME(WLC_E_MLO_LINK_INFO),
+ BCMEVENT_NAME(WLC_E_C2C),
+ BCMEVENT_NAME(WLC_E_BCN_TSF),
};
const char *bcmevent_get_name(uint event_type)
diff --git a/bcmsdh.c b/bcmsdh.c
index 6079c6c..2190716 100644
--- a/bcmsdh.c
+++ b/bcmsdh.c
@@ -2,7 +2,7 @@
* BCMSDH interface glue
* implement bcmsdh API for SDIOH driver
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/bcmsdh_linux.c b/bcmsdh_linux.c
index 9297d40..fa1b110 100644
--- a/bcmsdh_linux.c
+++ b/bcmsdh_linux.c
@@ -1,7 +1,7 @@
/*
* SDIO access interface for drivers - linux specific (pci only)
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -235,6 +235,19 @@
spin_unlock_irqrestore(&bcmsdh_osinfo->oob_irq_spinlock, flags);
return ret;
}
+int bcmsdh_get_wake(bcmsdh_info_t *bcmsdh, int flag)
+{
+ bcmsdh_os_info_t *bcmsdh_osinfo = bcmsdh->os_cxt;
+ unsigned long flags;
+ int ret;
+
+ spin_lock_irqsave(&bcmsdh_osinfo->oob_irq_spinlock, flags);
+
+ ret = bcmsdh->pkt_wake;
+
+ spin_unlock_irqrestore(&bcmsdh_osinfo->oob_irq_spinlock, flags);
+ return ret;
+}
#endif /* DHD_WAKE_STATUS */
int bcmsdh_suspend(bcmsdh_info_t *bcmsdh)
diff --git a/bcmsdh_sdmmc.c b/bcmsdh_sdmmc.c
index b3aca0e..dd1dda0 100644
--- a/bcmsdh_sdmmc.c
+++ b/bcmsdh_sdmmc.c
@@ -1,7 +1,7 @@
/*
* BCMSDH Function Driver for the native SDIO/MMC driver in the Linux Kernel
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/bcmsdh_sdmmc_linux.c b/bcmsdh_sdmmc_linux.c
index ab79e6c..2f6f58f 100644
--- a/bcmsdh_sdmmc_linux.c
+++ b/bcmsdh_sdmmc_linux.c
@@ -1,7 +1,7 @@
/*
* BCMSDH Function Driver for the native SDIO/MMC driver in the Linux Kernel
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -194,6 +194,7 @@
{ SDIO_DEVICE(SDIO_VENDOR_ID_BROADCOM, BCM43013_D11N_ID) },
{ SDIO_DEVICE(SDIO_VENDOR_ID_BROADCOM, BCM43013_D11N2G_ID) },
{ SDIO_DEVICE(SDIO_VENDOR_ID_BROADCOM, BCM43013_D11N5G_ID) },
+ { SDIO_DEVICE(SDIO_VENDOR_ID_BROADCOM, BCM4381_CHIP_ID) },
{ 0, 0, 0, 0 /* end: all zeroes */
},
};
diff --git a/bcmsdspi.h b/bcmsdspi.h
index 39dff8e..f35e2f4 100644
--- a/bcmsdspi.h
+++ b/bcmsdspi.h
@@ -1,7 +1,7 @@
/*
* SD-SPI Protocol Conversion - BCMSDH->SPI Translation Layer
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/bcmsdspi_linux.c b/bcmsdspi_linux.c
index d8e90a5..845f216 100644
--- a/bcmsdspi_linux.c
+++ b/bcmsdspi_linux.c
@@ -1,7 +1,7 @@
/*
* Broadcom SPI Host Controller Driver - Linux Per-port
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/bcmsdstd.h b/bcmsdstd.h
index bd67ed7..de742ed 100644
--- a/bcmsdstd.h
+++ b/bcmsdstd.h
@@ -1,7 +1,7 @@
/*
* 'Standard' SDIO HOST CONTROLLER driver
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/bcmspibrcm.c b/bcmspibrcm.c
index 885203c..898e132 100644
--- a/bcmspibrcm.c
+++ b/bcmspibrcm.c
@@ -1,7 +1,7 @@
/*
* Broadcom BCMSDH to gSPI Protocol Conversion Layer
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/bcmstdlib_s.c b/bcmstdlib_s.c
index 39bea23..c540349 100644
--- a/bcmstdlib_s.c
+++ b/bcmstdlib_s.c
@@ -1,7 +1,7 @@
/*
* Broadcom Secure Standard Library.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/bcmutils.c b/bcmutils.c
old mode 100755
new mode 100644
index 91e3679..94ef020
--- a/bcmutils.c
+++ b/bcmutils.c
@@ -1,7 +1,7 @@
/*
* Driver O/S-independent utility routines
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -45,6 +45,9 @@
#ifndef ASSERT
#define ASSERT(exp)
#endif
+#ifndef ASSERT_FP
+#define ASSERT_FP(exp)
+#endif
#endif /* !BCMDRIVER */
@@ -1115,6 +1118,15 @@
priority = PRIO_8021D_NC;
rc = PKTPRIO_DSCP;
#endif /* EAPOL_PKT_PRIO || DHD_LOSSLESS_ROAMING */
+#if defined(PRIORITIZE_ARP)
+ } else if (eh->ether_type == hton16(ETHER_TYPE_ARP)) {
+ /* Certain Host stacks attempt disconnection on continous ARP timeouts. In
+ * congested scenarios with traffic, ARP packets may not get chance
+ * for transmission leading to disconnection. so prioritize it.
+ */
+ priority = PRIO_8021D_NC;
+ rc = PKTPRIO_DSCP;
+#endif /* PRIORITIZE_ARP */
#if defined(WLTDLS)
} else if (eh->ether_type == hton16(ETHER_TYPE_89_0D)) {
/* Bump up the priority for TDLS frames */
@@ -1447,6 +1459,7 @@
pktlist->list[(*idx)].pkt_trace[bit/NBBY] |= (1 << ((bit)%NBBY));
}
+
void
pktlist_trace(pktlist_info_t *pktlist, void *pkt, uint16 bit)
{
@@ -1993,7 +2006,7 @@
BCM_MWBMAP_AUDIT(mwbmap_hdl);
mwbmap_p = BCM_MWBMAP_PTR(mwbmap_hdl);
- ASSERT(mwbmap_p->ifree >= 0);
+ ASSERT_FP(mwbmap_p->ifree >= 0);
return (uint32)mwbmap_p->ifree;
}
@@ -2079,6 +2092,7 @@
ASSERT((int)free_cnt == mwbmap_p->ifree);
}
+
/* END : Multiword bitmap based 64bit to Unique 32bit Id allocator. */
/* Simple 16bit Id allocator using a stack implementation. */
@@ -2361,6 +2375,7 @@
/* invoke any other system audits */
return (!!insane);
}
+
/* END: Simple id16 allocator */
void
@@ -2511,8 +2526,7 @@
#ifndef DONGLEBUILD
if (bcm_bprintf_bypass == TRUE) {
- static const char BCMPOST_TRAP_RODATA(bcm_bprintf_ptstr_1)[] = "%s";
- printf(bcm_bprintf_ptstr_1, b->buf);
+ printf("%s", b->buf);
goto exit;
}
#endif /* !DONGLEBUILD */
@@ -2550,6 +2564,24 @@
bcm_bprintf(b, "\n");
}
+/* print the buffer in hex string format with the most significant byte first */
+void
+bcm_bprhex_msb(struct bcmstrbuf *b, const char *msg, bool newline,
+ const uint8 *buf, uint len)
+{
+ int i;
+
+ if (msg != NULL && msg[0] != '\0') {
+ bcm_bprintf(b, "%s", msg);
+ }
+ for (i = (int)len - 1; i >= 0; i --) {
+ bcm_bprintf(b, "%02X", buf[i]);
+ }
+ if (newline) {
+ bcm_bprintf(b, "\n");
+ }
+}
+
void
bcm_inc_bytes(uchar *num, int num_bytes, uint8 amount)
{
@@ -4478,6 +4510,48 @@
}
return NULL;
}
+
+/**
+ * Return a const tlv buffer pointer and length representing the sub-buffer contained
+ * inside the given 'elt' starting at the given 'body_offset'.
+ * The function assumes that elt is a valid tlv; the elt pointer and data
+ * are all in the range of its parent buffer/length.
+ *
+ * @param elt pointer to a valid bcm_tlv_t
+ * @param body_offset offset into the data body of elt
+ * @param buffer on return, pointer to an offset in elt
+ * @param buflen on return, length of the buffer to the end of elt
+ *
+ * On return, if body_offset is not less than the elt's body length, the *buffer parameter
+ * will be set to NULL and *buflen parameter will be set to zero. Otherwise,
+ * *buffer will point to the sub-buffer at the body_offset, and *buflen be the remaining
+ * bytes in the body.
+ * E.g. Given a TLV with elt->len == 10, the call
+ * bcm_tlv_sub_buffer(elt, 4, &buffer, &buflen)
+ * will result with buffer = elt->data + 4, and buflen = 6.
+ */
+void
+bcm_tlv_sub_buffer(const bcm_tlv_t *elt, uint body_offset, const uint8 **buffer, uint8 *buflen)
+{
+ if (elt->len > body_offset) {
+ uint8 body_len = elt->len;
+
+#if defined(__COVERITY__)
+ /* The 'body_len' value is tainted in Coverity because it is read from
+ * the tainted data pointed to by 'elt'. However, bcm_parse_tlvs() verifies
+ * that the elt pointer is a valid element, so its body length is in the bounds
+ * of the buffer.
+ * Clearing the tainted attribute of 'body_len' for Coverity.
+ */
+ __coverity_tainted_data_sanitize__(body_len);
+#endif /* __COVERITY__ */
+ *buflen = body_len - body_offset;
+ *buffer = elt->data + body_offset;
+ } else {
+ *buflen = 0u;
+ *buffer = NULL;
+ }
+}
#endif /* !BCMROMOFFLOAD_EXCLUDE_BCMUTILS_FUNCS */
uint
@@ -4961,6 +5035,61 @@
return bitcount;
}
+/* Count 0s or 1s in an octets list from 'from_bit' to 'to_bit' inclusively */
+uint
+bcm_count_bits(const uint8 *buf, uint buf_len, uint from_bit, uint to_bit, bool val_1)
+{
+ uint from;
+ uint to;
+ uint len;
+ uint8 tmp;
+ uint bits;
+
+ /* sanity check */
+ if (to_bit < from_bit) {
+ return 0u;
+ }
+
+ /* byte offset */
+ from = from_bit >> 3u;
+ to = to_bit >> 3u;
+ if (from >= buf_len || to >= buf_len) {
+ return 0u;
+ }
+
+ /* count 1s always */
+ len = to - from + 1u;
+ if (len == 1u) {
+ /* the only octet */
+ ASSERT(from == to);
+ tmp = buf[from];
+ tmp &= (0xffu << (from_bit & 7u));
+ tmp &= ~(0xffu << ((to_bit & 7u) + 1u));
+ bits = bcm_bitcount(&tmp, 1u);
+ } else {
+ ASSERT(len >= 2u);
+ /* the first octet */
+ tmp = buf[from];
+ tmp &= (0xffu << (from_bit & 7u));
+ bits = bcm_bitcount(&tmp, 1u);
+ /* the middle octet(s) */
+ if (len > 2u) {
+ bits += bcm_bitcount(&buf[from + 1u], len - 2u);
+ }
+ /* the last octet */
+ tmp = buf[to];
+ tmp &= ~(0xffu << ((to_bit & 7u) + 1u));
+ bits += bcm_bitcount(&tmp, 1u);
+ }
+
+ /* calc 0s if requested */
+ if (!val_1) {
+ bits = to_bit - from_bit + 1u - bits;
+ }
+
+ return bits;
+}
+
/*
* ProcessVars:Takes a buffer of "<var>=<value>\n" lines read from a file and ending in a NUL.
* also accepts nvram files which are already in the format of <var1>=<value>\0\<var2>=<value2>\0
@@ -5475,6 +5604,7 @@
return root;
}
+
/* GROUP 1 --- end */
/* read/write field in a consecutive bits in an octet array.
@@ -5552,9 +5682,9 @@
BCM_REFERENCE(size);
- ASSERT(fbyte < size);
- ASSERT(lbyte < size);
- ASSERT(nbits <= (sizeof(val) << 3u));
+ ASSERT_FP(fbyte < size);
+ ASSERT_FP(lbyte < size);
+ ASSERT_FP(nbits <= (sizeof(val) << 3u));
/* all bits are in the same byte */
if (fbyte == lbyte) {
@@ -6091,6 +6221,25 @@
}
}
+/* print the buffer in hex string format with the most significant byte first */
+void
+prhexstr_msb(const char *prefix, const uint8 *buf, uint len, bool newline)
+{
+ if (len > 0) {
+ int i;
+
+ if (prefix != NULL) {
+ printf("%s", prefix);
+ }
+ for (i = (int)len - 1; i >= 0; i --) {
+ printf("%02X", buf[i]);
+ }
+ if (newline) {
+ printf("\n");
+ }
+ }
+}
+
#ifdef DONGLEBUILD
static const char BCMPOST_TRAP_RODATA(bcm_print_string)[] = "%s";
diff --git a/bcmwifi_channels.c b/bcmwifi_channels.c
index cfe66e6..25b2f86 100644
--- a/bcmwifi_channels.c
+++ b/bcmwifi_channels.c
@@ -3,7 +3,7 @@
* Contents are wifi-specific, used by any kernel or app-level
* software that might want wifi things as it grows.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/bcmxtlv.c b/bcmxtlv.c
index b37e45e..ad330ca 100644
--- a/bcmxtlv.c
+++ b/bcmxtlv.c
@@ -1,7 +1,7 @@
/*
* Driver O/S-independent utility routines
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/copyrights.json b/copyrights.json
new file mode 100644
index 0000000..9f91ad9
--- /dev/null
+++ b/copyrights.json
@@ -0,0 +1,3 @@
+{
+ "copyrights": []
+}
diff --git a/dhd.h b/dhd.h
index 1cde679..7d713ea 100644
--- a/dhd.h
+++ b/dhd.h
@@ -4,7 +4,7 @@
* Provides type definitions and function prototypes used to link the
* DHD OS, bus, and protocol modules.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -193,6 +193,8 @@
#define DHD_BUS_BUSY_IN_NAPI 0x10000
#define DHD_BUS_BUSY_IN_DS_DEASSERT 0x20000
#define DHD_BUS_BUSY_IN_DUMP_DONGLE_MEM 0x40000
+#define DHD_BUS_BUSY_IN_SYSFS_DUMP 0x80000
+#define DHD_BUS_BUSY_IN_PM_CALLBACK 0x100000
#define DHD_BUS_BUSY_SET_IN_TX(dhdp) \
(dhdp)->dhd_bus_busy_state |= DHD_BUS_BUSY_IN_TX
@@ -232,6 +234,10 @@
(dhdp)->dhd_bus_busy_state |= DHD_BUS_BUSY_IN_DS_DEASSERT
#define DHD_BUS_BUSY_SET_IN_DUMP_DONGLE_MEM(dhdp) \
(dhdp)->dhd_bus_busy_state |= DHD_BUS_BUSY_IN_DUMP_DONGLE_MEM
+#define DHD_BUS_BUSY_SET_IN_SYSFS_DUMP(dhdp) \
+ (dhdp)->dhd_bus_busy_state |= DHD_BUS_BUSY_IN_SYSFS_DUMP
+#define DHD_BUS_BUSY_SET_IN_PM_CALLBACK(dhdp) \
+ (dhdp)->dhd_bus_busy_state |= DHD_BUS_BUSY_IN_PM_CALLBACK
#define DHD_BUS_BUSY_CLEAR_IN_TX(dhdp) \
(dhdp)->dhd_bus_busy_state &= ~DHD_BUS_BUSY_IN_TX
@@ -271,6 +277,10 @@
(dhdp)->dhd_bus_busy_state &= ~DHD_BUS_BUSY_IN_DS_DEASSERT
#define DHD_BUS_BUSY_CLEAR_IN_DUMP_DONGLE_MEM(dhdp) \
(dhdp)->dhd_bus_busy_state &= ~DHD_BUS_BUSY_IN_DUMP_DONGLE_MEM
+#define DHD_BUS_BUSY_CLEAR_IN_SYSFS_DUMP(dhdp) \
+ (dhdp)->dhd_bus_busy_state &= ~DHD_BUS_BUSY_IN_SYSFS_DUMP
+#define DHD_BUS_BUSY_CLEAR_IN_PM_CALLBACK(dhdp) \
+ (dhdp)->dhd_bus_busy_state &= ~DHD_BUS_BUSY_IN_PM_CALLBACK
#define DHD_BUS_BUSY_CHECK_IN_TX(dhdp) \
((dhdp)->dhd_bus_busy_state & DHD_BUS_BUSY_IN_TX)
@@ -310,6 +320,8 @@
((dhdp)->dhd_bus_busy_state & DHD_BUS_BUSY_IN_DS_DEASSERT)
#define DHD_BUS_BUSY_CHECK_IN_DUMP_DONGLE_MEM(dhdp) \
((dhdp)->dhd_bus_busy_state & DHD_BUS_BUSY_IN_DUMP_DONGLE_MEM)
+#define DHD_BUS_BUSY_CHECK_IN_SYSFS_DUMP(dhdp) \
+ ((dhdp)->dhd_bus_busy_state & DHD_BUS_BUSY_IN_SYSFS_DUMP)
#define DHD_BUS_BUSY_CHECK_IDLE(dhdp) \
((dhdp)->dhd_bus_busy_state == 0)
@@ -472,7 +484,11 @@
#define DHD_SCAN_UNASSOC_ACTIVE_TIME CUSTOM_SCAN_UNASSOC_ACTIVE_TIME
#endif /* CUSTOM_SCAN_UNASSOC_ACTIVE_TIME */
#define DHD_SCAN_HOME_TIME 45 /* ms: Embedded default Home time setting from DHD */
+#ifndef CUSTOM_SCAN_HOME_AWAY_TIME
#define DHD_SCAN_HOME_AWAY_TIME 100 /* ms: Embedded default Home Away time setting from DHD */
+#else
+#define DHD_SCAN_HOME_AWAY_TIME CUSTOM_SCAN_HOME_AWAY_TIME /* ms: Custom setting from DHD */
+#endif /* CUSTOM_SCAN_HOME_AWAY_TIME */
#ifndef CUSTOM_SCAN_PASSIVE_TIME
#define DHD_SCAN_PASSIVE_TIME 130 /* ms: Embedded default Passive setting from DHD */
#else
@@ -491,7 +507,7 @@
* This also needs to be increased if NVRAM files size increases
*/
#define MAX_NVRAMBUF_SIZE (32 * 1024) /* max nvram buf size */
-#define MAX_CLM_BUF_SIZE (48 * 1024) /* max clm blob size */
+#define MAX_CLM_BUF_SIZE (64 * 1024) /* max clm blob size */
#define MAX_TXCAP_BUF_SIZE (16 * 1024) /* max txcap blob size */
#ifdef DHD_DEBUG
#define DHD_JOIN_MAX_TIME_DEFAULT 10000 /* ms: Max time out for joining AP */
@@ -555,6 +571,12 @@
DW_DEVICE_HOST_WAKE_WAIT = 7,
DW_DEVICE_DS_D3_INFORM_WAIT = 8
};
+#ifdef PCIE_INB_DSACK_EXT_WAIT
+/* DS ack timeout is 3sec, FW retry count is 5.
+ * 5times * 3sec = 15sec.
+ */
+#define DW_DS_ACK_RETRY_THRESHOLD 15u
+#endif /* PCIE_INB_DSACK_EXT_WAIT */
#endif /* PCIE_INB_DW */
enum dhd_prealloc_index {
@@ -630,7 +652,10 @@
DUMP_TYPE_ESCAN_SYNCID_MISMATCH = 32,
DUMP_TYPE_INVALID_SHINFO_NRFRAGS = 33,
DUMP_TYPE_P2P_DISC_BUSY = 34,
- DUMP_TYPE_CONT_EXCESS_PM_AWAKE = 35
+ DUMP_TYPE_CONT_EXCESS_PM_AWAKE = 35,
+ DUMP_TYPE_DONGLE_TRAP_DURING_WIFI_ONOFF = 36,
+ DUMP_TYPE_BY_DSACK_HC_DUE_TO_ISR_DELAY = 37,
+ DUMP_TYPE_BY_DSACK_HC_DUE_TO_DPC_DELAY = 38
};
enum dhd_hang_reason {
@@ -663,7 +688,8 @@
HANG_REASON_PCIE_CTO_DETECT = 0x8809,
HANG_REASON_SLEEP_FAILURE = 0x880A,
HANG_REASON_DS_SKIP_TIMEOUT = 0x880B,
- HANG_REASON_MAX = 0x880C
+ HANG_REASON_BT2WL_REG_RESET = 0x880C,
+ HANG_REASON_MAX = 0x880D
};
#define WLC_E_DEAUTH_MAX_REASON 0x0FFF
@@ -902,7 +928,8 @@
PACKET_LOG_RING_ID = 0x7,
DEBUG_DUMP_RING1_ID = 0x8,
DEBUG_DUMP_RING2_ID = 0x9,
- DEBUG_RING_ID_MAX = 0xa
+ MEM_DUMP_RING_ID = 0xa,
+ DEBUG_RING_ID_MAX = 0xb
} dhd_ring_id_t;
#define HEALTH_CHK_BUF_SIZE 256
@@ -928,7 +955,9 @@
#if defined(CUSTOMER_HW2_DEBUG)
#define DHD_COMMON_DUMP_PATH PLATFORM_PATH
#elif defined(BOARD_HIKEY)
+#ifndef DHD_COMMON_DUMP_PATH
#define DHD_COMMON_DUMP_PATH "/data/misc/wifi/"
+#endif /* !DHD_COMMON_DUMP_PATH */
#elif defined(__ARM_ARCH_7A__)
#define DHD_COMMON_DUMP_PATH "/data/vendor/wifi/"
#else
@@ -1059,9 +1088,13 @@
DHD_INDUCE_BH_ON_FAIL_ONCE = 0x10,
DHD_INDUCE_BH_ON_FAIL_ALWAYS = 0x11,
DHD_INDUCE_BH_CBP_HANG = 0x12,
+ DHD_INDUCE_P2P_DISC_BUSY = 0x13,
+ DHD_INDUCE_PCIE_LINK_DOWN_IN_ISR = 0x14,
DHD_INDUCE_ERROR_MAX
} dhd_induce_error_states_t;
+#define MAX_MDRING_ITEM_DUMP 20
+
#define MAX_RX_LAT_PRIO 8
#define MAX_RX_LAT_HIST_BIN 50
#define MAX_RXCPL_HISTORY 50
@@ -1215,6 +1248,8 @@
ulong tx_realloc; /* Number of tx packets we had to realloc for headroom */
ulong fc_packets; /* Number of flow control pkts recvd */
ulong tx_big_packets; /* Dropped data packets that are larger than MAX_MTU_SZ */
+ ulong tx_bytes; /* total no. of bytes transmitted successfully */
+ ulong rx_bytes; /* total no. of bytes received */
#ifdef DMAMAP_STATS
/* DMA Mapping statistics */
dma_stats_t dma_stats;
@@ -1343,6 +1378,9 @@
#endif
bool smmu_fault_occurred; /* flag to indicate SMMU Fault */
bool p2p_disc_busy_occurred;
+ bool dongle_trap_during_wifi_onoff; /* flag to indicate trap during wifi on/off */
+ bool dsack_hc_due_to_isr_delay; /* flag to indicate DSACK HC by ISR delay */
+ bool dsack_hc_due_to_dpc_delay; /* flag to indicate DSACK HC by DPC delay */
/*
* Add any new variables to track Bus errors above
* this line. Also ensure that the variable is
@@ -1741,6 +1779,10 @@
bool ring_attached;
#ifdef DHD_PCIE_RUNTIMEPM
bool rx_pending_due_to_rpm;
+#ifdef RPM_FAST_TRIGGER
+ bool rpm_fast_trigger;
+ bool rpm_fast_candidate;
+#endif /* RPM_FAST_TRIGGER */
#endif /* DHD_PCIE_RUNTIMEPM */
union {
wl_roam_stats_v1_t v1;
@@ -1806,6 +1848,14 @@
#endif /* DHD_SUPPORT_SPMI_MODE */
/* Flag to indicate H2D flowring phase nibble value support */
uint8 fr_phase_nibble;
+ bool mdring_capable; /* FW supports metadata ring cpl ring */
+ uint8 *mdring_info; /* Saved metadta ring work items */
+ uint32 md_item_count; /* # of saved metadata work items */
+#if defined(DEVICE_TX_STUCK_DETECT) && defined(ASSOC_CHECK_SR)
+ /* is infra associated or not before suspend ? */
+ bool assoc_at_suspend;
+#endif /* DEVICE_TX_STUCK_DETECT && ASSOC_CHECK_SR */
+ uint32 p2p_disc_busy_cnt;
} dhd_pub_t;
#if defined(__linux__)
@@ -2214,10 +2264,14 @@
#define DHD_OS_OOB_IRQ_WAKE_UNLOCK(pub) dhd_os_oob_irq_wake_unlock(pub)
#endif /* BCMPCIE_OOB_HOST_WAKE */
-#define DHD_PACKET_TIMEOUT_MS 500
+/* The DHD_PACKET_TIMEOUT_MS & MAX_TX_TIMEOUT are used for wake_lock timeout
+ * to prevent the system from entering suspend during TX/RX frame processing.
+ * It can be adjusted depending on the host platform.
+ */
+#define DHD_PACKET_TIMEOUT_MS 100
#define DHD_EVENT_TIMEOUT_MS 1500
#define SCAN_WAKE_LOCK_TIMEOUT 10000
-#define MAX_TX_TIMEOUT 500
+#define MAX_TX_TIMEOUT 100
/* Enum for IOCTL recieved status */
typedef enum dhd_ioctl_recieved_status
@@ -2758,6 +2812,9 @@
#if defined(WIFI_TURNON_USE_HALINIT)
extern int dhd_open(struct net_device *net);
#endif /* WIFI_TURNON_USE_HALINIT */
+#if defined(LINUX) || defined(linux)
+extern int dhd_stop(struct net_device *net);
+#endif /* LINUX */
extern int dhd_bus_devreset(dhd_pub_t *dhdp, uint8 flag);
extern uint dhd_bus_status(dhd_pub_t *dhdp);
extern int dhd_bus_start(dhd_pub_t *dhdp);
@@ -2977,6 +3034,14 @@
} tcm_test_status_t;
extern tcm_test_status_t dhd_tcm_test_status;
+/* TCM test mode */
+typedef enum tcm_test_mode {
+ TCM_TEST_MODE_DISABLE = 0,
+ TCM_TEST_MODE_ONCE = 1,
+ TCM_TEST_MODE_ALWAYS = 2
+} tcm_test_mode_t;
+extern tcm_test_mode_t dhd_tcm_test_mode;
+
/* Initial idletime ticks (may be -1 for immediate idle, 0 for no idle) */
extern int dhd_idletime;
#ifdef DHD_USE_IDLECOUNT
@@ -3211,7 +3276,6 @@
/* End of Overrides, rely on what is dictated by Android */
#define PLATFORM_PATH "/data/misc/conn/"
#define DHD_MAC_ADDR_EXPORT
-#define DHD_ADPS_BAM_EXPORT
#define DHD_EXPORT_CNTL_FILE
#define DHD_SOFTAP_DUAL_IF_INFO
#define DHD_SEND_HANG_PRIVCMD_ERRORS
@@ -3282,10 +3346,6 @@
defined(GET_MAC_FROM_OTP)
#define DHD_USE_CISINFO
#endif /* READ_MACADDR || WRITE_MACADDR || USE_CID_CHECK || GET_MAC_FROM_OTP */
-#if defined(CONFIG_WIFI_BROADCOM_COB) && defined(BCM4389_CHIP_DEF)
-extern int otpinfo_val;
-int dhd_read_otp_hw_rgn(dhd_pub_t *dhdp);
-#endif /* CONFIG_WIFI_BROADCOM_COB && BCM4389_CHIP_DEF */
#ifdef DHD_USE_CISINFO
int dhd_read_cis(dhd_pub_t *dhdp);
@@ -3405,6 +3465,7 @@
int dhd_common_socram_dump(dhd_pub_t *dhdp);
int dhd_dump(dhd_pub_t *dhdp, char *buf, int buflen);
+int dhd_counters(dhd_pub_t *dhdp, char *buf, int buflen);
int dhd_os_get_version(struct net_device *dev, bool dhd_ver, char **buf, uint32 size);
void dhd_get_memdump_filename(struct net_device *ndev, char *memdump_path, int len, char *fname);
@@ -3943,6 +4004,12 @@
extern bool dhdpcie_is_resume_done(dhd_pub_t *dhdp);
extern void dhd_runtime_pm_disable(dhd_pub_t *dhdp);
extern void dhd_runtime_pm_enable(dhd_pub_t *dhdp);
+#ifdef RPM_FAST_TRIGGER
+/* Requirement is 20msec, but keep it 10msec to account for any scheduling latencies */
+#define RPM_FAST_TRIGGER_THR 10
+extern uint dhd_fast_runtimepm_ms;
+extern void dhdpcie_trigger_rpm_fast(dhd_pub_t *dhdp);
+#endif /* RPM_FAST_TRIGGER */
/* Disable the Runtime PM thread and wake up if the bus is already in suspend */
#define DHD_DISABLE_RUNTIME_PM(dhdp) \
do { \
@@ -3975,7 +4042,7 @@
#define DHD_START_RPM_TIMER(dhdp)
#endif /* DHD_PCIE_RUNTIMEPM */
-extern bool dhd_prot_is_cmpl_ring_empty(dhd_pub_t *dhd, void *prot_info);
+extern bool dhd_prot_is_h2d_ring_empty(dhd_pub_t *dhd, void *prot_info);
extern void dhd_prot_dump_ring_ptrs(void *prot_info);
extern bool dhd_prot_check_pending_ctrl_cmpls(dhd_pub_t *dhd);
@@ -4283,6 +4350,9 @@
/* Change TID for UDP frames based on UID */
SET_TID_BASED_ON_UID
};
+
+#define DEFAULT_SET_TID_TARGET_UID 0
+#define DEFAULT_SET_TID_TARGET_PRIO 0
#if defined(linux) || defined(LINUX)
extern void dhd_set_tid_based_on_uid(dhd_pub_t *dhdp, void *pkt);
#else
@@ -4301,6 +4371,18 @@
#define FILE_NAME_HAL_TAG "_hal" /* The tag name concatenated by HAL */
#endif /* DHD_DUMP_FILE_WRITE_FROM_KERNEL */
+void dhd_bus_counters(dhd_pub_t *dhdp, struct bcmstrbuf *strbuf);
+
+#define DHD_HISTOGRAM_ENTRIES (14u)
+#define DHD_HISTOGRAM_SIZE (sizeof(uint64) * DHD_HISTOGRAM_ENTRIES)
+
+void dhd_histo_update(dhd_pub_t *dhd, uint64 *histo, uint32 value);
+void dhd_histo_clear(dhd_pub_t *dhd, uint64 *histo);
+void dhd_histo_tag_dump(dhd_pub_t *dhd, struct bcmstrbuf *strbuf, char *tagname);
+void dhd_histo_dump(dhd_pub_t *dhd, struct bcmstrbuf *strbuf, uint64 *histo, char *histoname);
+uint64 *dhd_histo_init(dhd_pub_t *dhd);
+void dhd_histo_deinit(dhd_pub_t *dhd, uint64 *histo);
+
/* Given a number 'n' returns 'm' that is next larger power of 2 after n */
static inline uint32 next_larger_power2(uint32 num)
{
@@ -4440,7 +4522,20 @@
int dhd_os_wake_lock_rx_timeout_enable(dhd_pub_t *pub, int val);
#if defined(__linux__)
+
#ifdef DHD_SUPPORT_VFS_CALL
+
+#if (LINUX_VERSION_CODE < KERNEL_VERSION(3, 19, 0))
+#define DHD_VFS_INODE(dir) (dir->d_inode)
+#else
+#define DHD_VFS_INODE(dir) d_inode(dir)
+#endif /* LINUX_VERSION_CODE < KERNEL_VERSION(3, 19, 0) */
+
+#if (LINUX_VERSION_CODE < KERNEL_VERSION(3, 13, 0))
+#define DHD_VFS_UNLINK(dir, b, c) vfs_unlink(DHD_VFS_INODE(dir), b)
+#else
+#define DHD_VFS_UNLINK(dir, b, c) vfs_unlink(DHD_VFS_INODE(dir), b, c)
+#endif /* LINUX_VERSION_CODE < KERNEL_VERSION(3, 13, 0) */
static INLINE struct file *dhd_filp_open(const char *filename, int flags, int mode)
{
return filp_open(filename, flags, mode);
@@ -4485,7 +4580,11 @@
{
return kern_path(name, flags, file_path);
}
-#else
+#endif /* DHD_SUPPORT_VFS_CALL */
+
+#ifndef DHD_SUPPORT_VFS_CALL
+#define DHD_VFS_UNLINK(dir, b, c) 0
+
static INLINE struct file *dhd_filp_open(const char *filename, int flags, int mode)
{ return NULL; }
static INLINE int dhd_filp_close(void *image, void *id)
@@ -4504,8 +4603,12 @@
{ return 0; }
static INLINE int dhd_kern_path(char *name, int flags, struct path *file_path)
{ return 0; }
-#endif /* DHD_SUPPORT_VFS_CALL */
+#endif /* !DHD_SUPPORT_VFS_CALL */
#endif /* __linux__ */
+#ifdef WL_TWT
+extern int dhd_config_twt_event_mask_in_suspend(dhd_pub_t *dhdp, bool suspend);
+extern int dhd_send_twt_info_suspend(dhd_pub_t *dhdp, bool suspend);
+#endif /* WL_TWT */
#if defined(DHD_WAKE_STATUS_PRINT) && defined(DHD_WAKE_RX_STATUS) && \
defined(DHD_WAKE_STATUS)
void dhd_dump_wake_status(dhd_pub_t *dhdp, wake_counts_t *wcp, struct ether_header *eh);
@@ -4516,4 +4619,13 @@
#if !defined(AP) && defined(WLP2P)
extern uint32 dhd_get_concurrent_capabilites(dhd_pub_t *dhd);
#endif
+#ifdef DHD_CUSTOM_CONFIG_RTS_IN_SUSPEND
+#ifndef CUSTOM_RETRUN_TO_SLEEP_TIME_SUSPEND
+#define CUSTOM_RETRUN_TO_SLEEP_TIME_SUSPEND 20
+#endif
+#ifndef CUSTOM_RETRUN_TO_SLEEP_TIME_DEFAULT
+#define CUSTOM_RETRUN_TO_SLEEP_TIME_DEFAULT 200
+#endif
+int dhd_config_rts_in_suspend(dhd_pub_t *dhdp, bool suspend);
+#endif /* DHD_CUSTOM_CONFIG_RTS_IN_SUSPEND */
#endif /* _dhd_h_ */
diff --git a/dhd_bitpack.h b/dhd_bitpack.h
index 12813ea..8332fb7 100644
--- a/dhd_bitpack.h
+++ b/dhd_bitpack.h
@@ -1,7 +1,7 @@
/*
* Bit packing and Base64 utils for EWP
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/dhd_bus.h b/dhd_bus.h
index 988f73f..7ffe51e 100644
--- a/dhd_bus.h
+++ b/dhd_bus.h
@@ -4,7 +4,7 @@
* Provides type definitions and function prototypes used to link the
* DHD OS, bus, and protocol modules.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -104,6 +104,7 @@
/* Add bus dump output to a buffer */
extern void dhd_bus_dump(dhd_pub_t *dhdp, struct bcmstrbuf *strbuf);
+extern void dhd_bus_dump_flowring(dhd_pub_t *dhdp, struct bcmstrbuf *strbuf);
/* Clear any bus counters */
extern void dhd_bus_clearcounts(dhd_pub_t *dhdp);
@@ -219,7 +220,8 @@
extern int dhd_bus_flow_ring_flush_request(struct dhd_bus *bus, void *flow_ring_node);
extern void dhd_bus_flow_ring_flush_response(struct dhd_bus *bus, uint16 flowid, uint32 status);
extern uint32 dhd_bus_max_h2d_queues(struct dhd_bus *bus);
-extern int dhd_bus_schedule_queue(struct dhd_bus *bus, uint16 flow_id, bool txs);
+extern int dhd_bus_schedule_queue(struct dhd_bus *bus, uint16 flow_id, bool txs,
+ uint32 bound, bool *is_qempty);
#ifdef IDLE_TX_FLOW_MGMT
extern void dhd_bus_flow_ring_resume_response(struct dhd_bus *bus, uint16 flowid, int32 status);
@@ -325,6 +327,10 @@
#ifdef DHD_WAKE_STATUS
extern wake_counts_t* dhd_bus_get_wakecount(dhd_pub_t *dhd);
extern int dhd_bus_get_bus_wake(dhd_pub_t * dhd);
+extern int dhd_bus_set_get_bus_wake(dhd_pub_t * dhd, int set);
+#if defined(BCMPCIE)
+extern int dhd_bus_set_get_bus_wake_pkt_dump(dhd_pub_t *dhd, int wake_pkt_dump);
+#endif /* BCMPCIE */
#endif /* DHD_WAKE_STATUS */
#ifdef BT_OVER_SDIO
@@ -354,6 +360,7 @@
extern void dhd_msgbuf_iovar_timeout_dump(dhd_pub_t *dhd);
extern void dhdpcie_induce_cbp_hang(dhd_pub_t *dhd);
extern void dhdpcie_busbusy_wait(dhd_pub_t *dhdp);
+extern int dhd_dump_flowrings(dhd_pub_t *dhdp, char *buf, int buflen);
#endif /* BCMPCIE */
extern bool dhd_bus_force_bt_quiesce_enabled(struct dhd_bus *bus);
diff --git a/dhd_buzzz.h b/dhd_buzzz.h
index 77373d7..36b5438 100644
--- a/dhd_buzzz.h
+++ b/dhd_buzzz.h
@@ -2,7 +2,7 @@
#define _DHD_BUZZZ_H_INCLUDED_
/*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/dhd_cdc.c b/dhd_cdc.c
index db6db0d..e3c89eb 100644
--- a/dhd_cdc.c
+++ b/dhd_cdc.c
@@ -1,7 +1,7 @@
/*
* DHD Protocol Module for CDC and BDC.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -168,6 +168,26 @@
dhd_prot_t *prot = dhd->prot;
DHD_TRACE(("%s: Enter\n", __FUNCTION__));
+ /*
+ * prot->msg is the buffer used to send the ioctl msg in dhdcdc_msg and the same is
+ * used for receiving the ioctl response.
+ * As this buffer is not cleared after sending message and before re-using for receive
+ * operation, problems are seen when bus errors occur.
+ * Example:- An error is seen on the bus where a 0 byte pkt is received.
+ * the bus-controller "layer below cdc" does not update the buffer in this 0 byte pkt case.
+ * bus-controller layer calls the completion callback without any error and with the
+ * same buffer.(no change)
+ * This issue is seen on DBUS/USB + FPGA platforms
+ * In this function if there is no update to the buffer, the stale id field of sent msg
+ * matches to expected ID and further processing is done thinking that
+ * proper response is received.
+ * This is a generic problem and its a good idea to clear the buffer or atleast
+ * the buffer's key value (ioctl ID within flags field in this case) before re-using it.
+ *
+ * To ensure that a new content is indeed received from the bus making flags = 0.
+ * Note that ID=0 is invalid value.
+ */
+ prot->msg.flags = 0;
do {
#ifdef BCMDBUS
@@ -507,6 +527,19 @@
#endif
}
+void
+dhd_prot_counters(dhd_pub_t *dhdp, struct bcmstrbuf *strbuf,
+ bool print_ringinfo, bool print_pktidinfo)
+{
+ return;
+}
+
+void
+dhd_bus_counters(dhd_pub_t *dhdp, struct bcmstrbuf *strbuf)
+{
+ return;
+}
+
/* The FreeBSD PKTPUSH could change the packet buf pinter
so we need to make it changable
*/
diff --git a/dhd_cfg80211.c b/dhd_cfg80211.c
index f36ac0e..47e92c8 100644
--- a/dhd_cfg80211.c
+++ b/dhd_cfg80211.c
@@ -1,7 +1,7 @@
/*
* Linux cfg80211 driver - Dongle Host Driver (DHD) related
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -336,3 +336,12 @@
return ret;
}
+
+#ifdef RPM_FAST_TRIGGER
+void
+dhd_trigger_rpm_fast(struct bcm_cfg80211 *cfg)
+{
+ dhd_pub_t *dhd = (dhd_pub_t *)cfg->pub;
+ dhdpcie_trigger_rpm_fast(dhd);
+}
+#endif /* RPM_FAST_TRIGGER */
diff --git a/dhd_cfg80211.h b/dhd_cfg80211.h
index 289144e..ae24bce 100644
--- a/dhd_cfg80211.h
+++ b/dhd_cfg80211.h
@@ -1,7 +1,7 @@
/*
* Linux cfg80211 driver - Dongle Host Driver (DHD) related
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -47,4 +47,7 @@
struct wireless_dev *wdev, const struct bcm_nlmsg_hdr *nlioc, void *data);
s32 wl_dongle_roam(struct net_device *ndev, u32 roamvar, u32 bcn_timeout);
int dhd_set_wsec_info(dhd_pub_t *dhd, uint32 data, int tag);
+#ifdef RPM_FAST_TRIGGER
+void dhd_trigger_rpm_fast(struct bcm_cfg80211 *cfg);
+#endif /* RPM_FAST_TRIGGER */
#endif /* __DHD_CFG80211__ */
diff --git a/dhd_common.c b/dhd_common.c
old mode 100644
new mode 100755
index b510b6a..8bb1e0a
--- a/dhd_common.c
+++ b/dhd_common.c
@@ -1,7 +1,7 @@
/*
* Broadcom Dongle Host Driver (DHD), common DHD core.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -352,7 +352,7 @@
IOV_BCMERROR,
IOV_WDTICK,
IOV_DUMP,
- IOV_CLEARCOUNTS,
+ IOV_RESET_COUNTS,
IOV_LOGDUMP,
IOV_LOGCAL,
IOV_LOGSTAMP,
@@ -496,6 +496,10 @@
#ifdef DHD_LOGLEVEL
IOV_LOGLEVEL,
#endif /* DHD_LOGLEVEL */
+ IOV_COUNTERS,
+#ifdef BCMPCIE
+ IOV_DUMP_FLOWRINGS,
+#endif
IOV_LAST
};
@@ -518,7 +522,7 @@
{"dump", IOV_DUMP, 0, 0, IOVT_BUFFER, DHD_IOCTL_MAXLEN_32K},
{"cons", IOV_CONS, 0, 0, IOVT_BUFFER, 0},
{"dconpoll", IOV_DCONSOLE_POLL, 0, 0, IOVT_UINT32, 0},
- {"clearcounts", IOV_CLEARCOUNTS, 0, 0, IOVT_VOID, 0},
+ {"reset_cnts", IOV_RESET_COUNTS, 0, 0, IOVT_VOID, 0},
#ifdef BCMPERFSTATS
{"logdump", IOV_LOGDUMP, 0, 0, IOVT_BUFFER, DHD_IOCTL_MAXLEN},
{"logcal", IOV_LOGCAL, 0, 0, IOVT_UINT32, 0},
@@ -671,6 +675,10 @@
#ifdef DHD_LOGLEVEL
{"loglevel", IOV_LOGLEVEL, (0), 0, IOVT_BUFFER, sizeof(dhd_loglevel_data_t)},
#endif /* DHD_LOGLEVEL */
+ {"counters", IOV_COUNTERS, 0, 0, IOVT_BUFFER, DHD_IOCTL_MAXLEN_32K},
+#ifdef BCMPCIE
+ {"dump_flowrings", IOV_DUMP_FLOWRINGS, 0, 0, IOVT_BUFFER, DHD_IOCTL_MAXLEN_32K},
+#endif
/* --- add new iovars *ABOVE* this line --- */
{NULL, 0, 0, 0, 0, 0 }
};
@@ -793,6 +801,8 @@
dhdp->dongle_reset = FALSE;
dhdp->dongle_trap_occured = FALSE;
+ dhdp->dsack_hc_due_to_isr_delay = FALSE;
+ dhdp->dsack_hc_due_to_dpc_delay = FALSE;
dhdp->iovar_timeout_occured = FALSE;
#ifdef PCIE_FULL_DONGLE
dhdp->d3ack_timeout_occured = FALSE;
@@ -829,7 +839,11 @@
int
dhd_sssr_mempool_init(dhd_pub_t *dhd)
{
+#ifdef CONFIG_BCMDHD_PCIE
+ dhd->sssr_mempool = (uint8 *) VMALLOCZ(dhd->osh, DHD_SSSR_MEMPOOL_SIZE);
+#else
dhd->sssr_mempool = (uint8 *) MALLOCZ(dhd->osh, DHD_SSSR_MEMPOOL_SIZE);
+#endif /* CONFIG_BCMDHD_PCIE */
if (dhd->sssr_mempool == NULL) {
DHD_ERROR(("%s: MALLOC of sssr_mempool failed\n",
__FUNCTION__));
@@ -842,7 +856,11 @@
dhd_sssr_mempool_deinit(dhd_pub_t *dhd)
{
if (dhd->sssr_mempool) {
+#ifdef CONFIG_BCMDHD_PCIE
+ VMFREE(dhd->osh, dhd->sssr_mempool, DHD_SSSR_MEMPOOL_SIZE);
+#else
MFREE(dhd->osh, dhd->sssr_mempool, DHD_SSSR_MEMPOOL_SIZE);
+#endif /* CONFIG_BCMDHD_PCIE */
dhd->sssr_mempool = NULL;
}
}
@@ -1536,19 +1554,78 @@
#endif /* BCMDBUS */
}
-int
-dhd_dump(dhd_pub_t *dhdp, char *buf, int buflen)
+static void
+dhd_dump_txrx_stats(dhd_pub_t *dhdp, struct bcmstrbuf *strbuf)
{
- struct bcmstrbuf b;
- struct bcmstrbuf *strbuf = &b;
+ /* TX Stats -- add any Tx counters in this section only */
+ bcm_bprintf(strbuf, "\nTX stats:\n=========\n");
+ bcm_bprintf(strbuf, "tx_packets %lu tx_bytes %lu tx_dropped %lu"
+ " tx_multicast %lu tx_errors %lu\n",
+ dhdp->tx_packets, dhdp->tx_bytes, dhdp->tx_dropped,
+ dhdp->tx_multicast, dhdp->tx_errors);
+ bcm_bprintf(strbuf, "tx_ctlpkts %lu tx_ctlerrs %lu\n",
+ dhdp->tx_ctlpkts, dhdp->tx_ctlerrs);
+ bcm_bprintf(strbuf, "tx_realloc %lu tx_pktgetfail %lu tx_big_packets %lu\n",
+ dhdp->tx_realloc, dhdp->tx_pktgetfail, dhdp->tx_big_packets);
+ /* ----------------------------------------------------- */
+
+ /* RX Stats -- add any Rx counters in this section only */
+ bcm_bprintf(strbuf, "\nRX stats:\n=========\n");
+ bcm_bprintf(strbuf, "rx_packets %lu rx_bytes %lu rx_forward"
+ " %lu rx_multicast %lu rx_errors %lu \n",
+ dhdp->rx_packets, dhdp->rx_bytes, dhdp->rx_forward,
+ dhdp->rx_multicast, dhdp->rx_errors);
+ bcm_bprintf(strbuf, "rx_ctlpkts %lu rx_ctlerrs %lu rx_dropped %lu\n",
+ dhdp->rx_ctlpkts, dhdp->rx_ctlerrs, dhdp->rx_dropped);
+ bcm_bprintf(strbuf, "rx_readahead_cnt %lu rx_pktgetfail %lu rx_pktgetpool_fail %lu\n",
+ dhdp->rx_readahead_cnt, dhdp->rx_pktgetfail, dhdp->rx_pktgetpool_fail);
+ bcm_bprintf(strbuf, "\n");
+ /* ----------------------------------------------------- */
+}
+
#ifdef DHD_MEM_STATS
+static void
+dhd_dump_memstats(dhd_pub_t *dhdp, struct bcmstrbuf *strbuf)
+{
uint64 malloc_mem = 0;
uint64 total_txpath_mem = 0;
uint64 txpath_bkpq_len = 0;
uint64 txpath_bkpq_mem = 0;
uint64 total_dhd_mem = 0;
+
+ malloc_mem = MALLOCED(dhdp->osh);
+
+ txpath_bkpq_len = dhd_active_tx_flowring_bkpq_len(dhdp);
+ /*
+ * Instead of traversing the entire queue to find the skbs length,
+ * considering MAX_MTU_SZ as lenth of each skb.
+ */
+ txpath_bkpq_mem = (txpath_bkpq_len* MAX_MTU_SZ);
+ total_txpath_mem = dhdp->txpath_mem + txpath_bkpq_mem;
+
+ bcm_bprintf(strbuf, "\nDHD malloc memory_usage: %llubytes %lluKB\n",
+ malloc_mem, (malloc_mem / 1024));
+
+ bcm_bprintf(strbuf, "\nDHD tx-bkpq len: %llu memory_usage: %llubytes %lluKB\n",
+ txpath_bkpq_len, txpath_bkpq_mem, (txpath_bkpq_mem / 1024));
+ bcm_bprintf(strbuf, "DHD tx-path memory_usage: %llubytes %lluKB\n",
+ total_txpath_mem, (total_txpath_mem / 1024));
+
+ total_dhd_mem = malloc_mem + total_txpath_mem;
+#if defined(DHD_LB_STATS)
+ total_dhd_mem += dhd_lb_mem_usage(dhdp, strbuf);
+#endif /* DHD_LB_STATS */
+ bcm_bprintf(strbuf, "\nDHD Total memory_usage: %llubytes %lluKB \n",
+ total_dhd_mem, (total_dhd_mem / 1024));
+}
#endif /* DHD_MEM_STATS */
+int
+dhd_dump(dhd_pub_t *dhdp, char *buf, int buflen)
+{
+ struct bcmstrbuf b;
+ struct bcmstrbuf *strbuf = &b;
+
if (!dhdp || !dhdp->prot || !buf) {
return BCME_ERROR;
}
@@ -1569,31 +1646,8 @@
dhdp->iswl, dhdp->drv_version, MAC2STRDBG(&dhdp->mac));
bcm_bprintf(strbuf, "pub.bcmerror %d tickcnt %u\n", dhdp->bcmerror, dhdp->tickcnt);
- bcm_bprintf(strbuf, "dongle stats:\n");
- bcm_bprintf(strbuf, "tx_packets %lu tx_bytes %lu tx_errors %lu tx_dropped %lu\n",
- dhdp->dstats.tx_packets, dhdp->dstats.tx_bytes,
- dhdp->dstats.tx_errors, dhdp->dstats.tx_dropped);
- bcm_bprintf(strbuf, "rx_packets %lu rx_bytes %lu rx_errors %lu rx_dropped %lu\n",
- dhdp->dstats.rx_packets, dhdp->dstats.rx_bytes,
- dhdp->dstats.rx_errors, dhdp->dstats.rx_dropped);
- bcm_bprintf(strbuf, "multicast %lu\n", dhdp->dstats.multicast);
+ dhd_dump_txrx_stats(dhdp, strbuf);
- bcm_bprintf(strbuf, "bus stats:\n");
- bcm_bprintf(strbuf, "tx_packets %lu tx_dropped %lu tx_multicast %lu tx_errors %lu\n",
- dhdp->tx_packets, dhdp->tx_dropped, dhdp->tx_multicast, dhdp->tx_errors);
- bcm_bprintf(strbuf, "tx_ctlpkts %lu tx_ctlerrs %lu\n",
- dhdp->tx_ctlpkts, dhdp->tx_ctlerrs);
- bcm_bprintf(strbuf, "rx_packets %lu rx_forward %lu rx_multicast %lu rx_errors %lu \n",
- dhdp->rx_packets, dhdp->rx_forward, dhdp->rx_multicast, dhdp->rx_errors);
- bcm_bprintf(strbuf, "rx_ctlpkts %lu rx_ctlerrs %lu rx_dropped %lu\n",
- dhdp->rx_ctlpkts, dhdp->rx_ctlerrs, dhdp->rx_dropped);
- bcm_bprintf(strbuf, "rx_readahead_cnt %lu tx_realloc %lu\n",
- dhdp->rx_readahead_cnt, dhdp->tx_realloc);
- bcm_bprintf(strbuf, "tx_pktgetfail %lu rx_pktgetfail %lu rx_pktgetpool_fail %lu\n",
- dhdp->tx_pktgetfail, dhdp->rx_pktgetfail, dhdp->rx_pktgetpool_fail);
- bcm_bprintf(strbuf, "tx_big_packets %lu\n",
- dhdp->tx_big_packets);
- bcm_bprintf(strbuf, "\n");
#ifdef DMAMAP_STATS
/* Add DMA MAP info */
bcm_bprintf(strbuf, "DMA MAP stats: \n");
@@ -1631,40 +1685,8 @@
#endif /* DHD_LB_STATS */
#ifdef DHD_MEM_STATS
-
- malloc_mem = MALLOCED(dhdp->osh);
-
- txpath_bkpq_len = dhd_active_tx_flowring_bkpq_len(dhdp);
- /*
- * Instead of traversing the entire queue to find the skbs length,
- * considering MAX_MTU_SZ as lenth of each skb.
- */
- txpath_bkpq_mem = (txpath_bkpq_len* MAX_MTU_SZ);
- total_txpath_mem = dhdp->txpath_mem + txpath_bkpq_mem;
-
- bcm_bprintf(strbuf, "\nDHD malloc memory_usage: %llubytes %lluKB\n",
- malloc_mem, (malloc_mem / 1024));
-
- bcm_bprintf(strbuf, "\nDHD tx-bkpq len: %llu memory_usage: %llubytes %lluKB\n",
- txpath_bkpq_len, txpath_bkpq_mem, (txpath_bkpq_mem / 1024));
- bcm_bprintf(strbuf, "DHD tx-path memory_usage: %llubytes %lluKB\n",
- total_txpath_mem, (total_txpath_mem / 1024));
-
- total_dhd_mem = malloc_mem + total_txpath_mem;
-#if defined(DHD_LB_STATS)
- total_dhd_mem += dhd_lb_mem_usage(dhdp, strbuf);
-#endif /* DHD_LB_STATS */
- bcm_bprintf(strbuf, "\nDHD Totoal memory_usage: %llubytes %lluKB \n",
- total_dhd_mem, (total_dhd_mem / 1024));
+ dhd_dump_memstats(dhdp, strbuf);
#endif /* DHD_MEM_STATS */
-#if defined(DHD_LB_STATS)
- bcm_bprintf(strbuf, "\nlb_rxp_stop_thr_hitcnt: %llu lb_rxp_strt_thr_hitcnt: %llu"
- " rx_dma_stall_hc_ignore_cnt: %llu\n",
- dhdp->lb_rxp_stop_thr_hitcnt, dhdp->lb_rxp_strt_thr_hitcnt,
- dhdp->rx_dma_stall_hc_ignore_cnt);
- bcm_bprintf(strbuf, "\nlb_rxp_napi_sched_cnt: %llu lb_rxp_napi_complete_cnt: %llu\n",
- dhdp->lb_rxp_napi_sched_cnt, dhdp->lb_rxp_napi_complete_cnt);
-#endif /* DHD_LB_STATS */
#if defined(DHD_MQ) && defined(DHD_MQ_STATS)
dhd_mqstats_dump(dhdp, strbuf);
@@ -1682,6 +1704,33 @@
return (!strbuf->size ? BCME_BUFTOOSHORT : strbuf->size);
}
+int
+dhd_counters(dhd_pub_t *dhdp, char *buf, int buflen)
+{
+ struct bcmstrbuf bcmbuf;
+ struct bcmstrbuf *strbuf = &bcmbuf;
+
+ if (!dhdp || !dhdp->prot || !buf) {
+ return BCME_ERROR;
+ }
+
+ bcm_binit(strbuf, buf, buflen);
+
+ dhd_dump_txrx_stats(dhdp, strbuf);
+
+ dhd_bus_counters(dhdp, strbuf);
+
+#if defined(DHD_LB_STATS)
+ dhd_lb_stats_dump(dhdp, strbuf);
+#endif /* DHD_LB_STATS */
+
+#ifdef DHD_MEM_STATS
+ dhd_dump_memstats(dhdp, strbuf);
+#endif /* DHD_MEM_STATS */
+
+ return (!strbuf->size ? BCME_BUFTOOSHORT : strbuf->size);
+}
+
void
dhd_dump_to_kernelog(dhd_pub_t *dhdp)
{
@@ -1811,7 +1860,7 @@
dhd_iov_li_t *iov_li;
#endif /* DUMP_IOCTL_IOV_LIST */
#ifdef REPORT_FATAL_TIMEOUTS
- wl_escan_params_t *eparams;
+ wl_escan_params_v1_t *eparams;
uint8 *buf_ptr = (uint8 *)buf;
uint16 action = 0;
#endif /* REPORT_FATAL_TIMEOUTS */
@@ -1912,6 +1961,28 @@
dhdpcie_runtime_bus_wake(dhd_pub, TRUE, dhd_wl_ioctl);
#endif /* DHD_PCIE_RUNTIMEPM */
+#ifdef OEM_ANDROID
+ /*
+ * If system suspend started before ioctl, after getting d3 ack,
+ * it will check for wakelock and as ioctl will hold wakelock,
+ * it will put bus back to d0 and bail out.
+ * So the current ioctl should wait till it is bailed out.
+ */
+ if (DHD_BUS_BUSY_CHECK_SUSPEND_IN_PROGRESS(dhd_pub)) {
+ int timeleft = 0;
+ DHD_PRINT(("%s: wait till system suspend bails out\n", __FUNCTION__));
+ /* wait till SUSPEND_IN_PROGRESS bit is cleared */
+ timeleft = dhd_os_busbusy_wait_bitmask(dhd_pub,
+ &dhd_pub->dhd_bus_busy_state,
+ DHD_BUS_BUSY_SUSPEND_IN_PROGRESS, 0);
+ if ((dhd_pub->dhd_bus_busy_state & DHD_BUS_BUSY_SUSPEND_IN_PROGRESS) != 0) {
+ DHD_ERROR(("%s: system suspend wait timed out(%d)"
+ " dhd_bus_busy_state=0x%x\n", __FUNCTION__, timeleft,
+ dhd_pub->dhd_bus_busy_state));
+ }
+ }
+#endif /* OEM_ANDROID */
+
DHD_LINUX_GENERAL_LOCK(dhd_pub, flags);
if (DHD_BUS_CHECK_SUSPEND_OR_ANY_SUSPEND_IN_PROGRESS(dhd_pub) ||
dhd_pub->dhd_induce_error == DHD_INDUCE_IOCTL_SUSPEND_ERROR) {
@@ -1977,7 +2048,7 @@
if ((ioc->cmd == WLC_SET_VAR &&
buf != NULL &&
strcmp("escan", buf) == 0)) {
- eparams = (wl_escan_params_t *) (buf_ptr + strlen("escan") + 1);
+ eparams = (wl_escan_params_v1_t *) (buf_ptr + strlen("escan") + 1);
action = dtoh16(eparams->action);
if (action == WL_SCAN_ACTION_START) {
++dhd_pub->esync_id;
@@ -2031,8 +2102,8 @@
lval = 0;
}
}
- DHD_IOVAR_MEM((
- "%s: cmd: %d, msg: %s val: 0x%x,"
+ DHD_IOVAR_LOG(dhd_pub, ioc->cmd, msg,
+ ("%s: cmd: %d, msg: %s val: 0x%x,"
" len: %d, set: %d, txn-id: %d\n",
ioc->cmd == WLC_GET_VAR ?
"WLC_GET_VAR" : "WLC_SET_VAR",
@@ -2558,8 +2629,10 @@
#endif /* BCMDBUS */
- case IOV_SVAL(IOV_CLEARCOUNTS):
+ case IOV_SVAL(IOV_RESET_COUNTS):
dhd_pub->tx_packets = dhd_pub->rx_packets = 0;
+ dhd_pub->tx_multicast = dhd_pub->rx_multicast = 0;
+ dhd_pub->tx_bytes = dhd_pub->rx_bytes = 0;
dhd_pub->tx_errors = dhd_pub->rx_errors = 0;
dhd_pub->tx_ctlpkts = dhd_pub->rx_ctlpkts = 0;
dhd_pub->tx_ctlerrs = dhd_pub->rx_ctlerrs = 0;
@@ -3734,6 +3807,20 @@
break;
}
+ case IOV_GVAL(IOV_COUNTERS):
+ if (dhd_counters(dhd_pub, arg, len) <= 0)
+ bcmerror = BCME_ERROR;
+ else
+ bcmerror = BCME_OK;
+ break;
+#ifdef BCMPCIE
+ case IOV_GVAL(IOV_DUMP_FLOWRINGS):
+ if (dhd_dump_flowrings(dhd_pub, arg, len) <= 0)
+ bcmerror = BCME_ERROR;
+ else
+ bcmerror = BCME_OK;
+ break;
+#endif /* BCMPCIE */
default:
bcmerror = BCME_UNSUPPORTED;
break;
@@ -4672,6 +4759,9 @@
case WLC_E_PFN_SCAN_NONE:
case WLC_E_PFN_SCAN_ALLGONE:
case WLC_E_PFN_GSCAN_FULL_RESULT:
+#ifdef WL_SCHED_SCAN
+ case WLC_E_PFN_PARTIAL_RESULT:
+#endif /* WL_SCHED_SCAN */
case WLC_E_PFN_SSID_EXT:
DHD_EVENT(("PNOEVENT: %s\n", event_name));
break;
@@ -4725,12 +4815,6 @@
DHD_EVENT(("MACEVENT: %s, MAC %s\n", event_name, eabuf));
break;
-#ifdef BT_WIFI_HANDOBER
- case WLC_E_BT_WIFI_HANDOVER_REQ:
- DHD_EVENT(("MACEVENT: %s, MAC %s\n", event_name, eabuf));
- break;
-#endif
-
case WLC_E_CCA_CHAN_QUAL:
/* I would like to check here that datalen >= sizeof(cca_chan_qual_event_t)
* but since definition of cca_chan_qual_event_t is different
@@ -5024,6 +5108,19 @@
DHD_EVENT(("MACEVENT: %s: Country code changed to %s\n", event_name,
(char*)event_data));
break;
+ case WLC_E_SCAN:
+ {
+ const char *scan_state;
+ if (reason == WL_SCAN_START) {
+ scan_state = "WL_SCAN_START";
+ } else if (reason == WL_SCAN_END) {
+ scan_state = "WL_SCAN_END";
+ } else {
+ scan_state = "Unknown";
+ }
+ DHD_EVENT(("MACEVENT: %s: scan state %s\n", event_name, scan_state));
+ break;
+ }
default:
DHD_INFO(("MACEVENT: %s %d, MAC %s, status %d, reason %d, auth %d\n",
event_name, event_type, eabuf, (int)status, (int)reason,
@@ -5328,6 +5425,26 @@
}
break;
}
+ case DNGL_E_SPMI_RESET_IND:
+ {
+ bcm_dngl_spmi_reset_ind_v1_t *spmi_reset_ind_v1_ptr =
+ (bcm_dngl_spmi_reset_ind_v1_t *)p;
+ uint16 ver = ltoh32(spmi_reset_ind_v1_ptr->version);
+ switch (ver) {
+ case DNGL_E_SPMI_RESET_IND_VERSION_1:
+ {
+ uint16 num_resets = ltoh32(spmi_reset_ind_v1_ptr->num_resets);
+ uint16 slave_idx = ltoh32(spmi_reset_ind_v1_ptr->slave_idx);
+ DHD_EVENT(("DNGL_E_SPMI_RESET_IND resets=%u SPMI core=%u\n",
+ num_resets, slave_idx));
+ break;
+ }
+ default:
+ DHD_ERROR(("DNGL_E_SPMI_RESET_IND: unknown version\n"));
+ break;
+ }
+ break;
+ }
default:
DHD_ERROR(("%s:Unknown DNGL Event Type:%d\n", __FUNCTION__, type));
if (p && DHD_EVENT_ON()) {
@@ -5521,7 +5638,9 @@
case WLC_E_IF:
{
struct wl_event_data_if *ifevent = (struct wl_event_data_if *)event_data;
- struct net_device *ndev = dhd_idx2net(dhd_pub, ifevent->ifidx);
+#if defined(__linux__)
+ struct net_device *ndev = NULL;
+#endif /* __linux__ */
/* Ignore the event if NOIF is set */
if (ifevent->reserved & WLC_E_IF_FLAGS_BSSCFG_NOIF) {
@@ -5568,11 +5687,19 @@
return (BCME_ERROR);
}
#if defined(__linux__)
- dhd_clear_del_in_progress(dhd_pub, ndev);
+ ndev = dhd_idx2net(dhd_pub, ifevent->ifidx);
+ if (ndev) {
+ dhd_clear_del_in_progress(dhd_pub, ndev);
+ }
#endif /* __linux__ */
} else if (ifevent->opcode == WLC_E_IF_DEL) {
- dhd_set_del_in_progress(dhd_pub, ndev);
- netif_tx_disable(ndev);
+#if defined(__linux__)
+ ndev = dhd_idx2net(dhd_pub, ifevent->ifidx);
+ if (ndev) {
+ dhd_set_del_in_progress(dhd_pub, ndev);
+ netif_tx_disable(ndev);
+ }
+#endif /* __linux__ */
#ifdef PCIE_FULL_DONGLE
dhd_flow_rings_delete(dhd_pub,
(uint8)dhd_ifname2idx(dhd_pub->info, event->ifname));
@@ -6916,7 +7043,7 @@
{
wl_iscan_results_t *list_buf;
wl_iscan_results_t list;
- wl_scan_results_t *results;
+ wl_scan_results_v109_t *results;
iscan_buf_t *iscan_cur;
int status = -1;
dhd_pub_t *dhd = dhd_bus_pub(dhdp);
@@ -7129,8 +7256,8 @@
{
char buf[32] = {0};
const char *str;
- wl_mkeep_alive_pkt_t mkeep_alive_pkt = {0, 0, 0, 0, 0, {0}};
- wl_mkeep_alive_pkt_t *mkeep_alive_pktp;
+ wl_mkeep_alive_pkt_v1_t mkeep_alive_pkt = {0, 0, 0, 0, 0, {0}};
+ wl_mkeep_alive_pkt_v1_t *mkeep_alive_pktp;
int buf_len;
int str_len;
int res = -1;
@@ -7143,10 +7270,10 @@
str = "mkeep_alive";
str_len = strlen(str);
strlcpy(buf, str, sizeof(buf));
- mkeep_alive_pktp = (wl_mkeep_alive_pkt_t *) (buf + str_len + 1);
+ mkeep_alive_pktp = (wl_mkeep_alive_pkt_v1_t *) (buf + str_len + 1);
mkeep_alive_pkt.period_msec = CUSTOM_KEEP_ALIVE_SETTING;
buf_len = str_len + 1;
- mkeep_alive_pkt.version = htod16(WL_MKEEP_ALIVE_VERSION);
+ mkeep_alive_pkt.version = htod16(WL_MKEEP_ALIVE_VERSION_1);
mkeep_alive_pkt.length = htod16(WL_MKEEP_ALIVE_FIXED_LEN);
/* Setup keep alive zero for null packet generation */
mkeep_alive_pkt.keep_alive_id = 0;
@@ -10902,6 +11029,15 @@
case DUMP_TYPE_DONGLE_TRAP:
type_str = "Dongle_Trap";
break;
+ case DUMP_TYPE_DONGLE_TRAP_DURING_WIFI_ONOFF:
+ type_str = "Dongle_Trap_During_Wifi_OnOff";
+ break;
+ case DUMP_TYPE_BY_DSACK_HC_DUE_TO_ISR_DELAY:
+ type_str = "Dongle_Trap_DSACK_HC_due_to_ISR_delay";
+ break;
+ case DUMP_TYPE_BY_DSACK_HC_DUE_TO_DPC_DELAY:
+ type_str = "Dongle_Trap_DSACK_HC_due_to_DPC_delay";
+ break;
case DUMP_TYPE_MEMORY_CORRUPTION:
type_str = "Memory_Corruption";
break;
@@ -11344,8 +11480,8 @@
case HANG_REASON_DS_SKIP_TIMEOUT:
type_str = "DS_SKIP_TIMEOUT";
break;
- case HANG_REASON_SLEEP_FAILURE:
- type_str = "SLEEP_FAILURE";
+ case HANG_REASON_BT2WL_REG_RESET:
+ type_str = "BT2WL_REG_RESET";
break;
default:
type_str = "Unknown_type";
@@ -11355,3 +11491,165 @@
strlcpy(buf, type_str, buf_len);
}
#endif /* DHD_COREDUMP */
+#ifdef DHD_CUSTOM_CONFIG_RTS_IN_SUSPEND
+int dhd_config_rts_in_suspend(dhd_pub_t *dhdp, bool suspend)
+{
+ int ret = BCME_OK;
+ uint return_to_sleep_time = 0;
+
+ int buf_len;
+ bcm_iov_buf_t *iov_buf = NULL;
+ wl_adps_suspend_v1_t *data = NULL;
+
+ if (!dhdp || dhdp->up == 0) {
+ return ret;
+ }
+
+ /* if it's not associated, skip to set */
+ if (!dhd_is_associated(dhdp, 0, NULL)) {
+ return ret;
+ }
+
+ if (suspend) {
+ return_to_sleep_time = CUSTOM_RETRUN_TO_SLEEP_TIME_SUSPEND;
+ }
+ else {
+ return_to_sleep_time = CUSTOM_RETRUN_TO_SLEEP_TIME_DEFAULT;
+ }
+
+ ret = dhd_iovar(dhdp, 0, "pm2_sleep_ret", (char *)&return_to_sleep_time,
+ sizeof(return_to_sleep_time), NULL, 0, TRUE);
+
+ if (ret < 0) {
+ DHD_ERROR(("%s set pm2_sleep_ret failed %d\n", __FUNCTION__, ret));
+ goto exit;
+ }
+
+ buf_len = OFFSETOF(bcm_iov_buf_t, data) + sizeof(*data);
+ iov_buf = MALLOCZ(dhdp->osh, buf_len);
+ if (iov_buf == NULL) {
+ DHD_ERROR(("%s - failed to alloc %d bytes for iov_buf\n",
+ __FUNCTION__, buf_len));
+ ret = BCME_NOMEM;
+ goto exit;
+ }
+
+ iov_buf->version = WL_ADPS_IOV_VER;
+ iov_buf->len = sizeof(*data);
+ iov_buf->id = WL_ADPS_IOV_SUSPEND;
+
+ data = (wl_adps_suspend_v1_t *)iov_buf->data;
+ data->version = ADPS_SUB_IOV_VERSION_1;
+ data->length = sizeof(*data);
+ data->suspend = suspend;
+
+ ret = dhd_iovar(dhdp, 0, "adps", (char *)iov_buf, buf_len,
+ NULL, 0, TRUE);
+ if (ret < 0) {
+ DHD_ERROR(("%s - fail to set adps suspend %d (%d)\n",
+ __FUNCTION__, suspend, ret));
+ goto exit;
+ }
+
+exit:
+ if (ret == BCME_OK) {
+ DHD_ERROR(("%s - Success to set RTS [%d] and ADPS suspend [%d].\n",
+ __FUNCTION__, return_to_sleep_time, suspend));
+ }
+ if (iov_buf) {
+ MFREE(dhdp->osh, iov_buf, buf_len);
+ }
+ return ret;
+}
+#endif /* DHD_CUSTOM_CONFIG_RTS_IN_SUSPEND */
+
+void
+dhd_histo_update(dhd_pub_t *dhd, uint64 *histo, uint32 value)
+{
+ uint64 *p;
+ uint64 *bin = histo;
+ uint32 bin_power = next_larger_power2(value);
+ if (histo == NULL) {
+ DHD_ERROR(("%s: histo is NULL\n", __FUNCTION__));
+ return;
+ }
+
+ switch (bin_power) {
+ case 1: p = bin + 0; break;
+ case 2: p = bin + 1; break;
+ case 4: p = bin + 2; break;
+ case 8: p = bin + 3; break;
+ case 16: p = bin + 4; break;
+ case 32: p = bin + 5; break;
+ case 64: p = bin + 6; break;
+ case 128: p = bin + 7; break;
+ case 256: p = bin + 8; break;
+ case 512: p = bin + 9; break;
+ case 1024: p = bin + 10; break;
+ case 2048: p = bin + 11; break;
+ case 4096: p = bin + 12; break;
+ case 8192: p = bin + 13; break;
+ default : p = bin + 13; break;
+ }
+ ASSERT((p - bin) < DHD_HISTOGRAM_ENTRIES);
+ *p = *p + 1;
+ return;
+}
+
+void
+dhd_histo_clear(dhd_pub_t *dhd, uint64 *histo)
+{
+
+ if (histo == NULL) {
+ return;
+ }
+
+ bzero(histo, DHD_HISTOGRAM_SIZE);
+}
+
+void
+dhd_histo_tag_dump(dhd_pub_t *dhd, struct bcmstrbuf *strbuf, char *tagname)
+{
+ uint32 i;
+
+ bcm_bprintf(strbuf, "%20s: ", tagname);
+ for (i = 0; i < DHD_HISTOGRAM_ENTRIES; i++) {
+ bcm_bprintf(strbuf, "%10llu ", 1ULL<<i);
+ }
+ bcm_bprintf(strbuf, "\n");
+}
+
+void
+dhd_histo_dump(dhd_pub_t *dhd, struct bcmstrbuf *strbuf, uint64 *histo, char *histoname)
+{
+ uint32 i;
+
+ if (histo == NULL) {
+ return;
+ }
+
+ bcm_bprintf(strbuf, "%20s: ", histoname);
+ for (i = 0; i < DHD_HISTOGRAM_ENTRIES; i++) {
+ bcm_bprintf(strbuf, "%10llu ", histo[i]);
+ }
+ bcm_bprintf(strbuf, "\n");
+}
+
+uint64 *
+dhd_histo_init(dhd_pub_t *dhd)
+{
+ uint64 *histo;
+ histo = (uint64 *)MALLOCZ(dhd->osh, DHD_HISTOGRAM_SIZE);
+ if (histo == NULL) {
+ DHD_ERROR(("%s: unable to alloc histo\n", __FUNCTION__));
+ }
+ return histo;
+}
+
+void
+dhd_histo_deinit(dhd_pub_t *dhd, uint64 *histo)
+{
+ if (histo) {
+ MFREE(dhd->osh, histo, DHD_HISTOGRAM_SIZE);
+ }
+}
diff --git a/dhd_custom_cis.c b/dhd_custom_cis.c
index eed5139..877dcc0 100644
--- a/dhd_custom_cis.c
+++ b/dhd_custom_cis.c
@@ -2,7 +2,7 @@
* Process CIS information from OTP for customer platform
* (Handle the MAC address and module information)
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -297,6 +297,7 @@
{ {"1wk_es50"}, {"_1wk_es50_c1"}, {"_c1"} },
{ {"1wk_es51"}, {"_1wk_es51_c1"}, {"_c1"} },
{ {"1wk_es60"}, {"_1wk_es60_c1"}, {"_c1"} },
+ { {"1wk_es61"}, {"_1wk_es61_c1"}, {"_c1"} },
{ {"1wk_es10"}, {"_1wk_es10_c1"}, {"_c1"} },
{ {"1wk_es11"}, {"_1wk_es11_c1"}, {"_c1"} },
{ {"usi_es10"}, {"_ES10"}, {"_c0"} },
@@ -307,6 +308,7 @@
{ {"usi_es17"}, {"_ES17"}, {""} },
{ {"usi_es19"}, {"_ES19"}, {""} },
{ {"usi_es21"}, {"_ES21"}, {""} },
+ { {"usi_es31"}, {"_ES31"}, {""} },
};
/* select the NVRAM/FW tag naming table */
@@ -684,7 +686,7 @@
/* check for version */
version = dtoh16(*(uint16 *)iov_resp);
- if (version != WL_OTP_IOV_VERSION) {
+ if (version != WL_OTP_IOV_VERSION_1_1) {
return BCME_VERSION;
}
@@ -730,7 +732,7 @@
}
/* fill header portion */
- iov_buf->version = WL_OTP_IOV_VERSION;
+ iov_buf->version = WL_OTP_IOV_VERSION_1_1;
iov_buf->len = (buflen_start - buflen);
iov_buf->id = cmd_id;
@@ -904,99 +906,6 @@
}
-#if defined(CONFIG_WIFI_BROADCOM_COB) && defined(BCM4389_CHIP_DEF)
-static int
-dhd_otp_packfn_hw_rgnstatus(void *ctx, uint8 *buf, uint16 *buflen)
-{
- uint8 *pxtlv = buf;
- int ret = BCME_OK;
- uint16 len = *buflen;
- uint8 rgnid = OTP_RGN_HW;
-
- BCM_REFERENCE(ctx);
-
- /* pack option <-r region> */
- ret = bcm_pack_xtlv_entry(&pxtlv, &len, WL_OTP_XTLV_RGN, sizeof(rgnid),
- &rgnid, BCM_XTLV_OPTION_ALIGN32);
- if (ret != BCME_OK) {
- DHD_ERROR(("%s: Failed pack xtlv entry of region: %d\n", __FUNCTION__, ret));
- return ret;
- }
-
- *buflen = len;
- return ret;
-}
-
-static int
-dhd_otp_packfn_hw_rgndump(void *ctx, uint8 *buf, uint16 *buflen)
-{
- uint8 *pxtlv = buf;
- int ret = BCME_OK;
- uint16 len = *buflen, size = WLC_IOCTL_MAXLEN;
- uint8 rgnid = OTP_RGN_HW;
-
- /* pack option <-r region> */
- ret = bcm_pack_xtlv_entry(&pxtlv, &len, WL_OTP_XTLV_RGN,
- sizeof(rgnid), &rgnid, BCM_XTLV_OPTION_ALIGN32);
- if (ret != BCME_OK) {
- DHD_ERROR(("%s: Failed pack xtlv entry of region: %d\n", __FUNCTION__, ret));
- goto fail;
- }
-
- /* pack option [-s size] */
- ret = bcm_pack_xtlv_entry(&pxtlv, &len, WL_OTP_XTLV_SIZE,
- sizeof(size), (uint8 *)&size, BCM_XTLV_OPTION_ALIGN32);
- if (ret != BCME_OK) {
- DHD_ERROR(("%s: Failed pack xtlv entry of size: %d\n", __FUNCTION__, ret));
- goto fail;
- }
- *buflen = len;
-fail:
- return ret;
-}
-
-int
-dhd_read_otp_hw_rgn(dhd_pub_t *dhdp)
-{
- int ret = BCME_OK;
- otp_rgn_rw_info_t rw_info;
- otp_rgn_stat_info_t stat_info;
-
- memset(&rw_info, 0, sizeof(rw_info));
- memset(&stat_info, 0, sizeof(stat_info));
-
- /* initialization */
- otpinfo_val = -1;
-
- ret = dhd_otp_get_iov_resp(dhdp, WL_OTP_CMD_RGNSTATUS, &stat_info,
- dhd_otp_packfn_hw_rgnstatus, dhd_otp_cbfn_rgnstatus);
- if (ret != BCME_OK) {
- DHD_ERROR(("%s: otp region status failed, ret=%d\n", __FUNCTION__, ret));
- goto fail;
- }
-
- rw_info.rgnsize = stat_info.rgnsize;
- ret = dhd_otp_get_iov_resp(dhdp, WL_OTP_CMD_RGNDUMP, &rw_info,
- dhd_otp_packfn_hw_rgndump, dhd_otp_cbfn_rgndump);
- if (ret != BCME_OK) {
- if (ret == BCME_NOTFOUND) {
- otpinfo_val = 0;
- DHD_ERROR(("%s: OTP not found otpinfo_val = %d \n",
- __FUNCTION__, otpinfo_val));
-
- }
- DHD_ERROR(("%s: otp region dump failed, ret=%d\n", __FUNCTION__, ret));
- goto fail;
- }
-
- otpinfo_val = 1;
- DHD_INFO(("%s: OTP written otpinfo_val = %d\n", __FUNCTION__, otpinfo_val));
-fail:
- return ret;
-
-}
-#endif /* CONFIG_WIFI_BROADCOM_COB && BCM4389_CHIP_DEF */
-
#if defined(GET_MAC_FROM_OTP) || defined(USE_CID_CHECK)
static tuple_entry_t*
dhd_alloc_tuple_entry(dhd_pub_t *dhdp, const int idx)
@@ -1757,6 +1666,7 @@
{ 3, { 0x50, 0x22, }, { "murata_mur_1wk_es50" } },
{ 3, { 0x51, 0x24, }, { "murata_mur_1wk_es51" } },
{ 3, { 0x60, 0x24, }, { "murata_mur_1wk_es60" } },
+ { 3, { 0x61, 0x24, }, { "murata_mur_1wk_es61" } },
{ 3, { 0x10, 0x25, }, { "murata_mur_1wk_es10" } },
{ 3, { 0x11, 0x25, }, { "murata_mur_1wk_es11" } },
{ 3, { 0x10, 0x99, }, { "USI_WM_usi_es10" } },
@@ -1767,6 +1677,7 @@
{ 3, { 0x17, 0x99, }, { "USI_WM_usi_es17" } },
{ 3, { 0x19, 0x99, }, { "USI_WM_usi_es19" } },
{ 3, { 0x21, 0x99, }, { "USI_WM_usi_es21" } },
+ { 3, { 0x31, 0x99, }, { "USI_WM_usi_es31" } },
#endif /* SUPPORT_MIXED_MODULES */
};
#else
diff --git a/dhd_custom_google.c b/dhd_custom_google.c
index 25b8cbf..b3c3e13 100644
--- a/dhd_custom_google.c
+++ b/dhd_custom_google.c
@@ -1,7 +1,7 @@
/*
* Platform Dependent file for Hikey
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -151,14 +151,20 @@
{ {"G8V0U"}, {"MMW"} },
{ {"GFQM1"}, {"MMW"} },
{ {"GB62Z"}, {"MMW"} },
+ { {"GE2AE"}, {"MMW"} },
+ { {"GQML3"}, {"MMW"} },
{ {"GB7N6"}, {"ROW"} },
{ {"GLU0G"}, {"ROW"} },
{ {"GNA8F"}, {"ROW"} },
{ {"GX7AS"}, {"ROW"} },
+ { {"GP4BC"}, {"ROW"} },
+ { {"GVU6C"}, {"ROW"} },
{ {"GR1YH"}, {"JPN"} },
{ {"GF5KQ"}, {"JPN"} },
{ {"GPQ72"}, {"JPN"} },
{ {"GB17L"}, {"JPN"} },
+ { {"GFE4J"}, {"JPN"} },
+ { {"G03Z5"}, {"JPN"} },
{ {"G1AZG"}, {"EU"} }
};
@@ -530,15 +536,6 @@
/* ========== WLAN_PWR_EN ============ */
DHD_INFO(("%s: gpio_wlan_power : %d\n", __FUNCTION__, wlan_reg_on));
-#ifdef EXYNOS_PCIE_RC_ONOFF
- if (of_property_read_u32(root_node, "ch-num", &pcie_ch_num)) {
- DHD_INFO(("%s: Failed to parse the channel number\n", __FUNCTION__));
- return -EINVAL;
- }
- /* ========== WLAN_PCIE_NUM ============ */
- DHD_INFO(("%s: pcie_ch_num : %d\n", __FUNCTION__, pcie_ch_num));
-#endif /* EXYNOS_PCIE_RC_ONOFF */
-
/*
* For reg_on, gpio_request will fail if the gpio is configured to output-high
* in the dts using gpio-hog, so do not return error for failure.
@@ -568,12 +565,7 @@
/* Wait for WIFI_TURNON_DELAY due to power stability */
msleep(WIFI_TURNON_DELAY);
-#ifdef EXYNOS_PCIE_RC_ONOFF
- if (exynos_pcie_pm_resume(pcie_ch_num)) {
- WARN(1, "pcie link up failure\n");
- return -ENODEV;
- }
-#endif /* EXYNOS_PCIE_RC_ONOFF */
+
#ifdef CONFIG_BCMDHD_OOB_HOST_WAKE
/* ========== WLAN_HOST_WAKE ============ */
wlan_host_wake_up = of_get_named_gpio(root_node,
@@ -644,6 +636,29 @@
static int
dhd_wlan_set_carddetect(int val)
{
+#ifdef EXYNOS_PCIE_RC_ONOFF
+ struct device_node *root_node = NULL;
+ char *wlan_node = DHD_DT_COMPAT_ENTRY;
+
+ root_node = of_find_compatible_node(NULL, NULL, wlan_node);
+ if (!root_node) {
+ DHD_ERROR(("failed to get device node of BRCM WLAN\n"));
+ return -ENODEV;
+ }
+
+ if (of_property_read_u32(root_node, "ch-num", &pcie_ch_num)) {
+ DHD_INFO(("%s: Failed to parse the channel number\n", __FUNCTION__));
+ return -EINVAL;
+ }
+ /* ========== WLAN_PCIE_NUM ============ */
+ DHD_INFO(("%s: pcie_ch_num : %d\n", __FUNCTION__, pcie_ch_num));
+#endif /* EXYNOS_PCIE_RC_ONOFF */
+
+ if (val) {
+ exynos_pcie_pm_resume(pcie_ch_num);
+ } else {
+ printk(KERN_INFO "%s Ignore carddetect: %d\n", __FUNCTION__, val);
+ }
return 0;
}
@@ -945,6 +960,7 @@
{
int ret = 0;
ret = exynos_pcie_pm_resume(pcie_ch_num);
+ is_irq_on_big_core = true;
return ret;
}
diff --git a/dhd_custom_gpio.c b/dhd_custom_gpio.c
index 1049391..071880a 100644
--- a/dhd_custom_gpio.c
+++ b/dhd_custom_gpio.c
@@ -1,7 +1,7 @@
/*
* Customer code to add GPIO control during WLAN start/stop
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/dhd_custom_memprealloc.c b/dhd_custom_memprealloc.c
old mode 100644
new mode 100755
index 4dfa6f4..fac72fe
--- a/dhd_custom_memprealloc.c
+++ b/dhd_custom_memprealloc.c
@@ -1,7 +1,7 @@
/*
* Platform Dependent file for usage of Preallocted Memory
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -112,7 +112,7 @@
((WLAN_MAX_PKTID_IOCTL_ITEMS+1) * WLAN_DHD_PKTID_IOCTL_MAP_ITEM_SIZE))
#define DHD_LOG_DUMP_BUF_SIZE (1024 * 1024 * 4)
-#define DHD_LOG_DUMP_BUF_EX_SIZE (1024 * 1024 * 2)
+#define DHD_LOG_DUMP_BUF_EX_SIZE (1024 * 8)
#define DHD_PKTLOG_DUMP_BUF_SIZE (64 * 1024)
@@ -291,8 +291,13 @@
for (i = 0; i < PREALLOC_WLAN_SEC_NUM; i++) {
if (wlan_mem_array[i].size > 0) {
+#ifdef CONFIG_BCMDHD_PCIE
+ wlan_mem_array[i].mem_ptr =
+ kvmalloc(wlan_mem_array[i].size, GFP_KERNEL);
+#else
wlan_mem_array[i].mem_ptr =
kmalloc(wlan_mem_array[i].size, GFP_KERNEL);
+#endif /* CONFIG_BCMDHD_PCIE */
if (!wlan_mem_array[i].mem_ptr) {
pr_err("Failed to mem_alloc for WLAN\n");
@@ -301,13 +306,21 @@
}
}
+#ifdef CONFIG_BCMDHD_PCIE
+ wlan_static_scan_buf0 = kvmalloc(WLAN_SCAN_BUF_SIZE, GFP_KERNEL);
+#else
wlan_static_scan_buf0 = kmalloc(WLAN_SCAN_BUF_SIZE, GFP_KERNEL);
+#endif /* CONFIG_BCMDHD_PCIE */
if (!wlan_static_scan_buf0) {
pr_err("Failed to alloc wlan_static_scan_buf0\n");
goto err_mem_alloc;
}
+#ifdef CONFIG_BCMDHD_PCIE
+ wlan_static_scan_buf1 = kvmalloc(WLAN_SCAN_BUF_SIZE, GFP_KERNEL);
+#else
wlan_static_scan_buf1 = kmalloc(WLAN_SCAN_BUF_SIZE, GFP_KERNEL);
+#endif /* CONFIG_BCMDHD_PCIE */
if (!wlan_static_scan_buf1) {
pr_err("Failed to alloc wlan_static_scan_buf1\n");
goto err_mem_alloc;
@@ -325,14 +338,18 @@
goto err_mem_alloc;
}
+#ifdef CONFIG_BCMDHD_PCIE
+ wlan_static_dhd_info_buf = kvmalloc(WLAN_DHD_INFO_BUF_SIZE, GFP_KERNEL);
+#else
wlan_static_dhd_info_buf = kmalloc(WLAN_DHD_INFO_BUF_SIZE, GFP_KERNEL);
+#endif /* CONFIG_BCMDHD_PCIE */
if (!wlan_static_dhd_info_buf) {
pr_err("Failed to alloc wlan_static_dhd_info_buf\n");
goto err_mem_alloc;
}
#ifdef CONFIG_BCMDHD_PCIE
- wlan_static_if_flow_lkup = kmalloc(WLAN_DHD_IF_FLOW_LKUP_SIZE,
+ wlan_static_if_flow_lkup = kvmalloc(WLAN_DHD_IF_FLOW_LKUP_SIZE,
GFP_KERNEL);
if (!wlan_static_if_flow_lkup) {
pr_err("Failed to alloc wlan_static_if_flow_lkup\n");
@@ -396,7 +413,7 @@
#ifdef CONFIG_BCMDHD_PCIE
if (wlan_static_if_flow_lkup) {
- kfree(wlan_static_if_flow_lkup);
+ kvfree(wlan_static_if_flow_lkup);
}
#else
if (wlan_static_dhd_wlfc_buf) {
@@ -408,7 +425,11 @@
}
#endif /* CONFIG_BCMDHD_PCIE */
if (wlan_static_dhd_info_buf) {
+#ifdef CONFIG_BCMDHD_PCIE
+ kvfree(wlan_static_dhd_info_buf);
+#else
kfree(wlan_static_dhd_info_buf);
+#endif /* CONFIG_BCMDHD_PCIE */
}
if (wlan_static_dhd_log_dump_buf) {
@@ -420,16 +441,28 @@
}
if (wlan_static_scan_buf1) {
+#ifdef CONFIG_BCMDHD_PCIE
+ kvfree(wlan_static_scan_buf1);
+#else
kfree(wlan_static_scan_buf1);
+#endif /* CONFIG_BCMDHD_PCIE */
}
if (wlan_static_scan_buf0) {
+#ifdef CONFIG_BCMDHD_PCIE
+ kvfree(wlan_static_scan_buf0);
+#else
kfree(wlan_static_scan_buf0);
+#endif /* CONFIG_BCMDHD_PCIE */
}
for (i = 0; i < PREALLOC_WLAN_SEC_NUM; i++) {
if (wlan_mem_array[i].mem_ptr) {
+#ifdef CONFIG_BCMDHD_PCIE
+ kvfree(wlan_mem_array[i].mem_ptr);
+#else
kfree(wlan_mem_array[i].mem_ptr);
+#endif /* CONFIG_BCMDHD_PCIE */
}
}
diff --git a/dhd_custom_msm.c b/dhd_custom_msm.c
index 160356f..ac8005b 100644
--- a/dhd_custom_msm.c
+++ b/dhd_custom_msm.c
@@ -1,7 +1,7 @@
/*
* Platform Dependent file for Qualcomm MSM/APQ
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -105,6 +105,11 @@
static dhd_pcie_event_cb_t g_pfn = NULL;
+char* dhd_get_device_dt_name(void)
+{
+ return DHD_DT_COMPAT_ENTRY;
+}
+
uint32 dhd_plat_get_info_size(void)
{
return sizeof(dhd_plat_info_t);
@@ -173,6 +178,11 @@
return -ENODEV;
}
+ if (!of_device_is_available(root_node)) {
+ printk(KERN_ERR "%s: brcm wlan device status is disable\n", __FUNCTION__);
+ return -ENXIO;
+ }
+
/* ========== WLAN_PWR_EN ============ */
wlan_reg_on = of_get_named_gpio(root_node, WIFI_WL_REG_ON_PROPNAME, 0);
printk(KERN_INFO "%s: gpio_wlan_power : %d\n", __FUNCTION__, wlan_reg_on);
@@ -220,11 +230,6 @@
wlan_host_wake_irq = gpio_to_irq(wlan_host_wake_up);
#endif /* CONFIG_BCMDHD_OOB_HOST_WAKE */
-#ifdef CONFIG_BCMDHD_PCIE
- printk(KERN_INFO "%s: Call msm_pcie_enumerate\n", __FUNCTION__);
- msm_pcie_enumerate(MSM_PCIE_CH_NUM);
-#endif /* CONFIG_BCMDHD_PCIE */
-
return 0;
}
diff --git a/dhd_dbg.h b/dhd_dbg.h
index 17846e0..fd81eef 100644
--- a/dhd_dbg.h
+++ b/dhd_dbg.h
@@ -1,7 +1,7 @@
/*
* Debug/trace/assert driver definitions for Dongle Host Driver.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -717,6 +717,25 @@
extern int log_print_threshold;
#endif /* DHD_LOG_PRINT_RATE_LIMIT */
+#ifdef DHD_IOVAR_LOG_FILTER_DUMP
+#define DHD_IOVAR_LOG_CHECK(dhd_pub, ioc_cmd, ioc_msg) \
+ dhd_iovar_log_dump_check(dhd_pub, ioc_cmd, ioc_msg)
+#else
+#define DHD_IOVAR_LOG_CHECK(dhd_pub, ioc_cmd, ioc_msg) TRUE
+#endif /* DHD_IOVAR_LOG_FILTER_DUMP */
+
+#define DHD_IOVAR_LOG(dhd_pub, ioc_cmd, ioc_msg, fmt) \
+ do { \
+ if (DHD_IOVAR_LOG_CHECK(dhd_pub, ioc_cmd, ioc_msg)) { \
+ DHD_IOVAR_MEM(fmt); \
+ } else { \
+ DHD_TRACE(fmt); \
+ } \
+ } while (0)
+
+/* DHD_PRINT - informational non-error messages which need to be always printed */
+#define DHD_PRINT DHD_ERROR
+
/* Defines msg bits */
#include <dhdioctl.h>
diff --git a/dhd_dbg_ring.c b/dhd_dbg_ring.c
index d4658e0..e741b03 100644
--- a/dhd_dbg_ring.c
+++ b/dhd_dbg_ring.c
@@ -1,7 +1,7 @@
/*
* DHD debug ring API and structures - implementation
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -98,8 +98,11 @@
unsigned long flags = 0;
if (allocd_buf == NULL) {
- /* DEBUG_DUMP RINGs need to be delayed allocation */
- if (id != DEBUG_DUMP_RING1_ID && id != DEBUG_DUMP_RING2_ID) {
+ /* for DEBUG_DUMP and MEM_DUMP, buffer can be NULL
+ * since act as delayed allocation or fake rings
+ */
+ if (id != DEBUG_DUMP_RING1_ID && id != DEBUG_DUMP_RING2_ID &&
+ id != MEM_DUMP_RING_ID) {
return BCME_NOMEM;
}
buf = NULL;
@@ -356,7 +359,7 @@
w_entry = (dhd_dbg_ring_entry_t *)((uint8 *)ring->ring_buf + ring->wp);
/* header */
ret = memcpy_s(w_entry, avail_size, hdr, DBG_RING_ENTRY_SIZE);
- if (unlikely(ret)) {
+ if (ret) {
DHD_ERROR((" memcpy_s() error : %d, destsz: %d, n: %d\n",
ret, avail_size, (int)DBG_RING_ENTRY_SIZE));
return BCME_ERROR;
@@ -366,7 +369,7 @@
avail_size -= DBG_RING_ENTRY_SIZE;
ret = memcpy_s((char *)w_entry + DBG_RING_ENTRY_SIZE,
avail_size, data, w_entry->len);
- if (unlikely(ret)) {
+ if (ret) {
DHD_ERROR((" memcpy_s() error : %d, destsz: %d, n: %d\n",
ret, avail_size, w_entry->len));
return BCME_ERROR;
diff --git a/dhd_dbg_ring.h b/dhd_dbg_ring.h
index 2faa4f2..bff2e62 100644
--- a/dhd_dbg_ring.h
+++ b/dhd_dbg_ring.h
@@ -1,7 +1,7 @@
/*
* DHD debug ring header file - interface
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -113,7 +113,6 @@
#define DBG_RING_ENTRY_SIZE (sizeof(dhd_dbg_ring_entry_t))
#define ENTRY_LENGTH(hdr) ((hdr)->len + DBG_RING_ENTRY_SIZE)
#define PAYLOAD_MAX_LEN 65535
-#define PAYLOAD_ECNTR_MAX_LEN 1648u
#define PAYLOAD_RTT_MAX_LEN 1648u
#define PAYLOAD_BCM_TRACE_MAX_LEN 1648u
#define PENDING_LEN_MAX 0xFFFFFFFF
diff --git a/dhd_debug.c b/dhd_debug.c
index 5db892b..6efe810 100644
--- a/dhd_debug.c
+++ b/dhd_debug.c
@@ -1,7 +1,7 @@
/*
* DHD debugability support
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -50,6 +50,10 @@
#include <dhd_event_log_filter.h>
#endif /* DHD_EVENT_LOG_FILTER */
+#ifdef WL_CFGVENDOR_CUST_ADVLOG
+void wl_cfgvendor_custom_advlog_roam_log(void *plog, uint32 armcycle);
+#endif /* WL_CFGVENDOR_CUST_ADVLOG */
+
#if defined(DHD_EFI) || defined(NDIS)
#if !defined(offsetof)
#define offsetof(TYPE, MEMBER) ((size_t) &((TYPE *)0)->MEMBER)
@@ -1238,7 +1242,7 @@
if (!ecntr_pushed && dhd_log_dump_ecntr_enabled()) {
if (dhd_dbg_send_evtlog_to_ring(plog_hdr, &msg_hdr,
dhdp->ecntr_dbg_ring,
- PAYLOAD_ECNTR_MAX_LEN, logbuf) != BCME_OK) {
+ EVENT_LOG_MAX_BLOCK_SIZE, logbuf) != BCME_OK) {
goto exit;
}
ecntr_pushed = TRUE;
@@ -1666,7 +1670,7 @@
return BCME_NOMEM;
}
- iov_in->hdr.ver = htod16(WL_AML_IOV_VERSION);
+ iov_in->hdr.ver = htod16(WL_AML_IOV_VERSION_1_0);
iov_in->hdr.len = htod16(alloc_len);
iov_in->hdr.subcmd = htod16(WL_AML_SUBCMD_ENABLE);
@@ -2630,36 +2634,50 @@
void pr_roam_btm_rep_v3(prcd_event_log_hdr_t *plog_hdr);
void pr_roam_6g_novlp_rep_v3(prcd_event_log_hdr_t *plog_hdr);
void pr_roam_wtc_btm_rep_v3(prcd_event_log_hdr_t *plog_hdr);
+void pr_roam_btm_query_v3(prcd_event_log_hdr_t *plog_hdr);
+
+void pr_roam_btm_resp_v4(prcd_event_log_hdr_t *plog_hdr);
+void pr_roam_btm_req_v4(prcd_event_log_hdr_t *plog_hdr);
+
+/* Will find an entity which has highest version of that ROAM_LOG id.
+ * ALL structure should support backward compatibility.
+ * { ROAM_LOG_VER, ROAM_LOG_ID, print ROAM_LOG function() },
+ */
static const pr_roam_tbl_t roam_log_print_tbl[] =
{
- {ROAM_LOG_VER_1, ROAM_LOG_SCANSTART, pr_roam_scan_start_v1},
- {ROAM_LOG_VER_1, ROAM_LOG_SCAN_CMPLT, pr_roam_scan_cmpl_v1},
- {ROAM_LOG_VER_1, ROAM_LOG_ROAM_CMPLT, pr_roam_cmpl_v1},
- {ROAM_LOG_VER_1, ROAM_LOG_NBR_REQ, pr_roam_nbr_req_v1},
- {ROAM_LOG_VER_1, ROAM_LOG_NBR_REP, pr_roam_nbr_rep_v1},
- {ROAM_LOG_VER_1, ROAM_LOG_BCN_REQ, pr_roam_bcn_req_v1},
- {ROAM_LOG_VER_1, ROAM_LOG_BCN_REP, pr_roam_bcn_rep_v1},
-
+ /* ROAM Scan Start */
{ROAM_LOG_VER_2, ROAM_LOG_SCANSTART, pr_roam_scan_start_v2},
+ {ROAM_LOG_VER_1, ROAM_LOG_SCANSTART, pr_roam_scan_start_v1},
+ /* ROAM Scan Completed */
{ROAM_LOG_VER_2, ROAM_LOG_SCAN_CMPLT, pr_roam_scan_cmpl_v2},
- {ROAM_LOG_VER_2, ROAM_LOG_ROAM_CMPLT, pr_roam_cmpl_v1},
- {ROAM_LOG_VER_2, ROAM_LOG_NBR_REQ, pr_roam_nbr_req_v1},
+ {ROAM_LOG_VER_1, ROAM_LOG_SCAN_CMPLT, pr_roam_scan_cmpl_v1},
+ /* ROAM Completed */
+ {ROAM_LOG_VER_1, ROAM_LOG_ROAM_CMPLT, pr_roam_cmpl_v1},
+ /* Neighbor Request */
+ {ROAM_LOG_VER_1, ROAM_LOG_NBR_REQ, pr_roam_nbr_req_v1},
+ /* Neighbor Report */
{ROAM_LOG_VER_2, ROAM_LOG_NBR_REP, pr_roam_nbr_rep_v2},
- {ROAM_LOG_VER_2, ROAM_LOG_BCN_REQ, pr_roam_bcn_req_v1},
- {ROAM_LOG_VER_2, ROAM_LOG_BCN_REP, pr_roam_bcn_rep_v2},
- {ROAM_LOG_VER_2, ROAM_LOG_BTM_REP, pr_roam_btm_rep_v2},
-
- {ROAM_LOG_VER_3, ROAM_LOG_SCANSTART, pr_roam_scan_start_v2},
- {ROAM_LOG_VER_3, ROAM_LOG_SCAN_CMPLT, pr_roam_scan_cmpl_v2},
- {ROAM_LOG_VER_3, ROAM_LOG_ROAM_CMPLT, pr_roam_cmpl_v1},
- {ROAM_LOG_VER_3, ROAM_LOG_NBR_REQ, pr_roam_nbr_req_v1},
- {ROAM_LOG_VER_3, ROAM_LOG_NBR_REP, pr_roam_nbr_rep_v2},
+ {ROAM_LOG_VER_1, ROAM_LOG_NBR_REP, pr_roam_nbr_rep_v1},
+ /* Beacon Request */
{ROAM_LOG_VER_3, ROAM_LOG_BCN_REQ, pr_roam_bcn_req_v3},
+ {ROAM_LOG_VER_1, ROAM_LOG_BCN_REQ, pr_roam_bcn_req_v1},
+ /* Beacon Report */
{ROAM_LOG_VER_3, ROAM_LOG_BCN_REP, pr_roam_bcn_rep_v3},
+ {ROAM_LOG_VER_2, ROAM_LOG_BCN_REP, pr_roam_bcn_rep_v2},
+ {ROAM_LOG_VER_1, ROAM_LOG_BCN_REP, pr_roam_bcn_rep_v1},
+ /* BTM Response */
+ {ROAM_LOG_VER_4, ROAM_LOG_BTM_REP, pr_roam_btm_resp_v4},
{ROAM_LOG_VER_3, ROAM_LOG_BTM_REP, pr_roam_btm_rep_v3},
+ {ROAM_LOG_VER_2, ROAM_LOG_BTM_REP, pr_roam_btm_rep_v2},
+ /* SCAN 6G no VLP channels */
{ROAM_LOG_VER_3, ROAM_LOG_6G_NOVLP_REP, pr_roam_6g_novlp_rep_v3},
+ /* BTM WTC Request/Response */
{ROAM_LOG_VER_3, ROAM_LOG_WTC_BTM_REP, pr_roam_wtc_btm_rep_v3},
+ /* BTM Query */
+ {ROAM_LOG_VER_3, ROAM_LOG_BTM_QUERY, pr_roam_btm_query_v3},
+ /* BTM Request */
+ {ROAM_LOG_VER_4, ROAM_LOG_BTM_REQ, pr_roam_btm_req_v4},
{0, PRSV_PERIODIC_ID_MAX, NULL}
};
@@ -2773,12 +2791,6 @@
log->reason == WLC_E_REASON_DISASSOC) {
DHD_ERROR_ROAM((" ROAM_LOG_PRT_ROAM: RCVD reason:%d\n",
log->prt_roam.rcvd_reason));
- } else if (log->reason == WLC_E_REASON_BSSTRANS_REQ) {
- DHD_ERROR_ROAM((" ROAM_LOG_BSS_REQ: mode:%d candidate:%d token:%d "
- "duration disassoc:%d valid:%d term:%d\n",
- log->bss_trans.req_mode, log->bss_trans.nbrlist_size,
- log->bss_trans.token, log->bss_trans.disassoc_dur,
- log->bss_trans.validity_dur, log->bss_trans.bss_term_dur));
} else if (log->reason == WLC_E_REASON_LOW_RSSI) {
DHD_ERROR_ROAM((" ROAM_LOG_LOW_RSSI: threshold:%d\n",
log->low_rssi.rssi_threshold));
@@ -2805,7 +2817,8 @@
"rssi:%d score:%d cu :%d channel:%s TPUT:%dkbps\n",
i, MAC2STRDBG((uint8 *)&log->scan_list[i].addr),
log->scan_list[i].rssi, log->scan_list[i].score,
- log->scan_list[i].cu * 100 / WL_MAX_CHANNEL_USAGE,
+ log->scan_list[i].cu_avail ?
+ (log->scan_list[i].cu * 100 / WL_MAX_CHANNEL_USAGE) : WL_CU_NOT_AVAIL,
wf_chspec_ntoa_ex(log->scan_list[i].chanspec,
chanspec_buf),
log->scan_list[i].estm_tput != ROAM_LOG_INVALID_TPUT?
@@ -2911,6 +2924,14 @@
}
void
+pr_roam_btm_query_v3(prcd_event_log_hdr_t *plog_hdr)
+{
+ roam_log_btm_query_v3_t *log = (roam_log_btm_query_v3_t *)plog_hdr->log_ptr;
+ DHD_ERROR_ROAM(("ROAM_LOG_BTM_QUERY: time:%d version:%d token:%d reason:%d\n",
+ plog_hdr->armcycle, log->hdr.version, log->token, log->reason));
+}
+
+void
pr_roam_6g_novlp_rep_v3(prcd_event_log_hdr_t *plog_hdr)
{
roam_log_6g_novlp_v3_t *log = (roam_log_6g_novlp_v3_t *)plog_hdr->log_ptr;
@@ -2957,6 +2978,37 @@
log->wtcresp.rsn_code, log->wtcresp.status));
}
}
+/* ROAM logging BTM Request */
+void
+pr_roam_btm_req_v4(prcd_event_log_hdr_t *plog_hdr)
+{
+ roam_log_btm_req_v4_t *log = (roam_log_btm_req_v4_t *)plog_hdr->log_ptr;
+ int i;
+ DHD_ERROR_ROAM(("ROAM_LOG_BTM_REQ: time:%d version:%d req_mode:%d "
+ "token:%d candi:%d duration disassoc:%d valid:%d term:%d\n",
+ plog_hdr->armcycle, log->hdr.version,
+ log->req_mode, log->token, log->nbrlist_size,
+ log->disassoc_dur, log->validity_dur, log->bss_term_dur));
+ if (log->nbrlist_size) {
+ int max_idx = MIN(log->nbrlist_size, ROAM_NBR_RPT_LIST_SIZE);
+ for (i = 0; i < max_idx; i++) {
+ DHD_ERROR_ROAM((" ROAM_LOG_NBR: [%d]" MACDBG " pref:0x%x\n",
+ i, MAC2STRDBG((uint8 *)&log->nbr_list[i].bssid),
+ log->nbr_list[i].preference));
+ }
+ }
+}
+/* ROAM logging BTM Response */
+void
+pr_roam_btm_resp_v4(prcd_event_log_hdr_t *plog_hdr)
+{
+ roam_log_btm_resp_v4_t *log = (roam_log_btm_resp_v4_t *)plog_hdr->log_ptr;
+ DHD_ERROR_ROAM(("ROAM_LOG_BTM_REP: time:%d version:%d req_mode:%d "
+ "status:%d token:%d term_delay:%d ret:%d target:" MACDBG "\n",
+ plog_hdr->armcycle, log->hdr.version,
+ log->req_mode, log->status, log->token, log->term_delay, log->result,
+ MAC2STRDBG((uint8 *)&log->target_addr)));
+}
void
print_roam_enhanced_log(prcd_event_log_hdr_t *plog_hdr)
@@ -2969,8 +3021,12 @@
char pr_buf[EL_LOG_STR_LEN] = { 0 };
const pr_roam_tbl_t *cur_elem = &roam_log_print_tbl[0];
+#ifdef WL_CFGVENDOR_CUST_ADVLOG
+ wl_cfgvendor_custom_advlog_roam_log(plog_hdr->log_ptr, plog_hdr->armcycle);
+#endif /* WL_CFGVENDOR_CUST_ADVLOG */
+
while (cur_elem && cur_elem->pr_func) {
- if (hdr->version == cur_elem->version &&
+ if (hdr->version >= cur_elem->version &&
hdr->id == cur_elem->id) {
cur_elem->pr_func(plog_hdr);
return;
@@ -3087,7 +3143,7 @@
}
#endif /* DHD_DEBUGABILITY_LOG_DUMP_RING */
-#ifdef DHD_DEBUGABILITY_DEBUG_DUMP
+#if defined(DHD_DEBUGABILITY_DEBUG_DUMP) || defined(DHD_HAL_RING_DUMP)
/*
* delayed memory allocation. memory will be allocated when debug_dump is invoked
* To prepare the ringbuffer in legacy HAL, we should initialize ring at this time
@@ -3107,7 +3163,16 @@
DHD_ERROR(("%s: Failed to init debug ring2\n", __func__));
goto error;
}
-#endif /* DHD_DEBUGABILITY_DEBUG_DUMP */
+#endif /* defined(DHD_DEBUGABILITY_DEBUG_DUMP) || defined(DHD_HAL_RING_DUMP) */
+
+#if defined(DHD_HAL_RING_DUMP_MEMDUMP)
+ ret = dhd_dbg_ring_init(dhdp, &dbg->dbg_rings[MEM_DUMP_RING_ID], MEM_DUMP_RING_ID,
+ (uint8 *)MEM_DUMP_RING_NAME, MEM_DUMP_RING_SIZE, NULL, FALSE);
+ if (ret) {
+ DHD_ERROR(("%s: Failed to init mem dump ring\n", __func__));
+ goto error;
+ }
+#endif /* DHD_HAL_RING_DUMP_MEMDUMP */
#ifdef BTLOG
buf = VMALLOCZ(dhdp->osh, BT_LOG_RING_SIZE);
@@ -3131,12 +3196,14 @@
if (!pktlog_ring) {
DHD_ERROR(("%s: pktlog_ring is NULL. return.\n", __FUNCTION__));
+ ret = BCME_NOMEM;
goto error;
}
buf = pktlog_ring->ring_info_mem;
if (!buf) {
DHD_ERROR(("%s: ring_info_mem is NULL. return.\n", __FUNCTION__));
+ ret = BCME_NOMEM;
goto error;
}
@@ -3217,12 +3284,6 @@
ring = &dbg->dbg_rings[ring_id];
dhd_dbg_ring_deinit(dhdp, ring);
if (ring->ring_buf) {
-#ifdef DHD_DEBUGABILITY_DEBUG_DUMP
- if (ring_id == DEBUG_DUMP_RING1_ID ||
- ring_id == DEBUG_DUMP_RING2_ID) {
- VMFREE(dhdp->osh, ring->ring_buf, ring->ring_size);
- }
-#endif /* DHD_DEBUGABILITY_DEBUG_DUMP */
#ifdef DHD_PKT_LOGGING_DBGRING
if (ring_id != PACKET_LOG_RING_ID)
#endif /* DHD_PKT_LOGGING_DBGRING */
@@ -3235,7 +3296,7 @@
}
}
- VMFREE(dhdp->osh, dhdp->dbg, sizeof(dhd_dbg_t));
+ VMFREE(dhdp->osh, dbg, sizeof(dhd_dbg_t));
#endif /* DHD_DEBUGABILITY_LOG_DUMP_RING || BTLOG ||
* DHD_DEBUGABILITY_EVENT_RING || DHD_PKT_LOGGING_DBGRING ||
* (DEBUGABILITY && CUSTOMER_HW6)
@@ -3329,14 +3390,21 @@
#ifdef EWP_RTT_LOGGING
sec_len[LOG_DUMP_SECTION_RTT] = dhd_get_rtt_len(NULL, dhdp);
#endif /* EWP_RTT_LOGGING */
+#ifdef DHD_MAP_PKTID_LOGGING
+ sec_len[LOG_DUMP_SECTION_PKTID_MAP_LOG] =
+ dhd_get_pktid_map_logging_len(NULL, dhdp, TRUE);
+ sec_len[LOG_DUMP_SECTION_PKTID_UNMAP_LOG] =
+ dhd_get_pktid_map_logging_len(NULL, dhdp, FALSE);
+#endif /* DHD_MAP_PKTID_LOGGING */
DHD_ERROR(("%s: TS:%d ECNTRS:%d DHD_DUMP:%d ETRAP:%d"
- " HCK:%d CKI:%d FLOW:%d STATUS:%d RTT:%d\n",
+ " HCK:%d CKI:%d FLOW:%d STATUS:%d RTT:%d PKTID_MAP:%d PKTID_UNMAP:%d\n",
__func__, sec_len[LOG_DUMP_SECTION_TIMESTAMP], sec_len[LOG_DUMP_SECTION_ECNTRS],
sec_len[LOG_DUMP_SECTION_DHD_DUMP], sec_len[LOG_DUMP_SECTION_EXT_TRAP],
sec_len[LOG_DUMP_SECTION_HEALTH_CHK], sec_len[LOG_DUMP_SECTION_COOKIE],
sec_len[LOG_DUMP_SECTION_RING], sec_len[LOG_DUMP_SECTION_STATUS],
- sec_len[LOG_DUMP_SECTION_RTT]));
+ sec_len[LOG_DUMP_SECTION_RTT], sec_len[LOG_DUMP_SECTION_PKTID_MAP_LOG],
+ sec_len[LOG_DUMP_SECTION_PKTID_UNMAP_LOG]));
return;
}
@@ -3384,6 +3452,9 @@
return ret;
}
+#ifdef DHD_MAP_PKTID_LOGGING
+ dhd_pktid_logging_dump(dhdp);
+#endif /* DHD_MAP_PKTID_LOGGING */
dhd_debug_dump_get_section_len(dhdp, sec_len);
ring_num = dhd_debug_dump_get_ring_num(LOG_DUMP_SECTION_TIMESTAMP);
@@ -3410,6 +3481,18 @@
DHD_ERROR(("Error section: RTT_LOG\n"));
}
#endif /* EWP_RTT_LOGGING */
+#ifdef DHD_MAP_PKTID_LOGGING
+ ring_num = dhd_debug_dump_get_ring_num(LOG_DUMP_SECTION_PKTID_MAP_LOG);
+ if (dhd_print_pktid_map_log_data(NULL, dhdp, NULL, NULL,
+ sec_len[LOG_DUMP_SECTION_PKTID_MAP_LOG], &ring_num, TRUE)) {
+ DHD_ERROR(("Error section: PKTID_MAP_LOG\n"));
+ }
+ ring_num = dhd_debug_dump_get_ring_num(LOG_DUMP_SECTION_PKTID_UNMAP_LOG);
+ if (dhd_print_pktid_map_log_data(NULL, dhdp, NULL, NULL,
+ sec_len[LOG_DUMP_SECTION_PKTID_UNMAP_LOG], &ring_num, FALSE)) {
+ DHD_ERROR(("Error section: PKTID_UNMAP_LOG\n"));
+ }
+#endif /* DHD_MAP_PKTID_LOGGING */
ring_num = dhd_debug_dump_get_ring_num(LOG_DUMP_SECTION_DHD_DUMP);
if (dhd_print_dump_data(NULL, dhdp, NULL, NULL,
sec_len[LOG_DUMP_SECTION_DHD_DUMP], &ring_num)) {
diff --git a/dhd_debug.h b/dhd_debug.h
index 9c03bf1..670e009 100644
--- a/dhd_debug.h
+++ b/dhd_debug.h
@@ -1,7 +1,7 @@
/*
* DHD debugability header file
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -86,6 +86,9 @@
#define DEBUG_DUMP_RING2_NAME "debug_dump2_"
#define DEBUG_DUMP_RING2_SIZE (2 * 1024 * 1024)
+#define MEM_DUMP_RING_NAME "mem_dump"
+#define MEM_DUMP_RING_SIZE (3 * 1024 * 1024)
+
#define DHD_DEBUG_DUMP_NETLINK_MAX (1024 * 8)
#define DHD_DEBUG_DUMP_MAX_SYNC_CNT 5u
#endif /* DHD_DEBUGABILITY_LOG_DUMP_RING */
@@ -845,6 +848,7 @@
#ifdef DHD_PKT_LOGGING_DBGRING
int dhd_dbg_update_to_ring(dhd_pub_t *dhdp, void *ring, uint32 w_len);
int dhd_dbg_pull_from_pktlog(dhd_pub_t *dhdp, int ring_id, void *data, uint32 buf_len);
+void dhd_os_dbg_urgent_pullreq(void *os_priv, int ring_id);
#endif /* DHD_PKT_LOGGING_DBGRING */
#ifdef DHD_DEBUGABILITY_DEBUG_DUMP
int dhd_debug_dump_ring_push(dhd_pub_t *dhdp, int ring_id, uint32 len, void *data);
diff --git a/dhd_debug_linux.c b/dhd_debug_linux.c
index 7e77bd2..69026b7 100644
--- a/dhd_debug_linux.c
+++ b/dhd_debug_linux.c
@@ -1,7 +1,7 @@
/*
* DHD debugability Linux os layer
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -257,8 +257,9 @@
if (!VALID_RING(ring_id))
return BCME_UNSUPPORTED;
- DHD_LOG_MEM(("%s , log_level : %d, time_intval : %d, threshod %d Bytes\n",
- __FUNCTION__, log_level, time_intval, threshold));
+ DHD_ERROR(("%s , ring_id : %d log_level : %d, "
+ "time_intval : %d, threshod %d Bytes\n",
+ __FUNCTION__, ring_id, log_level, time_intval, threshold));
/* change the configuration */
ret = dhd_dbg_set_configuration(dhdp, ring_id, log_level, flags, threshold);
diff --git a/dhd_event_log_filter.c b/dhd_event_log_filter.c
index 7194d6a..b5417ae 100644
--- a/dhd_event_log_filter.c
+++ b/dhd_event_log_filter.c
@@ -1,7 +1,7 @@
/*
* Wifi dongle status Filter and Report
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/dhd_event_log_filter.h b/dhd_event_log_filter.h
index 9e9d380..37612db 100644
--- a/dhd_event_log_filter.h
+++ b/dhd_event_log_filter.h
@@ -1,7 +1,7 @@
/*
* Wifi dongle status Filter and Report
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/dhd_flowring.c b/dhd_flowring.c
index 1132a84..9be5e67 100644
--- a/dhd_flowring.c
+++ b/dhd_flowring.c
@@ -4,7 +4,7 @@
* Flow rings are transmit traffic (=propagating towards antenna) related entities
*
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -1152,8 +1152,8 @@
dhd_del_flowid(dhdp, ifindex, flowid);
dhd_flowid_map_free(dhdp, ifindex, flowid);
- DHD_FLOWID_UNLOCK(dhdp->flowid_lock, flags);
MFREE(dhdp->osh, cur, sizeof(flow_hash_info_t));
+ DHD_FLOWID_UNLOCK(dhdp->flowid_lock, flags);
return;
}
diff --git a/dhd_flowring.h b/dhd_flowring.h
index 47af2c8..8f6222f 100644
--- a/dhd_flowring.h
+++ b/dhd_flowring.h
@@ -6,7 +6,7 @@
* Provides type definitions and function prototypes used to create, delete and manage flow rings at
* high level.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/dhd_ip.c b/dhd_ip.c
index 815b6e4..f10cff8 100644
--- a/dhd_ip.c
+++ b/dhd_ip.c
@@ -1,7 +1,7 @@
/*
* IP Packet Parser Module.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/dhd_ip.h b/dhd_ip.h
index a95a389..bc36039 100644
--- a/dhd_ip.h
+++ b/dhd_ip.h
@@ -3,7 +3,7 @@
*
* Provides type definitions and function prototypes used to parse ip packet.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/dhd_linux.c b/dhd_linux.c
index fa660d8..eee3301 100644
--- a/dhd_linux.c
+++ b/dhd_linux.c
@@ -2,7 +2,7 @@
* Broadcom Dongle Host Driver (DHD), Linux-specific network interface.
* Basically selected code segments from usb-cdc.c and usb-rndis.c
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -404,27 +404,22 @@
.priority = 1,
};
-#ifdef BCMPCIE
-static int is_reboot = 0;
-#endif /* BCMPCIE */
-
dhd_pub_t *g_dhd_pub = NULL;
#if defined(BT_OVER_SDIO)
#include "dhd_bt_interface.h"
#endif /* defined (BT_OVER_SDIO) */
-#ifdef CONFIG_ARCH_EXYNOS
-#if IS_ENABLED(CONFIG_EXYNOS_S2MPU)
+#if defined(DHD_ENABLE_S2MPU)
#include <soc/samsung/exynos-s2mpu.h>
-#endif /* CONFIG_EXYNOS_S2MPU */
-#endif /* CONFIG_ARCH_EXYNOS */
+#endif /* DHD_ENABLE_S2MPU */
#ifdef WL_STATIC_IF
bool dhd_is_static_ndev(dhd_pub_t *dhdp, struct net_device *ndev);
#endif /* WL_STATIC_IF */
atomic_t exit_in_progress = ATOMIC_INIT(0);
+atomic_t reboot_in_progress = ATOMIC_INIT(-1);
static void dhd_process_daemon_msg(struct sk_buff *skb);
static void dhd_destroy_to_notifier_skt(void);
@@ -562,7 +557,12 @@
#ifdef DHD_PCIE_RUNTIMEPM
uint dhd_runtimepm_ms = CUSTOM_DHD_RUNTIME_MS;
-#endif /* DHD_PCIE_RUNTIMEPMT */
+
+#ifdef RPM_FAST_TRIGGER
+uint dhd_fast_runtimepm_ms = RPM_FAST_TRIGGER_THR;
+#endif /* RPM_FAST_TRIGGER */
+
+#endif /* DHD_PCIE_RUNTIMEPM */
#if defined(DHD_DEBUG)
/* Console poll interval */
uint dhd_console_ms = CUSTOM_DHD_CONSOLE_MS;
@@ -804,6 +804,19 @@
extern void dhd_dbgfs_remove(void);
#endif
+#ifdef BCMPCIE
+/* Tx/Rx/Ctrl cpl/post bounds */
+extern uint dhd_tx_cpl_bound;
+extern uint dhd_rx_cpl_post_bound;
+extern uint dhd_tx_post_bound;
+extern uint dhd_ctrl_cpl_post_bound;
+
+module_param(dhd_tx_cpl_bound, uint, 0);
+module_param(dhd_rx_cpl_post_bound, uint, 0);
+module_param(dhd_tx_post_bound, uint, 0);
+module_param(dhd_ctrl_cpl_post_bound, uint, 0);
+#endif /* BCMPCIE */
+
/* Enable TX status metadta report: 0=disable 1=enable 2=debug */
static uint pcie_txs_metadata_enable = 0;
module_param(pcie_txs_metadata_enable, int, 0);
@@ -923,6 +936,7 @@
module_param(dhd_tcm_test_enable, uint, 0644);
tcm_test_status_t dhd_tcm_test_status = TCM_TEST_NOT_RUN;
+tcm_test_mode_t dhd_tcm_test_mode = TCM_TEST_MODE_ALWAYS;
extern char dhd_version[];
extern char fw_version[];
@@ -973,48 +987,263 @@
void dhd_smmu_fault_handler(uint32 axid, ulong fault_addr);
#endif /* DHD_MAP_LOGGING */
-#ifdef CONFIG_ARCH_EXYNOS
-#if IS_ENABLED(CONFIG_EXYNOS_S2MPU)
+#if defined(DHD_ENABLE_S2MPU)
int s2mpufd_notifier_callback(struct s2mpufd_notifier_block *block,
struct s2mpufd_notifier_info *info);
static void dhd_module_s2mpu_register(struct device *dev);
-#endif /* CONFIG_EXYNOS_S2MPU */
-#endif /* CONFIG_ARCH_EXYNOS */
+#endif /* DHD_ENABLE_S2MPU */
+#ifdef DHD_REGISTER_SMMU_FAULT_HANDLER
+extern int pcie_sysmmu_add_fault_handler(struct notifier_block *pcie_sysmmu_nb);
+static int sysmmu_notifier_callback(struct notifier_block *nb, unsigned long addr,
+ void *flag);
+static struct notifier_block dhd_pcie_sysmmu_nb = {
+ .notifier_call = sysmmu_notifier_callback
+};
+#endif /* DHD_REGISTER_SMMU_FAULT_HANDLER */
static int dhd_suspend_resume_helper(struct dhd_info *dhd, int val, int force);
#if defined(DHD_FILE_DUMP_EVENT) && defined(DHD_FW_COREDUMP)
static void dhd_dump_proc(struct work_struct *work_data);
#endif /* DHD_FILE_DUMP_EVENT && DHD_FW_COREDUMP */
+#ifdef CUSTOM_EVENT_PM_WAKE
+void
+dhd_set_excess_pm_awake(dhd_pub_t *dhd, bool suspend)
+{
+ int ret = 0;
+ uint32 iovar_val = 0; /* Disable the excess PM notify */
+ char *iovar_name;
+
+#ifdef CUSTOM_EVENT_PM_PERCENT
+ iovar_name = "excess_pm_period";
+#else
+ iovar_name = "const_awake_thresh";
+ iovar_val = CUSTOM_EVENT_PM_WAKE;
+#endif /* CUSTOM_EVENT_PM_PERCENT */
+
+ if (suspend) {
+ iovar_val = CUSTOM_EVENT_PM_WAKE * 4;
+ }
+
+ ret = dhd_iovar(dhd, 0, iovar_name, (char *)&iovar_val,
+ sizeof(iovar_val), NULL, 0, TRUE);
+ if (ret < 0) {
+ DHD_ERROR(("%s set %s failed %d\n", __FUNCTION__, iovar_name, ret));
+ }
+ return;
+}
+void
+dhd_init_excess_pm_awake(dhd_pub_t *dhd)
+{
+ int ret = 0;
+ uint32 pm_awake_thresh = CUSTOM_EVENT_PM_WAKE;
+#ifdef CUSTOM_EVENT_PM_PERCENT
+ uint32 pm_awake_percent = CUSTOM_EVENT_PM_PERCENT;
+
+ ret = dhd_iovar(dhd, 0, "excess_pm_percent", (char *)&pm_awake_percent,
+ sizeof(pm_awake_percent), NULL, 0, TRUE);
+ if (ret < 0) {
+ DHD_ERROR(("%s set excess_pm_percent failed %d\n", __FUNCTION__, ret));
+ }
+ pm_awake_thresh = 0; /* Disable the excess PM notify */
+#endif /* CUSTOM_EVENT_PM_PERCENT */
+ ret = dhd_iovar(dhd, 0, "const_awake_thresh", (char *)&pm_awake_thresh,
+ sizeof(pm_awake_thresh), NULL, 0, TRUE);
+ if (ret < 0) {
+ DHD_ERROR(("%s set const_awake_thresh failed %d\n", __FUNCTION__, ret));
+ }
+
+ return;
+}
+#endif /* CUSTOM_EVENT_PM_WAKE */
+
#if defined(CONFIG_PM_SLEEP)
+#ifdef WL_TWT
+#define TWT_NOMINAL_RESUME (5U * 1024U) /* 5ms */
+
+int dhd_send_twt_info_suspend(dhd_pub_t *dhdp, bool suspend)
+{
+ int ret = BCME_OK;
+ wl_twt_info_t ti;
+ u8 buf[WLC_IOCTL_SMLEN] = {0};
+
+ uint8 *pbuf = buf;
+ uint16 param_len = sizeof(buf);
+
+ bzero(&ti, sizeof(ti));
+ ti.version = WL_TWT_INFO_VER;
+ ti.length = sizeof(ti.version) + sizeof(ti.length);
+
+ if (!dhdp || dhdp->up == 0) {
+ return ret;
+ }
+
+ /* if it's not associated, skip send info */
+ if (!dhd_is_associated(dhdp, 0, NULL)) {
+ return ret;
+ }
+
+ /* Default values, Overide Below */
+ ti.infodesc.flow_id = 0xFF;
+ ti.desc.next_twt_h = 0xFFFFFFFF;
+ ti.desc.next_twt_l = 0xFFFFFFFF;
+
+ /* Set allTWT info suspend, ConfigID = 0 */
+ ti.configID = 0;
+
+ /* resume TWT session in resume */
+ if (suspend == FALSE) {
+ /* Resume TWT session */
+ ti.infodesc.next_twt_h = htod32((u32)((u64)TWT_NOMINAL_RESUME >> 32));
+ ti.infodesc.next_twt_l = htod32((u32)TWT_NOMINAL_RESUME);
+ ti.infodesc.flow_flags |= WL_TWT_INFO_FLAG_RESUME;
+ }
+
+ /* Packing parameters */
+ ret = bcm_pack_xtlv_entry(&pbuf, ¶m_len, WL_TWT_CMD_INFO,
+ sizeof(ti), (uint8 *)&ti, BCM_XTLV_OPTION_ALIGN32);
+ if (ret != BCME_OK) {
+ DHD_ERROR(("%s : parameter packing error \n", __FUNCTION__));
+ return ret;
+ }
+
+ ret = dhd_iovar(dhdp, 0, "twt", buf, sizeof(buf) - param_len, NULL, 0, TRUE);
+ if (ret) {
+ DHD_ERROR(("%s : TWT info failed ret : %d\n", __FUNCTION__, ret));
+ }
+ return ret;
+
+}
+int dhd_config_twt_event_mask_in_suspend(dhd_pub_t *dhdp, bool suspend)
+{
+ int ret = BCME_OK;
+ u8 buf[WLC_IOCTL_SMLEN] = {0};
+ eventmsgs_ext_t *eventmask_msg = NULL;
+
+ int msglen = WL_EVENTING_MASK_EXT_LEN + EVENTMSGS_EXT_STRUCT_SIZE;
+
+ if (!dhdp || dhdp->up == 0) {
+ return ret;
+ }
+
+ /* if it's not associated in suspend, skip teardown */
+ if (suspend && !dhd_is_associated(dhdp, 0, NULL)) {
+ return ret;
+ }
+
+ /* TWT_E_TWT event mask configuration */
+ eventmask_msg = (eventmsgs_ext_t *)MALLOC(dhdp->osh, msglen);
+ if (eventmask_msg == NULL) {
+ DHD_ERROR(("%s : failed to allocate for event_msg_ext\n", __FUNCTION__));
+ return ret;
+ }
+
+ bzero(eventmask_msg, msglen);
+ eventmask_msg->ver = EVENTMSGS_VER;
+ eventmask_msg->len = ROUNDUP(WLC_E_LAST, NBBY)/NBBY;
+
+ /* Read event_msgs_ext mask */
+ ret = dhd_iovar(dhdp, 0, "event_msgs_ext", (char *)eventmask_msg, msglen, buf,
+ WLC_IOCTL_SMLEN, FALSE);
+ /* event_msgs_ext must be supported */
+ if (ret != BCME_OK) {
+ DHD_ERROR(("%s read event mask ext failed %d\n", __FUNCTION__, ret));
+ goto fail;
+ }
+
+ bcopy(buf, eventmask_msg, msglen);
+
+ /* suspend */
+ if (suspend) {
+ /* Clear TWT EVENT bit mask */
+ clrbit(eventmask_msg->mask, WLC_E_TWT);
+ } else {
+ /* resume */
+ /* Set TWT EVENT bit mask */
+ setbit(eventmask_msg->mask, WLC_E_TWT);
+ }
+
+ /* Write updated Event mask */
+ eventmask_msg->ver = EVENTMSGS_VER;
+ eventmask_msg->command = EVENTMSGS_SET_MASK;
+ eventmask_msg->len = WL_EVENTING_MASK_EXT_LEN;
+
+ ret = dhd_iovar(dhdp, 0, "event_msgs_ext", (char *)eventmask_msg, msglen,
+ NULL, 0, TRUE);
+ if (ret < 0) {
+ DHD_ERROR(("%s write event mask ext failed %d\n", __FUNCTION__, ret));
+ goto fail;
+ }
+
+fail:
+ if (eventmask_msg) {
+ MFREE(dhdp->osh, eventmask_msg, msglen);
+ }
+
+ return ret;
+
+}
+#endif /* WL_TWT */
+
static int dhd_pm_callback(struct notifier_block *nfb, unsigned long action, void *ignored)
{
int ret = NOTIFY_DONE;
bool suspend = FALSE;
dhd_info_t *dhdinfo;
+ unsigned long flags = 0;
BCM_REFERENCE(dhdinfo);
BCM_REFERENCE(suspend);
+ GCC_DIAGNOSTIC_PUSH_SUPPRESS_CAST();
+ dhdinfo = container_of(nfb, struct dhd_info, pm_notifier);
+ GCC_DIAGNOSTIC_POP();
+
+ if (!dhdinfo->pub.up) {
+ return ret;
+ }
+
+ DHD_GENERAL_LOCK(&dhdinfo->pub, flags);
+ DHD_BUS_BUSY_SET_IN_PM_CALLBACK(&dhdinfo->pub);
+ DHD_GENERAL_UNLOCK(&dhdinfo->pub, flags);
+ DHD_ERROR(("%s action: %lu\n", __FUNCTION__, action));
+
switch (action) {
case PM_HIBERNATION_PREPARE:
case PM_SUSPEND_PREPARE:
suspend = TRUE;
+#ifdef DHD_PCIE_RUNTIMEPM
+ DHD_DISABLE_RUNTIME_PM(&dhdinfo->pub);
+#endif /* DHD_PCIE_RUNTIMEPM */
+#ifdef WL_TWT
+ dhd_config_twt_event_mask_in_suspend(&dhdinfo->pub, TRUE);
+ dhd_send_twt_info_suspend(&dhdinfo->pub, TRUE);
+#endif /* WL_TWT */
break;
case PM_POST_HIBERNATION:
case PM_POST_SUSPEND:
suspend = FALSE;
+#ifdef DHD_PCIE_RUNTIMEPM
+ DHD_ENABLE_RUNTIME_PM(&dhdinfo->pub);
+#endif /* DHD_PCIE_RUNTIMEPM */
break;
}
-#if (defined(SUPPORT_P2P_GO_PS) && defined(PROP_TXSTATUS)) || defined(DHD_USE_PM_SLEEP)
- dhdinfo = container_of(nfb, struct dhd_info, pm_notifier);
-#endif /* (SUPPORT_P2P_GO_PS && PROP_TXSTATUS) || DHD_USE_PM_SLEEP */
#if defined(DHD_USE_PM_SLEEP)
- dhd_suspend_resume_helper(dhdinfo, suspend, 0);
+ /* The resume setting is handled in wl_android_set_suspendmode(). */
+ if (suspend == TRUE) {
+ dhd_suspend_resume_helper(dhdinfo, suspend, 0);
+ }
#endif /* DHD_USE_PM_SLEEP */
+#ifdef DHD_CUSTOM_CONFIG_RTS_IN_SUSPEND
+ dhd_config_rts_in_suspend(&dhdinfo->pub, suspend);
+#endif /* DHD_CUSTOM_CONFIG_RTS_IN_SUSPEND */
+#ifdef CUSTOM_EVENT_PM_WAKE
+ dhd_set_excess_pm_awake(&dhdinfo->pub, suspend);
+#endif /* CUSTOM_EVENT_PM_WAKE */
+
#if defined(SUPPORT_P2P_GO_PS) && defined(PROP_TXSTATUS)
if (suspend) {
DHD_OS_WAKE_LOCK_WAIVE(&dhdinfo->pub);
@@ -1031,6 +1260,9 @@
smp_mb();
#endif
+ DHD_GENERAL_LOCK(&dhdinfo->pub, flags);
+ DHD_BUS_BUSY_CLEAR_IN_PM_CALLBACK(&dhdinfo->pub);
+ DHD_GENERAL_UNLOCK(&dhdinfo->pub, flags);
return ret;
}
@@ -2031,57 +2263,6 @@
}
#endif /* PKT_FILTER_SUPPORT */
-#ifdef CUSTOM_EVENT_PM_WAKE
-void
-dhd_set_excess_pm_awake(dhd_pub_t *dhd, bool suspend)
-{
- int ret = 0;
- uint32 iovar_val = 0; /* Disable the excess PM notify */
- char *iovar_name;
-
-#ifdef CUSTOM_EVENT_PM_PERCENT
- iovar_name = "excess_pm_period";
-#else
- iovar_name = "const_awake_thresh";
- iovar_val = CUSTOM_EVENT_PM_WAKE;
-#endif /* CUSTOM_EVENT_PM_PERCENT */
-
- if (suspend) {
- iovar_val = CUSTOM_EVENT_PM_WAKE * 4;
- }
-
- ret = dhd_iovar(dhd, 0, iovar_name, (char *)&iovar_val,
- sizeof(iovar_val), NULL, 0, TRUE);
- if (ret < 0) {
- DHD_ERROR(("%s set %s failed %d\n", __FUNCTION__, iovar_name, ret));
- }
- return;
-}
-void
-dhd_init_excess_pm_awake(dhd_pub_t *dhd)
-{
- int ret = 0;
- uint32 pm_awake_thresh = CUSTOM_EVENT_PM_WAKE;
-#ifdef CUSTOM_EVENT_PM_PERCENT
- uint32 pm_awake_percent = CUSTOM_EVENT_PM_PERCENT;
-
- ret = dhd_iovar(dhd, 0, "excess_pm_percent", (char *)&pm_awake_percent,
- sizeof(pm_awake_percent), NULL, 0, TRUE);
- if (ret < 0) {
- DHD_ERROR(("%s set excess_pm_percent failed %d\n", __FUNCTION__, ret));
- }
- pm_awake_thresh = 0; /* Disable the excess PM notify */
-#endif /* CUSTOM_EVENT_PM_PERCENT */
- ret = dhd_iovar(dhd, 0, "const_awake_thresh", (char *)&pm_awake_thresh,
- sizeof(pm_awake_thresh), NULL, 0, TRUE);
- if (ret < 0) {
- DHD_ERROR(("%s set const_awake_thresh failed %d\n", __FUNCTION__, ret));
- }
-
- return;
-}
-#endif /* CUSTOM_EVENT_PM_WAKE */
-
static int dhd_set_suspend(int value, dhd_pub_t *dhd)
{
/* wl_pkt_filter_enable_t enable_parm; */
@@ -2148,17 +2329,29 @@
}
#endif /* ARP_OFFLOAD_SUPPORT */
#ifdef PASS_ALL_MCAST_PKTS
- allmulti = 0;
for (i = 0; i < DHD_MAX_IFS; i++) {
- if (dhdinfo->iflist[i] && dhdinfo->iflist[i]->net) {
- ret = dhd_iovar(dhd, i, "allmulti",
- (char *)&allmulti,
- sizeof(allmulti),
- NULL, 0, TRUE);
- if (ret < 0) {
- DHD_ERROR(("%s allmulti failed %d\n",
- __FUNCTION__, ret));
- }
+ struct net_device *ndev = NULL;
+ if (!dhdinfo->iflist[i] || !dhdinfo->iflist[i]->net) {
+ continue;
+ }
+
+ ndev = dhdinfo->iflist[i]->net;
+ if (ndev->ieee80211_ptr->iftype == NL80211_IFTYPE_P2P_GO ||
+ ndev->ieee80211_ptr->iftype == NL80211_IFTYPE_AP) {
+ allmulti = 1;
+ DHD_LOG_MEM(("%s: IF[%s] is AP/GO, set allmulti.\n",
+ __FUNCTION__, ndev->name));
+ } else {
+ allmulti = 0;
+ }
+
+ ret = dhd_iovar(dhd, i, "allmulti",
+ (char *)&allmulti,
+ sizeof(allmulti),
+ NULL, 0, TRUE);
+ if (ret < 0) {
+ DHD_ERROR(("%s allmulti failed %d\n",
+ __FUNCTION__, ret));
}
}
#endif /* PASS_ALL_MCAST_PKTS */
@@ -3937,6 +4130,11 @@
}
} while (ret > 0);
}
+ /* Check terminated in case of dongle_reset */
+ if (tsk->terminated) {
+ DHD_ERROR(("%s: task terminated\n", __FUNCTION__));
+ goto exit;
+ }
if (tsk->flush_ind) {
DHD_ERROR(("%s: flushed\n", __FUNCTION__));
dhdp->logtrace_thr_ts.flush_time = OSL_LOCALTIME_NS();
@@ -4082,7 +4280,8 @@
dhd_event_logtrace_enqueue(dhd_pub_t *dhdp, int ifidx, void *pktbuf)
{
dhd_info_t *dhd = (dhd_info_t *)dhdp->info;
-
+ BCM_REFERENCE(dhd);
+#ifndef BCMDBUS
#ifdef PCIE_FULL_DONGLE
/* Add ifidx in the PKTTAG */
DHD_PKTTAG_SET_IFID((dhd_pkttag_fr_t *)PKTTAG(pktbuf), ifidx);
@@ -4090,6 +4289,13 @@
skb_queue_tail(&dhd->evt_trace_queue, pktbuf);
dhd_schedule_logtrace(dhd);
+#else /* !BCMDBUS */
+#ifdef DHD_USE_STATIC_CTRLBUF
+ PKTFREE_STATIC(dhdp->osh, pktbuf, FALSE);
+#else
+ PKTFREE(dhdp->osh, pktbuf, FALSE);
+#endif /* DHD_USE_STATIC_CTRLBUF */
+#endif /* BCMDBUS */
}
void
@@ -4556,12 +4762,22 @@
/* Reschedule the watchdog */
if (dhd->rpm_timer_valid) {
- mod_timer(&dhd->rpm_timer,
- jiffies +
- msecs_to_jiffies(dhd_runtimepm_ms) -
- min(msecs_to_jiffies(dhd_runtimepm_ms),
- time_lapse));
+#ifdef RPM_FAST_TRIGGER
+ /* reset rpm_fast_trigger flags */
+ if (dhd->pub.rpm_fast_trigger) {
+ mod_timer(&dhd->rpm_timer, jiffies +
+ msecs_to_jiffies(dhd_fast_runtimepm_ms));
+ } else
+#endif /* RPM_FAST_TRIGGER */
+ {
+ mod_timer(&dhd->rpm_timer,
+ jiffies +
+ msecs_to_jiffies(dhd_runtimepm_ms) -
+ min(msecs_to_jiffies(dhd_runtimepm_ms),
+ time_lapse));
+ }
}
+
DHD_GENERAL_UNLOCK(&dhd->pub, flags);
}
} else {
@@ -5568,7 +5784,7 @@
if (FW_SUPPORTED((&dhd->pub), monitor)) {
#ifdef DHD_PCIE_RUNTIMEPM
/* Disable RuntimePM in monitor mode */
- DHD_DISABLE_RUNTIME_PM(&dhd->pub);
+ DHD_STOP_RPM_TIMER(&dhd->pub);
DHD_ERROR(("%s : disable runtime PM in monitor mode\n", __FUNCTION__));
#endif /* DHD_PCIE_RUNTIME_PM */
scan_suppress = TRUE;
@@ -5611,6 +5827,7 @@
return;
}
#ifdef WL_CFG80211_MONITOR
+ dhd->monitor_type = FALSE;
dev_priv = DHD_MON_DEV_PRIV(dhd->monitor_dev);
dev_priv->dhd = (dhd_info_t *)NULL;
bzero(&dev_priv->stats, sizeof(dev_priv->stats));
@@ -5619,7 +5836,7 @@
if (FW_SUPPORTED((&dhd->pub), monitor)) {
#ifdef DHD_PCIE_RUNTIMEPM
/* Enable RuntimePM */
- DHD_ENABLE_RUNTIME_PM(&dhd->pub);
+ DHD_START_RPM_TIMER(&dhd->pub);
DHD_ERROR(("%s : enabled runtime PM\n", __FUNCTION__));
#endif /* DHD_PCIE_RUNTIME_PM */
scan_suppress = FALSE;
@@ -5746,7 +5963,9 @@
goto done;
}
buflen = ioc->len;
- } else if (!bcmstricmp((char *)data_buf, "dump")) {
+ } else if (!bcmstricmp((char *)data_buf, "dump") ||
+ !bcmstricmp((char *)data_buf, "counters") ||
+ !bcmstricmp((char *)data_buf, "dump_flowrings")) {
buflen = MIN(ioc->len, DHD_IOCTL_MAXLEN_32K);
} else {
/* This is a DHD IOVAR, truncate buflen to DHD_IOCTL_MAXLEN */
@@ -6162,7 +6381,21 @@
}
#endif /* LINUX_VERSION_CODE > 4.19.0 && DHD_TCP_LIMIT_OUTPUT */
-static int
+void
+dhd_force_collect_socram_during_wifi_onoff(dhd_pub_t *dhdp)
+{
+#ifdef DHD_FW_COREDUMP
+ if (dhdp->memdump_enabled && (dhdp->busstate != DHD_BUS_DOWN)) {
+#ifdef DHD_SSSR_DUMP
+ dhdp->collect_sssr = TRUE;
+#endif /* DHD_SSSR_DUMP */
+ dhdp->memdump_type = DUMP_TYPE_DONGLE_TRAP_DURING_WIFI_ONOFF;
+ dhd_bus_mem_dump(dhdp);
+ }
+#endif /* DHD_FW_COREDUMP */
+}
+
+int
dhd_stop(struct net_device *net)
{
int ifidx = 0;
@@ -6174,6 +6407,8 @@
#endif /* WL_STATIC_IF */
#endif /* WL_CFG80211 */
dhd_info_t *dhd = DHD_DEV_INFO(net);
+ int timeleft = 0;
+ uint32 bitmask = (uint32)-1;
DHD_ERROR(("%s: ENTER\n", __FUNCTION__));
DHD_OS_WAKE_LOCK(&dhd->pub);
@@ -6187,7 +6422,21 @@
/* Synchronize between the stop and rx path */
dhd->pub.stop_in_progress = true;
OSL_SMP_WMB();
- dhd_os_busbusy_wait_negation(&dhd->pub, &dhd->pub.dhd_bus_busy_state);
+
+#ifdef DHD_COREDUMP
+ if (DHD_BUS_BUSY_CHECK_IN_HALDUMP(&dhd->pub)) {
+ DHD_ERROR(("%s: Cancel the triggerd HAL dump.\n", __FUNCTION__));
+ DHD_BUS_BUSY_CLEAR_IN_HALDUMP(&dhd->pub);
+ }
+ bitmask = ~(DHD_BUS_BUSY_IN_HALDUMP);
+#endif /* DHD_COREDUMP */
+ timeleft = dhd_os_busbusy_wait_bitmask(&dhd->pub,
+ &dhd->pub.dhd_bus_busy_state,
+ bitmask, 0);
+ if (dhd->pub.dhd_bus_busy_state & bitmask) {
+ DHD_ERROR(("%s: Timed out(%d) dhd_bus_busy_state=0x%x\n",
+ __FUNCTION__, timeleft, dhd->pub.dhd_bus_busy_state));
+ }
mutex_lock(&dhd->pub.ndev_op_sync);
if (dhd->pub.up == 0) {
@@ -6382,6 +6631,13 @@
#if defined(WL_CFG80211)
if (ifidx == 0 && !dhd_download_fw_on_driverload) {
#if defined(WLAN_ACCEL_BOOT)
+ if (dhd->pub.dongle_trap_during_wifi_onoff) {
+ DHD_ERROR(("%s: force collect socram due to trap "
+ "during wifi on/off.\n", __FUNCTION__));
+ dhd_force_collect_socram_during_wifi_onoff(&dhd->pub);
+ dhd->pub.dongle_trap_during_wifi_onoff = 0;
+ }
+
wl_android_wifi_accel_off(net, dhd->wl_accel_force_reg_on);
#else
#if defined(BT_OVER_SDIO)
@@ -6565,13 +6821,16 @@
}
#endif /* PREVENT_REOPEN_DURING_HANG */
- dhd_tcm_test_status = TCM_TEST_NOT_RUN; /* clear to run TCM test once per dhd_open() */
+ /* clear to run TCM test once per dhd_open() */
+ if (dhd_tcm_test_mode != TCM_TEST_MODE_ONCE) {
+ dhd_tcm_test_status = TCM_TEST_NOT_RUN;
+ }
mutex_lock(&dhd->pub.ndev_op_sync);
if (dhd->pub.up == 1) {
/* already up */
- DHD_INFO(("Primary net_device is already up \n"));
+ DHD_ERROR(("Primary net_device is already up \n"));
mutex_unlock(&dhd->pub.ndev_op_sync);
return BCME_OK;
}
@@ -6582,6 +6841,12 @@
DHD_ERROR(("%s: set force reg on\n", __FUNCTION__));
dhd->wl_accel_force_reg_on = TRUE;
}
+ if (!dhd->wl_accel_force_reg_on && !DHD_BUS_BUSY_CHECK_IDLE(&dhd->pub)) {
+ DHD_ERROR(("%s: clear dhd_bus_busy_state: 0x%x\n",
+ __FUNCTION__, dhd->pub.dhd_bus_busy_state));
+ dhd->pub.dhd_bus_busy_state = 0;
+ dhd->wl_accel_force_reg_on = TRUE;
+ }
#endif /* WLAN_ACCEL_BOOT */
if (!dhd_driver_init_done) {
DHD_ERROR(("%s: WLAN driver is not initialized\n", __FUNCTION__));
@@ -6621,6 +6886,9 @@
DHD_OS_WAKE_LOCK(&dhd->pub);
dhd->pub.dongle_trap_occured = 0;
+ dhd->pub.dsack_hc_due_to_isr_delay = 0;
+ dhd->pub.dsack_hc_due_to_dpc_delay = 0;
+ dhd->pub.dongle_trap_during_wifi_onoff = 0;
dhd->pub.hang_was_sent = 0;
dhd->pub.hang_was_pending = 0;
dhd->pub.hang_reason = 0;
@@ -6684,6 +6952,7 @@
DHD_ERROR(("%s: ######### called for ifidx=%d #########\n", __FUNCTION__, ifidx));
+ dhd->pub.p2p_disc_busy_cnt = 0;
#if defined(WLAN_ACCEL_BOOT)
dhd_verify_firmware_mode_change(dhd);
#endif /* WLAN_ACCEL_BOOT */
@@ -6890,11 +7159,6 @@
#if defined(NUM_SCB_MAX_PROBE)
dhd_set_scb_probe(&dhd->pub);
#endif /* NUM_SCB_MAX_PROBE */
-#if defined(CONFIG_WIFI_BROADCOM_COB) && defined(BCM4389_CHIP_DEF)
- if (dhd_get_fw_mode(dhd) == DHD_FLAG_MFG_MODE) {
- dhd_read_otp_hw_rgn(&dhd->pub);
- }
-#endif /* CONFIG_WIFI_BROADCOM_COB && BCM4389_CHIP_DEF */
#endif /* WL_CFG80211 */
}
@@ -6930,6 +7194,11 @@
exit:
mutex_unlock(&dhd->pub.ndev_op_sync);
+
+ if (dhd_query_bus_erros(&dhd->pub)) {
+ ret = BCME_ERROR;
+ }
+
if (ret) {
if (ret != BCME_NOMEM) {
dhd_force_collect_init_fail_dumps(&dhd->pub);
@@ -9264,11 +9533,12 @@
#ifdef WL_CFGVENDOR_SEND_ALERT_EVENT
INIT_WORK(&dhd->dhd_alert_process_work, dhd_alert_process);
#endif /* WL_CFGVENDOR_SEND_ALERT_EVENT */
-#ifdef CONFIG_ARCH_EXYNOS
-#if IS_ENABLED(CONFIG_EXYNOS_S2MPU)
+#if defined(DHD_ENABLE_S2MPU)
dhd_module_s2mpu_register(dhd_bus_to_dev(bus));
-#endif /* CONFIG_EXYNOS_S2MPU */
-#endif /* CONFIG_ARCH_EXYNOS */
+#endif /* DHD_ENABLE_S2MPU */
+#ifdef DHD_REGISTER_SMMU_FAULT_HANDLER
+ pcie_sysmmu_add_fault_handler(&dhd_pcie_sysmmu_nb);
+#endif /* DHD_REGISTER_SMMU_FAULT_HANDLER */
#if defined(DHD_FILE_DUMP_EVENT) && defined(DHD_FW_COREDUMP)
OSL_ATOMIC_SET(dhd->pub.osh, &dhd->dump_status, DUMP_NOT_READY);
INIT_WORK(&dhd->dhd_dump_proc_work, dhd_dump_proc);
@@ -9457,7 +9727,7 @@
#endif /* DHD_USE_SINGLE_NVRAM_FILE */
}
if (signature_path[0] != '\0') {
- sig_len = strlen(fw);
+ sig_len = strlen(signature_path);
if (sig_len >= sig_path_len) {
DHD_ERROR(("signature path len exceeds max len of dhdinfo->sig_path\n"));
return FALSE;
@@ -9601,6 +9871,9 @@
DHD_TRACE(("Enter %s:\n", __FUNCTION__));
dhdp->memdump_type = 0;
dhdp->dongle_trap_occured = 0;
+ dhd->pub.dsack_hc_due_to_isr_delay = 0;
+ dhd->pub.dsack_hc_due_to_dpc_delay = 0;
+ dhdp->dongle_trap_during_wifi_onoff = 0;
#ifdef DHD_SSSR_DUMP
dhdp->collect_sssr = FALSE;
#endif /* DHD_SSSR_DUMP */
@@ -9640,6 +9913,7 @@
#endif /* DHD_SUPPORT_SPMI_MODE */
dhd->pub.tput_test_done = FALSE;
+ dhd->pub.p2p_disc_busy_cnt = 0;
/* try to download image and nvram to the dongle */
if (dhd->pub.busstate == DHD_BUS_DOWN && dhd_update_fw_nv_path(dhd)) {
/* Indicate FW Download has not yet done */
@@ -10358,7 +10632,11 @@
*logset_mask = 0;
memset(&logset_type, 0, sizeof(logset_type));
memset(&logset_op, 0, sizeof(logset_op));
+#if defined(EVENT_LOG_SET_TYPE_VERSION_0)
+ logset_type.version = htod16(EVENT_LOG_SET_TYPE_VERSION_0);
+#else
logset_type.version = htod16(EVENT_LOG_SET_TYPE_CURRENT_VERSION);
+#endif
logset_type.len = htod16(sizeof(wl_el_set_type_t));
/* Try with set = event_log_max_sets, if fails, use legacy event_log_set_type */
@@ -12378,9 +12656,6 @@
setbit(mask, WLC_E_ROAM_EXP_EVENT);
#endif /* GSCAN_SUPPORT */
setbit(mask, WLC_E_RSSI_LQM);
-#ifdef BT_WIFI_HANDOVER
- setbit(mask, WLC_E_BT_WIFI_HANDOVER_REQ);
-#endif /* BT_WIFI_HANDOVER */
#ifdef DBG_PKT_MON
setbit(mask, WLC_E_ROAM_PREP);
#endif /* DBG_PKT_MON */
@@ -12938,8 +13213,10 @@
return ret;
}
+#if defined(BCMPCIE)
/* Deafult enable preinit optimisation */
#define DHD_PREINIT_OPTIMISATION
+#endif /* BCMPCIE */
int
dhd_preinit_ioctls(dhd_pub_t *dhd)
@@ -13054,6 +13331,11 @@
return BCME_ERROR;
}
+ if (dhdp->stop_in_progress) {
+ DHD_ERROR(("%s: dhd_stop in progress\n", __FUNCTION__));
+ return BCME_ERROR;
+ }
+
DHD_GENERAL_LOCK(dhdp, flags);
if (DHD_BUS_CHECK_DOWN_OR_DOWN_IN_PROGRESS(dhdp)) {
DHD_BUS_BUSY_CLEAR_IN_HALDUMP(dhdp);
@@ -13071,6 +13353,9 @@
int timeleft = 0;
DHD_ERROR(("[DUMP] %s: HAL started. send urgent event\n", __FUNCTION__));
+#ifdef DHD_MAP_PKTID_LOGGING
+ dhd_pktid_logging_dump(dhdp);
+#endif /* DHD_MAP_PKTID_LOGGING */
dhd_dbg_send_urgent_evt(dhdp, NULL, 0);
DHD_ERROR(("%s: wait to clear dhd_bus_busy_state: 0x%x\n",
@@ -13386,7 +13671,7 @@
dhdp = &dhd->pub;
idx = dhd_net2idx(dhd, inet6_ifa->idev->dev);
- if ((idx < DHD_MAX_IFS) && IS_STA_IFACE(ndev_to_wdev(inet6_ifa->idev->dev))) {
+ if ((idx >= 0 && idx < DHD_MAX_IFS) && IS_STA_IFACE(ndev_to_wdev(inet6_ifa->idev->dev))) {
DHD_TRACE(("ifidx : %p %s %d\n", dhd->iflist[idx]->net,
dhd->iflist[idx]->name, dhd->iflist[idx]->idx));
} else {
@@ -13721,16 +14006,6 @@
if (dhd->dhd_state & DHD_ATTACH_STATE_PROT_ATTACH) {
dhd_bus_detach(dhdp);
-#ifdef BCMPCIE
- if (is_reboot == SYS_RESTART) {
- extern bcmdhd_wifi_platdata_t *dhd_wifi_platdata;
- if (dhd_wifi_platdata && !dhdp->dongle_reset) {
- dhdpcie_bus_stop_host_dev(dhdp->bus);
- wifi_platform_set_power(dhd_wifi_platdata->adapters,
- FALSE, WIFI_TURNOFF_DELAY);
- }
- }
-#endif /* BCMPCIE */
#ifndef PCIE_FULL_DONGLE
if (dhdp->prot)
dhd_prot_detach(dhdp);
@@ -13813,6 +14088,9 @@
MFREE(dhd->pub.osh, ifp, sizeof(*ifp));
ifp = NULL;
+#ifdef WL_CFG80211
+ cfg->wdev->netdev = NULL;
+#endif
}
}
@@ -14252,6 +14530,10 @@
static void
dhd_module_cleanup(void)
{
+#if defined(ENABLE_NOT_LOAD_DHD_MODULE)
+ DHD_ERROR(("%s ##### Do not clean-up due to secondary build\n", __FUNCTION__));
+ return;
+#endif /* ENABLE_NOT_LOAD_DHD_MODULE */
DHD_TRACE(("%s: Enter\n", __FUNCTION__));
#ifdef BCMDBUS
@@ -14268,6 +14550,10 @@
static void __exit
dhd_module_exit(void)
{
+#if defined(ENABLE_NOT_LOAD_DHD_MODULE)
+ DHD_ERROR(("%s ##### Do not unload driver due to secondary build\n", __FUNCTION__));
+ return;
+#endif /* ENABLE_NOT_LOAD_DHD_MODULE */
atomic_set(&exit_in_progress, 1);
#ifdef DHD_BUZZZ_LOG_ENABLED
dhd_buzzz_detach();
@@ -14277,6 +14563,10 @@
dhd_destroy_to_notifier_skt();
}
+#if defined(CONFIG_ARCH_WAIPIO) || defined(CONFIG_SOC_S5E9925)
+extern bool devid_mismatch;
+#endif /* CONFIG_ARCH_WAIPIO || CONFIG_SOC_S5E9925 */
+
static int
_dhd_module_init(void)
{
@@ -14321,8 +14611,20 @@
err = dhd_wifi_platform_register_drv();
if (!err) {
register_reboot_notifier(&dhd_reboot_notifier);
+ dhd_create_to_notifier_skt();
break;
} else {
+ if (err == -ENXIO) {
+ DHD_ERROR(("%s: driver is disabled\n", __FUNCTION__));
+ break;
+ }
+#if defined(CONFIG_ARCH_WAIPIO) || defined(CONFIG_SOC_S5E9925)
+ if (devid_mismatch == TRUE) {
+ DHD_ERROR(("%s: Devid is mismatch, don't retry\n",
+ __FUNCTION__));
+ break;
+ }
+#endif /* CONFIG_ARCH_WAIPIO || CONFIG_SOC_S5E9925 */
DHD_ERROR(("%s: Failed to load the driver, try cnt %d\n",
__FUNCTION__, retry));
strlcpy(firmware_path, fw_bak_path, sizeof(firmware_path));
@@ -14330,7 +14632,12 @@
}
} while (retry--);
- dhd_create_to_notifier_skt();
+#if defined(CONFIG_ARCH_WAIPIO) || defined(CONFIG_SOC_S5E9925)
+ if (devid_mismatch == TRUE) {
+ DHD_ERROR(("%s: Return true if devid is mismatch \n", __FUNCTION__));
+ return 0;
+ }
+#endif /* CONFIG_ARCH_WAIPIO || CONFIG_SOC_S5E9925 */
if (err) {
DHD_ERROR(("%s: Failed to load driver max retry reached**\n", __FUNCTION__));
@@ -14350,6 +14657,10 @@
{
int err;
+#if defined(ENABLE_NOT_LOAD_DHD_MODULE)
+ DHD_ERROR(("%s ##### Do not load driver due to secondary build\n", __FUNCTION__));
+ return 0;
+#endif /* ENABLE_NOT_LOAD_DHD_MODULE */
err = _dhd_module_init();
#ifdef DHD_SUPPORT_HDM
if (hdm_wifi_support && err && !dhd_download_fw_on_driverload) {
@@ -14396,12 +14707,16 @@
static int
dhd_reboot_callback(struct notifier_block *this, unsigned long code, void *unused)
{
- DHD_TRACE(("%s: code = %ld\n", __FUNCTION__, code));
- if (code == SYS_RESTART) {
-#ifdef BCMPCIE
- is_reboot = code;
-#endif /* BCMPCIE */
+ dhd_pub_t *dhdp = g_dhd_pub;
+
+ BCM_REFERENCE(dhdp);
+ DHD_ERROR(("%s: code = %ld\n", __FUNCTION__, code));
+ if (!OSL_ATOMIC_INC_AND_TEST(dhdp->osh, &reboot_in_progress)) {
+ DHD_ERROR(("%s: Skip duplicated reboot callback!\n", __FUNCTION__));
+ return NOTIFY_DONE;
}
+
+ dhd_module_cleanup();
return NOTIFY_DONE;
}
@@ -14856,6 +15171,35 @@
}
#ifdef DHD_PCIE_RUNTIMEPM
+#ifdef RPM_FAST_TRIGGER
+void
+dhdpcie_trigger_rpm_fast(dhd_pub_t *dhdp)
+{
+ unsigned long flags = 0;
+ dhd_info_t *dhd = NULL;
+
+ DHD_TRACE(("%s : Enter \n", __FUNCTION__));
+
+ if (!dhdp) {
+ DHD_ERROR(("%s: dhd is NULL\n", __FUNCTION__));
+ return;
+ }
+
+ dhd = (dhd_info_t *)dhdp->info;
+
+ /* check it's bus idle state, and check previous timer is scheduled */
+ DHD_GENERAL_LOCK(dhdp, flags);
+ if (dhd->rpm_timer_valid && dhd_get_rpm_state(dhdp) &&
+ !DHD_BUS_CHECK_DOWN_OR_DOWN_IN_PROGRESS(dhdp)) {
+ dhdp->rpm_fast_trigger = TRUE;
+ DHD_ERROR(("%s: trigger rpm timer : %d msec\n",
+ __FUNCTION__, dhd_fast_runtimepm_ms));
+ mod_timer(&dhd->rpm_timer, jiffies + msecs_to_jiffies(dhd_fast_runtimepm_ms));
+ }
+ DHD_GENERAL_UNLOCK(dhdp, flags);
+
+}
+#endif /* RPM_FAST_TRIGGER */
void
dhd_os_runtimepm_timer(void *bus, uint tick)
{
@@ -14874,8 +15218,10 @@
/* don't start the RPM until fw is loaded */
if (DHD_BUS_CHECK_DOWN_OR_DOWN_IN_PROGRESS(pub)) {
- DHD_GENERAL_UNLOCK(pub, flags);
- return;
+ if (dhd->rpm_timer_valid == FALSE) {
+ DHD_GENERAL_UNLOCK(pub, flags);
+ return;
+ }
}
/* If tick is non-zero, the request is to start the timer */
@@ -15316,6 +15662,8 @@
if (flag) {
/* Clear some flags for recovery logic */
dhd->pub.dongle_trap_occured = 0;
+ dhd->pub.dsack_hc_due_to_isr_delay = 0;
+ dhd->pub.dsack_hc_due_to_dpc_delay = 0;
dhd->pub.iovar_timeout_occured = 0;
#ifdef PCIE_FULL_DONGLE
dhd->pub.d3ack_timeout_occured = 0;
@@ -15330,6 +15678,8 @@
dhd->pub.p2p_disc_busy_occurred = 0;
}
+ dhd->pub.p2p_disc_busy_cnt = 0;
+
if (ret == BCME_NOMEM) {
DHD_ERROR(("%s: skip collect dump in case of BCME_NOMEM\n",
__FUNCTION__));
@@ -16128,7 +16478,7 @@
roam_param->alert_roam_trigger_threshold, roam_param->a_band_max_boost));
memcpy(&roam_exp_cfg.params, roam_param, sizeof(*roam_param));
- roam_exp_cfg.version = ROAM_EXP_CFG_VERSION;
+ roam_exp_cfg.version = ROAM_EXP_CFG_VERSION_1;
roam_exp_cfg.flags = ROAM_EXP_CFG_PRESENT;
if (dhd->pub.lazy_roam_enable) {
roam_exp_cfg.flags |= ROAM_EXP_ENABLE_FLAG;
@@ -16150,7 +16500,7 @@
wl_roam_exp_cfg_t roam_exp_cfg;
memset(&roam_exp_cfg, 0, sizeof(roam_exp_cfg));
- roam_exp_cfg.version = ROAM_EXP_CFG_VERSION;
+ roam_exp_cfg.version = ROAM_EXP_CFG_VERSION_1;
if (enable) {
roam_exp_cfg.flags = ROAM_EXP_ENABLE_FLAG;
}
@@ -16173,7 +16523,7 @@
uint len;
dhd_info_t *dhd = *(dhd_info_t **)netdev_priv(dev);
- bssid_pref->version = BSSID_PREF_LIST_VERSION;
+ bssid_pref->version = BSSID_PREF_LIST_VERSION_1;
/* By default programming bssid pref flushes out old values */
bssid_pref->flags = (flush && !bssid_pref->count) ? ROAM_EXP_CLEAR_BSSID_PREF: 0;
len = sizeof(wl_bssid_pref_cfg_t);
@@ -16231,7 +16581,7 @@
return BCME_BADARG;
}
}
- ssid_whitelist->version = SSID_WHITELIST_VERSION;
+ ssid_whitelist->version = SSID_WHITELIST_VERSION_1;
ssid_whitelist->flags = flush ? ROAM_EXP_CLEAR_SSID_WHITELIST : 0;
err = dhd_iovar(&dhd->pub, 0, "roam_exp_ssid_whitelist", (char *)ssid_whitelist, len, NULL,
0, TRUE);
@@ -16257,7 +16607,7 @@
wl_rssi_monitor_cfg_t rssi_monitor;
dhd_info_t *dhd = *(dhd_info_t **)netdev_priv(dev);
- rssi_monitor.version = RSSI_MONITOR_VERSION;
+ rssi_monitor.version = RSSI_MONITOR_VERSION_1;
rssi_monitor.max_rssi = max_rssi;
rssi_monitor.min_rssi = min_rssi;
rssi_monitor.flags = start ? 0: RSSI_MONITOR_STOP;
@@ -16861,21 +17211,45 @@
uint8 i = 0;
#endif /* IFACE_HANG_FORCE_DEV_CLOSE */
struct dhd_info *dhd;
+ dhd_pub_t *dhdp;
+#ifdef WL_CFG80211
+ struct bcm_cfg80211 *cfg;
+#endif /* WL_CFG80211 */
+
/* Ignore compiler warnings due to -Werror=cast-qual */
GCC_DIAGNOSTIC_PUSH_SUPPRESS_CAST();
dhd = container_of(work_data, dhd_info_t, dhd_hang_process_work);
GCC_DIAGNOSTIC_POP();
+ dhdp = &dhd->pub;
- dev = dhd->iflist[0]->net;
+ dev = dhd_linux_get_primary_netdev(dhdp);
- if (dev) {
+ if (!dev) {
+ DHD_ERROR(("%s: Cannot find primary netdev\n", __FUNCTION__));
+ dhdp->hang_was_sent = 0;
+ return;
+ }
+#ifdef WL_CFG80211
+ cfg = wl_get_cfg(dev);
+ if (!cfg) {
+ DHD_ERROR(("%s: Cannot find cfg\n", __FUNCTION__));
+ dhdp->hang_was_sent = 0;
+ return;
+ }
+ /* Skip sending HANG event to framework if driver is not ready */
+ if (!wl_get_drv_status(cfg, READY, dev)) {
+ DHD_ERROR(("%s: device is not ready\n", __FUNCTION__));
+ dhdp->hang_was_sent = 0;
+ return;
+ }
+#endif /* WL_CFG80211 */
#if defined(WL_WIRELESS_EXT)
- wl_iw_send_priv_event(dev, "HANG");
+ wl_iw_send_priv_event(dev, "HANG");
#endif
#if defined(WL_CFG80211)
- wl_cfg80211_hang(dev, WLAN_REASON_UNSPECIFIED);
+ wl_cfg80211_hang(dev, WLAN_REASON_UNSPECIFIED);
#endif
- }
+
#ifdef IFACE_HANG_FORCE_DEV_CLOSE
/*
* In case of wif scan only mode, upper layer doesn't handle hang
@@ -16918,14 +17292,14 @@
EXPORT_SYMBOL(dhd_host_recover_link);
#endif /* CONFIG_ARCH_EXYNOS && BCMPCIE */
+/*
+ * Note that this function should be called in both interrupt and process context
+ * Therefore, Keep it simple, and use workqueue for complex/time-consuming work
+ */
int dhd_os_send_hang_message(dhd_pub_t *dhdp)
{
int ret = 0;
dhd_info_t *dhd_info = NULL;
-#ifdef WL_CFG80211
- struct net_device *primary_ndev;
- struct bcm_cfg80211 *cfg;
-#endif /* WL_CFG80211 */
if (!dhdp) {
DHD_ERROR(("%s: dhdp is null\n", __FUNCTION__));
@@ -16934,7 +17308,15 @@
dhd_info = (dhd_info_t *)dhdp->info;
BCM_REFERENCE(dhd_info);
-
+#ifdef DHD_FW_COREDUMP
+ if (dhdp->memdump_enabled == DUMP_MEMFILE_BUGON &&
+ (dhdp->hang_reason == HANG_REASON_PCIE_LINK_DOWN_RC_DETECT ||
+ dhdp->hang_reason == HANG_REASON_PCIE_LINK_DOWN_EP_DETECT)) {
+ DHD_ERROR(("%s: BUG_ON for pcie link down memdump_enabled:%d\n",
+ __FUNCTION__, dhdp->memdump_enabled));
+ BUG_ON(1);
+ }
+#endif /* DHD_FW_COREDUMP */
#if defined(WLAN_ACCEL_BOOT)
if (!dhd_info->wl_accel_force_reg_on) {
DHD_ERROR(("%s: set force reg on\n", __FUNCTION__));
@@ -16947,6 +17329,11 @@
return BCME_ERROR;
}
+ if (dhdp->stop_in_progress) {
+ DHD_ERROR(("%s: dhd_stop in progress\n", __FUNCTION__));
+ return BCME_OK;
+ }
+
#if defined(WL_CFG80211) && (defined(DHD_FILE_DUMP_EVENT) || defined(DHD_COREDUMP))
if (dhd_info->scheduled_memdump) {
DHD_ERROR_RLMT(("[DUMP]:%s, memdump in progress. return\n", __FUNCTION__));
@@ -16955,25 +17342,6 @@
}
#endif /* WL_CFG80211 && (DHD_FILE_DUMP_EVENT || DHD_COREDUMP) */
-#ifdef WL_CFG80211
- primary_ndev = dhd_linux_get_primary_netdev(dhdp);
- if (!primary_ndev) {
- DHD_ERROR(("%s: Cannot find primary netdev\n", __FUNCTION__));
- return -ENODEV;
- }
- cfg = wl_get_cfg(primary_ndev);
- if (!cfg) {
- DHD_ERROR(("%s: Cannot find cfg\n", __FUNCTION__));
- return -EINVAL;
- }
-
- /* Skip sending HANG event to framework if driver is not ready */
- if (!wl_get_drv_status(cfg, READY, primary_ndev)) {
- DHD_ERROR(("%s: device is not ready\n", __FUNCTION__));
- return -ENODEV;
- }
-#endif /* WL_CFG80211 */
-
#if defined(DHD_HANG_SEND_UP_TEST)
if (dhdp->req_hang_type) {
DHD_ERROR(("%s, Clear HANG test request 0x%x\n",
@@ -17866,6 +18234,13 @@
DHD_ERROR(("%s wakelock c-%d wl-%d wd-%d rx-%d "
"ctl-%d intr-%d scan-%d evt-%d, pm-%d, txfl-%d nan-%d\n",
__FUNCTION__, c, l1, l2, l3, l4, l5, l6, l7, l8, l9, l10));
+#ifdef RPM_FAST_TRIGGER
+ if (pub->rpm_fast_trigger && l4) {
+ DHD_ERROR(("%s : reset rpm_fast_trigger becasue of wl_ctrlwake activated\n",
+ __FUNCTION__));
+ pub->rpm_fast_trigger = FALSE;
+ }
+#endif /* RPM_FAST_TRIGGER */
return 1;
}
#elif defined(BCMSDIO)
@@ -18607,12 +18982,14 @@
if ((dhdp->memdump_type == DUMP_TYPE_DONGLE_INIT_FAILURE) ||
(dhdp->memdump_type == DUMP_TYPE_DUE_TO_BT) ||
- (dhdp->memdump_type == DUMP_TYPE_SMMU_FAULT))
+ (dhdp->memdump_type == DUMP_TYPE_SMMU_FAULT) ||
+ (dhdp->memdump_type == DUMP_TYPE_DONGLE_TRAP_DURING_WIFI_ONOFF))
{
dhd_info->scheduled_memdump = FALSE;
dhd_mem_dump((void *)dhdp->info, (void *)dump, 0);
/* No need to collect debug dump for init failure */
- if (dhdp->memdump_type == DUMP_TYPE_DONGLE_INIT_FAILURE) {
+ if (dhdp->memdump_type == DUMP_TYPE_DONGLE_INIT_FAILURE ||
+ dhdp->memdump_type == DUMP_TYPE_DONGLE_TRAP_DURING_WIFI_ONOFF) {
return;
}
#ifdef DHD_LOG_DUMP
@@ -18678,6 +19055,7 @@
char pc_fn[DHD_FUNC_STR_LEN] = "\0";
char lr_fn[DHD_FUNC_STR_LEN] = "\0";
trap_t *tr;
+ uint32 memdump_type;
#endif /* DHD_COREDUMP */
DHD_ERROR(("%s: ENTER \n", __FUNCTION__));
@@ -18778,15 +19156,28 @@
#ifdef DHD_COREDUMP
memset_s(dhdp->memdump_str, DHD_MEMDUMP_LONGSTR_LEN, 0, DHD_MEMDUMP_LONGSTR_LEN);
- dhd_convert_memdump_type_to_str(dhdp->memdump_type, dhdp->memdump_str,
+
+ if (dhdp->dsack_hc_due_to_isr_delay) {
+ memdump_type = DUMP_TYPE_BY_DSACK_HC_DUE_TO_ISR_DELAY;
+ } else if (dhdp->dsack_hc_due_to_dpc_delay) {
+ memdump_type = DUMP_TYPE_BY_DSACK_HC_DUE_TO_DPC_DELAY;
+ } else {
+ memdump_type = dhdp->memdump_type;
+ }
+
+ dhd_convert_memdump_type_to_str(memdump_type, dhdp->memdump_str,
DHD_MEMDUMP_LONGSTR_LEN, dhdp->debug_dump_subcmd);
+
if (dhdp->memdump_type == DUMP_TYPE_DONGLE_TRAP &&
dhdp->dongle_trap_occured == TRUE) {
- tr = &dhdp->last_trap_info;
- dhd_lookup_map(dhdp->osh, map_path,
- ltoh32(tr->epc), pc_fn, ltoh32(tr->r14), lr_fn);
- sprintf(&dhdp->memdump_str[strlen(dhdp->memdump_str)], "_%.79s_%.79s",
- pc_fn, lr_fn);
+ if (!dhdp->dsack_hc_due_to_isr_delay &&
+ !dhdp->dsack_hc_due_to_dpc_delay) {
+ tr = &dhdp->last_trap_info;
+ dhd_lookup_map(dhdp->osh, map_path,
+ ltoh32(tr->epc), pc_fn, ltoh32(tr->r14), lr_fn);
+ sprintf(&dhdp->memdump_str[strlen(dhdp->memdump_str)],
+ "_%.79s_%.79s", pc_fn, lr_fn);
+ }
}
DHD_ERROR(("%s: dump reason: %s\n", __FUNCTION__, dhdp->memdump_str));
@@ -18932,9 +19323,6 @@
DHD_BUS_BUSY_CLEAR_IN_MEMDUMP(&dhd->pub);
dhd_os_busbusy_wake(dhdp);
DHD_GENERAL_UNLOCK(dhdp, flags);
-#ifdef DHD_SSSR_DUMP
- dhdp->collect_sssr = FALSE;
-#endif /* DHD_SSSR_DUMP */
dhd->scheduled_memdump = FALSE;
if (dhdp->hang_was_pending) {
@@ -20812,10 +21200,6 @@
}
i++;
}
- if (bcm_atoi((char*)buf) > 255) {
- DHD_ERROR(("error: element id cannot be greater than 255 \n"));
- return BCME_ERROR;
- }
return BCME_OK;
}
@@ -20842,7 +21226,7 @@
}
/* setup filter iovar header */
- p_filter_iov->version = WL_FILTER_IE_VERSION;
+ p_filter_iov->version = WL_FILTER_IE_VERSION_1;
p_filter_iov->len = filter_iovsize;
p_filter_iov->fixed_length = p_filter_iov->len - FILTER_IE_BUFSZ;
p_filter_iov->pktflag = FC_PROBE_REQ;
@@ -21367,6 +21751,7 @@
}
DHD_ERROR(("DHD Tasklet status : 0x%lx\n", dhdinfo->tasklet.state));
+ DHD_ERROR(("DPC thread thr_pid: %ld\n", dhdinfo->thr_dpc_ctl.thr_pid));
}
#if defined(DHD_MQ) && defined(DHD_MQ_STATS)
@@ -22626,21 +23011,6 @@
}
/* END of DHD RING */
-#if (LINUX_VERSION_CODE < KERNEL_VERSION(3, 19, 0))
-#define DHD_VFS_INODE(dir) (dir->d_inode)
-#else
-#define DHD_VFS_INODE(dir) d_inode(dir)
-#endif /* LINUX_VERSION_CODE < KERNEL_VERSION(3, 19, 0) */
-
-#ifdef DHD_SUPPORT_VFS_CALL
-#if (LINUX_VERSION_CODE < KERNEL_VERSION(3, 13, 0))
-#define DHD_VFS_UNLINK(dir, b, c) vfs_unlink(DHD_VFS_INODE(dir), b)
-#else
-#define DHD_VFS_UNLINK(dir, b, c) vfs_unlink(DHD_VFS_INODE(dir), b, c)
-#endif /* LINUX_VERSION_CODE < KERNEL_VERSION(3, 13, 0) */
-#else
-#define DHD_VFS_UNLINK(dir, b, c) 0
-#endif /* DHD_SUPPORT_VFS_CALL */
int
dhd_file_delete(char *path)
{
@@ -23065,6 +23435,21 @@
#endif /* DHD_PCIE_RUNTIMEPM */
dhd_flow_rings_delete(dhd, ifp->idx);
}
+#if defined(WBRC) && defined(WBRC_BT2WL_RESET)
+void
+dhd_wbrc_wl_trap(void)
+{
+ dhd_pub_t *dhdp = g_dhd_pub;
+
+ dhdpcie_db7_trap(dhdp->bus);
+ /* set that dongle trap has occured to stop other contests from firing IOVARS */
+ dhdp->dongle_trap_occured = TRUE;
+ /* Set chip big hammer */
+ dhdp->do_chip_bighammer = TRUE;
+ dhdp->hang_reason = HANG_REASON_BT2WL_REG_RESET;
+ dhd_os_send_hang_message(dhdp);
+}
+#endif /* WBRC && WBRC_BT2WL_RESET */
#endif /* PCIE_FULL_DONGLE */
static void
@@ -23193,8 +23578,7 @@
}
#endif /* TPUT_DEBUG_DUMP */
-#ifdef CONFIG_ARCH_EXYNOS
-#if IS_ENABLED(CONFIG_EXYNOS_S2MPU)
+#if defined(DHD_ENABLE_S2MPU)
/*
* return
* S2MPUFD_NOTIFY_BAD : watchdog reset
@@ -23231,8 +23615,20 @@
s2mpu_nb->notifier_call = s2mpufd_notifier_callback;
s2mpufd_notifier_call_register(s2mpu_nb);
}
-#endif /* CONFIG_EXYNOS_S2MPU */
-#endif /* CONFIG_ARCH_EXYNOS */
+#endif /* DHD_ENABLE_S2MPU */
+
+#ifdef DHD_REGISTER_SMMU_FAULT_HANDLER
+#define SYSMMU_NOTIFY_SKIP_PANIC 3
+static int sysmmu_notifier_callback(struct notifier_block *nb, unsigned long addr,
+ void *flag)
+{
+ int fault_info = *(int *)flag;
+ DHD_ERROR(("%s: Fault ADDR 0x%lx - %s\n", __FUNCTION__, addr,
+ (fault_info & 0x1) ? "WRITE" : "READ"));
+ dhd_smmu_fault_handler(0, addr);
+ return SYSMMU_NOTIFY_SKIP_PANIC;
+}
+#endif /* DHD_REGISTER_SMMU_FAULT_HANDLER */
#ifdef BCMDBUS
struct device *dhd_bus_to_dev(struct dhd_bus *bus)
@@ -23260,6 +23656,7 @@
{
dhd_info_t *dhd_info = NULL;
dhd_pub_t *dhdp = NULL;
+ unsigned long flags = 0;
/* Ignore compiler warnings due to -Werror=cast-qual */
GCC_DIAGNOSTIC_PUSH_SUPPRESS_CAST();
@@ -23271,6 +23668,12 @@
return;
}
+ DHD_GENERAL_LOCK(dhdp, flags);
+ DHD_BUS_BUSY_SET_IN_SYSFS_DUMP(dhdp);
+ DHD_GENERAL_UNLOCK(dhdp, flags);
dhd_log_dump_trigger(dhdp, CMD_DEFAULT);
+ DHD_GENERAL_LOCK(dhdp, flags);
+ DHD_BUS_BUSY_CLEAR_IN_SYSFS_DUMP(dhdp);
+ DHD_GENERAL_UNLOCK(dhdp, flags);
}
#endif /* DHD_FILE_DUMP_EVENT && DHD_FW_COREDUMP */
diff --git a/dhd_linux.h b/dhd_linux.h
index b234d14..6931fd3 100644
--- a/dhd_linux.h
+++ b/dhd_linux.h
@@ -1,7 +1,7 @@
/*
* DHD Linux header file (dhd_linux exports for cfg80211 and other components)
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -535,8 +535,8 @@
extern void dhd_reset_tcpsync_info_by_ifp(dhd_if_t *ifp);
extern void dhd_reset_tcpsync_info_by_dev(struct net_device *dev);
#endif /* DHDTCPSYNC_FLOOD_BLK */
-extern void dhd_set_del_in_progress(dhd_pub_t * dhdp, struct net_device * ndev);
-extern void dhd_clear_del_in_progress(dhd_pub_t * dhdp, struct net_device * ndev);
+extern void dhd_set_del_in_progress(dhd_pub_t *dhdp, struct net_device * ndev);
+extern void dhd_clear_del_in_progress(dhd_pub_t *dhdp, struct net_device * ndev);
#ifdef PCIE_FULL_DONGLE
extern void dhd_net_del_flowrings_sta(dhd_pub_t * dhd, struct net_device * ndev);
#endif /* PCIE_FULL_DONGLE */
diff --git a/dhd_linux_exportfs.c b/dhd_linux_exportfs.c
index 5c299c1..90ed554 100644
--- a/dhd_linux_exportfs.c
+++ b/dhd_linux_exportfs.c
@@ -2,7 +2,7 @@
* Broadcom Dongle Host Driver (DHD), Linux-specific network interface
* Basically selected code segments from usb-cdc.c and usb-rndis.c
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -30,6 +30,7 @@
#include <dhd.h>
#include <dhd_dbg.h>
#include <dhd_linux_priv.h>
+#include <dhd_proto.h>
#ifdef PWRSTATS_SYSFS
#include <wldev_common.h>
#endif /* PWRSTATS_SYSFS */
@@ -803,6 +804,40 @@
}
#endif /* PWRSTATS_SYSFS */
+static ssize_t
+show_tcm_test_mode(struct dhd_info *dev, char *buf)
+{
+ ssize_t ret = 0;
+ unsigned long mode;
+
+ mode = dhd_tcm_test_mode;
+ ret = scnprintf(buf, PAGE_SIZE - 1, "%lu \n",
+ mode);
+ return ret;
+}
+
+static ssize_t
+set_tcm_test_mode(struct dhd_info *dev, const char *buf, size_t count)
+{
+ unsigned long mode;
+
+ mode = bcm_strtoul(buf, NULL, 10);
+
+ sscanf(buf, "%lu", &mode);
+ if (mode > TCM_TEST_MODE_ALWAYS) {
+ return -EINVAL;
+ }
+
+ /* reset with the mode change */
+ if (dhd_tcm_test_mode != mode) {
+ dhd_tcm_test_status = TCM_TEST_NOT_RUN;
+ }
+
+ dhd_tcm_test_mode = (uint)mode;
+
+ return count;
+}
+
/*
* Generic Attribute Structure for DHD.
* If we have to add a new sysfs entry under /sys/bcm-dhd/, we have
@@ -856,6 +891,9 @@
__ATTR(power_stats, 0664, show_pwrstats_path, NULL);
#endif /* PWRSTATS_SYSFS */
+static struct dhd_attr dhd_attr_tcm_test_mode =
+ __ATTR(tcm_test_mode, 0660, show_tcm_test_mode, set_tcm_test_mode);
+
#define to_dhd(k) container_of(k, struct dhd_info, dhd_kobj)
#define to_attr(a) container_of(a, struct dhd_attr, attr)
@@ -1203,21 +1241,6 @@
__ATTR(cid, 0660, show_cid_info, set_cid_info);
#endif /* USE_CID_CHECK || USE_DIRECT_VID_TAG */
-#if defined(CONFIG_WIFI_BROADCOM_COB) && defined(BCM4389_CHIP_DEF)
-int otpinfo_val = -1;
-
-static ssize_t
-show_otp_info(struct dhd_info *dev, char *buf)
-{
- ssize_t ret = 0;
- ret = snprintf(buf, PAGE_SIZE-1, "%d\n", otpinfo_val);
- return ret;
-}
-
-static struct dhd_attr dhd_attr_otpinfo =
- __ATTR(otp, 0660, show_otp_info, NULL);
-#endif /* CONFIG_WIFI_BROADCOM_COB && BCM4389_CHIP_DEF */
-
#if defined(GEN_SOFTAP_INFO_FILE)
char softapinfostr[SOFTAP_INFO_BUF_SZ];
static ssize_t
@@ -1742,6 +1765,37 @@
__ATTR(l1ss_enab, 0660, show_l1ss_enab, dhd_set_l1ss_enab);
#endif /* PCIE_FULL_DONGLE */
+#ifdef RPM_FAST_TRIGGER
+static ssize_t
+dhd_show_fast_rpm_thresh(struct dhd_info *dev, char *buf)
+{
+ ssize_t ret = 0;
+ unsigned long val;
+
+ val = dhd_fast_runtimepm_ms;
+ ret = scnprintf(buf, PAGE_SIZE - 1, "%lu \n", val);
+ return ret;
+}
+
+static ssize_t
+dhd_set_fast_rpm_thresh(struct dhd_info *dev, const char *buf, size_t count)
+{
+ unsigned long val;
+
+ val = bcm_strtoul(buf, NULL, 10);
+
+ sscanf(buf, "%lu", &val);
+ /* Ensure fast RPM threashold is lesser than regular RPM threshold */
+ if (val == 0 || val >= dhd_runtimepm_ms) {
+ return -EINVAL;
+ }
+ dhd_fast_runtimepm_ms = val;
+ return count;
+}
+static struct dhd_attr dhd_attr_fast_rpm_thresh =
+__ATTR(fast_rpm_thresh, 0660, dhd_show_fast_rpm_thresh, dhd_set_fast_rpm_thresh);
+#endif /* RPM_FAST_TRIGGER */
+
#if defined(CUSTOM_CONTROL_HE_ENAB)
static ssize_t
show_control_he_enab(struct dhd_info *dev, char *buf)
@@ -2228,10 +2282,11 @@
&dhd_attr_aspm_enab.attr,
&dhd_attr_l1ss_enab.attr,
#endif /* PCIE_FULL_DONGLE */
-#if defined(CONFIG_WIFI_BROADCOM_COB) && defined(BCM4389_CHIP_DEF)
- &dhd_attr_otpinfo.attr,
-#endif /* CONFIG_WIFI_BROADCOM_COB && BCM4389_CHIP_DEF */
+#ifdef RPM_FAST_TRIGGER
+ &dhd_attr_fast_rpm_thresh.attr,
+#endif /* RPM_FAST_TRIGGER */
&dhd_attr_sig_path.attr,
+ &dhd_attr_tcm_test_mode.attr,
NULL
};
@@ -2753,6 +2808,197 @@
};
#endif /* DHD_LB */
+/*
+ * ************ DPC BOUNDS *************
+ */
+
+static ssize_t
+show_ctrl_cpl_post_bound(struct dhd_info *dev, char *buf)
+{
+ ssize_t ret = 0;
+
+ ret = scnprintf(buf, PAGE_SIZE - 1, "%d\n",
+ dhd_prot_get_ctrl_cpl_post_bound(&dev->pub));
+ return ret;
+}
+
+static ssize_t
+set_ctrl_cpl_post_bound(struct dhd_info *dev, const char *buf, size_t count)
+{
+ int val;
+
+ val = (uint32)bcm_atoi(buf);
+ if (val <= 0)
+ {
+ DHD_ERROR(("%s : invalid ctrl_cpl_post_bound %u\n",
+ __FUNCTION__, val));
+ return count;
+ }
+
+ dhd_prot_set_ctrl_cpl_post_bound(&dev->pub, val);
+ return count;
+}
+
+static ssize_t
+show_tx_post_bound(struct dhd_info *dev, char *buf)
+{
+ ssize_t ret = 0;
+
+ ret = scnprintf(buf, PAGE_SIZE - 1, "%d\n", dhd_prot_get_tx_post_bound(&dev->pub));
+ return ret;
+}
+
+static ssize_t
+set_tx_post_bound(struct dhd_info *dev, const char *buf, size_t count)
+{
+ int val;
+
+ val = (uint32)bcm_atoi(buf);
+ if (val <= 0)
+ {
+ DHD_ERROR(("%s : invalid tx_post_bound %u\n",
+ __FUNCTION__, val));
+ return count;
+ }
+
+ dhd_prot_set_tx_post_bound(&dev->pub, val);
+ return count;
+}
+
+static ssize_t
+show_rx_cpl_post_bound(struct dhd_info *dev, char *buf)
+{
+ ssize_t ret = 0;
+
+ ret = scnprintf(buf, PAGE_SIZE - 1, "%d\n",
+ dhd_prot_get_rx_cpl_post_bound(&dev->pub));
+ return ret;
+}
+
+static ssize_t
+set_rx_cpl_post_bound(struct dhd_info *dev, const char *buf, size_t count)
+{
+ int val;
+
+ val = (uint32)bcm_atoi(buf);
+ if (val <= 0)
+ {
+ DHD_ERROR(("%s : invalid rx_cpl_post_bound %u\n",
+ __FUNCTION__, val));
+ return count;
+ }
+
+ dhd_prot_set_rx_cpl_post_bound(&dev->pub, val);
+ return count;
+}
+
+static ssize_t
+show_tx_cpl_bound(struct dhd_info *dev, char *buf)
+{
+ ssize_t ret = 0;
+
+ ret = scnprintf(buf, PAGE_SIZE - 1, "%d\n", dhd_prot_get_tx_cpl_bound(&dev->pub));
+ return ret;
+}
+
+static ssize_t
+set_tx_cpl_bound(struct dhd_info *dev, const char *buf, size_t count)
+{
+ int val;
+
+ val = (uint32)bcm_atoi(buf);
+ if (val <= 0)
+ {
+ DHD_ERROR(("%s : invalid tx_cpl_bound %u\n",
+ __FUNCTION__, val));
+ return count;
+ }
+
+ dhd_prot_set_tx_cpl_bound(&dev->pub, val);
+ return count;
+}
+
+static struct dhd_attr dhd_attr_ctrl_cpl_post_bound =
+__ATTR(ctrl_cpl_post_bound, 0660, show_ctrl_cpl_post_bound, set_ctrl_cpl_post_bound);
+static struct dhd_attr dhd_attr_tx_post_bound =
+__ATTR(tx_post_bound, 0660, show_tx_post_bound, set_tx_post_bound);
+static struct dhd_attr dhd_attr_rx_cpl_post_bound =
+__ATTR(rx_cpl_post_bound, 0660, show_rx_cpl_post_bound, set_rx_cpl_post_bound);
+static struct dhd_attr dhd_attr_tx_cpl_bound =
+__ATTR(tx_cpl_bound, 0660, show_tx_cpl_bound, set_tx_cpl_bound);
+
+static struct attribute *debug_dpc_bounds_attrs[] = {
+ &dhd_attr_tx_cpl_bound.attr,
+ &dhd_attr_rx_cpl_post_bound.attr,
+ &dhd_attr_tx_post_bound.attr,
+ &dhd_attr_ctrl_cpl_post_bound.attr,
+ NULL
+};
+
+#define to_dhd_dpc_bounds(k) container_of(k, struct dhd_info, dhd_dpc_bounds_kobj)
+
+/*
+ * wifi/dpc_bounds kobject show function, the "attr" attribute specifices to which
+ * node under "sys/wifi/dpc_bounds" the show function is called.
+ */
+static ssize_t dhd_dpc_bounds_show(struct kobject *kobj, struct attribute *attr, char *buf)
+{
+ dhd_info_t *dhd;
+ struct dhd_attr *d_attr;
+ int ret;
+
+ GCC_DIAGNOSTIC_PUSH_SUPPRESS_CAST();
+ dhd = to_dhd_dpc_bounds(kobj);
+ d_attr = to_attr(attr);
+ GCC_DIAGNOSTIC_POP();
+
+ if (d_attr->show)
+ ret = d_attr->show(dhd, buf);
+ else
+ ret = -EIO;
+
+ return ret;
+}
+
+/*
+ * wifi/dpc_bounds kobject store function, the "attr" attribute specifices to which
+ * node under "sys/wifi/dpc_bounds" the store function is called.
+ */
+static ssize_t dhd_dpc_bounds_store(struct kobject *kobj, struct attribute *attr,
+ const char *buf, size_t count)
+{
+ dhd_info_t *dhd;
+ struct dhd_attr *d_attr;
+ int ret;
+
+ GCC_DIAGNOSTIC_PUSH_SUPPRESS_CAST();
+ dhd = to_dhd_dpc_bounds(kobj);
+ d_attr = to_attr(attr);
+ GCC_DIAGNOSTIC_POP();
+
+ if (d_attr->store)
+ ret = d_attr->store(dhd, buf, count);
+ else
+ ret = -EIO;
+
+ return ret;
+
+}
+
+static struct sysfs_ops dhd_sysfs_dpc_bounds_ops = {
+ .show = dhd_dpc_bounds_show,
+ .store = dhd_dpc_bounds_store,
+};
+
+static struct kobj_type dhd_dpc_bounds_ktype = {
+ .sysfs_ops = &dhd_sysfs_dpc_bounds_ops,
+ .default_attrs = debug_dpc_bounds_attrs,
+};
+
+/*
+ * *************************************
+ */
+
/* Create a kobject and attach to sysfs interface */
int dhd_sysfs_init(dhd_info_t *dhd)
{
@@ -2782,13 +3028,22 @@
&dhd_lb_ktype, &dhd->dhd_kobj, "lb");
if (ret) {
kobject_put(&dhd->dhd_lb_kobj);
- DHD_ERROR(("%s(): Unable to allocate kobject \r\n", __FUNCTION__));
+ DHD_ERROR(("%s(): Unable to allocate kobject for 'lb'\r\n", __FUNCTION__));
return ret;
}
kobject_uevent(&dhd->dhd_lb_kobj, KOBJ_ADD);
#endif /* DHD_LB */
+ /* DPC bounds */
+ ret = kobject_init_and_add(&dhd->dhd_dpc_bounds_kobj,
+ &dhd_dpc_bounds_ktype, &dhd->dhd_kobj, "dpc_bounds");
+ if (ret) {
+ kobject_put(&dhd->dhd_dpc_bounds_kobj);
+ DHD_ERROR(("%s(): Unable to allocate kobject for 'dpc_bounds'\r\n", __FUNCTION__));
+ return ret;
+ }
+ kobject_uevent(&dhd->dhd_dpc_bounds_kobj, KOBJ_ADD);
return ret;
}
@@ -2804,7 +3059,10 @@
kobject_put(&dhd->dhd_lb_kobj);
#endif /* DHD_LB */
- /* Releae the kobject */
+ /* DPC bounds */
+ kobject_put(&dhd->dhd_dpc_bounds_kobj);
+
+ /* Release the kobject */
kobject_put(&dhd->dhd_kobj);
}
diff --git a/dhd_linux_lb.c b/dhd_linux_lb.c
index c357e81..bfb0c9b 100644
--- a/dhd_linux_lb.c
+++ b/dhd_linux_lb.c
@@ -2,7 +2,7 @@
* Broadcom Dongle Host Driver (DHD), Linux-specific network interface
* Basically selected code segments from usb-cdc.c and usb-rndis.c
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -251,6 +251,12 @@
{
dhd_info_t *dhd = g_dhd_pub->info;
+ if (!dhd || !(dhd->dhd_state & DHD_ATTACH_STATE_LB_ATTACH_DONE)) {
+ DHD_ERROR(("%s(): LB data is not initialized yet.\n",
+ __FUNCTION__));
+ return 0;
+ }
+
DHD_INFO(("%s(): \r\n cpu:%d", __FUNCTION__, cpu));
DHD_LB_STATS_INCR(dhd->cpu_online_cnt[cpu]);
cpumask_set_cpu(cpu, dhd->cpumask_curr_avail);
@@ -263,6 +269,12 @@
{
dhd_info_t *dhd = g_dhd_pub->info;
+ if (!dhd || !(dhd->dhd_state & DHD_ATTACH_STATE_LB_ATTACH_DONE)) {
+ DHD_ERROR(("%s(): LB data is not initialized yet.\n",
+ __FUNCTION__));
+ return 0;
+ }
+
DHD_INFO(("%s(): \r\n cpu:%d", __FUNCTION__, cpu));
DHD_LB_STATS_INCR(dhd->cpu_offline_cnt[cpu]);
cpumask_clear_cpu(cpu, dhd->cpumask_curr_avail);
@@ -696,7 +708,7 @@
}
dhdp->rxpath_mem = rx_path_memory_usage;
- bcm_bprintf(strbuf, "\n rxbufpost_alloc_sz: %d rx_post_active: %d rx_cmpl_active: %d "
+ bcm_bprintf(strbuf, "\nrxbufpost_alloc_sz: %d rx_post_active: %d rx_cmpl_active: %d "
"emerge_queue_len: %d pend_queue_len: %d napi_queue_len: %d"
" process_queue_len: %d\n",
rxbufpost_alloc_sz, rx_post_active, rx_cmpl_active,
@@ -724,6 +736,7 @@
return;
}
+ bcm_bprintf(strbuf, "\nLoad Balancing/NAPI stats:\n==========================\n");
bcm_bprintf(strbuf, "\ncpu_online_cnt:\n");
dhd_lb_stats_dump_cpu_array(strbuf, dhd->cpu_online_cnt);
@@ -747,6 +760,13 @@
dhd_lb_stats_dump_histo(dhdp, strbuf, dhd->napi_rx_hist);
bcm_bprintf(strbuf, "\nNAPI poll latency stats ie from napi schedule to napi execution\n");
dhd_lb_stats_dump_napi_latency(dhdp, strbuf, dhd->napi_latency);
+
+ bcm_bprintf(strbuf, "\nlb_rxp_stop_thr_hitcnt: %llu lb_rxp_strt_thr_hitcnt: %llu"
+ " rx_dma_stall_hc_ignore_cnt: %llu\n",
+ dhdp->lb_rxp_stop_thr_hitcnt, dhdp->lb_rxp_strt_thr_hitcnt,
+ dhdp->rx_dma_stall_hc_ignore_cnt);
+ bcm_bprintf(strbuf, "\nlb_rxp_napi_sched_cnt: %llu lb_rxp_napi_omplete_cnt: %llu\n",
+ dhdp->lb_rxp_napi_sched_cnt, dhdp->lb_rxp_napi_complete_cnt);
#endif /* DHD_LB_RXP */
#ifdef DHD_LB_TXP
@@ -756,6 +776,7 @@
bcm_bprintf(strbuf, "\ntx_start_percpu_run_cnt:\n");
dhd_lb_stats_dump_cpu_array(strbuf, dhd->tx_start_percpu_run_cnt);
#endif /* DHD_LB_TXP */
+ bcm_bprintf(strbuf, "\n");
}
void dhd_lb_stats_update_napi_latency(uint64 *bin, uint32 latency)
@@ -1125,31 +1146,6 @@
*/
}
-/**
- * dhd_napi_schedule_on - API to schedule on a desired CPU core a NET_RX_SOFTIRQ
- * action after placing the dhd's rx_process napi object in the the remote CPU's
- * softnet data's poll_list.
- *
- * @dhd: dhd_info which has the rx_process napi object
- * @on_cpu: desired remote CPU id
- */
-static INLINE int
-dhd_napi_schedule_on(dhd_info_t *dhd, int on_cpu)
-{
- int wait = 0; /* asynchronous IPI */
- DHD_INFO(("%s dhd<%p> napi<%p> on_cpu<%d>\n",
- __FUNCTION__, dhd, &dhd->rx_napi_struct, on_cpu));
-
- if (smp_call_function_single(on_cpu, dhd_napi_schedule, dhd, wait)) {
- DHD_ERROR(("%s smp_call_function_single on_cpu<%d> failed\n",
- __FUNCTION__, on_cpu));
- }
-
- DHD_LB_STATS_INCR(dhd->napi_sched_cnt);
-
- return 0;
-}
-
/*
* Call get_online_cpus/put_online_cpus around dhd_napi_schedule_on
* Why should we do this?
@@ -1345,7 +1341,7 @@
#endif /* DHD_LB_TXP */
#ifdef DHD_LB_TXP
-#define DHD_LB_TXBOUND 64
+#define DHD_LB_TXBOUND 32
/*
* Function that performs the TX processing on a given CPU
*/
diff --git a/dhd_linux_pktdump.c b/dhd_linux_pktdump.c
old mode 100755
new mode 100644
index e1d4809..449f389
--- a/dhd_linux_pktdump.c
+++ b/dhd_linux_pktdump.c
@@ -1,7 +1,7 @@
/*
* Packet dump helper functions
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -39,6 +39,11 @@
#include <bcmicmp.h>
#include <bcmigmp.h>
#include <dhd_linux_pktdump.h>
+#ifdef WL_CFGVENDOR_CUST_ADVLOG
+#include <wl_cfg80211.h>
+#include <wl_cfgvendor.h>
+#include <dhd_flowring.h>
+#endif /* WL_CFGVENDOR_CUST_ADVLOG */
#define DHD_PKTDUMP(arg) DHD_ERROR(arg)
#define DHD_PKTDUMP_MEM(arg) DHD_ERROR_MEM(arg)
@@ -165,18 +170,27 @@
"INVALID"
};
-static const char tx_pktfate[][30] = {
- "TX_PKT_FATE_ACKED", /* 0: WLFC_CTL_PKTFLAG_DISCARD */
- "TX_PKT_FATE_FW_D11SUPPRESS", /* 1: WLFC_CTL_PKTFLAG_D11SUPPRESS */
- "TX_PKT_FATE_FW_WLSUPPRESS", /* 2: WLFC_CTL_PKTFLAG_WLSUPPRESS */
- "TX_PKT_FATE_FW_TOSSED_BYWLC", /* 3: WLFC_CTL_PKTFLAG_TOSSED_BYWLC */
- "TX_PKT_FATE_SENT_NOACK", /* 4: WLFC_CTL_PKTFLAG_DISCARD_NOACK */
- "TX_PKT_FATE_FW_SUPPRESS_ACKED", /* 5: WLFC_CTL_PKTFLAG_SUPPRESS_ACKED */
- "TX_PKT_FATE_FW_DROP_EXPTIME", /* 6: WLFC_CTL_PKTFLAG_EXPIRED */
- "TX_PKT_FATE_FW_DROP_OTHER", /* 7: WLFC_CTL_PKTFLAG_DROPPED */
- "TX_PKT_FATE_FW_PKT_FREE", /* 8: WLFC_CTL_PKTFLAG_MKTFREE */
- "TX_PKT_FATE_FW_MAX_SUP_RETR", /* 9: WLFC_CTL_PKTFLAG_MAX_SUP_RETR */
- "TX_PKT_FATE_FW_FORCED_EXPIRED" /* 10: WLFC_CTL_PKTFLAG_FORCED_EXPIRED */
+#if defined(DHD_DNS_DUMP) || defined(DHD_ARP_DUMP) || defined(DHD_ICMP_DUMP) || \
+ defined(DHD_DHCP_DUMP) || defined(DHD_8021X_DUMP) || defined(DHD_PKTDUMP_ROAM)
+#define DHD_PKTFATE_STR_MAX 30
+#define DHD_PKTFATE_EX_STR_MAX 10
+typedef struct dhd_tx_pktfate_entry {
+ const char reason[DHD_PKTFATE_STR_MAX];
+ const char ex[DHD_PKTFATE_EX_STR_MAX];
+} dhd_tx_pktfate_entry_t;
+
+static dhd_tx_pktfate_entry_t tx_pktfate[] = {
+ {"TX_PKT_FATE_ACKED", "ACK"}, /* 0: WLFC_CTL_PKTFLAG_DISCARD */
+ {"TX_PKT_FATE_FW_D11SUPPRESS", "TX_FAIL"}, /* 1: WLFC_CTL_PKTFLAG_D11SUPPRESS */
+ {"TX_PKT_FATE_FW_WLSUPPRESS", "TX_FAIL"}, /* 2: WLFC_CTL_PKTFLAG_WLSUPPRESS */
+ {"TX_PKT_FATE_FW_TOSSED_BYWLC", "TX_FAIL"}, /* 3: WLFC_CTL_PKTFLAG_TOSSED_BYWLC */
+ {"TX_PKT_FATE_SENT_NOACK", "NO_ACK"}, /* 4: WLFC_CTL_PKTFLAG_DISCARD_NOACK */
+ {"TX_PKT_FATE_FW_SUPPRESS_ACKED", "TX_FAIL"}, /* 5: WLFC_CTL_PKTFLAG_SUPPRESS_ACKED */
+ {"TX_PKT_FATE_FW_DROP_EXPTIME", "TX_FAIL"}, /* 6: WLFC_CTL_PKTFLAG_EXPIRED */
+ {"TX_PKT_FATE_FW_DROP_OTHER", "TX_FAIL"}, /* 7: WLFC_CTL_PKTFLAG_DROPPED */
+ {"TX_PKT_FATE_FW_PKT_FREE", "TX_FAIL"}, /* 8: WLFC_CTL_PKTFLAG_MKTFREE */
+ {"TX_PKT_FATE_FW_MAX_SUP_RETR", "TX_FAIL"}, /* 9: WLFC_CTL_PKTFLAG_MAX_SUP_RETR */
+ {"TX_PKT_FATE_FW_FORCED_EXPIRED", "TX_FAIL"}, /* 10: WLFC_CTL_PKTFLAG_FORCED_EXPIRED */
};
#define DBGREPLAY " Replay Counter: %02x%02x%02x%02x%02x%02x%02x%02x"
@@ -191,9 +205,16 @@
#define TXFATE_FMT " TX_PKTHASH:0x%X TX_PKT_FATE:%s"
#define TX_PKTHASH(pkthash) ((pkthash) ? (*pkthash) : (0))
#define TX_FATE_STR(fate) (((*fate) >= (0) && (*fate) <= (WLFC_CTL_PKTFLAG_FORCED_EXPIRED)) ?\
- (tx_pktfate[(*fate)]) : "TX_PKT_FATE_UNKNOWN")
+ (tx_pktfate[(*fate)].reason) : "TX_PKT_FATE_UNKNOWN")
+#define TX_FATE_STR_EX(fate) (((*fate) <= (WLFC_CTL_PKTFLAG_FORCED_EXPIRED)) ? \
+ (tx_pktfate[(*fate)].ex) : NULL)
#define TX_FATE(fate) ((fate) ? (TX_FATE_STR(fate)) : "N/A")
+#define TX_FATE_EX(fate) ((fate) ? (TX_FATE_STR_EX(fate)) : NULL)
#define TX_FATE_ACKED(fate) ((fate) ? ((*fate) == (WLFC_CTL_PKTFLAG_DISCARD)) : (0))
+#endif /*
+ * DHD_DNS_DUMP || DHD_ARP_DUMP || DHD_ICMP_DUMP ||
+ * DHD_DHCP_DUMP || DHD_8021X_DUMP || DHD_PKTDUMP_ROAM
+ */
#define EAP_PRINT(str) \
do { \
@@ -874,7 +895,7 @@
return TRUE;
}
-#ifdef DHD_DHCP_DUMP
+#if defined(DHD_DHCP_DUMP) || defined(WL_CFGVENDOR_CUST_ADVLOG)
#define BOOTP_CHADDR_LEN 16
#define BOOTP_SNAME_LEN 64
#define BOOTP_FILE_LEN 128
@@ -890,18 +911,6 @@
#define DHCP_MSGTYPE_RELEASE 7
#define DHCP_MSGTYPE_INFORM 8
-#define DHCP_PRINT(str) \
- do { \
- if (tx) { \
- DHD_PKTDUMP((str " %s[%s][%s] [TX] -" TXFATE_FMT "\n", \
- typestr, opstr, ifname, \
- TX_PKTHASH(pkthash), TX_FATE(pktfate))); \
- } else { \
- DHD_PKTDUMP((str " %s[%s][%s] [RX]\n", \
- typestr, opstr, ifname)); \
- } \
- } while (0)
-
typedef struct bootp_fmt {
struct ipv4_hdr iph;
struct bcmudp_hdr udph;
@@ -921,6 +930,20 @@
uint8 file_name[BOOTP_FILE_LEN];
uint8 options[BOOTP_MIN_DHCP_OPT_LEN];
} PACKED_STRUCT bootp_fmt_t;
+#endif /* DHD_DHCP_DUMP || WL_CFGVENDOR_CUST_ADVLOG */
+
+#ifdef DHD_DHCP_DUMP
+#define DHCP_PRINT(str) \
+ do { \
+ if (tx) { \
+ DHD_PKTDUMP((str " %s[%s][%s] [TX] -" TXFATE_FMT "\n", \
+ typestr, opstr, ifname, \
+ TX_PKTHASH(pkthash), TX_FATE(pktfate))); \
+ } else { \
+ DHD_PKTDUMP((str " %s[%s][%s] [RX]\n", \
+ typestr, opstr, ifname)); \
+ } \
+ } while (0)
#define MAX_DHCP_OPS_STR 3
#define MAX_DHCP_TYPES_STR 9
@@ -934,14 +957,14 @@
};
#define DHCP_OPS_STR(ops) ((ops < MAX_DHCP_OPS_STR) ? \
- (dhcp_ops[ops]) : "UNKNOWN_DHCP_OPS")
+ (dhcp_ops[ops]) : "UNKNOWN_DHCP_OPS")
#define DHCP_TYPES_STR(type) ((type < MAX_DHCP_TYPES_STR) ? \
- (dhcp_types[type]) : "UNKNOWN_DHCP_TYPE")
+ (dhcp_types[type]) : "UNKNOWN_DHCP_TYPE")
#ifdef DHD_STATUS_LOGGING
#define MAX_DHCP_TYPES_STAT 9
#define DHCP_TYPES_STAT(type) ((type < MAX_DHCP_TYPES_STAT) ? \
- (dhcp_types_stat[type]) : ST(INVALID))
+ (dhcp_types_stat[type]) : ST(INVALID))
static const int dhcp_types_stat[MAX_DHCP_TYPES_STAT] = {
ST(INVALID), ST(DHCP_DISCOVER), ST(DHCP_OFFER), ST(DHCP_REQUEST),
ST(DHCP_DECLINE), ST(DHCP_ACK), ST(DHCP_NAK), ST(DHCP_RELEASE),
@@ -1370,3 +1393,219 @@
}
}
#endif /* DHD_RX_DUMP */
+
+#ifdef WL_CFGVENDOR_CUST_ADVLOG
+typedef struct dhd_advlog_arr_map_entry {
+ uint32 avglog_type;
+ dhd_advlog_map_entry_t *arr;
+ uint32 arr_len;
+} dhd_advlog_arr_map_entry_t;
+
+typedef enum dhd_advlog_type {
+ DHD_ADVLOG_DHCP_TX = 0,
+ DHD_ADVLOG_DHCP_RX = 1,
+ DHD_ADVLOG_EAP = 2,
+ DHD_ADVLOG_EAPOL = 3,
+ DHD_ADVLOG_LAST = 4
+} dhd_advlog_type_t;
+
+static dhd_advlog_map_entry_t eap_type_map[] = {
+ {EAP_TYPE_IDENT, "Identity"},
+ {EAP_TYPE_TLS, "TLS"},
+ {EAP_TYPE_LEAP, "LEAP"},
+ {EAP_TYPE_TTLS, "TTLS"},
+ {EAP_TYPE_AKA, "AKA"},
+ {EAP_TYPE_PEAP, "PEAP"},
+ {EAP_TYPE_FAST, "FAST"},
+ {EAP_TYPE_PSK, "PSK"},
+ {EAP_TYPE_AKAP, "AKAP"},
+};
+
+static dhd_advlog_map_entry_t eap_advlog_map[] = {
+ {EAP_CODE_REQUEST, "[EAP] REQ type=%s len=%d"},
+ {EAP_CODE_RESPONSE, "[EAP] RESP type=%s len=%d tx_status=%s"},
+ {EAP_CODE_SUCCESS, "[EAP] SUCC"},
+ {EAP_CODE_FAILURE, "[EAP] FAIL"},
+};
+
+static dhd_advlog_map_entry_t dhcp_tx_advlog_map[] = {
+ {DHCP_MSGTYPE_DISCOVER, "[DHCP] DISCOVER tx_status=%s"},
+ {DHCP_MSGTYPE_REQUEST, "[DHCP] REQUEST tx_status=%s"},
+};
+
+static dhd_advlog_map_entry_t dhcp_rx_advlog_map[] = {
+ {DHCP_MSGTYPE_OFFER, "[DHCP] OFFER"},
+ {DHCP_MSGTYPE_ACK, "[DHCP] ACK"},
+ {DHCP_MSGTYPE_NAK, "[DHCP] NAK"},
+};
+
+static dhd_advlog_map_entry_t eapol_advlog_map[] = {
+ {EAPOL_4WAY_M1, "[EAPOL] 4WAY M1"},
+ {EAPOL_4WAY_M2, "[EAPOL] 4WAY M2 tx_status=%s"},
+ {EAPOL_4WAY_M3, "[EAPOL] 4WAY M3"},
+ {EAPOL_4WAY_M4, "[EAPOL] 4WAY M4 tx_status=%s"},
+ {EAPOL_GROUPKEY_M1, "[EAPOL] GTK M1"},
+ {EAPOL_GROUPKEY_M2, "[EAPOL] GTK M2 tx_status=%s"},
+};
+
+static dhd_advlog_arr_map_entry_t advlog_map_arr[] = {
+ {DHD_ADVLOG_DHCP_TX, dhcp_tx_advlog_map, ARRAY_SIZE(dhcp_tx_advlog_map)},
+ {DHD_ADVLOG_DHCP_RX, dhcp_rx_advlog_map, ARRAY_SIZE(dhcp_rx_advlog_map)},
+ {DHD_ADVLOG_EAP, eap_advlog_map, ARRAY_SIZE(eap_advlog_map)},
+ {DHD_ADVLOG_EAPOL, eapol_advlog_map, ARRAY_SIZE(eapol_advlog_map)},
+};
+
+const char* get_advlog_val(dhd_advlog_map_entry_t *arr, uint32 arr_len, int tag)
+{
+ int i;
+ for (i = 0; i < arr_len; i++) {
+ if (tag == arr[i].key) {
+ return arr[i].val;
+ }
+ }
+ return NULL;
+}
+
+static int get_dhcp_type(uint8 *pktdata)
+{
+ bootp_fmt_t *b = (bootp_fmt_t *)&pktdata[ETHER_HDR_LEN];
+ uint8 *ptr, *opt, *end = (uint8 *) b + ntohs(b->iph.tot_len);
+ int dhcp_type = 0, len, opt_len;
+
+ len = ntohs(b->udph.len) - sizeof(struct bcmudp_hdr);
+ opt_len = len - (sizeof(*b) - sizeof(struct ipv4_hdr) -
+ sizeof(struct bcmudp_hdr) - sizeof(b->options));
+
+ /* parse bootp options */
+ if (opt_len >= BOOTP_MAGIC_COOKIE_LEN &&
+ !memcmp(b->options, bootp_magic_cookie, BOOTP_MAGIC_COOKIE_LEN)) {
+ ptr = &b->options[BOOTP_MAGIC_COOKIE_LEN];
+ while (ptr < end && *ptr != 0xff) {
+ opt = ptr++;
+ if (*opt == 0) {
+ continue;
+ }
+ ptr += *ptr + 1;
+ if (ptr >= end) {
+ break;
+ }
+ if (*opt == DHCP_OPT_MSGTYPE) {
+ if (opt[1]) {
+ dhcp_type = opt[2];
+ return dhcp_type;
+ }
+ }
+ }
+ }
+ return BCME_ERROR;
+}
+
+static int dhd_send_supp(uint32 avglog_type, int arg_tag, int arg_type, uint32 pktlen,
+ bool tx, uint16 *pktfate)
+{
+ const char *type_str = NULL;
+ const char *fmt_str = NULL;
+ dhd_advlog_map_entry_t *fmt_arr;
+ uint32 fmt_arr_len;
+
+ if (avglog_type >= DHD_ADVLOG_LAST) {
+ DHD_ERROR(("%s incorrect array index type:%d tag:%d\n",
+ __func__, avglog_type, arg_tag));
+ return BCME_ERROR;
+ }
+ if ((arg_type && !pktlen) || (!arg_type && pktlen)) {
+ DHD_ERROR(("%s Not expected value pair type:%d tag:%d pktlen:%u\n",
+ __func__, avglog_type, arg_tag, pktlen));
+ return BCME_ERROR;
+ }
+ if (arg_tag <= 0) {
+ DHD_ERROR(("%s Invalid tag number type:%d tag:%d\n",
+ __func__, avglog_type, arg_tag));
+ return BCME_ERROR;
+ }
+
+ /* Get the format string corresponding to the type */
+ fmt_arr = advlog_map_arr[avglog_type].arr;
+ fmt_arr_len = advlog_map_arr[avglog_type].arr_len;
+ fmt_str = get_advlog_val(fmt_arr, fmt_arr_len, arg_tag);
+ if (!fmt_str) {
+ DHD_ERROR(("%s map arr not found type:%d tag:%d\n",
+ __func__, avglog_type, arg_tag));
+ return BCME_ERROR;
+ }
+
+ /* EAP REQ/RESP */
+ if (arg_type && pktlen) {
+ /* Get Identity/PEAP/FAST/etc string */
+ type_str = get_advlog_val(eap_type_map, ARRAY_SIZE(eap_type_map), arg_type);
+ if (!type_str) {
+ DHD_ERROR(("%s type string not found type:%d tag:%d\n",
+ __func__, avglog_type, arg_tag));
+ return BCME_ERROR;
+ }
+ if (tx && pktfate) {
+ /* EAP RESP */
+ SUPP_ADVLOG((fmt_str, type_str, pktlen, TX_FATE_EX(pktfate)));
+ } else if (!tx) {
+ /* EAP REQ */
+ SUPP_ADVLOG((fmt_str, type_str, pktlen));
+ }
+ } else {
+ if (tx && pktfate) {
+ /* EAPOL M2/M4, GTK M2, DHCP DISC/REQ */
+ SUPP_ADVLOG((fmt_str, TX_FATE_EX(pktfate)));
+ } else if (!tx) {
+ /* EAPOL M1/M3, GTK M1, DHCP OFFER/ACK/NAK, EAP SUCC/FAIL */
+ SUPP_ADVLOG((fmt_str));
+ }
+ }
+ return BCME_OK;
+}
+
+void dhd_send_supp_dhcp(dhd_pub_t *dhdp, int ifidx, uint8 *pktdata, bool tx, uint16 *pktfate)
+{
+ uint32 advlog_type;
+
+ /* Advanced Logging supports only STA mode */
+ if (!DHD_IF_ROLE_STA(dhdp, ifidx)) {
+ return;
+ }
+
+ if (tx) {
+ advlog_type = DHD_ADVLOG_DHCP_TX;
+ } else {
+ advlog_type = DHD_ADVLOG_DHCP_RX;
+ }
+ dhd_send_supp(advlog_type, get_dhcp_type(pktdata), 0, 0, tx, pktfate);
+}
+
+void dhd_send_supp_eap(dhd_pub_t *dhdp, int ifidx, uint8 *pktdata, uint32 pktlen,
+ bool tx, uint16 *pktfate)
+{
+ eapol_header_t *eapol_hdr;
+ eap_header_fmt_t *eap_hdr;
+ uint16 len = 0;
+ uint8 type = 0;
+
+ /* Advanced Logging supports only STA mode */
+ if (!DHD_IF_ROLE_STA(dhdp, ifidx)) {
+ return;
+ }
+
+ eapol_hdr = (eapol_header_t *)pktdata;
+ eap_hdr = (eap_header_fmt_t *)(eapol_hdr->body);
+
+ if (eapol_hdr->type == EAP_PACKET) {
+ /* EAP SUCC/FAIL has no arg to print */
+ if (eap_hdr->code != EAP_CODE_SUCCESS &&
+ eap_hdr->code != EAP_CODE_FAILURE) {
+ type = eap_hdr->type;
+ len = ntoh16(eap_hdr->len);
+ }
+ dhd_send_supp(DHD_ADVLOG_EAP, eap_hdr->code, type, len, tx, pktfate);
+ } else if (eapol_hdr->type == EAPOL_KEY) {
+ dhd_send_supp(DHD_ADVLOG_EAPOL, dhd_is_4way_msg(pktdata),
+ 0, 0, tx, pktfate);
+ }
+}
+#endif /* WL_CFGVENDOR_CUST_ADVLOG */
diff --git a/dhd_linux_pktdump.h b/dhd_linux_pktdump.h
index 0a93a97..3905015 100644
--- a/dhd_linux_pktdump.h
+++ b/dhd_linux_pktdump.h
@@ -1,7 +1,7 @@
/*
* Header file for the Packet dump helper functions
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -58,6 +58,24 @@
PKT_TYPE_IGMP = 7
};
+#ifdef WL_CFGVENDOR_CUST_ADVLOG
+#define DHD_ADVLOG_FMT_MAX 256u
+typedef struct dhd_advlog_map_entry {
+ uint32 key;
+ const char val[DHD_ADVLOG_FMT_MAX];
+} dhd_advlog_map_entry_t;
+
+extern void dhd_send_supp_dhcp(dhd_pub_t *dhdp, int ifidx, uint8 *pktdata,
+ bool tx, uint16 *pktfate);
+extern void dhd_send_supp_eap(dhd_pub_t *dhdp, int ifidx, uint8 *pktdata, uint32 pktlen,
+ bool tx, uint16 *pktfate);
+#else
+static INLINE void dhd_send_supp_dhcp(dhd_pub_t *dhdp, int ifidx, uint8 *pktdata,
+ bool tx, uint16 *pktfate) {}
+static INLINE void dhd_send_supp_eap(dhd_pub_t *dhdp, int ifidx, uint8 *pktdata,
+ uint32 pktlen, bool tx, uint16 *pktfate) {}
+#endif /* WL_CFGVENDOR_CUST_ADVLOG */
+
extern msg_eapol_t dhd_is_4way_msg(uint8 *pktdata);
extern void dhd_dump_pkt(dhd_pub_t *dhd, int ifidx, uint8 *pktdata,
uint32 pktlen, bool tx, uint32 *pkthash, uint16 *pktfate);
diff --git a/dhd_linux_platdev.c b/dhd_linux_platdev.c
index ddd3bc6..e686e65 100644
--- a/dhd_linux_platdev.c
+++ b/dhd_linux_platdev.c
@@ -1,7 +1,7 @@
/*
* Linux platform device for DHD WLAN adapter
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -50,6 +50,11 @@
#define WIFI_PLAT_NAME2 "bcm4329_wlan"
#define WIFI_PLAT_EXT "bcmdhd_wifi_platform"
+#if defined(SUPPORT_MULTIPLE_BOARD_REVISION)
+#include <linux/of.h>
+extern char* dhd_get_device_dt_name(void);
+#endif /* SUPPORT_MULTIPLE_BOARD_REVISION */
+
#ifdef DHD_WIFI_SHUTDOWN
extern void wifi_plat_dev_drv_shutdown(struct platform_device *pdev);
#endif
@@ -597,6 +602,7 @@
}
#ifdef BCMDHD_MODULAR
dhd_wlan_deinit();
+ osl_static_mem_deinit(NULL, NULL);
#ifdef WBRC
wbrc_exit();
#endif /* WBRC */
@@ -686,17 +692,22 @@
#ifdef BCMPCIE
static int dhd_wifi_platform_load_pcie(void)
{
- int err = 0;
int i;
+ int err;
+ int retry;
wifi_adapter_info_t *adapter;
- BCM_REFERENCE(i);
- BCM_REFERENCE(adapter);
-
- if (dhd_wifi_platdata == NULL) {
- /* XXX For x86 Bringup PC or BRIX */
- err = dhd_bus_register();
- } else {
+ if (dhd_wifi_platdata) {
+ /* enumerate PCIe RC */
+ for (i = 0; i < dhd_wifi_platdata->num_adapters; i++) {
+ adapter = &dhd_wifi_platdata->adapters[i];
+ err = wifi_platform_bus_enumerate(adapter, TRUE);
+ if (err) {
+ DHD_ERROR(("failed to enumerate bus %s err=%d",
+ adapter->name, err));
+ return err;
+ }
+ }
#ifdef DHD_SUPPORT_HDM
if (dhd_download_fw_on_driverload || hdm_trigger_init) {
#else
@@ -704,7 +715,7 @@
#endif /* DHD_SUPPORT_HDM */
/* power up all adapters */
for (i = 0; i < dhd_wifi_platdata->num_adapters; i++) {
- int retry = POWERUP_MAX_RETRY;
+ retry = POWERUP_MAX_RETRY;
adapter = &dhd_wifi_platdata->adapters[i];
DHD_ERROR(("Power-up adapter '%s'\n", adapter->name));
@@ -725,17 +736,17 @@
wifi_platform_set_power(adapter,
FALSE, WIFI_TURNOFF_DELAY);
continue;
+ }
+
+ err = wifi_platform_bus_enumerate(adapter, TRUE);
+ if (err) {
+ DHD_ERROR(("failed to enumerate bus %s, "
+ "%d retry left\n",
+ adapter->name, retry));
+ wifi_platform_set_power(adapter, FALSE,
+ WIFI_TURNOFF_DELAY);
} else {
- err = wifi_platform_bus_enumerate(adapter, TRUE);
- if (err) {
- DHD_ERROR(("failed to enumerate bus %s, "
- "%d retry left\n",
- adapter->name, retry));
- wifi_platform_set_power(adapter, FALSE,
- WIFI_TURNOFF_DELAY);
- } else {
- break;
- }
+ break;
}
} while (retry--);
@@ -746,19 +757,18 @@
}
}
}
+ }
- err = dhd_bus_register();
-
- if (err) {
- DHD_ERROR(("%s: pcie_register_driver failed\n", __FUNCTION__));
- if (dhd_download_fw_on_driverload) {
- /* power down all adapters */
- for (i = 0; i < dhd_wifi_platdata->num_adapters; i++) {
- adapter = &dhd_wifi_platdata->adapters[i];
- wifi_platform_bus_enumerate(adapter, FALSE);
- wifi_platform_set_power(adapter,
- FALSE, WIFI_TURNOFF_DELAY);
- }
+ err = dhd_bus_register();
+ if (err) {
+ DHD_ERROR(("%s: dhd_bus_register failed err=%d\n", __FUNCTION__, err));
+ if (dhd_wifi_platdata && dhd_download_fw_on_driverload) {
+ /* power down all adapters */
+ for (i = 0; i < dhd_wifi_platdata->num_adapters; i++) {
+ adapter = &dhd_wifi_platdata->adapters[i];
+ wifi_platform_bus_enumerate(adapter, FALSE);
+ wifi_platform_set_power(adapter,
+ FALSE, WIFI_TURNOFF_DELAY);
}
}
}
@@ -968,7 +978,52 @@
return err;
}
+#if defined(SUPPORT_MULTIPLE_BOARD_REVISION)
+void
+concate_custom_board_revision(char *nv_path)
+{
+ uint32 board_revision = 0;
+ struct device_node *root_node = NULL;
+ char* wlan_node = NULL;
+
+ if (!nv_path) {
+ DHD_ERROR(("nv_path is null\n"));
+ return;
+ }
+
+ wlan_node = dhd_get_device_dt_name();
+ if (!wlan_node) {
+ DHD_ERROR(("Failed to dt name\n"));
+ return;
+ }
+
+ root_node = of_find_compatible_node(NULL, NULL, wlan_node);
+ if (!root_node) {
+ DHD_ERROR(("Failed to get device node\n"));
+ return;
+ }
+
+ if (of_property_read_u32(root_node, "nvram-ES", &board_revision)) {
+ DHD_ERROR(("No board revision property in dtsi\n"));
+ return;
+ }
+
+ DHD_INFO(("Board revision:%d\n", board_revision));
+
+ if (board_revision == 1) {
+ strcat(nv_path, "_ES10");
+ DHD_INFO(("Mached Board revision ES10: nvram name:%s\n", nv_path));
+ }
+
+}
+#endif /* SUPPORT_MULTIPLE_BOARD_REVISION */
+
/* Weak functions that can be overridden in Platform specific implementation */
+char* __attribute__ ((weak)) dhd_get_device_dt_name(void)
+{
+ return NULL;
+}
+
uint32 __attribute__ ((weak)) dhd_plat_get_info_size(void)
{
return 0;
diff --git a/dhd_linux_priv.h b/dhd_linux_priv.h
index 605800d..874699e 100644
--- a/dhd_linux_priv.h
+++ b/dhd_linux_priv.h
@@ -1,7 +1,7 @@
/*
* DHD Linux header file - contains private structure definition of the Linux specific layer
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -351,6 +351,10 @@
struct kobject dhd_lb_kobj;
bool dhd_lb_candidacy_override;
#endif /* DHD_LB */
+
+ /* DPC bounds sysfs */
+ struct kobject dhd_dpc_bounds_kobj;
+
#if defined(DNGL_AXI_ERROR_LOGGING) && defined(DHD_USE_WQ_FOR_DNGL_AXI_ERROR)
struct work_struct axi_error_dispatcher_work;
#endif /* DNGL_AXI_ERROR_LOGGING && DHD_USE_WQ_FOR_DNGL_AXI_ERROR */
diff --git a/dhd_linux_rx.c b/dhd_linux_rx.c
index af1068b..8f8727d 100644
--- a/dhd_linux_rx.c
+++ b/dhd_linux_rx.c
@@ -2,7 +2,7 @@
* Broadcom Dongle Host Driver (DHD),
* Linux-specific network interface for receive(rx) path
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -422,7 +422,12 @@
}
#ifdef DHD_WAKE_STATUS
- pkt_wake = dhd_bus_get_bus_wake(dhdp);
+ /* Get pkt_wake and clear it */
+#if defined(BCMPCIE)
+ pkt_wake = dhd_bus_set_get_bus_wake_pkt_dump(dhdp, 0);
+#else /* SDIO */
+ pkt_wake = dhd_bus_set_get_bus_wake(dhdp, 0);
+#endif /* BCMPCIE */
wcp = dhd_bus_get_wakecount(dhdp);
if (wcp == NULL) {
/* If wakeinfo count buffer is null do not update wake count values */
@@ -733,9 +738,9 @@
#ifdef ARP_OFFLOAD_SUPPORT
DHD_ERROR(("arp hmac_update:%d \n", dhdp->hmac_updated));
#endif /* ARP_OFFLOAD_SUPPORT */
-#if defined(DHD_WAKEPKT_SET_MARK)
+#if defined(DHD_WAKEPKT_SET_MARK) && defined(CONFIG_NF_CONNTRACK_MARK)
PKTMARK(skb) |= 0x80000000;
-#endif /* DHD_WAKEPKT_SET_MARK */
+#endif /* DHD_WAKEPKT_SET_MARK && CONFIG_NF_CONNTRACK_MARK */
}
#endif /* DHD_WAKE_STATUS && DHD_WAKEPKT_DUMP */
@@ -969,6 +974,7 @@
if (ntoh16(skb->protocol) != ETHER_TYPE_BRCM) {
dhdp->dstats.rx_bytes += skb->len;
+ dhdp->rx_bytes += skb->len;
dhdp->rx_packets++; /* Local count */
ifp->stats.rx_bytes += skb->len;
ifp->stats.rx_packets++;
diff --git a/dhd_linux_sched.c b/dhd_linux_sched.c
index c93423d..cd04bb2 100644
--- a/dhd_linux_sched.c
+++ b/dhd_linux_sched.c
@@ -1,7 +1,7 @@
/*
* Expose some of the kernel scheduler routines
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/dhd_linux_sock_qos.h b/dhd_linux_sock_qos.h
index f37cc03..f6745d8 100644
--- a/dhd_linux_sock_qos.h
+++ b/dhd_linux_sock_qos.h
@@ -4,7 +4,7 @@
* Provides type definitions and function prototypes to call into
* DHD's QOS on Socket Flow module.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/dhd_linux_tx.c b/dhd_linux_tx.c
index 845e1f2..d370c03 100644
--- a/dhd_linux_tx.c
+++ b/dhd_linux_tx.c
@@ -2,7 +2,7 @@
* Broadcom Dongle Host Driver (DHD),
* Linux-specific network interface for transmit(tx) path
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -189,10 +189,20 @@
dhd_info_t *dhd = (dhd_info_t *)(dhdp->info);
struct ether_header *eh = NULL;
uint8 pkt_flow_prio;
+ dhd_if_t *ifp;
+ unsigned long flags;
+ uint datalen;
-#if (defined(DHD_L2_FILTER) || (defined(BCM_ROUTER_DHD) && defined(QOS_MAP_SET)))
- dhd_if_t *ifp = dhd_get_ifp(dhdp, ifidx);
-#endif /* DHD_L2_FILTER || (BCM_ROUTER_DHD && QOS_MAP_SET) */
+ DHD_GENERAL_LOCK(dhdp, flags);
+ ifp = dhd_get_ifp(dhdp, ifidx);
+ if (!ifp || ifp->del_in_progress) {
+ DHD_ERROR(("%s: ifp:%p del_in_progress:%d\n",
+ __FUNCTION__, ifp, ifp ? ifp->del_in_progress : 0));
+ DHD_GENERAL_UNLOCK(dhdp, flags);
+ PKTCFREE(dhdp->osh, pktbuf, TRUE);
+ return -ENODEV;
+ }
+ DHD_GENERAL_UNLOCK(dhdp, flags);
/* Reject if down */
if (!dhdp->up || (dhdp->busstate == DHD_BUS_DOWN)) {
@@ -217,6 +227,8 @@
return BCME_ERROR;
}
+ datalen = PKTLEN(dhdp->osh, pktbuf);
+
#ifdef DHD_L2_FILTER
/* if dhcp_unicast is enabled, we need to convert the */
/* broadcast DHCP ACK/REPLY packets to Unicast. */
@@ -417,6 +429,24 @@
#endif /* BCMDBUS */
+ /* Update the packet counters here, as it is called for LB Tx and non-LB Tx too */
+ if (ret) {
+ ifp->stats.tx_dropped++;
+ dhdp->tx_dropped++;
+ } else {
+#ifdef PROP_TXSTATUS
+ /* tx_packets counter can counted only when wlfc is disabled */
+ if (!dhd_wlfc_is_supported(dhdp))
+#endif
+ {
+ dhdp->tx_packets++;
+ dhdp->tx_bytes += datalen;
+ ifp->stats.tx_packets++;
+ ifp->stats.tx_bytes += datalen;
+ }
+ dhdp->actual_tx_pkts++;
+ }
+
return ret;
}
@@ -524,7 +554,6 @@
BCMFASTPATH(dhd_start_xmit)(struct sk_buff *skb, struct net_device *net)
{
int ret;
- uint datalen;
void *pktbuf;
dhd_info_t *dhd = DHD_DEV_INFO(net);
dhd_if_t *ifp = NULL;
@@ -590,7 +619,7 @@
DHD_GENERAL_LOCK(&dhd->pub, flags);
if (DHD_BUS_CHECK_SUSPEND_OR_SUSPEND_IN_PROGRESS(&dhd->pub)) {
- DHD_ERROR(("%s: bus is in suspend(%d) or suspending(0x%x) state!!\n",
+ DHD_ERROR_RLMT(("%s: bus is in suspend(%d) or suspending(0x%x) state!!\n",
__FUNCTION__, dhd->pub.busstate, dhd->pub.dhd_bus_busy_state));
DHD_BUS_BUSY_CLEAR_IN_TX(&dhd->pub);
#ifdef PCIE_FULL_DONGLE
@@ -650,7 +679,13 @@
DHD_OS_WAKE_UNLOCK(&dhd->pub);
return NETDEV_TX_BUSY;
}
-
+#ifdef RPM_FAST_TRIGGER
+ /* Xmit is running reset RPM fast trigger */
+ if (dhd->pub.rpm_fast_trigger) {
+ DHD_ERROR(("%s: Reset RPM fast trigger\n", __FUNCTION__));
+ dhd->pub.rpm_fast_trigger = FALSE;
+ }
+#endif /* RPM_FAST_TRIGGER */
DHD_GENERAL_UNLOCK(&dhd->pub, flags);
/* If tput test is in progress */
@@ -672,8 +707,6 @@
PKTSETLEN(dhd->pub.osh, skb, length);
}
- datalen = PKTLEN(dhd->pub.osh, skb);
-
/* Make sure there's enough room for any header */
#if !defined(BCM_ROUTER_DHD)
if (skb_headroom(skb) < dhd->pub.hdrlen + htsfdlystat_sz) {
@@ -866,27 +899,9 @@
#else
ret = __dhd_sendpkt(&dhd->pub, ifidx, pktbuf);
#endif
+ BCM_REFERENCE(ret);
done:
- /* XXX Bus modules may have different "native" error spaces? */
- /* XXX USB is native linux and it'd be nice to retain errno */
- /* XXX meaning, but SDIO is not so we'd need an OSL_ERROR. */
- if (ret) {
- ifp->stats.tx_dropped++;
- dhd->pub.tx_dropped++;
- } else {
-#ifdef PROP_TXSTATUS
- /* tx_packets counter can counted only when wlfc is disabled */
- if (!dhd_wlfc_is_supported(&dhd->pub))
-#endif
- {
- dhd->pub.tx_packets++;
- ifp->stats.tx_packets++;
- ifp->stats.tx_bytes += datalen;
- }
- dhd->pub.actual_tx_pkts++;
- }
-
DHD_GENERAL_LOCK(&dhd->pub, flags);
DHD_BUS_BUSY_CLEAR_IN_TX(&dhd->pub);
DHD_IF_CLR_TX_ACTIVE(ifp, DHD_TX_START_XMIT);
@@ -1010,6 +1025,7 @@
if (ifp != NULL) {
if (success) {
dhd->pub.tx_packets++;
+ dhd->pub.tx_bytes += datalen;
ifp->stats.tx_packets++;
ifp->stats.tx_bytes += datalen;
} else {
@@ -1105,9 +1121,6 @@
}
#endif /* DHD_4WAYM4_FAIL_DISCONNECT */
-#ifdef DHD_PKT_LOGGING_DBGRING
-extern void dhd_os_dbg_urgent_pullreq(void *os_priv, int ring_id);
-#endif /* DHD_PKT_LOGGING_DBGRING */
void
dhd_handle_pktdata(dhd_pub_t *dhdp, int ifidx, void *pkt, uint8 *pktdata, uint32 pktid,
uint32 pktlen, uint16 *pktfate, uint8 *dhd_udr, uint8 *dhd_igmp,
@@ -1228,6 +1241,7 @@
switch (pkt_type) {
case PKT_TYPE_DHCP:
dhd_dhcp_dump(dhdp, ifidx, pktdata, tx, &pkthash, pktfate);
+ dhd_send_supp_dhcp(dhdp, ifidx, pktdata, tx, pktfate);
break;
case PKT_TYPE_ICMP:
dhd_icmp_dump(dhdp, ifidx, pktdata, tx, &pkthash, pktfate);
@@ -1240,6 +1254,7 @@
break;
case PKT_TYPE_EAP:
dhd_dump_eapol_message(dhdp, ifidx, pktdata, pktlen, tx, &pkthash, pktfate);
+ dhd_send_supp_eap(dhdp, ifidx, pktdata, pktlen, tx, pktfate);
break;
default:
break;
diff --git a/dhd_linux_tx.h b/dhd_linux_tx.h
index 242cc1e..1484f7b 100644
--- a/dhd_linux_tx.h
+++ b/dhd_linux_tx.h
@@ -2,7 +2,7 @@
* Broadcom Dongle Host Driver (DHD),
* Linux-specific network interface for transmit(tx) path
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/dhd_linux_wq.c b/dhd_linux_wq.c
index 3370a47..7cc2eaf 100644
--- a/dhd_linux_wq.c
+++ b/dhd_linux_wq.c
@@ -2,7 +2,7 @@
* Broadcom Dongle Host Driver (DHD), Generic work queue framework
* Generic interface to handle dhd deferred work events
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/dhd_linux_wq.h b/dhd_linux_wq.h
index 32275d1..d7bd0ec 100644
--- a/dhd_linux_wq.h
+++ b/dhd_linux_wq.h
@@ -2,7 +2,7 @@
* Broadcom Dongle Host Driver (DHD), Generic work queue framework
* Generic interface to handle dhd deferred work events
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/dhd_log_dump.c b/dhd_log_dump.c
index 82fc885..1496d28 100644
--- a/dhd_log_dump.c
+++ b/dhd_log_dump.c
@@ -1,7 +1,7 @@
/*
* log_dump - debugability support for dumping logs to file
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -81,6 +81,7 @@
#else
int logdump_rtt_enable = FALSE;
#endif /* EWP_RTT_LOGGING */
+
int logdump_prsrv_tailsize = DHD_LOG_DUMP_MAX_TAIL_FLUSH_SIZE;
#ifdef DHD_DEBUGABILITY_DEBUG_DUMP
@@ -89,6 +90,8 @@
{LOG_DUMP_SECTION_ECNTRS, DEBUG_DUMP_RING2_ID},
{LOG_DUMP_SECTION_STATUS, DEBUG_DUMP_RING1_ID},
{LOG_DUMP_SECTION_RTT, DEBUG_DUMP_RING2_ID},
+ {LOG_DUMP_SECTION_PKTID_MAP_LOG, DEBUG_DUMP_RING2_ID},
+ {LOG_DUMP_SECTION_PKTID_UNMAP_LOG, DEBUG_DUMP_RING2_ID},
{LOG_DUMP_SECTION_DHD_DUMP, DEBUG_DUMP_RING1_ID},
{LOG_DUMP_SECTION_EXT_TRAP, DEBUG_DUMP_RING1_ID},
{LOG_DUMP_SECTION_HEALTH_CHK, DEBUG_DUMP_RING1_ID},
@@ -2465,4 +2468,58 @@
}
#endif /* WL_CFGVENDOR_SEND_HANG_EVENT || DHD_PKT_LOGGING */
+#ifdef DHD_IOVAR_LOG_FILTER_DUMP
+typedef struct iovar_log_filter_table {
+ char command[64];
+ int enable;
+} iovar_log_filter_table_t;
+
+/* WLC_GET_VAR is not being logged by default. Add for logging in debug_dump. */
+static const iovar_log_filter_table_t iovar_get_filter_params[] = {
+ {"cur_etheraddr", TRUE},
+ {"\0", TRUE}
+};
+
+/* WLC_SET_VAR is being logged by default. Add for not logging in debug_dump. */
+static const iovar_log_filter_table_t iovar_set_filter_params[] = {
+ {"pkt_filter_enable", FALSE},
+ {"pkt_filter_mode", FALSE},
+ {"\0", FALSE}
+};
+
+bool
+dhd_iovar_log_dump_check(dhd_pub_t *dhd_pub, uint32 cmd, char *msg)
+{
+ int cnt = 0;
+ const iovar_log_filter_table_t *table;
+ bool ret_val = TRUE;
+
+ /* Logging all IOVARs with DHD_IOVAR_MEM() in debug_dump file
+ * during during Wifi ON.
+ */
+ if (dhd_pub->up == FALSE) {
+ return TRUE;
+ }
+
+ if (cmd == WLC_GET_VAR) {
+ ret_val = FALSE;
+ table = iovar_get_filter_params;
+ } else if (cmd == WLC_SET_VAR) {
+ ret_val = TRUE;
+ table = iovar_set_filter_params;
+ } else {
+ return TRUE;
+ }
+ while (strlen(table[cnt].command) > 0) {
+ if (!strncmp(msg, table[cnt].command,
+ strlen(table[cnt].command))) {
+ return table[cnt].enable;
+ }
+
+ cnt++;
+ }
+
+ return ret_val;
+}
+#endif /* DHD_IOVAR_LOG_FILTER_DUMP */
#endif /* DHD_LOG_DUMP */
diff --git a/dhd_log_dump.h b/dhd_log_dump.h
index fcea9f2..9328b27 100644
--- a/dhd_log_dump.h
+++ b/dhd_log_dump.h
@@ -1,7 +1,7 @@
/*
* log_dump - debugability support for dumping logs to file - header file
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -136,7 +136,8 @@
#define COOKIE_LOG_HDR "\n-------------------- Cookie List ----------------------------\n"
#define DHD_PKTID_MAP_LOG_HDR "\n---------------- PKTID MAP log -----------------------\n"
#define DHD_PKTID_UNMAP_LOG_HDR "\n------------------ PKTID UNMAP log -----------------------\n"
-#define PKTID_LOG_DUMP_FMT "\nIndex(Current=%d) Timestamp Pktaddr(PA) Pktid Size\n"
+#define PKTID_LOG_DUMP_FMT \
+ "\nIndex \t\tTimestamp \tPktaddr(PA) \tPktid \tSize \tPkttype\n(Current=%d)\n"
/* 0: DLD_BUF_TYPE_GENERAL, 1: DLD_BUF_TYPE_PRESERVE
* 2: DLD_BUF_TYPE_SPECIAL
@@ -404,6 +405,9 @@
void dhd_get_debug_dump_len(void *handle, struct sk_buff *skb, void *event_info, uint8 event);
void cfgvendor_log_dump_len(dhd_pub_t *dhdp, log_dump_type_t *type, struct sk_buff *skb);
#endif
+#ifdef DHD_IOVAR_LOG_FILTER_DUMP
+bool dhd_iovar_log_dump_check(dhd_pub_t *dhd_pub, uint32 cmd, char *msg);
+#endif /* DHD_IOVAR_LOG_FILTER_DUMP */
#endif /* DHD_LOG_DUMP */
#endif /* !__DHD_LOG_DUMP_H__ */
diff --git a/dhd_mschdbg.c b/dhd_mschdbg.c
index dd88135..4ba6fd2 100644
--- a/dhd_mschdbg.c
+++ b/dhd_mschdbg.c
@@ -1,7 +1,7 @@
/*
* DHD debugability support
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/dhd_mschdbg.h b/dhd_mschdbg.h
index 349f567..533b4eb 100644
--- a/dhd_mschdbg.h
+++ b/dhd_mschdbg.h
@@ -1,7 +1,7 @@
/*
* DHD debugability header file
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/dhd_msgbuf.c b/dhd_msgbuf.c
old mode 100755
new mode 100644
index 3659fd9..f41324c
--- a/dhd_msgbuf.c
+++ b/dhd_msgbuf.c
@@ -3,7 +3,7 @@
* Provides type definitions and function prototypes used to link the
* DHD OS, bus, and protocol modules.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -481,15 +481,16 @@
#endif /* AGG_H2D_DB */
#endif /* TXP_FLUSH_NITEMS */
- uint8 ring_type;
- uint8 n_completion_ids;
- bool create_pending;
- uint16 create_req_id;
- uint8 current_phase;
- uint16 compeltion_ring_ids[MAX_COMPLETION_RING_IDS_ASSOCIATED];
+ uint8 ring_type;
+ uint8 n_completion_ids;
+ bool create_pending;
+ uint16 create_req_id;
+ uint8 current_phase;
+ uint16 compeltion_ring_ids[MAX_COMPLETION_RING_IDS_ASSOCIATED];
uchar name[RING_NAME_MAX_LENGTH];
uint32 ring_mem_allocated;
- void *ring_lock;
+ void *ring_lock;
+ struct msgbuf_ring *linked_ring; /* Ring Associated to metadata ring */
} msgbuf_ring_t;
#define DHD_RING_BGN_VA(ring) ((ring)->dma_buf.va)
@@ -554,88 +555,23 @@
uint rx_buf_burst;
uint rx_bufpost_threshold;
-void
-dhd_prot_set_ring_size_ver(dhd_pub_t *dhd, int version)
-{
- if (ring_size_alloc_version < version) {
- DHD_ERROR(("%s: Ring alloced version(%d) is lesser than requested(%d), ABORT\n",
- __FUNCTION__, ring_size_alloc_version, version));
- return;
- }
- ring_size_version = version;
+#ifndef DHD_RX_CPL_POST_BOUND
+#define DHD_RX_CPL_POST_BOUND 1024
+#endif
+#ifndef DHD_TX_POST_BOUND
+#define DHD_TX_POST_BOUND 256
+#endif
+#ifndef DHD_CTRL_CPL_POST_BOUND
+#define DHD_CTRL_CPL_POST_BOUND 64
+#endif
+#ifndef DHD_TX_CPL_BOUND
+#define DHD_TX_CPL_BOUND 2048
+#endif
- /* Change each parameters only if they are 0s, non-zero means,
- * it is overridden via module parameter.
- */
- switch (version) {
- case 1:
- if (!h2d_max_txpost) {
- h2d_max_txpost = H2DRING_TXPOST_SIZE_V1;
- }
- if (!h2d_htput_max_txpost) {
- h2d_htput_max_txpost = H2DRING_HTPUT_TXPOST_SIZE_V1;
- }
- if (!d2h_max_txcpl) {
- d2h_max_txcpl = D2HRING_TXCPL_SIZE_V1;
- }
-
- if (!h2d_max_rxpost) {
- h2d_max_rxpost = H2DRING_RXPOST_SIZE_V1;
- }
- if (!d2h_max_rxcpl) {
- d2h_max_rxcpl = D2HRING_RXCPL_SIZE_V1;
- }
-
- if (!h2d_max_ctrlpost) {
- h2d_max_ctrlpost = H2DRING_CTRLPOST_SIZE_V1;
- }
- if (!d2h_max_ctrlcpl) {
- d2h_max_ctrlcpl = D2HRING_CTRLCPL_SIZE_V1;
- }
-
- if (!rx_buf_burst) {
- rx_buf_burst = RX_BUF_BURST_V1;
- }
- if (!rx_bufpost_threshold) {
- rx_bufpost_threshold = RX_BUFPOST_THRESHOLD_V1;
- }
- break;
- case 2:
- if (!h2d_max_txpost) {
- h2d_max_txpost = H2DRING_TXPOST_SIZE_V2;
- }
- if (!h2d_htput_max_txpost) {
- h2d_htput_max_txpost = H2DRING_HTPUT_TXPOST_SIZE_V2;
- }
- if (!d2h_max_txcpl) {
- d2h_max_txcpl = D2HRING_TXCPL_SIZE_V2;
- }
-
- if (!h2d_max_rxpost) {
- h2d_max_rxpost = H2DRING_RXPOST_SIZE_V2;
- }
- if (!d2h_max_rxcpl) {
- d2h_max_rxcpl = D2HRING_RXCPL_SIZE_V2;
- }
-
- if (!h2d_max_ctrlpost) {
- h2d_max_ctrlpost = H2DRING_CTRLPOST_SIZE_V2;
- }
- if (!d2h_max_ctrlcpl) {
- d2h_max_ctrlcpl = D2HRING_CTRLCPL_SIZE_V2;
- }
-
- if (!rx_buf_burst) {
- rx_buf_burst = RX_BUF_BURST_V2;
- }
- if (!rx_bufpost_threshold) {
- rx_bufpost_threshold = RX_BUFPOST_THRESHOLD_V2;
- }
- break;
- default:
- DHD_ERROR(("%s: invalid override version:%d", __FUNCTION__, version));
- }
-}
+uint dhd_rx_cpl_post_bound = DHD_RX_CPL_POST_BOUND;
+uint dhd_tx_post_bound = DHD_TX_POST_BOUND;
+uint dhd_tx_cpl_bound = DHD_TX_CPL_BOUND;
+uint dhd_ctrl_cpl_post_bound = DHD_CTRL_CPL_POST_BOUND;
#ifdef AGG_H2D_DB
bool agg_h2d_db_enab = TRUE;
@@ -844,6 +780,19 @@
uint32 event_wakeup_pkt; /* Number of event wakeup packet rcvd */
uint32 rx_wakeup_pkt; /* Number of Rx wakeup packet rcvd */
uint32 info_wakeup_pkt; /* Number of info cpl wakeup packet rcvd */
+ msgbuf_ring_t *d2hring_md_cpl; /* D2H metadata completion ring */
+ /* no. which controls how many rx cpl/post items are processed per dpc */
+ uint32 rx_cpl_post_bound;
+ /*
+ * no. which controls how many tx post items are processed per dpc,
+ * i.e, how many tx pkts are posted to flowring from the bkp queue
+ * from dpc context
+ */
+ uint32 tx_post_bound;
+ /* no. which controls how many tx cpl items are processed per dpc */
+ uint32 tx_cpl_bound;
+ /* no. which controls how many ctrl cpl/post items are processed per dpc */
+ uint32 ctrl_cpl_post_bound;
} dhd_prot_t;
#ifdef DHD_EWPR_VER2
@@ -896,7 +845,7 @@
/* Consumer: Determine the location where the next message may be consumed */
static uint8* dhd_prot_get_read_addr(dhd_pub_t *dhd, msgbuf_ring_t *ring,
- uint32 *available_len);
+ uint32 *available_len, uint32 bound);
/* Producer (WR index update) or Consumer (RD index update) indication */
static void dhd_prot_ring_write_complete(dhd_pub_t *dhd, msgbuf_ring_t *ring,
@@ -996,6 +945,7 @@
#ifdef EWP_EDL
static void dhd_prot_detach_edl_rings(dhd_pub_t *dhd);
#endif
+static void dhd_prot_detach_md_rings(dhd_pub_t *dhd);
static void dhd_prot_process_d2h_host_ts_complete(dhd_pub_t *dhd, void* buf);
static void dhd_prot_process_snapshot_complete(dhd_pub_t *dhd, void *buf);
@@ -1107,6 +1057,144 @@
static void dhd_prot_h2d_sync_init(dhd_pub_t *dhd);
+uint32
+dhd_prot_get_tx_post_bound(dhd_pub_t *dhd)
+{
+ dhd_prot_t *prot = dhd->prot;
+ return prot->tx_post_bound;
+}
+
+uint32
+dhd_prot_get_ctrl_cpl_post_bound(dhd_pub_t *dhd)
+{
+ dhd_prot_t *prot = dhd->prot;
+ return prot->ctrl_cpl_post_bound;
+}
+
+uint32
+dhd_prot_get_tx_cpl_bound(dhd_pub_t *dhd)
+{
+ dhd_prot_t *prot = dhd->prot;
+ return prot->tx_cpl_bound;
+}
+
+uint32
+dhd_prot_get_rx_cpl_post_bound(dhd_pub_t *dhd)
+{
+ dhd_prot_t *prot = dhd->prot;
+ return prot->rx_cpl_post_bound;
+}
+
+void
+dhd_prot_set_tx_post_bound(dhd_pub_t *dhd, uint32 val)
+{
+ dhd_prot_t *prot = dhd->prot;
+ prot->tx_post_bound = val;
+}
+
+void
+dhd_prot_set_ctrl_cpl_post_bound(dhd_pub_t *dhd, uint32 val)
+{
+ dhd_prot_t *prot = dhd->prot;
+ prot->ctrl_cpl_post_bound = val;
+}
+
+void
+dhd_prot_set_tx_cpl_bound(dhd_pub_t *dhd, uint32 val)
+{
+ dhd_prot_t *prot = dhd->prot;
+ prot->tx_cpl_bound = val;
+}
+
+void dhd_prot_set_rx_cpl_post_bound(dhd_pub_t *dhd, uint32 val)
+{
+ dhd_prot_t *prot = dhd->prot;
+ prot->rx_cpl_post_bound = val;
+}
+
+void
+dhd_prot_set_ring_size_ver(dhd_pub_t *dhd, int version)
+{
+ if (ring_size_alloc_version < version) {
+ DHD_ERROR(("%s: Ring alloced version(%d) is lesser than requested(%d), ABORT\n",
+ __FUNCTION__, ring_size_alloc_version, version));
+ return;
+ }
+ ring_size_version = version;
+
+ /* Change each parameters only if they are 0s, non-zero means,
+ * it is overridden via module parameter.
+ */
+ switch (version) {
+ case 1:
+ if (!h2d_max_txpost) {
+ h2d_max_txpost = H2DRING_TXPOST_SIZE_V1;
+ }
+ if (!h2d_htput_max_txpost) {
+ h2d_htput_max_txpost = H2DRING_HTPUT_TXPOST_SIZE_V1;
+ }
+ if (!d2h_max_txcpl) {
+ d2h_max_txcpl = D2HRING_TXCPL_SIZE_V1;
+ }
+
+ if (!h2d_max_rxpost) {
+ h2d_max_rxpost = H2DRING_RXPOST_SIZE_V1;
+ }
+ if (!d2h_max_rxcpl) {
+ d2h_max_rxcpl = D2HRING_RXCPL_SIZE_V1;
+ }
+
+ if (!h2d_max_ctrlpost) {
+ h2d_max_ctrlpost = H2DRING_CTRLPOST_SIZE_V1;
+ }
+ if (!d2h_max_ctrlcpl) {
+ d2h_max_ctrlcpl = D2HRING_CTRLCPL_SIZE_V1;
+ }
+
+ if (!rx_buf_burst) {
+ rx_buf_burst = RX_BUF_BURST_V1;
+ }
+ if (!rx_bufpost_threshold) {
+ rx_bufpost_threshold = RX_BUFPOST_THRESHOLD_V1;
+ }
+ break;
+ case 2:
+ if (!h2d_max_txpost) {
+ h2d_max_txpost = H2DRING_TXPOST_SIZE_V2;
+ }
+ if (!h2d_htput_max_txpost) {
+ h2d_htput_max_txpost = H2DRING_HTPUT_TXPOST_SIZE_V2;
+ }
+ if (!d2h_max_txcpl) {
+ d2h_max_txcpl = D2HRING_TXCPL_SIZE_V2;
+ }
+
+ if (!h2d_max_rxpost) {
+ h2d_max_rxpost = H2DRING_RXPOST_SIZE_V2;
+ }
+ if (!d2h_max_rxcpl) {
+ d2h_max_rxcpl = D2HRING_RXCPL_SIZE_V2;
+ }
+
+ if (!h2d_max_ctrlpost) {
+ h2d_max_ctrlpost = H2DRING_CTRLPOST_SIZE_V2;
+ }
+ if (!d2h_max_ctrlcpl) {
+ d2h_max_ctrlcpl = D2HRING_CTRLCPL_SIZE_V2;
+ }
+
+ if (!rx_buf_burst) {
+ rx_buf_burst = RX_BUF_BURST_V2;
+ }
+ if (!rx_bufpost_threshold) {
+ rx_bufpost_threshold = RX_BUFPOST_THRESHOLD_V2;
+ }
+ break;
+ default:
+ DHD_ERROR(("%s: invalid override version:%d", __FUNCTION__, version));
+ }
+}
+
#ifdef D2H_MINIDUMP
dhd_dma_buf_t *
dhd_prot_get_minidump_buf(dhd_pub_t *dhd)
@@ -1164,21 +1252,18 @@
}
bool
-dhd_prot_is_cmpl_ring_empty(dhd_pub_t *dhd, void *prot_info)
+dhd_prot_is_h2d_ring_empty(dhd_pub_t *dhd, void *prot_info)
{
- msgbuf_ring_t *flow_ring = (msgbuf_ring_t *)prot_info;
+ msgbuf_ring_t *ring = (msgbuf_ring_t *)prot_info;
uint16 rd, wr;
bool ret;
- if (dhd->dma_d2h_ring_upd_support) {
- wr = flow_ring->wr;
- } else {
- dhd_bus_cmn_readshared(dhd->bus, &wr, RING_WR_UPD, flow_ring->idx);
- }
+ /* For h2d ring, WR is owned by host, RD is owned by dongle */
+ wr = ring->wr;
if (dhd->dma_h2d_ring_upd_support) {
- rd = flow_ring->rd;
+ rd = dhd_prot_dma_indx_get(dhd, H2D_DMA_INDX_RD_UPD, ring->idx);
} else {
- dhd_bus_cmn_readshared(dhd->bus, &rd, RING_RD_UPD, flow_ring->idx);
+ dhd_bus_cmn_readshared(dhd->bus, &rd, RING_RD_UPD, ring->idx);
}
ret = (wr == rd) ? TRUE : FALSE;
return ret;
@@ -1192,8 +1277,9 @@
uint16 wr, host_rd;
bool ret;
+ /* For Completion ring, WR is owned by dongle, RD is owned by Host */
if (dhd->dma_d2h_ring_upd_support) {
- wr = ring->wr;
+ wr = dhd_prot_dma_indx_get(dhd, D2H_DMA_INDX_WR_UPD, ring->idx);
} else {
dhd_bus_cmn_readshared(dhd->bus, &wr, RING_WR_UPD, ring->idx);
}
@@ -1205,6 +1291,7 @@
}
host_rd = ring->rd;
+
/* Consider the ring as processed if host rd and dongle wr are same */
ret = (host_rd != wr) ? TRUE : FALSE;
return ret;
@@ -1912,14 +1999,16 @@
typedef void * dhd_pktid_log_handle_t; /* opaque handle to pktid log */
-#define MAX_PKTID_LOG (2048)
+#define MAX_PKTID_LOG (2048u)
/*
* index timestamp pktaddr(pa) pktid size
- * index(4) + timestamp (<= 12) + pa (<=12) + pktid (4) + size(4) + space x 4 + 2 (lf)
- * ex) 1 22531185990 0x91fc38010 1017 8192
+ * index(5) + timestamp (<= 20) + dummy(4) + pa (<=11) + pktid (10) + size(7) +
+ * pkttype(7) + space(6) + null/lf(2)
+ * ex) 1367 78348654722 0xabbe69040 3317 1920 1
*/
-#define PKTID_LOG_STR_SZ 48u
-#define MAX_PKTID_LOG_BUF_SZ MAX_PKTID_LOG * PKTID_LOG_STR_SZ
+#define PKTID_LOG_STR_SZ 72u
+#define MAX_PKTID_LOG_BUF_SZ MAX_PKTID_LOG * PKTID_LOG_STR_SZ + \
+ strlen(PKTID_LOG_DUMP_FMT)
#define DHD_PKTID_LOG_ITEM_SZ (sizeof(dhd_pktid_log_item_t))
#define DHD_PKTID_LOG_SZ(items) (uint32)((sizeof(dhd_pktid_log_t)) + \
((DHD_PKTID_LOG_ITEM_SZ) * (items)))
@@ -1941,9 +2030,9 @@
uint32 log_size;
log_size = DHD_PKTID_LOG_SZ(num_items);
- log = (dhd_pktid_log_t *)MALLOCZ(dhd->osh, log_size);
+ log = (dhd_pktid_log_t *)KVMALLOCZ(dhd->osh, log_size);
if (log == NULL) {
- DHD_ERROR(("%s: MALLOC failed for size %d\n",
+ DHD_ERROR(("%s: KVMALLOC failed for size %d\n",
__FUNCTION__, log_size));
return (dhd_pktid_log_handle_t *)NULL;
}
@@ -1967,7 +2056,7 @@
log = (dhd_pktid_log_t *)handle;
log_size = DHD_PKTID_LOG_SZ(log->items);
- MFREE(dhd->osh, handle, log_size);
+ KVMFREE(dhd->osh, handle, log_size);
}
static void
@@ -2010,6 +2099,9 @@
unmap_log = (dhd_pktid_log_t *)(prot->pktid_dma_unmap);
OSL_GET_LOCALTIME(&ts_sec, &ts_usec);
if (map_log && unmap_log) {
+ DHD_ERROR(("%s: map_log(%s), unmap_log(%s)\n", __FUNCTION__,
+ is_vmalloc_addr(map_log) ? "vmalloc" : "kmalloc",
+ is_vmalloc_addr(unmap_log) ? "vmalloc" : "kmalloc"));
DHD_ERROR(("%s: map_idx=%d unmap_idx=%d "
"current time=[%5lu.%06lu]\n", __FUNCTION__,
map_log->index, unmap_log->index,
@@ -2038,9 +2130,14 @@
len += strlen(DHD_PKTID_UNMAP_LOG_HDR);
}
+ if (!pktlog_buf) {
+ return 0; /* len should be 0. */
+ }
+
/* Adding Format string + LineFeed */
len += strlen(PKTID_LOG_DUMP_FMT) + 2;
len += (uint32)PKTID_LOG_STR_SZ * pktlog_buf->items;
+
return len;
}
@@ -2063,6 +2160,10 @@
}
buf = (char *)VMALLOCZ(dhdp->osh, MAX_PKTID_LOG_BUF_SZ);
+ if (!buf) {
+ DHD_ERROR(("%s: buf alloc fails!\n", __FUNCTION__));
+ return BCME_NOMEM;
+ }
remain_len = buflen = MAX_PKTID_LOG_BUF_SZ;
dhd_init_sec_hdr(&sec_hdr);
@@ -2100,9 +2201,10 @@
addr = PHYSADDRLO(log_buf->map[i].pa);
#endif /* BCMDMA64OSL */
remain_len -= scnprintf(&buf[buflen - remain_len], remain_len,
- "%4u %12llu 0x%llx %4u %4u\n",
- i, log_buf->map[i].ts_nsec, addr,
- log_buf->map[i].pktid, log_buf->map[i].size);
+ "%5u %20llu %4s 0x%llx %10u %7u %7u\n",
+ i, log_buf->map[i].ts_nsec, " ", addr,
+ log_buf->map[i].pktid, log_buf->map[i].size,
+ log_buf->map[i].pkttype);
}
remain_len -= scnprintf(&buf[buflen - remain_len], remain_len, "\n");
@@ -2176,6 +2278,7 @@
#define DHD_H2D_BTLOGRING_REQ_PKTID 0xFFFA
#define DHD_D2H_BTLOGRING_REQ_PKTID 0xFFF9
#define DHD_H2D_SNAPSHOT_UPLOAD_REQ_PKTID 0xFFF8
+#define DHD_D2H_MDRING_REQ_PKTID 0xFFF8
#define IS_FLOWRING(ring) \
((strncmp(ring->name, "h2dflr", sizeof("h2dflr"))) == (0))
@@ -2221,6 +2324,15 @@
uint32 id, dmaaddr_t *pa, uint32 *len, void **dmah,
void **secdma, dhd_pkttype_t pkttype, bool rsv_locker);
+/* Metadata d2h completion ring linking/unlink ring types */
+typedef enum dhd_mdata_linked_ring_idx {
+ DHD_METADATA_NO_RING = 0,
+ DHD_METADATA_D2H_TXCPL,
+ DHD_METADATA_D2H_RXCPL,
+ DHD_METADATA_D2H_HP2PTX,
+ DHD_METADATA_D2H_HP2PRX
+} dhd_mdata_linked_ring_idx_t;
+
/*
* DHD_PKTID_AUDIT_ENABLED: Audit of PktIds in DHD for duplicate alloc and frees
*
@@ -4167,6 +4279,15 @@
prot->host_ipc_version = PCIE_SHARED_VERSION;
prot->no_tx_resource = FALSE;
+ prot->rx_cpl_post_bound =
+ (dhd_rx_cpl_post_bound) ? dhd_rx_cpl_post_bound : DHD_RX_CPL_POST_BOUND;
+ prot->tx_post_bound =
+ (dhd_tx_post_bound) ? dhd_tx_post_bound : DHD_TX_POST_BOUND;
+ prot->tx_cpl_bound =
+ (dhd_tx_cpl_bound) ? dhd_tx_cpl_bound : DHD_TX_CPL_BOUND;
+ prot->ctrl_cpl_post_bound =
+ (dhd_ctrl_cpl_post_bound) ? dhd_ctrl_cpl_post_bound : DHD_CTRL_CPL_POST_BOUND;
+
/* Init the host API version */
dhd_set_host_cap(dhd);
@@ -4372,6 +4493,17 @@
}
#endif /* BTLOG */
+ /* create MD cpl rings */
+ if (dhd->bus->api.fw_rev >= PCIE_SHARED_VERSION_7 && dhd->mdring_capable) {
+ if ((ret = dhd_prot_init_md_rings(dhd)) != BCME_OK) {
+ /* For now log and proceed, further clean up action maybe necessary
+ * when we have more clarity.
+ */
+ DHD_ERROR(("%s MD rings couldn't be created: Err Code%d",
+ __FUNCTION__, ret));
+ }
+ }
+
#ifdef DHD_LB_RXP
/* defualt rx flow ctrl thresholds. Can be changed at run time through sysfs */
dhd->lb_rxp_stop_thr = (D2HRING_RXCMPLT_MAX_ITEM * LB_RXP_STOP_THR);
@@ -4456,6 +4588,7 @@
#ifdef EWP_EDL
dhd_prot_detach_edl_rings(dhd);
#endif
+ dhd_prot_detach_md_rings(dhd);
/* if IOCTLRESP_USE_CONSTMEM is defined IOCTL PKTs use pktid_map_handle_ioctl
* handler and PKT memory is allocated using alloc_ioctl_return_buffer(), Otherwise
@@ -4620,6 +4753,9 @@
dhd_prot_ring_reset(dhd, prot->d2hring_btlog_cpln);
}
#endif /* BTLOG */
+ if (prot->d2hring_md_cpl) {
+ dhd_prot_ring_reset(dhd, prot->d2hring_md_cpl);
+ }
/* Reset PKTID map */
DHD_NATIVE_TO_PKTID_RESET(dhd, prot->pktid_ctrl_map);
@@ -4828,6 +4964,96 @@
}
}
+static int
+dhd_check_create_md_rings(dhd_pub_t *dhd)
+{
+ dhd_prot_t *prot = dhd->prot;
+ int ret = BCME_ERROR;
+ uint16 ringid;
+
+ /* Last dynamic ring indices are used by metadata rings */
+ ringid = dhd->bus->max_submission_rings + dhd->bus->max_completion_rings - 1;
+
+ if (prot->d2hring_md_cpl == NULL) {
+ prot->d2hring_md_cpl = MALLOCZ(prot->osh, sizeof(msgbuf_ring_t));
+
+ if (prot->d2hring_md_cpl == NULL) {
+ DHD_ERROR(("%s: couldn't alloc memory for d2hring_md_cpl\n",
+ __FUNCTION__));
+ return BCME_NOMEM;
+ }
+
+ DHD_INFO(("%s: about to create md cpl ring\n", __FUNCTION__));
+ ret = dhd_prot_ring_attach(dhd, prot->d2hring_md_cpl, "d2hmd_cpl",
+ D2HRING_MDRING_MAX_ITEM, D2HRING_MDCMPLT_ITEMSIZE,
+ ringid);
+ if (ret != BCME_OK) {
+ DHD_ERROR(("%s: couldn't alloc resources for md txcpl ring\n",
+ __FUNCTION__));
+ goto err;
+ }
+ dhd->md_item_count = 0;
+ if ((dhd->mdring_info = MALLOCZ(prot->osh,
+ MAX_MDRING_ITEM_DUMP * D2HRING_MDCMPLT_ITEMSIZE)) == NULL) {
+ DHD_ERROR(("%s: couldn't alloc resources for md ring dump\n",
+ __FUNCTION__));
+ }
+ }
+ if (prot->d2hring_md_cpl != NULL) {
+ /* dhd_prot_init rentry after a dhd_prot_reset */
+ ret = BCME_OK;
+ }
+
+ return ret;
+err:
+ MFREE(prot->osh, prot->d2hring_md_cpl, sizeof(msgbuf_ring_t));
+ prot->d2hring_md_cpl = NULL;
+ return ret;
+} /* dhd_check_create_md_rings */
+
+int
+dhd_prot_init_md_rings(dhd_pub_t *dhd)
+{
+ dhd_prot_t *prot = dhd->prot;
+ int ret = BCME_OK;
+
+ if ((ret = dhd_check_create_md_rings(dhd)) != BCME_OK) {
+ DHD_ERROR(("%s: md rings aren't created! \n",
+ __FUNCTION__));
+ return ret;
+ }
+
+ if ((prot->d2hring_md_cpl->inited) || (prot->d2hring_md_cpl->create_pending)) {
+ DHD_INFO(("md completion ring was created!\n"));
+ return ret;
+ }
+
+ DHD_ERROR(("trying to send create d2h md cpl ring: id %d\n",
+ prot->d2hring_md_cpl->idx));
+ ret = dhd_send_d2h_ringcreate(dhd, prot->d2hring_md_cpl,
+ BCMPCIE_D2H_RING_TYPE_MDATA_CPL, DHD_D2H_MDRING_REQ_PKTID);
+ if (ret != BCME_OK)
+ return ret;
+
+ prot->d2hring_md_cpl->seqnum = D2H_EPOCH_INIT_VAL;
+ prot->d2hring_md_cpl->current_phase = BCMPCIE_CMNHDR_PHASE_BIT_INIT;
+
+ /* Note that there is no way to delete d2h or h2d ring deletion incase either fails,
+ * so can not cleanup if one ring was created while the other failed
+ */
+ return BCME_OK;
+} /* dhd_prot_init_md_rings */
+
+static void
+dhd_prot_detach_md_rings(dhd_pub_t *dhd)
+{
+ if (dhd->prot->d2hring_md_cpl) {
+ dhd_prot_ring_detach(dhd, dhd->prot->d2hring_md_cpl);
+ MFREE(dhd->prot->osh, dhd->prot->d2hring_md_cpl, sizeof(msgbuf_ring_t));
+ dhd->prot->d2hring_md_cpl = NULL;
+ }
+}
+
#ifdef BTLOG
static int
dhd_check_create_btlog_rings(dhd_pub_t *dhd)
@@ -6201,7 +6427,8 @@
}
bool
-BCMFASTPATH(dhd_prot_process_msgbuf_infocpl)(dhd_pub_t *dhd, uint bound)
+BCMFASTPATH(dhd_prot_process_msgbuf_infocpl)(dhd_pub_t *dhd, uint bound,
+ uint32 *info_items)
{
dhd_prot_t *prot = dhd->prot;
bool more = TRUE;
@@ -6231,13 +6458,23 @@
DHD_RING_LOCK(ring->ring_lock, flags);
/* Get the message from ring */
- msg_addr = dhd_prot_get_read_addr(dhd, ring, &msg_len);
+ /* must pass 'bound - n' rather than just 'bound', because
+ * within this loop, dhd_prot_get_read_addr is called multiple
+ * times, so if just 'bound' is passed we may end up reading
+ * more than 'bound' items, ex:- for a bound of 2048,
+ * during the first iteration let us say n = 2000, so the loop
+ * continues and for the second iteration n = 1000 items may be read,
+ * so the total items read will be 3000 which is > 2048
+ */
+ msg_addr = dhd_prot_get_read_addr(dhd, ring, &msg_len, bound - n);
DHD_RING_UNLOCK(ring->ring_lock, flags);
if (msg_addr == NULL) {
more = FALSE;
break;
}
+ *info_items = msg_len / ring->item_len;
+
/* Prefetch data to populate the cache */
OSL_PREFETCH(msg_addr);
@@ -6294,7 +6531,15 @@
}
/* Get the message from ring */
- msg_addr = dhd_prot_get_read_addr(dhd, ring, &msg_len);
+ /* must pass 'bound - n' rather than just 'bound', because
+ * within this loop, dhd_prot_get_read_addr is called multiple
+ * times, so if just 'bound' is passed we may end up reading
+ * more than 'bound' items, ex:- for a bound of 2048,
+ * during the first iteration let us say n = 2000, so the loop
+ * continues and for the second iteration n = 1000 items may be read,
+ * so the total items read will be 3000 which is > 2048
+ */
+ msg_addr = dhd_prot_get_read_addr(dhd, ring, &msg_len, bound - n);
if (msg_addr == NULL) {
more = FALSE;
break;
@@ -6324,7 +6569,7 @@
#ifdef EWP_EDL
bool
-dhd_prot_process_msgbuf_edl(dhd_pub_t *dhd, uint32 *edl_itmes)
+dhd_prot_process_msgbuf_edl(dhd_pub_t *dhd, uint32 *evtlog_items)
{
dhd_prot_t *prot = dhd->prot;
msgbuf_ring_t *ring = prot->d2hring_edl;
@@ -6370,7 +6615,7 @@
depth = ring->max_items;
/* check for avail space, in number of ring items */
items = READ_AVAIL_SPACE(ring->wr, rd, depth);
- *edl_itmes = items;
+ *evtlog_items = items;
if (items == 0) {
/* no work items in edl ring */
return FALSE;
@@ -6645,7 +6890,7 @@
/** called when DHD needs to check for 'receive complete' messages from the dongle */
bool
-BCMFASTPATH(dhd_prot_process_msgbuf_rxcpl)(dhd_pub_t *dhd, uint bound, int ringtype)
+BCMFASTPATH(dhd_prot_process_msgbuf_rxcpl)(dhd_pub_t *dhd, int ringtype, uint32 *rxcpl_items)
{
bool more = FALSE;
uint n = 0;
@@ -6704,12 +6949,23 @@
DHD_RING_LOCK(ring->ring_lock, flags);
/* Get the address of the next message to be read from ring */
- msg_addr = dhd_prot_get_read_addr(dhd, ring, &msg_len);
+ /* must pass 'bound - n' rather than just 'bound', because
+ * within this loop, dhd_prot_get_read_addr is called multiple
+ * times, so if just 'bound' is passed we may end up reading
+ * more than 'bound' items, ex:- for a bound of 2048,
+ * during the first iteration let us say n = 2000, so the loop
+ * continues and for the second iteration n = 1000 items may be read,
+ * so the total items read will be 3000 which is > 2048
+ */
+ msg_addr = dhd_prot_get_read_addr(dhd, ring, &msg_len,
+ prot->rx_cpl_post_bound - n);
if (msg_addr == NULL) {
DHD_RING_UNLOCK(ring->ring_lock, flags);
break;
}
+ *rxcpl_items = msg_len / ring->item_len;
+
while (msg_len > 0) {
msg = (host_rxbuf_cmpl_t *)msg_addr;
@@ -6736,11 +6992,11 @@
pktid = ltoh32(msg->cmn_hdr.request_id);
if (msg->cmn_hdr.flags & BCMPCIE_CMNHDR_FLAGS_WAKE_PACKET) {
DHD_ERROR(("%s:Rx: Wakeup Packet received\n", __FUNCTION__));
- dhd->prot->rx_wakeup_pkt ++;
+ prot->rx_wakeup_pkt ++;
}
#ifdef DHD_PKTID_AUDIT_RING
- if (DHD_PKTID_AUDIT_RING_DEBUG(dhd, dhd->prot->pktid_rx_map, pktid,
+ if (DHD_PKTID_AUDIT_RING_DEBUG(dhd, prot->pktid_rx_map, pktid,
DHD_DUPLICATE_FREE, msg, D2HRING_RXCMPLT_ITEMSIZE) != BCME_OK) {
msg_len -= item_len;
msg_addr += item_len;
@@ -6756,7 +7012,7 @@
msg_addr += item_len;
continue;
}
- dhd->prot->tot_rxcpl++;
+ prot->tot_rxcpl++;
DMA_UNMAP(dhd->osh, pa, (uint) len, DMA_RX, 0, dmah);
@@ -6765,28 +7021,28 @@
dhd->dma_stats.rxdata_sz -= len;
#endif /* DMAMAP_STATS */
#ifdef DHD_HMAPTEST
- if ((dhd->prot->hmaptest_rx_active == HMAPTEST_D11_RX_POSTED) &&
- (pktid == dhd->prot->hmaptest_rx_pktid)) {
+ if ((prot->hmaptest_rx_active == HMAPTEST_D11_RX_POSTED) &&
+ (pktid == prot->hmaptest_rx_pktid)) {
uchar *ptr;
ptr = PKTDATA(dhd->osh, pkt) - (prot->rx_metadata_offset);
- DMA_UNMAP(dhd->osh, dhd->prot->hmap_rx_buf_pa,
- (uint)dhd->prot->hmap_rx_buf_len, DMA_RX, 0, dmah);
+ DMA_UNMAP(dhd->osh, prot->hmap_rx_buf_pa,
+ (uint)prot->hmap_rx_buf_len, DMA_RX, 0, dmah);
DHD_ERROR(("hmaptest: d11write rxcpl rcvd sc rxbuf pktid=0x%08x\n",
pktid));
DHD_ERROR(("hmaptest: d11write rxcpl r0_st=0x%08x r1_stat=0x%08x\n",
msg->rx_status_0, msg->rx_status_1));
DHD_ERROR(("hmaptest: d11write rxcpl rxbuf va=0x%p pa=0x%08x\n",
- dhd->prot->hmap_rx_buf_va,
- (uint32)PHYSADDRLO(dhd->prot->hmap_rx_buf_pa)));
+ prot->hmap_rx_buf_va,
+ (uint32)PHYSADDRLO(prot->hmap_rx_buf_pa)));
DHD_ERROR(("hmaptest: d11write rxcpl pktdata va=0x%p pa=0x%08x\n",
PKTDATA(dhd->osh, pkt), (uint32)PHYSADDRLO(pa)));
- memcpy(ptr, dhd->prot->hmap_rx_buf_va, dhd->prot->hmap_rx_buf_len);
- dhd->prot->hmaptest_rx_active = HMAPTEST_D11_RX_INACTIVE;
- dhd->prot->hmap_rx_buf_va = NULL;
- dhd->prot->hmap_rx_buf_len = 0;
- PHYSADDRHISET(dhd->prot->hmap_rx_buf_pa, 0);
- PHYSADDRLOSET(dhd->prot->hmap_rx_buf_pa, 0);
+ memcpy(ptr, prot->hmap_rx_buf_va, prot->hmap_rx_buf_len);
+ prot->hmaptest_rx_active = HMAPTEST_D11_RX_INACTIVE;
+ prot->hmap_rx_buf_va = NULL;
+ prot->hmap_rx_buf_len = 0;
+ PHYSADDRHISET(prot->hmap_rx_buf_pa, 0);
+ PHYSADDRLOSET(prot->hmap_rx_buf_pa, 0);
prot->hmaptest.in_progress = FALSE;
}
#endif /* DHD_HMAPTEST */
@@ -6883,7 +7139,7 @@
}
#ifdef DHD_TIMESYNC
- if (dhd->prot->rx_ts_log_enabled) {
+ if (prot->rx_ts_log_enabled) {
dhd_pkt_parse_t parse;
ts_timestamp_t *ts = (ts_timestamp_t *)&msg->ts;
@@ -6944,7 +7200,7 @@
/* After batch processing, check RX bound */
n += pkt_cnt;
- if (n >= bound) {
+ if (n >= prot->rx_cpl_post_bound) {
more = TRUE;
break;
}
@@ -6966,14 +7222,17 @@
/**
* Hands transmit packets (with a caller provided flow_id) over to dongle territory (the flow ring)
*/
-void
+bool
dhd_prot_update_txflowring(dhd_pub_t *dhd, uint16 flowid, void *msgring)
{
msgbuf_ring_t *ring = (msgbuf_ring_t *)msgring;
+ dhd_prot_t *prot = dhd->prot;
+ bool is_qempty = FALSE;
+ int ret = 0;
if (ring == NULL) {
DHD_ERROR(("%s: NULL txflowring. exiting...\n", __FUNCTION__));
- return;
+ return FALSE;
}
/* Update read pointer */
if (dhd->dma_d2h_ring_upd_support) {
@@ -6984,19 +7243,26 @@
ring->idx, flowid, ring->wr, ring->rd));
/* Need more logic here, but for now use it directly */
- dhd_bus_schedule_queue(dhd->bus, flowid, TRUE); /* from queue to flowring */
+ ret = dhd_bus_schedule_queue(dhd->bus, flowid, TRUE,
+ prot->tx_post_bound, &is_qempty); /* from queue to flowring */
+ if (ret == BCME_OK) {
+ return !is_qempty;
+ } else {
+ return FALSE;
+ }
}
/** called when DHD needs to check for 'transmit complete' messages from the dongle */
bool
-BCMFASTPATH(dhd_prot_process_msgbuf_txcpl)(dhd_pub_t *dhd, uint bound, int ringtype)
+BCMFASTPATH(dhd_prot_process_msgbuf_txcpl)(dhd_pub_t *dhd, int ringtype, uint32 *txcpl_items)
{
bool more = TRUE;
uint n = 0;
msgbuf_ring_t *ring;
unsigned long flags;
+ dhd_prot_t *prot = dhd->prot;
- ring = &dhd->prot->d2hring_tx_cpln;
+ ring = &prot->d2hring_tx_cpln;
/* Process all the messages - DTOH direction */
while (!dhd_is_device_removed(dhd)) {
@@ -7019,8 +7285,17 @@
}
DHD_RING_LOCK(ring->ring_lock, flags);
+
/* Get the address of the next message to be read from ring */
- msg_addr = dhd_prot_get_read_addr(dhd, ring, &msg_len);
+ /* must pass 'bound - n' rather than just 'bound', because
+ * within this loop, dhd_prot_get_read_addr is called multiple
+ * times, so if just 'bound' is passed we may end up reading
+ * more than 'bound' items, ex:- for a bound of 2048,
+ * during the first iteration let us say n = 2000, so the loop
+ * continues and for the second iteration n = 1000 items may be read,
+ * so the total items read will be 3000 which is > 2048
+ */
+ msg_addr = dhd_prot_get_read_addr(dhd, ring, &msg_len, prot->tx_cpl_bound - n);
DHD_RING_UNLOCK(ring->ring_lock, flags);
if (msg_addr == NULL) {
@@ -7028,6 +7303,8 @@
break;
}
+ *txcpl_items = msg_len / ring->item_len;
+
/* Prefetch data to populate the cache */
OSL_PREFETCH(msg_addr);
@@ -7041,7 +7318,8 @@
/* After batch processing, check bound */
n += msg_len / ring->item_len;
- if (n >= bound) {
+
+ if (n >= prot->tx_cpl_bound) {
break;
}
}
@@ -7074,6 +7352,14 @@
DHD_ERROR(("Firmware trapped and trap_data is 0x%04x\n", data));
}
+#if defined(PCIE_INB_DW) && defined(PCIE_INB_DSACK_EXT_WAIT)
+ if (INBAND_DW_ENAB(dhd->bus)) {
+ if (data & D2H_DEV_TRAP_DS_ACK_TIMEOUT) {
+ dhd_bus_ds_ack_debug_dump(dhd->bus);
+ }
+ }
+#endif /* PCIE_INB_DW && PCIE_INB_DSACK_EXT_WAIT */
+
if (data & D2H_DEV_EXT_TRAP_DATA)
{
if (dhd->extended_trap_data) {
@@ -7092,12 +7378,14 @@
}
/** called when DHD needs to check for 'ioctl complete' messages from the dongle */
-int
-BCMFASTPATH(dhd_prot_process_ctrlbuf)(dhd_pub_t *dhd)
+bool
+BCMFASTPATH(dhd_prot_process_ctrlbuf)(dhd_pub_t *dhd, uint32 *ctrlcpl_items)
{
dhd_prot_t *prot = dhd->prot;
msgbuf_ring_t *ring = &prot->d2hring_ctrl_cpln;
unsigned long flags;
+ uint32 n = 0;
+ bool more = TRUE;
/* Process all the messages - DTOH direction */
while (!dhd_is_device_removed(dhd)) {
@@ -7105,26 +7393,41 @@
uint32 msg_len;
if (dhd_query_bus_erros(dhd)) {
+ more = FALSE;
break;
}
if (dhd->hang_was_sent) {
+ more = FALSE;
break;
}
if (dhd->smmu_fault_occurred) {
+ more = FALSE;
break;
}
DHD_RING_LOCK(ring->ring_lock, flags);
/* Get the address of the next message to be read from ring */
- msg_addr = dhd_prot_get_read_addr(dhd, ring, &msg_len);
+ /* must pass 'bound - n' rather than just 'bound', because
+ * within this loop, dhd_prot_get_read_addr is called multiple
+ * times, so if just 'bound' is passed we may end up reading
+ * more than 'bound' items, ex:- for a bound of 2048,
+ * during the first iteration let us say n = 2000, so the loop
+ * continues and for the second iteration n = 1000 items may be read,
+ * so the total items read will be 3000 which is > 2048
+ */
+ msg_addr = dhd_prot_get_read_addr(dhd, ring, &msg_len,
+ prot->ctrl_cpl_post_bound - n);
DHD_RING_UNLOCK(ring->ring_lock, flags);
if (msg_addr == NULL) {
+ more = FALSE;
break;
}
+ *ctrlcpl_items = msg_len / ring->item_len;
+
/* Prefetch data to populate the cache */
OSL_PREFETCH(msg_addr);
if (dhd_prot_process_msgtype(dhd, ring, msg_addr, msg_len) != BCME_OK) {
@@ -7134,9 +7437,14 @@
/* Write to dngl rd ptr */
dhd_prot_upd_read_idx(dhd, ring);
+
+ n += msg_len / ring->item_len;
+ if (n >= prot->ctrl_cpl_post_bound) {
+ break;
+ }
}
- return 0;
+ return more;
}
/**
@@ -7645,6 +7953,7 @@
#if defined(DHD_PKTID_AUDIT_RING) && !defined(BCM_ROUTER_DHD)
if (DHD_PKTID_AUDIT_RING_DEBUG(dhd, dhd->prot->pktid_tx_map, pktid,
DHD_DUPLICATE_FREE, msg, D2HRING_TXCMPLT_ITEMSIZE) != BCME_OK) {
+ DHD_RING_UNLOCK(ring->ring_lock, flags);
return;
}
#endif /* DHD_PKTID_AUDIT_RING && !BCM_ROUTER_DHD */
@@ -9250,6 +9559,7 @@
}
dmaxfer->len = len;
+ DHD_ERROR(("using pattern %d, for loopback test\n", dhd->bus->lpbk_xfer_data_pattern_type));
/* Populate source with a pattern like below
* 0x00000000
@@ -9262,10 +9572,28 @@
* 0xFFFFFFFF
*/
while (i < dmaxfer->len) {
- ((uint8*)dmaxfer->srcmem.va)[i] = j % 256;
- i++;
- if (i % 4 == 0) {
- j++;
+ if (dhd->bus->lpbk_xfer_data_pattern_type == LPBK_DMA_XFER_DTPTRN_0x00) {
+ ((uint8*)dmaxfer->srcmem.va)[i] = 0x00;
+ i++;
+ }
+ else if (dhd->bus->lpbk_xfer_data_pattern_type == LPBK_DMA_XFER_DTPTRN_0xFF) {
+ ((uint8*)dmaxfer->srcmem.va)[i] = 0xFF;
+ i++;
+ }
+ else if (dhd->bus->lpbk_xfer_data_pattern_type == LPBK_DMA_XFER_DTPTRN_0x55) {
+ ((uint8*)dmaxfer->srcmem.va)[i] = 0x55;
+ i++;
+ }
+ else if (dhd->bus->lpbk_xfer_data_pattern_type == LPBK_DMA_XFER_DTPTRN_0xAA) {
+ ((uint8*)dmaxfer->srcmem.va)[i] = 0xAA;
+ i++;
+ }
+ else {
+ ((uint8*)dmaxfer->srcmem.va)[i] = j % 256;
+ i++;
+ if (i % 4 == 0) {
+ j++;
+ }
}
}
@@ -10084,6 +10412,55 @@
#endif /* EWP_EDL */
#endif /* DHD_DUMP_PCIE_RINGS */
+static void
+dhd_prot_print_ring_info(dhd_pub_t *dhd, struct bcmstrbuf *strbuf)
+{
+ dhd_prot_t *prot = dhd->prot;
+
+ bcm_bprintf(strbuf, "max RX bufs to post: %d, \t posted %d \n",
+ dhd->prot->max_rxbufpost, dhd->prot->rxbufpost);
+
+ bcm_bprintf(strbuf, "Total RX bufs posted: %d, \t RX cpl got %d \n",
+ dhd->prot->tot_rxbufpost, dhd->prot->tot_rxcpl);
+
+ bcm_bprintf(strbuf, "Total TX packets: %lu, \t TX cpl got %lu \n",
+ dhd->actual_tx_pkts, dhd->tot_txcpl);
+
+ bcm_bprintf(strbuf,
+ "%14s %18s %18s %17s %17s %14s %14s %10s\n",
+ "Type", "TRD: HLRD: HDRD", "TWR: HLWR: HDWR", "BASE(VA)", "BASE(PA)",
+ "WORK_ITEM_SIZE", "MAX_WORK_ITEMS", "TOTAL_SIZE");
+ bcm_bprintf(strbuf, "%14s", "H2DCtrlPost");
+ dhd_prot_print_flow_ring(dhd, &prot->h2dring_ctrl_subn, TRUE, strbuf,
+ " %5d:%5d:%5d %5d:%5d:%5d %17p %8x:%8x %14d %14d %10d\n");
+ bcm_bprintf(strbuf, "%14s", "D2HCtrlCpl");
+ dhd_prot_print_flow_ring(dhd, &prot->d2hring_ctrl_cpln, FALSE, strbuf,
+ " %5d:%5d:%5d %5d:%5d:%5d %17p %8x:%8x %14d %14d %10d\n");
+ bcm_bprintf(strbuf, "%14s", "H2DRxPost");
+ dhd_prot_print_flow_ring(dhd, &prot->h2dring_rxp_subn, TRUE, strbuf,
+ " %5d:%5d:%5d %5d:%5d:%5d %17p %8x:%8x %14d %14d %10d\n");
+ bcm_bprintf(strbuf, "%14s", "D2HRxCpl");
+ dhd_prot_print_flow_ring(dhd, &prot->d2hring_rx_cpln, FALSE, strbuf,
+ " %5d:%5d:%5d %5d:%5d:%5d %17p %8x:%8x %14d %14d %10d\n");
+ bcm_bprintf(strbuf, "%14s", "D2HTxCpl");
+ dhd_prot_print_flow_ring(dhd, &prot->d2hring_tx_cpln, FALSE, strbuf,
+ " %5d:%5d:%5d %5d:%5d:%5d %17p %8x:%8x %14d %14d %10d\n");
+ if (dhd->prot->h2dring_info_subn != NULL && dhd->prot->d2hring_info_cpln != NULL) {
+ bcm_bprintf(strbuf, "%14s", "H2DRingInfoSub");
+ dhd_prot_print_flow_ring(dhd, prot->h2dring_info_subn, TRUE, strbuf,
+ " %5d:%5d:%5d %5d:%5d:%5d %17p %8x:%8x %14d %14d %10d\n");
+ bcm_bprintf(strbuf, "%14s", "D2HRingInfoCpl");
+ dhd_prot_print_flow_ring(dhd, prot->d2hring_info_cpln, FALSE, strbuf,
+ " %5d:%5d:%5d %5d:%5d:%5d %17p %8x:%8x %14d %14d %10d\n");
+ }
+ if (dhd->prot->d2hring_edl != NULL) {
+ bcm_bprintf(strbuf, "%14s", "D2HRingEDL");
+ dhd_prot_print_flow_ring(dhd, prot->d2hring_edl, FALSE, strbuf,
+ " %5d:%5d:%5d %5d:%5d:%5d %17p %8x:%8x %14d %14d %10d\n");
+ }
+ bcm_bprintf(strbuf, "\n");
+}
+
/** Add prot dump output to a buffer */
void dhd_prot_dump(dhd_pub_t *dhd, struct bcmstrbuf *b)
{
@@ -10104,6 +10481,19 @@
dhd->dma_h2d_ring_upd_support,
dhd->dma_d2h_ring_upd_support,
dhd->prot->rw_index_sz);
+#ifdef DHD_DMA_INDICES_SEQNUM
+ bcm_bprintf(b, "host_seqnum %u dngl_seqnum %u\n", dhd_prot_read_seqnum(dhd, TRUE),
+ dhd_prot_read_seqnum(dhd, FALSE));
+#endif /* DHD_DMA_INDICES_SEQNUM */
+
+ dhd_prot_counters(dhd, b, FALSE, FALSE);
+}
+
+void dhd_prot_counters(dhd_pub_t *dhd, struct bcmstrbuf *b,
+ bool print_ringinfo, bool print_pktidinfo)
+{
+ bcm_bprintf(b, "\nTX Post, doorbell(DB) stats:\n======================\n");
+
bcm_bprintf(b, "h2d_max_txpost: %d, prot->h2d_max_txpost: %d\n",
h2d_max_txpost, dhd->prot->h2d_max_txpost);
if (dhd->htput_support) {
@@ -10114,18 +10504,36 @@
bcm_bprintf(b, "pktid_txq_stop_cnt: %d\n", dhd->prot->pktid_txq_stop_cnt);
bcm_bprintf(b, "pktid_depleted_cnt: %d\n", dhd->prot->pktid_depleted_cnt);
bcm_bprintf(b, "txcpl_db_cnt: %d\n", dhd->prot->txcpl_db_cnt);
-#ifdef DHD_DMA_INDICES_SEQNUM
- bcm_bprintf(b, "host_seqnum %u dngl_seqnum %u\n", dhd_prot_read_seqnum(dhd, TRUE),
- dhd_prot_read_seqnum(dhd, FALSE));
-#endif /* DHD_DMA_INDICES_SEQNUM */
bcm_bprintf(b, "tx_h2d_db_cnt:%llu\n", dhd->prot->tx_h2d_db_cnt);
+ bcm_bprintf(b, "\n");
+
#ifdef AGG_H2D_DB
+ bcm_bprintf(b, "Aggregated DB, workitem stats:\n======================\n");
bcm_bprintf(b, "agg_h2d_db_enab:%d agg_h2d_db_timeout:%d agg_h2d_db_inflight_thresh:%d\n",
agg_h2d_db_enab, agg_h2d_db_timeout, agg_h2d_db_inflight_thresh);
bcm_bprintf(b, "agg_h2d_db: timer_db_cnt:%d direct_db_cnt:%d\n",
dhd->prot->agg_h2d_db_info.timer_db_cnt, dhd->prot->agg_h2d_db_info.direct_db_cnt);
dhd_agg_inflight_stats_dump(dhd, b);
#endif /* AGG_H2D_DB */
+ bcm_bprintf(b, "\nrx_buf_burst: %d\n", dhd->prot->rx_buf_burst);
+ bcm_bprintf(b, "\n");
+
+ if (print_ringinfo) {
+ bcm_bprintf(b, "\nRing Info:\n=========\n");
+ bcm_bprintf(b, "[RD=read ptr; WR=write ptr; T=TCM; H=Host;"
+ " L=Local; D=DMA index'd]\n");
+ dhd_prot_print_ring_info(dhd, b);
+ }
+
+ if (print_pktidinfo) {
+ bcm_bprintf(b, "active_tx_count %d pktidmap_avail(ctrl/rx/tx) %d %d %d\n",
+ OSL_ATOMIC_READ(dhd->osh, &dhd->prot->active_tx_count),
+ DHD_PKTID_AVAIL(dhd->prot->pktid_ctrl_map),
+ DHD_PKTID_AVAIL(dhd->prot->pktid_rx_map),
+ DHD_PKTID_AVAIL(dhd->prot->pktid_tx_map));
+ }
+
+ bcm_bprintf(b, "\n");
}
/* Update local copy of dongle statistics */
@@ -11652,10 +12060,11 @@
/**
* Called on checking for 'completion' messages from the dongle. Returns next host buffer to read
- * from, or NULL if there are no more messages to read.
+ * from, or NULL if there are no more messages to read. If 'bound' is non-zero, limits
+ * the no. of items read to bound
*/
static uint8*
-dhd_prot_get_read_addr(dhd_pub_t *dhd, msgbuf_ring_t *ring, uint32 *available_len)
+dhd_prot_get_read_addr(dhd_pub_t *dhd, msgbuf_ring_t *ring, uint32 *available_len, uint32 bound)
{
uint16 wr;
uint16 rd;
@@ -11663,6 +12072,10 @@
uint16 items;
void *read_addr = NULL; /* address of next msg to be read in ring */
uint16 d2h_wr = 0;
+ void *md_read_addr = NULL; /* address of next msg to be read in ring */
+ int i;
+ uint8 *ptr = NULL;
+ uint32 total_md_len = 0;
DHD_TRACE(("%s: d2h_dma_indx_rd_buf %p, d2h_dma_indx_wr_buf %p\n",
__FUNCTION__, (uint32 *)(dhd->prot->d2h_dma_indx_rd_buf.va),
@@ -11731,6 +12144,11 @@
/* if space is available, calculate address to be read */
read_addr = (char*)ring->dma_buf.va + (rd * ring->item_len);
+ /* limit no. of items to bound */
+ if (bound) {
+ items = MIN(items, bound);
+ }
+
/* update read pointer */
if ((ring->rd + items) >= ring->max_items)
ring->rd = 0;
@@ -11745,6 +12163,36 @@
/* XXX Double cache invalidate for ARM with L2 cache/prefetch */
OSL_CACHE_INV(read_addr, *available_len);
+ if (ring->linked_ring) {
+ md_read_addr = (char*)ring->linked_ring->dma_buf.va +
+ (rd * ring->linked_ring->item_len);
+ total_md_len = (uint32)(items * ring->linked_ring->item_len);
+ OSL_CACHE_INV(md_read_addr, total_md_len);
+ /* Prefetch data to populate the cache */
+ DHD_INFO(("ring address:0x%p, mdring address:0x%p, item:%d:%d\n",
+ read_addr, md_read_addr, items, total_md_len));
+ if (dhd->mdring_info) {
+ ptr = (uint8 *)md_read_addr;
+ for (i = 0; i < items; i ++) {
+ ptr += ring->linked_ring->item_len;
+ DHD_INFO(("md:0x%x:0x%x:0x%x:0x%x 0x%x:0x%x:0x%x:0x%x\n",
+ ptr[0], ptr[1], ptr[2], ptr[3],
+ ptr[4], ptr[5], ptr[6], ptr[7]));
+ if (memcpy_s(&dhd->mdring_info[dhd->md_item_count *
+ ring->linked_ring->item_len],
+ ring->linked_ring->item_len, ptr,
+ ring->linked_ring->item_len) != BCME_OK) {
+ DHD_ERROR(("%s:Couldn't copy md item:%d,len:%d\n",
+ __FUNCTION__,
+ i, ring->linked_ring->item_len));
+ break;
+ }
+ dhd->md_item_count =
+ (dhd->md_item_count + 1) % MAX_MDRING_ITEM_DUMP;
+ }
+ }
+ }
+
/* return read address */
return read_addr;
@@ -11774,8 +12222,10 @@
if ((INBAND_DW_ENAB(dhd->bus)) &&
(dhdpcie_bus_get_pcie_inband_dw_state(dhd->bus) ==
DW_DEVICE_DS_DEV_SLEEP)) {
- if (mb_data == H2D_HOST_CONS_INT) {
+ if (mb_data == H2D_HOST_CONS_INT || mb_data == H2D_HOST_PTM_ENABLE ||
+ mb_data == H2D_HOST_PTM_DISABLE) {
/* One additional device_wake post needed */
+ DHD_INFO(("%s One additional device_wake post needed\n", __FUNCTION__));
num_post = 2;
}
}
@@ -11816,7 +12266,8 @@
h2d_mb_data->mail_box_data = htol32(mb_data);
}
- DHD_INFO(("%s Send H2D MB data Req data 0x%04x\n", __FUNCTION__, mb_data));
+ DHD_INFO(("%s Send H2D MB data Req data 0x%04x\n", __FUNCTION__,
+ h2d_mb_data->mail_box_data));
/* upd wrt ptr and raise interrupt */
dhd_prot_ring_write_complete_mbdata(dhd, ctrl_ring, h2d_mb_data,
@@ -12006,6 +12457,7 @@
ltoh32(resp->cmn_hdr.request_id)));
if ((ltoh32(resp->cmn_hdr.request_id) != DHD_D2H_DBGRING_REQ_PKTID) &&
(ltoh32(resp->cmn_hdr.request_id) != DHD_D2H_BTLOGRING_REQ_PKTID) &&
+ (ltoh32(resp->cmn_hdr.request_id) != DHD_D2H_MDRING_REQ_PKTID) &&
TRUE) {
DHD_ERROR(("invalid request ID with d2h ring create complete\n"));
return;
@@ -12063,6 +12515,21 @@
dhd->prot->d2hring_btlog_cpln->inited = TRUE;
}
#endif /* BTLOG */
+ if (dhd->prot->d2hring_md_cpl &&
+ ltoh32(resp->cmn_hdr.request_id) == DHD_D2H_MDRING_REQ_PKTID) {
+ if (!dhd->prot->d2hring_md_cpl->create_pending) {
+ DHD_ERROR(("metadata ring create status for not pending cpl ring\n"));
+ return;
+ }
+
+ if (ltoh16(resp->cmplt.status) != BCMPCIE_SUCCESS) {
+ DHD_ERROR(("metadata cpl ring create failed with status %d\n",
+ ltoh16(resp->cmplt.status)));
+ return;
+ }
+ dhd->prot->d2hring_md_cpl->create_pending = FALSE;
+ dhd->prot->d2hring_md_cpl->inited = TRUE;
+ }
}
static void
@@ -12157,73 +12624,34 @@
{
dhd_prot_t *prot = dhd->prot;
bcm_bprintf(strbuf, "IPCrevs: Dev %d, \t Host %d, \tactive %d\n",
- dhd->prot->device_ipc_version,
- dhd->prot->host_ipc_version,
- dhd->prot->active_ipc_version);
+ prot->device_ipc_version,
+ prot->host_ipc_version,
+ prot->active_ipc_version);
bcm_bprintf(strbuf, "max Host TS bufs to post: %d, \t posted %d \n",
- dhd->prot->max_tsbufpost, dhd->prot->cur_ts_bufs_posted);
+ prot->max_tsbufpost, prot->cur_ts_bufs_posted);
bcm_bprintf(strbuf, "max INFO bufs to post: %d, \t posted %d \n",
- dhd->prot->max_infobufpost, dhd->prot->infobufpost);
+ prot->max_infobufpost, prot->infobufpost);
#ifdef BTLOG
bcm_bprintf(strbuf, "max BTLOG bufs to post: %d, \t posted %d \n",
- dhd->prot->max_btlogbufpost, dhd->prot->btlogbufpost);
+ prot->max_btlogbufpost, prot->btlogbufpost);
#endif /* BTLOG */
bcm_bprintf(strbuf, "max event bufs to post: %d, \t posted %d \n",
- dhd->prot->max_eventbufpost, dhd->prot->cur_event_bufs_posted);
+ prot->max_eventbufpost, prot->cur_event_bufs_posted);
bcm_bprintf(strbuf, "max ioctlresp bufs to post: %d, \t posted %d \n",
- dhd->prot->max_ioctlrespbufpost, dhd->prot->cur_ioctlresp_bufs_posted);
- bcm_bprintf(strbuf, "max RX bufs to post: %d, \t posted %d \n",
- dhd->prot->max_rxbufpost, dhd->prot->rxbufpost);
+ prot->max_ioctlrespbufpost, prot->cur_ioctlresp_bufs_posted);
- bcm_bprintf(strbuf, "Total RX bufs posted: %d, \t RX cpl got %d \n",
- dhd->prot->tot_rxbufpost, dhd->prot->tot_rxcpl);
-
- bcm_bprintf(strbuf, "Total TX packets: %lu, \t TX cpl got %lu \n",
- dhd->actual_tx_pkts, dhd->tot_txcpl);
-
- bcm_bprintf(strbuf,
- "%14s %18s %18s %17s %17s %14s %14s %10s\n",
- "Type", "TRD: HLRD: HDRD", "TWR: HLWR: HDWR", "BASE(VA)", "BASE(PA)",
- "WORK_ITEM_SIZE", "MAX_WORK_ITEMS", "TOTAL_SIZE");
- bcm_bprintf(strbuf, "%14s", "H2DCtrlPost");
- dhd_prot_print_flow_ring(dhd, &prot->h2dring_ctrl_subn, TRUE, strbuf,
- " %5d:%5d:%5d %5d:%5d:%5d %17p %8x:%8x %14d %14d %10d\n");
- bcm_bprintf(strbuf, "%14s", "D2HCtrlCpl");
- dhd_prot_print_flow_ring(dhd, &prot->d2hring_ctrl_cpln, FALSE, strbuf,
- " %5d:%5d:%5d %5d:%5d:%5d %17p %8x:%8x %14d %14d %10d\n");
- bcm_bprintf(strbuf, "%14s", "H2DRxPost");
- dhd_prot_print_flow_ring(dhd, &prot->h2dring_rxp_subn, TRUE, strbuf,
- " %5d:%5d:%5d %5d:%5d:%5d %17p %8x:%8x %14d %14d %10d\n");
- bcm_bprintf(strbuf, "%14s", "D2HRxCpl");
- dhd_prot_print_flow_ring(dhd, &prot->d2hring_rx_cpln, FALSE, strbuf,
- " %5d:%5d:%5d %5d:%5d:%5d %17p %8x:%8x %14d %14d %10d\n");
- bcm_bprintf(strbuf, "%14s", "D2HTxCpl");
- dhd_prot_print_flow_ring(dhd, &prot->d2hring_tx_cpln, FALSE, strbuf,
- " %5d:%5d:%5d %5d:%5d:%5d %17p %8x:%8x %14d %14d %10d\n");
- if (dhd->prot->h2dring_info_subn != NULL && dhd->prot->d2hring_info_cpln != NULL) {
- bcm_bprintf(strbuf, "%14s", "H2DRingInfoSub");
- dhd_prot_print_flow_ring(dhd, prot->h2dring_info_subn, TRUE, strbuf,
- " %5d:%5d:%5d %5d:%5d:%5d %17p %8x:%8x %14d %14d %10d\n");
- bcm_bprintf(strbuf, "%14s", "D2HRingInfoCpl");
- dhd_prot_print_flow_ring(dhd, prot->d2hring_info_cpln, FALSE, strbuf,
- " %5d:%5d:%5d %5d:%5d:%5d %17p %8x:%8x %14d %14d %10d\n");
- }
- if (dhd->prot->d2hring_edl != NULL) {
- bcm_bprintf(strbuf, "%14s", "D2HRingEDL");
- dhd_prot_print_flow_ring(dhd, prot->d2hring_edl, FALSE, strbuf,
- " %5d:%5d:%5d %5d:%5d:%5d %17p %8x:%8x %14d %14d %10d\n");
- }
-
- bcm_bprintf(strbuf, "Total wakeup packet rcvd: Event:%d,\t RX:%d,\t Info:%d\n",
- dhd->prot->event_wakeup_pkt, dhd->prot->rx_wakeup_pkt,
- dhd->prot->info_wakeup_pkt);
+ dhd_prot_print_ring_info(dhd, strbuf);
bcm_bprintf(strbuf, "active_tx_count %d pktidmap_avail(ctrl/rx/tx) %d %d %d\n",
- OSL_ATOMIC_READ(dhd->osh, &dhd->prot->active_tx_count),
- DHD_PKTID_AVAIL(dhd->prot->pktid_ctrl_map),
- DHD_PKTID_AVAIL(dhd->prot->pktid_rx_map),
- DHD_PKTID_AVAIL(dhd->prot->pktid_tx_map));
+ OSL_ATOMIC_READ(dhd->osh, &prot->active_tx_count),
+ DHD_PKTID_AVAIL(prot->pktid_ctrl_map),
+ DHD_PKTID_AVAIL(prot->pktid_rx_map),
+ DHD_PKTID_AVAIL(prot->pktid_tx_map));
+
+ bcm_bprintf(strbuf, "Total wakeup packet rcvd: Event:%d,\t RX:%d,\t Info:%d\n",
+ prot->event_wakeup_pkt, prot->rx_wakeup_pkt,
+ prot->info_wakeup_pkt);
#ifdef DHD_MMIO_TRACE
dhd_dump_bus_mmio_trace(dhd->bus, strbuf);
@@ -12531,9 +12959,36 @@
static void
dhd_prot_process_d2h_ring_config_complete(dhd_pub_t *dhd, void *msg)
{
- DHD_INFO(("%s: Ring Config Response - status %d ringid %d\n",
+ ring_config_resp_t *ring_config_resp = (ring_config_resp_t *)msg;
+ dhd_prot_t *prot = dhd->prot;
+ msgbuf_ring_t *cpl_ring = NULL;
+
+ DHD_INFO(("%s: Ring Config Response - status %d ringid %d subtype:%d\n",
__FUNCTION__, ltoh16(((ring_config_resp_t *)msg)->compl_hdr.status),
- ltoh16(((ring_config_resp_t *)msg)->compl_hdr.flow_ring_id)));
+ ltoh16(((ring_config_resp_t *)msg)->compl_hdr.flow_ring_id),
+ ltoh16(((ring_config_resp_t *)msg)->subtype)));
+
+ if (ltoh16(ring_config_resp->compl_hdr.status) == 0) {
+ if (ring_config_resp->subtype ==
+ htol16(D2H_RING_CONFIG_SUBTYPE_MDATA_LINK)) {
+ cpl_ring = prot->d2hring_md_cpl->linked_ring;
+ cpl_ring->linked_ring = prot->d2hring_md_cpl;
+ }
+ else if (ring_config_resp->subtype ==
+ htol16(D2H_RING_CONFIG_SUBTYPE_MDATA_UNLINK)) {
+ cpl_ring = prot->d2hring_md_cpl->linked_ring;
+ cpl_ring->linked_ring = NULL;
+ prot->d2hring_md_cpl->linked_ring = NULL;
+ bzero(dhd->mdring_info,
+ (MAX_MDRING_ITEM_DUMP * D2HRING_MDCMPLT_ITEMSIZE));
+ }
+ } else {
+ DHD_ERROR(("%s: Ring Config Failed - status %d ringid %d subtype:%d\n",
+ __FUNCTION__, ltoh16(((ring_config_resp_t *)msg)->compl_hdr.status),
+ ltoh16(((ring_config_resp_t *)msg)->compl_hdr.flow_ring_id),
+ ltoh16(((ring_config_resp_t *)msg)->subtype)));
+ prot->d2hring_md_cpl->linked_ring = NULL;
+ }
}
#ifdef WL_CFGVENDOR_SEND_HANG_EVENT
@@ -13719,9 +14174,9 @@
static void dump_psmwd_v1(const bcm_tlv_t *tlv, struct bcmstrbuf *b)
{
- const hnd_ext_trap_psmwd_v1_t* psmwd = NULL;
+ const hnd_ext_trap_psmwd_v1_t* psmwd = (const hnd_ext_trap_psmwd_v1_t *)tlv->data;
uint32 i;
- psmwd = (const hnd_ext_trap_psmwd_v1_t *)tlv;
+
for (i = 0; i < PSMDBG_REG_READ_CNT_FOR_PSMWDTRAP_V1; i++) {
bcm_bprintf(b, " psmdebug[%d]: 0x%x\n", i, psmwd->i32_psmdebug[i]);
}
@@ -13753,9 +14208,9 @@
static void dump_psmwd_v2(const bcm_tlv_t *tlv, struct bcmstrbuf *b)
{
- const hnd_ext_trap_psmwd_t* psmwd = NULL;
+ const hnd_ext_trap_psmwd_v2_t* psmwd = (const hnd_ext_trap_psmwd_v2_t *)tlv->data;
uint32 i;
- psmwd = (const hnd_ext_trap_psmwd_t *)tlv;
+
for (i = 0; i < PSMDBG_REG_READ_CNT_FOR_PSMWDTRAP_V2; i++) {
bcm_bprintf(b, " psmdebug[%d]: 0x%x\n", i, psmwd->i32_psmdebug[i]);
}
@@ -13790,6 +14245,130 @@
bcm_bprintf(b, " shm_txphyerr_cnt: 0x%x\n", psmwd->shm_txphyerr_cnt);
}
+static void dump_psmwd_v3(const bcm_tlv_t *tlv, struct bcmstrbuf *b)
+{
+ const hnd_ext_trap_psmwd_v3_t* psmwd = (const hnd_ext_trap_psmwd_v3_t *)tlv->data;
+ uint32 i;
+
+ for (i = 0; i < PSMDBG_REG_READ_CNT_FOR_PSMWDTRAP_V1; i++) {
+ bcm_bprintf(b, " psmdebug[%d]: 0x%x\n", i, psmwd->i32_psmdebug[i]);
+ }
+
+ bcm_bprintf(b, " i32_gated_clock_en: 0x%x\n", psmwd->i32_gated_clock_en);
+ bcm_bprintf(b, " Rcv Fifo Ctrl: 0x%x\n", psmwd->rcv_fifo_ctrl);
+ bcm_bprintf(b, " Rx ctrl 1: 0x%x\n", psmwd->rx_ctrl1);
+ bcm_bprintf(b, " Rxe Status 1: 0x%x\n", psmwd->rxe_status1);
+ bcm_bprintf(b, " Rxe Status 2: 0x%x\n", psmwd->rxe_status2);
+
+ bcm_bprintf(b, " rcv wrd count 0: 0x%x\n", psmwd->rcv_wrd_count0);
+ bcm_bprintf(b, " rcv wrd count 1: 0x%x\n", psmwd->rcv_wrd_count1);
+ bcm_bprintf(b, " RCV_LFIFO_STS: 0x%x\n", psmwd->rcv_lfifo_sts);
+ bcm_bprintf(b, " PSM_SLP_TMR: 0x%x\n", psmwd->psm_slp_tmr);
+ bcm_bprintf(b, " PSM BRC: 0x%x\n", psmwd->psm_brc);
+
+ bcm_bprintf(b, " TXE CTRL: 0x%x\n", psmwd->txe_ctrl);
+ bcm_bprintf(b, " TXE Status: 0x%x\n", psmwd->txe_status);
+ bcm_bprintf(b, " TXE_xmtdmabusy: 0x%x\n", psmwd->txe_xmtdmabusy);
+ bcm_bprintf(b, " TXE_XMTfifosuspflush: 0x%x\n", psmwd->txe_xmt_fifo_susp_flush);
+ bcm_bprintf(b, " IFS Stat: 0x%x\n", psmwd->ifs_stat);
+
+ bcm_bprintf(b, " IFS_MEDBUSY_CTR: 0x%x\n", psmwd->ifs_medbusy_ctr);
+ bcm_bprintf(b, " IFS_TX_DUR: 0x%x\n", psmwd->ifs_tx_dur);
+ bcm_bprintf(b, " SLow_CTL: 0x%x\n", psmwd->slow_ctl);
+ bcm_bprintf(b, " TXE_AQM fifo Ready: 0x%x\n", psmwd->txe_aqm_fifo_ready);
+ bcm_bprintf(b, " Dagg ctrl: 0x%x\n", psmwd->dagg_ctrl);
+
+ bcm_bprintf(b, " shm_prewds_cnt: 0x%x\n", psmwd->shm_prewds_cnt);
+ bcm_bprintf(b, " shm_txtplufl_cnt: 0x%x\n", psmwd->shm_txtplufl_cnt);
+ bcm_bprintf(b, " shm_txphyerr_cnt: 0x%x\n", psmwd->shm_txphyerr_cnt);
+}
+
+static void dump_psmwd(const bcm_tlv_t *tlv, struct bcmstrbuf *b)
+{
+ const hnd_ext_trap_psmwd_v1_t * psmwd = (const hnd_ext_trap_psmwd_v1_t*)tlv->data;
+
+ if (psmwd->version == 0 || psmwd->version > HND_EXT_TRAP_PSMWD_INFO_VER_3) {
+ bcm_bprintf(b, " Bad version: 0x%x\n", psmwd->version);
+ return;
+ }
+ bcm_bprintf(b, " version: 0x%x\n", psmwd->version);
+ bcm_bprintf(b, " maccontrol: 0x%x\n", psmwd->i32_maccontrol);
+ bcm_bprintf(b, " maccommand: 0x%x\n", psmwd->i32_maccommand);
+ bcm_bprintf(b, " macintstatus: 0x%x\n", psmwd->i32_macintstatus);
+ bcm_bprintf(b, " phydebug: 0x%x\n", psmwd->i32_phydebug);
+ bcm_bprintf(b, " clk_ctl_st: 0x%x\n", psmwd->i32_clk_ctl_st);
+ if (psmwd->version == HND_EXT_TRAP_PSMWD_INFO_VER_1) {
+ dump_psmwd_v1(tlv, b);
+ } else if (psmwd->version == HND_EXT_TRAP_PSMWD_INFO_VER_2) {
+ dump_psmwd_v2(tlv, b);
+ } else if (psmwd->version == HND_EXT_TRAP_PSMWD_INFO_VER_3) {
+ dump_psmwd_v3(tlv, b);
+ }
+ return;
+}
+
+static void dump_macwake_v1(const bcm_tlv_t *tlv, struct bcmstrbuf *b)
+{
+ const hnd_ext_trap_macenab_v1_t* macwake = (const hnd_ext_trap_macenab_v1_t *)tlv->data;
+
+ bcm_bprintf(b, " gated clock en: 0x%x\n", macwake->i16_0x1a8);
+ bcm_bprintf(b, " PSM_SLP_TMR: 0x%x\n", macwake->i16_0x480);
+ bcm_bprintf(b, " PSM BRC: 0x%x\n", macwake->i16_0x490);
+ bcm_bprintf(b, " TSF CTL: 0x%x\n", macwake->i16_0x600);
+ bcm_bprintf(b, " IFS Stat: 0x%x\n", macwake->i16_0x690);
+ bcm_bprintf(b, " IFS_MEDBUSY_CTR: 0x%x\n", macwake->i16_0x692);
+ bcm_bprintf(b, " Slow_CTL: 0x%x\n", macwake->i16_0x6a0);
+ bcm_bprintf(b, " Slow_FRAC: 0x%x\n", macwake->i16_0x6a6);
+ bcm_bprintf(b, " fast power up delay: 0x%x\n", macwake->i16_0x6a8);
+ bcm_bprintf(b, " Slow_PER: 0x%x\n", macwake->i16_0x6aa);
+ bcm_bprintf(b, " shm_ucode_dbgst: 0x%x\n", macwake->shm_ucode_dbgst);
+}
+
+static void dump_macwake_v2(const bcm_tlv_t *tlv, struct bcmstrbuf *b)
+{
+ const hnd_ext_trap_macenab_v2_t* macwake = (const hnd_ext_trap_macenab_v2_t *)tlv->data;
+
+ bcm_bprintf(b, " gated clock en: 0x%x\n", macwake->i32_gated_clock_en);
+ bcm_bprintf(b, " PSM_SLP_TMR: 0x%x\n", macwake->psm_slp_tmr);
+ bcm_bprintf(b, " PSM BRC: 0x%x\n", macwake->psm_brc);
+ bcm_bprintf(b, " TSF CTL: 0x%x\n", macwake->tsf_ctl);
+ bcm_bprintf(b, " IFS Stat: 0x%x\n", macwake->ifs_stat);
+ bcm_bprintf(b, " IFS_MEDBUSY_CTR: 0x%x\n", macwake->ifs_medbusy_ctr);
+ bcm_bprintf(b, " Slow_CTL: 0x%x\n", macwake->slow_ctl);
+ bcm_bprintf(b, " Slow_FRAC: 0x%x\n", macwake->slow_frac);
+ bcm_bprintf(b, " fast power up delay: 0x%x\n", macwake->fast_powerup_delay);
+ bcm_bprintf(b, " Slow_PER: 0x%x\n", macwake->slow_per);
+ bcm_bprintf(b, " shm_ucode_dbgst: 0x%x\n", macwake->shm_ucode_dbgst);
+}
+
+static void dump_macwake(const bcm_tlv_t *tlv, struct bcmstrbuf *b)
+{
+ const hnd_ext_trap_macenab_v1_t* macwake = (const hnd_ext_trap_macenab_v1_t *)tlv->data;
+ uint32 i;
+
+ if (macwake->version == 0 || macwake->version > HND_EXT_TRAP_MACENAB_INFO_VER_2) {
+ bcm_bprintf(b, " Bad version: 0x%x\n", macwake->version);
+ return;
+ }
+
+ bcm_bprintf(b, " version: 0x%x\n", macwake->version);
+ bcm_bprintf(b, " trap_reason: 0x%x\n", macwake->trap_reason);
+ bcm_bprintf(b, " maccontrol: 0x%x\n", macwake->i32_maccontrol);
+ bcm_bprintf(b, " maccommand: 0x%x\n", macwake->i32_maccommand);
+ bcm_bprintf(b, " macintstatus: 0x%x\n", macwake->i32_macintstatus);
+ for (i = 0; i < 8; i++)
+ bcm_bprintf(b, " psmdebug[%d]: 0x%x\n", i, macwake->i32_psmdebug[i]);
+ bcm_bprintf(b, " clk_ctl_st: 0x%x\n", macwake->i32_clk_ctl_st);
+ bcm_bprintf(b, " powerctl: 0x%x\n", macwake->i32_powerctl);
+
+ if (macwake->version == HND_EXT_TRAP_MACENAB_INFO_VER_1) {
+ dump_macwake_v1(tlv, b);
+ } else if (macwake->version == HND_EXT_TRAP_MACENAB_INFO_VER_2) {
+ dump_macwake_v2(tlv, b);
+ }
+ return;
+}
+
static const char* etd_trap_name(hnd_ext_tag_trap_t tag)
{
switch (tag) {
@@ -14025,22 +14604,8 @@
tlv = bcm_parse_tlvs(hdr->data, hdr->len, TAG_TRAP_PSM_WD);
if (tlv) {
- const hnd_ext_trap_psmwd_t* psmwd;
-
bcm_bprintf(b, "\n%s len: %d\n", etd_trap_name(TAG_TRAP_PSM_WD), tlv->len);
- psmwd = (const hnd_ext_trap_psmwd_t *)tlv->data;
- bcm_bprintf(b, " version: 0x%x\n", psmwd->version);
- bcm_bprintf(b, " maccontrol: 0x%x\n", psmwd->i32_maccontrol);
- bcm_bprintf(b, " maccommand: 0x%x\n", psmwd->i32_maccommand);
- bcm_bprintf(b, " macintstatus: 0x%x\n", psmwd->i32_macintstatus);
- bcm_bprintf(b, " phydebug: 0x%x\n", psmwd->i32_phydebug);
- bcm_bprintf(b, " clk_ctl_st: 0x%x\n", psmwd->i32_clk_ctl_st);
- if (psmwd->version == 1) {
- dump_psmwd_v1(tlv, b);
- }
- if (psmwd->version == 2) {
- dump_psmwd_v2(tlv, b);
- }
+ dump_psmwd(tlv, b);
}
/* PHY TxErr MacDump */
tlv = bcm_parse_tlvs(hdr->data, hdr->len, TAG_TRAP_PHYTXERR_THRESH);
@@ -14114,29 +14679,8 @@
tlv = bcm_parse_tlvs(hdr->data, hdr->len, TAG_TRAP_MAC_WAKE);
if (tlv) {
- const hnd_ext_trap_macenab_t* macwake;
bcm_bprintf(b, "\n%s len: %d\n", etd_trap_name(TAG_TRAP_MAC_WAKE), tlv->len);
- macwake = (const hnd_ext_trap_macenab_t *)tlv->data;
- bcm_bprintf(b, " version: 0x%x\n", macwake->version);
- bcm_bprintf(b, " trap_reason: 0x%x\n", macwake->trap_reason);
- bcm_bprintf(b, " maccontrol: 0x%x\n", macwake->i32_maccontrol);
- bcm_bprintf(b, " maccommand: 0x%x\n", macwake->i32_maccommand);
- bcm_bprintf(b, " macintstatus: 0x%x\n", macwake->i32_macintstatus);
- for (i = 0; i < 8; i++)
- bcm_bprintf(b, " psmdebug[%d]: 0x%x\n", i, macwake->i32_psmdebug[i]);
- bcm_bprintf(b, " clk_ctl_st: 0x%x\n", macwake->i32_clk_ctl_st);
- bcm_bprintf(b, " powerctl: 0x%x\n", macwake->i32_powerctl);
- bcm_bprintf(b, " gated clock en: 0x%x\n", macwake->i16_0x1a8);
- bcm_bprintf(b, " PSM_SLP_TMR: 0x%x\n", macwake->i16_0x480);
- bcm_bprintf(b, " PSM BRC: 0x%x\n", macwake->i16_0x490);
- bcm_bprintf(b, " TSF CTL: 0x%x\n", macwake->i16_0x600);
- bcm_bprintf(b, " IFS Stat: 0x%x\n", macwake->i16_0x690);
- bcm_bprintf(b, " IFS_MEDBUSY_CTR: 0x%x\n", macwake->i16_0x692);
- bcm_bprintf(b, " Slow_CTL: 0x%x\n", macwake->i16_0x6a0);
- bcm_bprintf(b, " Slow_FRAC: 0x%x\n", macwake->i16_0x6a6);
- bcm_bprintf(b, " fast power up delay: 0x%x\n", macwake->i16_0x6a8);
- bcm_bprintf(b, " Slow_PER: 0x%x\n", macwake->i16_0x6aa);
- bcm_bprintf(b, " shm_ucode_dbgst: 0x%x\n", macwake->shm_ucode_dbgst);
+ dump_macwake(tlv, b);
}
tlv = bcm_parse_tlvs(hdr->data, hdr->len, TAG_TRAP_BUS);
@@ -14516,6 +15060,152 @@
return BCME_OK;
}
+static uint16
+dhd_d2h_cpl_ring_id(dhd_pub_t *dhd, msgbuf_ring_t *ring)
+{
+ uint16 max_h2d_rings = dhd->bus->max_submission_rings;
+ dhd_prot_t *prot = dhd->prot;
+
+ if (ring == &prot->d2hring_tx_cpln)
+ return prot->d2hring_tx_cpln.idx;
+ if (ring == &prot->d2hring_rx_cpln)
+ return prot->d2hring_rx_cpln.idx;
+
+ return (DHD_D2H_RING_OFFSET(ring->idx, max_h2d_rings) +
+ BCMPCIE_D2H_COMMON_MSGRINGS);
+}
+
+static int
+dhd_d2h_id_from_cpl_ring_idx(dhd_pub_t *dhd, uint16 idx)
+{
+ dhd_prot_t *prot = dhd->prot;
+
+ if (prot->d2hring_tx_cpln.idx == idx) {
+ return DHD_METADATA_D2H_TXCPL;
+ }
+ if (prot->d2hring_rx_cpln.idx == idx) {
+ return DHD_METADATA_D2H_RXCPL;
+ }
+ return DHD_METADATA_NO_RING;
+}
+
+static msgbuf_ring_t *
+dhd_d2h_cpl_ring_from_id(dhd_pub_t *dhd, int idx)
+{
+ dhd_prot_t *prot = dhd->prot;
+
+ switch (idx) {
+ case DHD_METADATA_D2H_TXCPL: /* D2H Tx Completion Ring */
+ if (prot->d2hring_tx_cpln.inited) {
+ return &prot->d2hring_tx_cpln;
+ }
+ break;
+ case DHD_METADATA_D2H_RXCPL: /* D2H Rx Completion Ring */
+ if (prot->d2hring_rx_cpln.inited) {
+ return &prot->d2hring_rx_cpln;
+ }
+ break;
+ default:
+ return NULL;
+ }
+ return NULL;
+}
+
+int
+dhd_prot_mdring_link_unlink(dhd_pub_t *dhd, int idx, bool link)
+{
+ void *msg_start;
+ uint16 alloced = 0;
+ unsigned long flags;
+ dhd_prot_t *prot = dhd->prot;
+ ring_config_req_t *ring_config_req;
+ msgbuf_ring_t *ctrl_ring = &prot->h2dring_ctrl_subn;
+ msgbuf_ring_t *linked_ring = NULL;
+
+ if (!prot->d2hring_md_cpl) {
+ DHD_ERROR(("%s No metadata ring exists\n", __FUNCTION__));
+ return BCME_ERROR;
+ }
+ if (link && prot->d2hring_md_cpl->linked_ring) {
+ DHD_ERROR(("%s Link:metadata ring already linked\n", __FUNCTION__));
+ return BCME_ERROR;
+ }
+ linked_ring = dhd_d2h_cpl_ring_from_id(dhd, idx);
+ if (!link && linked_ring != prot->d2hring_md_cpl->linked_ring) {
+ DHD_ERROR(("%s Unlink:metadata ring not linked\n", __FUNCTION__));
+ return BCME_ERROR;
+ }
+ prot->d2hring_md_cpl->linked_ring = linked_ring;
+#ifdef PCIE_INB_DW
+ if (dhd_prot_inc_hostactive_devwake_assert(dhd->bus) != BCME_OK)
+ return BCME_ERROR;
+#endif /* PCIE_INB_DW */
+ /* Claim space for 1 d2h_ring_config_req_t messages */
+ DHD_RING_LOCK(ctrl_ring->ring_lock, flags);
+ msg_start = dhd_prot_alloc_ring_space(dhd, ctrl_ring, 1, &alloced, TRUE);
+
+ if (msg_start == NULL) {
+ DHD_ERROR(("%s Msgbuf no space for D2H ring config metadta ring link/unlink\n",
+ __FUNCTION__));
+ DHD_RING_UNLOCK(ctrl_ring->ring_lock, flags);
+#ifdef PCIE_INB_DW
+ dhd_prot_dec_hostactive_ack_pending_dsreq(dhd->bus);
+#endif
+ return BCME_ERROR;
+ }
+
+ /* position the ring_config_req into the ctrl subm ring */
+ ring_config_req = (ring_config_req_t *)msg_start;
+
+ /* Common msg header */
+ ring_config_req->msg.msg_type = MSG_TYPE_D2H_RING_CONFIG;
+ ring_config_req->msg.if_id = 0;
+ ring_config_req->msg.request_id = htol32(0); /* TBD */
+ ring_config_req->msg.flags = ctrl_ring->current_phase;
+
+ ring_config_req->msg.epoch = ctrl_ring->seqnum % H2D_EPOCH_MODULO;
+ ctrl_ring->seqnum++;
+
+ ring_config_req->msg.request_id = htol32(DHD_FAKE_PKTID); /* unused */
+
+ /* Ring Config subtype and d2h ring_id */
+ if (link) {
+ ring_config_req->subtype = htol16(D2H_RING_CONFIG_SUBTYPE_MDATA_LINK);
+ } else {
+ ring_config_req->subtype = htol16(D2H_RING_CONFIG_SUBTYPE_MDATA_UNLINK);
+ }
+ ring_config_req->ring_id =
+ htol16(dhd_d2h_cpl_ring_id(dhd, prot->d2hring_md_cpl));
+
+ ring_config_req->mdata_assoc.ringid =
+ htol16(dhd_d2h_cpl_ring_id(dhd, prot->d2hring_md_cpl->linked_ring));
+
+ DHD_ERROR(("%s: metadata:%d link to ring:%d\n",
+ __FUNCTION__, ring_config_req->ring_id,
+ ring_config_req->mdata_assoc.ringid));
+
+ /* update control subn ring's WR index and ring doorbell to dongle */
+ dhd_prot_ring_write_complete(dhd, ctrl_ring, msg_start, 1);
+
+ DHD_RING_UNLOCK(ctrl_ring->ring_lock, flags);
+
+#ifdef PCIE_INB_DW
+ dhd_prot_dec_hostactive_ack_pending_dsreq(dhd->bus);
+#endif
+ return BCME_OK;
+}
+
+int
+dhd_prot_mdring_linked_ring(dhd_pub_t *dhd)
+{
+ dhd_prot_t *prot = dhd->prot;
+ if (prot->d2hring_md_cpl && prot->d2hring_md_cpl->linked_ring) {
+ return dhd_d2h_id_from_cpl_ring_idx
+ (dhd, prot->d2hring_md_cpl->linked_ring->idx);
+ }
+ return 0;
+}
+
/*
* rx_status1:
* Bit [31:0] - Packet reception time
diff --git a/dhd_pcie.c b/dhd_pcie.c
index 65dbdd7..0644ea9 100644
--- a/dhd_pcie.c
+++ b/dhd_pcie.c
@@ -1,7 +1,7 @@
/*
* DHD Bus Module for PCIE
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -271,6 +271,7 @@
static void dhd_bus_dump_rxlat_info(dhd_pub_t *dhdp, struct bcmstrbuf *strbuf);
static void dhd_bus_dump_rxlat_histo(dhd_pub_t *dhdp, struct bcmstrbuf *strbuf);
static void dhd_bus_dump_txcpl_info(dhd_pub_t *dhdp, struct bcmstrbuf *strbuf);
+static void dhd_bus_dump_mdring_info(dhd_pub_t *dhdp, struct bcmstrbuf *strbuf);
static bool dhd_bus_support_dar_sec_status(dhd_bus_t *bus);
static int dhd_bus_security_info(dhd_pub_t *dhdp, struct bcmstrbuf *strbuf);
static int dhd_bus_sboot_disable(dhd_pub_t *dhdp, struct bcmstrbuf *strbuf);
@@ -353,6 +354,9 @@
static int dhdpcie_download_rtlv(dhd_bus_t *bus, dngl_rtlv_type_t type, dngl_rtlv_len_t len,
uint8 *value);
+#if defined(SUPPORT_MULTIPLE_BOARD_REVISION)
+extern void concate_custom_board_revision(char *nv_path);
+#endif /* SUPPORT_MULTIPLE_BOARD_REVISION */
/* IOVar table */
enum {
@@ -385,8 +389,10 @@
#ifdef DHD_PCIE_RUNTIMEPM
IOV_IDLETIME,
#endif /* DHD_PCIE_RUNTIMEPM */
- IOV_RXBOUND,
- IOV_TXBOUND,
+ IOV_RX_CPL_POST_BOUND,
+ IOV_TX_CPL_BOUND,
+ IOV_CTRL_CPL_POST_BOUND,
+ IOV_TX_POST_BOUND,
IOV_HANGREPORT,
IOV_H2D_MAILBOXDATA,
IOV_INFORINGS,
@@ -456,6 +462,11 @@
IOV_DONGLE_SEC_INFO,
IOV_DONGLE_SBOOT_DIS,
IOV_LPM_MODE,
+ IOV_MDRING_LINK,
+ IOV_MDRING_UNLINK,
+ IOV_MDRING_DUMP,
+ IOV_PTM_ENABLE,
+ IOV_PCIE_DMAXFER_PTRN,
IOV_PCIE_LAST /**< unused IOVAR */
};
@@ -474,6 +485,7 @@
{"ramsize", IOV_RAMSIZE, 0, 0, IOVT_UINT32, 0 },
{"ramstart", IOV_RAMSTART, 0, 0, IOVT_UINT32, 0 },
{"pcie_dmaxfer", IOV_PCIE_DMAXFER, 0, 0, IOVT_BUFFER, sizeof(dma_xfer_info_t)},
+ {"lpbk_dmaxfer_data_pattern", IOV_PCIE_DMAXFER_PTRN, 0, 0, IOVT_UINT32, 0},
{"pcie_suspend", IOV_PCIE_SUSPEND, DHD_IOVF_PWRREQ_BYPASS, 0, IOVT_UINT32, 0 },
#ifdef PCIE_OOB
{"oob_bt_reg_on", IOV_OOB_BT_REG_ON, 0, 0, IOVT_UINT32, 0 },
@@ -494,8 +506,10 @@
#ifdef DHD_PCIE_RUNTIMEPM
{"idletime", IOV_IDLETIME, 0, 0, IOVT_INT32, 0 },
#endif /* DHD_PCIE_RUNTIMEPM */
- {"rxbound", IOV_RXBOUND, 0, 0, IOVT_UINT32, 0 },
- {"txbound", IOV_TXBOUND, 0, 0, IOVT_UINT32, 0 },
+ {"rx_cpl_post_bound", IOV_RX_CPL_POST_BOUND, 0, 0, IOVT_UINT32, 0 },
+ {"tx_cpl_bound", IOV_TX_CPL_BOUND, 0, 0, IOVT_UINT32, 0 },
+ {"ctrl_cpl_post_bound", IOV_CTRL_CPL_POST_BOUND, 0, 0, IOVT_UINT32, 0 },
+ {"tx_post_bound", IOV_TX_POST_BOUND, 0, 0, IOVT_UINT32, 0 },
{"fw_hang_report", IOV_HANGREPORT, 0, 0, IOVT_BOOL, 0 },
{"h2d_mb_data", IOV_H2D_MAILBOXDATA, 0, 0, IOVT_UINT32, 0 },
{"inforings", IOV_INFORINGS, 0, 0, IOVT_UINT32, 0 },
@@ -567,6 +581,12 @@
{"sboot_disable", IOV_DONGLE_SBOOT_DIS, 0, 0, IOVT_BUFFER,
sizeof(tx_cpl_history_t) * MAX_TXCPL_HISTORY + 128 },
+ {"mdring_link", IOV_MDRING_LINK, 0, 0, IOVT_UINT32, 0 },
+ {"mdring_unlink", IOV_MDRING_UNLINK, 0, 0, IOVT_UINT32, 0 },
+ {"dump_mdring", IOV_MDRING_DUMP, 0, 0, IOVT_BUFFER,
+ MAX_MDRING_ITEM_DUMP * D2HRING_MDCMPLT_ITEMSIZE },
+ {"ptm_enable", IOV_PTM_ENABLE, 0, 0, IOVT_UINT32, 0 },
+
{NULL, 0, 0, 0, 0, 0 }
};
@@ -578,19 +598,9 @@
#define MAX_READ_TIMEOUT 2 * 1000 * 1000
#endif
-#ifndef DHD_RXBOUND
-#define DHD_RXBOUND 64
-#endif
-#ifndef DHD_TXBOUND
-#define DHD_TXBOUND 64
-#endif
-
#define DHD_INFORING_BOUND 32
#define DHD_BTLOGRING_BOUND 32
-uint dhd_rxbound = DHD_RXBOUND;
-uint dhd_txbound = DHD_TXBOUND;
-
#if defined(DEBUGGER) || defined(DHD_DSCOPE)
/** the GDB debugger layer will call back into this (bus) layer to read/write dongle memory */
static struct dhd_gdb_bus_ops_s bus_ops = {
@@ -890,7 +900,7 @@
DHD_ERROR(("%s: buscorerev=%d chipid=0x%x\n",
__FUNCTION__, bus->sih->buscorerev, si_chipid(bus->sih)));
if (bus->sih->buscorerev <= 14 ||
- si_chipid(bus->sih) == BCM4389_CHIP_ID ||
+ si_chipid(bus->sih) == BCM4381_CHIP_ID ||
si_chipid(bus->sih) == BCM4385_CHIP_ID ||
si_chipid(bus->sih) == BCM4375_CHIP_ID ||
si_chipid(bus->sih) == BCM4376_CHIP_ID ||
@@ -1169,12 +1179,14 @@
if (sched_err) {
/* print out minimum timestamp info */
DHD_ERROR(("isr_entry_time="SEC_USEC_FMT
+ " prev_isr_entry_time="SEC_USEC_FMT
" isr_exit_time="SEC_USEC_FMT
" dpc_entry_time="SEC_USEC_FMT
"\ndpc_exit_time="SEC_USEC_FMT
" isr_sched_dpc_time="SEC_USEC_FMT
" resched_dpc_time="SEC_USEC_FMT"\n",
GET_SEC_USEC(bus->isr_entry_time),
+ GET_SEC_USEC(bus->prev_isr_entry_time),
GET_SEC_USEC(bus->isr_exit_time),
GET_SEC_USEC(bus->dpc_entry_time),
GET_SEC_USEC(bus->dpc_exit_time),
@@ -1405,11 +1417,22 @@
/* read pci_intstatus */
intstatus = dhdpcie_bus_cfg_read_dword(bus, PCI_INT_STATUS, 4);
- if (intstatus == (uint32)-1) {
- DHD_ERROR(("%s: Invalid cfg intstatus(0x%x):0x%x, pcie link down\n",
- __FUNCTION__, PCI_INT_STATUS, intstatus));
+ if (intstatus == (uint32)-1 ||
+ bus->dhd->dhd_induce_error == DHD_INDUCE_PCIE_LINK_DOWN_IN_ISR) {
+ DHD_ERROR(("%s: Invalid cfg intstatus(0x%x):0x%x, pcie link down,"
+ "induce %u\n", __FUNCTION__, PCI_INT_STATUS, intstatus,
+ bus->dhd->dhd_induce_error));
bus->is_linkdown = 1;
dhdpcie_disable_irq_nosync(bus);
+ dhd_pcie_debug_info_dump(bus->dhd);
+#if defined(CONFIG_ARCH_MSM) && defined(SUPPORT_LINKDOWN_RECOVERY)
+ bus->no_cfg_restore = 1;
+#endif /* CONFIG_ARCH_MSM && SUPPORT_LINKDOWN_RECOVERY */
+ bus->dhd->hang_reason = HANG_REASON_PCIE_LINK_DOWN_EP_DETECT;
+#ifdef WL_CFGVENDOR_SEND_HANG_EVENT
+ copy_hang_info_linkdown(bus->dhd);
+#endif /* WL_CFGVENDOR_SEND_HANG_EVENT */
+ dhd_os_send_hang_message(bus->dhd);
break;
}
@@ -1757,6 +1780,27 @@
}
#ifdef BCMQT_HW
+/* Xtal to ALP clock ratio can change from chip to chip and this functions returns the
+ * Xtal to ALP clock ratio by extracting the value for the current chip.
+ */
+static uint32
+dhdpcie_get_xtal_to_alp_ratio(dhd_bus_t *bus)
+{
+ uint16 chipid = si_chipid(bus->sih);
+ uint32 xtal_to_alp_ratio;
+
+ switch (chipid) {
+ case BCM4397_CHIP_ID:
+ xtal_to_alp_ratio = 2;
+ break;
+ default:
+ xtal_to_alp_ratio = 1;
+ break;
+ }
+
+ return xtal_to_alp_ratio;
+}
+
/* Calculate dongle/host clock ratio for QT so the waiting period in host driver can be scaled
* properly. The dongle uses ALP clock by default which can't be read directly. But ILP and
* ALP clocks are scaled disproportionally in QT. So DHD must know the preset crystal frequency
@@ -1772,9 +1816,11 @@
#define XTAL_FREQ_37M4 37400000u
void dhdpcie_htclkratio_cal(dhd_bus_t *bus)
{
- uint cur_coreidx, pmu_idx;
- uint32 ilp_start, ilp_tick, xtal_ratio;
+ uint cur_coreidx, pmu_idx, ilp_on_fast_lpo = 0;
+ uint32 ilp_start, ilp_tick = 0, alp_to_ilp_ratio = 0;
int xtalfreq = 0;
+ uint32 alp_freq = 0;
+ uint32 xtal_to_alp_ratio = dhdpcie_get_xtal_to_alp_ratio(bus);
/* If a larger than 1 htclkratio is set through module parameter, use it directly */
if (htclkratio > 1) {
@@ -1797,9 +1843,23 @@
/* -1 to compensate the incomplete cycle at the beginning */
ilp_tick -= ilp_start - 1;
+ ilp_on_fast_lpo = si_corereg(bus->sih, pmu_idx, offsetof(pmuregs_t, pmustatus), 0, 0) &
+ PST_ILPFASTLPO;
+
+ if (PMUREV(bus->sih->pmurev) <= 45) {
+ /* If ILP is running on Fast LPO is enabled, XtalFreqRatio uses 1 Mhz ILP
+ * instead of 32 KHz. But PMUTimer runs at 32 KHz only irrespective of Fast
+ * LPO is enabled or not. Thereby scale up ilp_tick when Fast LPO is enabled.
+ * In case of Zebu/QT, Fast LPO is exactly 32 times of ILP clock.
+ * [Reference: CRWLPMU-284]
+ */
+ if (ilp_on_fast_lpo) {
+ ilp_tick *= 32;
+ }
+ }
/* Get xtal vs ILP ratio from XtalFreqRatio(0x66c) */
- xtal_ratio = si_corereg(bus->sih, pmu_idx, offsetof(pmuregs_t, pmu_xtalfreq), 0, 0);
- xtal_ratio = (xtal_ratio & PMU_XTALFREQ_REG_ILPCTR_MASK) / 4;
+ alp_to_ilp_ratio = si_corereg(bus->sih, pmu_idx, offsetof(pmuregs_t, pmu_xtalfreq), 0, 0);
+ alp_to_ilp_ratio = (alp_to_ilp_ratio & PMU_XTALFREQ_REG_ILPCTR_MASK) / 4;
/* Go back to original core */
si_setcoreidx(bus->sih, cur_coreidx);
@@ -1811,16 +1871,21 @@
xtalfreq = XTAL_FREQ_37M4;
}
- /* htclkratio = xtalfreq / QT_XTAL_FREQ
- * = xtalfreq / (ilp_tick * xtal_ratio)
+ alp_freq = xtalfreq / xtal_to_alp_ratio;
+
+ /* htclkratio = Expected ALP Freq / Real ALP Freq
+ * = Expected ALP Freq / (Real ILP Tick * Real alp_to_ilp_ratio)
*/
- htclkratio = xtalfreq / (ilp_tick * xtal_ratio);
+ htclkratio = alp_freq / (ilp_tick * alp_to_ilp_ratio);
bus->xtalfreq = xtalfreq;
bus->ilp_tick = ilp_tick;
- bus->xtal_ratio = xtal_ratio;
+ bus->alp_to_ilp_ratio = alp_to_ilp_ratio;
+ bus->xtal_to_alp_ratio = xtal_to_alp_ratio;
exit:
- DHD_ERROR(("Dongle/Host clock ratio %u with %dHz xtal frequency\n", htclkratio, xtalfreq));
+ DHD_ERROR(("Dongle/Host clock ratio %u with %dHz xtal frequency, ilp_tick: %d, "
+ "alp_to_ilp_ratio: %d, ilp_on_fast_lpo: %d\n",
+ htclkratio, xtalfreq, ilp_tick, alp_to_ilp_ratio, !!ilp_on_fast_lpo));
}
/* Re-calculate htclkratio if nvram provides a different xtalfreq */
@@ -1829,6 +1894,9 @@
char *freq_c = NULL;
uint len, p;
int xtalfreq = 0;
+ uint cur_coreidx, pmu_idx;
+ uint32 alp_to_ilp_ratio = 0;
+ uint32 alp_freq = 0;
/* Do not re-calculate if xtalfreq is overridden by module parameter */
if (dngl_xtalfreq)
@@ -1870,11 +1938,26 @@
DHD_ERROR(("Re-calculating htclkratio because nvram xtalfreq %dHz is different from %dHz\n",
xtalfreq, bus->xtalfreq));
- htclkratio = xtalfreq / (bus->ilp_tick * bus->xtal_ratio);
+ alp_freq = xtalfreq / bus->xtal_to_alp_ratio;
+ htclkratio = alp_freq / (bus->ilp_tick * bus->alp_to_ilp_ratio);
bus->xtalfreq = xtalfreq;
- DHD_ERROR(("Corrected dongle/Host clock ratio %u with %dHz xtal frequency\n",
- htclkratio, xtalfreq));
+ /* Recalculate alp_to_ilp_ratio just to aid in debuggability. Mainly to compare with the
+ * previously calculated alp_to_ilp_ratio.
+ */
+
+ cur_coreidx = si_coreidx(bus->sih);
+ si_setcore(bus->sih, PMU_CORE_ID, 0);
+ pmu_idx = si_coreidx(bus->sih);
+
+ alp_to_ilp_ratio = si_corereg(bus->sih, pmu_idx, offsetof(pmuregs_t, pmu_xtalfreq), 0, 0);
+ alp_to_ilp_ratio = (alp_to_ilp_ratio & PMU_XTALFREQ_REG_ILPCTR_MASK) / 4;
+
+ si_setcoreidx(bus->sih, cur_coreidx);
+
+ DHD_ERROR(("Corrected Host/Dongle clock ratio %u with %dHz xtal frequency, ilp_tick: %d, "
+ "alp_to_ilp_ratio: %d, alp_to_ilp_ratio (recalculated): %d\n", htclkratio,
+ xtalfreq, bus->ilp_tick, bus->alp_to_ilp_ratio, alp_to_ilp_ratio));
}
#endif /* BCMQT_HW */
@@ -1934,17 +2017,39 @@
static INLINE void dhd_sbreg_op(dhd_pub_t *dhd, uint addr, uint *val, bool read);
+static uint32
+dhd_get_pcie_slave_wrapper(si_t *sih)
+{
+ uint32 pcie_slave_wrapper = 0;
+ uint16 chipid = si_chipid(sih);
+
+ switch (chipid) {
+ case BCM4389_CHIP_ID:
+ case BCM4387_CHIP_ID:
+ pcie_slave_wrapper = PCIE_SLAVER_WRAPPER_BASE;
+ break;
+ default:
+ pcie_slave_wrapper = 0;
+ break;
+ }
+
+ return pcie_slave_wrapper;
+}
+
static void
dhd_dump_pcie_slave_wrapper_regs(dhd_bus_t *bus)
{
uint32 i, val;
+ uint32 pcie_slave_wrapper_base = 0;
uint32 total_wrapper_regs;
if (bus->dhd == NULL) {
return;
}
- if (si_chipid(bus->sih) != BCM4389_CHIP_ID) {
+ pcie_slave_wrapper_base = dhd_get_pcie_slave_wrapper(bus->sih);
+ if (!pcie_slave_wrapper_base) {
+ DHD_ERROR(("%s pcie slave wrapper base not populated\n", __FUNCTION__));
return;
}
@@ -1954,7 +2059,7 @@
sizeof(pcie_slave_wrapper_offsets) / sizeof(pcie_slave_wrapper_offsets[0]);
for (i = 0; i < total_wrapper_regs; i++) {
- dhd_sbreg_op(bus->dhd, (PCIE_SLAVER_WRAPPER_BASE + pcie_slave_wrapper_offsets[i]),
+ dhd_sbreg_op(bus->dhd, (pcie_slave_wrapper_base + pcie_slave_wrapper_offsets[i]),
&val, TRUE);
}
@@ -2325,6 +2430,9 @@
case BCM4377_CHIP_ID:
bus->dongle_ram_base = CR4_4377_RAM_BASE;
break;
+ case BCM4381_CHIP_ID:
+ bus->dongle_ram_base = CR4_4381_RAM_BASE;
+ break;
case BCM4387_CHIP_GRPID:
bus->dongle_ram_base = CR4_4387_RAM_BASE;
break;
@@ -2734,6 +2842,72 @@
}
}
+void
+dhd_init_dpc_histos(dhd_pub_t *dhd)
+{
+ dhd_bus_t *bus = dhd->bus;
+ if (!bus->dpc_time_histo) {
+ bus->dpc_time_histo = dhd_histo_init(dhd);
+ }
+ if (!bus->ctrl_cpl_post_time_histo) {
+ bus->ctrl_cpl_post_time_histo = dhd_histo_init(dhd);
+ }
+ if (!bus->tx_post_time_histo) {
+ bus->tx_post_time_histo = dhd_histo_init(dhd);
+ }
+ if (!bus->tx_cpl_time_histo) {
+ bus->tx_cpl_time_histo = dhd_histo_init(dhd);
+ }
+ if (!bus->rx_cpl_post_time_histo) {
+ bus->rx_cpl_post_time_histo = dhd_histo_init(dhd);
+ }
+}
+
+void
+dhd_deinit_dpc_histos(dhd_pub_t *dhd)
+{
+ dhd_bus_t *bus = dhd->bus;
+ if (bus->dpc_time_histo) {
+ dhd_histo_deinit(dhd, bus->dpc_time_histo);
+ }
+ if (bus->ctrl_cpl_post_time_histo) {
+ dhd_histo_deinit(dhd, bus->ctrl_cpl_post_time_histo);
+ }
+ if (bus->tx_post_time_histo) {
+ dhd_histo_deinit(dhd, bus->tx_post_time_histo);
+ }
+ if (bus->tx_cpl_time_histo) {
+ dhd_histo_deinit(dhd, bus->tx_cpl_time_histo);
+ }
+ if (bus->rx_cpl_post_time_histo) {
+ dhd_histo_deinit(dhd, bus->rx_cpl_post_time_histo);
+ }
+}
+
+void
+dhd_dump_dpc_histos(dhd_pub_t *dhd, struct bcmstrbuf *strbuf)
+{
+ dhd_bus_t *bus = dhd->bus;
+ bcm_bprintf(strbuf, "==== DPC Histograms in Usec ====\n");
+ dhd_histo_tag_dump(dhd, strbuf, "usec/histo");
+ dhd_histo_dump(dhd, strbuf, bus->dpc_time_histo, "dpc");
+ dhd_histo_dump(dhd, strbuf, bus->ctrl_cpl_post_time_histo, "ctrl_cpl_post");
+ dhd_histo_dump(dhd, strbuf, bus->tx_post_time_histo, "tx_post");
+ dhd_histo_dump(dhd, strbuf, bus->tx_cpl_time_histo, "tx_cpl");
+ dhd_histo_dump(dhd, strbuf, bus->rx_cpl_post_time_histo, "rx_cpl_post");
+ bcm_bprintf(strbuf, "================================\n");
+}
+
+void
+dhd_clear_dpc_histos(dhd_pub_t *dhd)
+{
+ dhd_bus_t *bus = dhd->bus;
+ dhd_histo_clear(dhd, bus->dpc_time_histo);
+ dhd_histo_clear(dhd, bus->ctrl_cpl_post_time_histo);
+ dhd_histo_clear(dhd, bus->tx_post_time_histo);
+ dhd_histo_clear(dhd, bus->tx_cpl_time_histo);
+ dhd_histo_clear(dhd, bus->rx_cpl_post_time_histo);
+}
/** Detach and free everything */
void
dhdpcie_bus_release(dhd_bus_t *bus)
@@ -2743,6 +2917,9 @@
uint buscorerev = 0;
#endif /* BCMQT */
osl_t *osh = NULL;
+#if defined(__linux__)
+ int bcmerror = 0;
+#endif /* __linux__ */
DHD_TRACE(("%s: Enter\n", __FUNCTION__));
@@ -2764,6 +2941,8 @@
dhdpcie_bus_intr_disable(bus);
dhdpcie_free_irq(bus);
}
+ dhd_deinit_dpc_histos(bus->dhd);
+
dhd_deinit_bus_lp_state_lock(bus);
dhd_deinit_bar1_switch_lock(bus);
dhd_deinit_backplane_access_lock(bus);
@@ -2791,6 +2970,20 @@
*/
dhd_detach(bus->dhd);
dhdpcie_bus_release_dongle(bus, osh, dongle_isolation, TRUE);
+#if defined(__linux__)
+ DHD_ERROR(("%s: disable pcie dev\n", __FUNCTION__));
+ bcmerror = dhdpcie_bus_disable_device(bus);
+ if (bcmerror) {
+ DHD_ERROR(("%s: dhdpcie_bus_disable_device: %d\n",
+ __FUNCTION__, bcmerror));
+ }
+ DHD_ERROR(("%s: stop host dev dev\n", __FUNCTION__));
+ bcmerror = dhdpcie_bus_stop_host_dev(bus);
+ if (bcmerror) {
+ DHD_ERROR(("%s: dhdpcie_bus_stop_host_dev failed: %d\n",
+ __FUNCTION__, bcmerror));
+ }
+#endif /* __linux__ */
dhd_free(bus->dhd);
bus->dhd = NULL;
}
@@ -3067,7 +3260,7 @@
tx_cmpl = flow_ring_node->tx_cmpl;
active = flow_ring_node->active;
status = flow_ring_node->status;
- ring_empty = dhd_prot_is_cmpl_ring_empty(bus->dhd, flow_ring_node->prot_info);
+ ring_empty = dhd_prot_is_h2d_ring_empty(bus->dhd, flow_ring_node->prot_info);
DHD_FLOWRING_UNLOCK(flow_ring_node->lock, ring_lock_flags);
/*
* Need not monitor the flow ring if,
@@ -3156,6 +3349,28 @@
}
return;
}
+#if defined(ASSOC_CHECK_SR)
+void
+dhd_assoc_check_sr(dhd_pub_t *dhd, bool state)
+{
+ int ret = -1;
+ /* if stuck monitor is disabled */
+ if (!dhd->bus->dev_tx_stuck_monitor) {
+ return;
+ }
+
+ if (state) { /* suspend */
+ dhd->assoc_at_suspend = dhd_is_associated(dhd, 0, NULL);
+ DHD_ERROR(("%s assoc_at_suspend: %d\n", __FUNCTION__, dhd->assoc_at_suspend));
+ } else if ((dhd->assoc_at_suspend) && (!dhd_is_associated(dhd, 0, NULL))) { /* resume */
+ DHD_ERROR(("%s - assoc lost in D3. Issue disassoc\n", __FUNCTION__));
+ ret = dhd_wl_ioctl_cmd(dhd, WLC_DISASSOC, NULL, 0, IOV_SET, 0);
+ if (ret != BCME_OK) {
+ DHD_ERROR(("%s error issuing disassoc, %d\n", __FUNCTION__, ret));
+ }
+ }
+}
+#endif /* ASSOC_CHECK_SR */
#endif /* DEVICE_TX_STUCK_DETECT */
/**
@@ -3582,6 +3797,10 @@
}
#endif /* SUPPORT_MULTIPLE_NVRAM */
+#if defined(SUPPORT_MULTIPLE_BOARD_REVISION)
+ concate_custom_board_revision(bus->nv_path);
+#endif /* SUPPORT_MULTIPLE_BOARD_REVISION */
+
#if defined(DHD_BLOB_EXISTENCE_CHECK)
dhd_set_blob_support(bus->dhd, bus->fw_path);
#endif /* DHD_BLOB_EXISTENCE_CHECK */
@@ -3674,17 +3893,23 @@
dhd_tcm_test_enable = FALSE;
}
#endif /* DHD_FW_MEM_CORRUPTION */
- DHD_ERROR(("%s: dhd_tcm_test_enable %u, dhd_tcm_test_status %u\n", __FUNCTION__,
- dhd_tcm_test_enable, dhd_tcm_test_status));
- /* run TCM test if not passed yet */
- if (dhd_tcm_test_enable && dhd_tcm_test_status != TCM_TEST_PASSED) {
- if (dhd_bus_tcm_test(bus) == FALSE) {
- DHD_ERROR(("dhd_bus_tcm_test failed\n"));
- dhd_tcm_test_status = TCM_TEST_FAILED;
- bcmerror = BCME_ERROR;
- goto err;
- } else {
- dhd_tcm_test_status = TCM_TEST_PASSED;
+ DHD_ERROR(("%s: dhd_tcm_test_enable %u, dhd_tcm_test_status %u, dhd_tcm_test_mode %u\n",
+ __FUNCTION__, dhd_tcm_test_enable, dhd_tcm_test_status, dhd_tcm_test_mode));
+
+ if (dhd_tcm_test_enable && dhd_tcm_test_mode != TCM_TEST_MODE_DISABLE) {
+ if (((dhd_tcm_test_mode == TCM_TEST_MODE_ONCE) &&
+ (dhd_tcm_test_status == TCM_TEST_NOT_RUN)) ||
+ (dhd_tcm_test_mode == TCM_TEST_MODE_ALWAYS)) {
+ if (dhd_tcm_test_status != TCM_TEST_PASSED) {
+ if (dhd_bus_tcm_test(bus) == FALSE) {
+ DHD_ERROR(("dhd_bus_tcm_test failed\n"));
+ dhd_tcm_test_status = TCM_TEST_FAILED;
+ bcmerror = BCME_ERROR;
+ goto err;
+ } else {
+ dhd_tcm_test_status = TCM_TEST_PASSED;
+ }
+ }
}
}
@@ -4924,6 +5149,7 @@
if (bus->dhd->up == 0) {
DHD_ERROR(("%s: socram will be collected in dhd_net_bus_devreset failure\n",
__FUNCTION__));
+ bus->dhd->dongle_trap_during_wifi_onoff = 1;
} else
{
/* save core dump or write to a file */
@@ -5252,8 +5478,6 @@
/* intentional fall through */
case DUMP_TYPE_P2P_DISC_BUSY:
/* intentional fall through */
- case DUMP_TYPE_CONT_EXCESS_PM_AWAKE:
- /* intentional fall through */
if (dhdp->db7_trap.fw_db7w_trap) {
/* Set fw_db7w_trap_inprogress here and clear from DPC */
dhdp->db7_trap.fw_db7w_trap_inprogress = TRUE;
@@ -5485,7 +5709,8 @@
* to the (non flow controlled) flow ring.
*/
int
-BCMFASTPATH(dhd_bus_schedule_queue)(struct dhd_bus *bus, uint16 flow_id, bool txs)
+BCMFASTPATH(dhd_bus_schedule_queue)(struct dhd_bus *bus, uint16 flow_id, bool txs,
+ uint32 bound, bool *is_qempty)
/** XXX function name could be more descriptive, eg use 'tx' and 'flow ring' in name */
{
flow_ring_node_t *flow_ring_node;
@@ -5493,6 +5718,7 @@
#ifdef DHD_LOSSLESS_ROAMING
dhd_pub_t *dhdp = bus->dhd;
#endif /* DHD_LOSSLESS_ROAMING */
+ uint32 cnt = 0;
DHD_INFO(("%s: flow_id is %d\n", __FUNCTION__, flow_id));
@@ -5565,6 +5791,7 @@
#endif /* DHDTCPACK_SUPPRESS */
/* Attempt to transfer packet over flow ring */
/* XXX: ifidx is wrong */
+ ++cnt;
ret = dhd_prot_txdata(bus->dhd, txp, flow_ring_node->flow_info.ifindex);
if (ret != BCME_OK) { /* may not have resources in flow ring */
DHD_INFO(("%s: Reinserrt %d\n", __FUNCTION__, ret));
@@ -5580,6 +5807,9 @@
dhd_flow_queue_reinsert(bus->dhd, queue, txp);
DHD_FLOWRING_UNLOCK(flow_ring_node->lock, flags);
+ if (is_qempty) {
+ *is_qempty = FALSE;
+ }
/* If we are able to requeue back, return success */
return BCME_OK;
}
@@ -5591,6 +5821,11 @@
__FUNCTION__, bus->dhd->txpath_mem, PKTLEN(bus->dhd->osh, txp)));
DHD_MEM_STATS_UNLOCK(bus->dhd->mem_stats_lock, flags);
#endif /* DHD_MEM_STATS */
+
+ /* check bound and break if exceeded */
+ if (bound && cnt >= bound) {
+ break;
+ }
}
{
@@ -5605,6 +5840,10 @@
}
DHD_FLOWRING_UNLOCK(flow_ring_node->lock, flags);
+
+ if (is_qempty) {
+ *is_qempty = queue->len > 0 ? FALSE : TRUE;
+ }
}
return ret;
@@ -5731,7 +5970,7 @@
}
return BCME_OK;
}
- ret = dhd_bus_schedule_queue(bus, flowid, FALSE); /* from queue to flowring */
+ ret = dhd_bus_schedule_queue(bus, flowid, FALSE, 0, NULL); /* from queue to flowring */
/* If we have anything pending, try to push into q */
if (txp_pend) {
@@ -6500,6 +6739,9 @@
dhd_bus_clearcounts(dhd_pub_t *dhdp)
{
dhd_prot_clearcounts(dhdp);
+ dhdp->rx_pktgetpool_fail = 0;
+
+ dhd_clear_dpc_histos(dhdp);
}
/**
@@ -7015,6 +7257,9 @@
CAN_SLEEP() ? OSL_SLEEP(DHD_FUNCTION_LEVEL_RESET_DELAY) :
OSL_DELAY(DHD_FUNCTION_LEVEL_RESET_DELAY * USEC_PER_MSEC);
+#ifdef USE_ISB_IN_FLR
+ OSL_ISB();
+#endif /* USE_ISB_IN_FLR */
if (force_fail) {
DHD_ERROR(("Set PCIE_SSRESET_DISABLE_BIT(%d) of"
@@ -7809,6 +8054,15 @@
bcmerror = dhdmsgbuf_dmaxfer_status(bus->dhd, dmaxfer);
break;
}
+ case IOV_GVAL(IOV_PCIE_DMAXFER_PTRN): {
+ int_val = bus->lpbk_xfer_data_pattern_type;
+ bcopy(&int_val, arg, val_size);
+ break;
+ }
+ case IOV_SVAL(IOV_PCIE_DMAXFER_PTRN): {
+ bus->lpbk_xfer_data_pattern_type = int_val;
+ break;
+ }
#ifdef PCIE_OOB
case IOV_GVAL(IOV_OOB_BT_REG_ON):
@@ -8322,15 +8576,6 @@
break;
#endif /* DHD_PCIE_RUNTIMEPM */
- case IOV_GVAL(IOV_TXBOUND):
- int_val = (int32)dhd_txbound;
- bcopy(&int_val, arg, val_size);
- break;
-
- case IOV_SVAL(IOV_TXBOUND):
- dhd_txbound = (uint)int_val;
- break;
-
case IOV_SVAL(IOV_H2D_MAILBOXDATA):
dhdpcie_send_mb_data(bus, (uint)int_val);
break;
@@ -8525,13 +8770,57 @@
bcopy(&int_val, arg, val_size);
break;
- case IOV_GVAL(IOV_RXBOUND):
- int_val = (int32)dhd_rxbound;
+ case IOV_GVAL(IOV_TX_CPL_BOUND):
+ int_val = (int32)dhd_prot_get_tx_cpl_bound(bus->dhd);
bcopy(&int_val, arg, val_size);
break;
-
- case IOV_SVAL(IOV_RXBOUND):
- dhd_rxbound = (uint)int_val;
+ case IOV_SVAL(IOV_TX_CPL_BOUND):
+ if (int_val <= 0) {
+ bcmerror = BCME_BADARG;
+ DHD_ERROR(("%s: invalid tx_cpl_bound value %d !\n",
+ __FUNCTION__, int_val));
+ } else {
+ dhd_prot_set_tx_cpl_bound(bus->dhd, (uint)int_val);
+ }
+ break;
+ case IOV_GVAL(IOV_RX_CPL_POST_BOUND):
+ int_val = (int32)dhd_prot_get_rx_cpl_post_bound(bus->dhd);
+ bcopy(&int_val, arg, val_size);
+ break;
+ case IOV_SVAL(IOV_RX_CPL_POST_BOUND):
+ if (int_val <= 0) {
+ bcmerror = BCME_BADARG;
+ DHD_ERROR(("%s: invalid rx_cpl_post_bound value %d !\n",
+ __FUNCTION__, int_val));
+ } else {
+ dhd_prot_set_rx_cpl_post_bound(bus->dhd, (uint)int_val);
+ }
+ break;
+ case IOV_GVAL(IOV_CTRL_CPL_POST_BOUND):
+ int_val = (int32)dhd_prot_get_ctrl_cpl_post_bound(bus->dhd);
+ bcopy(&int_val, arg, val_size);
+ break;
+ case IOV_SVAL(IOV_CTRL_CPL_POST_BOUND):
+ if (int_val <= 0) {
+ bcmerror = BCME_BADARG;
+ DHD_ERROR(("%s: invalid ctrl_cpl_post_bound value %d !\n",
+ __FUNCTION__, int_val));
+ } else {
+ dhd_prot_set_ctrl_cpl_post_bound(bus->dhd, (uint)int_val);
+ }
+ break;
+ case IOV_GVAL(IOV_TX_POST_BOUND):
+ int_val = (int32)dhd_prot_get_tx_post_bound(bus->dhd);
+ bcopy(&int_val, arg, val_size);
+ break;
+ case IOV_SVAL(IOV_TX_POST_BOUND):
+ if (int_val <= 0) {
+ bcmerror = BCME_BADARG;
+ DHD_ERROR(("%s: invalid tx_post_bound value %d !\n",
+ __FUNCTION__, int_val));
+ } else {
+ dhd_prot_set_tx_post_bound(bus->dhd, (uint)int_val);
+ }
break;
case IOV_GVAL(IOV_TRAPDATA):
@@ -8792,6 +9081,45 @@
bus->lpm_force_flr = FALSE;
}
break;
+ case IOV_GVAL(IOV_MDRING_DUMP):
+ {
+ struct bcmstrbuf strbuf;
+
+ if (bus->dhd->mdring_capable) {
+ bcm_binit(&strbuf, arg, len);
+ dhd_bus_dump_mdring_info(bus->dhd, &strbuf);
+ }
+ break;
+ }
+ case IOV_SVAL(IOV_MDRING_LINK):
+ if (bus->dhd->mdring_capable && int_val) {
+ dhd_prot_mdring_link_unlink(bus->dhd, int_val, TRUE);
+ }
+ break;
+ case IOV_GVAL(IOV_MDRING_LINK):
+ if (bus->dhd->mdring_capable) {
+ int_val = dhd_prot_mdring_linked_ring(bus->dhd);
+ bcopy(&int_val, arg, val_size);
+ }
+ break;
+ case IOV_SVAL(IOV_MDRING_UNLINK):
+ if (bus->dhd->mdring_capable) {
+ dhd_prot_mdring_link_unlink(bus->dhd, int_val, FALSE);
+ }
+ break;
+ case IOV_GVAL(IOV_MDRING_UNLINK):
+ if (bus->dhd->mdring_capable) {
+ int_val = dhd_prot_mdring_linked_ring(bus->dhd);
+ bcopy(&int_val, arg, val_size);
+ }
+ break;
+ case IOV_SVAL(IOV_PTM_ENABLE):
+ if (int_val) {
+ dhdpcie_send_mb_data(bus, H2D_HOST_PTM_ENABLE);
+ } else {
+ dhdpcie_send_mb_data(bus, H2D_HOST_PTM_DISABLE);
+ }
+ break;
default:
bcmerror = BCME_UNSUPPORTED;
break;
@@ -9319,7 +9647,7 @@
#if defined(LINUX) || defined(linux)
dhdpcie_dump_resource(bus);
#endif /* LINUX || linux */
- DHD_RPM(("lpm_mode %d, fw_lpm_support %d\n", bus->lpm_mode,
+ DHD_INFO(("lpm_mode %d, fw_lpm_support %d\n", bus->lpm_mode,
bus->dhd->fw_lpm_support));
/* Once LPM mode is entered, recovery is only through WL_REG_ON */
if (bus->lpm_mode && bus->dhd->fw_lpm_support) {
@@ -9341,12 +9669,12 @@
dhd_pcie_handle_lpm_memkill(bus);
}
}
- DHD_RPM(("Doing the D3\n"));
+ DHD_INFO(("Doing the D3\n"));
rc = dhdpcie_pci_suspend_resume(bus, state);
if (!rc) {
bus->last_suspend_end_time = OSL_LOCALTIME_NS();
}
- DHD_RPM(("Doing the FLR, lpm_mode %d, lpm_force_flr %d,"
+ DHD_INFO(("Doing the FLR, lpm_mode %d, lpm_force_flr %d,"
" fwsupport %d\n",
bus->lpm_mode, bus->lpm_force_flr,
bus->dhd->fw_lpm_support));
@@ -9355,11 +9683,8 @@
bus->lpm_keep_in_reset = TRUE;
dhd_bus_perform_flr(bus, FALSE);
bus->lpm_keep_in_reset = FALSE;
+ DHD_ERROR(("FLR done\n"));
}
- else {
- DHD_RPM(("NO FLR\n"));
- }
- DHD_RPM(("FLR done\n"));
}
} else if (timeleft == 0) { /* D3 ACK Timeout */
#ifdef DHD_FW_COREDUMP
@@ -11020,7 +11345,7 @@
dhdpcie_get_oob_irq_level());
#endif /* BCMPCIE_OOB_HOST_WAKE */
bcm_bprintf(strbuf, "\ncurrent_time="SEC_USEC_FMT" isr_entry_time="SEC_USEC_FMT
- " isr_exit_time="SEC_USEC_FMT"\n"
+ " prev_isr_entry_time="SEC_USEC_FMT" isr_exit_time="SEC_USEC_FMT"\n"
"isr_sched_dpc_time="SEC_USEC_FMT" rpm_sched_dpc_time="SEC_USEC_FMT"\n"
" last_non_ours_irq_time="SEC_USEC_FMT" dpc_entry_time="SEC_USEC_FMT"\n"
"last_process_ctrlbuf_time="SEC_USEC_FMT " last_process_flowring_time="SEC_USEC_FMT
@@ -11029,6 +11354,7 @@
"\ndpc_exit_time="SEC_USEC_FMT" resched_dpc_time="SEC_USEC_FMT"\n"
"last_d3_inform_time="SEC_USEC_FMT"\n",
GET_SEC_USEC(current_time), GET_SEC_USEC(bus->isr_entry_time),
+ GET_SEC_USEC(bus->prev_isr_entry_time),
GET_SEC_USEC(bus->isr_exit_time), GET_SEC_USEC(bus->isr_sched_dpc_time),
GET_SEC_USEC(bus->rpm_sched_dpc_time),
GET_SEC_USEC(bus->last_non_ours_irq_time), GET_SEC_USEC(bus->dpc_entry_time),
@@ -11087,21 +11413,135 @@
bcm_bprintf(strbuf, "d2h_mb_data=0x%x def_intmask=0x%x\n",
d2h_mb_data, dhd->bus->def_intmask);
}
-/** Add bus dump output to a buffer */
-void dhd_bus_dump(dhd_pub_t *dhdp, struct bcmstrbuf *strbuf)
+
+void dhd_bus_dump_flowring(dhd_pub_t *dhdp, struct bcmstrbuf *strbuf)
{
uint16 flowid;
int ix = 0;
flow_ring_node_t *flow_ring_node;
flow_info_t *flow_info;
-#ifdef BCMDBG
- flow_info_t *local_flow_info;
-#endif /* BCMDBG */
#ifdef TX_STATUS_LATENCY_STATS
uint8 ifindex;
if_flow_lkup_t *if_flow_lkup;
dhd_if_tx_status_latency_t if_tx_status_latency[DHD_MAX_IFS];
#endif /* TX_STATUS_LATENCY_STATS */
+ unsigned long flags;
+
+#ifdef TX_STATUS_LATENCY_STATS
+ bzero(if_tx_status_latency, sizeof(if_tx_status_latency));
+#endif /* TX_STATUS_LATENCY_STATS */
+
+ bcm_bprintf(strbuf, "Flowring info:\n==============\n");
+ bcm_bprintf(strbuf, "[RD=read ptr; WR=write ptr; T=TCM; H=Host; L=Local; D=DMA index'd]\n");
+#ifndef BCM_ROUTER_DHD
+ bcm_bprintf(strbuf,
+ "%4s %4s %2s %4s %17s %4s %10s %17s %17s %17s %17s %14s %14s %10s ",
+ "Num:", "Flow", "If", "Prio", ":Dest_MacAddress:", "Qlen",
+ " Overflows", "TRD: HLRD: HDRD", "TWR: HLWR: HDWR", "BASE(VA)", "BASE(PA)",
+ "WORK_ITEM_SIZE", "MAX_WORK_ITEMS", "TOTAL_SIZE");
+#else
+ bcm_bprintf(strbuf,
+ "%4s %4s %2s %4s %17s %4s %4s %6s %10s %17s %17s %17s %17s %14s %14s %10s ",
+ "Num:", "Flow", "If", "Prio", ":Dest_MacAddress:", "Qlen", "CLen", "L2CLen",
+ " Overflows", "TRD: HLRD: HDRD", "TWR: HLWR: HDWR", "BASE(VA)", "BASE(PA)",
+ "WORK_ITEM_SIZE", "MAX_WORK_ITEMS", "TOTAL_SIZE");
+#endif /* !BCM_ROUTER_DHD */
+
+#ifdef TX_STATUS_LATENCY_STATS
+ /* Average Tx status/Completion Latency in micro secs */
+ bcm_bprintf(strbuf, "%16s %16s ", " NumTxPkts", " AvgTxCmpL_Us");
+#endif /* TX_STATUS_LATENCY_STATS */
+
+ bcm_bprintf(strbuf, "\n");
+
+ for (flowid = 0; flowid < dhdp->num_h2d_rings; flowid++) {
+ flow_ring_node = DHD_FLOW_RING(dhdp, flowid);
+ DHD_FLOWRING_LOCK(flow_ring_node->lock, flags);
+ if (flow_ring_node->status != FLOW_RING_STATUS_OPEN) {
+ DHD_FLOWRING_UNLOCK(flow_ring_node->lock, flags);
+ continue;
+ }
+
+ flow_info = &flow_ring_node->flow_info;
+ bcm_bprintf(strbuf,
+ "%4d %4d %2d %4d "MACDBG" %4d"
+#ifdef BCM_ROUTER_DHD
+ "%4d %6d"
+#endif
+ "%10u ", ix++,
+ flow_ring_node->flowid, flow_info->ifindex, flow_info->tid,
+ MAC2STRDBG(flow_info->da),
+ DHD_FLOW_QUEUE_LEN(&flow_ring_node->queue),
+#ifdef BCM_ROUTER_DHD
+ DHD_CUMM_CTR_READ(DHD_FLOW_QUEUE_CLEN_PTR(&flow_ring_node->queue)),
+ DHD_CUMM_CTR_READ(DHD_FLOW_QUEUE_L2CLEN_PTR(&flow_ring_node->queue)),
+#endif
+ DHD_FLOW_QUEUE_FAILURES(&flow_ring_node->queue));
+ dhd_prot_print_flow_ring(dhdp, flow_ring_node->prot_info, TRUE, strbuf,
+ "%5d:%5d:%5d %5d:%5d:%5d %17p %8x:%8x %14d %14d %10d");
+
+#ifdef TX_STATUS_LATENCY_STATS
+ bcm_bprintf(strbuf, "%16llu %16llu ",
+ flow_info->num_tx_pkts,
+ flow_info->num_tx_status ?
+ DIV_U64_BY_U64(flow_info->cum_tx_status_latency,
+ flow_info->num_tx_status) : 0);
+ ifindex = flow_info->ifindex;
+ ASSERT(ifindex < DHD_MAX_IFS);
+ if (ifindex < DHD_MAX_IFS) {
+ if_tx_status_latency[ifindex].num_tx_status += flow_info->num_tx_status;
+ if_tx_status_latency[ifindex].cum_tx_status_latency +=
+ flow_info->cum_tx_status_latency;
+ } else {
+ DHD_ERROR(("%s: Bad IF index: %d associated with flowid: %d\n",
+ __FUNCTION__, ifindex, flowid));
+ }
+#endif /* TX_STATUS_LATENCY_STATS */
+ bcm_bprintf(strbuf, "\n");
+ DHD_FLOWRING_UNLOCK(flow_ring_node->lock, flags);
+ }
+
+#ifdef TX_STATUS_LATENCY_STATS
+ bcm_bprintf(strbuf, "\n%s %16s %16s\n", "If", "AvgTxCmpL_Us", "NumTxStatus");
+ if_flow_lkup = (if_flow_lkup_t *)dhdp->if_flow_lkup;
+ for (ix = 0; ix < DHD_MAX_IFS; ix++) {
+ if (!if_flow_lkup[ix].status) {
+ continue;
+ }
+ bcm_bprintf(strbuf, "%2d %16llu %16llu\n",
+ ix,
+ if_tx_status_latency[ix].num_tx_status ?
+ DIV_U64_BY_U64(if_tx_status_latency[ix].cum_tx_status_latency,
+ if_tx_status_latency[ix].num_tx_status): 0,
+ if_tx_status_latency[ix].num_tx_status);
+ }
+#endif /* TX_STATUS_LATENCY_STATS */
+
+ bcm_bprintf(strbuf, "\n");
+}
+
+void
+dhd_bus_counters(dhd_pub_t *dhdp, struct bcmstrbuf *strbuf)
+{
+ dhd_prot_counters(dhdp, strbuf, TRUE, TRUE);
+
+ dhd_bus_dump_flowring(dhdp, strbuf);
+
+ dhd_dump_dpc_histos(dhdp, strbuf);
+}
+
+/** Add bus dump output to a buffer */
+void dhd_bus_dump(dhd_pub_t *dhdp, struct bcmstrbuf *strbuf)
+{
+ uint16 flowid;
+#ifdef BCMDBG
+ int ix = 0;
+ flow_ring_node_t *flow_ring_node;
+ flow_info_t *flow_info;
+ flow_info_t *local_flow_info;
+#endif /* BCMDBG */
+
+ BCM_REFERENCE(flowid);
#if defined(FW_SIGNATURE)
/* Dump secure firmware status. */
@@ -11113,9 +11553,6 @@
if (dhdp->busstate != DHD_BUS_DATA)
return;
-#ifdef TX_STATUS_LATENCY_STATS
- memset(if_tx_status_latency, 0, sizeof(if_tx_status_latency));
-#endif /* TX_STATUS_LATENCY_STATS */
#ifdef DHD_WAKE_STATUS
bcm_bprintf(strbuf, "wake %u rxwake %u readctrlwake %u\n",
bcmpcie_get_total_wake(dhdp->bus), dhdp->bus->wake_counts.rxwake,
@@ -11166,60 +11603,7 @@
dhdp->htput_client_flow_rings);
}
- bcm_bprintf(strbuf,
- "%4s %4s %2s %4s %17s %4s %4s %6s %10s %17s %17s %17s %17s %14s %14s %10s ",
- "Num:", "Flow", "If", "Prio", ":Dest_MacAddress:", "Qlen", "CLen", "L2CLen",
- " Overflows", "TRD: HLRD: HDRD", "TWR: HLWR: HDWR", "BASE(VA)", "BASE(PA)",
- "WORK_ITEM_SIZE", "MAX_WORK_ITEMS", "TOTAL_SIZE");
-
-#ifdef TX_STATUS_LATENCY_STATS
- /* Average Tx status/Completion Latency in micro secs */
- bcm_bprintf(strbuf, "%16s %16s ", " NumTxPkts", " AvgTxCmpL_Us");
-#endif /* TX_STATUS_LATENCY_STATS */
-
- bcm_bprintf(strbuf, "\n");
-
- for (flowid = 0; flowid < dhdp->num_h2d_rings; flowid++) {
- unsigned long flags;
- flow_ring_node = DHD_FLOW_RING(dhdp, flowid);
- DHD_FLOWRING_LOCK(flow_ring_node->lock, flags);
- if (flow_ring_node->status != FLOW_RING_STATUS_OPEN) {
- DHD_FLOWRING_UNLOCK(flow_ring_node->lock, flags);
- continue;
- }
-
- flow_info = &flow_ring_node->flow_info;
- bcm_bprintf(strbuf,
- "%4d %4d %2d %4d "MACDBG" %4d %4d %6d %10u ", ix++,
- flow_ring_node->flowid, flow_info->ifindex, flow_info->tid,
- MAC2STRDBG(flow_info->da),
- DHD_FLOW_QUEUE_LEN(&flow_ring_node->queue),
- DHD_CUMM_CTR_READ(DHD_FLOW_QUEUE_CLEN_PTR(&flow_ring_node->queue)),
- DHD_CUMM_CTR_READ(DHD_FLOW_QUEUE_L2CLEN_PTR(&flow_ring_node->queue)),
- DHD_FLOW_QUEUE_FAILURES(&flow_ring_node->queue));
- dhd_prot_print_flow_ring(dhdp, flow_ring_node->prot_info, TRUE, strbuf,
- "%5d:%5d:%5d %5d:%5d:%5d %17p %8x:%8x %14d %14d %10d");
-
-#ifdef TX_STATUS_LATENCY_STATS
- bcm_bprintf(strbuf, "%16llu %16llu ",
- flow_info->num_tx_pkts,
- flow_info->num_tx_status ?
- DIV_U64_BY_U64(flow_info->cum_tx_status_latency,
- flow_info->num_tx_status) : 0);
- ifindex = flow_info->ifindex;
- ASSERT(ifindex < DHD_MAX_IFS);
- if (ifindex < DHD_MAX_IFS) {
- if_tx_status_latency[ifindex].num_tx_status += flow_info->num_tx_status;
- if_tx_status_latency[ifindex].cum_tx_status_latency +=
- flow_info->cum_tx_status_latency;
- } else {
- DHD_ERROR(("%s: Bad IF index: %d associated with flowid: %d\n",
- __FUNCTION__, ifindex, flowid));
- }
-#endif /* TX_STATUS_LATENCY_STATS */
- bcm_bprintf(strbuf, "\n");
- DHD_FLOWRING_UNLOCK(flow_ring_node->lock, flags);
- }
+ dhd_bus_dump_flowring(dhdp, strbuf);
#ifdef BCMDBG
if (!dhdp->d2h_sync_mode) {
@@ -11250,21 +11634,7 @@
}
#endif /* BCMDBG */
-#ifdef TX_STATUS_LATENCY_STATS
- bcm_bprintf(strbuf, "\n%s %16s %16s\n", "If", "AvgTxCmpL_Us", "NumTxStatus");
- if_flow_lkup = (if_flow_lkup_t *)dhdp->if_flow_lkup;
- for (ix = 0; ix < DHD_MAX_IFS; ix++) {
- if (!if_flow_lkup[ix].status) {
- continue;
- }
- bcm_bprintf(strbuf, "%2d %16llu %16llu\n",
- ix,
- if_tx_status_latency[ix].num_tx_status ?
- DIV_U64_BY_U64(if_tx_status_latency[ix].cum_tx_status_latency,
- if_tx_status_latency[ix].num_tx_status): 0,
- if_tx_status_latency[ix].num_tx_status);
- }
-#endif /* TX_STATUS_LATENCY_STATS */
+ dhd_dump_dpc_histos(dhdp, strbuf);
bcm_bprintf(strbuf, "D3 inform cnt %d\n", dhdp->bus->d3_inform_cnt);
bcm_bprintf(strbuf, "D0 inform cnt %d\n", dhdp->bus->d0_inform_cnt);
@@ -11303,6 +11673,21 @@
dhdp->db7_trap.debug_db7_timing_error_cnt);
}
+int
+dhd_dump_flowrings(dhd_pub_t *dhdp, char *buf, int buflen)
+{
+ struct bcmstrbuf b;
+ struct bcmstrbuf *strbuf = &b;
+
+ if (!dhdp || !dhdp->prot || !buf) {
+ return BCME_ERROR;
+ }
+
+ bcm_binit(strbuf, buf, buflen);
+ dhd_bus_dump_flowring(dhdp, strbuf);
+ return (!strbuf->size ? BCME_BUFTOOSHORT : strbuf->size);
+}
+
static void
dhd_bus_dump_txcpl_info(dhd_pub_t *dhdp, struct bcmstrbuf *strbuf)
{
@@ -11327,6 +11712,25 @@
bcm_bprintf(strbuf, "\n");
}
+static void
+dhd_bus_dump_mdring_info(dhd_pub_t *dhdp, struct bcmstrbuf *strbuf)
+{
+ int i;
+ int count;
+
+ bcm_bprintf(strbuf, "\nMetadata Ring Dump\n");
+ for (i = 0, count = 0;
+ i < MAX_MDRING_ITEM_DUMP * D2HRING_MDCMPLT_ITEMSIZE; i += 4) {
+ if ((i % D2HRING_MDCMPLT_ITEMSIZE) == 0) {
+ bcm_bprintf(strbuf, "\nEntry:%d:", ++count);
+ }
+ bcm_bprintf(strbuf, "0x%x%x%x%x:",
+ dhdp->mdring_info[i], dhdp->mdring_info[i+1],
+ dhdp->mdring_info[i+2], dhdp->mdring_info[i+3]);
+ }
+ bcm_bprintf(strbuf, "\n");
+}
+
static bool
dhd_bus_support_dar_sec_status(dhd_bus_t *bus)
{
@@ -11373,14 +11777,27 @@
}
bcm_bprintf(strbuf, "\nDAR Security Status Reg\n");
- bcm_bprintf(strbuf, " Jtag Disable: %d\n", (dar_sec_val & DAR_SEC_JTAG_MASK));
- bcm_bprintf(strbuf, " Secure Boot: %d\n", (dar_sec_val & DAR_SEC_SBOOT_MASK) >>
- DAR_SEC_SBOOT_SHIFT);
- bcm_bprintf(strbuf, " Arm Dbg Disable: %d\n", (dar_sec_val & DAR_SEC_ARM_DBG_MASK) >>
- DAR_SEC_ARM_DBG_SHIFT);
- bcm_bprintf(strbuf, " Transient Unlock: %d\n", (dar_sec_val & DAR_SEC_UNLOCK_MASK) >>
- DAR_SEC_UNLOCK_SHIFT);
+ bcm_bprintf(strbuf, " Jtag Disable: %d\n",
+ (dar_sec_val & DAR_SEC_JTAG_MASK) >> DAR_SEC_JTAG_SHIFT);
+ bcm_bprintf(strbuf, " Secure Boot: %d\n",
+ (dar_sec_val & DAR_SEC_SBOOT_MASK) >> DAR_SEC_SBOOT_SHIFT);
+ bcm_bprintf(strbuf, " Arm Dbg Disable: %d\n",
+ (dar_sec_val & DAR_SEC_ARM_DBG_MASK) >> DAR_SEC_ARM_DBG_SHIFT);
+ bcm_bprintf(strbuf, " Transient Unlock: %d\n",
+ (dar_sec_val & DAR_SEC_UNLOCK_MASK) >> DAR_SEC_UNLOCK_SHIFT);
+ /* The following bits in security status register provided for pcie core
+ * generation2 at revisions > 76 and for generation3 at revisions > 129
+ */
+ if (((bus->sih->buscorerev > 76) && (bus->sih->buscorerev < 128)) ||
+ (bus->sih->buscorerev > 129)) {
+ bcm_bprintf(strbuf, " Rom Protect: %d\n",
+ (dar_sec_val & DAR_SEC_ROM_PROT_MASK) >> DAR_SEC_ROM_PROT_SHIFT);
+ bcm_bprintf(strbuf, " Non Secure Write: %d\n",
+ (dar_sec_val & DAR_SEC_NSEC_WR_MASK) >> DAR_SEC_NSEC_WR_SHIFT);
+ bcm_bprintf(strbuf, " Non Secure Read: %d\n",
+ (dar_sec_val & DAR_SEC_NSEC_RD_MASK) >> DAR_SEC_NSEC_RD_SHIFT);
+ }
return BCME_OK;
}
@@ -11666,7 +12083,7 @@
* Brings transmit packets on all flow rings closer to the dongle, by moving (a subset) from their
* flow queue to their flow ring.
*/
-static void
+static bool
dhd_update_txflowrings(dhd_pub_t *dhd)
{
unsigned long flags;
@@ -11674,9 +12091,10 @@
flow_ring_node_t *flow_ring_node;
struct dhd_bus *bus = dhd->bus;
int count = 0;
+ bool more = FALSE;
if (dhd_query_bus_erros(dhd)) {
- return;
+ return more;
}
/* Hold flowring_list_lock to ensure no race condition while accessing the List */
@@ -11685,6 +12103,7 @@
(!dhd_is_device_removed(dhd) && !dll_end(&bus->flowring_active_list, item));
item = next, count++) {
if (dhd->hang_was_sent) {
+ more = FALSE;
break;
}
@@ -11692,6 +12111,7 @@
DHD_ERROR(("%s : overflow max flowrings\n", __FUNCTION__));
dhd->hang_reason = HANG_REASON_UNKNOWN;
dhd_os_send_hang_message(dhd);
+ more = FALSE;
break;
}
@@ -11704,9 +12124,12 @@
/* Ensure that the flowring node has valid contents */
ASSERT(flow_ring_node->prot_info != NULL);
- dhd_prot_update_txflowring(dhd, flow_ring_node->flowid, flow_ring_node->prot_info);
+ more = dhd_prot_update_txflowring(dhd, flow_ring_node->flowid,
+ flow_ring_node->prot_info);
}
DHD_FLOWRING_LIST_UNLOCK(bus->dhd->flowring_list_lock, flags);
+
+ return more;
}
/** Mailbox ringbell Function */
@@ -11936,6 +12359,33 @@
exit:
return ret;
}
+
+#ifdef PCIE_INB_DSACK_EXT_WAIT
+void
+dhd_bus_ds_ack_debug_dump(struct dhd_bus *bus)
+{
+ if ((DIV_U64_BY_U32(bus->isr_entry_time, NSEC_PER_SEC) -
+ DIV_U64_BY_U32(bus->prev_isr_entry_time, NSEC_PER_SEC)) >=
+ DW_DS_ACK_RETRY_THRESHOLD) {
+ bus->dhd->dsack_hc_due_to_isr_delay = TRUE;
+ DHD_ERROR(("ISR did not run causing DS ack timeout\n"));
+ } else if ((bus->dpc_entry_time > bus->isr_entry_time) &&
+ (DIV_U64_BY_U32(bus->dpc_entry_time, NSEC_PER_SEC) -
+ DIV_U64_BY_U32(bus->isr_entry_time, NSEC_PER_SEC)) >=
+ DW_DS_ACK_RETRY_THRESHOLD) {
+ bus->dhd->dsack_hc_due_to_dpc_delay = TRUE;
+ DHD_ERROR(("Delay in scheduling DPC causing DS ack timeout\n"));
+ } else {
+ DHD_ERROR(("Failed to send DS ack\n"));
+ }
+ DHD_ERROR(("prev_isr_entry_time="SEC_USEC_FMT
+ " isr_entry_time="SEC_USEC_FMT
+ " dpc_entry_time="SEC_USEC_FMT"\n",
+ GET_SEC_USEC(bus->prev_isr_entry_time),
+ GET_SEC_USEC(bus->isr_entry_time),
+ GET_SEC_USEC(bus->dpc_entry_time)));
+}
+#endif /* PCIE_INB_DSACK_EXT_WAIT */
#endif /* PCIE_INB_DW */
#if defined(PCIE_OOB) || defined(PCIE_INB_DW)
void
@@ -12289,6 +12739,7 @@
if (!resched) {
bus->intstatus = 0;
bus->dpc_exit_time = OSL_LOCALTIME_NS();
+ bus->dpc_time_usec = (bus->dpc_exit_time - bus->dpc_entry_time) / NSEC_PER_USEC;
if (!dhd_query_bus_erros(bus->dhd)) {
/* Due to irq mismatch WARNING in linux, currently keeping it disabled and
* using dongle intmask to control INTR enable/disable
@@ -12304,7 +12755,9 @@
}
} else {
bus->resched_dpc_time = OSL_LOCALTIME_NS();
+ bus->dpc_time_usec = (bus->resched_dpc_time - bus->dpc_entry_time) / NSEC_PER_USEC;
}
+ dhd_histo_update(bus->dhd, bus->dpc_time_histo, (uint32)bus->dpc_time_usec);
bus->dpc_sched = resched;
#ifdef DHD_FLOW_RING_STATUS_TRACE
@@ -12397,6 +12850,12 @@
DHD_INFO_HW4(("%s: send H2D_HOST_D0_INFORM to dongle\n", __FUNCTION__));
bus->d0_inform_cnt++;
}
+ if (h2d_mb_data == H2D_HOST_PTM_ENABLE) {
+ DHD_INFO(("%s: send H2D_HOST_PTM_ENABLE to dongle\n", __FUNCTION__));
+ }
+ if (h2d_mb_data == H2D_HOST_PTM_DISABLE) {
+ DHD_INFO(("%s: send H2D_HOST_PTM_DISABLE to dongle\n", __FUNCTION__));
+ }
return BCME_OK;
fail:
return BCME_ERROR;
@@ -12440,9 +12899,6 @@
#ifdef PCIE_INB_DW
unsigned long flags = 0;
#endif /* PCIE_INB_DW */
- if (MULTIBP_ENAB(bus->sih)) {
- dhd_bus_pcie_pwr_req(bus);
- }
DHD_INFO(("D2H_MB_DATA: 0x%04x\n", d2h_mb_data));
#ifdef PCIE_INB_DW
@@ -12671,10 +13127,16 @@
}
}
-exit:
- if (MULTIBP_ENAB(bus->sih)) {
- dhd_bus_pcie_pwr_req_clear(bus);
+ if (d2h_mb_data & D2H_DEV_PTM_ENABLED) {
+ DHD_INFO(("D2H_MB_DATA: PTM ENABLED\n"));
}
+
+ if (d2h_mb_data & D2H_DEV_PTM_DISABLED) {
+ DHD_INFO(("D2H_MB_DATA: PTM DISABLED\n"));
+ }
+
+exit:
+ return;
}
static void
@@ -12821,9 +13283,6 @@
return resched;
}
- if (MULTIBP_ENAB(bus->sih)) {
- dhd_bus_pcie_pwr_req(bus);
- }
if ((bus->sih->buscorerev == 2) || (bus->sih->buscorerev == 6) ||
(bus->sih->buscorerev == 4)) {
/* Msg stream interrupt */
@@ -12854,9 +13313,6 @@
dhd_bus_handle_intx_ahead_dma_indices(bus);
- if (MULTIBP_ENAB(bus->sih)) {
- dhd_bus_pcie_pwr_req_clear(bus);
- }
return resched;
}
@@ -12895,9 +13351,11 @@
dhdpci_bus_read_frames(dhd_bus_t *bus)
{
bool more = FALSE;
-#if defined(EWP_EDL)
- uint32 edl_itmes = 0;
-#endif /* EWP_EDL */
+ uint32 ctrlcpl_items = 0;
+ uint32 txcpl_items = 0;
+ uint32 rxcpl_items = 0;
+ uint32 evtlog_items = 0;
+ uint64 read_frames_entry_time = OSL_LOCALTIME_NS();
/* First check if there a FW trap */
if ((bus->api.fw_rev >= PCIE_SHARED_VERSION_6) &&
@@ -12921,9 +13379,14 @@
dhd_prot_save_dmaidx(bus->dhd);
#endif /* DHD_DMA_INDICES_SEQNUM */
/* There may be frames in both ctrl buf and data buf; check ctrl buf first */
- dhd_prot_process_ctrlbuf(bus->dhd);
+ more |= dhd_prot_process_ctrlbuf(bus->dhd, &ctrlcpl_items);
bus->last_process_ctrlbuf_time = OSL_LOCALTIME_NS();
+ bus->ctrl_cpl_post_time_usec =
+ (bus->last_process_ctrlbuf_time - read_frames_entry_time) / NSEC_PER_USEC;
+ dhd_histo_update(bus->dhd, bus->ctrl_cpl_post_time_histo,
+ (uint32)bus->ctrl_cpl_post_time_usec);
+
/* Do not process rest of ring buf once bus enters low power state (D3_INFORM/D3_ACK) */
if (DHD_CHK_BUS_IN_LPS(bus)) {
DHD_RPM(("%s: Bus is in power save state (%d). "
@@ -12933,32 +13396,45 @@
}
/* update the flow ring cpls */
- dhd_update_txflowrings(bus->dhd);
+ more |= dhd_update_txflowrings(bus->dhd);
bus->last_process_flowring_time = OSL_LOCALTIME_NS();
+ bus->tx_post_time_usec =
+ (bus->last_process_flowring_time - bus->last_process_ctrlbuf_time) / NSEC_PER_USEC;
+ dhd_histo_update(bus->dhd, bus->tx_post_time_histo, (uint32)bus->tx_post_time_usec);
+
/* With heavy TX traffic, we could get a lot of TxStatus
* so add bound
*/
- more |= dhd_prot_process_msgbuf_txcpl(bus->dhd, dhd_txbound, DHD_REGULAR_RING);
+ more |= dhd_prot_process_msgbuf_txcpl(bus->dhd, DHD_REGULAR_RING, &txcpl_items);
bus->last_process_txcpl_time = OSL_LOCALTIME_NS();
+ bus->tx_cpl_time_usec =
+ (bus->last_process_txcpl_time - bus->last_process_flowring_time) / NSEC_PER_USEC;
+ dhd_histo_update(bus->dhd, bus->tx_cpl_time_histo, (uint32)bus->tx_cpl_time_usec);
+
/* With heavy RX traffic, this routine potentially could spend some time
* processing RX frames without RX bound
*/
- more |= dhd_prot_process_msgbuf_rxcpl(bus->dhd, dhd_rxbound, DHD_REGULAR_RING);
+ more |= dhd_prot_process_msgbuf_rxcpl(bus->dhd, DHD_REGULAR_RING, &rxcpl_items);
bus->last_process_rxcpl_time = OSL_LOCALTIME_NS();
+ bus->rx_cpl_post_time_usec =
+ (bus->last_process_rxcpl_time - bus->last_process_txcpl_time) / NSEC_PER_USEC;
+ dhd_histo_update(bus->dhd, bus->rx_cpl_post_time_histo, (uint32)bus->rx_cpl_post_time_usec);
+
/* Process info ring completion messages */
#ifdef EWP_EDL
if (!bus->dhd->dongle_edl_support)
#endif
{
- more |= dhd_prot_process_msgbuf_infocpl(bus->dhd, DHD_INFORING_BOUND);
+ more |= dhd_prot_process_msgbuf_infocpl(bus->dhd, DHD_INFORING_BOUND,
+ &evtlog_items);
bus->last_process_infocpl_time = OSL_LOCALTIME_NS();
}
#ifdef EWP_EDL
else {
- more |= dhd_prot_process_msgbuf_edl(bus->dhd, &edl_itmes);
+ more |= dhd_prot_process_msgbuf_edl(bus->dhd, &evtlog_items);
bus->last_process_edl_time = OSL_LOCALTIME_NS();
}
#endif /* EWP_EDL */
@@ -13024,12 +13500,24 @@
dhdpci_bus_rte_log_time_sync_poll(bus);
#endif /* DHD_H2D_LOG_TIME_SYNC */
-#if defined(EWP_EDL) && defined(DHD_WAKE_STATUS)
- if ((edl_itmes > 0) && (bcmpcie_get_edl_wake(bus) > 0)) {
- DHD_ERROR(("##### dhdpcie_host_wake caused by Event Logs, edl_itmes %d\n",
- edl_itmes));
+#if defined(DHD_WAKE_STATUS)
+ /* Check if host was woken up by any packets */
+ if (dhd_bus_get_bus_wake(bus->dhd) > 0) {
+ /*
+ * If wake is due to Rx packets,
+ * pktwake info will be printed and cleared from dhd_rx_frame()
+ */
+ DHD_ERROR(("#### dhdpcie_host_wake: rxcpl:%d ctrlcpl:%d txcpl:%d evtlog:%d ####\n",
+ rxcpl_items, ctrlcpl_items, txcpl_items, evtlog_items));
+
+ dhd_bus_set_get_bus_wake(bus->dhd, 0);
+
+ if (rxcpl_items > 0) {
+ /* Request packet dump for first Rx packet */
+ dhd_bus_set_get_bus_wake_pkt_dump(bus->dhd, 1);
+ }
}
-#endif /* EWP_EDL && DHD_WAKE_STATUS */
+#endif /* DHD_WAKE_STATUS */
return more;
}
@@ -13589,6 +14077,12 @@
bus->dhd->rx_cpl_lat_capable =
(sh->flags2 & PCIE_SHARED2_RX_CMPL_PRIO_VALID) ? TRUE : FALSE;
+ bus->dhd->mdring_capable =
+ (sh->flags2 & PCIE_SHARED2_METADATA_RING) ? TRUE : FALSE;
+
+ DHD_ERROR(("FW supports MD ring ? %s\n",
+ bus->dhd->mdring_capable ? "Y" : "N"));
+
if (MULTIBP_ENAB(bus->sih)) {
dhd_bus_pcie_pwr_req_clear(bus);
@@ -13750,6 +14244,8 @@
dhd_bus_pcie_pwr_req_clear_reload_war(bus);
+ dhd_init_dpc_histos(bus->dhd);
+
if (MULTIBP_ENAB(bus->sih)) {
dhd_bus_pcie_pwr_req(bus);
}
@@ -13970,6 +14466,8 @@
case BCM43752_D11AX2G_ID:
case BCM43752_D11AX5G_ID:
case BCM43752_CHIP_ID:
+ case BCM4381_CHIP_ID:
+ case BCM4381_D11AX_ID:
case BCM4388_CHIP_ID:
case BCM4388_D11AX_ID:
case BCM4389_CHIP_ID:
@@ -14301,7 +14799,7 @@
dll_prepend(&bus->flowring_active_list, &flow_ring_node->list);
DHD_FLOWRING_LIST_UNLOCK(bus->dhd->flowring_list_lock, flags);
- dhd_bus_schedule_queue(bus, flowid, FALSE); /* from queue to flowring */
+ dhd_bus_schedule_queue(bus, flowid, FALSE, 0, NULL); /* from queue to flowring */
return;
}
@@ -14544,7 +15042,7 @@
flow_ring_node->status = FLOW_RING_STATUS_OPEN;
- dhd_bus_schedule_queue(bus, flowid, FALSE);
+ dhd_bus_schedule_queue(bus, flowid, FALSE, 0, NULL);
return;
}
@@ -16704,7 +17202,18 @@
int
dhd_bus_get_bus_wake(dhd_pub_t *dhd)
{
- return bcmpcie_set_get_wake(dhd->bus, 0);
+ return bcmpcie_get_wake(dhd->bus);
+}
+int
+dhd_bus_set_get_bus_wake(dhd_pub_t *dhd, int set)
+{
+ return bcmpcie_set_get_wake(dhd->bus, set);
+}
+
+int
+dhd_bus_set_get_bus_wake_pkt_dump(dhd_pub_t *dhd, int wake_pkt_dump)
+{
+ return bcmpcie_set_get_wake_pkt_dump(dhd->bus, wake_pkt_dump);
}
#endif /* DHD_WAKE_STATUS */
@@ -16774,8 +17283,10 @@
DHD_ERROR(("\ncurrent_time="SEC_USEC_FMT"\n",
GET_SEC_USEC(current_time)));
DHD_ERROR(("isr_entry_time="SEC_USEC_FMT
+ " prev_isr_entry_time="SEC_USEC_FMT
" isr_exit_time="SEC_USEC_FMT"\n",
GET_SEC_USEC(bus->isr_entry_time),
+ GET_SEC_USEC(bus->prev_isr_entry_time),
GET_SEC_USEC(bus->isr_exit_time)));
DHD_ERROR(("isr_sched_dpc_time="SEC_USEC_FMT
" rpm_sched_dpc_time="SEC_USEC_FMT
@@ -16862,6 +17373,8 @@
}
}
+ dhd_dump_pcie_slave_wrapper_regs(dhd->bus);
+
if ((cr4regs = si_setcore(sih, ARMCR4_CORE_ID, 0)) != NULL) {
DHD_ERROR(("%s: ARM CR4 wrapper Reg\n", __FUNCTION__));
for (i = 0; i < (uint32)sizeof(wrapper_dump_list) / 4; i++) {
@@ -17219,10 +17732,6 @@
dhd_pcie_config_read(dhd->bus, PCIECFGREG_PML1_SUB_CTRL2,
sizeof(uint32))));
dhd_bus_dump_dar_registers(dhd->bus);
- if (dhd->bus->dar_err_set) {
- DHD_ERROR(("Skip dumping the PCIe Core registers. DAR error log set\n"));
- return 0;
- }
}
#endif /* EXTENDED_PCIE_DEBUG_DUMP */
@@ -17235,6 +17744,13 @@
dhd_bus_pcie_pwr_req(dhd->bus);
}
+ dhd_pcie_dump_wrapper_regs(dhd);
+
+ if (dhd->bus->dar_err_set) {
+ DHD_ERROR(("Skip dumping the PCIe Core registers. DAR error log set\n"));
+ goto exit;
+ }
+
DHD_ERROR(("\n ------- DUMPING PCIE core Registers ------- \r\n"));
/* XXX: hwnbu-twiki.sj.broadcom.com/twiki/pub/Mwgroup/
* CurrentPcieGen2ProgramGuide/pcie_ep.htm
@@ -17313,13 +17829,12 @@
si_corereg(dhd->bus->sih, dhd->bus->sih->buscoreidx,
dhd_bus_db0_addr_get(dhd->bus), 0, 0)));
- dhd_pcie_dump_wrapper_regs(dhd);
dhdpcie_hw_war_regdump(dhd->bus);
}
#endif /* EXTENDED_PCIE_DEBUG_DUMP */
dhd_pcie_dma_info_dump(dhd);
-
+exit:
if (MULTIBP_ENAB(dhd->bus->sih)) {
dhd_bus_pcie_pwr_req_clear(dhd->bus);
}
diff --git a/dhd_pcie.h b/dhd_pcie.h
index 5f5c717..df38944 100644
--- a/dhd_pcie.h
+++ b/dhd_pcie.h
@@ -1,7 +1,7 @@
/*
* Linux DHD Bus Module for PCIE
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -156,7 +156,7 @@
#define PCIE_FASTLPO_ENABLED(buscorerev) \
((buscorerev == 66) || (buscorerev == 67) || (buscorerev == 68) || \
- (buscorerev == 70) || (buscorerev == 72))
+ (buscorerev == 70) || (buscorerev == 72) || (buscorerev == 76))
/*
* HW JIRA - CRWLPCIEGEN2-672
@@ -250,8 +250,6 @@
#if !defined(NDIS)
struct pci_dev *rc_dev; /* pci RC device handle */
struct pci_dev *dev; /* pci device handle */
- uint32 aspm_enab_during_suspend; /* aspm enab flag during suspend */
- uint32 l1ss_enab_during_suspend; /* l1ss enab flag during suspend */
#endif /* !defined(NDIS) */
#ifdef DHD_EFI
void *pcie_dev;
@@ -440,6 +438,7 @@
uint64 last_oob_irq_disable_time;
#endif /* BCMPCIE_OOB_HOST_WAKE */
uint64 isr_entry_time;
+ uint64 prev_isr_entry_time;
uint64 isr_exit_time;
uint64 isr_sched_dpc_time;
uint64 rpm_sched_dpc_time;
@@ -459,6 +458,16 @@
uint64 last_resume_start_time;
uint64 last_resume_end_time;
uint64 last_non_ours_irq_time;
+ uint64 dpc_time_usec;
+ uint64 *dpc_time_histo;
+ uint64 ctrl_cpl_post_time_usec;
+ uint64 *ctrl_cpl_post_time_histo;
+ uint64 tx_post_time_usec;
+ uint64 *tx_post_time_histo;
+ uint64 tx_cpl_time_usec;
+ uint64 *tx_cpl_time_histo;
+ uint64 rx_cpl_post_time_usec;
+ uint64 *rx_cpl_post_time_histo;
bool hwa_enabled;
bool idma_enabled;
bool ifrm_enabled;
@@ -544,7 +553,8 @@
#ifdef BCMSLTGT
int xtalfreq; /* Xtal frequency used for htclkratio calculation */
uint32 ilp_tick; /* ILP ticks per second read from pmutimer */
- uint32 xtal_ratio; /* xtal ticks per 4 ILP ticks read from pmu_xtalfreq */
+ uint32 alp_to_ilp_ratio; /* ALP ticks per ILP ticks read from pmu_xtalfreq */
+ uint32 xtal_to_alp_ratio; /* xtal to ALP ratio which can change from chip to chip */
#endif /* BCMSLTGT */
uint16 hp2p_txcpl_max_items;
uint16 hp2p_rxcpl_max_items;
@@ -563,8 +573,15 @@
bool lpm_keep_in_reset; /* during LPM keep in FLR, if FLR force is enabled */
bool lpm_mem_kill; /* kill WLAN memories in LPM */
bool lpm_force_flr; /* Force F0 FLR on WLAN when in LPM */
+ uint32 lpbk_xfer_data_pattern_type; /* data Pattern type DMA lpbk */
} dhd_bus_t;
+#define LPBK_DMA_XFER_DTPTRN_DEFAULT 0
+#define LPBK_DMA_XFER_DTPTRN_0x00 1
+#define LPBK_DMA_XFER_DTPTRN_0xFF 2
+#define LPBK_DMA_XFER_DTPTRN_0x55 3
+#define LPBK_DMA_XFER_DTPTRN_0xAA 4
+
#define LPM_MODE_LPM_ALL 0x1
#define LPM_MODE_NO_MEMKILL 0x010
#define LPM_MODE_NO_FLR 0x100
@@ -836,9 +853,8 @@
#ifdef DHD_WAKE_STATUS
int bcmpcie_get_total_wake(struct dhd_bus *bus);
int bcmpcie_set_get_wake(struct dhd_bus *bus, int flag);
-#if defined(EWP_EDL)
-int bcmpcie_get_edl_wake(struct dhd_bus *bus);
-#endif /* EWP_EDL */
+int bcmpcie_get_wake(struct dhd_bus *bus);
+int bcmpcie_set_get_wake_pkt_dump(struct dhd_bus *bus, int wake_pkt_dump);
#endif /* DHD_WAKE_STATUS */
#ifdef DHD_MMIO_TRACE
extern void dhd_dump_bus_mmio_trace(dhd_bus_t *bus, struct bcmstrbuf *strbuf);
@@ -857,6 +873,9 @@
extern const char * dhd_convert_inb_state_names(enum dhd_bus_ds_state inbstate);
extern const char * dhd_convert_dsval(uint32 val, bool d2h);
extern int dhd_bus_inb_set_device_wake(struct dhd_bus *bus, bool val);
+#ifdef PCIE_INB_DSACK_EXT_WAIT
+extern void dhd_bus_ds_ack_debug_dump(struct dhd_bus *bus);
+#endif /* PCIE_INB_DSACK_EXT_WAIT */
extern void dhd_bus_inb_ack_pending_ds_req(dhd_bus_t *bus);
#endif /* PCIE_INB_DW */
extern void dhdpcie_bus_enab_pcie_dw(dhd_bus_t *bus, uint8 dw_option);
@@ -947,4 +966,7 @@
extern bool dhd_check_htput_chip(dhd_bus_t *bus);
+#if defined(DEVICE_TX_STUCK_DETECT) && defined(ASSOC_CHECK_SR)
+void dhd_assoc_check_sr(dhd_pub_t *dhd, bool state);
+#endif /* DEVICE_TX_STUCK_DETECT && ASSOC_CHECK_SR */
#endif /* dhd_pcie_h */
diff --git a/dhd_pcie_linux.c b/dhd_pcie_linux.c
old mode 100755
new mode 100644
index cd7db34..5eaeefe
--- a/dhd_pcie_linux.c
+++ b/dhd_pcie_linux.c
@@ -1,7 +1,7 @@
/*
* Linux DHD Bus Module for PCIE
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -134,9 +134,7 @@
unsigned int total_wake_count;
int pkt_wake;
int wake_irq;
-#if defined(EWP_EDL)
- int edl_wake;
-#endif /* EWP_EDL */
+ int pkt_wake_dump;
#endif /* DHD_WAKE_STATUS */
#ifdef USE_SMMU_ARCH_MSM
void *smmu_cxt;
@@ -206,8 +204,9 @@
static int dhdpcie_pm_system_suspend_noirq(struct device * dev);
static int dhdpcie_pm_system_resume_noirq(struct device * dev);
#else
-static int dhdpcie_pci_suspend(struct pci_dev *dev, pm_message_t state);
-static int dhdpcie_pci_resume(struct pci_dev *dev);
+static int dhdpcie_pci_suspend(struct device * dev);
+static int dhdpcie_pci_resume(struct device * dev);
+static int dhdpcie_pci_resume_early(struct device * dev);
#endif /* DHD_PCIE_NATIVE_RUNTIMEPM */
#endif /* DHD_PCIE_RUNTIMEPM */
@@ -255,14 +254,20 @@
.resume = dhdpcie_pm_resume,
.complete = dhdpcie_pm_complete,
};
-#endif /* DHD_PCIE_RUNTIMEPM */
-#ifdef DHD_PCIE_NATIVE_RUNTIMEPM
+#elif defined(DHD_PCIE_NATIVE_RUNTIMEPM)
static const struct dev_pm_ops dhdpcie_pm_ops = {
SET_RUNTIME_PM_OPS(dhdpcie_pm_runtime_suspend, dhdpcie_pm_runtime_resume, NULL)
.suspend_noirq = dhdpcie_pm_system_suspend_noirq,
.resume_noirq = dhdpcie_pm_system_resume_noirq
};
-#endif /* DHD_PCIE_NATIVE_RUNTIMEPM */
+#else
+/* for linux platforms */
+static const struct dev_pm_ops dhd_pcie_pm_ops = {
+ .suspend = dhdpcie_pci_suspend,
+ .resume = dhdpcie_pci_resume,
+ .resume_early = dhdpcie_pci_resume_early,
+};
+#endif /* DHD_PCIE_RUNTIMEPM */
static struct pci_driver dhdpcie_driver = {
node: {&dhdpcie_driver.node, &dhdpcie_driver.node},
@@ -270,12 +275,7 @@
id_table: dhdpcie_pci_devid,
probe: dhdpcie_pci_probe,
remove: dhdpcie_pci_remove,
-#if defined(DHD_PCIE_RUNTIMEPM) || defined(DHD_PCIE_NATIVE_RUNTIMEPM)
.driver.pm = &dhd_pcie_pm_ops,
-#else
- suspend: dhdpcie_pci_suspend,
- resume: dhdpcie_pci_resume,
-#endif /* DHD_PCIE_RUNTIMEPM || DHD_PCIE_NATIVE_RUNTIMEPM */
shutdown: dhdpcie_pci_shutdown,
};
@@ -759,10 +759,6 @@
}
bus = pch->bus;
-
- if (bus->dhd->up)
- DHD_DISABLE_RUNTIME_PM(bus->dhd);
-
bus->chk_pm = TRUE;
return 0;
@@ -795,14 +791,6 @@
dhd_os_busbusy_wake(bus->dhd);
DHD_GENERAL_UNLOCK(bus->dhd, flags);
-#if defined(CUSTOMER_HW4_DEBUG)
- if (ret == BCME_OK) {
- uint32 pm_dur = 0;
- dhd_iovar(bus->dhd, 0, "pm_dur", NULL, 0, (char *)&pm_dur, sizeof(pm_dur), FALSE);
- DHD_ERROR(("%s: PM duration(%d)\n", __FUNCTION__, pm_dur));
- }
-#endif /* CUSTOMER_HW4_DEBUG */
-
return ret;
}
@@ -811,6 +799,9 @@
struct pci_dev *pdev = to_pci_dev(dev);
dhdpcie_info_t *pch = pci_get_drvdata(pdev);
dhd_bus_t *bus = NULL;
+#if defined(CUSTOMER_HW4_DEBUG)
+ uint32 pm_dur = 0;
+#endif /* CUSTOMER_HW4_DEBUG */
if (!pch || !pch->bus) {
return;
@@ -818,17 +809,23 @@
bus = pch->bus;
- if (bus->dhd->up)
- DHD_ENABLE_RUNTIME_PM(bus->dhd);
+#ifdef WL_TWT
+ dhd_config_twt_event_mask_in_suspend(bus->dhd, FALSE);
+ dhd_send_twt_info_suspend(bus->dhd, FALSE);
+#endif /* WL_TWT */
bus->chk_pm = FALSE;
-
+#if defined(CUSTOMER_HW4_DEBUG)
+ dhd_iovar(bus->dhd, 0, "pm_dur", NULL, 0, (char *)&pm_dur, sizeof(pm_dur), FALSE);
+ DHD_ERROR(("%s: PM duration(%d)\n", __FUNCTION__, pm_dur));
+#endif /* CUSTOMER_HW4_DEBUG */
return;
}
#else
-static int dhdpcie_pci_suspend(struct pci_dev * pdev, pm_message_t state)
+static int dhdpcie_pci_suspend(struct device *dev)
{
int ret = 0;
+ struct pci_dev *pdev = to_pci_dev(dev);
dhdpcie_info_t *pch = pci_get_drvdata(pdev);
dhd_bus_t *bus = NULL;
unsigned long flags;
@@ -842,8 +839,9 @@
return ret;
}
- BCM_REFERENCE(state);
-
+#if defined(DEVICE_TX_STUCK_DETECT) && defined(ASSOC_CHECK_SR)
+ dhd_assoc_check_sr(bus->dhd, TRUE);
+#endif /* DEVICE_TX_STUCK_DETECT && ASSOC_CHECK_SR */
DHD_GENERAL_LOCK(bus->dhd, flags);
if (!DHD_BUS_BUSY_CHECK_IDLE(bus->dhd)) {
DHD_BUS_BUSY_SET_SUSPEND_IN_PROGRESS(bus->dhd);
@@ -878,9 +876,61 @@
return ret;
}
-static int dhdpcie_pci_resume(struct pci_dev *pdev)
+static int dhdpcie_pci_resume_early(struct device *dev)
{
int ret = 0;
+ struct pci_dev *pdev = to_pci_dev(dev);
+ dhdpcie_info_t *pch = pci_get_drvdata(pdev);
+ dhd_bus_t *bus = NULL;
+ uint32 pmcsr;
+
+ if (pch) {
+ bus = pch->bus;
+ }
+ if (!bus) {
+ return ret;
+ }
+
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(5, 0, 9))
+ /* On fc30 (linux ver 5.0.9),
+ * PMEStat of PMCSR(cfg reg) is cleared before this callback by kernel.
+ * So, we use SwPme of FunctionControl(enum reg) instead of PMEStat without kernel change.
+ */
+ if (bus->sih->buscorerev >= 64) {
+ uint32 ftnctrl;
+ volatile void *regsva = (volatile void *)bus->regs;
+
+ ftnctrl = pcie_corereg(bus->osh, regsva,
+ OFFSETOF(sbpcieregs_t, ftn_ctrl.control), 0, 0);
+ pmcsr = OSL_PCI_READ_CONFIG(bus->osh, PCIE_CFG_PMCSR, sizeof(pmcsr));
+
+ DHD_ERROR(("%s(): pmcsr is 0x%x, ftnctrl is 0x%8x \r\n",
+ __FUNCTION__, pmcsr, ftnctrl));
+ if (ftnctrl & PCIE_FTN_SWPME_MASK) {
+ DHD_ERROR(("%s(): Wakeup due to WLAN \r\n", __FUNCTION__));
+ }
+ } else
+#endif /* (LINUX_VERSION_CODE >= KERNEL_VERSION(5, 0, 9)) */
+ {
+ pmcsr = OSL_PCI_READ_CONFIG(bus->osh, PCIE_CFG_PMCSR, sizeof(pmcsr));
+
+ DHD_ERROR(("%s(): pmcsr is 0x%x \r\n", __FUNCTION__, pmcsr));
+ if (pmcsr & PCIE_PMCSR_PMESTAT) {
+ DHD_ERROR(("%s(): Wakeup due to WLAN \r\n", __FUNCTION__));
+ }
+ }
+
+ /*
+ * TODO: Add code to take adavantage of what is read from pmcsr
+ */
+
+ return ret;
+}
+
+static int dhdpcie_pci_resume(struct device *dev)
+{
+ int ret = 0;
+ struct pci_dev *pdev = to_pci_dev(dev);
dhdpcie_info_t *pch = pci_get_drvdata(pdev);
dhd_bus_t *bus = NULL;
unsigned long flags;
@@ -903,6 +953,14 @@
DHD_BUS_BUSY_CLEAR_RESUME_IN_PROGRESS(bus->dhd);
dhd_os_busbusy_wake(bus->dhd);
DHD_GENERAL_UNLOCK(bus->dhd, flags);
+#if defined(DEVICE_TX_STUCK_DETECT) && defined(ASSOC_CHECK_SR)
+ dhd_assoc_check_sr(bus->dhd, FALSE);
+#endif /* DEVICE_TX_STUCK_DETECT && ASSOC_CHECK_SR */
+
+#ifdef WL_TWT
+ dhd_config_twt_event_mask_in_suspend(bus->dhd, FALSE);
+ dhd_send_twt_info_suspend(bus->dhd, FALSE);
+#endif /* WL_TWT */
#ifdef DHD_CFG80211_SUSPEND_RESUME
dhd_cfg80211_resume(bus->dhd);
@@ -1106,12 +1164,6 @@
}
#endif /* OEM_ANDROID && LINUX_VERSION_CODE >= KERNEL_VERSION(3, 0, 0) */
- /* Save aspm and l1ss state before doing to suspend, if they are disabled,
- * keep them disabled after resume.
- */
- bus->aspm_enab_during_suspend = dhd_bus_is_aspm_enab_rc_ep(bus);
- bus->l1ss_enab_during_suspend = dhd_bus_is_l1ss_enab_rc_ep(bus);
-
#if defined(CUSTOMER_HW4_DEBUG)
clear_debug_dump_time(dhd_suspend_resume_time_str);
get_debug_dump_time(dhd_suspend_resume_time_str);
@@ -1168,26 +1220,34 @@
ret = pch->pkt_wake;
pch->total_wake_count += flag;
pch->pkt_wake = flag;
-#if defined(EWP_EDL)
- pch->edl_wake = flag;
-#endif /* EWP_EDL */
DHD_PKT_WAKE_UNLOCK(&pch->pkt_wake_lock, flags);
return ret;
}
-#if defined(EWP_EDL)
-int
-bcmpcie_get_edl_wake(struct dhd_bus *bus)
+int bcmpcie_get_wake(struct dhd_bus *bus)
{
- int ret;
dhdpcie_info_t *pch = pci_get_drvdata(bus->dev);
+ unsigned long flags;
+ int ret;
- ret = pch->edl_wake;
- pch->edl_wake = 0;
-
+ DHD_PKT_WAKE_LOCK(&pch->pkt_wake_lock, flags);
+ ret = pch->pkt_wake;
+ DHD_PKT_WAKE_UNLOCK(&pch->pkt_wake_lock, flags);
return ret;
}
-#endif /* EWP_EDL */
+
+int bcmpcie_set_get_wake_pkt_dump(struct dhd_bus *bus, int wake_pkt_dump)
+{
+ dhdpcie_info_t *pch = pci_get_drvdata(bus->dev);
+ unsigned long flags;
+ int ret;
+
+ DHD_PKT_WAKE_LOCK(&pch->pkt_wake_lock, flags);
+ ret = pch->pkt_wake_dump;
+ pch->pkt_wake_dump = wake_pkt_dump;
+ DHD_PKT_WAKE_UNLOCK(&pch->pkt_wake_lock, flags);
+ return ret;
+}
#endif /* DHD_WAKE_STATUS */
static int dhdpcie_resume_dev(struct pci_dev *dev)
@@ -1237,18 +1297,6 @@
*/
dhd_plat_l1ss_ctrl(1);
- /* Disable ASPM and L1SS if they were disabled during suspend,
- * after resume they are enabled by default.
- */
- if ((pch->bus->aspm_enab_during_suspend == FALSE) &&
- (dhd_bus_is_aspm_enab_rc_ep(pch->bus) == TRUE)) {
- dhd_bus_aspm_enable_rc_ep(pch->bus, FALSE);
- }
- if ((pch->bus->l1ss_enab_during_suspend == FALSE) &&
- (dhd_bus_is_l1ss_enab_rc_ep(pch->bus) == TRUE)) {
- dhd_bus_l1ss_enable_rc_ep(pch->bus, FALSE);
- }
-
out:
return err;
}
@@ -1539,9 +1587,55 @@
void
dhdpcie_bus_unregister(void)
{
+ unsigned long flags;
+ dhd_pub_t *dhdp = NULL;
+ if (!g_dhd_bus) {
+ DHD_ERROR(("%s: Bus is NULL\n", __FUNCTION__));
+ return;
+ }
+ dhdp = g_dhd_bus->dhd;
+ DHD_GENERAL_LOCK(dhdp, flags);
+ /* Check if bus is in suspend due to wifi off with accel boot */
+ if (dhdp->up == FALSE && dhdp->busstate == DHD_BUS_SUSPEND) {
+ DHD_GENERAL_UNLOCK(dhdp, flags);
+ DHD_ERROR(("%s Bus is in suspend state\n", __FUNCTION__));
+ dhdpcie_pci_suspend_resume(dhdp->bus, FALSE);
+ } else {
+ DHD_GENERAL_UNLOCK(dhdp, flags);
+ }
pci_unregister_driver(&dhdpcie_driver);
}
+#if defined(CONFIG_ARCH_WAIPIO) || defined(CONFIG_SOC_S5E9925)
+bool devid_mismatch = FALSE;
+
+bool dhdpcie_validate_devid(uint16 device)
+{
+ uint16 config_devid;
+
+#ifdef BCM4389_CHIP_DEF
+ config_devid = BCM4389_D11AX_ID;
+#elif defined(BCM4375_CHIP)
+ config_devid = BCM4375_D11AX_ID;
+#else
+ DHD_ERROR(("%s: Unknown dev id, BCMXXXX_CHIP is not defined \n",
+ __FUNCTION__));
+ config_devid = 0;
+
+ return FALSE;
+#endif /* BCM4389_CHIP_DEF */
+
+ DHD_ERROR(("%s: config_devid %X device %X\n", __FUNCTION__, config_devid, device));
+
+ if ((config_devid == BCM4389_D11AX_ID) && (device == BCM4389_CHIP_ID)) {
+ /* The dev id is 4389 if OTP is not written. */
+ return TRUE;
+ }
+
+ return config_devid == device;
+}
+#endif /* CONFIG_ARCH_WAIPIO || CONFIG_SOC_S5E9925 */
+
int __devinit
dhdpcie_pci_probe(struct pci_dev *pdev, const struct pci_device_id *ent)
{
@@ -1555,6 +1649,15 @@
"(good PCI location)\n", pdev->bus->number,
PCI_SLOT(pdev->devfn), pdev->vendor, pdev->device));
+#if defined(CONFIG_ARCH_WAIPIO) || defined(CONFIG_SOC_S5E9925)
+ if (dhdpcie_validate_devid(pdev->device) == FALSE) {
+ DHD_ERROR(("%s: dev id and BCMXXXX_CHIP definition is not matched\n",
+ __FUNCTION__));
+ devid_mismatch = TRUE;
+ return -ENODEV;
+ }
+#endif /* CONFIG_ARCH_WAIPIO || CONFIG_SOC_S5E9925 */
+
if (dhdpcie_init_succeeded == TRUE) {
DHD_ERROR(("%s(): === Driver Already attached to a BRCM device === \r\n",
__FUNCTION__));
@@ -1619,10 +1722,6 @@
#endif /* DHD_PCIE_NATIVE_RUNTIMEPM */
if (bus) {
- if (bus->dhd->up == FALSE) {
- DHD_ERROR(("%s: Wlan is in OFF state return\n", __FUNCTION__));
- return;
- }
#ifdef SUPPORT_LINKDOWN_RECOVERY
dhd_plat_pcie_deregister_event(bus->dhd->plat_info);
#endif /* SUPPORT_LINKDOWN_RECOVERY */
@@ -2280,10 +2379,15 @@
if (bus) {
pdev = bus->dev;
if (bus->irq_registered) {
+#if defined(SET_PCIE_IRQ_CPU_CORE) || defined(DHD_CONTROL_PCIE_CPUCORE_WIFI_TURNON) || \
+ defined(CLEAN_IRQ_AFFINITY_HINT)
/* clean up the affinity_hint before
* the unregistration of PCIe irq
*/
(void)irq_set_affinity_hint(pdev->irq, NULL);
+#endif /* SET_PCIE_IRQ_CPU_CORE || DHD_CONTROL_PCIE_CPUCORE_WIFI_TURNON ||
+ * CLEAN_IRQ_AFFINITY_HINT
+ */
free_irq(pdev->irq, bus);
bus->irq_registered = FALSE;
if (bus->d2h_intr_method == PCIE_MSI) {
@@ -2319,6 +2423,7 @@
dhdpcie_isr(int irq, void *arg)
{
dhd_bus_t *bus = (dhd_bus_t*)arg;
+ bus->prev_isr_entry_time = bus->isr_entry_time;
bus->isr_entry_time = OSL_LOCALTIME_NS();
if (!dhdpcie_bus_isr(bus)) {
DHD_LOG_MEM(("%s: dhdpcie_bus_isr returns with FALSE\n", __FUNCTION__));
@@ -2410,13 +2515,29 @@
#ifdef CONFIG_ARCH_MSM
#ifdef SUPPORT_LINKDOWN_RECOVERY
+#if (LINUX_VERSION_CODE < KERNEL_VERSION(5, 4, 0))
if (bus->no_cfg_restore) {
options = MSM_PCIE_CONFIG_NO_CFG_RESTORE;
}
+#endif /* LINUX_VERSION_CODE < KERNEL_VERSION(5, 4, 0) */
ret = msm_pcie_pm_control(MSM_PCIE_RESUME, bus->dev->bus->number,
bus->dev, NULL, options);
if (bus->no_cfg_restore && !ret) {
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(5, 4, 0))
+ dhdpcie_info_t *pch;
+ pch = pci_get_drvdata(bus->dev);
+ if (pch == NULL) {
+ return BCME_ERROR;
+ }
+ if (pch->state) {
+ pci_load_and_free_saved_state(bus->dev, &pch->state);
+ } else {
+ pci_load_saved_state(bus->dev, pch->default_state);
+ }
+ pci_restore_state(bus->dev);
+#else
msm_pcie_recover_config(bus->dev);
+#endif /* LINUX_VERSION_CODE >= KERNEL_VERSION(5, 4, 0) */
bus->no_cfg_restore = 0;
}
#else
@@ -2462,10 +2583,11 @@
#ifdef CONFIG_ARCH_MSM
#ifdef SUPPORT_LINKDOWN_RECOVERY
+#if (LINUX_VERSION_CODE < KERNEL_VERSION(5, 4, 0))
if (bus->no_cfg_restore) {
options = MSM_PCIE_CONFIG_NO_CFG_RESTORE | MSM_PCIE_CONFIG_LINKDOWN;
}
-
+#endif /* LINUX_VERSION_CODE < KERNEL_VERSION(5, 4, 0) */
ret = msm_pcie_pm_control(MSM_PCIE_SUSPEND, bus->dev->bus->number,
bus->dev, NULL, options);
#else
@@ -2544,18 +2666,6 @@
uint32 vid, saved_vid;
pci_read_config_dword(bus->dev, PCI_CFG_VID, &vid);
saved_vid = bus->dev->saved_config_space[PCI_CFG_VID];
-#if defined(CONFIG_WIFI_BROADCOM_COB) && defined(BCM4389_CHIP_DEF)
- /*
- * WAR for changing PCIe config space after OTP writing
- * If vid changes 4389 -> 4441 and otpinfo_val = 1, OTP is changed
- * so, calling panic for rebooting the device
- */
- if (saved_vid == 0x438914e4 && vid == 0x444114e4 && otpinfo_val == 1) {
- panic("BCM4389 COB WLAN PCI config space is changed after "
- "OTP writing process, needs to reboot,\n"
- "This process is required only once.\n");
- }
-#endif /* CONFIG_WIFI_BROADCOM_COB && BCM4389_CHIP_DEF */
if (vid != saved_vid) {
DHD_ERROR(("%s: VID(0x%x) is different from saved VID(0x%x) "
"Skip the bus init\n", __FUNCTION__, vid, saved_vid));
@@ -3186,7 +3296,13 @@
return FALSE;
}
- if ((bus->idletime > 0) && (bus->idlecount >= bus->idletime)) {
+#ifdef RPM_FAST_TRIGGER
+ if ((dhd->rpm_fast_trigger == TRUE) ||
+ ((bus->idletime > 0) && (bus->idlecount >= bus->idletime)))
+#else
+ if (((bus->idletime > 0) && (bus->idlecount >= bus->idletime)))
+#endif /* RPM_FAST_TRIGGER */
+ {
bus->idlecount = 0;
if (DHD_BUS_BUSY_CHECK_IDLE(dhd) && !DHD_BUS_CHECK_DOWN_OR_DOWN_IN_PROGRESS(dhd) &&
!DHD_CHECK_CFG_IN_PROGRESS(dhd) && !dhd_os_check_wakelock_all(bus->dhd)) {
@@ -3231,6 +3347,12 @@
DHD_BUS_BUSY_SET_RPM_SUSPEND_DONE(dhd);
/* For making sure NET TX Queue active */
dhd_bus_start_queue(bus);
+#ifdef RPM_FAST_TRIGGER
+ if (dhd->rpm_fast_trigger) {
+ DHD_ERROR(("%s : reset rpm_fast_trigger\n", __FUNCTION__));
+ dhd->rpm_fast_trigger = FALSE;
+ }
+#endif /* RPM_FAST_TRIGGER */
DHD_GENERAL_UNLOCK(dhd, flags);
#if defined(DHD_KERNEL_SCHED_DEBUG) && defined(DHD_FW_COREDUMP)
curr_time_ns = OSL_LOCALTIME_NS();
@@ -3300,8 +3422,9 @@
/* Since one of the contexts are busy (TX, IOVAR or RX)
* we should not suspend
*/
- DHD_ERROR(("%s : bus is active with dhd_bus_busy_state = 0x%x\n",
- __FUNCTION__, dhd->dhd_bus_busy_state));
+ DHD_ERROR(("%s : bus active dhd_bus_busy_state:0x%x cfg_in_progress:%d\n",
+ __FUNCTION__, dhd->dhd_bus_busy_state,
+ DHD_CHECK_CFG_IN_PROGRESS(dhd)));
return FALSE;
}
}
@@ -3339,7 +3462,7 @@
DHD_GENERAL_UNLOCK(bus->dhd, flags);
- DHD_ERROR_RLMT(("Runtime Resume is called in %ps\n", func_addr));
+ DHD_ERROR(("Runtime Resume is called in %ps\n", func_addr));
smp_wmb();
wake_up(&bus->rpm_queue);
/* No need to wake up the RPM state thread */
@@ -3425,7 +3548,9 @@
void
dhd_bus_inform_ep_loaded_to_rc(dhd_pub_t *dhdp, bool up)
{
- sec_pcie_set_ep_driver_loaded(dhdp->bus->rc_dev, up);
+ if (dhdp->bus->rc_dev) {
+ sec_pcie_set_ep_driver_loaded(dhdp->bus->rc_dev, up);
+ }
}
#endif /* CONFIG_ARCH_MSM && CONFIG_SEC_PCIE_L1SS */
diff --git a/dhd_pktlog.c b/dhd_pktlog.c
index 76edfe4..bb7cc12 100644
--- a/dhd_pktlog.c
+++ b/dhd_pktlog.c
@@ -1,7 +1,7 @@
/*
* DHD debugability packet logging support
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -168,7 +168,7 @@
return -EINVAL;
}
- pktlog = (dhd_pktlog_t *)MALLOCZ(dhdp->osh, sizeof(dhd_pktlog_t));
+ pktlog = (dhd_pktlog_t *)VMALLOCZ(dhdp->osh, sizeof(dhd_pktlog_t));
if (unlikely(!pktlog)) {
DHD_ERROR(("%s(): could not allocate memory for - "
"dhd_pktlog_t\n", __FUNCTION__));
@@ -222,7 +222,7 @@
DHD_INFO(("%s(): dhd_os_attach_pktlog detach\n", __FUNCTION__));
- MFREE(dhdp->osh, dhdp->pktlog, sizeof(dhd_pktlog_t));
+ VMFREE(dhdp->osh, dhdp->pktlog, sizeof(dhd_pktlog_t));
return BCME_OK;
}
@@ -230,8 +230,6 @@
#ifdef DHD_PKT_LOGGING_DBGRING
int dhd_pktlog_is_enabled(dhd_pub_t *dhdp)
{
- struct dhd_pktlog_ring *pktlog_ring;
-
if (!dhdp || !dhdp->pktlog) {
DHD_ERROR(("%s(): dhdp=%p pktlog=%p\n",
__FUNCTION__, dhdp, (dhdp ? dhdp->pktlog : NULL)));
@@ -244,7 +242,6 @@
return BCME_ERROR;
}
- pktlog_ring = dhdp->pktlog->pktlog_ring;
return OSL_ATOMIC_READ(dhdp->osh, &dhdp->pktlog->enable);
}
@@ -308,7 +305,7 @@
return NULL;
}
- ring = (dhd_pktlog_ring_t *)MALLOCZ(dhdp->osh, sizeof(dhd_pktlog_ring_t));
+ ring = (dhd_pktlog_ring_t *)VMALLOCZ(dhdp->osh, sizeof(dhd_pktlog_ring_t));
if (unlikely(!ring)) {
DHD_ERROR(("%s(): could not allocate memory for - "
"dhd_pktlog_ring_t\n", __FUNCTION__));
@@ -318,7 +315,7 @@
dll_init(&ring->ring_info_head);
dll_init(&ring->ring_info_free);
- ring->ring_info_mem = (dhd_pktlog_ring_info_t *)MALLOCZ(dhdp->osh,
+ ring->ring_info_mem = (dhd_pktlog_ring_info_t *)VMALLOCZ(dhdp->osh,
sizeof(dhd_pktlog_ring_info_t) * size);
if (unlikely(!ring->ring_info_mem)) {
DHD_ERROR(("%s(): could not allocate memory for - "
@@ -346,7 +343,7 @@
return ring;
fail:
if (ring) {
- MFREE(dhdp->osh, ring, sizeof(dhd_pktlog_ring_t));
+ VMFREE(dhdp->osh, ring, sizeof(dhd_pktlog_ring_t));
}
return NULL;
@@ -405,7 +402,7 @@
}
if (ring->ring_info_mem) {
- MFREE(ring->dhdp->osh, ring->ring_info_mem,
+ VMFREE(ring->dhdp->osh, ring->ring_info_mem,
sizeof(dhd_pktlog_ring_info_t) * ring->pktlog_len);
}
@@ -413,7 +410,7 @@
osl_spin_lock_deinit(ring->dhdp->osh, ring->pktlog_ring_lock);
}
- MFREE(dhdp->osh, ring, sizeof(dhd_pktlog_ring_t));
+ VMFREE(dhdp->osh, ring, sizeof(dhd_pktlog_ring_t));
DHD_INFO(("%s(): pktlog ring deinit\n", __FUNCTION__));
@@ -1072,6 +1069,7 @@
/* Ethernet Type MAC Header 12 bytes + Frame payload 10 bytes */
#define PKTLOG_MINIMIZE_REPORT_LEN 22
+#ifndef DHD_PKT_LOGGING_DBGRING
static char pktlog_minmize_mask_table[] = {
0xff, 0x00, 0x00, 0x00, 0xff, 0x0f, /* Ethernet Type MAC Header - Destination MAC Address */
0xff, 0x00, 0x00, 0x00, 0xff, 0x0f, /* Ethernet Type MAC Header - Source MAC Address */
@@ -1125,6 +1123,7 @@
}
vfree(mem_buf);
}
+#endif /* !DHD_PKT_LOGGING_DBGRING */
dhd_pktlog_ring_t*
dhd_pktlog_ring_change_size(dhd_pktlog_ring_t *ringbuf, int size)
diff --git a/dhd_pktlog.h b/dhd_pktlog.h
index e7518ae..f4f9f26 100644
--- a/dhd_pktlog.h
+++ b/dhd_pktlog.h
@@ -1,7 +1,7 @@
/*
* DHD debugability packet logging header file
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/dhd_plat.h b/dhd_plat.h
index 00827bb..df87778 100644
--- a/dhd_plat.h
+++ b/dhd_plat.h
@@ -1,7 +1,7 @@
/*
* DHD Linux platform header file
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/dhd_pno.c b/dhd_pno.c
index b1775a0..3089328 100644
--- a/dhd_pno.c
+++ b/dhd_pno.c
@@ -2,7 +2,7 @@
* Broadcom Dongle Host Driver (DHD)
* Prefered Network Offload and Wi-Fi Location Service(WLS) code.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -399,6 +399,7 @@
exit:
return err;
}
+
static int
_dhd_pno_enable(dhd_pub_t *dhd, int enable)
{
@@ -495,6 +496,10 @@
pfn_param.flags = ((PFN_LIST_ORDER << SORT_CRITERIA_BIT) |
(ENABLE << IMMEDIATE_SCAN_BIT) | (ENABLE << REPORT_SEPERATELY_BIT));
+#ifdef WL_SCHED_SCAN
+ /* bit to select the pfn partial scan result event logic */
+ pfn_param.flags |= htod16(ENABLE << PFN_FULL_SCAN_RESULT_BIT);
+#endif /* WL_SCHED_SCAN */
if (mode == DHD_PNO_LEGACY_MODE) {
pfn_param.repeat = (uchar) (pno_params->params_legacy.pno_repeat);
/* check and set extra pno params */
@@ -678,6 +683,7 @@
exit:
return err;
}
+
static int
_dhd_pno_add_ssid(dhd_pub_t *dhd, struct list_head* ssid_list, int nssid)
{
@@ -732,12 +738,14 @@
MFREE(dhd->osh, pfn_elem_buf, mem_needed);
return err;
}
+
/* qsort compare function */
static int
_dhd_pno_cmpfunc(const void *a, const void *b)
{
return (*(const uint16*)a - *(const uint16*)b);
}
+
static int
_dhd_pno_chan_merge(uint16 *d_chan_list, int *nchan,
uint16 *chan_list1, int nchan1, uint16 *chan_list2, int nchan2)
@@ -773,6 +781,7 @@
*nchan = k;
return err;
}
+
static int
_dhd_pno_get_channels(dhd_pub_t *dhd, uint16 *d_chan_list,
int *nchan, uint8 band, bool skip_dfs)
@@ -824,6 +833,7 @@
*nchan = j;
return err;
}
+
static int
_dhd_pno_convert_format(dhd_pub_t *dhd, struct dhd_pno_batch_params *params_batch,
char *buf, int nbufsize)
@@ -958,6 +968,7 @@
bytes_written = (int32)(bp - buf);
return bytes_written;
}
+
static int
_dhd_pno_clear_all_batch_results(dhd_pub_t *dhd, struct list_head *head, bool only_last)
{
@@ -1040,6 +1051,7 @@
exit:
return err;
}
+
static int
_dhd_pno_reinitialize_prof(dhd_pub_t *dhd, dhd_pno_params_t *params, dhd_pno_mode_t mode)
{
@@ -1123,6 +1135,7 @@
mutex_unlock(&_pno_state->pno_mutex);
return err;
}
+
static int
_dhd_pno_add_bssid(dhd_pub_t *dhd, wl_pfn_bssid_t *p_pfn_bssid, int nbssid)
{
@@ -1531,6 +1544,7 @@
}
return err;
}
+
int
dhd_pno_set_for_batch(dhd_pub_t *dhd, struct dhd_pno_batch_params *batch_params)
{
@@ -1600,13 +1614,13 @@
sizeof(_params->params_batch.chan_list[0]), _dhd_pno_cmpfunc, NULL);
}
#ifdef PNO_DEBUG
-{
+ {
DHD_PNO(("Channel list : "));
for (i = 0; i < _params->params_batch.nchan; i++) {
DHD_PNO(("%d ", _params->params_batch.chan_list[i]));
}
DHD_PNO(("\n"));
-}
+ }
#endif
if (_params->params_batch.nchan) {
/* copy the channel list into local array */
@@ -2147,7 +2161,7 @@
goto exit;
}
- pfn_gscan_cfg_t->version = WL_GSCAN_CFG_VERSION;
+ pfn_gscan_cfg_t->version = WL_GSCAN_CFG_VERSION_1;
if (gscan_params->mscan)
pfn_gscan_cfg_t->buffer_threshold = gscan_params->buffer_threshold;
else
@@ -2516,7 +2530,7 @@
if (old_flag != gscan_params->send_all_results_flag) {
wl_pfn_gscan_cfg_t gscan_cfg;
- gscan_cfg.version = WL_GSCAN_CFG_VERSION;
+ gscan_cfg.version = WL_GSCAN_CFG_VERSION_1;
gscan_cfg.flags = (gscan_params->send_all_results_flag &
GSCAN_SEND_ALL_RESULTS_MASK);
gscan_cfg.flags |= GSCAN_CFG_FLAGS_ONLY_MASK;
@@ -3504,6 +3518,7 @@
complete(&_pno_state->get_batch_done);
return err;
}
+
static void
_dhd_pno_get_batch_handler(struct work_struct *work)
{
@@ -3768,14 +3783,14 @@
sizeof(_params->params_hotlist.chan_list[0]), _dhd_pno_cmpfunc, NULL);
}
#ifdef PNO_DEBUG
-{
+ {
int i;
DHD_PNO(("Channel list : "));
for (i = 0; i < _params->params_batch.nchan; i++) {
DHD_PNO(("%d ", _params->params_batch.chan_list[i]));
}
DHD_PNO(("\n"));
-}
+ }
#endif
if (_params->params_hotlist.nchan) {
/* copy the channel list into local array */
@@ -3994,8 +4009,8 @@
void *
dhd_process_full_gscan_result(dhd_pub_t *dhd, const void *data, uint32 len, int *size)
{
- wl_bss_info_t *bi = NULL;
- wl_gscan_result_t *gscan_result;
+ wl_bss_info_v109_t *bi = NULL;
+ wl_gscan_result_v2_t *gscan_result;
wifi_gscan_full_result_t *result = NULL;
u32 bi_length = 0;
uint8 channel;
@@ -4006,7 +4021,7 @@
*size = 0;
GCC_DIAGNOSTIC_PUSH_SUPPRESS_CAST();
- gscan_result = (wl_gscan_result_t *)data;
+ gscan_result = (wl_gscan_result_v2_t *)data;
GCC_DIAGNOSTIC_POP();
if (!gscan_result) {
DHD_ERROR(("Invalid gscan result (NULL pointer)\n"));
@@ -4025,7 +4040,8 @@
bi = &gscan_result->bss_info[0].info;
bi_length = dtoh32(bi->length);
if (bi_length != (dtoh32(gscan_result->buflen) -
- WL_GSCAN_RESULTS_FIXED_SIZE - WL_GSCAN_INFO_FIXED_FIELD_SIZE)) {
+ OFFSETOF(wl_gscan_result_v2_t, bss_info) -
+ OFFSETOF(wl_gscan_bss_info_v2_t, info))) {
DHD_ERROR(("Invalid bss_info length %d: ignoring\n", bi_length));
goto exit;
}
@@ -4591,6 +4607,7 @@
MFREE(dhd->osh, buf, WLC_IOCTL_SMLEN);
return err;
}
+
int dhd_pno_deinit(dhd_pub_t *dhd)
{
int err = BCME_OK;
diff --git a/dhd_pno.h b/dhd_pno.h
index fecba43..9fcc8c9 100644
--- a/dhd_pno.h
+++ b/dhd_pno.h
@@ -2,7 +2,7 @@
* Header file of Broadcom Dongle Host Driver (DHD)
* Prefered Network Offload code and Wi-Fi Location Service(WLS) code.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/dhd_proto.h b/dhd_proto.h
index a914f02..2a16f9e 100644
--- a/dhd_proto.h
+++ b/dhd_proto.h
@@ -4,7 +4,7 @@
* Provides type definitions and function prototypes used to link the
* DHD OS, bus, and protocol modules.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -127,6 +127,8 @@
/* Add prot dump output to a buffer */
extern void dhd_prot_dump(dhd_pub_t *dhdp, struct bcmstrbuf *strbuf);
+extern void dhd_prot_counters(dhd_pub_t *dhdp, struct bcmstrbuf *strbuf,
+ bool print_ringinfo, bool print_pktidinfo);
/* Dump extended trap data */
extern int dhd_prot_dump_extended_trap(dhd_pub_t *dhdp, struct bcmstrbuf *b, bool raw);
@@ -142,13 +144,22 @@
uint reorder_info_len, void **pkt, uint32 *free_buf_count);
#ifdef BCMPCIE
-extern bool dhd_prot_process_msgbuf_txcpl(dhd_pub_t *dhd, uint bound, int ringtype);
-extern bool dhd_prot_process_msgbuf_rxcpl(dhd_pub_t *dhd, uint bound, int ringtype);
-extern bool dhd_prot_process_msgbuf_infocpl(dhd_pub_t *dhd, uint bound);
+extern bool dhd_prot_process_msgbuf_txcpl(dhd_pub_t *dhd, int ringtype, uint32 *txcpl_items);
+extern bool dhd_prot_process_msgbuf_rxcpl(dhd_pub_t *dhd, int ringtype, uint32 *rxcpl_items);
+extern bool dhd_prot_process_msgbuf_infocpl(dhd_pub_t *dhd, uint bound,
+ uint32 *evtlog_items);
+uint32 dhd_prot_get_tx_post_bound(dhd_pub_t *dhd);
+uint32 dhd_prot_get_ctrl_cpl_post_bound(dhd_pub_t *dhd);
+uint32 dhd_prot_get_tx_cpl_bound(dhd_pub_t *dhd);
+uint32 dhd_prot_get_rx_cpl_post_bound(dhd_pub_t *dhd);
+void dhd_prot_set_tx_cpl_bound(dhd_pub_t *dhd, uint32 val);
+void dhd_prot_set_rx_cpl_post_bound(dhd_pub_t *dhd, uint32 val);
+void dhd_prot_set_tx_post_bound(dhd_pub_t *dhd, uint32 val);
+void dhd_prot_set_ctrl_cpl_post_bound(dhd_pub_t *dhd, uint32 val);
#ifdef BTLOG
extern bool dhd_prot_process_msgbuf_btlogcpl(dhd_pub_t *dhd, uint bound);
#endif /* BTLOG */
-extern int dhd_prot_process_ctrlbuf(dhd_pub_t * dhd);
+extern bool dhd_prot_process_ctrlbuf(dhd_pub_t * dhd, uint32 *ctrlcpl_items);
extern int dhd_prot_process_trapbuf(dhd_pub_t * dhd);
extern bool dhd_prot_dtohsplit(dhd_pub_t * dhd);
extern int dhd_post_dummy_msg(dhd_pub_t *dhd);
@@ -177,7 +188,7 @@
extern void dhd_prot_print_flow_ring(dhd_pub_t *dhd, void *msgbuf_flow_info, bool h2d,
struct bcmstrbuf *strbuf, const char * fmt);
extern void dhd_prot_print_info(dhd_pub_t *dhd, struct bcmstrbuf *strbuf);
-extern void dhd_prot_update_txflowring(dhd_pub_t *dhdp, uint16 flow_id, void *msgring_info);
+extern bool dhd_prot_update_txflowring(dhd_pub_t *dhdp, uint16 flow_id, void *msgring_info);
extern void dhd_prot_txdata_write_flush(dhd_pub_t *dhd, uint16 flow_id);
extern uint32 dhd_prot_txp_threshold(dhd_pub_t *dhd, bool set, uint32 val);
extern void dhd_prot_reset(dhd_pub_t *dhd);
@@ -191,7 +202,17 @@
#ifdef BTLOG
extern int dhd_prot_init_btlog_rings(dhd_pub_t *dhd);
#endif /* BTLOG */
+extern int dhd_prot_init_md_rings(dhd_pub_t *dhd);
extern int dhd_prot_check_tx_resource(dhd_pub_t *dhd);
+#else /* BCMPCIE */
+static INLINE uint32 dhd_prot_get_tx_post_bound(dhd_pub_t *dhd) { return 0; }
+static INLINE uint32 dhd_prot_get_ctrl_cpl_post_bound(dhd_pub_t *dhd) { return 0; }
+static INLINE uint32 dhd_prot_get_tx_cpl_bound(dhd_pub_t *dhd) { return 0; }
+static INLINE uint32 dhd_prot_get_rx_cpl_post_bound(dhd_pub_t *dhd) { return 0; }
+static INLINE void dhd_prot_set_tx_cpl_bound(dhd_pub_t *dhd, uint32 val) { }
+static INLINE void dhd_prot_set_rx_cpl_post_bound(dhd_pub_t *dhd, uint32 val) { }
+static INLINE void dhd_prot_set_tx_post_bound(dhd_pub_t *dhd, uint32 val) { }
+static INLINE void dhd_prot_set_ctrl_cpl_post_bound(dhd_pub_t *dhd, uint32 val) { }
#endif /* BCMPCIE */
#ifdef DHD_LB
@@ -227,7 +248,7 @@
#ifdef EWP_EDL
int dhd_prot_init_edl_rings(dhd_pub_t *dhd);
-bool dhd_prot_process_msgbuf_edl(dhd_pub_t *dhd, uint32 *edl_itmes);
+bool dhd_prot_process_msgbuf_edl(dhd_pub_t *dhd, uint32 *evtlog_items);
int dhd_prot_process_edl_complete(dhd_pub_t *dhd, void *evt_decode_data);
#endif /* EWP_EDL */
@@ -250,6 +271,9 @@
int dhd_get_hscb_info(dhd_pub_t *dhd, void ** va, uint32 *len);
int dhd_get_hscb_buff(dhd_pub_t *dhd, uint32 offset, uint32 length, void * buff);
+extern int dhd_prot_mdring_link_unlink(dhd_pub_t *dhd, int idx, bool link);
+extern int dhd_prot_mdring_linked_ring(dhd_pub_t *dhd);
+
#ifdef DHD_MAP_LOGGING
extern void dhd_prot_smmu_fault_dump(dhd_pub_t *dhdp);
#endif /* DHD_MAP_LOGGING */
diff --git a/dhd_rtt.c b/dhd_rtt.c
index af14a0f..0558240 100644
--- a/dhd_rtt.c
+++ b/dhd_rtt.c
@@ -1,7 +1,7 @@
/*
* Broadcom Dongle Host Driver (DHD), RTT
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -494,6 +494,7 @@
}
return ret;
}
+
uint64
ftm_intvl2usec(const wl_proxd_intvl_t *intvl)
{
@@ -533,6 +534,7 @@
}
return RTT_STATUS_FAILURE; /* not found */
}
+
/*
* lookup 'id' (as a key) from a table
* if found, return the entry pointer, otherwise return NULL
@@ -727,7 +729,7 @@
}
/* setup proxd-FTM-method iovar header */
- p_proxd_iov->version = htol16(WL_PROXD_API_VERSION);
+ p_proxd_iov->version = htol16(WL_PROXD_API_VERSION_3);
p_proxd_iov->len = htol16(proxd_iovsize); /* caller may adjust it based on #of TLVs */
p_proxd_iov->cmd = htol16(cmdid);
p_proxd_iov->method = htol16(method);
@@ -1320,6 +1322,7 @@
return dhd_rtt_common_set_handler(dhd, &subcmd_info,
WL_PROXD_METHOD_FTM, session_id);
}
+
#ifdef WL_NAN
int
dhd_rtt_delete_nan_session(dhd_pub_t *dhd)
@@ -1331,6 +1334,7 @@
wl_cfgnan_terminate_directed_rtt_sessions(dev, cfg);
return BCME_OK;
}
+
/* API to find out if the given Peer Mac from FTM events
* is nan-peer. Based on this we will handle the SESSION_END
* event. For nan-peer FTM_SESSION_END event is ignored and handled in
@@ -1475,7 +1479,7 @@
msg.datalen = hton32(sizeof(p_event));
msg.addr = rtt_target->addr;
- p_event.version = htol16(WL_PROXD_API_VERSION);
+ p_event.version = htol16(WL_PROXD_API_VERSION_3);
p_event.type = htol16(WL_PROXD_EVENT_SESSION_END);
p_event.len = htol16(OFFSETOF(wl_proxd_event_t, tlvs));
@@ -2496,6 +2500,7 @@
RTT_SCHED_RTT_RETRY_GEOFENCE);
}
+
static void
dhd_rtt_retry_work(struct work_struct *work)
{
@@ -3153,7 +3158,6 @@
return err;
}
-
/* Work thread API to start the RTT.
* If all targets are AP only, then this API will confgure all sessions
* and start(FW) the RTT for first session.
@@ -4134,6 +4138,7 @@
}
return err;
}
+
#ifdef WL_CFG80211
/* Common API for handling Session End.
* This API will flush out the results for a peer MAC.
@@ -4664,9 +4669,9 @@
}
p_event = (wl_proxd_event_t *) event_data;
version = ltoh16(p_event->version);
- if (version < WL_PROXD_API_VERSION) {
+ if (version < WL_PROXD_API_VERSION_3) {
DHD_RTT_ERR(("ignore non-ftm event version = 0x%0x < WL_PROXD_API_VERSION (0x%x)\n",
- version, WL_PROXD_API_VERSION));
+ version, WL_PROXD_API_VERSION_3));
return ret;
}
@@ -5305,7 +5310,7 @@
DHD_RTT_MEM(("dhd_rtt_init ENTRY\n"));
ret = dhd_rtt_get_version(dhd, &version);
- if (ret == BCME_OK && (version == WL_PROXD_API_VERSION)) {
+ if (ret == BCME_OK && (version == WL_PROXD_API_VERSION_3)) {
DHD_RTT_ERR(("%s : FTM is supported\n", __FUNCTION__));
#ifdef WL_RTT_ONE_WAY
rtt_status->rtt_capa.proto |= RTT_CAP_ONE_WAY;
@@ -5332,7 +5337,7 @@
DHD_RTT_ERR(("%s : FTM is not supported\n", __FUNCTION__));
} else {
DHD_RTT_ERR(("%s : FTM version mismatch between HOST (%d) and FW (%d)\n",
- __FUNCTION__, WL_PROXD_API_VERSION, version));
+ __FUNCTION__, WL_PROXD_API_VERSION_3, version));
}
goto exit;
}
diff --git a/dhd_rtt.h b/dhd_rtt.h
index 760cd91..6fb3500 100644
--- a/dhd_rtt.h
+++ b/dhd_rtt.h
@@ -1,7 +1,7 @@
/*
* Broadcom Dongle Host Driver (DHD), RTT
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/dhd_sdio.c b/dhd_sdio.c
index 04a6dd6..24a7432 100644
--- a/dhd_sdio.c
+++ b/dhd_sdio.c
@@ -1,7 +1,7 @@
/*
* DHD Bus Module for SDIO
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -927,6 +927,7 @@
(BCM4349_CHIP(bus->sih->chip)) ||
(bus->sih->chip == BCM4350_CHIP_ID) ||
(bus->sih->chip == BCM4362_CHIP_ID) ||
+ (bus->sih->chip == BCM4381_CHIP_ID) ||
(bus->sih->chip == BCM43012_CHIP_ID) ||
(bus->sih->chip == BCM43013_CHIP_ID) ||
(bus->sih->chip == BCM43014_CHIP_ID) ||
@@ -1016,6 +1017,7 @@
CHIPID(bus->sih->chip) == BCM43018_CHIP_ID ||
CHIPID(bus->sih->chip) == BCM4339_CHIP_ID ||
CHIPID(bus->sih->chip) == BCM4362_CHIP_ID ||
+ CHIPID(bus->sih->chip) == BCM4381_CHIP_ID ||
CHIPID(bus->sih->chip) == BCM43012_CHIP_ID ||
CHIPID(bus->sih->chip) == BCM43013_CHIP_ID ||
CHIPID(bus->sih->chip) == BCM43014_CHIP_ID ||
@@ -1068,6 +1070,20 @@
return 0;
}
+static void
+dhdsdio_set_wakeupctrl(dhd_bus_t *bus)
+{
+ uint8 val;
+ int err = 0;
+
+ /* programme the wakeup wait */
+ val = bcmsdh_cfg_read(bus->sdh, SDIO_FUNC_1, SBSDIO_FUNC1_WAKEUPCTRL, NULL);
+ val |= 1 << SBSDIO_FUNC1_WCTRL_HTWAIT_SHIFT;
+ bcmsdh_cfg_write(bus->sdh, SDIO_FUNC_1, SBSDIO_FUNC1_WAKEUPCTRL,
+ 1 << SBSDIO_FUNC1_WCTRL_HTWAIT_SHIFT, &err);
+ val = bcmsdh_cfg_read(bus->sdh, SDIO_FUNC_1, SBSDIO_FUNC1_WAKEUPCTRL, NULL);
+}
+
#define KSO_DBG(x)
/* XXX KSO set typically takes depending on resource up & number of
* resources which were down. Max value is PMU_MAX_TRANSITION_DLY usec.
@@ -1106,6 +1122,7 @@
* after clearing KSO bit, to avoid polling of KSO bit.
*/
if ((!on) && (bus->sih->chip == BCM43012_CHIP_ID ||
+ (bus->sih->chip == BCM4381_CHIP_ID) ||
bus->sih->chip == BCM43013_CHIP_ID ||
bus->sih->chip == BCM43014_CHIP_ID)) {
return err;
@@ -7937,6 +7954,10 @@
if (chipid == BCM4364_CHIP_ID)
return TRUE;
+ if (chipid == BCM4381_CHIP_ID) {
+ return TRUE;
+ }
+
if (chipid == BCM43012_CHIP_ID)
return TRUE;
@@ -8299,10 +8320,14 @@
goto fail;
}
- if (bus->sih->buscorerev >= 12)
+ if (bus->sih->buscorerev >= 12) {
dhdsdio_clk_kso_init(bus);
- else
+ } else {
bus->kso = TRUE;
+ }
+
+ /* to wake up completely incase sleep is triggered before bus start */
+ dhdsdio_set_wakeupctrl(bus);
si_sdiod_drive_strength_init(bus->sih, osh, dhd_sdiod_drive_strength);
@@ -8355,6 +8380,9 @@
case BCM4364_CHIP_ID:
bus->dongle_ram_base = CR4_4364_RAM_BASE;
break;
+ case BCM4381_CHIP_ID:
+ bus->dongle_ram_base = CR4_4381_RAM_BASE;
+ break;
case BCM4362_CHIP_ID:
bus->dongle_ram_base = CR4_4362_RAM_BASE;
break;
@@ -10444,7 +10472,12 @@
int
dhd_bus_get_bus_wake(dhd_pub_t *dhd)
{
- return bcmsdh_set_get_wake(dhd->bus->sdh, 0);
+ return bcmsdh_get_wake(dhd->bus->sdh);
+}
+int
+dhd_bus_set_get_bus_wake(dhd_pub_t *dhd, int set)
+{
+ return bcmsdh_set_get_wake(dhd->bus, set);
}
#endif /* DHD_WAKE_STATUS */
diff --git a/dhd_statlog.c b/dhd_statlog.c
index d773a53..396cbcd 100644
--- a/dhd_statlog.c
+++ b/dhd_statlog.c
@@ -1,7 +1,7 @@
/*
* DHD debugability: Status Information Logging support
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -693,7 +693,7 @@
ts_sec = elem->ts_tz;
rem_usec = DIV_AND_MOD_U64_BY_U32(ts_sec, USEC_PER_SEC);
- rtc_time_to_tm((unsigned long)ts_sec, &tm);
+ rtc_time_to_tm(ts_sec, &tm);
snprintf(buf, buflen, DHD_STATLOG_TZFMT_YYMMDDHHMMSSMS,
tm.tm_year - 100, tm.tm_mon + 1, tm.tm_mday,
tm.tm_hour, tm.tm_min, tm.tm_sec,
diff --git a/dhd_statlog.h b/dhd_statlog.h
index dd3152d..04e7340 100644
--- a/dhd_statlog.h
+++ b/dhd_statlog.h
@@ -1,7 +1,7 @@
/*
* DHD debugability: Header file for the Status Information Logging
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/dhd_wlfc.c b/dhd_wlfc.c
index c57f5d1..14270a9 100644
--- a/dhd_wlfc.c
+++ b/dhd_wlfc.c
@@ -1,7 +1,7 @@
/*
* DHD PROP_TXSTATUS Module.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/dhd_wlfc.h b/dhd_wlfc.h
index c1ee487..daf021b 100644
--- a/dhd_wlfc.h
+++ b/dhd_wlfc.h
@@ -1,5 +1,5 @@
/*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/document/README_Licenses.txt b/document/README_Licenses.txt
deleted file mode 100755
index 4c96941..0000000
--- a/document/README_Licenses.txt
+++ /dev/null
@@ -1,368 +0,0 @@
-[
- {
- "files": [
- "components/apf/include/apf_interpreter.h"
- ],
- "copyright": [
- [
- "Copyright 2015, The Android Open Source Project"
- ],
- [
- "Licensed under the Apache License, Version 2.0 (the \"License\");",
- "you may not use this file except in compliance with the License.",
- "You may obtain a copy of the License at",
- "src/wl/apf/include/apf_interpreter.h (revision 0)"
- ],
- [
- "http://www.apache.org/licenses/LICENSE-2.0"
- ],
- [
- "Unless required by applicable law or agreed to in writing, software",
- "distributed under the License is distributed on an \"AS IS\" BASIS,",
- "WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.",
- "See the License for the specific language governing permissions and",
- "limitations under the License."
- ]
- ]
- },
- {
- "files": [
- "components/apf/src/apf_interpreter.c"
- ],
- "copyright": [
- [
- "Copyright 2016, The Android Open Source Project"
- ],
- [
- "Licensed under the Apache License, Version 2.0 (the \"License\");",
- "you may not use this file except in compliance with the License.",
- "You may obtain a copy of the License at"
- ],
- [
- "http://www.apache.org/licenses/LICENSE-2.0"
- ],
- [
- "Unless required by applicable law or agreed to in writing, software",
- "distributed under the License is distributed on an \"AS IS\" BASIS,",
- "WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.",
- "See the License for the specific language governing permissions and",
- "limitations under the License."
- ]
- ]
- },
- {
- "files": [
- "components/bcmcrypto/include/md5.h",
- "components/bcmcrypto/src/md5.c"
- ],
- "copyright": [
- [
- "Copyright (C) 1990, RSA Data Security, Inc. All rights reserved."
- ],
- [
- "License to copy and use this software is granted provided that",
- "it is identified as the \"RSA Data Security, Inc. MD5 Message-",
- "Digest Algorithm\" in all material mentioning or referencing this",
- "software or this function."
- ],
- [
- "License is also granted to make and use derivative works",
- "provided that such works are identified as \"derived from the RSA",
- "Data Security, Inc. MD5 Message-Digest Algorithm\" in all",
- "material mentioning or referencing the derived work."
- ],
- [
- "RSA Data Security, Inc. makes no representations concerning",
- "either the merchantability of this software or the suitability",
- "of this software for any particular purpose. It is provided \"as",
- "is\" without express or implied warranty of any kind."
- ],
- [
- "These notices must be retained in any copies of any part of this",
- "documentation and/or software."
- ]
- ]
- },
- {
- "files": [
- "components/proto/include/ieee80211_radiotap.h"
- ],
- "copyright": [
- [
- "Copyright (c) 2003, 2004 David Young. All rights reserved."
- ],
- [
- "Redistribution and use in source and binary forms, with or without",
- "modification, are permitted provided that the following conditions",
- "are met:",
- "1. Redistributions of source code must retain the above copyright",
- "notice, this list of conditions and the following disclaimer.",
- "2. Redistributions in binary form must reproduce the above copyright",
- "notice, this list of conditions and the following disclaimer in the",
- "documentation and/or other materials provided with the distribution.",
- "3. The name of David Young may not be used to endorse or promote",
- "products derived from this software without specific prior",
- "written permission."
- ],
- [
- "THIS SOFTWARE IS PROVIDED BY DAVID YOUNG ``AS IS'' AND ANY",
- "EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,",
- "THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A",
- "PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL DAVID",
- "YOUNG BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,",
- "EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED",
- "TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,",
- "DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND",
- "ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,",
- "OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY",
- "OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY",
- "OF SUCH DAMAGE."
- ]
- ]
- },
- {
- "supplements": {
- "apache_license_2": [
- [
- "Apache License"
- ],
- [
- "Version 2.0, January 2004"
- ],
- [
- "http://www.apache.org/licenses/"
- ],
- [
- "TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION"
- ],
- [
- "1. Definitions."
- ],
- [
- "\"License\" shall mean the terms and conditions for use, reproduction,",
- "and distribution as defined by Sections 1 through 9 of this document."
- ],
- [
- "\"Licensor\" shall mean the copyright owner or entity authorized by",
- "the copyright owner that is granting the License."
- ],
- [
- "\"Legal Entity\" shall mean the union of the acting entity and all",
- "other entities that control, are controlled by, or are under common",
- "control with that entity. For the purposes of this definition,",
- "\"control\" means (i) the power, direct or indirect, to cause the",
- "direction or management of such entity, whether by contract or",
- "otherwise, or (ii) ownership of fifty percent (50%) or more of the",
- "outstanding shares, or (iii) beneficial ownership of such entity."
- ],
- [
- "\"You\" (or \"Your\") shall mean an individual or Legal Entity",
- "exercising permissions granted by this License."
- ],
- [
- "\"Source\" form shall mean the preferred form for making modifications,",
- "including but not limited to software source code, documentation",
- "source, and configuration files."
- ],
- [
- "\"Object\" form shall mean any form resulting from mechanical",
- "transformation or translation of a Source form, including but",
- "not limited to compiled object code, generated documentation,",
- "and conversions to other media types."
- ],
- [
- "\"Work\" shall mean the work of authorship, whether in Source or",
- "Object form, made available under the License, as indicated by a",
- "copyright notice that is included in or attached to the work",
- "(an example is provided in the Appendix below)."
- ],
- [
- "\"Derivative Works\" shall mean any work, whether in Source or Object",
- "form, that is based on (or derived from) the Work and for which the",
- "editorial revisions, annotations, elaborations, or other modifications",
- "represent, as a whole, an original work of authorship. For the purposes",
- "of this License, Derivative Works shall not include works that remain",
- "separable from, or merely link (or bind by name) to the interfaces of,",
- "the Work and Derivative Works thereof."
- ],
- [
- "\"Contribution\" shall mean any work of authorship, including",
- "the original version of the Work and any modifications or additions",
- "to that Work or Derivative Works thereof, that is intentionally",
- "submitted to Licensor for inclusion in the Work by the copyright owner",
- "or by an individual or Legal Entity authorized to submit on behalf of",
- "the copyright owner. For the purposes of this definition, \"submitted\"",
- "means any form of electronic, verbal, or written communication sent",
- "to the Licensor or its representatives, including but not limited to",
- "communication on electronic mailing lists, source code control systems,",
- "and issue tracking systems that are managed by, or on behalf of, the",
- "Licensor for the purpose of discussing and improving the Work, but",
- "excluding communication that is conspicuously marked or otherwise",
- "designated in writing by the copyright owner as \"Not a Contribution.\""
- ],
- [
- "\"Contributor\" shall mean Licensor and any individual or Legal Entity",
- "on behalf of whom a Contribution has been received by Licensor and",
- "subsequently incorporated within the Work."
- ],
- [
- "2. Grant of Copyright License. Subject to the terms and conditions of",
- "this License, each Contributor hereby grants to You a perpetual,",
- "worldwide, non-exclusive, no-charge, royalty-free, irrevocable",
- "copyright license to reproduce, prepare Derivative Works of,",
- "publicly display, publicly perform, sublicense, and distribute the",
- "Work and such Derivative Works in Source or Object form."
- ],
- [
- "3. Grant of Patent License. Subject to the terms and conditions of",
- "this License, each Contributor hereby grants to You a perpetual,",
- "worldwide, non-exclusive, no-charge, royalty-free, irrevocable",
- "(except as stated in this section) patent license to make, have made,",
- "use, offer to sell, sell, import, and otherwise transfer the Work,",
- "where such license applies only to those patent claims licensable",
- "by such Contributor that are necessarily infringed by their",
- "Contribution(s) alone or by combination of their Contribution(s)",
- "with the Work to which such Contribution(s) was submitted. If You",
- "institute patent litigation against any entity (including a",
- "cross-claim or counterclaim in a lawsuit) alleging that the Work",
- "or a Contribution incorporated within the Work constitutes direct",
- "or contributory patent infringement, then any patent licenses",
- "granted to You under this License for that Work shall terminate",
- "as of the date such litigation is filed."
- ],
- [
- "4. Redistribution. You may reproduce and distribute copies of the",
- "Work or Derivative Works thereof in any medium, with or without",
- "modifications, and in Source or Object form, provided that You",
- "meet the following conditions:"
- ],
- [
- "(a) You must give any other recipients of the Work or",
- "Derivative Works a copy of this License; and"
- ],
- [
- "(b) You must cause any modified files to carry prominent notices",
- "stating that You changed the files; and"
- ],
- [
- "(c) You must retain, in the Source form of any Derivative Works",
- "that You distribute, all copyright, patent, trademark, and",
- "attribution notices from the Source form of the Work,",
- "excluding those notices that do not pertain to any part of",
- "the Derivative Works; and"
- ],
- [
- "(d) If the Work includes a \"NOTICE\" text file as part of its",
- "distribution, then any Derivative Works that You distribute must",
- "include a readable copy of the attribution notices contained",
- "within such NOTICE file, excluding those notices that do not",
- "pertain to any part of the Derivative Works, in at least one",
- "of the following places: within a NOTICE text file distributed",
- "as part of the Derivative Works; within the Source form or",
- "documentation, if provided along with the Derivative Works; or,",
- "within a display generated by the Derivative Works, if and",
- "wherever such third-party notices normally appear. The contents",
- "of the NOTICE file are for informational purposes only and",
- "do not modify the License. You may add Your own attribution",
- "notices within Derivative Works that You distribute, alongside",
- "or as an addendum to the NOTICE text from the Work, provided",
- "that such additional attribution notices cannot be construed",
- "as modifying the License."
- ],
- [
- "You may add Your own copyright statement to Your modifications and",
- "may provide additional or different license terms and conditions",
- "for use, reproduction, or distribution of Your modifications, or",
- "for any such Derivative Works as a whole, provided Your use,",
- "reproduction, and distribution of the Work otherwise complies with",
- "the conditions stated in this License."
- ],
- [
- "5. Submission of Contributions. Unless You explicitly state otherwise,",
- "any Contribution intentionally submitted for inclusion in the Work",
- "by You to the Licensor shall be under the terms and conditions of",
- "this License, without any additional terms or conditions.",
- "Notwithstanding the above, nothing herein shall supersede or modify",
- "the terms of any separate license agreement you may have executed",
- "with Licensor regarding such Contributions."
- ],
- [
- "6. Trademarks. This License does not grant permission to use the trade",
- "names, trademarks, service marks, or product names of the Licensor,",
- "except as required for reasonable and customary use in describing the",
- "origin of the Work and reproducing the content of the NOTICE file."
- ],
- [
- "7. Disclaimer of Warranty. Unless required by applicable law or",
- "agreed to in writing, Licensor provides the Work (and each",
- "Contributor provides its Contributions) on an \"AS IS\" BASIS,",
- "WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or",
- "implied, including, without limitation, any warranties or conditions",
- "of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A",
- "PARTICULAR PURPOSE. You are solely responsible for determining the",
- "appropriateness of using or redistributing the Work and assume any",
- "risks associated with Your exercise of permissions under this License."
- ],
- [
- "8. Limitation of Liability. In no event and under no legal theory,",
- "whether in tort (including negligence), contract, or otherwise,",
- "unless required by applicable law (such as deliberate and grossly",
- "negligent acts) or agreed to in writing, shall any Contributor be",
- "liable to You for damages, including any direct, indirect, special,",
- "incidental, or consequential damages of any character arising as a",
- "result of this License or out of the use or inability to use the",
- "Work (including but not limited to damages for loss of goodwill,",
- "work stoppage, computer failure or malfunction, or any and all",
- "other commercial damages or losses), even if such Contributor",
- "has been advised of the possibility of such damages."
- ],
- [
- "9. Accepting Warranty or Additional Liability. While redistributing",
- "the Work or Derivative Works thereof, You may choose to offer,",
- "and charge a fee for, acceptance of support, warranty, indemnity,",
- "or other liability obligations and/or rights consistent with this",
- "License. However, in accepting such obligations, You may act only",
- "on Your own behalf and on Your sole responsibility, not on behalf",
- "of any other Contributor, and only if You agree to indemnify,",
- "defend, and hold each Contributor harmless for any liability",
- "incurred by, or claims asserted against, such Contributor by reason",
- "of your accepting any such warranty or additional liability."
- ],
- [
- "END OF TERMS AND CONDITIONS"
- ],
- [
- "APPENDIX: How to apply the Apache License to your work."
- ],
- [
- "To apply the Apache License to your work, attach the following",
- "boilerplate notice, with the fields enclosed by brackets \"[]\"",
- "replaced with your own identifying information. (Don't include",
- "the brackets!) The text should be enclosed in the appropriate",
- "comment syntax for the file format. We also recommend that a",
- "file or class name and description of purpose be included on the",
- "same \"printed page\" as the copyright notice for easier",
- "identification within third-party archives."
- ],
- [
- "Copyright [yyyy] [name of copyright owner]"
- ],
- [
- "Licensed under the Apache License, Version 2.0 (the \"License\");",
- "you may not use this file except in compliance with the License.",
- "You may obtain a copy of the License at"
- ],
- [
- "http://www.apache.org/licenses/LICENSE-2.0"
- ],
- [
- "Unless required by applicable law or agreed to in writing, software",
- "distributed under the License is distributed on an \"AS IS\" BASIS,",
- "WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.",
- "See the License for the specific language governing permissions and",
- "limitations under the License."
- ]
- ]
- }
- }
-]
diff --git a/frag.c b/frag.c
index 7d42d04..e11b78a 100644
--- a/frag.c
+++ b/frag.c
@@ -2,7 +2,7 @@
* IE/TLV fragmentation/defragmentation support for
* Broadcom 802.11bang Networking Device Driver
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/fwpkg_utils.c b/fwpkg_utils.c
index 9ce9122..7e3ad76 100644
--- a/fwpkg_utils.c
+++ b/fwpkg_utils.c
@@ -1,7 +1,7 @@
/*
* Firmware package functionality
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/hnd_pktpool.c b/hnd_pktpool.c
index 70d0360..6881357 100644
--- a/hnd_pktpool.c
+++ b/hnd_pktpool.c
@@ -1,7 +1,7 @@
/*
* HND generic packet pool operation primitives
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -116,6 +116,7 @@
#endif /* BCMPKTIDMAP || BCMPKTIDMAP_MIN */
#ifdef POOL_HEAP_RECONFIG
+static uint32 pktpool_add_fail_cnt = 0; /* Counter if pktpool_add fails */
typedef struct pktpool_heap_cb_reg {
pktpool_heap_cb_t fn;
void *ctxt;
@@ -139,6 +140,31 @@
/** add declaration */
static void pktpool_avail_notify(pktpool_t *pktp);
+#ifdef DONGLEBUILD
+#define PKTPOOL_RXLFRAG(pktp) ((pktp)->type == lbuf_rxfrag)
+#else
+#define PKTPOOL_RXLFRAG(pktp) FALSE
+#endif
+
+#define RXLRAG_POOL_FREELIST_TAIL(pktp) ((pktp)->freelist_tail)
+#ifdef RXLFRAGPOOL_SORT_RXFRAG_DBG
+static const char BCMPOST_TRAP_RODATA(pktpool_deq_print_1)[] =
+ "\n%d removing buffer from the rxlfrag pool\n";
+static const char BCMPOST_TRAP_RODATA(pktpool_enq_print_1)[] =
+ "\n%d adding non rxfrag buffer to the rxlfrag pool, %p, %p\n";
+static const char BCMPOST_TRAP_RODATA(pktpool_enq_print_2)[] =
+ "\n%d adding rxfrag buffer to the rxlfrag pool, %p, %p\n";
+uint32 g_rxlfrag_rxfrag_queued = 0;
+uint32 g_rxlfrag_non_rxfrag_queued = 0;
+#define RXLFRAG_SORT_DBG_PRINT(args) do { printf args;} while (0)
+#define INCR_RXLFRAG_QUEUE_RXFRAG() do { g_rxlfrag_rxfrag_queued++; } while (0)
+#define INCR_RXLFRAG_QUEUE_NONRXFRAG() do { g_rxlfrag_non_rxfrag_queued++; } while (0)
+#else
+#define RXLFRAG_SORT_DBG_PRINT(args) do { } while (0)
+#define INCR_RXLFRAG_QUEUE_RXFRAG() do { } while (0)
+#define INCR_RXLFRAG_QUEUE_NONRXFRAG() do { } while (0)
+#endif /* RXLFRAGPOOL_SORT_RXFRAG_DBG */
+
/** accessor functions required when ROMming this file, forced into RAM */
pktpool_t *
@@ -351,6 +377,12 @@
PKTSETFREELIST(p, pktp->freelist); /* insert p at head of free list */
pktp->freelist = p;
+ if (PKTPOOL_RXLFRAG(pktp) && (pktp->pktpool_flags & PKTPOOL_RXLFRAG_SORTED_INSERT))
+ {
+ if (RXLRAG_POOL_FREELIST_TAIL(pktp) == NULL) {
+ RXLRAG_POOL_FREELIST_TAIL(pktp) = pktp->freelist;
+ }
+ }
pktp->avail++;
@@ -675,6 +707,14 @@
p = pktp->freelist; /* dequeue packet from head of pktpool free list */
pktp->freelist = PKTFREELIST(p); /* free list points to next packet */
+ /* rxlfrag list is ordered list rxfrag packets at head followed by non rxfrag packets */
+ /* rxfrag is packet which already has associated host buffer */
+ if (PKTPOOL_RXLFRAG(pktp) && (pktp->pktpool_flags & PKTPOOL_RXLFRAG_SORTED_INSERT)) {
+ RXLFRAG_SORT_DBG_PRINT((pktpool_deq_print_1, pktp->avail));
+ if (pktp->freelist == NULL) {
+ RXLRAG_POOL_FREELIST_TAIL(pktp) = NULL;
+ }
+ }
#if defined(DONGLEBUILD) && defined(SRMEM)
if (SRMEM_ENAB()) {
@@ -696,8 +736,39 @@
ASSERT_FP(p != NULL);
PKTSETQCALLER(p, pktp, CALL_SITE);
- PKTSETFREELIST(p, pktp->freelist); /* insert at head of pktpool free list */
- pktp->freelist = p; /* free list points to newly inserted packet */
+
+ if (PKTPOOL_RXLFRAG(pktp) && (pktp->pktpool_flags & PKTPOOL_RXLFRAG_SORTED_INSERT)) {
+ /* rxfrag pkt becomes head of freelist, non rxfrag becomes tail of the freelist */
+ /* rxfrag is packet which already has associated host buffer */
+ if (PKTISRXFRAG(OSH_NULL, p)) {
+ INCR_RXLFRAG_QUEUE_RXFRAG();
+ RXLFRAG_SORT_DBG_PRINT((pktpool_enq_print_2, pktp->avail,
+ pktp->freelist, RXLRAG_POOL_FREELIST_TAIL(pktp)));
+ PKTSETFREELIST(p, pktp->freelist); /* insert at head of pktpool free list */
+ if (RXLRAG_POOL_FREELIST_TAIL(pktp) == NULL) {
+ RXLRAG_POOL_FREELIST_TAIL(pktp) = p;
+ }
+ pktp->freelist = p; /* free list points to newly inserted packet */
+ } else {
+ INCR_RXLFRAG_QUEUE_NONRXFRAG();
+ RXLFRAG_SORT_DBG_PRINT((pktpool_enq_print_1, pktp->avail,
+ pktp->freelist, RXLRAG_POOL_FREELIST_TAIL(pktp)));
+ if (pktp->freelist == NULL) {
+ pktp->freelist = p;
+ RXLRAG_POOL_FREELIST_TAIL(pktp) = p;
+ }
+ else {
+ /* this pkt becomes tail */
+ PKTSETFREELIST(RXLRAG_POOL_FREELIST_TAIL(pktp), p);
+ RXLRAG_POOL_FREELIST_TAIL(pktp) = p;
+ PKTSETFREELIST(p, NULL);
+ }
+ }
+ }
+ else {
+ PKTSETFREELIST(p, pktp->freelist); /* insert at head of pktpool free list */
+ pktp->freelist = p; /* free list points to newly inserted packet */
+ }
#if defined(DONGLEBUILD) && defined(SRMEM)
if (SRMEM_ENAB()) {
@@ -1234,7 +1305,7 @@
return;
}
-#ifdef APP_RX
+#ifdef BCMPCIEDEV
/* Update freelist and avail count for a given packet pool */
void
BCMPOSTTRAPFASTPATH(pktpool_update_freelist)(pktpool_t *pktp, void *p, uint pkts_consumed)
@@ -1244,7 +1315,7 @@
pktp->freelist = p;
pktp->avail -= pkts_consumed;
}
-#endif /* APP_RX */
+#endif /* BCMPCIEDEV */
int
BCMFASTPATH(pktpool_get_last_err)(pktpool_t *pktp)
@@ -1261,6 +1332,7 @@
#if defined(DONGLEBUILD)
uint pkts_avail;
bool rxcpl = (pktp->rxcplidfn.cb != NULL) ? TRUE : FALSE;
+ BCM_REFERENCE(pkts_avail);
#endif /* DONGLEBUILD */
if (pktcnt) {
@@ -1296,7 +1368,7 @@
}
}
-#ifdef APP_RX
+#ifdef BCMPCIEDEV
if (pktcnt) {
p = pktp->freelist;
if (pktp->avail < pkts_requested) {
@@ -1312,7 +1384,7 @@
goto done;
}
} else
-#endif /* APP_RX */
+#endif /* BCMPCIEDEV */
{
ASSERT_FP(pkts_requested == 1);
p = pktpool_deq(pktp);
@@ -1321,23 +1393,6 @@
ASSERT_FP(p);
#if defined(DONGLEBUILD)
-#ifndef APP_RX
- if (BCMSPLITRX_ENAB() && (type == lbuf_rxfrag)) {
- /* If pool is shared rx pool, use call back fn to populate host address.
- * In case of APP, callback may use lesser number of packets than what
- * we have given to callback because of some resource crunch and the exact
- * number of packets that are used by the callback are returned using
- * (*pktcnt) and the pktpool freelist head is updated accordingly.
- */
- ASSERT_FP(pktp->cbext.cb != NULL);
- if ((last_alloc_err = pktp->cbext.cb(pktp, pktp->cbext.arg, p,
- rxcpl, &pkts_avail))) {
- pktpool_enq(pktp, p);
- p = NULL;
- }
- }
-#endif /* APP_RX */
-
if ((type == lbuf_basic) && rxcpl) {
/* If pool is shared rx pool, use call back fn to populate Rx cpl ID */
ASSERT_FP(pktp->rxcplidfn.cb != NULL);
@@ -1357,13 +1412,11 @@
/* protect shared resource */
if (HND_PKTPOOL_MUTEX_RELEASE(&pktp->mutex) != OSL_EXT_SUCCESS)
return NULL;
-
-#ifdef APP
+#ifdef BCMPCIEDEV
if (p && (type == lbuf_alfrag_data)) {
p = (uint8 *)p + LBUFMEMSZ;
}
-#endif /* APP */
-
+#endif /* BCMPCIEDEV */
return p;
}
@@ -1371,6 +1424,9 @@
BCMFASTPATH(pktpool_nfree)(pktpool_t *pktp, void *head, void *tail, uint count)
{
void *_head = head;
+ uint count_orig = count;
+
+ BCM_REFERENCE(count_orig);
#ifdef URB
if (URB_ENAB() && count && PKT_IS_RX_PKT(OSH_NULL, head)) {
@@ -1405,6 +1461,7 @@
}
}
+ PKTSETQCALLER_LIST(PKTLINK(head), (count_orig - 1), pktp->freelist, CALL_SITE);
PKTSETFREELIST(tail, pktp->freelist);
pktp->freelist = PKTLINK(head);
PKTSETLINK(head, NULL);
@@ -1546,10 +1603,10 @@
}
void
-BCMPOSTTRAPFN(pktpool_emptycb_disable)(pktpool_t *pktp, bool disable)
+BCMPOSTTRAPFASTPATH(pktpool_emptycb_disable)(pktpool_t *pktp, bool disable)
{
bool notify = FALSE;
- ASSERT(pktp);
+ ASSERT_FP(pktp);
/**
* To more efficiently use the cpu cycles, callbacks can be temporarily disabled.
@@ -1601,21 +1658,14 @@
#ifdef BCMFRAGPOOL
pktpool_t *pktpool_shared_lfrag = NULL;
-#endif /* BCMFRAGPOOL */
-
-#ifdef BCMALFRAGPOOL
pktpool_t *pktpool_shared_alfrag = NULL;
pktpool_t *pktpool_shared_alfrag_data = NULL;
-#endif /* BCMALFRAGPOOL */
+#endif /* BCMFRAGPOOL */
#ifdef BCMRESVFRAGPOOL
resv_info_t *resv_pool_info = NULL;
-#ifdef APP
pktpool_t *pktpool_resv_alfrag = NULL;
pktpool_t *pktpool_resv_alfrag_data = NULL;
-#else
-pktpool_t *pktpool_resv_lfrag = NULL;
-#endif /* APP */
#endif /* BCMRESVFRAGPOOL */
pktpool_t *pktpool_shared_rxlfrag = NULL;
@@ -1669,7 +1719,6 @@
goto error;
}
-#ifdef APP
pktpool_resv_alfrag = resv_pool_info->rip[RESV_FRAGPOOL_ALFRAG]->pktp;
if (pktpool_resv_alfrag == NULL) {
err = BCME_ERROR;
@@ -1682,18 +1731,10 @@
ASSERT(0);
goto error;
}
-#else
- pktpool_resv_lfrag = resv_pool_info->rip[RESV_FRAGPOOL_LFRAG]->pktp;
- if (pktpool_resv_lfrag == NULL) {
- err = BCME_ERROR;
- ASSERT(0);
- goto error;
- }
-#endif /* APP */
#endif /* RESVFRAGPOOL */
#endif /* FRAGPOOL */
-#if defined(BCMALFRAGPOOL) && !defined(BCMALFRAGPOOL_DISABLED)
+#if defined(BCMFRAGPOOL) && !defined(BCMFRAGPOOL_DISABLED)
pktpool_shared_alfrag = MALLOCZ(osh, sizeof(pktpool_t));
if (pktpool_shared_alfrag == NULL) {
ASSERT(0);
@@ -1716,7 +1757,7 @@
err = BCME_NOMEM;
goto error;
}
-#endif
+#endif /* defined(BCMRXFRAGPOOL) && !defined(BCMRXFRAGPOOL_DISABLED) */
#if defined(BCMRXDATAPOOL) && !defined(BCMRXDATAPOOL_DISABLE)
pktpool_shared_rxdata = MALLOCZ(osh, sizeof(pktpool_t));
@@ -1768,7 +1809,7 @@
#endif /* BCMFRAGPOOL */
-#if defined(BCMALFRAGPOOL) && !defined(BCMALFRAGPOOL_DISABLED)
+#if defined(BCMFRAGPOOL) && !defined(BCMFRAGPOOL_DISABLED)
n = 1;
is_heap_pool = FALSE;
@@ -1796,7 +1837,6 @@
is_heap_pool = FALSE;
#endif /* RESV_POOL_HEAP */
-#ifdef APP
/* resv alfrag pool */
n = 0; /* IMPORTANT: DO NOT allocate any packets in resv pool */
if ((err = pktpool_init(osh, pktpool_resv_alfrag, &n, PKTFRAGSZ, TRUE, lbuf_alfrag,
@@ -1814,16 +1854,6 @@
goto error;
}
pktpool_setmaxlen(pktpool_resv_alfrag_data, RESV_ALFRAG_DATA_POOL_LEN);
-#else
- /* resv lfrag pool */
- n = 0; /* IMPORTANT: DO NOT allocate any packets in resv pool */
- if ((err = pktpool_init(osh, pktpool_resv_lfrag, &n, PKTFRAGSZ, TRUE, lbuf_frag,
- is_heap_pool, POOL_HEAP_FLAG_RSRVPOOL, 0)) != BCME_OK) {
- ASSERT(0);
- goto error;
- }
- pktpool_setmaxlen(pktpool_resv_lfrag, RESV_FRAG_POOL_LEN);
-#endif /* APP */
#endif /* RESVFRAGPOOL */
#if defined(BCMRXFRAGPOOL) && !defined(BCMRXFRAGPOOL_DISABLED)
#if defined(URB) && !defined(URB_DISABLED)
@@ -1934,7 +1964,7 @@
}
#endif /* BCMFRAGPOOL */
-#if defined(BCMALFRAGPOOL) && !defined(BCMALFRAGPOOL_DISABLED)
+#if defined(BCMFRAGPOOL) && !defined(BCMFRAGPOOL_DISABLED)
if (pktpool_shared_alfrag != NULL) {
if (pktpool_shared_alfrag->inited) {
pktpool_deinit(osh, pktpool_shared_alfrag);
@@ -1954,7 +1984,6 @@
#endif /* BCMFRAGPOOL */
#if defined(BCMRESVFRAGPOOL) && !defined(BCMRESVFRAGPOOL_DISABLED)
-#ifdef APP
if (resv_pool_info) {
if (pktpool_resv_alfrag) {
pktpool_resv_alfrag = NULL;
@@ -1964,14 +1993,6 @@
}
hnd_free(resv_pool_info);
}
-#else
- if (resv_pool_info) {
- if (pktpool_resv_lfrag) {
- pktpool_resv_lfrag = NULL;
- }
- hnd_free(resv_pool_info);
- }
-#endif /* APP */
#endif /* RESVFRAGPOOL */
if (pktpool_shared != NULL) {
@@ -1999,6 +2020,7 @@
void
hnd_pktpool_refill(bool minimal)
{
+ MB_START(hnd_pktpool_refill);
if (POOL_ENAB(pktpool_shared)) {
#if defined(SRMEM)
if (SRMEM_ENAB()) {
@@ -2020,10 +2042,8 @@
if (POOL_ENAB(pktpool_shared_lfrag)) {
pktpool_fill(pktpool_osh, pktpool_shared_lfrag, minimal);
}
-#endif /* BCMFRAGPOOL */
/* alfragpool reclaim */
-#ifdef BCMALFRAGPOOL
if (POOL_ENAB(pktpool_shared_alfrag)) {
pktpool_fill(pktpool_osh, pktpool_shared_alfrag, minimal);
}
@@ -2031,7 +2051,7 @@
if (POOL_ENAB(pktpool_shared_alfrag_data)) {
pktpool_fill(pktpool_osh, pktpool_shared_alfrag_data, minimal);
}
-#endif /* BCMALFRAGPOOL */
+#endif /* BCMFRAGPOOL */
/* rx fragpool reclaim */
#ifdef BCMRXFRAGPOOL
@@ -2051,6 +2071,7 @@
hnd_resv_pool_enable(resv_pool_info);
}
#endif /* BCMRESVFRAGPOOL */
+ MB_END(hnd_pktpool_refill, "hnd_pktpool_refill");
}
#ifdef POOL_HEAP_RECONFIG
@@ -2235,6 +2256,7 @@
* free this buffer to heap
*/
PKTFREE(pktpool_osh, lb, pktsize);
+ pktpool_add_fail_cnt++;
}
ret = BCME_OK;
}
diff --git a/hnd_pktq.c b/hnd_pktq.c
index 64f73a2..f96e664 100644
--- a/hnd_pktq.c
+++ b/hnd_pktq.c
@@ -1,7 +1,7 @@
/*
* HND generic pktq operation primitives
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -1051,7 +1051,7 @@
{
uint prec;
- ASSERT(num_prec > 0 && num_prec <= PKTQ_MAX_PREC);
+ ASSERT_FP(num_prec > 0 && num_prec <= PKTQ_MAX_PREC);
/* pq is variable size; only zero out what's requested */
bzero(pq, OFFSETOF(struct pktq, q) + (sizeof(struct pktq_prec) * num_prec));
@@ -1083,12 +1083,13 @@
}
bool
-spktq_init_list(struct spktq *spq, uint max_pkts, void *head, void *tail, uint16 n_pkts)
+BCMFASTPATH(spktq_init_list)(struct spktq *spq, uint max_pkts, void *head,
+ void *tail, uint16 n_pkts)
{
if (HND_PKTQ_MUTEX_CREATE("spktq", &spq->mutex) != OSL_EXT_SUCCESS)
return FALSE;
- ASSERT(PKTLINK(tail) == NULL);
+ ASSERT_FP(PKTLINK(tail) == NULL);
PKTSETLINK(tail, NULL);
spq->q.head = head;
spq->q.tail = tail;
@@ -1474,6 +1475,7 @@
return p;
}
+
/* Priority dequeue from a specific set of precedences */
void *
BCMPOSTTRAPFASTPATH(pktq_mdeq)(struct pktq *pq, uint prec_bmp, int *prec_out)
diff --git a/hndlhl.c b/hndlhl.c
index 7826290..d8e7120 100644
--- a/hndlhl.c
+++ b/hndlhl.c
@@ -2,7 +2,7 @@
* Misc utility routines for accessing lhl specific features
* of the SiliconBackplane-based Broadcom chips.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -218,7 +218,8 @@
/* for 4377 and chiprev B0 and greater do not power-off other LPOs */
if (BCM4389_CHIP(sih->chip) || BCM4378_CHIP(sih->chip) || BCM4397_CHIP(sih->chip) ||
BCM4388_CHIP(sih->chip) || BCM4387_CHIP(sih->chip) || BCM4381_CHIP(sih->chip) ||
- BCM4382_CHIP(sih->chip) || (CHIPID(sih->chip) == BCM4377_CHIP_ID)) {
+ BCM4382_CHIP(sih->chip) || BCM43852_CHIP(sih->chip) ||
+ (CHIPID(sih->chip) == BCM4377_CHIP_ID)) {
LHL_ERROR(("NOT Power Down other LPO\n"));
} else {
/* Power down the rest of the LPOs */
diff --git a/hndmem.c b/hndmem.c
index 97b6a8b..2b18df4 100644
--- a/hndmem.c
+++ b/hndmem.c
@@ -1,7 +1,7 @@
/*
* Utility routines for configuring different memories in Broadcom chips.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/hndpmu.c b/hndpmu.c
index 871e184..754cd30 100644
--- a/hndpmu.c
+++ b/hndpmu.c
@@ -2,7 +2,7 @@
* Misc utility routines for accessing PMU corerev specific features
* of the SiliconBackplane-based Broadcom chips.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/802.11.h b/include/802.11.h
index 7cacc1e..356e9e2 100644
--- a/include/802.11.h
+++ b/include/802.11.h
@@ -1,7 +1,7 @@
/*
* Fundamental types and constants relating to 802.11
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -180,19 +180,6 @@
} BWL_POST_PACKED_STRUCT;
#define DOT11_CS_END_LEN 16 /* d11 CF-END frame length */
-/**
- * RWL wifi protocol: The Vendor Specific Action frame is defined for vendor-specific signaling
- * category+OUI+vendor specific content ( this can be variable)
- */
-BWL_PRE_PACKED_STRUCT struct dot11_action_wifi_vendor_specific {
- uint8 category;
- uint8 OUI[3];
- uint8 type;
- uint8 subtype;
- uint8 data[1040];
-} BWL_POST_PACKED_STRUCT;
-typedef struct dot11_action_wifi_vendor_specific dot11_action_wifi_vendor_specific_t;
-
/** generic vendor specific action frame with variable length */
BWL_PRE_PACKED_STRUCT struct dot11_action_vs_frmhdr {
uint8 category;
@@ -205,10 +192,6 @@
#define DOT11_ACTION_VS_HDR_LEN 6
-#define BCM_ACTION_OUI_BYTE0 0x00
-#define BCM_ACTION_OUI_BYTE1 0x90
-#define BCM_ACTION_OUI_BYTE2 0x4c
-
/* BA/BAR Control parameters */
#define DOT11_BA_CTL_POLICY_NORMAL 0x0000 /* normal ack */
#define DOT11_BA_CTL_POLICY_NOACK 0x0001 /* no ack */
@@ -231,6 +214,7 @@
struct ether_addr ra; /* receiver address */
struct ether_addr ta; /* transmitter address */
} BWL_POST_PACKED_STRUCT;
+typedef struct dot11_ctl_header dot11_ctl_header_t;
#define DOT11_CTL_HDR_LEN 16 /* control frame hdr len */
/** BAR frame payload */
@@ -402,17 +386,6 @@
} BWL_POST_PACKED_STRUCT;
typedef struct dot11_extch dot11_extch_ie_t;
-BWL_PRE_PACKED_STRUCT struct dot11_brcm_extch {
- uint8 id; /* IE ID, 221, DOT11_MNG_PROPR_ID */
- uint8 len; /* IE length */
- uint8 oui[3]; /* Proprietary OUI, BRCM_PROP_OUI */
- uint8 type; /* type indicates what follows */
- uint8 extch;
-} BWL_POST_PACKED_STRUCT;
-typedef struct dot11_brcm_extch dot11_brcm_extch_ie_t;
-
-#define BRCM_EXTCH_IE_LEN 5
-#define BRCM_EXTCH_IE_TYPE 53 /* 802.11n ID not yet assigned */
#define DOT11_EXTCH_IE_LEN 1
#define DOT11_EXT_CH_MASK 0x03 /* extension channel mask */
#define DOT11_EXT_CH_UPPER 0x01 /* ext. ch. on upper sb */
@@ -453,13 +426,6 @@
#define DOT11_CSA_MODE_ADVISORY 0 /* no DOT11_CSA_MODE_NO_TX restriction imposed */
#define DOT11_CSA_MODE_NO_TX 1 /* no transmission upon receiving CSA frame. */
-BWL_PRE_PACKED_STRUCT struct dot11_action_switch_channel {
- uint8 category;
- uint8 action;
- dot11_chan_switch_ie_t chan_switch_ie; /* for switch IE */
- dot11_brcm_extch_ie_t extch_ie; /* extension channel offset */
-} BWL_POST_PACKED_STRUCT;
-
BWL_PRE_PACKED_STRUCT struct dot11_csa_body {
uint8 mode; /* mode 0 or 1 */
uint8 reg; /* regulatory class */
@@ -915,16 +881,6 @@
} BWL_POST_PACKED_STRUCT;
typedef struct dot11_ibss_dfs dot11_ibss_dfs_t;
-/* WME Elements */
-#define WME_OUI "\x00\x50\xf2" /* WME OUI */
-#define WME_OUI_LEN 3
-#define WME_OUI_TYPE 2 /* WME type */
-#define WME_TYPE 2 /* WME type, deprecated */
-#define WME_SUBTYPE_IE 0 /* Information Element */
-#define WME_SUBTYPE_PARAM_IE 1 /* Parameter Element */
-#define WME_SUBTYPE_TSPEC 2 /* Traffic Specification */
-#define WME_VER 1 /* WME version */
-
/* WME Access Category Indices (ACIs) */
#define AC_BE 0 /* Best Effort */
#define AC_BK 1 /* Background */
@@ -941,24 +897,10 @@
#define AC_BITMAP_RESET(ab, ac) (((ab) &= ~(1 << (ac))))
/* Management PKT Lifetime indices */
-/* Removing flag checks 'WLTEST'
- * while merging MERGE BIS120RC4 to DINGO2
- */
#define MGMT_ALL 0xffff
#define MGMT_AUTH_LT FC_SUBTYPE_AUTH
#define MGMT_ASSOC_LT FC_SUBTYPE_ASSOC_REQ
-/** WME Information Element (IE) */
-BWL_PRE_PACKED_STRUCT struct wme_ie {
- uint8 oui[3];
- uint8 type;
- uint8 subtype;
- uint8 version;
- uint8 qosinfo;
-} BWL_POST_PACKED_STRUCT;
-typedef struct wme_ie wme_ie_t;
-#define WME_IE_LEN 7 /* WME IE length */
-
BWL_PRE_PACKED_STRUCT struct edcf_acparam {
uint8 ACI;
uint8 ECW;
@@ -966,39 +908,6 @@
} BWL_POST_PACKED_STRUCT;
typedef struct edcf_acparam edcf_acparam_t;
-/** WME Parameter Element (PE) */
-BWL_PRE_PACKED_STRUCT struct wme_param_ie {
- uint8 oui[3];
- uint8 type;
- uint8 subtype;
- uint8 version;
- uint8 qosinfo;
- uint8 rsvd;
- edcf_acparam_t acparam[AC_COUNT];
-} BWL_POST_PACKED_STRUCT;
-typedef struct wme_param_ie wme_param_ie_t;
-#define WME_PARAM_IE_LEN 24 /* WME Parameter IE length */
-
-/* QoS Info field for IE as sent from AP */
-#define WME_QI_AP_APSD_MASK 0x80 /* U-APSD Supported mask */
-#define WME_QI_AP_APSD_SHIFT 7 /* U-APSD Supported shift */
-#define WME_QI_AP_COUNT_MASK 0x0f /* Parameter set count mask */
-#define WME_QI_AP_COUNT_SHIFT 0 /* Parameter set count shift */
-
-/* QoS Info field for IE as sent from STA */
-#define WME_QI_STA_MAXSPLEN_MASK 0x60 /* Max Service Period Length mask */
-#define WME_QI_STA_MAXSPLEN_SHIFT 5 /* Max Service Period Length shift */
-#define WME_QI_STA_APSD_ALL_MASK 0xf /* APSD all AC bits mask */
-#define WME_QI_STA_APSD_ALL_SHIFT 0 /* APSD all AC bits shift */
-#define WME_QI_STA_APSD_BE_MASK 0x8 /* APSD AC_BE mask */
-#define WME_QI_STA_APSD_BE_SHIFT 3 /* APSD AC_BE shift */
-#define WME_QI_STA_APSD_BK_MASK 0x4 /* APSD AC_BK mask */
-#define WME_QI_STA_APSD_BK_SHIFT 2 /* APSD AC_BK shift */
-#define WME_QI_STA_APSD_VI_MASK 0x2 /* APSD AC_VI mask */
-#define WME_QI_STA_APSD_VI_SHIFT 1 /* APSD AC_VI shift */
-#define WME_QI_STA_APSD_VO_MASK 0x1 /* APSD AC_VO mask */
-#define WME_QI_STA_APSD_VO_SHIFT 0 /* APSD AC_VO shift */
-
/* ACI */
#define EDCF_AIFSN_MIN 1 /* AIFSN minimum value */
#define EDCF_AIFSN_MAX 15 /* AIFSN maximum value */
@@ -1021,9 +930,6 @@
#define EDCF_TXOP_MAX 65535 /* TXOP maximum value */
#define EDCF_TXOP2USEC(txop) ((txop) << 5)
-/* Default BE ACI value for non-WME connection STA */
-#define NON_EDCF_AC_BE_ACI_STA 0x02
-
/* Default EDCF parameters that AP advertises for STA to use; WMM draft Table 12 */
#define EDCF_AC_BE_ACI_STA 0x03 /* STA ACI value for best effort AC */
#define EDCF_AC_BE_ECW_STA 0xA4 /* STA ECW value for best effort AC */
@@ -1139,37 +1045,6 @@
#define TI_TYPE_REASSOC_DEADLINE 1
#define TI_TYPE_KEY_LIFETIME 2
-#ifndef CISCO_AIRONET_OUI
-#define CISCO_AIRONET_OUI "\x00\x40\x96" /* Cisco AIRONET OUI */
-#endif
-/* QoS FastLane IE. */
-BWL_PRE_PACKED_STRUCT struct ccx_qfl_ie {
- uint8 id; /* 221, DOT11_MNG_VS_ID */
- uint8 length; /* 5 */
- uint8 oui[3]; /* 00:40:96 */
- uint8 type; /* 11 */
- uint8 data;
-} BWL_POST_PACKED_STRUCT;
-typedef struct ccx_qfl_ie ccx_qfl_ie_t;
-#define CCX_QFL_IE_TYPE 11
-#define CCX_QFL_ENABLE_SHIFT 5
-#define CCX_QFL_ENALBE (1 << CCX_QFL_ENABLE_SHIFT)
-
-/* WME Action Codes */
-#define WME_ADDTS_REQUEST 0 /* WME ADDTS request */
-#define WME_ADDTS_RESPONSE 1 /* WME ADDTS response */
-#define WME_DELTS_REQUEST 2 /* WME DELTS request */
-
-/* WME Setup Response Status Codes */
-#define WME_ADMISSION_ACCEPTED 0 /* WME admission accepted */
-#define WME_INVALID_PARAMETERS 1 /* WME invalide parameters */
-#define WME_ADMISSION_REFUSED 3 /* WME admission refused */
-
-/* Macro to take a pointer to a beacon or probe response
- * body and return the char* pointer to the SSID info element
- */
-#define BCN_PRB_SSID(body) ((char*)(body) + DOT11_BCN_PRB_LEN)
-
/* Authentication frame payload constants */
#define DOT11_OPEN_SYSTEM 0 /* d11 open authentication */
#define DOT11_SHARED_KEY 1 /* d11 shared authentication */
@@ -1416,6 +1291,11 @@
#define DOT11_RC_SETUP_NEEDED 38 /* mechanism needs a setup */
#define DOT11_RC_TIMEOUT 39 /* timeout */
+#define DOT11_RC_INVALID_FT_ACTION_FC 48 /* Invalid FT Action frame count */
+#define DOT11_RC_INVALID_PMKID 49 /* Invalid PMKID */
+#define DOT11_RC_INVALID_MDE 50 /* Invalid MDE */
+#define DOT11_RC_INVALID_FTE 51 /* Invalid FTE */
+
#define DOT11_RC_MESH_PEERING_CANCELLED 52
#define DOT11_RC_MESH_MAX_PEERS 53
#define DOT11_RC_MESH_CONFIG_POLICY_VIOLN 54
@@ -1576,19 +1456,37 @@
*/
#define DOT11_SC_TCLAS_PROCESSING_TERMINATED_POLICY_CONFLICT 129u
-/* Draft P802.11be D0.3 Table 9-50 - TBD */
-#define DOT11_SC_DENIED_EXIST_MLD_ASSOC 150u /* Association denied because the requesting STA
- * is affiliated with a non-AP MLD that is
- * associated with the AP MLD.
- */
-#define DOT11_SC_NSEP_DENIED_UNAUTH 151u /* NSEP priority access denied because
- * the non-AP STA is not authorized
- * to use the service.
- */
-#define DOT11_SC_NSEP_DENIED_O_REASON 152u /* NSEP priority access denied due to
- * reason outside the scope of
- * this standard.
- */
+#define DOT11_SC_INVALID_PUBLIC_KEY 130u /* Public key format is invalid */
+#define DOT11_SC_PASN_BASE_AKM_FAILED 131u /* Failure from Base AKM processing during PASN */
+#define DOT11_SC_OCI_MISMATCH 132u /* OCI does not match received */
+
+/* Draft P802.11be D1.4 Table 9-78 Status codes */
+/* DENIED_STA_AFFILIATED_WITH_MLD_WITH_EXISTING_MLD_ASSOCIATION
+ * Association denied because the requesting STA is affiliated with a non-AP MLD
+ * that is associated with the AP MLD.
+ */
+#define DOT11_SC_DENIED_EXIST_MLD_ASSOC 130u
+/* EPCS_DENIED_UNAUTHO- RIZED
+ * EPCS priority access denied because the non-AP MLD or non-AP EHT STA is not authorized
+ * to use the service.
+ */
+#define DOT11_SC_EPCS_DENIED_UNAUTH 131u
+/* EPCS_DENIED- _OTHER_REASON
+ * EPCS priority access denied due to reason out- side the scope of this standard.
+ */
+#define DOT11_SC_EPCS_DENIED_O_REASON 132u
+/* DENIED_TID_TO_LINK_MAPPING
+ * Request denied because the requested TID-to-link map- ping is unacceptable.
+ */
+#define DOT11_SC_DENIED_TID_MAP 133u
+/* PREFERRED_TID_TO_LINK_MAP- PING_SUGGESTED
+ * Preferred TID-to-link mapping suggested.
+ */
+#define DOT11_SC_PREFER_TID_MAP 134u
+/* DENIED_EHT_NOT_SUPPORTED
+ * Association denied because the requesting STA does not support EHT features.
+ */
+#define DOT11_SC_DENIED_EHT_UNSUPPORTED 135u /* TBD */
/* Info Elts, length of INFORMATION portion of Info Elts */
#define DOT11_MNG_DS_PARAM_LEN 1 /* d11 management DS parameter length */
@@ -1734,8 +1632,8 @@
DOT11_MNG_VS_ID = 221, /* d11 management Vendor Specific IE */
DOT11_MNG_MESH_CSP_ID = 222, /* d11 Mesh Channel Switch Parameter */
DOT11_MNG_FILS_IND_ID = 240, /* 11ai FILS Indication element */
- DOT11_MNG_FRAGMENT_ID = 242, /* IE's fragment ID */
- DOT11_MNG_RSNXE_ID = 244, /* RSN Extension Element (RSNXE) ID */
+ DOT11_MNG_FRAGMENT_ID = 242, /* IE's fragment ID */
+ DOT11_MNG_RSNXE_ID = 244, /* RSN Extension Element (RSNXE) ID */
/* The follwing ID extensions should be defined >= 255
* i.e. the values should include 255 (DOT11_MNG_ID_EXT_ID + ID Extension).
@@ -1766,6 +1664,8 @@
#define EXTID_MNG_WRAPPED_DATA_ID FILS_EXTID_MNG_WRAPPED_DATA_ID
#define DOT11_MNG_WRAPPED_DATA DOT11_MNG_FILS_WRAPPED_DATA
+#define EXT_MNG_EXT_REQ_ID 10u /* Extended Request element */
+#define DOT11_MNG_EXT_REQ_ID (DOT11_MNG_ID_EXT_ID + EXT_MNG_EXT_REQ_ID)
#define OCE_EXTID_MNG_ESP_ID 11u /* Estimated Service Parameters element */
#define DOT11_MNG_ESP (DOT11_MNG_ID_EXT_ID + OCE_EXTID_MNG_ESP_ID)
#define FILS_EXTID_MNG_PUBLIC_KEY_ID 12u /* FILS Public Key element */
@@ -1791,7 +1691,7 @@
#define EXT_MNG_BSSCOLOR_CHANGE_ID 42u /* BSS Color Change Announcement */
#define DOT11_MNG_BSSCOLOR_CHANGE_ID (DOT11_MNG_ID_EXT_ID + EXT_MNG_BSSCOLOR_CHANGE_ID)
#define OCV_EXTID_MNG_OCI_ID 54u /* OCI element */
-#define DOT11_MNG_OCI_ID (DOT11_MNG_ID_EXT_ID + OCV_EXT_OCI_ID)
+#define DOT11_MNG_OCI_ID (DOT11_MNG_ID_EXT_ID + OCV_EXTID_MNG_OCI_ID)
#define EXT_MNG_NON_INHERITANCE_ID 56u /* Non-Inheritance element */
#define DOT11_MNG_NON_INHERITANCE_ID (DOT11_MNG_ID_EXT_ID + EXT_MNG_NON_INHERITANCE_ID)
#define EXT_MNG_SHORT_SSID_ID 58u /* SHORT SSID ELEMENT */
@@ -1831,31 +1731,26 @@
#define EXT_MNG_DIR_MEAS_RESULTS_ID 102u /* Direction Measurement Results */
#define DOT11_MNG_DIR_MEAS_RESULTS_ID (DOT11_MNG_ID_EXT_ID + EXT_MNG_DIR_MEAS_RESULTS_ID)
#define EXT_MNG_MULTI_AOD_FEEDBACK_ID 103u /* Multiple AOD Feedback */
-#define DOT11_MNG_MULTI_AOD_FEEDDBACK_ID (DOT11_MNG_ID_EXT_ID + EXT_MNG_MULTI_AOD_FEEDBACK_ID)
+#define DOT11_MNG_MULTI_AOD_FEEDDBACK_ID (DOT11_MNG_ID_EXT_ID + \
+ EXT_MNG_MULTI_AOD_FEEDBACK_ID)
#define EXT_MNG_MULTI_BEST_AWV_ID_ID 104u /* Multiple Best AWV ID */
#define DOT11_MNG_MULTI_BEST_AWV_ID_ID (DOT11_MNG_ID_EXT_ID + EXT_MNG_MULTI_BEST_AWV_ID_ID)
#define EXT_MNG_LOS_LIKELIHOOD_ID 105u /* LOS Likelihood */
#define DOT11_MNG_LOS_LIKELIHOOD_ID (DOT11_MNG_ID_EXT_ID + EXT_MNG_LOS_LIKELIHOOD_ID)
-
-/* Draft P802.11be D0.1 - TBD */
-#define EXT_MNG_NON_INH_ID 110u /* Non-inheritance */
-#define DOT11_MNG_NON_INH_ID (DOT11_MNG_ID_EXT_ID + EXT_MNG_NON_INH_ID)
-#define EXT_MNG_EHT_OP_ID 111u /* EHT Operation */
+/* Draft P802.11be D1.2 Table 9-92 Element IDs */
+#define EXT_MNG_EHT_OP_ID 106u /* EHT Operation */
#define DOT11_MNG_EHT_OP_ID (DOT11_MNG_ID_EXT_ID + EXT_MNG_EHT_OP_ID)
-#define EXT_MNG_ML_ID 112u /* Multi-Link */
+#define EXT_MNG_ML_ID 107u /* Multi-Link */
#define DOT11_MNG_ML_ID (DOT11_MNG_ID_EXT_ID + EXT_MNG_ML_ID)
-#define EXT_MNG_EHT_CAP_ID 113u /* EHT Capabilities */
+#define EXT_MNG_EHT_CAP_ID 108u /* EHT Capabilities */
#define DOT11_MNG_EHT_CAP_ID (DOT11_MNG_ID_EXT_ID + EXT_MNG_EHT_CAP_ID)
-/* Draft P802.11be D1.0 - TBD */
-#define EXT_MNG_TID_MAP_ID 114u /* TID-To-Link Mapping */
+#define EXT_MNG_TID_MAP_ID 109u /* TID-To-Link Mapping */
#define DOT11_MNG_TID_MAP_ID (DOT11_MNG_ID_EXT_ID + EXT_MNG_TID_MAP_ID)
-#define EXT_MNG_ML_TRAFFIC_ID 115u /* Multi-Link Traffic */
+#define EXT_MNG_ML_TRAFFIC_ID 110u /* Multi-Link Traffic */
#define DOT11_MNG_ML_TRAFFIC_ID (DOT11_MNG_ID_EXT_ID + EXT_MNG_ML_TRAFFIC_ID)
-
-/* P802.11az/D2.5 - Table 9-322h23fd Ranging Subelement IDs for Ranging Parameters */
-#define RANGING_PARAMS_NTB_SUB_ELT_ID 0u /* Non-TB specific subelement */
-#define RANGING_PARAMS_TB_SUB_ELT_ID 1u /* TB specific subelement */
-#define RANGING_PARAMS_VNDR_SUB_ELT_ID 221u /* Vendor specific subelement */
+/* Draft P802.11be D1.4 Table 9-128 Element IDs - TBD */
+#define EXT_MNG_QOS_CHAR_ID 111u /* QoS Characteristics */
+#define DOT11_MNG_QOS_CHAR_ID (DOT11_MNG_ID_EXT_ID + EXT_MNG_QOS_CHAR_ID)
/* deprecated definitions, do not use, to be deleted later */
#define FILS_HLP_CONTAINER_EXT_ID FILS_EXTID_MNG_HLP_CONTAINER_ID
@@ -1876,6 +1771,16 @@
(_ie)->id_ext = _id; \
} while (0)
+/* P802.11az/D2.5 - Table 9-322h23fd Ranging Subelement IDs for Ranging Parameters */
+#define RANGING_PARAMS_NTB_SUB_ELT_ID 0u /* Non-TB specific subelement */
+#define RANGING_PARAMS_TB_SUB_ELT_ID 1u /* TB specific subelement */
+#define RANGING_PARAMS_SLTF_SUB_ELT_ID 2u /* Secure LTF subelement */
+#define RANGING_PARAMS_STLF_SUB_ELT_ID RANGING_PARAMS_SLTF_SUB_ELT_ID /* to be obsoleted */
+#define RANGING_PARAMS_VNDR_SUB_ELT_ID 221u /* Vendor specific subelement */
+
+/* P802.11az/D3.1 - Table 9-788edm1 Secure LTF subelement format */
+#define FTM_PARAM_SLTF_REQUIRED_BIT 0x08
+
/* Rate Defines */
/* Valid rates for the Supported Rates and Extended Supported Rates IEs.
@@ -1908,18 +1813,21 @@
#define DOT11_RATE_MASK 0x7F /* mask for numeric part of rate */
/* BSS Membership Selector parameters
- * 802.11-2016 (and 802.11ax-D1.1), Sec 9.4.2.3
- * 802.11-2020, Sec 9.4.2.3
* These selector values are advertised in Supported Rates and Extended Supported Rates IEs
* in the supported rates list with the Basic rate bit set.
* Constants below include the basic bit.
*/
+/* IEEE Std 802.11-2016 Table 9-78 BSS membership selector value encoding */
#define DOT11_BSS_MEMBERSHIP_HT 0xFF /* Basic 0x80 + 127, HT Required to join */
#define DOT11_BSS_MEMBERSHIP_VHT 0xFE /* Basic 0x80 + 126, VHT Required to join */
-#define DOT11_BSS_MEMBERSHIP_HE 0xFD /* Basic 0x80 + 125, HE Required to join */
-/* Draft P802.11be D0.1 - TBD */
-#define DOT11_BSS_MEMBERSHIP_EHT 0xFC /* Basic 0x80 + 124, EHT Required to join */
-#define DOT11_BSS_SAE_HASH_TO_ELEMENT 0xFB /* Basic 0x80 + 123, SAE Hash-to-element */
+/* IEEE P802.11-REVmd D5.0 Table 9-93 BSS membership selector value encoding */
+#define DOT11_BSS_MEMBERSHIP_GLK 0xFD /* Basic 0x80 + 125, GLK Op is required */
+#define DOT11_BSS_MEMBERSHIP_EPD 0xFC /* Basic 0x80 + 124, EPD is required */
+#define DOT11_BSS_SAE_HASH_TO_ELEMENT 0xFB /* Basic 0x80 + 123, SAE Hash-to-element */
+/* Draft P802.11ax D8.0 Table 9-93 BSS membership selector value encoding */
+#define DOT11_BSS_MEMBERSHIP_HE 0xFA /* Basic 0x80 + 122, HE Required to join */
+/* Draft P802.11be - TBD */
+#define DOT11_BSS_MEMBERSHIP_EHT 0xF9 /* Basic 0x80 + 121, EHT Required to join */
/* TS Delay element offset & size */
#define DOT11_MGN_TS_DELAY_LEN 4 /* length of TS DELAY IE */
@@ -2216,9 +2124,9 @@
#define DOT11_ACTION_CAT_HEP 31 /* Protected HE action frame */
/* Protected Fine Timing action frame - Draft P802.11az/D2.5 Table 9-51 Category values */
#define DOT11_ACTION_CAT_PFT 34u /* Protected Fine Timing action frame */
-/* EHT Action frames - Draft P802.11be D0.3 Table 9-51 - TDB */
-#define DOT11_ACTION_CAT_NESP 40u /* NSEP Priority Access Action frame */
-#define DOT11_ACTION_CAT_EHT 41u /* EHT Action frame */
+/* EHT Action frames - Draft P802.11be D1.2 Table 9-51 Category values */
+#define DOT11_ACTION_CAT_EHT 36u /* EHT action frame */
+#define DOT11_ACTION_CAT_EHTP 37u /* Protected EHT action frame */
#define DOT11_ACTION_CAT_VSP 126 /* protected vendor specific */
#define DOT11_ACTION_CAT_VS 127 /* category Vendor Specific */
@@ -3931,16 +3839,9 @@
uint8 mode;
uint8 type;
uint8 subj;
-
- /* Following 3 fields are unused. Keep for ROM compatibility. */
- uint8 lat_res;
- uint8 lon_res;
- uint8 alt_res;
-
/* optional sub-elements */
} BWL_POST_PACKED_STRUCT;
typedef struct dot11_rmreq_ftm_lci dot11_rmreq_ftm_lci_t;
-#define DOT11_RMREQ_LCI_LEN 9
BWL_PRE_PACKED_STRUCT struct dot11_rmrep_ftm_lci {
uint8 id;
@@ -4345,163 +4246,6 @@
#define VHT_N_SERVICE 16 /* bits in SERVICE field */
#define VHT_N_TAIL 6 /* tail bits per BCC encoder */
-/** dot11Counters Table - 802.11 spec., Annex D */
-typedef struct d11cnt {
- uint32 txfrag; /* dot11TransmittedFragmentCount */
- uint32 txmulti; /* dot11MulticastTransmittedFrameCount */
- uint32 txfail; /* dot11FailedCount */
- uint32 txretry; /* dot11RetryCount */
- uint32 txretrie; /* dot11MultipleRetryCount */
- uint32 rxdup; /* dot11FrameduplicateCount */
- uint32 txrts; /* dot11RTSSuccessCount */
- uint32 txnocts; /* dot11RTSFailureCount */
- uint32 txnoack; /* dot11ACKFailureCount */
- uint32 rxfrag; /* dot11ReceivedFragmentCount */
- uint32 rxmulti; /* dot11MulticastReceivedFrameCount */
- uint32 rxcrc; /* dot11FCSErrorCount */
- uint32 txfrmsnt; /* dot11TransmittedFrameCount */
- uint32 rxundec; /* dot11WEPUndecryptableCount */
-} d11cnt_t;
-
-/* OUI for BRCM proprietary IE */
-#define BRCM_PROP_OUI "\x00\x90\x4C" /* Broadcom proprietary OUI */
-
-/* Broadcom Proprietary OUI type list. Please update below page when adding a new type.
- * Twiki http://hwnbu-twiki.sj.broadcom.com/bin/view/Mwgroup/WlBrcmPropIE
- */
-/* The following BRCM_PROP_OUI types are currently in use (defined in
- * relevant subsections). Each of them will be in a separate proprietary(221) IE
- * #define RWL_WIFI_DEFAULT 0
- * #define SES_VNDR_IE_TYPE 1 (defined in src/ses/shared/ses.h)
- * #define VHT_FEATURES_IE_TYPE 4
- * #define RWL_WIFI_FIND_MY_PEER 9
- * #define RWL_WIFI_FOUND_PEER 10
- * #define PROXD_IE_TYPE 11
- */
-
-#define BRCM_FTM_IE_TYPE 14
-
-/* #define HT_CAP_IE_TYPE 51
- * #define HT_ADD_IE_TYPE 52
- * #define BRCM_EXTCH_IE_TYPE 53
- * #define MEMBER_OF_BRCM_PROP_IE_TYPE 54
- * #define BRCM_RELMACST_IE_TYPE 55
- * #define BRCM_EVT_WL_BSS_INFO 64
- * #define RWL_ACTION_WIFI_FRAG_TYPE 85
- * #define BTC_INFO_BRCM_PROP_IE_TYPE 90
- * #define ULB_BRCM_PROP_IE_TYPE 91
- * #define SDB_BRCM_PROP_IE_TYPE 92
- */
-
-/* Action frame type for RWL */
-#define RWL_WIFI_DEFAULT 0
-#define RWL_WIFI_FIND_MY_PEER 9 /* Used while finding server */
-#define RWL_WIFI_FOUND_PEER 10 /* Server response to the client */
-#define RWL_ACTION_WIFI_FRAG_TYPE 85 /* Fragment indicator for receiver */
-
-#define PROXD_AF_TYPE 11 /* Wifi proximity action frame type */
-#define BRCM_RELMACST_AF_TYPE 12 /* RMC action frame type */
-
-/* Action frame type for FTM Initiator Report */
-#define BRCM_FTM_VS_AF_TYPE 14
-enum {
- BRCM_FTM_VS_INITIATOR_RPT_SUBTYPE = 1, /* FTM Initiator Report */
- BRCM_FTM_VS_COLLECT_SUBTYPE = 2, /* FTM Collect debug protocol */
-};
-
-/* Action frame type for vendor specific action frames */
-#define VS_AF_TYPE 221
-
-/*
- * This BRCM_PROP_OUI types is intended for use in events to embed additional
- * data, and would not be expected to appear on the air -- but having an IE
- * format allows IE frame data with extra data in events in that allows for
- * more flexible parsing.
- */
-#define BRCM_EVT_WL_BSS_INFO 64
-
-/**
- * Following is the generic structure for brcm_prop_ie (uses BRCM_PROP_OUI).
- * DPT uses this format with type set to DPT_IE_TYPE
- */
-BWL_PRE_PACKED_STRUCT struct brcm_prop_ie_s {
- uint8 id; /* IE ID, 221, DOT11_MNG_PROPR_ID */
- uint8 len; /* IE length */
- uint8 oui[3]; /* Proprietary OUI, BRCM_PROP_OUI */
- uint8 type; /* type of this IE */
- uint16 cap; /* DPT capabilities */
-} BWL_POST_PACKED_STRUCT;
-typedef struct brcm_prop_ie_s brcm_prop_ie_t;
-
-#define BRCM_PROP_IE_LEN 6 /* len of fixed part of brcm_prop ie */
-
-#define DPT_IE_TYPE 2
-
-#define BRCM_SYSCAP_IE_TYPE 3
-#define WET_TUNNEL_IE_TYPE 3
-
-/* brcm syscap_ie cap */
-#define BRCM_SYSCAP_WET_TUNNEL 0x0100 /* Device with WET_TUNNEL support */
-
-/* BRCM OUI: Used in the proprietary(221) IE in all broadcom devices */
-#define BRCM_OUI "\x00\x10\x18" /* Broadcom OUI */
-
-/** BRCM info element */
-BWL_PRE_PACKED_STRUCT struct brcm_ie {
- uint8 id; /* IE ID, 221, DOT11_MNG_PROPR_ID */
- uint8 len; /* IE length */
- uint8 oui[3]; /* Proprietary OUI, BRCM_OUI */
- uint8 ver; /* type/ver of this IE */
- uint8 assoc; /* # of assoc STAs */
- uint8 flags; /* misc flags */
- uint8 flags1; /* misc flags */
- uint16 amsdu_mtu_pref; /* preferred A-MSDU MTU */
- uint8 flags2; /* DTPC Cap flags */
-} BWL_POST_PACKED_STRUCT;
-typedef struct brcm_ie brcm_ie_t;
-#define BRCM_IE_LEN 12u /* BRCM IE length */
-#define BRCM_IE_VER 2u /* BRCM IE version */
-#define BRCM_IE_LEGACY_AES_VER 1u /* BRCM IE legacy AES version */
-
-/* brcm_ie flags */
-#define BRF_ABCAP 0x01 /* afterburner is obsolete, defined for backward compat */
-#define BRF_ABRQRD 0x02 /* afterburner is obsolete, defined for backward compat */
-#define BRF_LZWDS 0x04 /* lazy wds enabled */
-#define BRF_BLOCKACK 0x08 /* BlockACK capable */
-#define BRF_ABCOUNTER_MASK 0xf0 /* afterburner is obsolete, defined for backward compat */
-#define BRF_PROP_11N_MCS 0x10 /* re-use afterburner bit */
-#define BRF_MEDIA_CLIENT 0x20 /* re-use afterburner bit to indicate media client device */
-
-/**
- * Support for Broadcom proprietary HT MCS rates. Re-uses afterburner bits since
- * afterburner is not used anymore. Checks for BRF_ABCAP to stay compliant with 'old'
- * images in the field.
- */
-#define GET_BRF_PROP_11N_MCS(brcm_ie) \
- (!((brcm_ie)->flags & BRF_ABCAP) && ((brcm_ie)->flags & BRF_PROP_11N_MCS))
-
-/* brcm_ie flags1 */
-#define BRF1_AMSDU 0x01 /* A-MSDU capable */
-#define BRF1_WNM 0x02 /* WNM capable */
-#define BRF1_WMEPS 0x04 /* AP is capable of handling WME + PS w/o APSD */
-#define BRF1_PSOFIX 0x08 /* AP has fixed PS mode out-of-order packets */
-#define BRF1_RX_LARGE_AGG 0x10 /* device can rx large aggregates */
-#define BRF1_RFAWARE_DCS 0x20 /* RFAWARE dynamic channel selection (DCS) */
-#define BRF1_SOFTAP 0x40 /* Configure as Broadcom SOFTAP */
-#define BRF1_DWDS 0x80 /* DWDS capable */
-
-/* brcm_ie flags2 */
-#define BRF2_DTPC_TX 0x01u /* DTPC: DTPC TX Cap */
-#define BRF2_DTPC_RX 0x02u /* DTPC: DTPC RX Cap */
-#define BRF2_DTPC_TX_RX 0x03u /* DTPC: Enable Both DTPC TX and RX Cap */
-#define BRF2_DTPC_NONBF 0x04u /* DTPC: Enable DTPC for NON-TXBF */
-#define BRF2_TWT_RESP_CAP 0x08u /* TWT responder Cap for Brcm Softap
- * only brcm sta parse this
- */
-#define BRF2_TWT_REQ_CAP 0x10u /* TWT requester Cap for BRCM STA
- * only brcm softap parse this
- */
-
/** Vendor IE structure */
BWL_PRE_PACKED_STRUCT struct vndr_ie {
uchar id;
@@ -4517,51 +4261,6 @@
#define VNDR_IE_MAX_LEN 255u /* vendor IE max length, without ID and len */
-/** BRCM PROP DEVICE PRIMARY MAC ADDRESS IE */
-BWL_PRE_PACKED_STRUCT struct member_of_brcm_prop_ie {
- uchar id;
- uchar len;
- uchar oui[3];
- uint8 type; /* type indicates what follows */
- struct ether_addr ea; /* Device Primary MAC Adrress */
-} BWL_POST_PACKED_STRUCT;
-typedef struct member_of_brcm_prop_ie member_of_brcm_prop_ie_t;
-
-#define MEMBER_OF_BRCM_PROP_IE_LEN 10 /* IE max length */
-#define MEMBER_OF_BRCM_PROP_IE_HDRLEN (sizeof(member_of_brcm_prop_ie_t))
-#define MEMBER_OF_BRCM_PROP_IE_TYPE 54 /* used in prop IE 221 only */
-
-/** BRCM Reliable Multicast IE */
-BWL_PRE_PACKED_STRUCT struct relmcast_brcm_prop_ie {
- uint8 id;
- uint8 len;
- uint8 oui[3];
- uint8 type; /* type indicates what follows */
- struct ether_addr ea; /* The ack sender's MAC Adrress */
- struct ether_addr mcast_ea; /* The multicast MAC address */
- uint8 updtmo; /* time interval(second) for client to send null packet to report its rssi */
-} BWL_POST_PACKED_STRUCT;
-typedef struct relmcast_brcm_prop_ie relmcast_brcm_prop_ie_t;
-
-/* IE length */
-/* BRCM_PROP_IE_LEN = sizeof(relmcast_brcm_prop_ie_t)-((sizeof (id) + sizeof (len)))? */
-#define RELMCAST_BRCM_PROP_IE_LEN (sizeof(relmcast_brcm_prop_ie_t)-(2*sizeof(uint8)))
-
-#define RELMCAST_BRCM_PROP_IE_TYPE 55 /* used in prop IE 221 only */
-
-/* BRCM BTC IE */
-BWL_PRE_PACKED_STRUCT struct btc_brcm_prop_ie {
- uint8 id;
- uint8 len;
- uint8 oui[3];
- uint8 type; /* type inidicates what follows */
- uint32 info;
-} BWL_POST_PACKED_STRUCT;
-typedef struct btc_brcm_prop_ie btc_brcm_prop_ie_t;
-
-#define BTC_INFO_BRCM_PROP_IE_TYPE 90
-#define BRCM_BTC_INFO_TYPE_LEN (sizeof(btc_brcm_prop_ie_t) - (2 * sizeof(uint8)))
-
/* ************* HT definitions. ************* */
#define MCSSET_LEN 16 /* 16-bits per 8-bit set to give 128-bits bitmap of MCS Index */
#define MAX_MCS_NUM (128) /* max mcs number = 128 */
@@ -4584,20 +4283,7 @@
} BWL_POST_PACKED_STRUCT;
typedef struct dot11_ht_cap_ie dot11_ht_cap_ie_t;
-/* CAP IE: HT 1.0 spec. simply stole a 802.11 IE, we use our prop. IE until this is resolved */
-/* the capability IE is primarily used to convey this nodes abilities */
-BWL_PRE_PACKED_STRUCT struct ht_prop_cap_ie {
- uint8 id; /* IE ID, 221, DOT11_MNG_PROPR_ID */
- uint8 len; /* IE length */
- uint8 oui[3]; /* Proprietary OUI, BRCM_PROP_OUI */
- uint8 type; /* type indicates what follows */
- ht_cap_ie_t cap_ie;
-} BWL_POST_PACKED_STRUCT;
-typedef struct ht_prop_cap_ie ht_prop_cap_ie_t;
-
-#define HT_PROP_IE_OVERHEAD 4 /* overhead bytes for prop oui ie */
#define HT_CAP_IE_LEN 26 /* HT capability len (based on .11n d2.0) */
-#define HT_CAP_IE_TYPE 51 /* used in prop IE 221 only */
#define HT_CAP_LDPC_CODING 0x0001 /* Support for rx of LDPC coded pkts */
#define HT_CAP_40MHZ 0x0002 /* FALSE:20Mhz, TRUE:20/40MHZ supported */
@@ -4694,11 +4380,7 @@
#define AMPDU_RX_FACTOR_1024K 7 /* max rcv ampdu len (1024kb) */
#define AMPDU_RX_FACTOR_BASE 8*1024 /* ampdu factor base for rx len */
-#ifdef WL_EXTBA
-#define AMPDU_RX_FACTOR_BASE_PWR 15 /* ampdu factor base for rx len in power of 2 */
-#else
#define AMPDU_RX_FACTOR_BASE_PWR 13 /* ampdu factor base for rx len in power of 2 */
-#endif
#define AMPDU_DELIMITER_LEN 4u /* length of ampdu delimiter */
#define AMPDU_DELIMITER_LEN_MAX 63 /* max length of ampdu delimiter(enforced in HW) */
@@ -4720,19 +4402,7 @@
} BWL_POST_PACKED_STRUCT;
typedef struct ht_add_ie ht_add_ie_t;
-/* ADD IE: HT 1.0 spec. simply stole a 802.11 IE, we use our prop. IE until this is resolved */
-/* the additional IE is primarily used to convey the current BSS configuration */
-BWL_PRE_PACKED_STRUCT struct ht_prop_add_ie {
- uint8 id; /* IE ID, 221, DOT11_MNG_PROPR_ID */
- uint8 len; /* IE length */
- uint8 oui[3]; /* Proprietary OUI, BRCM_PROP_OUI */
- uint8 type; /* indicates what follows */
- ht_add_ie_t add_ie;
-} BWL_POST_PACKED_STRUCT;
-typedef struct ht_prop_add_ie ht_prop_add_ie_t;
-
#define HT_ADD_IE_LEN 22 /* HT capability len (based on .11n d1.0) */
-#define HT_ADD_IE_TYPE 52 /* faked out as current spec is illegal */
/* byte1 defn's */
#define HT_BW_ANY 0x04 /* set, STA can use 20 or 40MHz */
@@ -5016,29 +4686,6 @@
/* AID length */
#define AID_IE_LEN 2
-/**
- * BRCM vht features IE header
- * The header if the fixed part of the IE
- * On the 5GHz band this is the entire IE,
- * on 2.4GHz the VHT IEs as defined in the 802.11ac
- * specification follows
- *
- *
- * VHT features rates bitmap.
- * Bit0: 5G MCS 0-9 BW 160MHz
- * Bit1: 5G MCS 0-9 support BW 80MHz
- * Bit2: 5G MCS 0-9 support BW 20MHz
- * Bit3: 2.4G MCS 0-9 support BW 20MHz
- * Bits:4-7 Reserved for future use
- *
- */
-#define VHT_FEATURES_IE_TYPE 0x4
-BWL_PRE_PACKED_STRUCT struct vht_features_ie_hdr {
- uint8 oui[3]; /* Proprietary OUI, BRCM_PROP_OUI */
- uint8 type; /* type of this IE = 4 */
- uint8 rate_mask; /* VHT rate mask */
-} BWL_POST_PACKED_STRUCT;
-typedef struct vht_features_ie_hdr vht_features_ie_hdr_t;
/* Def for rx & tx basic mcs maps - ea ss num has 2 bits of info */
#define VHT_MCS_MAP_GET_SS_IDX(nss) (((nss)-1) * VHT_CAP_MCS_MAP_S)
@@ -5063,71 +4710,6 @@
VHT_MCS_SS_SUPPORTED(2, mcsMap) ? 2 : \
VHT_MCS_SS_SUPPORTED(1, mcsMap) ? 1 : 0
-#ifdef IBSS_RMC
-/* customer's OUI */
-#define RMC_PROP_OUI "\x00\x16\x32"
-#endif
-
-/* ************* WPA definitions. ************* */
-#define WPA_OUI "\x00\x50\xF2" /* WPA OUI */
-#define WPA_OUI_LEN 3 /* WPA OUI length */
-#define WPA_OUI_TYPE 1
-#define WPA_VERSION 1 /* WPA version */
-#define WPA_VERSION_LEN 2 /* WPA version length */
-
-/* ************* WPA2 definitions. ************* */
-#define WPA2_OUI "\x00\x0F\xAC" /* WPA2 OUI */
-#define WPA2_OUI_LEN 3 /* WPA2 OUI length */
-#define WPA2_VERSION 1 /* WPA2 version */
-#define WPA2_VERSION_LEN 2 /* WAP2 version length */
-#define MAX_RSNE_SUPPORTED_VERSION WPA2_VERSION /* Max supported version */
-
-/* ************* WPS definitions. ************* */
-#define WPS_OUI "\x00\x50\xF2" /* WPS OUI */
-#define WPS_OUI_LEN 3 /* WPS OUI length */
-#define WPS_OUI_TYPE 4
-
-/* ************* TPC definitions. ************* */
-#define TPC_OUI "\x00\x50\xF2" /* TPC OUI */
-#define TPC_OUI_LEN 3 /* TPC OUI length */
-#define TPC_OUI_TYPE 8
-#define WFA_OUI_TYPE_TPC 8 /* deprecated */
-
-/* ************* WFA definitions. ************* */
-#define WFA_OUI "\x50\x6F\x9A" /* WFA OUI */
-#define WFA_OUI_LEN 3 /* WFA OUI length */
-#define WFA_OUI_TYPE_P2P 9
-
-/* WFA definitions for LEGACY P2P */
-
-#define P2P_OUI WFA_OUI
-#define P2P_OUI_LEN WFA_OUI_LEN
-#define P2P_OUI_TYPE WFA_OUI_TYPE_P2P
-
-#ifdef WLTDLS
-#define WFA_OUI_TYPE_TPQ 4 /* WFD Tunneled Probe ReQuest */
-#define WFA_OUI_TYPE_TPS 5 /* WFD Tunneled Probe ReSponse */
-#define WFA_OUI_TYPE_WFD 10
-#endif /* WTDLS */
-#define WFA_OUI_TYPE_HS20 0x10
-#define WFA_OUI_TYPE_OSEN 0x12
-#define WFA_OUI_TYPE_NAN 0x13
-#define WFA_OUI_TYPE_MBO 0x16
-#define WFA_OUI_TYPE_MBO_OCE 0x16
-#define WFA_OUI_TYPE_OWE 0x1C
-#define WFA_OUI_TYPE_SAE_PK 0x1F
-#define WFA_OUI_TYPE_TD_INDICATION 0x20
-
-#define SAE_PK_MOD_LEN 32u
-BWL_PRE_PACKED_STRUCT struct dot11_sae_pk_element {
- uint8 id; /* IE ID, 221, DOT11_MNG_PROPR_ID */
- uint8 len; /* IE length */
- uint8 oui[WFA_OUI_LEN]; /* WFA_OUI */
- uint8 type; /* SAE-PK */
- uint8 data[SAE_PK_MOD_LEN]; /* Modifier. 32Byte fixed */
-} BWL_POST_PACKED_STRUCT;
-typedef struct dot11_sae_pk_element dot11_sae_pk_element_t;
-
/* RSN authenticated key managment suite */
#define RSN_AKM_NONE 0 /* None (IBSS) */
#define RSN_AKM_UNSPECIFIED 1 /* Over 802.1x */
@@ -5193,15 +4775,6 @@
#define AES256_KEY_SIZE 32 /* size of AES 256 key - .11acD5 */
#define AES256_MIC_SIZE 16 /* size of MIC for 256 bit keys, incl BIP */
-/* WCN */
-#define WCN_OUI "\x00\x50\xf2" /* WCN OUI */
-#define WCN_TYPE 4 /* WCN type */
-
-#ifdef BCMWAPI_WPI
-#define SMS4_KEY_LEN 16
-#define SMS4_WPI_CBC_MAC_LEN 16
-#endif
-
/* 802.11r protocol definitions */
/** Mobility Domain IE */
@@ -5315,25 +4888,6 @@
#define BSSID_INVALID "\x00\x00\x00\x00\x00\x00"
#define BSSID_BROADCAST "\xFF\xFF\xFF\xFF\xFF\xFF"
-#ifdef BCMWAPI_WAI
-#define WAPI_IE_MIN_LEN 20 /* WAPI IE min length */
-#define WAPI_VERSION 1 /* WAPI version */
-#define WAPI_VERSION_LEN 2 /* WAPI version length */
-#define WAPI_OUI "\x00\x14\x72" /* WAPI OUI */
-#define WAPI_OUI_LEN DOT11_OUI_LEN /* WAPI OUI length */
-#endif /* BCMWAPI_WAI */
-
-/* ************* WMM Parameter definitions. ************* */
-#define WMM_OUI "\x00\x50\xF2" /* WNN OUI */
-#define WMM_OUI_LEN 3 /* WMM OUI length */
-#define WMM_OUI_TYPE 2 /* WMM OUT type */
-#define WMM_VERSION 1
-#define WMM_VERSION_LEN 1
-
-/* WMM OUI subtype */
-#define WMM_OUI_SUBTYPE_PARAMETER 1
-#define WMM_PARAMETER_IE_LEN 24
-
/** Link Identifier Element */
BWL_PRE_PACKED_STRUCT struct link_id_ie {
uint8 id;
@@ -5455,21 +5009,63 @@
} BWL_POST_PACKED_STRUCT;
typedef struct dot11_ftm_lmr dot11_ftm_lmr_t;
-BWL_PRE_PACKED_STRUCT struct dot11_ftm_ranging_ndpa {
- uint16 fc; /* frame control */
- uint16 durid; /* duration/ID */
- struct ether_addr ra; /* receiver address */
- struct ether_addr ta; /* transmitter address */
- uint8 dialog_token; /* sounding dialog token */
+BWL_PRE_PACKED_STRUCT struct dot11_ranging_ndpa {
+ uint8 dialog_token; /* sounding dialog token */
+ uint8 sta_info[]; /* STA infos */
} BWL_POST_PACKED_STRUCT;
-typedef struct dot11_ftm_ranging_ndpa dot11_ftm_ranging_ndpa_t;
+typedef struct dot11_ranging_ndpa dot11_ranging_ndpa_t;
/* NDPA types = dialog token byte lower 2 bits */
-#define DOT11_NDPA_TYPE_MASK 0x03
-#define DOT11_NDPA_TYPE_VHT 0x00
-#define DOT11_NDPA_TYPE_RANGING 0x01
-#define DOT11_NDPA_TYPE_HE 0x02
-#define DOT11_NPDA_TOKEN_SHIFT 2u
+#define DOT11_NDPA_TYPE_MASK 0x03u
+#define DOT11_NDPA_TYPE_VHT 0x00u
+#define DOT11_NDPA_TYPE_RANGING 0x01u
+#define DOT11_NDPA_TYPE_HE 0x02u
+#define DOT11_NPDA_TOKEN_SHIFT 2u
+
+/* NDPA STA info size */
+#define DOT11_NDPA_STA_INFO_SIZE 4u
+
+#define DOT11_RANGING_TF_CMN_INFO_FIXED_SIZE 8u
+BWL_PRE_PACKED_STRUCT struct dot11_ranging_trigger {
+ uint8 cmn_info[DOT11_RANGING_TF_CMN_INFO_FIXED_SIZE]; /* trigger common info */
+ uint8 dep_cmn_info[BCM_FLEX_ARRAY]; /* type dependent common info */
+ /* followed by user info list */
+} BWL_POST_PACKED_STRUCT;
+typedef struct dot11_ranging_trigger dot11_ranging_trigger_t;
+
+/* Trigger frame types
+ * P802.11ax/D8.0 & P802.11az/D4.0 Table 9-20c Trigger Type subfield encoding
+ */
+#define DOT11_TF_TYPE_MASK 0x0Fu
+#define DOT11_TF_TYPE_BASIC 0u /* basic */
+#define DOT11_TF_TYPE_BFRP 1u /* Beamforming Report Poll */
+#define DOT11_TF_TYPE_MUBAR 2u /* MU-BAR */
+#define DOT11_TF_TYPE_MURTS 3u /* MU-RTS */
+#define DOT11_TF_TYPE_BSRP 4u /* Buffer Status Report Poll */
+#define DOT11_TF_TYPE_GCR_MUBAR 5u /* GCR MU-BAR */
+#define DOT11_TF_TYPE_BQRP 6u /* Bandwidth Query Report Poll */
+#define DOT11_TF_TYPE_NFRP 7u /* NDP Feedback Report Poll */
+#define DOT11_TF_TYPE_RANGING 8u /* Ranging */
+
+/* Ranging TF subtypes in Ranging trigger dependent common info
+ * P802.11az/D4.0 Table 9-30ka Ranging Trigger Subtype subfield encoding
+ */
+#define DOT11_RANGING_TF_SUBTYPE_MASK 0x0Fu
+#define DOT11_RANGING_TF_SUBTYPE_POLL 0u /* Ranging TF Poll */
+#define DOT11_RANGING_TF_SUBTYPE_SND 1u /* Ranging TF Sounding */
+#define DOT11_RANGING_TF_SUBTYPE_SSND 2u /* Ranging TF Secure Sounding */
+#define DOT11_RANGING_TF_SUBTYPE_RPT 3u /* Ranging TF Report */
+#define DOT11_RANGING_TF_SUBTYPE_PSND 4u /* Ranging TF Passive Sounding */
+
+/* Ranging TF dependent common info len */
+#define DOT11_RANGING_TF_DEP_CMN_INFO_LEN 1u /* Ranging TF variant */
+#define DOT11_RANGING_TF_PSND_DEP_CMN_INFO_LEN 2u /* Ranging TF Passive sounding */
+
+/* Ranging TF user info fixed len - followed by TF dependent user info */
+#define DOT11_RANGING_TF_USER_INFO_FIXED_LEN 5u
+
+/* start of padding marker in user info */
+#define DOT11_TF_USER_INFO_PADDING_START 4095u
#define DOT11_FTM_ERR_NOT_CONT_OFFSET 1
#define DOT11_FTM_ERR_NOT_CONT_MASK 0x80
@@ -5498,62 +5094,109 @@
DOT11_FTM_ERR_SET_NOT_CONT(_err, _not_cont); \
} while (0)
-#if defined(DOT11_FTM_ERR_ROM_COMPAT)
-/* incorrect defs - here for ROM compatibiity */
-#undef DOT11_FTM_ERR_NOT_CONT_OFFSET
-#undef DOT11_FTM_ERR_NOT_CONT_MASK
-#undef DOT11_FTM_ERR_NOT_CONT_SHIFT
-#undef DOT11_FTM_ERR_NOT_CONT
-#undef DOT11_FTM_ERR_SET_NOT_CONT
-
-#define DOT11_FTM_ERR_NOT_CONT_OFFSET 0
-#define DOT11_FTM_ERR_NOT_CONT_MASK 0x0001
-#define DOT11_FTM_ERR_NOT_CONT_SHIFT 0
-#define DOT11_FTM_ERR_NOT_CONT(_err) (((_err)[DOT11_FTM_ERR_NOT_CONT_OFFSET] & \
- DOT11_FTM_ERR_NOT_CONT_MASK) >> DOT11_FTM_ERR_NOT_CONT_SHIFT)
-#define DOT11_FTM_ERR_SET_NOT_CONT(_err, _val) do {\
- uint8 _err2 = (_err)[DOT11_FTM_ERR_NOT_CONT_OFFSET]; \
- _err2 &= ~DOT11_FTM_ERR_NOT_CONT_MASK; \
- _err2 |= ((_val) << DOT11_FTM_ERR_NOT_CONT_SHIFT) & DOT11_FTM_ERR_NOT_CONT_MASK; \
- (_err)[DOT11_FTM_ERR_NOT_CONT_OFFSET] = _err2; \
-} while (0)
-
-#undef DOT11_FTM_ERR_MAX_ERR_OFFSET
-#undef DOT11_FTM_ERR_MAX_ERR_MASK
-#undef DOT11_FTM_ERR_MAX_ERR_SHIFT
-#undef DOT11_FTM_ERR_MAX_ERR
-#undef DOT11_FTM_ERR_SET_MAX_ERR
-
-#define DOT11_FTM_ERR_MAX_ERR_OFFSET 0
-#define DOT11_FTM_ERR_MAX_ERR_MASK 0xfff7
-#define DOT11_FTM_ERR_MAX_ERR_SHIFT 1
-#define DOT11_FTM_ERR_MAX_ERR(_err) ((((_err)[1] << 7) | (_err)[0]) >> 1)
-#define DOT11_FTM_ERR_SET_MAX_ERR(_err, _val) do {\
- uint16 _val2; \
- _val2 = (((_val) << DOT11_FTM_ERR_MAX_ERR_SHIFT) |\
- ((_err)[DOT11_FTM_ERR_NOT_CONT_OFFSET] & DOT11_FTM_ERR_NOT_CONT_MASK)); \
- (_err)[0] = _val2 & 0xff; \
- (_err)[1] = _val2 >> 8 & 0xff; \
-} while (0)
-#endif /* DOT11_FTM_ERR_ROM_COMPAT */
-
BWL_PRE_PACKED_STRUCT struct dot11_ftm_params {
- uint8 id; /* DOT11_MNG_FTM_PARAM_ID 8.4.2.166 11mcd2.6/2014 - revisit */
+ uint8 id; /* DOT11_MNG_FTM_PARAM_ID 8.4.2.166 11mcd2.6/2014 - revisit */
uint8 len;
uint8 info[9];
} BWL_POST_PACKED_STRUCT;
-
typedef struct dot11_ftm_params dot11_ftm_params_t;
-#define DOT11_FTM_PARAMS_IE_LEN (sizeof(dot11_ftm_params_t) - 2)
+#define DOT11_FTM_PARAMS_IE_LEN (sizeof(dot11_ftm_params_t) - OFFSETOF(dot11_ftm_params_t, info))
-/* common part for both TB and NTB */
+/* FTM Ranging parameters element */
+#define DOT11_FTM_RANGING_PARAMS_FIXED_SIZE 7u
BWL_PRE_PACKED_STRUCT struct dot11_ftm_ranging_params {
uint8 id; /* 255 */
uint8 len;
uint8 ext_id; /* EXT_MNG_RANGING_PARAMS_ID */
- uint8 info[6];
+ uint8 info[DOT11_FTM_RANGING_PARAMS_FIXED_SIZE];
+ uint8 subelmts[]; /* sub-elements (NTB/TB/SLTF/Vendor) */
} BWL_POST_PACKED_STRUCT;
typedef struct dot11_ftm_ranging_params dot11_ftm_ranging_params_t;
+#define DOT11_FTM_RANGING_PARAMS_MIN_LEN \
+ (sizeof(dot11_ftm_ranging_params_t) - OFFSETOF(dot11_ftm_ranging_params_t, ext_id))
+
+/* FTM NTB specific sub-element */
+#define DOT11_FTM_NTB_SUBELMT_FIXED_SIZE 6u
+BWL_PRE_PACKED_STRUCT struct dot11_ftm_ntb_subelmt {
+ uint8 id; /* RANGING_PARAMS_NTB_SUB_ELT_ID */
+ uint8 len;
+ uint8 info[DOT11_FTM_NTB_SUBELMT_FIXED_SIZE];
+} BWL_POST_PACKED_STRUCT;
+typedef struct dot11_ftm_ntb_subelmt dot11_ftm_ntb_subelmt_t;
+
+/* FTM TB specific sub-element */
+#define DOT11_FTM_TB_SUBELMT_FIXED_SIZE 4u
+BWL_PRE_PACKED_STRUCT struct dot11_ftm_tb_subelmt {
+ uint8 id; /* RANGING_PARAMS_TB_SUB_ELT_ID */
+ uint8 len;
+ uint8 info[DOT11_FTM_TB_SUBELMT_FIXED_SIZE];
+ uint8 aw_elmts[]; /* AW elements */
+} BWL_POST_PACKED_STRUCT;
+typedef struct dot11_ftm_tb_subelmt dot11_ftm_tb_subelmt_t;
+
+/* FTM ISTA availability window element */
+BWL_PRE_PACKED_STRUCT struct dot11_ftm_ista_aw {
+ uint8 id; /* 255 */
+ uint8 len;
+ uint8 ext_id; /* EXT_MNG_ISTA_AVAIL_WINDOW_ID */
+ uint16 count;
+ uint8 bitmap[];
+} BWL_POST_PACKED_STRUCT;
+typedef struct dot11_ftm_ista_aw dot11_ftm_ista_aw_t;
+#define DOT11_FTM_ISTA_AW_MIN_LEN \
+ (sizeof(dot11_ftm_ista_aw_t) - OFFSETOF(dot11_ftm_ista_aw_t, ext_id))
+
+/* FTM RSTA availability window element */
+BWL_PRE_PACKED_STRUCT struct dot11_ftm_rsta_aw {
+ uint8 id; /* 255 */
+ uint8 len;
+ uint8 ext_id; /* EXT_MNG_RSTA_AVAIL_WINDOW_ID */
+ uint8 hdr;
+ uint8 aw_info[]; /* AW info subfields */
+} BWL_POST_PACKED_STRUCT;
+typedef struct dot11_ftm_rsta_aw dot11_ftm_rsta_aw_t;
+#define DOT11_FTM_RSTA_AW_MIN_LEN \
+ (sizeof(dot11_ftm_rsta_aw_t) - OFFSETOF(dot11_ftm_rsta_aw_t, ext_id))
+
+/* FTM Secure LTF sub-element */
+BWL_PRE_PACKED_STRUCT struct dot11_ftm_sltf_subelmt {
+ uint8 id; /* RANGING_PARAMS_STLF_SUB_ELT_ID */
+ uint8 len;
+ uint8 info;
+} BWL_POST_PACKED_STRUCT;
+typedef struct dot11_ftm_sltf_subelmt dot11_ftm_sltf_subelmt_t;
+#define DOT11_FTM_SLTF_SUBELMT_LEN \
+ (sizeof(dot11_ftm_sltf_subelmt_t) - OFFSETOF(dot11_ftm_sltf_subelmt_t, info))
+
+/* FTM Secure LTF parameters element */
+#define DOT11_FTM_SLTF_PARAMS_SLTF_COUNTER_LEN 6u
+#define DOT11_FTM_SLTF_PARAMS_SAC_LEN 2u
+BWL_PRE_PACKED_STRUCT struct dot11_ftm_sltf_params {
+ uint8 id; /* 255 */
+ uint8 len;
+ uint8 ext_id; /* EXT_MNG_SLTF_PARAMS_ID */
+ uint8 sltf_counter[DOT11_FTM_SLTF_PARAMS_SLTF_COUNTER_LEN];
+ uint8 validation_sac[DOT11_FTM_SLTF_PARAMS_SAC_LEN];
+ uint8 measurement_sac[DOT11_FTM_SLTF_PARAMS_SAC_LEN];
+ uint8 meas_result_ltf_offset;
+} BWL_POST_PACKED_STRUCT;
+typedef struct dot11_ftm_sltf_params dot11_ftm_sltf_params_t;
+#define DOT11_FTM_SLTF_PARAMS_LEN \
+ (sizeof(dot11_ftm_sltf_params_t) - OFFSETOF(dot11_ftm_sltf_params_t, ext_id))
+
+BWL_PRE_PACKED_STRUCT struct dot11_ftm_ranging_ndpa {
+ uint16 fc; /* frame control */
+ uint16 durid; /* duration/ID */
+ struct ether_addr ra; /* receiver address */
+ struct ether_addr ta; /* transmitter address */
+ uint8 dialog_token; /* sounding dialog token */
+} BWL_POST_PACKED_STRUCT;
+typedef struct dot11_ftm_ranging_ndpa dot11_ftm_ranging_ndpa_t;
+
+typedef struct dot11_ftm_sltf_subelmt dot11_ftm_sec_ltf_subie_params_t;
+#define DOT11_FTM_SLTF_PARAMS_SUB_IE_LEN (sizeof(dot11_ftm_sec_ltf_subie_params_t))
+
+#define DOT11_FTM_RANGING_CMN_PARAM_SIZE DOT11_FTM_RANGING_PARAMS_FIXED_SIZE
#define DOT11_FTM_CMN_RANGING_PARAMS_IE_LEN (sizeof(dot11_ftm_ranging_params_t) - TLV_EXT_HDR_LEN)
/* FTM NTB specific */
@@ -5563,7 +5206,6 @@
uint8 info[6];
} BWL_POST_PACKED_STRUCT;
typedef struct dot11_ftm_ntb_params dot11_ftm_ntb_params_t;
-
#define DOT11_FTM_NTB_PARAMS_SUB_IE_LEN (sizeof(dot11_ftm_ntb_params_t))
#define DOT11_FTM_NTB_PARAMS_IE_LEN (DOT11_FTM_CMN_RANGING_PARAMS_IE_LEN + \
DOT11_FTM_NTB_PARAMS_SUB_IE_LEN)
@@ -5574,7 +5216,6 @@
uint8 len;
uint8 info[]; /* variable length */
} BWL_POST_PACKED_STRUCT;
-
typedef struct dot11_ftm_tb_params dot11_ftm_tb_params_t;
#define DOT11_FTM_TB_PARAMS_IE_LEN sizeof(dot11_ftm_tb_params_t)
@@ -5586,7 +5227,6 @@
*/
uint8 info[];
} BWL_POST_PACKED_STRUCT;
-
typedef struct dot11_ftm_tb_avail_window dot11_ftm_tb_avail_window_t;
#define DOT11_FTM_TB_AVAIL_WINDOW_HDR_LEN sizeof(dot11_ftm_tb_avail_window_t)
@@ -5597,7 +5237,7 @@
uint8 info[11];
} BWL_POST_PACKED_STRUCT;
typedef struct dot11_ftm_sec_ltf_params dot11_ftm_sec_ltf_params_t;
-#define DOT11_FTM_SEC_LTF_PARAMS_IE_LEN (sizeof(dot11_ftm_sec_ltf_params_t) - 3)
+#define DOT11_FTM_SEC_LTF_PARAMS_IE_LEN (sizeof(dot11_ftm_sec_ltf_params_t) - TLV_EXT_HDR_LEN)
#define FTM_PARAMS_FIELD(_p, _off, _mask, _shift) (((_p)->info[(_off)] & (_mask)) >> (_shift))
#define FTM_PARAMS_SET_FIELD(_p, _off, _mask, _shift, _val) do {\
@@ -5788,50 +5428,6 @@
FTM_PARAMS_CHAN_INFO_MAX = 63
};
-/* tag_ID/length/value_buffer tuple */
-typedef BWL_PRE_PACKED_STRUCT struct {
- uint8 id;
- uint8 len;
- uint8 data[1];
-} BWL_POST_PACKED_STRUCT ftm_vs_tlv_t;
-
-BWL_PRE_PACKED_STRUCT struct dot11_ftm_vs_ie {
- uint8 id; /* DOT11_MNG_VS_ID */
- uint8 len; /* length following */
- uint8 oui[3]; /* BRCM_PROP_OUI (or Customer) */
- uint8 sub_type; /* BRCM_FTM_IE_TYPE (or Customer) */
- uint8 version;
- ftm_vs_tlv_t tlvs[BCM_FLEX_ARRAY];
-} BWL_POST_PACKED_STRUCT;
-typedef struct dot11_ftm_vs_ie dot11_ftm_vs_ie_t;
-
-/* same as payload of dot11_ftm_vs_ie.
-* This definition helps in having struct access
-* of pay load while building FTM VS IE from other modules(NAN)
-*/
-BWL_PRE_PACKED_STRUCT struct dot11_ftm_vs_ie_pyld {
- uint8 sub_type; /* BRCM_FTM_IE_TYPE (or Customer) */
- uint8 version;
- ftm_vs_tlv_t tlvs[BCM_FLEX_ARRAY];
-} BWL_POST_PACKED_STRUCT;
-typedef struct dot11_ftm_vs_ie_pyld dot11_ftm_vs_ie_pyld_t;
-
-/* ftm vs api version */
-#define BCM_FTM_VS_PARAMS_VERSION 0x01
-
-/* ftm vendor specific information tlv types */
-enum {
- FTM_VS_TLV_NONE = 0,
- FTM_VS_TLV_REQ_PARAMS = 1, /* additional request params (in FTM_REQ) */
- FTM_VS_TLV_MEAS_INFO = 2, /* measurement information (in FTM_MEAS) */
- FTM_VS_TLV_SEC_PARAMS = 3, /* security parameters (in either) */
- FTM_VS_TLV_SEQ_PARAMS = 4, /* toast parameters (FTM_REQ, BRCM proprietary) */
- FTM_VS_TLV_MF_BUF = 5, /* multi frame buffer - may span ftm vs ie's */
- FTM_VS_TLV_TIMING_PARAMS = 6, /* timing adjustments */
- FTM_VS_TLV_MF_STATS_BUF = 7 /* multi frame statistics buffer */
- /* add additional types above */
-};
-
/* the following definitions are *DEPRECATED* and moved to implementation files. They
* are retained here because previous (May 2016) some branches use them
*/
@@ -5841,7 +5437,6 @@
#define FTM_TPK_RI_RR_LEN_SECURE_2_0 28
#define FTM_TPK_RI_PHY_LEN 7u
#define FTM_TPK_RR_PHY_LEN 7u
-#define FTM_TPK_DATA_BUFFER_LEN 88u
#define FTM_TPK_LEN_SECURE_2_0 64u
#define FTM_TPK_RI_PHY_LEN_SECURE_2_0 14u
#define FTM_TPK_RR_PHY_LEN_SECURE_2_0 14u
@@ -5864,27 +5459,17 @@
#define FTM_TPK_RI_PHY_LEN_SECURE_2_0_20MHZ 14u
#define FTM_TPK_RI_PHY_LEN_SECURE_2_0_80MHZ 31u
-#define FTM_TPK_RR_PHY_LEN_SECURE_2_0_80MHZ 31u
#define FTM_TPK_RI_PHY_LEN_FROM_CHANSPEC(chanspec) \
(CHSPEC_IS20((chanspec)) ? FTM_TPK_RI_PHY_LEN_SECURE_2_0_20MHZ : \
FTM_TPK_RI_PHY_LEN_SECURE_2_0_80MHZ)
#define FTM_TPK_RR_PHY_LEN_SECURE_2_0_20MHZ 14u
+#define FTM_TPK_RR_PHY_LEN_SECURE_2_0_80MHZ 31u
#define FTM_TPK_RR_PHY_LEN_FROM_CHANSPEC(chanspec) \
(CHSPEC_IS20((chanspec)) ? FTM_TPK_RR_PHY_LEN_SECURE_2_0_20MHZ : \
FTM_TPK_RR_PHY_LEN_SECURE_2_0_80MHZ)
-
-BWL_PRE_PACKED_STRUCT struct dot11_ftm_vs_params {
- uint8 id; /* DOT11_MNG_VS_ID */
- uint8 len;
- uint8 oui[3]; /* Proprietary OUI, BRCM_PROP_OUI */
- uint8 bcm_vs_id;
- ftm_vs_tlv_t ftm_tpk_ri_rr[BCM_FLEX_ARRAY]; /* ftm_TPK_ri_rr place holder */
-} BWL_POST_PACKED_STRUCT;
-typedef struct dot11_ftm_vs_params dot11_ftm_vs_tpk_ri_rr_params_t;
-#define DOT11_FTM_VS_LEN (sizeof(dot11_ftm_vs_tpk_ri_rr_params_t) - TLV_HDR_LEN)
/* end *DEPRECATED* ftm definitions */
BWL_PRE_PACKED_STRUCT struct dot11_ftm_sync_info {
@@ -6126,27 +5711,6 @@
/* QoS map */
#define QOS_MAP_FIXED_LENGTH (8 * 2) /* DSCP ranges fixed with 8 entries */
-/* BCM proprietary IE type for AIBSS */
-#define BCM_AIBSS_IE_TYPE 56
-
-/* BCM proprietary flag type for WL_DISCO_VSIE */
-#define SSE_OUI "\x00\x00\xF0"
-#define VENDOR_ENTERPRISE_STA_OUI_TYPE 0x22
-#define MAX_VSIE_DISASSOC (1)
-#define DISCO_VSIE_LEN 0x09u
-
-/* Single PMK IE */
-#define CCX_SPMK_TYPE 3 /* CCX Extended Cap IE type for SPMK */
-/* CCX Extended Capability IE */
-BWL_PRE_PACKED_STRUCT struct ccx_spmk_cap_ie {
- uint8 id; /* 221, DOT11_MNG_PROPR_ID */
- uint8 len;
- uint8 oui[DOT11_OUI_LEN]; /* 00:40:96, CISCO_AIRONET_OUI */
- uint8 type; /* 11 */
- uint8 cap;
-} BWL_POST_PACKED_STRUCT;
-typedef struct ccx_spmk_cap_ie ccx_spmk_cap_ie_t;
-
/* OWE definitions */
/* ID + len + OUI + OI type + BSSID + SSID_len */
#define OWE_TRANS_MODE_IE_FIXED_LEN 13u
@@ -6160,26 +5724,13 @@
} BWL_POST_PACKED_STRUCT;
typedef struct supp_op_classes_ie supp_op_classes_ie_t;
-/* WPA3 Transition Mode bits */
-#define TRANSISION_MODE_WPA3_PSK BCM_BIT(0)
-#define TRANSITION_MODE_WPA3_PSK BCM_BIT(0)
-#define TRANSITION_MODE_SAE_PK BCM_BIT(1)
-#define TRANSITION_MODE_WPA3_ENTERPRISE BCM_BIT(2)
-#define TRANSITION_MODE_ENHANCED_OPEN BCM_BIT(3)
-
-#define TRANSITION_MODE_SUPPORTED_MASK (\
- TRANSITION_MODE_WPA3_PSK | \
- TRANSITION_MODE_SAE_PK | \
- TRANSITION_MODE_WPA3_ENTERPRISE | \
- TRANSITION_MODE_ENHANCED_OPEN)
-
/* 11az d2.5 table 9-92 */
#define DOT11_PASN_PARAMS_EXT_ID 100u
#define DOT11_MNG_PASN_PARAMS (DOT11_MNG_ID_EXT_ID + \
DOT11_PASN_PARAMS_EXT_ID)
-#define PASN_PARAMS_CTRL_CBINFO_PRESENT BCM_BIT(0)
-#define PASN_PARAMS_CTRL_GROUP_KEY_PRESENT BCM_BIT(1u)
+#define PASN_PARAMS_CTRL_CBINFO_PRESENT (1u << 0)
+#define PASN_PARAMS_CTRL_GROUP_KEY_PRESENT (1u << 1)
enum {
PASN_WRAPPED_NO_DATA = 0,
@@ -6218,21 +5769,45 @@
typedef union pasn_params_cbinfo_field pasn_params_cbinfo_field_t;
BWL_PRE_PACKED_STRUCT struct pasn_params_group_key {
- uint16 group_id; /* IANA id of Finite Cyclic Group */
- uint8 len; /* Public key length */
- uint8 key[]; /* public key encoded using RFC 5480 conventions */
+ uint16 group_id; /* IANA id of Finite Cyclic Group */
+ uint8 len; /* Public key length */
+ uint8 key[]; /* public key encoded using RFC 5480 conventions */
} BWL_POST_PACKED_STRUCT;
typedef struct pasn_params_group_key pasn_params_group_key_t;
/* MIC ie */
BWL_PRE_PACKED_STRUCT struct mic_ie {
- uint8 id; /* IE ID: DOT11_MNG_MIE_ID */
- uint8 len; /* IE length */
- uint8 mic[]; /* mic: 16 or 24 octets */
+ uint8 id; /* IE ID: DOT11_MNG_MIE_ID */
+ uint8 len; /* IE length */
+ uint8 mic[]; /* mic: 16 or 24 octets */
} BWL_POST_PACKED_STRUCT;
typedef struct mic_ie mic_ie_t;
+/* Requset IE */
+BWL_PRE_PACKED_STRUCT struct dot11_req_ie {
+ uint8 id; /* DOT11_MNG_REQUEST_ID */
+ uint8 len;
+ uint8 ids[]; /* requested element IDs */
+} BWL_POST_PACKED_STRUCT;
+typedef struct dot11_req_ie dot11_req_ie_t;
+
+/* Extended Requset IE */
+BWL_PRE_PACKED_STRUCT struct dot11_ext_req_ie {
+ uint8 id; /* DOT11_MNG_ID_EXT_ID */
+ uint8 len;
+ uint8 id_ext; /* element ID extension */
+ uint8 reqd_id; /* requested element ID */
+ uint8 id_exts[]; /* requested element ID extensions */
+} BWL_POST_PACKED_STRUCT;
+typedef struct dot11_ext_req_ie dot11_ext_req_ie_t;
+
/* This marks the end of a packed structure section. */
#include <packed_section_end.h>
+/* Include these header files here for compatibility */
+#include "802.11wfa.h"
+#include "802.11wapi.h"
+#include "802.11brcm.h"
+#include "802.11cust.h"
+
#endif /* _802_11_H_ */
diff --git a/include/802.11ah.h b/include/802.11ah.h
index c2b505c..6e30f3a 100644
--- a/include/802.11ah.h
+++ b/include/802.11ah.h
@@ -2,7 +2,7 @@
* Basic types and constants relating to 802.11ah standard.
* This is a portion of 802.11ah definition. The rest are in 802.11.h.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -19,7 +19,7 @@
* modifications of the software.
*
*
- * <<Broadcom-WL-IPTag/Open:>>
+ * <<Broadcom-WL-IPTag/Dual:>>
*/
#ifndef _802_11ah_h_
diff --git a/include/802.11ax.h b/include/802.11ax.h
index 0515f25..d98d54d 100644
--- a/include/802.11ax.h
+++ b/include/802.11ax.h
@@ -2,7 +2,7 @@
* Basic types and constants relating to 802.11ax/HE STA
* This is a portion of 802.11ax definition. The rest are in 802.11.h.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -441,6 +441,12 @@
#define HE_MCS_CODE_SIZE 2u /* num bits */
#define HE_MCS_CODE_MASK 0x3u /* mask for 1-stream */
+/* Whenever SSID is not known and short ssid is included in the
+* 6g probe request SSID element contains one octet value
+* 128 in the SSID element
+*/
+#define WLC_SSID_VAL_IN_SHORT_SSID 128u
+
/* Defines for The Max HE MCS For n SS subfield (where n = 1, ..., 8) */
#define HE_MCS_MAP_NSS_MAX 8u /* Max number of streams possible */
#define HE_MCS_NSS_SET_MASK 0xffffu /* Field is to be 16 bits long */
@@ -647,10 +653,12 @@
#define HE_6G_OP_CTL_REG_INFO(ctl) \
((ctl & HE_6G_CTL_REG_INFO_MASK) >> HE_6G_CTL_REG_INFO_SHIFT)
-#define HE_6G_OP_REG_INFO_LOW_PWR 0u /* INDOOR Low Power */
-#define HE_6G_OP_REG_INFO_STD_PWR 1u /* Standard Power */
-#define HE_6G_OP_REG_INFO_VLP_PWR 2u /* Very low Power (Not yet defined in spec) */
-#define HE_6G_OP_REG_INFO_CAT_MAX 2u /* Category reserved */
+#define HE_6G_OP_REG_INFO_LOW_PWR 0u /* INDOOR Low Power */
+#define HE_6G_OP_REG_INFO_STD_PWR 1u /* Standard Power */
+#define HE_6G_OP_REG_INFO_VLP_PWR 2u /* Very low Power */
+#define HE_6G_OP_REG_INFO_INDR_ENAB 3u /* Indoor Enabled */
+#define HE_6G_OP_REG_INFO_INDR_STD_PWR 4u /* Indoor Standard Power */
+#define HE_6G_OP_REG_INFO_CAT_MAX 5u /* Category reserved */
#define HE_6G_CTL_DUP_BCN_SHIFT 0x02u
#define HE_6G_OP_CTL_DUP_BCN(ctl) \
diff --git a/include/802.11brcm.h b/include/802.11brcm.h
new file mode 100644
index 0000000..1c413fc
--- /dev/null
+++ b/include/802.11brcm.h
@@ -0,0 +1,346 @@
+/*
+ * Broadcom proprietary types and constants relating to 802.11
+ *
+ * Copyright (C) 2022, Broadcom.
+ *
+ * Unless you and Broadcom execute a separate written software license
+ * agreement governing use of this software, this software is licensed to you
+ * under the terms of the GNU General Public License version 2 (the "GPL"),
+ * available at http://www.broadcom.com/licenses/GPLv2.php, with the
+ * following added to such license:
+ *
+ * As a special exception, the copyright holders of this software give you
+ * permission to link this software with independent modules, and to copy and
+ * distribute the resulting executable under terms of your choice, provided that
+ * you also meet, for each linked independent module, the terms and conditions of
+ * the license of that module. An independent module is a module which is not
+ * derived from this software. The special exception does not apply to any
+ * modifications of the software.
+ *
+ *
+ * <<Broadcom-WL-IPTag/Dual:>>
+ */
+
+#ifndef _802_11brcm_h_
+#define _802_11brcm_h_
+
+#ifndef _TYPEDEFS_H_
+#include <typedefs.h>
+#endif
+
+#ifndef _NET_ETHERNET_H_
+#include <ethernet.h>
+#endif
+
+/* This marks the start of a packed structure section. */
+#include <packed_section_start.h>
+
+/**
+ * RWL wifi protocol: The Vendor Specific Action frame is defined for vendor-specific signaling
+ * category+OUI+vendor specific content ( this can be variable)
+ */
+BWL_PRE_PACKED_STRUCT struct dot11_action_wifi_vendor_specific {
+ uint8 category;
+ uint8 OUI[3];
+ uint8 type;
+ uint8 subtype;
+ uint8 data[1040];
+} BWL_POST_PACKED_STRUCT;
+typedef struct dot11_action_wifi_vendor_specific dot11_action_wifi_vendor_specific_t;
+
+#define BCM_ACTION_OUI_BYTE0 0x00
+#define BCM_ACTION_OUI_BYTE1 0x90
+#define BCM_ACTION_OUI_BYTE2 0x4c
+
+BWL_PRE_PACKED_STRUCT struct dot11_brcm_extch {
+ uint8 id; /* IE ID, 221, DOT11_MNG_PROPR_ID */
+ uint8 len; /* IE length */
+ uint8 oui[3]; /* Proprietary OUI, BRCM_PROP_OUI */
+ uint8 type; /* type indicates what follows */
+ uint8 extch;
+} BWL_POST_PACKED_STRUCT;
+typedef struct dot11_brcm_extch dot11_brcm_extch_ie_t;
+
+#define BRCM_EXTCH_IE_LEN 5
+
+/* OUI for BRCM proprietary IE */
+#define BRCM_PROP_OUI "\x00\x90\x4C" /* Broadcom proprietary OUI */
+
+/* Broadcom Proprietary OUI type list. Please update below page when adding a new type.
+ * Twiki https://hwnbu-twiki.lvn.broadcom.net/bin/view/Mwgroup/WlDriverIOVars?topic=WlBrcmPropIE
+ */
+/* The following BRCM_PROP_OUI types are currently in use (defined in
+ * relevant subsections). Each of them will be in a separate proprietary(221) IE
+ * #define SES_VNDR_IE_TYPE 1 (defined in src/ses/shared/ses.h)
+ * #define BRCM_SYSCAP_IE_TYPE 3
+ * #define WET_TUNNEL_IE_TYPE 3
+ * #define ULB_BRCM_PROP_IE_TYPE 91
+ * #define SDB_BRCM_PROP_IE_TYPE 92
+ * #define BCM_RESERVED_ACCESS 93 (Reserved, definition pending)
+ */
+#define RWL_WIFI_DEFAULT 0
+#define DPT_IE_TYPE 2
+#define VHT_FEATURES_IE_TYPE 4
+#define RWL_WIFI_FIND_MY_PEER 9 /* Used while finding server */
+#define RWL_WIFI_FOUND_PEER 10 /* Server response to the client */
+#define PROXD_IE_TYPE 11 /* Wifi proximity action frame type */
+#define BRCM_FTM_IE_TYPE 14
+#define HT_CAP_IE_TYPE 51 /* used in prop IE 221 only */
+#define HT_ADD_IE_TYPE 52 /* faked out as current spec is illegal */
+#define BRCM_EXTCH_IE_TYPE 53 /* 802.11n ID not yet assigned */
+#define MEMBER_OF_BRCM_PROP_IE_TYPE 54 /* used in prop IE 221 only */
+#define RELMCAST_BRCM_PROP_IE_TYPE 55 /* used in prop IE 221 only */
+/* BCM proprietary IE type for AIBSS */
+#define BCM_AIBSS_IE_TYPE 56
+/*
+ * This BRCM_PROP_OUI types is intended for use in events to embed additional
+ * data, and would not be expected to appear on the air -- but having an IE
+ * format allows IE frame data with extra data in events in that allows for
+ * more flexible parsing.
+ */
+#define BRCM_EVT_WL_BSS_INFO 64
+#define RWL_ACTION_WIFI_FRAG_TYPE 85 /* Fragment indicator for receiver */
+#define BTC_INFO_BRCM_PROP_IE_TYPE 90
+
+/* Action frame type */
+#define PROXD_AF_TYPE 11 /* Wifi proximity action frame type */
+#define BRCM_RELMACST_AF_TYPE 12 /* RMC action frame type */
+/* Action frame type for FTM Initiator Report */
+#define BRCM_FTM_VS_AF_TYPE 14
+
+enum {
+ BRCM_FTM_VS_INITIATOR_RPT_SUBTYPE = 1, /* FTM Initiator Report */
+ BRCM_FTM_VS_COLLECT_SUBTYPE = 2, /* FTM Collect debug protocol */
+};
+
+/**
+ * Following is the generic structure for brcm_prop_ie (uses BRCM_PROP_OUI).
+ * DPT uses this format with type set to DPT_IE_TYPE
+ */
+#ifdef NEW_BRCM_PROP_IE
+BWL_PRE_PACKED_STRUCT struct brcm_prop_ie_s {
+ uint8 id; /* IE ID, 221, DOT11_MNG_PROPR_ID */
+ uint8 len; /* IE length */
+ uint8 oui[3]; /* Proprietary OUI, BRCM_PROP_OUI */
+ uint8 type; /* type of this IE */
+} BWL_POST_PACKED_STRUCT;
+typedef struct brcm_prop_ie_s brcm_prop_ie_t;
+#else
+typedef struct dpt_brcm_prop_ie_s brcm_prop_ie_t;
+#endif /* NEW_BRCM_PROP_IE */
+#define BRCM_PROP_IE_LEN 6 /* len of fixed part of brcm_prop ie */
+
+/**
+ * Following is the generic structure for brcm_prop_ie (uses BRCM_PROP_OUI).
+ * DPT uses this format with type set to DPT_IE_TYPE
+ */
+BWL_PRE_PACKED_STRUCT struct dpt_brcm_prop_ie_s {
+ uint8 id; /* IE ID, 221, DOT11_MNG_PROPR_ID */
+ uint8 len; /* IE length */
+ uint8 oui[3]; /* Proprietary OUI, BRCM_PROP_OUI */
+ uint8 type; /* type of this IE */
+ uint16 cap;
+} BWL_POST_PACKED_STRUCT;
+typedef struct brcm_prop_ie_s dpt_brcm_prop_ie_t;
+
+/* BRCM OUI: Used in the proprietary(221) IE in all broadcom devices */
+#define BRCM_OUI "\x00\x10\x18" /* Broadcom OUI */
+
+/** BRCM info element */
+BWL_PRE_PACKED_STRUCT struct brcm_ie {
+ uint8 id; /* IE ID, 221, DOT11_MNG_PROPR_ID */
+ uint8 len; /* IE length */
+ uint8 oui[3]; /* Proprietary OUI, BRCM_OUI */
+ uint8 ver; /* type/ver of this IE */
+ uint8 assoc; /* # of assoc STAs */
+ uint8 flags; /* misc flags */
+ uint8 flags1; /* misc flags */
+ uint16 amsdu_mtu_pref; /* preferred A-MSDU MTU */
+ uint8 flags2; /* DTPC Cap flags */
+} BWL_POST_PACKED_STRUCT;
+typedef struct brcm_ie brcm_ie_t;
+#define BRCM_IE_LEN 12u /* BRCM IE length */
+#define BRCM_IE_VER 2u /* BRCM IE version */
+#define BRCM_IE_LEGACY_AES_VER 1u /* BRCM IE legacy AES version */
+
+/* brcm_ie flags */
+#define BRF_ABCAP 0x01 /* afterburner is obsolete, defined for backward compat */
+#define BRF_ABRQRD 0x02 /* afterburner is obsolete, defined for backward compat */
+#define BRF_LZWDS 0x04 /* lazy wds enabled */
+#define BRF_BLOCKACK 0x08 /* BlockACK capable */
+#define BRF_ABCOUNTER_MASK 0xf0 /* afterburner is obsolete, defined for backward compat */
+#define BRF_PROP_11N_MCS 0x10 /* re-use afterburner bit */
+#define BRF_MEDIA_CLIENT 0x20 /* re-use afterburner bit to indicate media client device */
+
+/**
+ * Support for Broadcom proprietary HT MCS rates. Re-uses afterburner bits since
+ * afterburner is not used anymore. Checks for BRF_ABCAP to stay compliant with 'old'
+ * images in the field.
+ */
+#define GET_BRF_PROP_11N_MCS(brcm_ie) \
+ (!((brcm_ie)->flags & BRF_ABCAP) && ((brcm_ie)->flags & BRF_PROP_11N_MCS))
+
+/* brcm_ie flags1 */
+#define BRF1_AMSDU 0x01 /* A-MSDU capable */
+#define BRF1_WNM 0x02 /* WNM capable */
+#define BRF1_WMEPS 0x04 /* AP is capable of handling WME + PS w/o APSD */
+#define BRF1_PSOFIX 0x08 /* AP has fixed PS mode out-of-order packets */
+#define BRF1_RX_LARGE_AGG 0x10 /* device can rx large aggregates */
+#define BRF1_RFAWARE_DCS 0x20 /* RFAWARE dynamic channel selection (DCS) */
+#define BRF1_SOFTAP 0x40 /* Configure as Broadcom SOFTAP */
+#define BRF1_DWDS 0x80 /* DWDS capable */
+
+/* brcm_ie flags2 */
+#define BRF2_DTPC_TX 0x01u /* DTPC: DTPC TX Cap */
+#define BRF2_DTPC_RX 0x02u /* DTPC: DTPC RX Cap */
+#define BRF2_DTPC_TX_RX 0x03u /* DTPC: Enable Both DTPC TX and RX Cap */
+#define BRF2_DTPC_NONBF 0x04u /* DTPC: Enable DTPC for NON-TXBF */
+#define BRF2_TWT_RESP_CAP 0x08u /* TWT responder Cap for Brcm Softap
+ * only brcm sta parse this
+ */
+#define BRF2_TWT_REQ_CAP 0x10u /* TWT requester Cap for BRCM STA
+ * only brcm softap parse this
+ */
+
+/** BRCM PROP DEVICE PRIMARY MAC ADDRESS IE */
+BWL_PRE_PACKED_STRUCT struct member_of_brcm_prop_ie {
+ uchar id;
+ uchar len;
+ uchar oui[3];
+ uint8 type; /* type indicates what follows */
+ struct ether_addr ea; /* Device Primary MAC Adrress */
+} BWL_POST_PACKED_STRUCT;
+typedef struct member_of_brcm_prop_ie member_of_brcm_prop_ie_t;
+
+#define MEMBER_OF_BRCM_PROP_IE_LEN 10 /* IE max length */
+#define MEMBER_OF_BRCM_PROP_IE_HDRLEN (sizeof(member_of_brcm_prop_ie_t))
+
+/** BRCM Reliable Multicast IE */
+BWL_PRE_PACKED_STRUCT struct relmcast_brcm_prop_ie {
+ uint8 id;
+ uint8 len;
+ uint8 oui[3];
+ uint8 type; /* type indicates what follows */
+ struct ether_addr ea; /* The ack sender's MAC Adrress */
+ struct ether_addr mcast_ea; /* The multicast MAC address */
+ uint8 updtmo; /* time interval(second) for client to send null packet to report its rssi */
+} BWL_POST_PACKED_STRUCT;
+typedef struct relmcast_brcm_prop_ie relmcast_brcm_prop_ie_t;
+
+/* IE length */
+/* BRCM_PROP_IE_LEN = sizeof(relmcast_brcm_prop_ie_t)-((sizeof (id) + sizeof (len)))? */
+#define RELMCAST_BRCM_PROP_IE_LEN (sizeof(relmcast_brcm_prop_ie_t)-(2*sizeof(uint8)))
+
+/* BRCM BTC IE */
+BWL_PRE_PACKED_STRUCT struct btc_brcm_prop_ie {
+ uint8 id;
+ uint8 len;
+ uint8 oui[3];
+ uint8 type; /* type inidicates what follows */
+ uint32 info;
+} BWL_POST_PACKED_STRUCT;
+typedef struct btc_brcm_prop_ie btc_brcm_prop_ie_t;
+
+#define BRCM_BTC_INFO_TYPE_LEN (sizeof(btc_brcm_prop_ie_t) - (2 * sizeof(uint8)))
+
+/* CAP IE: HT 1.0 spec. simply stole a 802.11 IE, we use our prop. IE until this is resolved */
+/* the capability IE is primarily used to convey this nodes abilities */
+BWL_PRE_PACKED_STRUCT struct ht_prop_cap_ie {
+ uint8 id; /* IE ID, 221, DOT11_MNG_PROPR_ID */
+ uint8 len; /* IE length */
+ uint8 oui[3]; /* Proprietary OUI, BRCM_PROP_OUI */
+ uint8 type; /* type indicates what follows */
+ ht_cap_ie_t cap_ie;
+} BWL_POST_PACKED_STRUCT;
+typedef struct ht_prop_cap_ie ht_prop_cap_ie_t;
+
+#define HT_PROP_IE_OVERHEAD 4 /* overhead bytes for prop oui ie */
+
+/* ADD IE: HT 1.0 spec. simply stole a 802.11 IE, we use our prop. IE until this is resolved */
+/* the additional IE is primarily used to convey the current BSS configuration */
+BWL_PRE_PACKED_STRUCT struct ht_prop_add_ie {
+ uint8 id; /* IE ID, 221, DOT11_MNG_PROPR_ID */
+ uint8 len; /* IE length */
+ uint8 oui[3]; /* Proprietary OUI, BRCM_PROP_OUI */
+ uint8 type; /* indicates what follows */
+ ht_add_ie_t add_ie;
+} BWL_POST_PACKED_STRUCT;
+typedef struct ht_prop_add_ie ht_prop_add_ie_t;
+
+/**
+ * BRCM vht features IE header
+ * The header if the fixed part of the IE
+ * On the 5GHz band this is the entire IE,
+ * on 2.4GHz the VHT IEs as defined in the 802.11ac
+ * specification follows
+ *
+ *
+ * VHT features rates bitmap.
+ * Bit0: 5G MCS 0-9 BW 160MHz
+ * Bit1: 5G MCS 0-9 support BW 80MHz
+ * Bit2: 5G MCS 0-9 support BW 20MHz
+ * Bit3: 2.4G MCS 0-9 support BW 20MHz
+ * Bits:4-7 Reserved for future use
+ *
+ */
+BWL_PRE_PACKED_STRUCT struct vht_features_ie_hdr {
+ uint8 oui[3]; /* Proprietary OUI, BRCM_PROP_OUI */
+ uint8 type; /* type of this IE = 4 */
+ uint8 rate_mask; /* VHT rate mask */
+} BWL_POST_PACKED_STRUCT;
+typedef struct vht_features_ie_hdr vht_features_ie_hdr_t;
+
+/* tag_ID/length/value_buffer tuple */
+typedef BWL_PRE_PACKED_STRUCT struct {
+ uint8 id;
+ uint8 len;
+ uint8 data[1];
+} BWL_POST_PACKED_STRUCT ftm_vs_tlv_t;
+
+BWL_PRE_PACKED_STRUCT struct dot11_ftm_vs_ie {
+ uint8 id; /* DOT11_MNG_VS_ID */
+ uint8 len; /* length following */
+ uint8 oui[3]; /* BRCM_PROP_OUI (or Customer) */
+ uint8 sub_type; /* BRCM_FTM_IE_TYPE (or Customer) */
+ uint8 version;
+ ftm_vs_tlv_t tlvs[BCM_FLEX_ARRAY];
+} BWL_POST_PACKED_STRUCT;
+typedef struct dot11_ftm_vs_ie dot11_ftm_vs_ie_t;
+
+/* same as payload of dot11_ftm_vs_ie.
+* This definition helps in having struct access
+* of pay load while building FTM VS IE from other modules(NAN)
+*/
+BWL_PRE_PACKED_STRUCT struct dot11_ftm_vs_ie_pyld {
+ uint8 sub_type; /* BRCM_FTM_IE_TYPE (or Customer) */
+ uint8 version;
+ ftm_vs_tlv_t tlvs[BCM_FLEX_ARRAY];
+} BWL_POST_PACKED_STRUCT;
+typedef struct dot11_ftm_vs_ie_pyld dot11_ftm_vs_ie_pyld_t;
+
+/* ftm vs api version */
+#define BCM_FTM_VS_PARAMS_VERSION 0x01
+
+/* ftm vendor specific information tlv types */
+enum {
+ FTM_VS_TLV_NONE = 0,
+ FTM_VS_TLV_REQ_PARAMS = 1, /* additional request params (in FTM_REQ) */
+ FTM_VS_TLV_MEAS_INFO = 2, /* measurement information (in FTM_MEAS) */
+ FTM_VS_TLV_SEC_PARAMS = 3, /* security parameters (in either) */
+ FTM_VS_TLV_SEQ_PARAMS = 4, /* toast parameters (FTM_REQ, BRCM proprietary) */
+ FTM_VS_TLV_MF_BUF = 5, /* multi frame buffer - may span ftm vs ie's */
+ FTM_VS_TLV_TIMING_PARAMS = 6, /* timing adjustments */
+ FTM_VS_TLV_MF_STATS_BUF = 7 /* multi frame statistics buffer */
+ /* add additional types above */
+};
+
+/* BCM proprietary flag type for WL_DISCO_VSIE */
+#define SSE_OUI "\x00\x00\xF0"
+#define VENDOR_ENTERPRISE_STA_OUI_TYPE 0x22
+#define MAX_VSIE_DISASSOC (1)
+#define DISCO_VSIE_LEN 0x09u
+
+/* This marks the end of a packed structure section. */
+#include <packed_section_end.h>
+
+#endif /* _802_11brcm_h_ */
diff --git a/include/802.11cust.h b/include/802.11cust.h
new file mode 100644
index 0000000..7cbe2fc
--- /dev/null
+++ b/include/802.11cust.h
@@ -0,0 +1,76 @@
+/*
+ * Customer specific types and constants relating to 802.11
+ *
+ * Copyright (C) 2022, Broadcom.
+ *
+ * Unless you and Broadcom execute a separate written software license
+ * agreement governing use of this software, this software is licensed to you
+ * under the terms of the GNU General Public License version 2 (the "GPL"),
+ * available at http://www.broadcom.com/licenses/GPLv2.php, with the
+ * following added to such license:
+ *
+ * As a special exception, the copyright holders of this software give you
+ * permission to link this software with independent modules, and to copy and
+ * distribute the resulting executable under terms of your choice, provided that
+ * you also meet, for each linked independent module, the terms and conditions of
+ * the license of that module. An independent module is a module which is not
+ * derived from this software. The special exception does not apply to any
+ * modifications of the software.
+ *
+ *
+ * <<Broadcom-WL-IPTag/Dual:>>
+ */
+
+#ifndef _802_11cust_h_
+#define _802_11cust_h_
+
+#ifndef _TYPEDEFS_H_
+#include <typedefs.h>
+#endif
+
+/* This marks the start of a packed structure section. */
+#include <packed_section_start.h>
+
+/* Action frame type for vendor specific action frames */
+#define VS_AF_TYPE 221
+
+#ifdef IBSS_RMC
+/* customer's OUI */
+#define RMC_PROP_OUI "\x00\x16\x32"
+#endif
+
+/* WFA definitions for LEGACY P2P */
+
+#ifndef CISCO_AIRONET_OUI
+#define CISCO_AIRONET_OUI "\x00\x40\x96" /* Cisco AIRONET OUI */
+#endif
+
+/* Single PMK IE */
+#define CCX_SPMK_TYPE 3 /* CCX Extended Cap IE type for SPMK */
+/* CCX Extended Capability IE */
+BWL_PRE_PACKED_STRUCT struct ccx_spmk_cap_ie {
+ uint8 id; /* 221, DOT11_MNG_PROPR_ID */
+ uint8 len;
+ uint8 oui[DOT11_OUI_LEN]; /* 00:40:96, CISCO_AIRONET_OUI */
+ uint8 type; /* 11 */
+ uint8 cap;
+} BWL_POST_PACKED_STRUCT;
+typedef struct ccx_spmk_cap_ie ccx_spmk_cap_ie_t;
+
+/* QoS FastLane IE. */
+BWL_PRE_PACKED_STRUCT struct ccx_qfl_ie {
+ uint8 id; /* 221, DOT11_MNG_VS_ID */
+ uint8 length; /* 5 */
+ uint8 oui[3]; /* 00:40:96 */
+ uint8 type; /* 11 */
+ uint8 data;
+} BWL_POST_PACKED_STRUCT;
+typedef struct ccx_qfl_ie ccx_qfl_ie_t;
+#define CCX_QFL_IE_TYPE 11
+#define CCX_QFL_ENABLE_SHIFT 5
+#define CCX_QFL_ENALBE (1 << CCX_QFL_ENABLE_SHIFT)
+
+/* This marks the end of a packed structure section. */
+#include <packed_section_end.h>
+
+#endif /* _802_11cust_h_ */
diff --git a/include/802.11s.h b/include/802.11s.h
index a2c6b5b..4295765 100644
--- a/include/802.11s.h
+++ b/include/802.11s.h
@@ -1,7 +1,7 @@
/*
* Fundamental types and constants relating to 802.11s Mesh
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/frag.h b/include/802.11wapi.h
similarity index 61%
copy from frag.h
copy to include/802.11wapi.h
index c5127ab..abbe5c0 100644
--- a/frag.h
+++ b/include/802.11wapi.h
@@ -1,8 +1,7 @@
/*
- * IE/TLV (de)fragmentation declarations/definitions for
- * Broadcom 802.11abgn Networking Device Driver
+ * WAPI specific types and constants relating to 802.11
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -20,13 +19,22 @@
*
*
* <<Broadcom-WL-IPTag/Dual:>>
- *
*/
-#ifndef __FRAG_H__
-#define __FRAG_H__
+#ifndef _802_11wapi_h_
+#define _802_11wapi_h_
-int bcm_tlv_dot11_frag_tot_len(const void *buf, uint buf_len,
- uint8 id, bool id_ext, uint *ie_len);
+#ifdef BCMWAPI_WAI
+#define WAPI_IE_MIN_LEN 20 /* WAPI IE min length */
+#define WAPI_VERSION 1 /* WAPI version */
+#define WAPI_VERSION_LEN 2 /* WAPI version length */
+#define WAPI_OUI "\x00\x14\x72" /* WAPI OUI */
+#define WAPI_OUI_LEN DOT11_OUI_LEN /* WAPI OUI length */
+#endif /* BCMWAPI_WAI */
-#endif /* __FRAG_H__ */
+#ifdef BCMWAPI_WPI
+#define SMS4_KEY_LEN 16
+#define SMS4_WPI_CBC_MAC_LEN 16
+#endif
+
+#endif /* _802_11wapi_h_ */
diff --git a/include/802.11wfa.h b/include/802.11wfa.h
new file mode 100644
index 0000000..0007f09
--- /dev/null
+++ b/include/802.11wfa.h
@@ -0,0 +1,234 @@
+/*
+ * WFA specific types and constants relating to 802.11
+ *
+ * Copyright (C) 2022, Broadcom.
+ *
+ * Unless you and Broadcom execute a separate written software license
+ * agreement governing use of this software, this software is licensed to you
+ * under the terms of the GNU General Public License version 2 (the "GPL"),
+ * available at http://www.broadcom.com/licenses/GPLv2.php, with the
+ * following added to such license:
+ *
+ * As a special exception, the copyright holders of this software give you
+ * permission to link this software with independent modules, and to copy and
+ * distribute the resulting executable under terms of your choice, provided that
+ * you also meet, for each linked independent module, the terms and conditions of
+ * the license of that module. An independent module is a module which is not
+ * derived from this software. The special exception does not apply to any
+ * modifications of the software.
+ *
+ *
+ * <<Broadcom-WL-IPTag/Dual:>>
+ */
+
+#ifndef _802_11wfa_h_
+#define _802_11wfa_h_
+
+#ifndef _TYPEDEFS_H_
+#include <typedefs.h>
+#endif
+
+#ifndef _NET_ETHERNET_H_
+#include <ethernet.h>
+#endif
+
+/* This marks the start of a packed structure section. */
+#include <packed_section_start.h>
+
+/* WME Elements */
+#define WME_OUI "\x00\x50\xf2" /* WME OUI */
+#define WME_OUI_LEN 3
+#define WME_OUI_TYPE 2 /* WME type */
+#define WME_TYPE 2 /* WME type, deprecated */
+#define WME_SUBTYPE_IE 0 /* Information Element */
+#define WME_SUBTYPE_PARAM_IE 1 /* Parameter Element */
+#define WME_SUBTYPE_TSPEC 2 /* Traffic Specification */
+#define WME_VER 1 /* WME version */
+
+/** WME Information Element (IE) */
+BWL_PRE_PACKED_STRUCT struct wme_ie {
+ uint8 oui[3];
+ uint8 type;
+ uint8 subtype;
+ uint8 version;
+ uint8 qosinfo;
+} BWL_POST_PACKED_STRUCT;
+typedef struct wme_ie wme_ie_t;
+#define WME_IE_LEN 7 /* WME IE length */
+
+/** WME Parameter Element (PE) */
+BWL_PRE_PACKED_STRUCT struct wme_param_ie {
+ uint8 oui[3];
+ uint8 type;
+ uint8 subtype;
+ uint8 version;
+ uint8 qosinfo;
+ uint8 rsvd;
+ edcf_acparam_t acparam[AC_COUNT];
+} BWL_POST_PACKED_STRUCT;
+typedef struct wme_param_ie wme_param_ie_t;
+#define WME_PARAM_IE_LEN 24 /* WME Parameter IE length */
+
+/* QoS Info field for IE as sent from AP */
+#define WME_QI_AP_APSD_MASK 0x80 /* U-APSD Supported mask */
+#define WME_QI_AP_APSD_SHIFT 7 /* U-APSD Supported shift */
+#define WME_QI_AP_COUNT_MASK 0x0f /* Parameter set count mask */
+#define WME_QI_AP_COUNT_SHIFT 0 /* Parameter set count shift */
+
+/* QoS Info field for IE as sent from STA */
+#define WME_QI_STA_MAXSPLEN_MASK 0x60 /* Max Service Period Length mask */
+#define WME_QI_STA_MAXSPLEN_SHIFT 5 /* Max Service Period Length shift */
+#define WME_QI_STA_APSD_ALL_MASK 0xf /* APSD all AC bits mask */
+#define WME_QI_STA_APSD_ALL_SHIFT 0 /* APSD all AC bits shift */
+#define WME_QI_STA_APSD_BE_MASK 0x8 /* APSD AC_BE mask */
+#define WME_QI_STA_APSD_BE_SHIFT 3 /* APSD AC_BE shift */
+#define WME_QI_STA_APSD_BK_MASK 0x4 /* APSD AC_BK mask */
+#define WME_QI_STA_APSD_BK_SHIFT 2 /* APSD AC_BK shift */
+#define WME_QI_STA_APSD_VI_MASK 0x2 /* APSD AC_VI mask */
+#define WME_QI_STA_APSD_VI_SHIFT 1 /* APSD AC_VI shift */
+#define WME_QI_STA_APSD_VO_MASK 0x1 /* APSD AC_VO mask */
+#define WME_QI_STA_APSD_VO_SHIFT 0 /* APSD AC_VO shift */
+
+/* Default BE ACI value for non-WME connection STA */
+#define NON_EDCF_AC_BE_ACI_STA 0x02
+
+/* WME Action Codes */
+#define WME_ADDTS_REQUEST 0 /* WME ADDTS request */
+#define WME_ADDTS_RESPONSE 1 /* WME ADDTS response */
+#define WME_DELTS_REQUEST 2 /* WME DELTS request */
+
+/* WME Setup Response Status Codes */
+#define WME_ADMISSION_ACCEPTED 0 /* WME admission accepted */
+#define WME_INVALID_PARAMETERS 1 /* WME invalide parameters */
+#define WME_ADMISSION_REFUSED 3 /* WME admission refused */
+
+/* ************* WPA definitions. ************* */
+#define WPA_OUI "\x00\x50\xF2" /* WPA OUI */
+#define WPA_OUI_LEN 3 /* WPA OUI length */
+#define WPA_OUI_TYPE 1
+#define WPA_VERSION 1 /* WPA version */
+#define WPA_VERSION_LEN 2 /* WPA version length */
+
+/* ************* WPA2 definitions. ************* */
+#define WPA2_OUI "\x00\x0F\xAC" /* WPA2 OUI */
+#define WPA2_OUI_LEN 3 /* WPA2 OUI length */
+#define WPA2_VERSION 1 /* WPA2 version */
+#define WPA2_VERSION_LEN 2 /* WAP2 version length */
+#define MAX_RSNE_SUPPORTED_VERSION WPA2_VERSION /* Max supported version */
+
+/* ************* WPS definitions. ************* */
+#define WPS_OUI "\x00\x50\xF2" /* WPS OUI */
+#define WPS_OUI_LEN 3 /* WPS OUI length */
+#define WPS_OUI_TYPE 4
+
+/* ************* TPC definitions. ************* */
+#define TPC_OUI "\x00\x50\xF2" /* TPC OUI */
+#define TPC_OUI_LEN 3 /* TPC OUI length */
+#define TPC_OUI_TYPE 8
+#define WFA_OUI_TYPE_TPC 8 /* deprecated */
+
+/* ************* WFA definitions. ************* */
+#define WFA_OUI "\x50\x6F\x9A" /* WFA OUI */
+#define WFA_OUI_LEN 3 /* WFA OUI length */
+#define WFA_OUI_TYPE_P2P 9
+
+#define P2P_OUI WFA_OUI
+#define P2P_OUI_LEN WFA_OUI_LEN
+#define P2P_OUI_TYPE WFA_OUI_TYPE_P2P
+
+#ifdef WLTDLS
+#define WFA_OUI_TYPE_TPQ 4 /* WFD Tunneled Probe ReQuest */
+#define WFA_OUI_TYPE_TPS 5 /* WFD Tunneled Probe ReSponse */
+#define WFA_OUI_TYPE_WFD 10
+#endif /* WTDLS */
+#define WFA_OUI_TYPE_HS20 0x10
+#define WFA_OUI_TYPE_OSEN 0x12
+#define WFA_OUI_TYPE_NAN 0x13
+#define WFA_OUI_TYPE_MBO 0x16
+#define WFA_OUI_TYPE_MBO_OCE 0x16
+#define WFA_OUI_TYPE_OWE 0x1C
+#define WFA_OUI_TYPE_SAE_PK 0x1F
+#define WFA_OUI_TYPE_TD_INDICATION 0x20
+
+/* WCN */
+#define WCN_OUI "\x00\x50\xf2" /* WCN OUI */
+#define WCN_TYPE 4 /* WCN type */
+
+/* ************* WMM Parameter definitions. ************* */
+#define WMM_OUI "\x00\x50\xF2" /* WNN OUI */
+#define WMM_OUI_LEN 3 /* WMM OUI length */
+#define WMM_OUI_TYPE 2 /* WMM OUT type */
+#define WMM_VERSION 1
+#define WMM_VERSION_LEN 1
+
+/* WMM OUI subtype */
+#define WMM_OUI_SUBTYPE_PARAMETER 1
+#define WMM_PARAMETER_IE_LEN 24
+
+#define SAE_PK_MOD_LEN 32u
+BWL_PRE_PACKED_STRUCT struct dot11_sae_pk_element {
+ uint8 id; /* IE ID, 221, DOT11_MNG_PROPR_ID */
+ uint8 len; /* IE length */
+ uint8 oui[WFA_OUI_LEN]; /* WFA_OUI */
+ uint8 type; /* SAE-PK */
+ uint8 data[SAE_PK_MOD_LEN]; /* Modifier. 32Byte fixed */
+} BWL_POST_PACKED_STRUCT;
+typedef struct dot11_sae_pk_element dot11_sae_pk_element_t;
+
+/* WPA3 Transition Mode bits */
+#define TRANSISION_MODE_WPA3_PSK BCM_BIT(0)
+#define TRANSITION_MODE_WPA3_PSK BCM_BIT(0)
+#define TRANSITION_MODE_SAE_PK BCM_BIT(1)
+#define TRANSITION_MODE_WPA3_ENTERPRISE BCM_BIT(2)
+#define TRANSITION_MODE_ENHANCED_OPEN BCM_BIT(3)
+
+#define TRANSITION_MODE_SUPPORTED_MASK (\
+ TRANSITION_MODE_WPA3_PSK | \
+ TRANSITION_MODE_SAE_PK | \
+ TRANSITION_MODE_WPA3_ENTERPRISE | \
+ TRANSITION_MODE_ENHANCED_OPEN)
+
+/** Transition Disable Indication element */
+BWL_PRE_PACKED_STRUCT struct dot11_tdi_element {
+ uint8 id; /* DOT11_MNG_VS_ID */
+ uint8 len; /* IE length */
+ uint8 oui[3]; /* WFA_OUI */
+ uint8 type; /* WFA_OUI_TYPE_TD_INDICATION */
+ uint8 tdi; /* Transition Disable Indication bitmap */
+} BWL_POST_PACKED_STRUCT;
+typedef struct dot11_tdi_element dot11_tdi_element_t;
+
+#define DOT11_TDI_ELEM_LENGTH sizeof(dot11_tdi_element_t)
+
+/* WiFi OWE transition OUI values */
+#define OWE_TRANS_OUI WFA_OUI /* WiFi OUI 50:6F:9A */
+/* oui_type field identifying the type and version of the OWE transition mode IE. */
+#define OWE_OUI_TYPE WFA_OUI_TYPE_OWE /* OUI Type/Version */
+/* IEEE 802.11 vendor specific information element. */
+#define OWE_IE_ID 0xdd
+
+/* 2.3.1 OWE transition mode IE (WFA OWE spec 1.1) */
+typedef BWL_PRE_PACKED_STRUCT struct wifi_owe_ie_s {
+ uint8 id; /* IE ID: OWE_IE_ID 0xDD */
+ uint8 len; /* IE length */
+ uint8 oui[WFA_OUI_LEN]; /* OWE OUI 50:6F:9A */
+ uint8 oui_type; /* WFA_OUI_TYPE_OWE 0x1A */
+ uint8 attr[]; /* var len attributes */
+} wifi_owe_ie_t;
+
+/* owe transition mode ie */
+typedef BWL_PRE_PACKED_STRUCT struct owe_transition_mode_ie_s {
+ uint8 bssid[ETHER_ADDR_LEN]; /* Contains the BSSID of the other virtual AP */
+ uint8 ssid_len;
+ uint8 *ssid; /* SSID of the other virtual AP */
+ uint8 band_info; /* operating band info of the other virtual AP */
+ uint8 chan; /* operating channel number of the other virtual AP */
+} BWL_POST_PACKED_STRUCT owe_transition_mode_ie_t;
+#define OWE_IE_HDR_SIZE (OFFSETOF(wifi_owe_ie_t, attr))
+/* oui:3 bytes + oui type:1 byte */
+#define OWE_IE_NO_ATTR_LEN 4
+
+/* This marks the end of a packed structure section. */
+#include <packed_section_end.h>
+
+#endif /* _802_11wfa_h_ */
diff --git a/include/802.1d.h b/include/802.1d.h
index f9416ab..45a94c0 100644
--- a/include/802.1d.h
+++ b/include/802.1d.h
@@ -1,7 +1,7 @@
/*
* Fundamental types and constants relating to 802.1D
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/802.3.h b/include/802.3.h
index 8ee0002..263e9e7 100644
--- a/include/802.3.h
+++ b/include/802.3.h
@@ -1,7 +1,7 @@
/*
* Fundamental constants relating to 802.3
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/aidmp.h b/include/aidmp.h
index b0fd87d..d76c888 100644
--- a/include/aidmp.h
+++ b/include/aidmp.h
@@ -1,7 +1,7 @@
/*
* Broadcom AMBA Interconnect definitions.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/bcm_l2_filter.h b/include/bcm_l2_filter.h
index e67ecdf..2230170 100644
--- a/include/bcm_l2_filter.h
+++ b/include/bcm_l2_filter.h
@@ -1,7 +1,7 @@
/*
* L2 Filter handling functions
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/bcm_mpool_pub.h b/include/bcm_mpool_pub.h
index c5812b3..a19fc20 100644
--- a/include/bcm_mpool_pub.h
+++ b/include/bcm_mpool_pub.h
@@ -35,7 +35,7 @@
* and instrumentation on top of the heap, without modifying the heap
* allocation implementation.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -172,7 +172,7 @@
uint nobj,
void *memstart,
unsigned int memsize,
- const char poolname[BCM_MP_NAMELEN],
+ const char *poolname,
bcm_mp_pool_h *newp);
/*
@@ -210,7 +210,7 @@
*
*/
int bcm_mpm_create_heap_pool(bcm_mpm_mgr_h mgr, unsigned int obj_sz,
- const char poolname[BCM_MP_NAMELEN],
+ const char *poolname,
bcm_mp_pool_h *newp);
/*
diff --git a/include/bcm_ring.h b/include/bcm_ring.h
index 6b64cd0..3990f9a 100644
--- a/include/bcm_ring.h
+++ b/include/bcm_ring.h
@@ -6,7 +6,7 @@
*
* NOTE: A ring of size N, may only hold N-1 elements.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/bcmarp.h b/include/bcmarp.h
index a010fce..21f5e24 100644
--- a/include/bcmarp.h
+++ b/include/bcmarp.h
@@ -1,7 +1,7 @@
/*
* Fundamental constants relating to ARP Protocol
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/bcmbloom.h b/include/bcmbloom.h
index 1744a65..a978d4d 100644
--- a/include/bcmbloom.h
+++ b/include/bcmbloom.h
@@ -1,7 +1,7 @@
/*
* Bloom filter support
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/bcmcdc.h b/include/bcmcdc.h
index 5d05089..ed02905 100644
--- a/include/bcmcdc.h
+++ b/include/bcmcdc.h
@@ -4,7 +4,7 @@
*
* Definitions subject to change without notice.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/bcmdefs.h b/include/bcmdefs.h
index baa1f96..d492c0d 100644
--- a/include/bcmdefs.h
+++ b/include/bcmdefs.h
@@ -1,7 +1,7 @@
/*
* Misc system wide definitions
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -35,7 +35,7 @@
/* For all the corerevs of the chip being built */
#ifdef VLSI_COREREVS
-#include <chip_defs.h> /* auto-generated definitions from vlsi_data */
+#include <vlsi_chip_defs.h> /* auto-generated definitions from vlsi_data */
#endif /* VLSI_COREREVS */
/* Use BCM_REFERENCE to suppress warnings about intentionally-unused function
@@ -172,7 +172,7 @@
#endif
/* In case of coex cpu reinit, we should not relcaim the functions that are needed for reinit */
-#ifdef COEX_CPU_REINIT
+#if defined(COEX_CPU_REINIT) && !defined(COEX_CPU_REINIT_DISABLED)
#define BCMCOEXCPUATTACHDATA(_data) _data
#define BCMCOEXCPUATTACHFN(_fn) _fn
#define BCMCOEXCPUPREATTACHDATA(_data) _data
@@ -182,7 +182,7 @@
#define BCMCOEXCPUATTACHFN(_fn) _fn
#define BCMCOEXCPUPREATTACHDATA(_data) BCMPREATTACHDATA(_data)
#define BCMCOEXCPUPREATTACHFN(_fn) BCMPREATTACHFN(_fn)
-#endif /* COEX_CPU_REINIT */
+#endif /* COEX_CPU_REINIT && !COEX_CPU_REINIT_DISABLED */
#define _data _data
#define _fn _fn
@@ -439,6 +439,14 @@
#define CR4REV_GE(rev, val) ((rev) >= (val))
#endif
+#ifdef BCMARMCA7REV
+#define CA7REV(rev) (BCMARMCA7REV)
+#define CA7REV_GE(rev, val) ((BCMARMCA7REV) >= (val))
+#else
+#define CA7REV(rev) (rev)
+#define CA7REV_GE(rev, val) ((rev) >= (val))
+#endif
+
#ifdef BCMLHLREV
#define LHLREV(rev) (BCMLHLREV)
#else
@@ -922,11 +930,12 @@
#else
#if defined(DONGLEBUILD)
#define BCMPOSTTRAPFN(_fn) __attribute__ ((__section__ (".text_posttrap." #_fn))) _fn
+#define BCMPOSTTRAPFASTPATH(_fn) __attribute__ ((__section__ (".text_posttrapfp." #_fn))) _fn
#else
#define BCMPOSTTRAPFN(_fn) _fn
+#define BCMPOSTTRAPFASTPATH(_fn) _fn
#endif /* DONGLEBUILD */
#define BCMPOSTTRAPRAMFN(fn) BCMPOSTTRAPFN(fn)
-#define BCMPOSTTRAPFASTPATH(fn) BCMPOSTTRAPFN(fn)
#endif /* ROMBUILD */
typedef struct bcm_rng * bcm_rng_handle_t;
@@ -1014,6 +1023,9 @@
/* Disable function inlining. */
#define BCM_NOINLINE __attribute__ ((noinline))
+/* Disable compiler optimizations for a function. */
+#define BCM_NO_OPTIMIZE __attribute__ ((optimize(0)))
+
/*
* A compact form for a list of valid register address offsets.
* Used for when dumping the contents of the register set for the user.
@@ -1029,6 +1041,8 @@
uint8 bmp_cnt[4]; /* bit[31]=1, bit[30:0] is count else it is a bitmap */
} regs_list_t;
+#ifndef WL_UNITTEST
typedef union d11rxhdr d11rxhdr_t;
+#endif /* WL_UNITTEST */
#endif /* _bcmdefs_h_ */
diff --git a/include/bcmdevs.h b/include/bcmdevs.h
index 5244e6e..7375289 100644
--- a/include/bcmdevs.h
+++ b/include/bcmdevs.h
@@ -1,7 +1,7 @@
/*
* Broadcom device-specific manifest constants.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -130,6 +130,7 @@
#define BCM4381_D11AX_ID 0x4446 /* 4381 802.11ax dualband device */
#define BCM4382_D11AX_ID 0x4447 /* 4382 802.11ax dualband device */
+#define BCM43852_D11AX_ID 0x4448 /* 43852 802.11ax dualband device */
#define BCM4387_D11AX_ID 0x4433 /* 4387 802.11ax dualband device */
#define BCM4388_D11AX_ID 0x4434 /* 4388 802.11ax dualband device */
@@ -185,6 +186,7 @@
#define BCM4378_CHIP_ID 0x4378 /* 4378 chipcommon chipid */
#define BCM4381_CHIP_ID 0x4381 /* 4381 chipcommon chipid */
#define BCM4382_CHIP_ID 0x4382 /* 4382 chipcommon chipid */
+#define BCM43852_CHIP_ID 0xAB4C /* 43852 chipcommon chipid */
#define BCM4385_CHIP_ID 0x4385 /* 4385 chipcommon chipid */
#define BCM4387_CHIP_ID 0x4387 /* 4387 chipcommon chipid */
#define BCM4388_CHIP_ID 0x4388 /* 4388 chipcommon chipid */
@@ -207,6 +209,9 @@
#define BCM4382_CHIP(chipid) (CHIPID(chipid) == BCM4382_CHIP_ID)
#define BCM4382_CHIP_GRPID BCM4382_CHIP_ID
+#define BCM43852_CHIP(chipid) (CHIPID(chipid) == BCM43852_CHIP_ID)
+#define BCM43852_CHIP_GRPID BCM43852_CHIP_ID
+
#define BCM4385_CHIP(chipid) (CHIPID(chipid) == BCM4385_CHIP_ID)
#define BCM4385_CHIP_GRPID BCM4385_CHIP_ID
diff --git a/include/bcmdevs_legacy.h b/include/bcmdevs_legacy.h
index 8edf4d5..63a951a 100644
--- a/include/bcmdevs_legacy.h
+++ b/include/bcmdevs_legacy.h
@@ -1,7 +1,7 @@
/*
* Broadcom device-specific manifest constants used by DHD, but deprecated in firmware.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/bcmdhcp.h b/include/bcmdhcp.h
index b4aed13..287c5e3 100644
--- a/include/bcmdhcp.h
+++ b/include/bcmdhcp.h
@@ -1,7 +1,7 @@
/*
* Fundamental constants relating to DHCP Protocol
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/bcmendian.h b/include/bcmendian.h
index 4639415..82968b4 100644
--- a/include/bcmendian.h
+++ b/include/bcmendian.h
@@ -1,7 +1,7 @@
/*
* Byte order utilities
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/bcmerror.h b/include/bcmerror.h
index 1220c97..5bed83a 100644
--- a/include/bcmerror.h
+++ b/include/bcmerror.h
@@ -1,7 +1,7 @@
/*
* Common header file for all error codes.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -132,8 +132,11 @@
#define BCME_ROAM -73 /* Roam related failures */
#define BCME_NO_SIG_FILE -74 /* Signature file is missing */
#define BCME_RESP_PENDING -75 /* Command response is pending */
+#define BCME_ACTIVE -76 /* Command/context is already active */
+#define BCME_IN_PROGRESS -77 /* Command/context is in progress */
+#define BCME_NOP -78 /* No action taken i.e. NOP */
-#define BCME_LAST BCME_RESP_PENDING
+#define BCME_LAST BCME_NOP
#define BCME_NOTENABLED BCME_DISABLED
@@ -225,11 +228,20 @@
"Critical roam in progress", \
"Signature file is missing", \
"Command response pending", \
+ "Command/context already active", \
+ "Command/context is in progress", \
+ "No action taken i.e. NOP", \
}
/* FTM error codes [-1024, -2047] */
enum {
- WL_FTM_E_LAST = -1073,
+ WL_FTM_E_LAST = -1079,
+ WL_FTM_E_OUTSIDE_RSTA_AW = -1079,
+ WL_FTM_E_NO_STA_INFO = -1078,
+ WL_FTM_E_SAC_MISMATCH = -1077,
+ WL_FTM_E_TOKEN_MISMATCH = -1076,
+ WL_FTM_E_IE_NOTFOUND = -1075,
+ WL_FTM_E_IE_BADLEN = -1074,
WL_FTM_E_INVALID_BW = -1073,
WL_FTM_E_INVALID_ST_CH = -1072,
WL_FTM_E_RSTA_AND_ISTA = -1071,
@@ -286,7 +298,8 @@
/* begin proxd codes compatible w/ ftm above - obsolete DO NOT extend */
enum {
- WL_PROXD_E_LAST = -1057,
+ WL_PROXD_E_LAST = -1058,
+ WL_PROXD_E_PKTFREED = -1058,
WL_PROXD_E_ASSOC_INPROG = -1057,
WL_PROXD_E_NOAVAIL = -1056,
WL_PROXD_E_EXT_SCHED = -1055,
@@ -657,6 +670,9 @@
/* signature patch invalid length */
BL_E_PATCH_INVALID_LENGTH = -4150,
+ /* bmpu configuration error */
+ BL_E_BUS_MPU_CONFIG_FAIL = -4151,
+
/* last error */
BL_E_LAST = -5119
};
@@ -791,7 +807,13 @@
/* cached PMK used in the session is expired */
WL_PASN_E_AUTH_PMKSA_EXPIRED = -8228,
/* PTKSA installed is deleted by keymgmt */
- WL_PASN_E_AUTH_PTKSA_DELETED = -8229
+ WL_PASN_E_AUTH_PTKSA_DELETED = -8229,
+ /* SA query timeout notification */
+ WL_PASN_E_SA_QUERY_TIMEOUT = -8230,
+ /* PTKSA lifetime expired */
+ WL_PASN_E_AUTH_PTKSA_EXPIRED = -8231,
+ /* Local to deauth peer. */
+ WL_PASN_E_DEAUTH_PEER = -8232
};
/* bcm fsm status codes. [-9216, -10239] */
@@ -831,6 +853,46 @@
WL_MSCS_E_IN_PROGRESS = -10241
} wl_mscs_status_e;
+/* bcmsm error code [-11264 ... -12287] */
+typedef enum {
+ BCMSM_IN_RTC = -11264, /**< In Run to completion loop */
+ BCMSM_TRANS_NOT_FOUND = -11265, /**< Transition was not found */
+ BCMSM_TRANS_GUARD_FAILED = -11266, /**< guard for a transition failed */
+ BCMSM_TRANS_EFFECT_FAILED = -11267, /**< transition effect returned err */
+ BCMSM_TRANS_ERROR = -11268, /**< Error while taking transition */
+ BCMSM_STATE_ENTRY_FAILED = -11269, /**< Entry to state failed */
+ BCMSM_STATE_EXIT_FAILED = -11270, /**< Failure while executing a state */
+ BCMSM_STATE_ID_EXISTS = -11271, /**< Same ID exists */
+ BCMSM_STATE_CONFIG_ERROR = -11272, /**< SM configuration has error */
+ BCMSM_Q_FULL = -11273, /**< Event queue is full */
+ BCMSM_Q_EMPTY = -11274, /**< Event queue is empty */
+ BCMSM_Q_NO_DEQUEUE = -11275, /**< Dequeue attempted was unsuccessful */
+ BCMSM_CHOICE_STATE_NO_TRANS = -11276, /**< Choice has no valid out transition */
+ BCMSM_EVENT_ALLOC_FAILED = -11277, /**< Event allocation failed */
+ BCMSM_EVENT_EXPIRED = -11278, /**< Event expired */
+ BCMSM_EVENT_NOT_POSTED = -11279, /**< Event was not posted */
+ BCMSM_HALTED = -11280, /**< State machine is in final state */
+ BCMSM_TMR_NOT_STOPPED = -11281, /**< Error in stopping a timer */
+ BCMSM_TMR_NOT_STARTED = -11282, /**< Error in starting a timer */
+ BCMSM_TMR_NOT_FOUND = -11283, /**< No timer available to be scheduled */
+ BCMSM_TMR_ERROR = -11284, /**< Error in starting a timer */
+
+ BCMSM_MAX = -12287
+} bcmsm_status_t;
+
#endif /* BCMUTILS_ERR_CODES */
+/*
+* 6G scan error code [-12288 .. -13311] (1K)
+*/
+enum {
+ /* TPE cache does not exit for the given 6G channel */
+ BCME_6G_SCAN_NO_TPE_CACHE = -12288,
+ /* TPE cache in the FW has expired */
+ BCME_6G_SCAN_TPE_CACHE_EXPIRED = -12289,
+ /* Wild card directed scan requested */
+ BCME_6G_SCAN_DIRECTED_WILDCARD = -12290,
+ /* TPE cache in the FW is invalid */
+ BCME_6G_SCAN_TPE_CACHE_INVALID = -12291
+};
#endif /* _bcmerror_h_ */
diff --git a/include/bcmeth.h b/include/bcmeth.h
index a9c3e05..8146910 100644
--- a/include/bcmeth.h
+++ b/include/bcmeth.h
@@ -1,7 +1,7 @@
/*
* Broadcom Ethernettype protocol definitions
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/bcmevent.h b/include/bcmevent.h
index 8fb94a4..efcaccd 100644
--- a/include/bcmevent.h
+++ b/include/bcmevent.h
@@ -3,7 +3,7 @@
*
* Dependencies: bcmeth.h
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -240,7 +240,8 @@
#define WLC_E_TX_STAT_ERROR 126 /* tx error indication */
#define WLC_E_BCMC_CREDIT_SUPPORT 127 /* credit check for BCMC supported */
#define WLC_E_PEER_TIMEOUT 128 /* silently drop a STA because of inactivity */
-#define WLC_E_BT_WIFI_HANDOVER_REQ 130 /* Handover Request Initiated */
+// 129 unused
+// 130 unused
#define WLC_E_SPW_TXINHIBIT 131 /* Southpaw TxInhibit notification */
#define WLC_E_FBT_AUTH_REQ_IND 132 /* FBT Authentication Request Indication */
#define WLC_E_RSSI_LQM 133 /* Enhancement addition for WLC_E_RSSI */
@@ -309,8 +310,12 @@
#define WLC_E_ROAM_SCAN_RESULT 197 /* roam/reassoc scan result event */
#define WLC_E_MSCS 200 /* MSCS success/failure events */
-
-#define WLC_E_LAST 201 /* highest val + 1 for range checking */
+#define WLC_E_RXDMA_RECOVERY_ATMPT 201 /* RXDMA Recovery Attempted Event */
+#define WLC_E_PFN_PARTIAL_RESULT 202
+#define WLC_E_MLO_LINK_INFO 203 /* 11be MLO link information */
+#define WLC_E_C2C 204 /* Client to client (C2C) for 6GHz TX */
+#define WLC_E_BCN_TSF 205 /* Report Beacon TSF */
+#define WLC_E_LAST 206 /* highest val + 1 for range checking */
/* define an API for getting the string name of an event */
extern const char *bcmevent_get_name(uint event_type);
@@ -443,18 +448,26 @@
#define WLC_E_STATUS_PSK_AUTH_GTK_REKEY_FAIL 6 /* GTK event status code */
/* SDB transition status code */
-#define WLC_E_STATUS_SDB_START 1
-#define WLC_E_STATUS_SDB_COMPLETE 2
+#define WLC_E_STATUS_SDB_START 1u
+#define WLC_E_STATUS_SDB_COMPLETE 2u
/* Slice-swap status code */
-#define WLC_E_STATUS_SLICE_SWAP_START 3
-#define WLC_E_STATUS_SLICE_SWAP_COMPLETE 4
+#define WLC_E_STATUS_SLICE_SWAP_START 3u
+#define WLC_E_STATUS_SLICE_SWAP_COMPLETE 4u
+#define WLC_E_STATUS_SDB_FAILED 5u
/* SDB transition reason code */
-#define WLC_E_REASON_HOST_DIRECT 0
-#define WLC_E_REASON_INFRA_ASSOC 1
-#define WLC_E_REASON_INFRA_ROAM 2
-#define WLC_E_REASON_INFRA_DISASSOC 3
-#define WLC_E_REASON_NO_MODE_CHANGE_NEEDED 4
+#define WLC_E_REASON_HOST_DIRECT 0u
+#define WLC_E_REASON_INFRA_ASSOC 1u
+#define WLC_E_REASON_INFRA_ROAM 2u
+#define WLC_E_REASON_INFRA_DISASSOC 3u
+#define WLC_E_REASON_NO_MODE_CHANGE_NEEDED 4u
+
+#define WLC_E_REASON_SDB_MODESW_SLICE_CHANGE 7u
+#define WLC_E_REASON_SDB_MODESW_CHAIN_CHANGE 8u
+#define WLC_E_REASON_SDB_MODESW_SLICE_AND_CHAIN_CHANGE 9u
+#define WLC_E_REASON_SDB_MODESW_UNKNOWN 10u
+#define WLC_E_REASON_SDB_MODESW_TIMEOUT 11u
+#define WLC_E_REASON_SDB_MODESW_FAILED 12u
/* TX STAT ERROR REASON CODE */
#define WLC_E_REASON_TXBACKOFF_NOT_DECREMENTED 0x1
@@ -503,44 +516,55 @@
#define WLC_E_REASON_ESTM_LOW 15 /* roamed due to ESTM low tput */
#define WLC_E_REASON_SILENT_ROAM 16 /* roamed due to Silent roam */
#define WLC_E_REASON_INACTIVITY 17 /* full roam scan due to inactivity */
-#define WLC_E_REASON_ROAM_SCAN_TIMEOUT 18 /* roam scan timer timeout */
+#define WLC_E_REASON_ROAM_SCAN_TIMEOUT 18 /* roam scan timer timeout */
#define WLC_E_REASON_REASSOC 19 /* roamed due to reassoc iovar */
-#define WLC_E_REASON_CCA 20 /* roamed due to better AP from cca measurement */
-#define WLC_E_REASON_LAST 21 /* NOTE: increment this as you add reasons above */
+#define WLC_E_REASON_CCA 20 /* roamed due to better AP from cca measurement */
+#define WLC_E_REASON_BTCX_ROAM 21 /* roamed due to Btcx roam */
+#define WLC_E_REASON_LAST 22 /* NOTE: increment this as you add reasons above */
/* prune reason codes */
-#define WLC_E_PRUNE_ENCR_MISMATCH 1 /* encryption mismatch */
-#define WLC_E_PRUNE_BCAST_BSSID 2 /* AP uses a broadcast BSSID */
-#define WLC_E_PRUNE_MAC_DENY 3 /* STA's MAC addr is in AP's MAC deny list */
-#define WLC_E_PRUNE_MAC_NA 4 /* STA's MAC addr is not in AP's MAC allow list */
-#define WLC_E_PRUNE_REG_PASSV 5 /* AP not allowed due to regulatory restriction */
-#define WLC_E_PRUNE_SPCT_MGMT 6 /* AP does not support STA locale spectrum mgmt */
-#define WLC_E_PRUNE_RADAR 7 /* AP is on a radar channel of STA locale */
-#define WLC_E_RSN_MISMATCH 8 /* STA does not support AP's RSN */
-#define WLC_E_PRUNE_NO_COMMON_RATES 9 /* No rates in common with AP */
-#define WLC_E_PRUNE_BASIC_RATES 10 /* STA does not support all basic rates of BSS */
+#define WLC_E_PRUNE_ENCR_MISMATCH 1u /* encryption mismatch */
+#define WLC_E_PRUNE_BCAST_BSSID 2u /* AP uses a broadcast BSSID */
+#define WLC_E_PRUNE_MAC_DENY 3u /* STA's MAC addr is in AP's MAC deny list */
+#define WLC_E_PRUNE_MAC_NA 4u /* STA's MAC addr is not in AP's MAC allow list */
+#define WLC_E_PRUNE_REG_PASSV 5u /* AP not allowed due to regulatory restriction */
+#define WLC_E_PRUNE_SPCT_MGMT 6u /* AP does not support STA locale spectrum mgmt */
+#define WLC_E_PRUNE_RADAR 7u /* AP is on a radar channel of STA locale */
+#define WLC_E_RSN_MISMATCH 8u /* STA does not support AP's RSN */
+#define WLC_E_PRUNE_NO_COMMON_RATES 9u /* No rates in common with AP */
+#define WLC_E_PRUNE_BASIC_RATES 10u /* STA does not support all basic rates of BSS */
#ifdef BCMCCX
-#define WLC_E_PRUNE_CCXFAST_PREVAP 11 /* CCX FAST ROAM: prune previous AP */
+#define WLC_E_PRUNE_CCXFAST_PREVAP 11u /* CCX FAST ROAM: prune previous AP */
#endif /* def BCMCCX */
-#define WLC_E_PRUNE_CIPHER_NA 12 /* BSS's cipher not supported */
-#define WLC_E_PRUNE_KNOWN_STA 13 /* AP is already known to us as a STA */
+#define WLC_E_PRUNE_CIPHER_NA 12u /* BSS's cipher not supported */
+#define WLC_E_PRUNE_KNOWN_STA 13u /* AP is already known to us as a STA */
#ifdef BCMCCX
-#define WLC_E_PRUNE_CCXFAST_DROAM 14 /* CCX FAST ROAM: prune unqualified AP */
+#define WLC_E_PRUNE_CCXFAST_DROAM 14u /* CCX FAST ROAM: prune unqualified AP */
#endif /* def BCMCCX */
-#define WLC_E_PRUNE_WDS_PEER 15 /* AP is already known to us as a WDS peer */
-#define WLC_E_PRUNE_QBSS_LOAD 16 /* QBSS LOAD - AAC is too low */
-#define WLC_E_PRUNE_HOME_AP 17 /* prune home AP */
+#define WLC_E_PRUNE_WDS_PEER 15u /* AP is already known to us as a WDS peer */
+#define WLC_E_PRUNE_QBSS_LOAD 16u /* QBSS LOAD - AAC is too low */
+#define WLC_E_PRUNE_HOME_AP 17u /* prune home AP */
#ifdef BCMCCX
-#define WLC_E_PRUNE_AP_BLOCKED 18 /* prune blocked AP */
-#define WLC_E_PRUNE_NO_DIAG_SUPPORT 19 /* prune due to diagnostic mode not supported */
+#define WLC_E_PRUNE_AP_BLOCKED 18u /* prune blocked AP */
+#define WLC_E_PRUNE_NO_DIAG_SUPPORT 19u /* prune due to diagnostic mode not supported */
#endif /* BCMCCX */
-#define WLC_E_PRUNE_AUTH_RESP_MAC 20 /* suppress auth resp by MAC filter */
-#define WLC_E_PRUNE_ASSOC_RETRY_DELAY 21 /* MBO assoc retry delay */
-#define WLC_E_PRUNE_RSSI_ASSOC_REJ 22 /* OCE RSSI-based assoc rejection */
-#define WLC_E_PRUNE_MAC_AVOID 23 /* AP's MAC addr is in STA's MAC avoid list */
-#define WLC_E_PRUNE_TRANSITION_DISABLE 24 /* AP's Transition Disable Policy */
-#define WLC_E_PRUNE_WRONG_COUNTRY_CODE 25 /* Prune AP due to Wrong Country Code */
-#define WLC_E_PRUNE_CHANNEL_NOT_IN_VLP 26 /* Prune AP due to Chanspec not in VLP cat */
+#define WLC_E_PRUNE_AUTH_RESP_MAC 20u /* suppress auth resp by MAC filter */
+#define WLC_E_PRUNE_ASSOC_RETRY_DELAY 21u /* MBO assoc retry delay */
+#define WLC_E_PRUNE_RSSI_ASSOC_REJ 22u /* OCE RSSI-based assoc rejection */
+#define WLC_E_PRUNE_MAC_AVOID 23u /* AP's MAC addr is in STA's MAC avoid list */
+#define WLC_E_PRUNE_TRANSITION_DISABLE 24u /* AP's Transition Disable Policy */
+#define WLC_E_PRUNE_WRONG_COUNTRY_CODE 25u /* Prune AP due to Wrong Country Code */
+#define WLC_E_PRUNE_CHANNEL_NOT_IN_VLP 26u /* Prune AP due to Chanspec not in VLP cat */
+#define WLC_E_PRUNE_MFP_COMPAT_MISMATCH 27u /* Prune AP due to MFP compatibility mismatch */
+#define WLC_E_PRUNE_CHAN_MISMATCH 28u /* Prune AP due to channel mismatch */
+#define WLC_E_PRUNE_MSTA 29u /* mSTA: Prune join to AP from multiple bsscfgs */
+#define WLC_E_PRUNE_BLIST_BTM 30u /* Prune AP due to BTM Black listing */
+#define WLC_E_PRUNE_BCN_MUTE_LOW_RSSI 31u /* Prune low rssi beacon muted AP */
+#define WLC_E_PRUNE_6G_RSN_MISMATCH 32u /* Prune AP due to RSN mismatch in 6G */
+#define WLC_E_PRUNE_INVALID_CHAN 33u /* Prune AP due to invalid channel */
+#define WLC_E_PRUNE_MESH_CFG_MISMATCH 34u /* Prune due to Mesh AP config mismatch */
+#define WLC_E_PRUNE_6G_RNR_INVALID_CHAN 35u /* Prune RNR due to invalid channel reporting */
+#define WLC_E_PRUNE_BY_OWE 36u /* Pruned by OWE */
/* WPA failure reason codes carried in the WLC_E_PSK_SUP event */
#define WLC_E_SUP_OTHER 0 /* Other reason */
@@ -568,6 +592,7 @@
#define WLC_E_SUP_MSG1_PMKID_MISMATCH 22 /* MSG1 PMKID not matched to PMKSA cache list */
#define WLC_E_SUP_GTK_UPDATE 23 /* GTK update */
#define WLC_E_SUP_KDK_UPDATE_FAIL 24 /* KDK update failure */
+#define WLC_E_SUP_MSG3_NO_MLO_GTK 25 /* encapsulated MLO GTK missing from msg 3 */
/* event msg for WLC_E_SUP_PTK_UPDATE */
typedef struct wlc_sup_ptk_update {
@@ -919,7 +944,7 @@
/* ********** NAN protocol events/subevents ********** */
#ifndef NAN_EVENT_BUFFER_SIZE
-#define NAN_EVENT_BUFFER_SIZE 1024 /* max size */
+#define NAN_EVENT_BUFFER_SIZE 1600 /* max size */
#endif /* NAN_EVENT_BUFFER_SIZE */
/* NAN Events sent by firmware */
@@ -1002,7 +1027,8 @@
typedef enum wl_scan_events {
WL_SCAN_START = 1,
- WL_SCAN_END = 2
+ WL_SCAN_END = 2,
+ WL_SCAN_ADD = 3
} wl_scan_events;
/* WLC_E_ULP event data */
@@ -1188,6 +1214,7 @@
WL_TWT_TD_RC_SETUP_FAIL = 6u, /* Setup fail midway. Teardown all connections */
WL_TWT_TD_RC_SCHED = 7u, /* Teardown by TWT Scheduler */
WL_TWT_TD_RC_TIMEOUT = 8u, /* NoAck/Ack timeout for Teardown */
+ WL_TWT_TD_RC_PM_OFF = 9u, /* Teardown due to PM Mode 0 */
/* Any new reason code add before this */
WL_TWT_TD_RC_ERROR = 255u, /* Generic Error cases */
} wl_twt_td_rc_t;
@@ -1241,6 +1268,17 @@
uint8 PAD[3];
} wl_twt_notify_t;
+/* Beacon TSF Event */
+typedef struct wl_bcn_tsf {
+ uint16 version;
+ uint16 length; /* the byte count of fields from 'reason_code' onwards */
+ uint32 bcn_tsf_h;
+ uint32 bcn_tsf_l;
+} wl_bcn_tsf_t;
+
+#define WL_BCN_TSF_VER_0 0u
+#define WL_BCN_TSF_LEN sizeof(wl_bcn_tsf_t)
+
#define WL_INVALID_IE_EVENT_VERSION 0
/* Invalid IE Event data */
@@ -1544,17 +1582,32 @@
*/
#define BCN_MUTE_MITI_END 2u /* Sent when beacon is received */
#define BCN_MUTE_MITI_TIMEOUT 3u /* Mitigation period is reached */
+#define BCN_MUTE_MITI_FAILED 4u /* Mitigation attempt failed */
/* Status code for sending event */
-#define BCN_MUTE_MITI_UNKNOWN 0u /* Mitigation status unknown */
-#define BCN_MUTE_MITI_ASSOC_COMP 1u /* Mitigation during Assoc phase */
-#define BCN_MUTE_MITI_BCN_LOST 2u /* Mitigation due to beacon lost */
-#define BCN_MUTE_MITI_BCN_RECV 3u /* Mitigation end due to bcn reception */
-#define BCN_MUTE_MITI_ROAM 4u /* Mitigation end due to Roam */
-#define BCN_MUTE_MITI_LINK_DOWN 5u /* Mitigation end due to link down */
-#define BCN_MUTE_MITI_RX_DEAUTH 6u /* Mitigation end due to AP deauth */
-#define BCN_MUTE_MITI_RX_DISASSOC 7u /* Mitigation end due to AP disassoc */
-#define BCN_MUTE_MITI_LOW_RSSI 8u /* Mitigation end due to Low RSSI */
+#define BCN_MUTE_MITI_UNKNOWN 0u /* Mitigation status unknown */
+#define BCN_MUTE_MITI_ASSOC_COMP 1u /* Mitigation during Assoc phase */
+#define BCN_MUTE_MITI_BCN_LOST 2u /* Mitigation due to beacon lost */
+#define BCN_MUTE_MITI_BCN_RECV 3u /* Mitigation end due to bcn reception */
+#define BCN_MUTE_MITI_ROAM 4u /* Mitigation end due to Roam */
+#define BCN_MUTE_MITI_LINK_DOWN 5u /* Mitigation end due to link down */
+#define BCN_MUTE_MITI_RX_DEAUTH 6u /* Mitigation end due to AP deauth */
+#define BCN_MUTE_MITI_RX_DISASSOC 7u /* Mitigation end due to AP disassoc */
+#define BCN_MUTE_MITI_LOW_RSSI 8u /* Mitigation end due to Low RSSI */
+#define BCN_MUTE_MITI_ASSOC_COMP_RX_UPR 9u /* Assoc succeeded using UPR reception */
+#define BCN_MUTE_MITI_BCN_LOST_RX_UPR 10u /* Beacon lost and Mitigation success with
+ * recent UPR Reception
+ */
+#define BCN_MUTE_MITI_ASSOC_COMP_RX_FILS 11u /* Assoc succeeded using FILS reception */
+#define BCN_MUTE_MITI_BCN_LOST_RX_FILS 12u /* Beacon lost and Mitigation success with
+ * recent FILS Reception
+ */
+#define BCN_MUTE_MITI_NO_PRB_RESP 13u /* Beacon lost and mitigation failed due to
+ * no Rx probe response.
+ */
+#define BCN_MUTE_MITI_PRB_RESP_LOW_RSSI 14u /* Beacon lost and mitigation failed due Rx
+ * Probe response with Low RSSI.
+ */
/* bcn_mute_miti event data */
#define WLC_BCN_MUTE_MITI_EVENT_DATA_VER_1 1u
@@ -1599,6 +1652,8 @@
uint32 switch_time; /**< csa switch time: TSF + BI * count, msec */
} wl_csa_event_t;
+/* SIB sub events */
+
/* Event structure for WLC_E_MSCS */
typedef struct wl_event_mscs {
uint16 version; /* structure version */
@@ -1610,4 +1665,60 @@
/* WLC_E_MSCS event structure version */
#define WL_MSCS_EVENT_VERSION 1u
+/* MLO link information (WLC_E_MLO_LINK_INFO) event data */
+#define WL_MLO_LINK_INFO_EVENT_VERSION_1 (1u)
+
+typedef enum wl_mlo_link_info_opcode {
+ WL_MLO_LINK_INFO_OPCODE_ADD = 1, /* MLO links addition */
+ WL_MLO_LINK_INFO_OPCODE_DEL = 2 /* MLO links deletion */
+} wl_mlo_link_info_opcode_t;
+
+typedef enum wl_mlo_link_info_role {
+ WL_MLO_LINK_INFO_ROLE_STA = 1, /* infrastructure mode station */
+ WL_MLO_LINK_INFO_ROLE_AP = 2 /* access point */
+} wl_mlo_link_info_role_t;
+
+/* MLO per link information structure */
+typedef struct wl_mlo_per_link_info_v1 {
+ uint8 if_idx; /* RTE virtual device index (for dongle) */
+ uint8 cfg_idx; /* bsscfg index */
+ uint8 link_id; /* link identifier - AP managed unique identifier */
+ uint8 link_idx; /* link index - local link config index */
+ struct ether_addr link_addr; /* link specific address */
+ uint8 PAD[2];
+} wl_mlo_per_link_info_v1_t;
+
+/* MLO link information event structure */
+typedef struct wl_mlo_link_info_event_v1 {
+ uint16 version; /* structure version */
+ uint16 length; /* length of this structure */
+ uint8 opcode; /* link opcode - wl_mlo_link_info_opcode */
+ uint8 role; /* link role - wl_mlo_link_info_role */
+ struct ether_addr mld_addr; /* mld addres */
+ uint8 num_links; /* number of operative links */
+ uint8 PAD[3];
+ wl_mlo_per_link_info_v1_t link_info[]; /* per link information */
+} wl_mlo_link_info_event_v1_t;
+
+/* ===== C2C event definitions ===== */
+#define C2C_EVENT_BUFFER_SIZE 1024u
+#define IS_C2C_EVT_ON(param, evt) ((param) & (1u << (evt)))
+#define C2C_ALLOWED_EVENT_MASK (1u << WL_EVT_C2C_START | \
+ (1u << WL_EVT_C2C_END) | (1u << WL_EVT_C2C_PRE_EXPIRY) | \
+ (1u << WL_EVT_C2C_EXTN) | \
+ (1u << WL_EVT_C2C_CACHE_ADD) | (1u << WL_EVT_C2C_CACHE_DEL) | \
+ (1u << WL_EVT_C2C_MUTE_ON) | (1u << WL_EVT_C2C_MUTE_OFF))
+
+/* WLC_E_C2C subevent ID */
+typedef enum wl_c2c_events {
+ WL_EVT_C2C_START, /* first enabling signal, c2c starts */
+ WL_EVT_C2C_END, /* enabling signal expired, c2c ends */
+ WL_EVT_C2C_PRE_EXPIRY, /* esig expiring soon; do scan or let expire */
+ WL_EVT_C2C_EXTN, /* received new esig, c2c continues */
+ WL_EVT_C2C_CACHE_ADD, /* added new LPI AP to cache */
+ WL_EVT_C2C_CACHE_DEL, /* removed LPI AP from cache */
+ WL_EVT_C2C_MUTE_ON, /* p2p tx is muted for 6GHz channels */
+ WL_EVT_C2C_MUTE_OFF /* p2p tx unmuted for 6GHz channels */
+} wl_c2c_events_e;
+
#endif /* _BCMEVENT_H_ */
diff --git a/include/bcmicmp.h b/include/bcmicmp.h
index 9ca3eed..3a58a85 100644
--- a/include/bcmicmp.h
+++ b/include/bcmicmp.h
@@ -1,7 +1,7 @@
/*
* Fundamental constants relating to ICMP Protocol
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/bcmigmp.h b/include/bcmigmp.h
index c1c8b18..559c964 100644
--- a/include/bcmigmp.h
+++ b/include/bcmigmp.h
@@ -1,7 +1,7 @@
/*
* Fundamental constants relating to IGMP Protocol
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/bcmiov.h b/include/bcmiov.h
index efac2b6..3e5a6fa 100644
--- a/include/bcmiov.h
+++ b/include/bcmiov.h
@@ -4,7 +4,7 @@
* To be used in firmware and host apps or dhd - reducing code size,
* duplication, and maintenance overhead.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/bcmip.h b/include/bcmip.h
index 8272b5d..7eb5736 100644
--- a/include/bcmip.h
+++ b/include/bcmip.h
@@ -1,7 +1,7 @@
/*
* Fundamental constants relating to IP Protocol
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -274,6 +274,7 @@
}
return len;
}
+
#define IPV4_ISMULTI(a) (((a) & 0xf0000000) == 0xe0000000)
#define IPV4_MCAST_TO_ETHER_MCAST(ipv4, ether) \
diff --git a/include/bcmipv6.h b/include/bcmipv6.h
index b9861ad..fbeb8ce 100644
--- a/include/bcmipv6.h
+++ b/include/bcmipv6.h
@@ -1,7 +1,7 @@
/*
* Fundamental constants relating to Neighbor Discovery Protocol
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/bcmmsgbuf.h b/include/bcmmsgbuf.h
index 9d4c2fe..6fd84a2 100644
--- a/include/bcmmsgbuf.h
+++ b/include/bcmmsgbuf.h
@@ -4,7 +4,7 @@
*
* Definitions subject to change without notice.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -62,6 +62,8 @@
#define D2HRING_TXCMPLT_ITEMSIZE 24
#define D2HRING_RXCMPLT_ITEMSIZE 40
+#define D2HRING_MDCMPLT_ITEMSIZE 80
+
#define D2HRING_TXCMPLT_ITEMSIZE_PREREV7 16
#define D2HRING_RXCMPLT_ITEMSIZE_PREREV7 32
@@ -75,6 +77,7 @@
#define D2HRING_DYNAMIC_INFO_MAX_ITEM 32
#define H2DRING_TXPOST_MAX_ITEM 512
+#define D2HRING_MDRING_MAX_ITEM 2048
#if defined(DHD_HTPUT_TUNABLES)
#define H2DRING_RXPOST_MAX_ITEM 2048
@@ -269,6 +272,7 @@
MSG_TYPE_TX_STATUS_AGGR = 0x30,
MSG_TYPE_RXBUF_POST_AGGR = 0x31,
MSG_TYPE_RX_CMPLT_AGGR = 0x32,
+ MSG_TYPE_MDATA_CPL = 0x33,
MSG_TYPE_API_MAX_RSVD = 0x3F
} bcmpcie_msg_type_t;
@@ -289,7 +293,8 @@
MSG_TYPE_HMAPTEST_PYLD = 0x4C,
MSG_TYPE_PVT_BT_SNAPSHOT_CMPLT = 0x4D,
MSG_TYPE_BT_SNAPSHOT_PYLD = 0x4E,
- MSG_TYPE_LPBK_DMAXFER_PYLD_ADDR = 0x4F /* loopback from addr pkt */
+ MSG_TYPE_LPBK_DMAXFER_PYLD_ADDR = 0x4F, /* loopback from addr pkt */
+ MSG_TYPE_PCIE_BUS_TPUT = 0x50 /* payload for pcie bus tput measurements */
} bcmpcie_msgtype_int_t;
typedef enum bcmpcie_msgtype_u {
@@ -352,6 +357,10 @@
bcmpcie_msi_offset_t bcmpcie_msi_offset[MSI_INTR_IDX_MAX];
} bcmpcie_msi_offset_config_t;
+typedef struct bcmpcie_mdata_config {
+ uint16 ringid;
+} bcmpcie_mdata_config_t;
+
#define BCMPCIE_D2H_MSI_OFFSET_DEFAULT BCMPCIE_D2H_MSI_OFFSET_DB1
#define BCMPCIE_D2H_MSI_SINGLE 0xFFFE
@@ -371,6 +380,7 @@
#define BCMPCIE_CMNHDR_FLAGS_DMA_R_IDX_INTR 0x2
#define BCMPCIE_CMNHDR_FLAGS_TS_SEQNUM_INIT 0x4
#define BCMPCIE_CMNHDR_FLAGS_WAKE_PACKET 0x8
+#define BCMPCIE_CMNHDR_FLAGS_MDATA_PRESENT 0x10
#define BCMPCIE_CMNHDR_FLAGS_PHASE_BIT 0x80
#define BCMPCIE_CMNHDR_PHASE_BIT_INIT 0x80
#define BCMPCIE_FLOWRING_PHASE_NIBBLE_INIT 0xA0
@@ -550,7 +560,9 @@
typedef enum ring_config_subtype {
/** Default D2H PCIE doorbell override using ring_config_req msg */
D2H_RING_CONFIG_SUBTYPE_SOFT_DOORBELL = 1, /* Software doorbell */
- D2H_RING_CONFIG_SUBTYPE_MSI_DOORBELL = 2 /* MSI configuration */
+ D2H_RING_CONFIG_SUBTYPE_MSI_DOORBELL = 2, /* MSI configuration */
+ D2H_RING_CONFIG_SUBTYPE_MDATA_LINK = 3, /* Metadata ring link */
+ D2H_RING_CONFIG_SUBTYPE_MDATA_UNLINK = 4 /* Metadata ring unlink */
} ring_config_subtype_t;
typedef struct ring_config_req { /* pulled from upcoming rev6 ... */
@@ -564,6 +576,7 @@
bcmpcie_soft_doorbell_t soft_doorbell;
/** D2H_RING_CONFIG_SUBTYPE_MSI_DOORBELL */
bcmpcie_msi_offset_config_t msi_offset;
+ bcmpcie_mdata_config_t mdata_assoc;
};
} ring_config_req_t;
@@ -1002,7 +1015,7 @@
#define BCMPCIE_RX_PKT_RSSI_SHIFT 0u
#define BCMPCIE_RX_PKT_DUR0_MASK 0xFFFF00u
#define BCMPCIE_RX_PKT_DUR0_SHIFT 8u
-#define BCMPCIE_RX_PKT_BAND_MASK 0x1000000u
+#define BCMPCIE_RX_PKT_BAND_MASK 0x3000000u
#define BCMPCIE_RX_PKT_BAND_SHIFT 24u
/* D2H Rxcompletion ring work items for IPC rev7 */
@@ -1165,6 +1178,7 @@
#define BCMPCIE_PKT_FLAGS_FRAME_MESH 0x400u
/* Indicate RX checksum verified and passed */
#define BCMPCIE_PKT_FLAGS_RCSUM_VALID 0x800u
+#define BCMPCIE_PKT_FLAGS_RCSUM_VALID_AGGR 0x01u
/* These are added to fix up compile issues */
#define BCMPCIE_TXPOST_FLAGS_FRAME_802_3 BCMPCIE_PKT_FLAGS_FRAME_802_3
@@ -1608,7 +1622,9 @@
/* each rx buffer work item */
typedef struct host_rxbuf_cmpl_pkt {
/** offset in the host rx buffer where the data starts */
- uint16 data_offset;
+ uint8 data_offset;
+ /** d2h flags */
+ uint8 flags;
/** filled up buffer len to receive data */
uint16 data_len;
/** packet Identifier for the associated host buffer */
@@ -1651,6 +1667,14 @@
TXPOST_EXT_TAG_LEN_MESH = 20u
};
+/* CSO specific information for the cso enabled txpost workitem */
+typedef struct txpost_wi_cso_info_s {
+ txpost_ext_tag_type_t ext_tag; /* extended tag (TXPOST_EXT_TAG_TYPE_CSO) */
+ uint8 pkt_csum_type; /* ipv4|ipv6|tcp|udp|nwk_csum|trans_csum|ph_csum */
+ uint8 nwk_hdr_len; /* IP header length */
+ uint8 trans_hdr_len; /* TCP header length */
+} txpost_wi_cso_info_t;
+
/*
* Note: The only requirement is that the overall size of the workitem be multiple of 8.
* However, each individual ext tag not necessarily 8x.
diff --git a/include/bcmnvram.h b/include/bcmnvram.h
index 372a1f3..2d6af02 100644
--- a/include/bcmnvram.h
+++ b/include/bcmnvram.h
@@ -1,7 +1,7 @@
/*
* NVRAM variable manipulation
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/bcmpcie.h b/include/bcmpcie.h
index 0d72a76..030d424 100644
--- a/include/bcmpcie.h
+++ b/include/bcmpcie.h
@@ -3,7 +3,7 @@
* Software-specific definitions shared between device and host side
* Explains the shared area between host and dongle
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -157,10 +157,13 @@
#define PCIE_SHARED2_LLW2 0x02000000u /* GCR based LLW2 */
#define PCIE_SHARED2_RX_CMPL_PRIO_VALID 0x04000000u /* Prio is valid in Rx Cmpl */
#define PCIE_SHARED2_LPM_SUPPORT 0x08000000u /* LPM mode support */
+#define PCIE_SHARED2_METADATA_RING 0x10000000u /* Metadata Ring support */
#define PCIE_SHARED2_D2H_D11_TX_STATUS 0x40000000
#define PCIE_SHARED2_H2D_D11_TX_STATUS 0x80000000
+#define PCIE_SHARED3_CFG_TRAP_SUPPORT 0x00000001 /* special trap sig supported in config space */
+
#define PCIE_SHARED_D2H_MAGIC 0xFEDCBA09
#define PCIE_SHARED_H2D_MAGIC 0x12345678
@@ -202,9 +205,10 @@
#define BCMPCIE_D2H_RING_TYPE_AC_RX_COMPLETE 0x5
#define BCMPCIE_D2H_RING_TYPE_BTLOG_CPL 0x6
#define BCMPCIE_D2H_RING_TYPE_EDL 0x7
-#define BCMPCIE_D2H_RING_TYPE_HPP_TX_CPL 0x8
-#define BCMPCIE_D2H_RING_TYPE_HPP_RX_CPL 0x9
-#define BCMPCIE_D2H_RING_TYPE_MESH_RX_CPL 0xA
+#define BCMPCIE_D2H_RING_TYPE_HPP_TX_CPL 0x8
+#define BCMPCIE_D2H_RING_TYPE_HPP_RX_CPL 0x9
+#define BCMPCIE_D2H_RING_TYPE_MESH_RX_CPL 0xA
+#define BCMPCIE_D2H_RING_TYPE_MDATA_CPL 0xB
/**
* H2D and D2H, WR and RD index, are maintained in the following arrays:
@@ -488,6 +492,8 @@
#define H2D_HOST_ACK_NOINT 0x00010000 /* d2h_ack interrupt ignore */
#define H2D_HOST_CONS_INT 0x80000000 /**< h2d int for console cmds */
#define H2D_FW_TRAP 0x20000000 /**< h2d force TRAP */
+#define H2D_HOST_PTM_ENABLE 0x01000000 /**< h2d enable PTM */
+#define H2D_HOST_PTM_DISABLE 0x02000000 /**< h2d disable PTM */
#define H2DMB_DS_HOST_SLEEP_INFORM H2D_HOST_D3_INFORM
#define H2DMB_DS_DEVICE_SLEEP_ACK H2D_HOST_DS_ACK
#define H2DMB_DS_DEVICE_SLEEP_NAK H2D_HOST_DS_NAK
@@ -497,6 +503,8 @@
#define H2DMB_HOST_CONS_INT H2D_HOST_CONS_INT
#define H2DMB_DS_DEVICE_WAKE_ASSERT H2DMB_DS_DEVICE_WAKE
#define H2DMB_DS_DEVICE_WAKE_DEASSERT H2DMB_DS_ACTIVE
+#define H2DMB_PTM_ENABLE H2D_HOST_PTM_ENABLE
+#define H2DMB_PTM_DISABLE H2D_HOST_PTM_DISABLE
/* D2H mail box Data */
#define D2H_DEV_D3_ACK 0x00000001
@@ -504,9 +512,13 @@
#define D2H_DEV_DS_EXIT_NOTE 0x00000004
#define D2HMB_DS_HOST_SLEEP_EXIT_ACK 0x00000008
#define D2H_DEV_IDMA_INITED 0x00000010
+#define D2H_DEV_PTM_ENABLED 0x02000000
+#define D2H_DEV_PTM_DISABLED 0x04000000
#define D2HMB_DS_HOST_SLEEP_ACK D2H_DEV_D3_ACK
#define D2HMB_DS_DEVICE_SLEEP_ENTER_REQ D2H_DEV_DS_ENTER_REQ
#define D2HMB_DS_DEVICE_SLEEP_EXIT D2H_DEV_DS_EXIT_NOTE
+#define D2HMB_PTM_ENABLED D2H_DEV_PTM_ENABLED
+#define D2HMB_PTM_DISABLED D2H_DEV_PTM_DISABLED
#define D2H_DEV_MB_MASK (D2H_DEV_D3_ACK | D2H_DEV_DS_ENTER_REQ | \
D2H_DEV_DS_EXIT_NOTE | D2H_DEV_IDMA_INITED)
@@ -523,6 +535,7 @@
/* Indicates whether HMAP violation was Write */
#define D2H_DEV_TRAP_HMAP_WRITE 0x04000000
#define D2H_DEV_TRAP_PING_HOST_FAILURE 0x08000000
+#define D2H_DEV_TRAP_DS_ACK_TIMEOUT 0x00100000u
#define D2H_FWTRAP_MASK 0x0000001F /* Adding maskbits for TRAP information */
#define D2HMB_FWHALT D2H_DEV_FWHALT
diff --git a/include/bcmpcispi.h b/include/bcmpcispi.h
index 71d0e67..76a1716 100644
--- a/include/bcmpcispi.h
+++ b/include/bcmpcispi.h
@@ -1,7 +1,7 @@
/*
* Broadcom PCI-SPI Host Controller Register Definitions
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/bcmperf.h b/include/bcmperf.h
index 7a137b1..8bc2d0e 100644
--- a/include/bcmperf.h
+++ b/include/bcmperf.h
@@ -1,7 +1,7 @@
/*
* Performance counters software interface.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/bcmproto.h b/include/bcmproto.h
index 1444f25..afc4616 100644
--- a/include/bcmproto.h
+++ b/include/bcmproto.h
@@ -1,7 +1,7 @@
/*
* Fundamental constants relating to IP Protocol
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/bcmrand.h b/include/bcmrand.h
index 6cde11f..b2fdf82 100644
--- a/include/bcmrand.h
+++ b/include/bcmrand.h
@@ -1,7 +1,7 @@
/*
* bcmrand.h.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/bcmsdbus.h b/include/bcmsdbus.h
index e7de6f9..168dada 100644
--- a/include/bcmsdbus.h
+++ b/include/bcmsdbus.h
@@ -2,7 +2,7 @@
* Definitions for API from sdio common code (bcmsdh) to individual
* host controller drivers.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/bcmsdh.h b/include/bcmsdh.h
index f825c61..7021da1 100644
--- a/include/bcmsdh.h
+++ b/include/bcmsdh.h
@@ -3,7 +3,7 @@
* export functions to client drivers
* abstract OS and BUS specific details of SDIO
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/bcmsdh_sdmmc.h b/include/bcmsdh_sdmmc.h
index 76bc256..955bd3b 100644
--- a/include/bcmsdh_sdmmc.h
+++ b/include/bcmsdh_sdmmc.h
@@ -1,7 +1,7 @@
/*
* BCMSDH Function Driver for the native SDIO/MMC driver in the Linux Kernel
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/bcmsdpcm.h b/include/bcmsdpcm.h
index 649098d..c5bdade 100644
--- a/include/bcmsdpcm.h
+++ b/include/bcmsdpcm.h
@@ -2,7 +2,7 @@
* Broadcom SDIO/PCMCIA
* Software-specific definitions shared between device and host side
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/bcmspi.h b/include/bcmspi.h
index 0830050..46b5226 100644
--- a/include/bcmspi.h
+++ b/include/bcmspi.h
@@ -1,7 +1,7 @@
/*
* Broadcom SPI Low-Level Hardware Driver API
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/bcmspibrcm.h b/include/bcmspibrcm.h
index f44469f..494b4a8 100644
--- a/include/bcmspibrcm.h
+++ b/include/bcmspibrcm.h
@@ -1,7 +1,7 @@
/*
* SD-SPI Protocol Conversion - BCMSDH->gSPI Translation Layer
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/bcmsrom_fmt.h b/include/bcmsrom_fmt.h
index 478fbde..332a539 100644
--- a/include/bcmsrom_fmt.h
+++ b/include/bcmsrom_fmt.h
@@ -1,7 +1,7 @@
/*
* SROM format definition.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/bcmsrom_tbl.h b/include/bcmsrom_tbl.h
index 87748f5..712e37f 100644
--- a/include/bcmsrom_tbl.h
+++ b/include/bcmsrom_tbl.h
@@ -1,7 +1,7 @@
/*
* Table that encodes the srom formats for PCI/PCIe NICs.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/bcmstdlib_s.h b/include/bcmstdlib_s.h
index 14d5a57..c704933 100644
--- a/include/bcmstdlib_s.h
+++ b/include/bcmstdlib_s.h
@@ -1,7 +1,7 @@
/*
* Broadcom Secure Standard Library.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/bcmtcp.h b/include/bcmtcp.h
index b8c4bc4..804026b 100644
--- a/include/bcmtcp.h
+++ b/include/bcmtcp.h
@@ -1,7 +1,7 @@
/*
* Fundamental constants relating to TCP Protocol
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/bcmtlv.h b/include/bcmtlv.h
index a92db9b..7b68fbe 100644
--- a/include/bcmtlv.h
+++ b/include/bcmtlv.h
@@ -1,7 +1,7 @@
/*
* TLV and XTLV support
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -132,6 +132,10 @@
/* same as parse_tlvs, but stops when found id > key */
const bcm_tlv_t *bcm_parse_ordered_tlvs(const void *buf, uint buflen, uint key);
+/* sub-buffer ptr/len contained inside the elt starting at the given body_offset */
+void bcm_tlv_sub_buffer(const bcm_tlv_t *elt, uint body_offset,
+ const uint8 **buffer, uint8 *buflen);
+
/* find a tlv with DOT11_MNG_PROPR_ID as id, and the given oui and type */
bcm_tlv_t *bcm_find_vendor_ie(const void *tlvs, uint tlvs_len, const char *voui,
uint8 *type, uint type_len);
diff --git a/include/bcmudp.h b/include/bcmudp.h
index 9058563..8e4405a 100644
--- a/include/bcmudp.h
+++ b/include/bcmudp.h
@@ -1,7 +1,7 @@
/*
* Fundamental constants relating to UDP Protocol
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/bcmutils.h b/include/bcmutils.h
index 66c416b..1d3560c 100644
--- a/include/bcmutils.h
+++ b/include/bcmutils.h
@@ -1,7 +1,7 @@
/*
* Misc useful os-independent macros and functions.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -145,7 +145,33 @@
#define SPINWAIT_TRAP(exp, us) SPINWAIT(exp, us)
+#elif defined(PHY_REG_TRACE_FRAMEWORK)
+#include <phy_utils_log_api.h>
+#define SPINWAIT(exp, us) { \
+ uint countdown = (us) + (SPINWAIT_POLL_PERIOD - 1U); \
+ phy_utils_log_spinwait_start_api(); \
+ while (((exp) != 0) && (uint)(countdown >= SPINWAIT_POLL_PERIOD)) { \
+ OSL_DELAY(SPINWAIT_POLL_PERIOD); \
+ countdown -= SPINWAIT_POLL_PERIOD; \
+ } \
+ phy_utils_log_spinwait_end_api(us, countdown); \
+}
+
+#define SPINWAIT_TRAP(exp, us) { \
+ uint countdown = (us) + (SPINWAIT_POLL_PERIOD - 1U); \
+ phy_utils_log_spinwait_start_api(); \
+ while (((exp) != 0) && (uint)(countdown >= SPINWAIT_POLL_PERIOD)) { \
+ OSL_DELAY(SPINWAIT_POLL_PERIOD); \
+ countdown -= SPINWAIT_POLL_PERIOD; \
+ } \
+ phy_utils_log_spinwait_end_api(us, countdown); \
+ if ((exp)) { \
+ OSL_SYS_HALT(); \
+ } \
+}
+
#else
+
#define SPINWAIT(exp, us) { \
uint countdown = (us) + (SPINWAIT_POLL_PERIOD - 1U); \
while (((exp) != 0) && (uint)(countdown >= SPINWAIT_POLL_PERIOD)) { \
@@ -154,6 +180,12 @@
} \
}
+/* No TRAP in bootloader */
+#if defined(BCM_BOOTLOADER)
+#define SPINWAIT_TRAP(x, y) SPINWAIT(x, y)
+
+#else /* !BCM_BOOTLOADER */
+
#define SPINWAIT_TRAP(exp, us) { \
uint countdown = (us) + (SPINWAIT_POLL_PERIOD - 1U); \
while (((exp) != 0) && (uint)(countdown >= SPINWAIT_POLL_PERIOD)) { \
@@ -164,6 +196,8 @@
OSL_SYS_HALT(); \
} \
}
+#endif /* BCM_BOOTLOADER */
+
#endif /* BCMFUZZ */
/* forward definition of ether_addr structure used by some function prototypes */
@@ -640,6 +674,45 @@
}
#endif /* BCMUTILS_ERR_CODES */
+#ifndef STRIP_PARENS
+/* DROP Parenthesis from the ARGS
+ * if ARG=(a,b,c) including parens, then ARG is evaluated as 1 argument not 3
+ * MACRO(ARG)==MACRO((a,b,c)), but MACRO(STRIP_PARENS(ARG))==MACRO(a,b,c)
+ */
+#undef __STRIP_PARENS
+#undef _STRIP_PARENS
+#define __STRIP_PARENS(...) __VA_ARGS__
+#define _STRIP_PARENS(X) X
+#define STRIP_PARENS(X) _STRIP_PARENS(__STRIP_PARENS X)
+#endif
+
+/* CONCAT 2 args to make single string that can be evaluated as MACRO */
+#ifndef CONCATENATE
+#undef __CONCATENATE
+#define __CONCATENATE(a, b) a ## b
+#define CONCATENATE(a, b) __CONCATENATE(a, b)
+#endif
+
+/* CONCAT as synonym to CONCATENATE */
+#ifndef CONCAT
+#define CONCAT(a, b) CONCATENATE(a, b)
+#endif
+
+#ifndef COUNT_ARGS
+/* returns the count of argument passed to COUNT_ARGS
+ * order or arguments to COUNT_ARGS_ is dummy, __VA_ARGS__, 30..0
+ * a30 is returned if NARGS is 30 and a0 if NARGS is 0
+ * e.g. for case when
+ * 30 Args are prsent, we will have dummy, a30-a1(args passed), and a0 == 30
+ * 5 Args present, dummy, a30-a26(args passed) a25-a1==30-6, and a0 == 5
+ */
+#undef __COUNT_ARGS
+#define __COUNT_ARGS(dummy, a30, a29, a28, a27, a26, a25, a24, a23, a22, a21, a20, a19, a18, \
+ a17, a16, a15, a14, a13, a12, a11, a10, a9, a8, a7, a6, a5, a4, a3, a2, a1, a0, ...) a0
+#define COUNT_ARGS(...) __COUNT_ARGS(dummy, ##__VA_ARGS__, 30, 29, 28, 27, 26, 25, 24, 23, 22, \
+ 21, 20, 19, 18, 17, 16, 15, 14, 13, 12, 11, 10, 9, 8, 7, 6, 5, 4, 3, 2, 1, 0)
+#endif
+
#ifndef ABS
#define ABS(a) (((a) < 0) ? -(a) : (a))
#endif /* ABS */
@@ -902,19 +975,25 @@
* If you want to use this macro to the logic,
* USE MACF instead
*/
-#if !defined(SIMPLE_MAC_PRINT)
-#define MACDBG "%02x:%02x:%02x:%02x:%02x:%02x"
-#define MAC2STRDBG(ea) ((const uint8*)(ea))[0], \
+#define MACDBG_FULL "%02x:%02x:%02x:%02x:%02x:%02x"
+#define MAC2STRDBG_FULL(ea) ((const uint8*)(ea))[0], \
((const uint8*)(ea))[1], \
((const uint8*)(ea))[2], \
((const uint8*)(ea))[3], \
((const uint8*)(ea))[4], \
((const uint8*)(ea))[5]
-#else
-#define MACDBG "%02x:xx:xx:xx:x%x:%02x"
-#define MAC2STRDBG(ea) ((const uint8*)(ea))[0], \
+
+#define MACDBG_SIMPLE "%02x:xx:xx:xx:x%x:%02x"
+#define MAC2STRDBG_SIMPLE(ea) ((const uint8*)(ea))[0], \
(((const uint8*)(ea))[4] & 0xf), \
((const uint8*)(ea))[5]
+
+#if !defined(SIMPLE_MAC_PRINT)
+#define MACDBG MACDBG_FULL
+#define MAC2STRDBG MAC2STRDBG_FULL
+#else
+#define MACDBG MACDBG_SIMPLE
+#define MAC2STRDBG MAC2STRDBG_SIMPLE
#endif /* SIMPLE_MAC_PRINT */
#define MACOUIDBG "%02x:%x:%02x"
@@ -1000,6 +1079,8 @@
extern void printbig(char *buf);
extern void prhex(const char *msg, const uchar *buf, uint len);
extern void prhexstr(const char *prefix, const uint8 *buf, uint len, bool newline);
+/* print the buffer in hex string format with the most significant byte first */
+extern void prhexstr_msb(const char *prefix, const uint8 *buf, uint len, bool newline);
/* bcmerror */
extern const char *bcmerrorstr(int bcmerror);
@@ -1034,6 +1115,10 @@
#define bcm_breset(b) do {bcm_binit(b, (b)->origbuf, (b)->origsize);} while (0)
extern void bcm_bprhex(struct bcmstrbuf *b, const char *msg, bool newline,
const uint8 *buf, uint len);
+/* print the buffer in hex string format with the most significant byte first */
+extern void bcm_bprhex_msb(struct bcmstrbuf *b, const char *msg, bool newline,
+ const uint8 *buf, uint len);
+extern int bcm_bprintf(struct bcmstrbuf *b, const char *fmt, ...);
extern void bcm_inc_bytes(uchar *num, int num_bytes, uint8 amount);
extern int bcm_cmp_bytes(const uchar *arg1, const uchar *arg2, uint8 nbytes);
@@ -1043,8 +1128,7 @@
extern uint bcmdumpfields(bcmutl_rdreg_rtn func_ptr, void *arg0, uint arg1, struct fielddesc *str,
char *buf, uint32 bufsize);
extern uint bcm_bitcount(const uint8 *bitmap, uint bytelength);
-
-extern int bcm_bprintf(struct bcmstrbuf *b, const char *fmt, ...);
+uint bcm_count_bits(const uint8 *buf, uint buf_len, uint from_bit, uint to_bit, bool val_1);
/* power conversion */
extern uint16 bcm_qdbm_to_mw(uint8 qdbm);
@@ -1114,7 +1198,8 @@
#define BCM_OBJECT_FEATURE_2 (1 << 2)
/* object feature: clear flag bits field set with this flag */
#define BCM_OBJECT_FEATURE_CLEAR (1 << 31)
-#if defined(BCM_OBJECT_TRACE) && !defined(BINCMP)
+#if defined(BCM_OBJECT_TRACE)
+#if !defined(BINCMP)
#define bcm_pkt_validate_chk(obj, func) do { \
void * pkttag; \
bcm_object_trace_chk(obj, 0, 0, \
@@ -1124,6 +1209,18 @@
func, __LINE__); \
} \
} while (0)
+#else /* BINCMP */
+/* Suppress line numbers in binary-comparison builds. Otherwise identical to above. */
+#define bcm_pkt_validate_chk(obj, func) do { \
+ void * pkttag; \
+ bcm_object_trace_chk(obj, 0, 0, \
+ func, 1); \
+ if ((pkttag = PKTTAG(obj))) { \
+ bcm_object_trace_chk(obj, 1, DHD_PKTTAG_SN(pkttag), \
+ func, 1); \
+ } \
+} while (0)
+#endif /* !BINCMP */
extern void bcm_object_trace_opr(void *obj, uint32 opt, const char *caller, int line);
extern void bcm_object_trace_upd(void *obj, void *obj_new);
extern void bcm_object_trace_chk(void *obj, uint32 chksn, uint32 sn,
@@ -1141,7 +1238,7 @@
#define bcm_object_feature_get(a, b, c)
#define bcm_object_trace_init()
#define bcm_object_trace_deinit()
-#endif /* BCM_OBJECT_TRACE && !BINCMP */
+#endif /* BCM_OBJECT_TRACE */
/* Public domain bit twiddling hacks/utilities: Sean Eron Anderson */
@@ -1362,6 +1459,7 @@
node_p->next_p = node_p;
node_p->prev_p = node_p;
}
+
/* dll macros returing a pointer to dll_t */
static INLINE_ALWAYS dll_t *
@@ -1527,8 +1625,8 @@
#define CALL_SITE ((void*) 0)
#endif
#ifdef SHOW_LOGTRACE
-#define TRACE_LOG_BUF_MAX_SIZE 1700
-#define RTT_LOG_BUF_MAX_SIZE 1700
+#define TRACE_LOG_BUF_MAX_SIZE 1900
+#define RTT_LOG_BUF_MAX_SIZE 1900
#define BUF_NOT_AVAILABLE 0
#define NEXT_BUF_NOT_AVAIL 1
#define NEXT_BUF_AVAIL 2
diff --git a/include/bcmwifi_channels.h b/include/bcmwifi_channels.h
index ed8af10..e6dd674 100644
--- a/include/bcmwifi_channels.h
+++ b/include/bcmwifi_channels.h
@@ -3,7 +3,7 @@
* This header file housing the define and function prototype use by
* both the wl driver, tools & Apps.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -958,4 +958,8 @@
uint8 wf_chspec_240_id2cch(chanspec_t chanspec);
+#ifndef WL_BW320MHZ
+#define wf_chspec_center_channel(chspec) CHSPEC_CHANNEL(chspec)
+#endif /* !WL_BW320MHZ */
+
#endif /* _bcmwifi_channels_h_ */
diff --git a/include/bcmwifi_rates.h b/include/bcmwifi_rates.h
index afec325..36b6e72 100644
--- a/include/bcmwifi_rates.h
+++ b/include/bcmwifi_rates.h
@@ -1,7 +1,7 @@
/*
* Indices for 802.11 a/b/g/n/ac 1-3 chain symmetric transmit rates
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/bcmwifi_rspec.h b/include/bcmwifi_rspec.h
index 6fad571..7ab1f09 100644
--- a/include/bcmwifi_rspec.h
+++ b/include/bcmwifi_rspec.h
@@ -1,7 +1,7 @@
/*
* Common OS-independent driver header for rate management.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/brcm_nl80211.h b/include/brcm_nl80211.h
index 5719324..fb61d45 100644
--- a/include/brcm_nl80211.h
+++ b/include/brcm_nl80211.h
@@ -1,7 +1,7 @@
/*
* Definitions for nl80211 vendor command/event access to host driver
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -40,7 +40,8 @@
BRCM_VENDOR_SCMD_SET_CONNECT_PARAMS = 7,
BRCM_VENDOR_SCMD_SET_START_AP_PARAMS = 8,
BRCM_VENDOR_SCMD_ACS = 9,
- BRCM_VENDOR_SCMD_MAX = 10
+ BRCM_VENDOR_SCMD_SET_TD_POLICY = 10,
+ BRCM_VENDOR_SCMD_MAX = 11
};
struct bcm_nlmsg_hdr {
diff --git a/include/dbus.h b/include/dbus.h
index 0e5da0e..5c35040 100644
--- a/include/dbus.h
+++ b/include/dbus.h
@@ -2,7 +2,7 @@
* Dongle BUS interface Abstraction layer
* target serial buses like USB, SDIO, SPI, etc.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -19,7 +19,7 @@
* modifications of the software.
*
*
- * <<Broadcom-WL-IPTag/Open:>>
+ * <<Broadcom-WL-IPTag/Dual:>>
*/
#ifndef __DBUS_H__
diff --git a/include/dhd_daemon.h b/include/dhd_daemon.h
index c60a6f6..f71d029 100644
--- a/include/dhd_daemon.h
+++ b/include/dhd_daemon.h
@@ -1,7 +1,7 @@
/*
* Header file for DHD daemon to handle timeouts
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/dhdioctl.h b/include/dhdioctl.h
index 38842a7..ad2e066 100644
--- a/include/dhdioctl.h
+++ b/include/dhdioctl.h
@@ -5,7 +5,7 @@
*
* Definitions subject to change without notice.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -299,6 +299,17 @@
#define DHD_PKTGEN_RECV 4 /* Continuous rx from continuous tx dongle */
#endif /* SDTEST */
+/* For membytes iovar - flags param bit definitions and accessor macros */
+#define DHD_MEMBYTES_FLAGS_MAGIC 0x5DA60900 /* indicates flags presence */
+#define DHD_MEMBYTES_FLAGS_MAGIC_MASK 0xFFFFFF00 /* magic bytes mask */
+#define DHD_MEMBYTES_FLAGS_BAR_MASK 0x00000007 /* bar region mask */
+#define DHD_MEMBYTES_FLAGS_BAR_MIN 0 /* Min valid value for BAR region */
+#define DHD_MEMBYTES_FLAGS_BAR_MAX 5 /* Max valid value for BAR region */
+#define DHD_MEMBYTES_FLAGS_INIT(x) ((x) = ((uint32)DHD_MEMBYTES_FLAGS_MAGIC))
+#define DHD_MEMBYTES_FLAGS_GET_MAGIC(x) ((x) & DHD_MEMBYTES_FLAGS_MAGIC_MASK)
+#define DHD_MEMBYTES_FLAGS_GET_BAR(x) ((x) & DHD_MEMBYTES_FLAGS_BAR_MASK)
+#define DHD_MEMBYTES_FLAGS_SET_BAR(x, b) ((x) |= ((b) & DHD_MEMBYTES_FLAGS_BAR_MASK))
+
/* Enter idle immediately (no timeout) */
#define DHD_IDLE_IMMEDIATE (-1)
diff --git a/include/dngl_rtlv.h b/include/dngl_rtlv.h
index 1f97715..a1a14ad 100644
--- a/include/dngl_rtlv.h
+++ b/include/dngl_rtlv.h
@@ -1,7 +1,7 @@
/*
* Interface definitions for reversed TLVs
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/dngl_stats.h b/include/dngl_stats.h
index 77c8f02..0d38086 100644
--- a/include/dngl_stats.h
+++ b/include/dngl_stats.h
@@ -2,7 +2,7 @@
* Common stats definitions for clients of dongle
* ports
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/dnglevent.h b/include/dnglevent.h
index c54b2c5..5cff81d 100644
--- a/include/dnglevent.h
+++ b/include/dnglevent.h
@@ -3,7 +3,7 @@
*
* Dependencies: bcmeth.h
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -50,6 +50,7 @@
#define DNGL_E_RSRVD_2 0x1
#define DNGL_E_SOCRAM_IND 0x2
#define DNGL_E_PROFILE_DATA_IND 0x3
+#define DNGL_E_SPMI_RESET_IND 0x4
typedef BWL_PRE_PACKED_STRUCT struct
{
uint16 version; /* Current version is 1 */
@@ -77,6 +78,16 @@
uint8 value[];
} BWL_POST_PACKED_STRUCT bcm_dngl_profile_data_ind_t;
+#define DNGL_E_SPMI_RESET_IND_VERSION_1 1u
+#define DNGL_E_SPMI_RESET_IND_VERSION DNGL_E_SPMI_RESET_IND_VERSION_1
+
+typedef BWL_PRE_PACKED_STRUCT struct bcm_dngl_spmi_reset_ind_v1_t {
+ uint16 version; /* Current version is 1 */
+ uint16 num_resets; /* number of resets seen since last message */
+ uint8 slave_idx; /* Slave idx of the SPMI core that was reset */
+ uint8 PAD[3];
+} BWL_POST_PACKED_STRUCT bcm_dngl_spmi_reset_ind_v1_t;
+
typedef BWL_PRE_PACKED_STRUCT struct bcm_dngl_arm_event {
uint32 type;
uint32 value;
@@ -144,6 +155,7 @@
#define HEALTH_CHECK_PCIEDEV_RXPOST_LONG_IND 0xB
#define HEALTH_CHECK_PCIEDEV_PTM_DRIFT_IND 0xC
#define HEALTH_CHECK_PCIEDEV_PTM_FAIL_IND 0xD
+#define HEALTH_CHECK_PCIEDEV_PTM_TIMEOUT_IND 0xE
#define HC_PCIEDEV_CONFIG_REGLIST_MAX 25
typedef BWL_PRE_PACKED_STRUCT struct bcm_dngl_pcie_hc {
diff --git a/include/dnglioctl.h b/include/dnglioctl.h
index e381b4d..5c18d6a 100644
--- a/include/dnglioctl.h
+++ b/include/dnglioctl.h
@@ -1,7 +1,7 @@
/*
* HND Run Time Environment ioctl.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -92,7 +92,8 @@
BUS_GET_MAXITEMS = 16,
BUS_SET_BUS_CSO_CAP = 17, /* Update the CSO cap from wl layer to bus layer */
BUS_DUMP_RX_DMA_STALL_RELATED_INFO = 18,
- BUS_UPDATE_RESVPOOL_STATE = 19 /* Update resvpool state */
+ BUS_UPDATE_RESVPOOL_STATE = 19, /* Update resvpool state */
+ BUS_GET_MAX_RING_NUM = 20 /* Get the Max num of the Tx rings */
};
#define SDPCMDEV_SET_MAXTXPKTGLOM 1
@@ -116,6 +117,65 @@
uint32 mf_count; /* Malloc failure count */
} memuse_info_t;
+#define RTE_POOLUSEINFO_VER 0x01
+typedef struct pooluse_info {
+ uint16 ver; /* version of this struct */
+ uint16 len; /* length in bytes of this structure */
+
+ uint32 shared_count; /* pktpool_shared pkt count */
+ uint32 shared_available; /* pktpool_shared pkt left */
+ uint32 shared_max_pkt_bytes; /* pktpool_shared max pkt size */
+ uint32 shared_overhead; /* pktpool_shared with overhead */
+
+ uint32 lfrag_count; /* pktpool_shared_lfrag pkt count */
+ uint32 lfrag_available; /* pktpool_shared_lfrag pkt left */
+ uint32 lfrag_max_pkt_bytes; /* pktpool_shared_lfrag max pkt size */
+ uint32 lfrag_overhead; /* pktpool_shared_lfrag with overhead */
+
+ uint32 resvlfrag_count; /* pktpool_resv_lfrag pkt count */
+ uint32 resvlfrag_available; /* pktpool_resv_lfrag pkt left */
+ uint32 resvlfrag_max_pkt_bytes; /* pktpool_resv_lfrag max pkt size */
+ uint32 resvlfrag_overhead; /* pktpool_resv_lfrag with overhead */
+
+ uint32 rxlfrag_count; /* pktpool_shared_rxlfrag pkt count */
+ uint32 rxlfrag_available; /* pktpool_shared_rxlfrag pkt left */
+ uint32 rxlfrag_max_pkt_bytes; /* pktpool_shared_rxlfrag max pkt size */
+ uint32 rxlfrag_overhead; /* pktpool_shared_rxlfrag with overhead */
+
+ uint32 rxdata_count; /* pktpool_shared_rxdata pkt count */
+ uint32 rxdata_available; /* pktpool_shared_rxdata pkt left */
+ uint32 rxdata_max_pkt_bytes; /* pktpool_shared_rxdata max pkt size */
+ uint32 rxdata_overhead; /* pktpool_shared_rxdata with overhead */
+
+ uint32 alfrag_count; /* pktpool_shared_alfrag pkt count */
+ uint32 alfrag_available; /* pktpool_shared_alfrag pkt left */
+ uint32 alfrag_max_pkt_bytes; /* pktpool_shared_alfrag max pkt size */
+ uint32 alfrag_overhead; /* pktpool_shared_alfrag with overhead */
+
+ uint32 alfragdata_count; /* pktpool_shared_alfrag_data pkt count */
+ uint32 alfragdata_available; /* pktpool_shared_alfrag_data pkt left */
+ uint32 alfragdata_max_pkt_bytes; /* pktpool_shared_alfrag_data max pkt size */
+ uint32 alfragdata_overhead; /* pktpool_shared_alfrag_data with overhead */
+
+ uint32 resvalfrag_count; /* pktpool_resv_alfrag pkt count */
+ uint32 resvalfrag_available; /* pktpool_resv_alfrag pkt left */
+ uint32 resvalfrag_max_pkt_bytes; /* pktpool_resv_alfrag max pkt size */
+ uint32 resvalfrag_overhead; /* pktpool_resv_alfrag with overhead */
+
+ uint32 resvalfragdata_count; /* pktpool_resv_alfrag_data pkt count */
+ uint32 resvalfragdata_available; /* pktpool_resv_alfrag_data pkt left */
+ uint32 resvalfragdata_max_pkt_bytes; /* pktpool_resv_alfrag_data max pkt size */
+ uint32 resvalfragdata_overhead; /* pktpool_resv_alfrag_data with overhead */
+
+ uint32 total_size; /* pktpool total size in bytes */
+ uint32 total_overhead; /* pktpool total with overhead */
+} pooluse_info_t;
+
+typedef struct memuse_ext_info {
+ memuse_info_t hu; /* heap usage */
+ pooluse_info_t pu; /* pktpool usage */
+} memuse_ext_info_t;
+
/* Different DMA loopback modes */
#define M2M_DMA_LOOPBACK 0 /* PCIE M2M mode */
#define D11_DMA_LOOPBACK 1 /* PCIE M2M and D11 mode without ucode */
@@ -268,4 +328,104 @@
DSEC_OTP_XTLV_SBOOT_ENCRYPTION_KEY = 28u, /* AES wrapped fw encryption key 320 bits */
DSEC_OTP_XTLV_SBOOT_LOT_NUM_MS = 29u, /* Chip lot num high bits [17:47] 31 bits */
};
+
+#define CAPEXT_INFO_VERSION_1 (1u)
+#define CAPEXT_INFO_VERSION CAPEXT_INFO_VERSION_1
+
+/* Top structure of capext reporting. For reporting, feature ids are used as types in XTLVs */
+typedef struct {
+ uint16 version; /**< see definition of CAPEXT_INFO_VERSION */
+ uint16 datalen; /**< length of data including all paddings. */
+ uint8 data []; /**< variable length payload:
+ * 1 or more bcm_xtlv_t type of tuples.
+ * each tuple is padded to multiple of 4 bytes.
+ * 'datalen' field of this structure includes all paddings.
+ */
+} capext_info_t;
+
+/* Each feature reported in capext has a feature id. Feature id is a 16-bit value.
+ * The feature id namespace is split into 3 partitions. One for BUS, the second for RTE,
+ * and the third for WL. All partitions are contiguous and fixed in size
+ */
+#define CAPEXT_FEATURE_ID_NUM_PARTITIONS (3u)
+#define CAPEXT_FEATURE_ID_PARTITION_SIZE (1024u)
+/* Feature IDs from 3072 for capext are reserved */
+#define CAPEXT_RSVD_FEATURE_ID_BASE (3072u)
+
+/* Bus partition */
+/* The features listed in the enumeration below have subfeatures.
+ * If a new feature is added/updated and that feature has sub-features that need to be reported,
+ * add that feature here
+ */
+#define CAPEXT_BUS_FEATURE_ID_BASE (0)
+enum capext_bus_feature_ids {
+ CAPEXT_BUS_FEATURE_RSVD = (CAPEXT_BUS_FEATURE_ID_BASE + 0),
+ /* BUS top level feature id to hold and report bitmaps of features with and
+ * without sub-features.
+ */
+ CAPEXT_BUS_FEATURE_BUS_FEATURES = (CAPEXT_BUS_FEATURE_ID_BASE + 1),
+ /* BUS feature ids below hold and report sub-feature bitmaps of some features
+ * mentioned in top level feature id bitmap
+ */
+ CAPEXT_BUS_FEATURE_PKTLAT = (CAPEXT_BUS_FEATURE_ID_BASE + 2),
+ CAPEXT_BUS_FEATURE_MAX
+};
+
+/* BUS features bit positions in top level rte feature id. Features mentioned below are reported */
+enum capext_bus_feature_bitpos {
+ CAPEXT_BUS_FEATURE_BITPOS_HP2P = 0,
+ CAPEXT_BUS_FEATURE_BITPOS_PTM = 1,
+ CAPEXT_BUS_FEATURE_BITPOS_PKTLAT = 2, /* feature with sub-features */
+ CAPEXT_BUS_FEATURE_BITPOS_MAX
+};
+
+/* Packet latency sub-feature bit positions. These sub-features need to be reported */
+enum capext_pktlat_subfeature_bitpos {
+ CAPEXT_PKTLAT_BITPOS_META = 0,
+ CAPEXT_PKTLAT_BITPOS_IPC = 1,
+ CAPEXT_PKTLAT_BITPOS_MAX
+};
+
+/* RTE partition */
+/* The features listed in the enumeration below have subfeatures.
+ * If a new feature is added and that feature has sub-features that need to be reported,
+ * add that feature here
+ */
+#define CAPEXT_RTE_FEATURE_ID_BASE (1024u)
+enum capext_rte_feature_ids {
+ CAPEXT_RTE_FEATURE_RSVD = (CAPEXT_RTE_FEATURE_ID_BASE + 0),
+ /* RTE top level feature id to hold and report bitmaps of features with and
+ * without sub-features.
+ */
+ CAPEXT_RTE_FEATURE_RTE_FEATURES = (CAPEXT_RTE_FEATURE_ID_BASE + 1),
+ /* RTE feature ids below hold and report sub-feature bitmaps of some features
+ * mentioned in top level feature id bitmap
+ */
+ CAPEXT_RTE_FEATURE_ECOUNTERS = (CAPEXT_RTE_FEATURE_ID_BASE + 2),
+ CAPEXT_RTE_FEATURE_MAX
+};
+
+/* Ecounters sub-feature bit positions. These sub-features need to be reported */
+enum capext_ecounters_subfeature_bitpos {
+ CAPEXT_ECOUNTERS_BITPOS_TXHIST = 0,
+ CAPEXT_ECOUNTERS_BITPOS_ADV = 1,
+ CAPEXT_ECOUNTERS_BITPOS_PHY = 2,
+ CAPEXT_ECOUNTERS_BITPOS_PHY_CAL = 3,
+ CAPEXT_ECOUNTERS_BITPOS_MAX
+};
+
+/* RTE features bit positions in top level rte feature id. Features mentioned below are reported */
+enum capext_rte_feature_bitpos {
+ CAPEXT_RTE_FEATURE_BITPOS_H2D_LOG_TIME_SYNC = 0,
+ CAPEXT_RTE_FEATURE_BITPOS_HWRNG = 1,
+ CAPEXT_RTE_FEATURE_BITPOS_SPMI = 2,
+ CAPEXT_RTE_FEATURE_BITPOS_ECOUNTERS = 3, /* feature with sub-features */
+ CAPEXT_RTE_FEATURE_BITPOS_EVENT_LOG = 4,
+
+ CAPEXT_RTE_FEATURE_BITPOS_LOGTRACE = 5,
+ CAPEXT_RTE_FEATURE_BITPOS_HCHK = 6,
+ CAPEXT_RTE_FEATURE_BITPOS_SMD = 7,
+ CAPEXT_RTE_FEATURE_BITPOS_ETD = 8,
+ CAPEXT_RTE_FEATURE_BITPOS_MAX
+};
#endif /* _dngl_ioctl_h_ */
diff --git a/include/eap.h b/include/eap.h
index ac0d141..30af8dd 100644
--- a/include/eap.h
+++ b/include/eap.h
@@ -4,7 +4,7 @@
* See
* RFC 2284: PPP Extensible Authentication Protocol (EAP)
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/eapol.h b/include/eapol.h
index c44462c..495ce20 100644
--- a/include/eapol.h
+++ b/include/eapol.h
@@ -5,7 +5,7 @@
* IEEE Std 802.1X-2001
* IEEE 802.1X RADIUS Usage Guidelines
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -237,15 +237,26 @@
uint8 data[BCM_FLEX_ARRAY];
} BWL_POST_PACKED_STRUCT eapol_wpa2_encap_data_t;
-#define EAPOL_WPA2_ENCAP_DATA_HDR_LEN 6
+#define EAPOL_WPA2_ENCAP_DATA_HDR_LEN 6u
-#define WPA2_KEY_DATA_SUBTYPE_GTK 1
-#define WPA2_KEY_DATA_SUBTYPE_STAKEY 2
-#define WPA2_KEY_DATA_SUBTYPE_MAC 3
-#define WPA2_KEY_DATA_SUBTYPE_PMKID 4
-#define WPA2_KEY_DATA_SUBTYPE_IGTK 9
-#define WPA2_KEY_DATA_SUBTYPE_OCI 13
-#define WPA2_KEY_DATA_SUBTYPE_BIGTK 14
+#define WPA2_KEY_DATA_SUBTYPE_GTK 1
+#define WPA2_KEY_DATA_SUBTYPE_STAKEY 2
+#define WPA2_KEY_DATA_SUBTYPE_MAC 3
+#define WPA2_KEY_DATA_SUBTYPE_PMKID 4
+#define WPA2_KEY_DATA_SUBTYPE_IGTK 9
+#define WPA2_KEY_DATA_SUBTYPE_OCI 13
+#define WPA2_KEY_DATA_SUBTYPE_BIGTK 14
+#define WPA2_KEY_DATA_SUBTYPE_MLO_GTK 16
+#define WPA2_KEY_DATA_SUBTYPE_MLO_IGTK 17
+#define WPA2_KEY_DATA_SUBTYPE_MLO_BIGTK 18
+#define WPA2_KEY_DATA_SUBTYPE_MLO_LINK_KDE 19
+
+#define WPA2_GTK_INDEX_MASK 0x03
+#define WPA2_GTK_INDEX_SHIFT 0x00
+#define WPA2_GTK_TRANSMIT 0x04
+#define WPA2_MLO_GTK_LINK_ID_MASK 0xF0u
+#define WPA2_MLO_GTK_LINK_ID_SHIFT 0x4u
+#define EAPOL_WPA2_KEY_GTK_ENCAP_HDR_LEN 2u
/* GTK encapsulation */
typedef BWL_PRE_PACKED_STRUCT struct {
@@ -254,12 +265,15 @@
uint8 gtk[EAPOL_WPA_MAX_KEY_SIZE];
} BWL_POST_PACKED_STRUCT eapol_wpa2_key_gtk_encap_t;
-#define EAPOL_WPA2_KEY_GTK_ENCAP_HDR_LEN 2
+#define EAPOL_WPA2_KEY_MLO_GTK_ENCAP_HDR_LEN 7u
+/* MLO GTK encapsulation */
+typedef BWL_PRE_PACKED_STRUCT struct {
+ uint8 flags; /* KeyID [0-1], Tx [2], rsvd [3], link_id [4-7] */
+ uint8 PN[6]; /* Packet number */
+ uint8 gtk[EAPOL_WPA_MAX_KEY_SIZE];
+} BWL_POST_PACKED_STRUCT eapol_wpa2_key_mlo_gtk_encap_t;
-#define WPA2_GTK_INDEX_MASK 0x03
-#define WPA2_GTK_INDEX_SHIFT 0x00
-
-#define WPA2_GTK_TRANSMIT 0x04
+#define EAPOL_WPA2_KEY_IGTK_ENCAP_HDR_LEN 8u
/* IGTK encapsulation */
#define EAPOL_RSN_IPN_SIZE 6u
@@ -269,17 +283,51 @@
uint8 key[EAPOL_WPA_MAX_KEY_SIZE];
} BWL_POST_PACKED_STRUCT eapol_wpa2_key_igtk_encap_t;
-#define EAPOL_WPA2_KEY_IGTK_ENCAP_HDR_LEN 8u
+#define EAPOL_WPA2_KEY_MLO_IGTK_ENCAP_HDR_LEN 9u
+
+/* MLO IGTK encapsulation */
+typedef BWL_PRE_PACKED_STRUCT struct {
+ uint16 key_id;
+ uint8 ipn[EAPOL_RSN_IPN_SIZE];
+ uint8 link_id; /* rsvd [0-3], link_id [4-7] */
+ uint8 key[EAPOL_WPA_MAX_KEY_SIZE];
+} BWL_POST_PACKED_STRUCT eapol_wpa2_key_mlo_igtk_encap_t;
/* BIGTK encapsulation */
#define EAPOL_RSN_BIPN_SIZE 6u
+#define EAPOL_WPA2_KEY_BIGTK_ENCAP_HDR_LEN 8u
+
typedef BWL_PRE_PACKED_STRUCT struct {
- uint16 key_id;
- uint8 bipn[EAPOL_RSN_BIPN_SIZE];
- uint8 key[EAPOL_WPA_MAX_KEY_SIZE];
+ uint16 key_id;
+ uint8 bipn[EAPOL_RSN_BIPN_SIZE];
+ uint8 key[EAPOL_WPA_MAX_KEY_SIZE];
} BWL_POST_PACKED_STRUCT eapol_wpa2_key_bigtk_encap_t;
-#define EAPOL_WPA2_KEY_BIGTK_ENCAP_HDR_LEN 8u
+/* MLO BIGTK encapsulation */
+#define EAPOL_RSN_MLO_BIPN_SIZE 6u
+#define EAPOL_WPA2_KEY_MLO_BIGTK_ENCAP_HDR_LEN 9u
+
+typedef BWL_PRE_PACKED_STRUCT struct {
+ uint16 key_id;
+ uint8 bipn[EAPOL_RSN_MLO_BIPN_SIZE];
+ uint8 link_id; /* rsvd [0-3], link_id [4-7] */
+ uint8 key[EAPOL_WPA_MAX_KEY_SIZE];
+} BWL_POST_PACKED_STRUCT eapol_wpa2_key_mlo_bigtk_encap_t;
+
+#define EAPOL_WPA2_LINK_INFO_LINKID_MASK (0xFu)
+#define EAPOL_WPA2_LINK_INFO_RSNE_PRESENT (0x1u << 4u)
+#define EAPOL_WPA2_LINK_INFO_RSNXE_PRESENT (0x1u << 5u)
+#define EAPOL_WPA2_LINK_KDE_ENCAP_HDR_LEN 7u
+/* Minimum length of WPA2 GTK encapsulation in EAPOL */
+#define EAPOL_WPA2_LINK_KDE_ENCAP_MIN_LEN (EAPOL_WPA2_ENCAP_DATA_HDR_LEN - \
+ TLV_HDR_LEN + EAPOL_WPA2_LINK_KDE_ENCAP_HDR_LEN)
+
+/* MLO KDE encapsulation */
+typedef BWL_PRE_PACKED_STRUCT struct {
+ uint8 link_info; /* link_id [0-3], Rxneinfo [4], rsvd [5-7] */
+ uint8 mac[ETHER_ADDR_LEN];
+ uint8 data[BCM_FLEX_ARRAY];
+} BWL_POST_PACKED_STRUCT eapol_wpa2_key_mlo_link_encap_t;
/* STAKey encapsulation */
typedef BWL_PRE_PACKED_STRUCT struct {
diff --git a/include/epivers.h b/include/epivers.h
index 1250d92..1354810 100644
--- a/include/epivers.h
+++ b/include/epivers.h
@@ -1,5 +1,5 @@
/*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -27,26 +27,27 @@
#define EPI_MINOR_VERSION 10
-#define EPI_RC_NUMBER 531
+#define EPI_RC_NUMBER 625
-#define EPI_INCREMENTAL_NUMBER 6
+#define EPI_INCREMENTAL_NUMBER 1
#define EPI_BUILD_NUMBER 0
-#define EPI_VERSION 101, 10, 531, 6
+#define EPI_VERSION 101, 10, 625, 1
-#define EPI_VERSION_NUM 0x650a2130
+#define EPI_VERSION_NUM 0x650a2710
-#define EPI_VERSION_DEV 101.10.531
+#define EPI_VERSION_DEV 101.10.625
/* Driver Version String, ASCII, 32 chars max */
#if defined (WLTEST)
-#define EPI_VERSION_STR "101.10.531.6 (wlan=r941975 WLTEST)"
-#elif (defined (BCMDBG_ASSERT) && !defined (BCMDBG_ASSERT_DISABLED) &&\
- !defined (ASSERT_FP_DISABLE))
-#define EPI_VERSION_STR "101.10.531.6 (wlan=r941975 ASSRT)"
+#define EPI_VERSION_STR "101.10.625.1 (wlan=r975530 WLTEST)"
+#elif (defined (BCMDBG_ASSERT) && \
+ !defined (BCMDBG_ASSERT_DISABLED) && \
+ !defined (ASSERT_FP_DISABLE))
+#define EPI_VERSION_STR "101.10.625.1 (wlan=r975530 ASSRT)"
#else
-#define EPI_VERSION_STR "101.10.531.6 (wlan=r941975)"
+#define EPI_VERSION_STR "101.10.625.1 (wlan=r975530)"
#endif /* BCMINTERNAL */
#endif /* _epivers_h_ */
diff --git a/include/etd.h b/include/etd.h
index 2d7172b..db436cf 100644
--- a/include/etd.h
+++ b/include/etd.h
@@ -1,7 +1,7 @@
/*
* Extended Trap data component interface file.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -28,6 +28,7 @@
#include <hnd_trap.h>
#endif
#include <bcmutils.h>
+
/* Tags for structures being used by etd info iovar.
* Related structures are defined in wlioctl.h.
*/
@@ -141,7 +142,7 @@
uint32 sr_dig_gci_status_0;
} hnd_ext_trap_axi_sr_err_v1_t;
-#define HND_EXT_TRAP_PSMWD_INFO_VER 1
+#define HND_EXT_TRAP_PSMWD_INFO_VER_1 (1u)
typedef struct hnd_ext_trap_psmwd_v1 {
uint16 xtag;
uint16 version; /* version of the information following this */
@@ -177,7 +178,8 @@
uint16 pad;
} hnd_ext_trap_psmwd_v1_t;
-typedef struct hnd_ext_trap_psmwd {
+#define HND_EXT_TRAP_PSMWD_INFO_VER_2 (2u)
+typedef struct hnd_ext_trap_psmwd_v2 {
uint16 xtag;
uint16 version; /* version of the information following this */
uint32 i32_maccontrol;
@@ -214,7 +216,44 @@
uint16 shm_prewds_cnt;
uint16 shm_txtplufl_cnt;
uint16 shm_txphyerr_cnt;
-} hnd_ext_trap_psmwd_t;
+} hnd_ext_trap_psmwd_v2_t;
+
+#define HND_EXT_TRAP_PSMWD_INFO_VER_3 (3u)
+typedef struct hnd_ext_trap_psmwd_v3 {
+ uint16 xtag;
+ uint16 version; /* version of the information following this */
+ uint32 i32_maccontrol;
+ uint32 i32_maccommand;
+ uint32 i32_macintstatus;
+ uint32 i32_phydebug;
+ uint32 i32_clk_ctl_st;
+ uint32 i32_psmdebug[PSMDBG_REG_READ_CNT_FOR_PSMWDTRAP_V1];
+ uint32 i32_gated_clock_en; /* gated clock en */
+ uint16 rcv_fifo_ctrl;
+ uint16 rx_ctrl1;
+ uint16 rxe_status1;
+ uint16 rxe_status2;
+ uint16 rcv_wrd_count0;
+ uint16 rcv_wrd_count1;
+ uint16 rcv_lfifo_sts;
+ uint16 psm_slp_tmr;
+ uint16 psm_brc;
+ uint16 txe_ctrl;
+ uint16 txe_status;
+ uint16 txe_xmtdmabusy;
+ uint16 txe_xmt_fifo_susp_flush;
+ uint16 ifs_stat;
+ uint16 ifs_medbusy_ctr;
+ uint16 ifs_tx_dur;
+ uint16 slow_ctl;
+ uint16 txe_aqm_fifo_ready;
+ uint16 dagg_ctrl;
+ uint16 shm_prewds_cnt;
+ uint16 shm_txtplufl_cnt;
+ uint16 shm_txphyerr_cnt;
+ uint16 shm_ucode_dbgst;
+ uint16 PAD;
+} hnd_ext_trap_psmwd_v3_t;
#define HEAP_HISTOGRAM_DUMP_LEN 6
#define HEAP_MAX_SZ_BLKS_LEN 2
@@ -348,8 +387,8 @@
uint16 shm_ucode_dbgst;
} hnd_ext_trap_macsusp_t;
-#define HND_EXT_TRAP_MACENAB_INFO_VER 1
-typedef struct hnd_ext_trap_macenab {
+#define HND_EXT_TRAP_MACENAB_INFO_VER_1 (1u)
+typedef struct hnd_ext_trap_macenab_v1 {
uint16 xtag;
uint8 version; /* version of the information following this */
uint8 trap_reason;
@@ -371,7 +410,33 @@
uint16 i16_0x6aa; /* SLow_PER */
uint16 shm_ucode_dbgst;
uint16 PAD;
-} hnd_ext_trap_macenab_t;
+} hnd_ext_trap_macenab_v1_t;
+
+#define HND_EXT_TRAP_MACENAB_INFO_VER_2 (2u)
+typedef struct hnd_ext_trap_macenab_v2 {
+ uint16 xtag;
+ uint8 version; /* version of the information following this */
+ uint8 trap_reason;
+ uint32 i32_maccontrol;
+ uint32 i32_maccommand;
+ uint32 i32_macintstatus;
+ uint32 i32_psmdebug[8];
+ uint32 i32_clk_ctl_st;
+ uint32 i32_powerctl;
+ uint32 i32_gated_clock_en;
+ uint16 psm_slp_tmr;
+ uint16 psm_brc;
+ uint16 tsf_ctl;
+ uint16 ifs_stat;
+ uint16 ifs_medbusy_ctr;
+ uint16 slow_ctl;
+ uint16 slow_frac;
+ uint16 fast_powerup_delay;
+ uint16 slow_per;
+ uint16 shm_ucode_dbgst;
+ uint16 shm_prewds_cnt;
+ uint16 PAD;
+} hnd_ext_trap_macenab_v2_t;
#define HND_EXT_TRAP_PHY_INFO_VER_1 (1)
typedef struct hnd_ext_trap_phydbg {
diff --git a/include/ethernet.h b/include/ethernet.h
index 76bb044..5609269 100644
--- a/include/ethernet.h
+++ b/include/ethernet.h
@@ -1,7 +1,7 @@
/*
* From FreeBSD 2.2.7: Fundamental constants relating to ethernet.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/event_log.h b/include/event_log.h
index c699fd6..d658ab9 100644
--- a/include/event_log.h
+++ b/include/event_log.h
@@ -1,7 +1,7 @@
/*
* EVENT_LOG system definitions
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -39,8 +39,8 @@
/* We make sure that the block size will fit in a single packet
* (allowing for a bit of overhead on each packet
*/
-#if defined(BCMPCIEDEV)
-#define EVENT_LOG_MAX_BLOCK_SIZE 1648
+#if (defined(BCMPCIEDEV) && defined(BCMPCIEDEV_ENABLED)) || defined(BCMPCIE)
+#define EVENT_LOG_MAX_BLOCK_SIZE 1832
#else
#define EVENT_LOG_MAX_BLOCK_SIZE 1400
#endif
@@ -48,6 +48,7 @@
#define EVENT_LOG_BLOCK_SIZE_1K 0x400u
#define EVENT_LOG_BLOCK_SIZE_512B 0x200u
#define EVENT_LOG_BLOCK_SIZE_256B 0x100u
+#define EVENT_LOG_BLOCK_SIZE_1648B 0x670u
#define EVENT_LOG_WL_BLOCK_SIZE 0x200
#define EVENT_LOG_PSM_BLOCK_SIZE 0x200
#define EVENT_LOG_MEM_API_BLOCK_SIZE 0x200
@@ -62,20 +63,47 @@
#define EVENT_LOG_TOF_INLINE_BLOCK_SIZE 1300u
#define EVENT_LOG_TOF_INLINE_BUF_SIZE (EVENT_LOG_TOF_INLINE_BLOCK_SIZE * 3u)
-#define EVENT_LOG_PRSRV_BUF_SIZE (EVENT_LOG_MAX_BLOCK_SIZE * 2)
+#define EVENT_LOG_PRSRV_BUF_SIZE (EVENT_LOG_BLOCK_SIZE_1648B * 2)
#define EVENT_LOG_BUS_PRSRV_BUF_SIZE (EVENT_LOG_BUS_BLOCK_SIZE * 2)
#define EVENT_LOG_WBUS_PRSRV_BUF_SIZE (EVENT_LOG_WBUS_BLOCK_SIZE * 2)
-#define EVENT_LOG_BLOCK_SIZE_PRSRV_CHATTY (EVENT_LOG_MAX_BLOCK_SIZE * 1)
-#define EVENT_LOG_BLOCK_SIZE_BUS_PRSRV_CHATTY (EVENT_LOG_MAX_BLOCK_SIZE * 1)
+#define EVENT_LOG_BLOCK_SIZE_PRSRV_CHATTY (EVENT_LOG_BLOCK_SIZE_1648B * 1)
+#define EVENT_LOG_BLOCK_SIZE_BUS_PRSRV_CHATTY (EVENT_LOG_BLOCK_SIZE_1648B * 1)
/* Maximum event log record payload size = 1016 bytes or 254 words. */
#define EVENT_LOG_MAX_RECORD_PAYLOAD_SIZE 254
+/* A format number entry in event header is shifted left by 2.
+ * To get the lower bits of actual format number used, shift the format number field in the
+ * event log header right by 2.
+ * When extended headers are not present, the actual format number is 14 bits long.
+ * Actual format number is used to index into the string table as mentioned in logstrs.bin
+ */
+#define EVENT_LOG_ACTUAL_FMT_NUM_LS_SHIFT (2u)
+/* When extended headers are present, the actual format number is 18 bits long.
+ * The extended format number represents top 4 bits of the actual format number
+ * Actual format number = (hdr->fmt_num >> EVENT_LOG_ACTUAL_FMT_NUM_LS_SHIFT) |
+ * ((ext_hdr->extended_fmt_num & EVENT_LOG_EXT_HDR_FMT_NUM_MASK) <<
+ * EVENT_LOG_ACTUAL_FMT_NUM_MS_SHIFT)
+ */
+#define EVENT_LOG_ACTUAL_FMT_NUM_MS_SHIFT (14u)
+/* Only 4 bits of extended format number are valid */
+#define EVENT_LOG_EXT_HDR_FMT_NUM_MASK (0xFu)
+
+/* Extended and binary data indication bits in the format number field in event log header */
#define EVENT_LOG_EXT_HDR_IND (0x01)
#define EVENT_LOG_EXT_HDR_BIN_DATA_IND (0x01 << 1)
+
+/* Actual format number for binary records with regular header */
+#define EVENT_LOG_ACTUAL_REG_BIN_FMT_NUM (0x3FFFu)
+/* Actual format number for binary records with extended header */
+#define EVENT_LOG_ACTUAL_EXT_BIN_FMT_NUM (0x3FFEu)
+
/* Format number to send binary data with extended event log header */
-#define EVENT_LOG_EXT_HDR_BIN_FMT_NUM (0x3FFE << 2)
+#define EVENT_LOG_EXT_HDR_BIN_FMT_NUM (EVENT_LOG_ACTUAL_EXT_BIN_FMT_NUM << 2)
+
+/* Format number to send binary data with regular event log header */
+#define EVENT_LOG_REG_HDR_BIN_FMT_NUM (EVENT_LOG_ACTUAL_REG_BIN_FMT_NUM << 2)
#define EVENT_LOGSET_ID_MASK 0x3F
/* For event_log_get iovar, set values from 240 to 255 mean special commands for a group of sets */
@@ -219,11 +247,12 @@
} event_log_set_t;
/* Definition of flags in set */
-#define EVENT_LOG_SET_SHRINK_ACTIVE (1 << 0)
-#define EVENT_LOG_SET_CONFIG_PARTIAL_BLK_SEND (0x1 << 1)
-#define EVENT_LOG_SET_CHECK_LOG_RATE (1 << 2)
-#define EVENT_LOG_SET_PERIODIC (1 << 3)
-#define EVENT_LOG_SET_D3PRSV (1 << 4)
+#define EVENT_LOG_SET_SHRINK_ACTIVE BCM_BIT(0)
+#define EVENT_LOG_SET_CONFIG_PARTIAL_BLK_SEND BCM_BIT(1)
+#define EVENT_LOG_SET_CHECK_LOG_RATE BCM_BIT(2)
+#define EVENT_LOG_SET_PERIODIC BCM_BIT(3)
+#define EVENT_LOG_SET_D3PRSV BCM_BIT(4)
+#define EVENT_LOG_SET_SHADOW BCM_BIT(5)
/* Top data structure for access to everything else */
typedef struct event_log_top {
@@ -368,6 +397,15 @@
#define EVENT_LOG_FORCE_FLUSH_ALL()
#define EVENT_LOG_FORCE_FLUSH_PRSRV_LOG_ALL()
+#define event_log_tag_start(tag, set_num, flags)
+#define event_log_tag_stop(tag)
+
+#define event_log_num_blocks_get(set, num_blocks) BCME_OK
+#define event_log_block_get(set, buf, len) BCME_OK
+
+#define event_log_enable_hostmem_access(hostmem_access_enabled)
+#define event_log_enable_event_trace(event_trace_enabled)
+
#else /* EVENT_LOG_COMPILE */
/* The first few _EVENT_LOGX() macros are special because they can be done more
@@ -388,6 +426,21 @@
#define _EVENT_LOG4(tag, fmt_num, fmt, t1, t2, t3, t4) \
event_log4(tag, fmt_num, t1, t2, t3, t4)
+#ifdef EVENT_LOG_FIXED_ARGS_ONLY
+/* Only 4 or less argumenents are supported */
+#define _EVENT_LOG_VA_ARGS_ERR() STATIC_ASSERT(0)
+#define _EVENT_LOG5(tag, fmt_num, fmt, ...) _EVENT_LOG_VA_ARGS_ERR()
+#define _EVENT_LOG6(tag, fmt_num, fmt, ...) _EVENT_LOG_VA_ARGS_ERR()
+#define _EVENT_LOG7(tag, fmt_num, fmt, ...) _EVENT_LOG_VA_ARGS_ERR()
+#define _EVENT_LOG8(tag, fmt_num, fmt, ...) _EVENT_LOG_VA_ARGS_ERR()
+#define _EVENT_LOG9(tag, fmt_num, fmt, ...) _EVENT_LOG_VA_ARGS_ERR()
+#define _EVENT_LOGA(tag, fmt_num, fmt, ...) _EVENT_LOG_VA_ARGS_ERR()
+#define _EVENT_LOGB(tag, fmt_num, fmt, ...) _EVENT_LOG_VA_ARGS_ERR()
+#define _EVENT_LOGC(tag, fmt_num, fmt, ...) _EVENT_LOG_VA_ARGS_ERR()
+#define _EVENT_LOGD(tag, fmt_num, fmt, ...) _EVENT_LOG_VA_ARGS_ERR()
+#define _EVENT_LOGE(tag, fmt_num, fmt, ...) _EVENT_LOG_VA_ARGS_ERR()
+#define _EVENT_LOGF(tag, fmt_num, fmt, ...) _EVENT_LOG_VA_ARGS_ERR()
+#else
/* The rest call the generic routine that takes a count */
#define _EVENT_LOG5(tag, fmt_num, fmt, ...) event_logn(5, tag, fmt_num, __VA_ARGS__)
#define _EVENT_LOG6(tag, fmt_num, fmt, ...) event_logn(6, tag, fmt_num, __VA_ARGS__)
@@ -400,6 +453,7 @@
#define _EVENT_LOGD(tag, fmt_num, fmt, ...) event_logn(13, tag, fmt_num, __VA_ARGS__)
#define _EVENT_LOGE(tag, fmt_num, fmt, ...) event_logn(14, tag, fmt_num, __VA_ARGS__)
#define _EVENT_LOGF(tag, fmt_num, fmt, ...) event_logn(15, tag, fmt_num, __VA_ARGS__)
+#endif /* EVENT_LOG_FIXED_ARGS_ONLY */
/* Casting low level macros */
#define _EVENT_LOG_CAST0(tag, fmt_num, fmt) \
@@ -574,15 +628,18 @@
int event_log_init_context(event_log_top_t *top, uint8 *tag_sets, uint16 tag_sets_len,
uint8 *tag_sets_ext, uint16 tag_sets_ext_len);
/* Initialize event log set context on a given buffer */
-void event_log_set_init_context(event_log_set_t *ts, int size);
+int event_log_set_init_context(event_log_set_t *ts, int size, int set_num);
/* Add a newly allocated block to a specific set */
void event_log_set_add_block(event_log_set_t *ts, event_log_block_t *tb);
/* Rest a set after adding new blocks */
void event_log_set_reset(event_log_set_t *ts);
-extern int event_log_init(osl_t *osh);
-extern int event_log_set_init(osl_t *osh, int set_num, int size);
-extern int event_log_set_expand(osl_t *osh, int set_num, int size);
-extern int event_log_set_shrink(osl_t *osh, int set_num, int size);
+int event_log_set_reset_by_num(int set_num);
+int event_log_init(osl_t *osh);
+void event_log_timestamp_init(osl_t *osh);
+int event_log_set_init(osl_t *osh, int set_num, int size);
+int event_log_set_expand(osl_t *osh, int set_num, int size);
+int event_log_set_expand_align(osl_t *osh, int set_num, int size, uint align_bits);
+int event_log_set_shrink(osl_t *osh, int set_num, int size);
/**
* @brief Event log host access state change notification callback function type
@@ -621,10 +678,6 @@
extern void event_log3(int tag, int fmtNum, uint32 t1, uint32 t2, uint32 t3);
extern void event_log4(int tag, int fmtNum, uint32 t1, uint32 t2, uint32 t3, uint32 t4);
extern void event_logn(int num_args, int tag, int fmtNum, ...);
-#ifdef ROM_COMPAT_MSCH_PROFILER
-/* For compatibility with ROM, for old msch event log function to pass parameters in stack */
-extern void event_logv(uint num_args, int tag, int fmtNum, va_list ap);
-#endif /* ROM_COMPAT_MSCH_PROFILER */
/* Use PTM based timestamping of event log records if PTM is available. */
#if defined(GTIMER_PTM) && !defined(GTIMER_PTM_DISABLED)
@@ -687,6 +740,12 @@
extern int event_log_block_get(int set, uint32 **buf, uint16 *len);
extern uint32 event_log_get_maxsets(void);
+/* Get cur_block of a specific set */
+event_log_block_t * event_log_block_get_cur(int set);
+
+/* API to notify event log framework that cur_block of the specific set is filled */
+void event_log_shadow_set_post(int set);
+
/* For all other non-logtrace consumers */
extern int event_log_set_is_valid(int set);
diff --git a/include/event_log_payload.h b/include/event_log_payload.h
index c5e4ace..1e6d6e3 100644
--- a/include/event_log_payload.h
+++ b/include/event_log_payload.h
@@ -4,7 +4,7 @@
* This file describes the payloads of event log entries that are data buffers
* rather than formatted string entries. The contents are generally XTLVs.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -255,6 +255,7 @@
#define SCAN_SUM_WLC_CORE1 0x8
#define HOME_CHAN 0x10
#define SCAN_SUM_SCAN_CORE 0x20
+#define FILS_SCAN_SCN_SUM 0x40 /* The 6G channels was dwelled only for FILS dur 25ms */
typedef struct wl_scan_ssid_info
{
@@ -265,11 +266,11 @@
typedef struct wl_scan_channel_info {
uint16 chanspec; /* chanspec scanned */
uint16 reserv;
- uint32 start_time; /* Scan start time in
+ uint32 start_time; /* Scan start time in
* milliseconds for the chanspec
* or home_dwell time start
*/
- uint32 end_time; /* Scan end time in
+ uint32 end_time; /* Scan end time in
* milliseconds for the chanspec
* or home_dwell time end
*/
@@ -280,15 +281,53 @@
*/
} wl_scan_channel_info_t;
+typedef struct wl_scan_channel_info_v2 {
+ uint16 chanspec; /* chanspec scanned */
+ uint16 reserv;
+ uint32 start_time; /* Scan start time in
+ * milliseconds for the chanspec
+ * or home_dwell time start
+ */
+ uint32 end_time; /* Scan end time in
+ * milliseconds for the chanspec
+ * or home_dwell time end
+ */
+ uint32 chan_6g_act_scn_strt_time; /* 6G active scan start, valid for 6G chan only */
+ uint16 probe_count; /* No of probes sent out. For future use
+ */
+ uint16 scn_res_count; /* Count of scan_results found per
+ * channel. For future use
+ */
+} wl_scan_channel_info_v2_t;
+
typedef struct wl_scan_summary_info {
- uint32 total_chan_num; /* Total number of channels scanned */
- uint32 scan_start_time; /* Scan start time in milliseconds */
- uint32 scan_end_time; /* Scan end time in milliseconds */
+ uint32 total_chan_num; /* Total number of channels scanned */
+ uint32 scan_start_time; /* Scan start time in milliseconds */
+ uint32 scan_end_time; /* Scan end time in milliseconds */
wl_scan_ssid_info_t ssid[BCM_FLEX_ARRAY]; /* SSID being scanned in current
- * channel. For future use
- */
+ * channel. For future use
+ */
} wl_scan_summary_info_t;
+typedef struct wl_scan_summary_info_v2 {
+ uint32 scan_start_time; /* Scan start time in milliseconds */
+ uint32 scan_end_time; /* Scan end time in milliseconds */
+ uint32 scan_dur_2g; /* 2g Scan duartion time in milliseconds */
+ uint32 scan_dur_5g; /* 5g Scan duartion time in milliseconds */
+ uint32 scan_dur_6g; /* 6g Scan duartion time in milliseconds */
+ uint8 total_chan_num; /* Total number of channels scanned */
+ /* scan_channel_ctx_t chan_cnt; */
+ uint8 channel_cnt_2g; /* Number of 2g channels to be scanned */
+ uint8 channel_cnt_5g; /* Number of 5g channels to be scanned */
+ uint8 channel_cnt_6g; /* Number of 6g channels to be scanned */
+ uint8 channel_cnt_sc_2g; /* Number of channels to be scanned on Scan core */
+ uint8 channel_cnt_sc_5g; /* Number of channels to be scanned on Scan core */
+ uint8 channel_cnt_sc_6g; /* Number of channels to be scanned on Scan core */
+ uint8 active_channel_cnt; /* Number of active channels to be scanned */
+ uint8 passive_channel_cnt; /* Number of passive channels to be scanned */
+ uint8 pad[3]; /* Pad to keep it 32 bit aligned */
+} wl_scan_summary_info_v2_t;
+
struct wl_scan_summary {
uint8 version; /* Version */
uint8 reserved;
@@ -398,6 +437,120 @@
*/
} u;
};
+
+#define SCAN_SUMMARY_VERSION_3 3u
+struct wl_scan_summary_v3 {
+ uint8 version; /* Version */
+ uint8 reserved;
+ uint16 len; /* Length of the data buffer including SSID
+ * list.
+ */
+ uint16 sync_id; /* Scan Sync ID */
+ uint16 scan_flags; /* flags [0] or SCAN_SUM_CHAN_INFO = */
+ /* channel_info, if not set */
+ /* it is scan_summary_info */
+ /* when channel_info is used, */
+ /* the following flag bits are overridden: */
+ /* flags[1] or ACTIVE_SCAN_SCN_SUM = active channel if set */
+ /* passive if not set */
+ /* flags[2] or WLC_CORE0 = if set, represents wlc_core0 */
+ /* flags[3] or WLC_CORE1 = if set, represents wlc_core1 */
+ /* flags[4] or HOME_CHAN = if set, represents home-channel */
+ /* flags[5] or SCAN_SUM_SCAN_CORE = if set,
+ * represents chan_info from scan core.
+ */
+ /* flags[6] or FILS_SCAN_SCN_SUM = if set,
+ * 6G channels was dwelled only for FILS duration.
+ */
+ /* flags[12] SCAN_SUM_CHAN_RESHED indicate scan rescheduled */
+ /* flags[7:11, 13:15] = reserved */
+ /* when scan_summary_info is used, */
+ /* the following flag bits are used: */
+ /* flags[1] or BAND5G_SIB_ENAB = */
+ /* allowSIBParallelPassiveScan on 5G band */
+ /* flags[2] or BAND2G_SIB_ENAB = */
+ /* allowSIBParallelPassiveScan on 2G band */
+ /* flags[3] or PARALLEL_SCAN = Parallel scan enabled or not */
+ /* flags[4] or SCAN_ABORT = SCAN_ABORTED scenario */
+ /* flags[5] = reserved */
+ /* flags[6:8] is used as count value to identify SCAN CLIENT
+ * WL_SSUM_CLIENT_ASSOCSCAN 0x0u, WL_SSUM_CLIENT_ROAMSCAN 0x1u,
+ * WL_SSUM_CLIENT_FWSCAN 0x2u, WL_SSUM_CLIENT_HOSTSCAN 0x3u
+ */
+ /* flags[9:11] is used as count value to identify SCAN MODE
+ * WL_SCAN_MODE_HIGH_ACC 0u, WL_SCAN_MODE_LOW_SPAN 1u,
+ * WL_SCAN_MODE_LOW_POWER 2u
+ */
+ /* flags[12] SCAN_SUM_CHAN_RESHED indicate scan rescheduled */
+ /* flags[13:15] = reserved */
+ union {
+ wl_scan_channel_info_v2_t scan_chan_info; /* scan related information
+ * for each channel scanned
+ */
+ wl_scan_summary_info_v2_t scan_sum_info; /* Cumulative scan related
+ * information.
+ */
+ } u;
+};
+
+/* Raom target evaluation detail data type */
+typedef enum {
+ WL_ROAM_TRGT_EVAL_BASIC = 1u,
+ WL_ROAM_TRGT_EVAL_RSSI_SCORE = 2u,
+ WL_ROAM_TRGT_EVAL_LOAD_SCORE = 3u,
+ WL_ROAM_TRGT_EVAL_SUMMARY = 4u,
+ WL_ROAM_TRGT_EVAL_MAX
+} wl_roam_trgt_eval_msg_type_t;
+
+struct wl_roam_target_cur_state {
+ uint32 type; /* = WL_ROAM_TRGT_EVAL_BASIC (1) */
+ uint32 roam_reason; /* existing definition of roam reasons */
+ uint32 roam_type; /* 0:ROAM_FULL 1:ROAM_PARTIAL 2:ROAM_SPLIT_PHASE */
+ uint32 home_bssid_hi; /* 32-bit MSB MAC address */
+ uint32 home_bssid_lo; /* 16-bit LSB MAC address */
+ uint32 channel; /* chanspec_t */
+ int32 rssi; /* raw value */
+ int32 roam_prof_idx; /* Roam profile index */
+ uint32 prof_flags; /* Info related to the current applicable roam profile */
+ int32 prof_trigger;
+ uint32 prof_delta;
+ uint32 user_ov; /* User roam cache override mode */
+};
+
+struct wl_roam_target_rssi_score {
+ uint32 type; /* = WL_ROAM_TRGT_EVAL_RSSI_SCORE (2) */
+ uint32 bssid_hi; /* 32-bit MSB MAC address */
+ uint32 bssid_lo; /* 16-bit LSB MAC address */
+ uint32 channel; /* chanspec_t */
+ int32 rssi; /* raw value */
+ int32 rssi_boosted;
+ uint32 rssi_score; /* = 65536 + MIN(0, rssi_boosted) */
+ uint32 load_aac; /* qbss load available admission capacity (when available) */
+ uint32 chan_free; /* IEEE802.11 format with 255 = 100% (when available) */
+};
+
+struct wl_roam_target_load_score {
+ uint32 type; /* = WL_ROAM_TRGT_EVAL_LOAD_SCORE (3) */
+ uint32 bssid_hi; /* 32-bit MSB MAC address */
+ uint32 bssid_lo; /* 16-bit LSB MAC address */
+ uint32 channel; /* chanspec_t */
+ int32 rssi; /* raw value */
+ int32 rssi_boosted;
+ uint32 rate_family; /* two-letter for A/ B/ G/ N/AC/AX/ */
+ uint32 rate; /* mapped rate (x500Kbps) */
+ uint32 bw; /* 20, 40, 80, 160, or ... */
+ uint32 nss;
+ uint32 chan_free; /* IEEE802.11 format with 255 = 100% */
+ uint32 load_score; /* = rate * nss * bw * chan_free */
+};
+
+struct wl_roam_target_summary {
+ uint32 type; /* = WL_ROAM_TRGT_EVAL_SUMMARY (4) */
+ uint32 ref_score; /* score reference (minimum score to beat) */
+ uint32 score_delta; /* score delta - additional marging */
+ uint32 num_of_targets; /* number of qualifying target */
+};
+
/* Channel switch log record structure
* Host may map the following structure on channel switch event log record
* received from dongle. Note that all payload entries in event log record are
@@ -471,8 +624,17 @@
WL_AMPDU_STATS_TYPE_RX_COUNTERS = 45, /* Additional AMPDU_RX module counters
* per-slice
*/
- WL_AMPDU_STATS_MAX_CNTS = 64
+ WL_AMPDU_STATS_TYPE_RXHEx1 = 46, /* RX HE rate (Nss = 1) */
+ WL_AMPDU_STATS_TYPE_RXHEx2 = 47,
+ WL_AMPDU_STATS_TYPE_RXHEx3 = 48,
+ WL_AMPDU_STATS_TYPE_RXHEx4 = 49,
+ WL_AMPDU_STATS_TYPE_TXHEx1 = 50, /* TX HE rate (Nss = 1) */
+ WL_AMPDU_STATS_TYPE_TXHEx2 = 51,
+ WL_AMPDU_STATS_TYPE_TXHEx3 = 52,
+ WL_AMPDU_STATS_TYPE_TXHEx4 = 53
} wl_ampdu_stat_enum_t;
+#define WL_AMPDU_STATS_MAX_CNTS (64) /* Possible max number of counters in any sub-categary */
+
typedef struct {
uint16 type; /* AMPDU statistics sub-type */
uint16 len; /* Number of 32-bit counters */
@@ -1211,11 +1373,11 @@
uint32 rxframe; /* Number of received frames */
/* Misc general purpose debug counters (will be used for future debugging) */
- uint32 debug_01;
- uint32 debug_02;
- uint32 debug_03;
- uint32 debug_04;
- uint32 debug_05;
+ uint32 tbtt; /* Per-interface stats report tbtt count */
+ uint32 p2ptbtt; /* MCNX TBTT */
+ uint32 p2ptbttmiss; /* TBTT coming when the radio is on an off channel */
+ uint32 missbcn_dbg; /* Number of beacon missed to receive */
+ uint32 noise_iqest_to; /* Count of IQ Est timeout during noise measurement */
uint32 rxanyerr; /* Any RX error that is not counted by other counters. */
@@ -1357,6 +1519,125 @@
uint32 last_bcn_ltsf; /* last beacon ltsf */
/* Misc general purpose debug counters (will be used for future debugging) */
+ uint32 tbtt; /* Per-interface stats report tbtt count */
+ uint32 p2ptbtt; /* MCNX TBTT */
+ uint32 p2ptbttmiss; /* TBTT coming when the radio is on an off channel */
+ uint32 missbcn_dbg; /* Number of beacon missed to receive */
+ uint32 noise_iqest_to; /* Count of IQ Est timeout during noise measurement */
+
+ uint32 rxanyerr; /* Any RX error that is not counted by other counters. */
+
+ uint32 phyovfl_cnt; /* RX PHY FIFO overflow */
+ uint32 rxf0ovfl; /* Rx FIFO0 overflow counters information */
+ uint32 rxf1ovfl; /* Rx FIFO1 overflow counters information */
+
+ uint32 lenfovfl_cnt; /* RX LFIFO overflow */
+ uint32 weppeof_cnt; /* WEP asserted premature end-of-frame */
+ uint32 rxbadplcp; /* number of parity check of the PLCP header failed */
+ uint32 strmeof_cnt; /* RX frame got aborted because PHY FIFO did not have
+ * sufficient bytes
+ */
+ uint32 pfifo_drop; /* PHY FIFO was not empty when a new frame arrived */
+ uint32 ctx_fifo_full; /* Low Priority Context FIFO is full */
+ uint32 ctx_fifo2_full; /* High Priority Context FIFO is full */
+ uint32 rxnodelim; /* number of no valid delimiter detected by ampdu parser */
+ uint32 rx20s_cnt; /* secondary 20 counter */
+ uint32 rxdrop20s; /* RX was discarded as the CRS was not seen on
+ * primary channel
+ */
+ uint32 new_rxin_plcp_wait_cnt; /* A new reception started waiting for PLCP bytes
+ * from a previous receive
+ */
+ uint32 rxtoolate; /* receive too late */
+ uint32 laterx_cnt; /* RX frame dropped as it was seen too (30us) late
+ * from the start of reception
+ */
+ uint32 rxfrmtoolong; /* Number of received frame that are too long */
+ uint32 rxfrmtooshrt; /* RX frame was dropped as it did not meet minimum
+ * number of bytes to be a valid 802.11 frame
+ */
+
+ uint32 rxlegacyfrminvalid; /* Invalid BPHY or L-OFDM reception */
+ uint32 txsifserr; /* A frame arrived in SIFS while we were about to
+ * transmit B/ACK
+ */
+ uint32 ooseq_macsusp; /* Ucode is out of sequence in processing reception
+ * (especially due to macsuspend).
+ * RX MEND is seen without RX STRT
+ */
+ uint32 desense_reason; /* desense paraemters to indicate reasons
+ * for bphy and ofdm_desense
+ */
+
+ uint16 nav_cntr_l; /* The state of the NAV */
+ uint16 nav_cntr_h;
+} phy_periodic_counters_v8_t;
+
+typedef struct phy_periodic_counters_v9 {
+ /* RX error related */
+ uint32 rxrsptmout; /* number of response timeouts for transmitted frames
+ * expecting a response
+ */
+ uint32 rxcrsglitch; /* PHY was able to correlate the preamble
+ * but not the header
+ */
+ uint32 bphy_badplcp; /* number of bad PLCP reception on BPHY rate */
+ uint32 bphy_rxcrsglitch; /* PHY count of bphy glitches */
+ uint32 rxdropped; /* Frame dropped */
+ uint32 rxnobuf; /* Rx error due to no buffer */
+ uint32 rxrunt; /* Runt frame counter */
+ uint32 rxbadfcs; /* number of frames for which the CRC check failed
+ * in the MAC
+ */
+
+ /* RX related */
+ uint32 rxstrt; /* number of received frames with a good PLCP */
+ uint32 rxbeaconmbss; /* beacons received from member of BSS */
+ uint32 rxdtucastmbss; /* number of received DATA frames with good FCS
+ * and matching RA
+ */
+ uint32 rxdtocast; /* number of received DATA frames
+ * (good FCS and no matching RA)
+ */
+ uint32 goodfcs; /* Good fcs counters */
+ uint32 rxctl; /* Number of control frames */
+ uint32 rxaction; /* Number of action frames */
+ uint32 rxback; /* Number of block ack frames rcvd */
+ uint32 rxctlucast; /* Number of received unicast ctl frames */
+ uint32 rxframe; /* Number of received frames */
+
+ uint32 rxbar; /* Number of block ack requests rcvd */
+ uint32 rxackucast; /* number of ucast ACKS received (good FCS) */
+ uint32 rxbeaconobss; /* number of OBSS beacons received */
+ uint32 rxctsucast; /* number of unicast CTS addressed to the MAC (good FCS) */
+ uint32 rxrtsucast; /* number of unicast RTS addressed to the MAC (good FCS) */
+
+ /* TX related */
+ uint32 txallfrm; /* total number of frames sent, incl. Data, ACK, RTS, CTS,
+ * Control Management (includes retransmissions)
+ */
+ uint32 txmpdu; /* Numer of transmitted mpdus */
+ uint32 txackbackctsfrm; /* Number of ACK + BACK + CTS */
+ uint32 txackfrm; /* number of ACK frames sent out */
+ uint32 txrtsfrm; /* number of RTS sent out by the MAC */
+ uint32 txctsfrm; /* number of CTS sent out by the MAC */
+
+ uint32 txctl; /* Number of control frames txd */
+ uint32 txbar; /* Number of block ack requests txd */
+ uint32 txrts; /* Number of RTS txd */
+ uint32 txback; /* Number of block ack frames txd */
+ uint32 txucast; /* number of unicast tx expecting response
+ * other than cts/cwcts
+ */
+
+ /* TX error related */
+ uint32 txrtsfail; /* RTS TX failure count */
+ uint32 txphyerr; /* PHY TX error count */
+
+ uint32 last_bcn_seq_num; /* last beacon seq no. */
+ uint32 last_bcn_ltsf; /* last beacon ltsf */
+
+ /* Misc general purpose debug counters (will be used for future debugging) */
uint32 debug_01;
uint32 debug_02;
uint32 debug_03;
@@ -1409,7 +1690,144 @@
uint16 nav_cntr_l; /* The state of the NAV */
uint16 nav_cntr_h;
-} phy_periodic_counters_v8_t;
+
+ uint32 tbtt; /* Per-interface stats report tbtt count */
+ uint32 p2ptbtt; /* MCNX TBTT */
+ uint32 p2ptbttmiss; /* TBTT coming when the radio is on an off channel */
+ uint32 noise_iqest_to; /* Count of IQ Est timeout during noise measurement */
+ uint16 missbcn_dbg; /* Number of beacon missed to receive */
+
+ /* Misc general purpose debug counters (will be used for future debugging) */
+ uint16 debug_06;
+ uint16 debug_07;
+ uint16 debug_08;
+ uint16 debug_09;
+ uint16 debug_10;
+
+ uint8 sc_dccal_incc_cnt; /* scan dccal counter */
+ uint8 sc_rxiqcal_skip_cnt; /* scan rxiqcal counter */
+ uint8 sc_noisecal_incc_cnt; /* scan noise cal counter */
+ uint8 debug_14;
+} phy_periodic_counters_v9_t;
+
+typedef struct phy_periodic_counters_v255 {
+ /* RX error related */
+ uint32 rxrsptmout; /* number of response timeouts for transmitted frames
+ * expecting a response
+ */
+ uint32 rxcrsglitch; /* PHY was able to correlate the preamble
+ * but not the header
+ */
+ uint32 bphy_badplcp; /* number of bad PLCP reception on BPHY rate */
+ uint32 bphy_rxcrsglitch; /* PHY count of bphy glitches */
+ uint32 rxdropped; /* Frame dropped */
+ uint32 rxnobuf; /* Rx error due to no buffer */
+ uint32 rxrunt; /* Runt frame counter */
+ uint32 rxbadfcs; /* number of frames for which the CRC check failed
+ * in the MAC
+ */
+
+ /* RX related */
+ uint32 rxstrt; /* number of received frames with a good PLCP */
+ uint32 rxbeaconmbss; /* beacons received from member of BSS */
+ uint32 rxdtucastmbss; /* number of received DATA frames with good FCS
+ * and matching RA
+ */
+ uint32 rxdtocast; /* number of received DATA frames
+ * (good FCS and no matching RA)
+ */
+ uint32 goodfcs; /* Good fcs counters */
+ uint32 rxctl; /* Number of control frames */
+ uint32 rxaction; /* Number of action frames */
+ uint32 rxback; /* Number of block ack frames rcvd */
+ uint32 rxctlucast; /* Number of received unicast ctl frames */
+ uint32 rxframe; /* Number of received frames */
+
+ uint32 rxbar; /* Number of block ack requests rcvd */
+ uint32 rxackucast; /* number of ucast ACKS received (good FCS) */
+ uint32 rxbeaconobss; /* number of OBSS beacons received */
+ uint32 rxctsucast; /* number of unicast CTS addressed to the MAC (good FCS) */
+ uint32 rxrtsucast; /* number of unicast RTS addressed to the MAC (good FCS) */
+
+ /* TX related */
+ uint32 txallfrm; /* total number of frames sent, incl. Data, ACK, RTS, CTS,
+ * Control Management (includes retransmissions)
+ */
+ uint32 txmpdu; /* Numer of transmitted mpdus */
+ uint32 txackbackctsfrm; /* Number of ACK + BACK + CTS */
+ uint32 txackfrm; /* number of ACK frames sent out */
+ uint32 txrtsfrm; /* number of RTS sent out by the MAC */
+ uint32 txctsfrm; /* number of CTS sent out by the MAC */
+
+ uint32 txctl; /* Number of control frames txd */
+ uint32 txbar; /* Number of block ack requests txd */
+ uint32 txrts; /* Number of RTS txd */
+ uint32 txback; /* Number of block ack frames txd */
+ uint32 txucast; /* number of unicast tx expecting response
+ * other than cts/cwcts
+ */
+
+ /* TX error related */
+ uint32 txrtsfail; /* RTS TX failure count */
+ uint32 txphyerr; /* PHY TX error count */
+
+ uint32 last_bcn_seq_num; /* last beacon seq no. */
+ uint32 last_bcn_ltsf; /* last beacon ltsf */
+
+ /* Misc general purpose debug counters (will be used for future debugging) */
+ uint32 debug_01;
+ uint32 debug_02;
+ uint32 debug_03;
+ uint32 debug_04;
+ uint32 debug_05;
+
+ uint32 rxanyerr; /* Any RX error that is not counted by other counters. */
+
+ uint32 phyovfl_cnt; /* RX PHY FIFO overflow */
+ uint32 rxf0ovfl; /* Rx FIFO0 overflow counters information */
+ uint32 rxf1ovfl; /* Rx FIFO1 overflow counters information */
+
+ uint32 lenfovfl_cnt; /* RX LFIFO overflow */
+ uint32 weppeof_cnt; /* WEP asserted premature end-of-frame */
+ uint32 rxbadplcp; /* number of parity check of the PLCP header failed */
+ uint32 strmeof_cnt; /* RX frame got aborted because PHY FIFO did not have
+ * sufficient bytes
+ */
+ uint32 pfifo_drop; /* PHY FIFO was not empty when a new frame arrived */
+ uint32 ctx_fifo_full; /* Low Priority Context FIFO is full */
+ uint32 ctx_fifo2_full; /* High Priority Context FIFO is full */
+ uint32 rxnodelim; /* number of no valid delimiter detected by ampdu parser */
+ uint32 rx20s_cnt; /* secondary 20 counter */
+ uint32 rxdrop20s; /* RX was discarded as the CRS was not seen on
+ * primary channel
+ */
+ uint32 new_rxin_plcp_wait_cnt; /* A new reception started waiting for PLCP bytes
+ * from a previous receive
+ */
+ uint32 rxtoolate; /* receive too late */
+ uint32 laterx_cnt; /* RX frame dropped as it was seen too (30us) late
+ * from the start of reception
+ */
+ uint32 rxfrmtoolong; /* Number of received frame that are too long */
+ uint32 rxfrmtooshrt; /* RX frame was dropped as it did not meet minimum
+ * number of bytes to be a valid 802.11 frame
+ */
+
+ uint32 rxlegacyfrminvalid; /* Invalid BPHY or L-OFDM reception */
+ uint32 txsifserr; /* A frame arrived in SIFS while we were about to
+ * transmit B/ACK
+ */
+ uint32 ooseq_macsusp; /* Ucode is out of sequence in processing reception
+ * (especially due to macsuspend).
+ * RX MEND is seen without RX STRT
+ */
+ uint32 desense_reason; /* desense paraemters to indicate reasons
+ * for bphy and ofdm_desense
+ */
+
+ uint16 nav_cntr_l; /* The state of the NAV */
+ uint16 nav_cntr_h;
+} phy_periodic_counters_v255_t;
typedef struct phycal_log_cmn {
uint16 chanspec; /* Current phy chanspec */
@@ -1858,9 +2276,9 @@
uint16 log_event_id; /* logging event id */
/* Misc general purpose debug counters (will be used for future debugging) */
- uint16 debug_01;
- uint16 debug_02;
- uint16 debug_03;
+ uint16 measurehold_high; /* PHY hold activities high16 */
+ uint16 measurehold_low; /* PHY hold activities low16 */
+ uint16 btcx_ackpwroffset; /* CoreMask (low8) and ack_pwr_offset (high8) */
uint16 debug_04;
uint16 debug_05;
@@ -2078,6 +2496,136 @@
uint16 log_event_id; /* logging event id */
/* Misc general purpose debug counters (will be used for future debugging) */
+ uint16 measurehold_high; /* PHY hold activities high16 */
+ uint16 measurehold_low; /* PHY hold activities low16 */
+ uint16 tpc_hc_count; /* RAM A HC counter */
+ uint16 tpc_hc_bkoff; /* RAM A HC core0 power backoff */
+ uint16 btcx_ackpwroffset; /* CoreMask (low8) and ack_pwr_offset (high8) */
+
+ uint16 macsusp_cnt; /* mac suspend counter */
+ uint8 amtbitmap; /* AMT status bitamp */
+
+ int8 chiptemp; /* Chip temparature */
+ int8 femtemp; /* Fem temparature */
+
+ uint8 cal_phase_id; /* Current Multi phase cal ID */
+ uint8 rxchain; /* Rx Chain */
+ uint8 txchain; /* Tx Chain */
+ uint8 ofdm_desense; /* OFDM desense */
+
+ uint8 slice;
+ uint8 dbgfw_ver; /* version of fw/ucode for debug purposes */
+ uint8 bphy_desense; /* BPHY desense */
+ uint8 pll_lockstatus; /* PLL Lock status */
+
+ /* dccal dcoe & idacc */
+ uint8 dcc_err; /* dccal health check error status */
+ uint8 dcoe_num_tries; /* number of retries on dcoe cal */
+ uint8 idacc_num_tries; /* number of retries on idac cal */
+
+ uint8 dccal_phyrxchain; /* phy rxchain during dc calibration */
+ uint8 dccal_type; /* DC cal type: single/multi phase, chan change, etc. */
+
+ uint8 gbd_bphy_sleep_counter; /* gbd sleep counter */
+ uint8 gbd_ofdm_sleep_counter; /* gbd sleep counter */
+ uint8 curr_home_channel; /* gbd input channel from cca */
+
+ /* desense data */
+ int8 btcx_mode; /* btcoex desense mode */
+ int8 ltecx_mode; /* lte coex desense mode */
+ uint8 gbd_ofdm_desense; /* gbd ofdm desense level */
+ uint8 gbd_bphy_desense; /* gbd bphy desense level */
+ uint8 current_elna_bypass; /* init gain desense: elna bypass */
+ uint8 current_tia_idx; /* init gain desense: tia index */
+ uint8 current_lpf_idx; /* init gain desense: lpf index */
+ uint8 crs_auto_thresh; /* crs auto threshold after desense */
+
+ int8 weakest_rssi; /* weakest link RSSI */
+ uint8 noise_cal_mode; /* noisecal mode */
+
+ bool phycal_disable; /* Set if calibration is disabled */
+ bool hwpwrctrlen; /* tx hwpwrctrl enable */
+ int8 ed_threshold; /* Threshold applied for ED */
+ uint16 ed_crs_status; /* Status of ED and CRS during noise cal */
+ uint16 preempt_status1; /* status of preemption */
+ uint16 preempt_status2; /* status of preemption */
+ uint16 preempt_status3; /* status of preemption */
+ uint16 preempt_status4; /* status of preemption */
+ uint32 ed_duration; /* ccastats: ed_duration */
+} phy_periodic_log_cmn_v8_t;
+
+/* Inherited from v8 */
+typedef struct phy_periodic_log_cmn_v9 {
+
+ uint32 nrate; /* Current Tx nrate */
+ uint32 duration; /* millisecs spent sampling this channel */
+ uint32 congest_ibss; /* millisecs in our bss (presumably this traffic will */
+ /* move if cur bss moves channels) */
+ uint32 congest_obss; /* traffic not in our bss */
+ uint32 interference; /* millisecs detecting a non 802.11 interferer. */
+ uint32 last_cal_time; /* Last cal execution time */
+
+ uint32 noise_cal_req_ts; /* Time-stamp when noise cal was requested */
+ uint32 noise_cal_intr_ts; /* Time-stamp when noise cal was completed */
+ uint32 phywdg_ts; /* Time-stamp when wd was fired */
+ uint32 phywd_dur; /* Duration of the watchdog */
+ uint32 chanspec_set_ts; /* Time-stamp when chanspec was set */
+ uint32 vcopll_failure_cnt; /* Number of VCO cal failures including */
+ /* failures detected in ucode */
+ uint32 log_ts; /* Time-stamp when this log was collected */
+
+ /* glitch based desense input from cca */
+ uint32 cca_stats_total_glitch;
+ uint32 cca_stats_bphy_glitch;
+ uint32 cca_stats_total_badplcp;
+ uint32 cca_stats_bphy_badplcp;
+ uint32 cca_stats_mbsstime;
+
+ uint32 counter_noise_request; /* count of noisecal request */
+ uint32 counter_noise_crsbit; /* count of crs high during noisecal request */
+ uint32 counter_noise_apply; /* count of applying noisecal result to crsmin */
+ uint32 fullphycalcntr; /* count of performing single phase cal */
+ uint32 multiphasecalcntr; /* count of performing multi-phase cal */
+
+ uint32 macsusp_dur; /* mac suspend duration */
+
+ uint32 featureflag; /* Currently active feature flags */
+
+ uint16 chanspec; /* Current phy chanspec */
+ uint16 vbatmeas; /* Measured VBAT sense value */
+
+ /* HP2P related params */
+ uint16 shm_mpif_cnt_val;
+ uint16 shm_thld_cnt_val;
+ uint16 shm_nav_cnt_val;
+ uint16 shm_cts_cnt_val;
+ uint16 shm_m_prewds_cnt; /* Count of pre-wds fired in the ucode */
+
+ uint16 deaf_count; /* Depth of stay_in_carrier_search function */
+
+ uint16 ed20_crs0; /* ED-CRS status on core 0 */
+ uint16 ed20_crs1; /* ED-CRS status on core 1 */
+
+ uint16 dcc_attempt_counter; /* Number of DC cal attempts */
+ uint16 dcc_fail_counter; /* Number of DC cal failures */
+
+ uint16 btcxovrd_dur; /* Cumulative btcx overide between WDGs */
+ uint16 btcxovrd_err_cnt; /* BTCX override flagged errors */
+
+ uint16 femtemp_read_fail_counter; /* Fem temparature read fail counter */
+ uint16 phy_log_counter;
+ uint16 noise_mmt_overdue; /* Count up if ucode noise mmt is overdue for 5 sec */
+ uint16 chan_switch_tm; /* Channel switch time */
+
+ uint16 dcc_hcfail; /* dcc health check failure count */
+ uint16 dcc_calfail; /* dcc failure count */
+ uint16 crsmin_pwr_apply_cnt; /* Count of desense power threshold update to phy */
+
+ uint16 txpustatus; /* txpu off definations */
+ uint16 tempinvalid_count; /* Count no. of invalid temp. measurements */
+ uint16 log_event_id; /* logging event id */
+
+ /* Misc general purpose debug counters (will be used for future debugging) */
uint16 debug_01;
uint16 debug_02;
uint16 debug_03;
@@ -2133,8 +2681,328 @@
uint16 preempt_status2; /* status of preemption */
uint16 preempt_status3; /* status of preemption */
uint16 preempt_status4; /* status of preemption */
+ uint16 debug_06;
uint32 ed_duration; /* ccastats: ed_duration */
-} phy_periodic_log_cmn_v8_t;
+} phy_periodic_log_cmn_v9_t;
+
+/* Inherited from v9 */
+typedef struct phy_periodic_log_cmn_v10 {
+
+ uint32 nrate; /* Current Tx nrate */
+ uint32 duration; /* millisecs spent sampling this channel */
+ uint32 congest_ibss; /* millisecs in our bss (presumably this traffic will */
+ /* move if cur bss moves channels) */
+ uint32 congest_obss; /* traffic not in our bss */
+ uint32 interference; /* millisecs detecting a non 802.11 interferer. */
+ uint32 last_cal_time; /* Last cal execution time */
+
+ uint32 noise_cal_req_ts; /* Time-stamp when noise cal was requested */
+ uint32 noise_cal_intr_ts; /* Time-stamp when noise cal was completed */
+ uint32 phywdg_ts; /* Time-stamp when wd was fired */
+ uint32 phywd_dur; /* Duration of the watchdog */
+ uint32 chanspec_set_ts; /* Time-stamp when chanspec was set */
+ uint32 vcopll_failure_cnt; /* Number of VCO cal failures including */
+ /* failures detected in ucode */
+ uint32 log_ts; /* Time-stamp when this log was collected */
+
+ /* glitch based desense input from cca */
+ uint32 cca_stats_total_glitch;
+ uint32 cca_stats_bphy_glitch;
+ uint32 cca_stats_total_badplcp;
+ uint32 cca_stats_bphy_badplcp;
+ uint32 cca_stats_mbsstime;
+
+ uint32 counter_noise_request; /* count of noisecal request */
+ uint32 counter_noise_crsbit; /* count of crs high during noisecal request */
+ uint32 counter_noise_apply; /* count of applying noisecal result to crsmin */
+ uint32 fullphycalcntr; /* count of performing single phase cal */
+ uint32 multiphasecalcntr; /* count of performing multi-phase cal */
+
+ uint32 macsusp_dur; /* mac suspend duration */
+
+ uint32 featureflag; /* Currently active feature flags */
+
+ uint16 chanspec; /* Current phy chanspec */
+ uint16 vbatmeas; /* Measured VBAT sense value */
+
+ /* HP2P related params */
+ uint16 shm_mpif_cnt_val;
+ uint16 shm_thld_cnt_val;
+ uint16 shm_nav_cnt_val;
+ uint16 shm_cts_cnt_val;
+ uint16 shm_m_prewds_cnt; /* Count of pre-wds fired in the ucode */
+
+ uint16 deaf_count; /* Depth of stay_in_carrier_search function */
+
+ uint16 ed20_crs0; /* ED-CRS status on core 0 */
+ uint16 ed20_crs1; /* ED-CRS status on core 1 */
+
+ uint16 dcc_attempt_counter; /* Number of DC cal attempts */
+ uint16 dcc_fail_counter; /* Number of DC cal failures */
+
+ uint16 btcxovrd_dur; /* Cumulative btcx overide between WDGs */
+ uint16 btcxovrd_err_cnt; /* BTCX override flagged errors */
+
+ uint16 femtemp_read_fail_counter; /* Fem temparature read fail counter */
+ uint16 phy_log_counter;
+ uint16 noise_mmt_overdue; /* Count up if ucode noise mmt is overdue for 5 sec */
+ uint16 chan_switch_tm; /* Channel switch time */
+
+ uint16 dcc_hcfail; /* dcc health check failure count */
+ uint16 dcc_calfail; /* dcc failure count */
+ uint16 crsmin_pwr_apply_cnt; /* Count of desense power threshold update to phy */
+
+ uint16 txpustatus; /* txpu off definations */
+ uint16 tempinvalid_count; /* Count no. of invalid temp. measurements */
+ uint16 log_event_id; /* logging event id */
+
+ /* Misc general purpose debug counters (will be used for future debugging) */
+ uint16 pktprocdebug;
+ uint16 pktprocdebug2;
+ uint16 timeoutstatus;
+ uint16 debug_04;
+ uint16 debug_05;
+
+ uint16 macsusp_cnt; /* mac suspend counter */
+ uint8 amtbitmap; /* AMT status bitamp */
+
+ int8 chiptemp; /* Chip temparature */
+ int8 femtemp; /* Fem temparature */
+
+ uint8 cal_phase_id; /* Current Multi phase cal ID */
+ uint8 rxchain; /* Rx Chain */
+ uint8 txchain; /* Tx Chain */
+ uint8 ofdm_desense; /* OFDM desense */
+
+ uint8 slice;
+ uint8 dbgfw_ver; /* version of fw/ucode for debug purposes */
+ uint8 bphy_desense; /* BPHY desense */
+ uint8 pll_lockstatus; /* PLL Lock status */
+
+ /* dccal dcoe & idacc */
+ uint8 dcc_err; /* dccal health check error status */
+ uint8 dcoe_num_tries; /* number of retries on dcoe cal */
+ uint8 idacc_num_tries; /* number of retries on idac cal */
+
+ uint8 dccal_phyrxchain; /* phy rxchain during dc calibration */
+ uint8 dccal_type; /* DC cal type: single/multi phase, chan change, etc. */
+
+ uint8 gbd_bphy_sleep_counter; /* gbd sleep counter */
+ uint8 gbd_ofdm_sleep_counter; /* gbd sleep counter */
+ uint8 curr_home_channel; /* gbd input channel from cca */
+
+ /* desense data */
+ int8 btcx_mode; /* btcoex desense mode */
+ int8 ltecx_mode; /* lte coex desense mode */
+ uint8 gbd_ofdm_desense; /* gbd ofdm desense level */
+ uint8 gbd_bphy_desense; /* gbd bphy desense level */
+ uint8 current_elna_bypass; /* init gain desense: elna bypass */
+ uint8 current_tia_idx; /* init gain desense: tia index */
+ uint8 current_lpf_idx; /* init gain desense: lpf index */
+ uint8 crs_auto_thresh; /* crs auto threshold after desense */
+
+ int8 weakest_rssi; /* weakest link RSSI */
+ uint8 noise_cal_mode; /* noisecal mode */
+
+ bool phycal_disable; /* Set if calibration is disabled */
+ bool hwpwrctrlen; /* tx hwpwrctrl enable */
+ int8 ed_threshold; /* Threshold applied for ED */
+ uint32 measurehold; /* PHY hold activities */
+ uint32 ed_duration; /* ccastats: ed_duration */
+ uint16 ed_crs_status; /* Status of ED and CRS during noise cal */
+ uint16 preempt_status1; /* status of preemption */
+ uint16 preempt_status2; /* status of preemption */
+ uint16 preempt_status3; /* status of preemption */
+ uint16 preempt_status4; /* status of preemption */
+
+ uint16 counter_noise_iqest_to; /* count of IQ_Est time out */
+ uint16 rfemstate2g; /* rFEM state register for 2g */
+ uint16 rfemstate5g; /* rFEM state register for 5g */
+ uint16 txiqcal_max_retry_cnt; /* txiqlocal retries reached max allowed count */
+ uint16 txiqcal_max_slope_cnt; /* txiqlocal slope reached max allowed count */
+ uint16 mppc_cal_failed_cnt; /* MPPC cal failure count */
+
+ uint16 gci_lst_inv_ctr;
+ uint16 gci_lst_rst_ctr;
+ uint16 gci_lst_sem_fail;
+ uint16 gci_lst_rb_state;
+ uint16 gci_lst_pad01;
+ uint16 gci_lst_pad02;
+ uint16 gci_lst_pad03;
+ uint16 gci_lst_pad04;
+ uint16 gci_lst_pad05;
+ uint16 gci_lst_state_mask;
+ uint16 gci_inv_tx; /* Tx inv cnt */
+ uint16 gci_inv_rx; /* Rx inv cnt */
+ uint16 gci_rst_tx; /* gci Tx reset cnt */
+ uint16 gci_rst_rx; /* gci Rx reset cnt */
+ uint16 gci_sem_fail;
+ uint16 gci_invstate; /* inv state */
+ uint16 gci_phyctl0; /* TX_PHYCTL0 */
+ uint16 gci_phyctl1; /* TX_PHYCTL1 */
+ uint16 gci_phyctl2; /* TX_PHYCTL2 */
+ uint16 gci_ctxtst; /* S_CTXTST */
+ uint16 gci_invts; /* When gci read request was placed and completed */
+ uint16 gci_invtsdn; /* */
+ uint16 gci_invtxs; /* timestamp for TXCRS assertion */
+ uint16 gci_invtxdur; /* IFS_TX_DUR */
+ uint16 gci_invifs; /* IFS status */
+ uint16 gci_chan; /* For additional ucode data */
+ uint16 gci_pad02; /* For additional ucode data */
+ uint16 gci_pad03; /* For additional ucode data */
+ uint16 gci_pad04; /* For additional ucode data */
+
+ uint32 rxsense_disable_req_ch; /* channel disable requests */
+ uint32 ocl_disable_reqs; /* OCL disable bitmap */
+
+ int8 rxsense_noise_idx; /* rxsense detection threshold desense index */
+ int8 rxsense_offset; /* rxsense min power desense index */
+ uint8 ocl_en_status; /* OCL requested state and OCL HW state */
+ uint8 lpc_status; /* Flag to enable/disable LPC, and runtime flag status */
+
+ uint16 rspfrm_ed_txncl_cnt; /* Response frame not sent due to ED */
+
+ int16 last_cal_temp;
+ uint8 cal_reason; /* reason for the cal */
+ uint8 cal_suppressed_cntr_ed; /* counter including ss, mp cals, MSB is current state */
+ uint8 phylog_noise_mode; /* Noise mode used */
+ uint8 debug_08;
+
+ /* Misc general purpose debug counters (will be used for future debugging) */
+ uint32 interference_mode; /* interference mitigation mode */
+ uint32 power_mode; /* LP/VLP logging */
+ uint32 debug_11;
+ uint32 debug_12;
+} phy_periodic_log_cmn_v10_t;
+
+typedef struct phy_periodic_log_cmn_v255 {
+ uint32 nrate; /* Current Tx nrate */
+ uint32 duration; /* millisecs spent sampling this channel */
+ uint32 congest_ibss; /* millisecs in our bss (presumably this traffic will */
+ /* move if cur bss moves channels) */
+ uint32 congest_obss; /* traffic not in our bss */
+ uint32 interference; /* millisecs detecting a non 802.11 interferer. */
+ uint32 last_cal_time; /* Last cal execution time */
+
+ uint32 noise_cal_req_ts; /* Time-stamp when noise cal was requested */
+ uint32 noise_cal_intr_ts; /* Time-stamp when noise cal was completed */
+ uint32 phywdg_ts; /* Time-stamp when wd was fired */
+ uint32 phywd_dur; /* Duration of the watchdog */
+ uint32 chanspec_set_ts; /* Time-stamp when chanspec was set */
+ uint32 vcopll_failure_cnt; /* Number of VCO cal failures including */
+ /* failures detected in ucode */
+ uint32 log_ts; /* Time-stamp when this log was collected */
+
+ /* glitch based desense input from cca */
+ uint32 cca_stats_total_glitch;
+ uint32 cca_stats_bphy_glitch;
+ uint32 cca_stats_total_badplcp;
+ uint32 cca_stats_bphy_badplcp;
+ uint32 cca_stats_mbsstime;
+
+ uint32 counter_noise_request; /* count of noisecal request */
+ uint32 counter_noise_crsbit; /* count of crs high during noisecal request */
+ uint32 counter_noise_apply; /* count of applying noisecal result to crsmin */
+ uint32 fullphycalcntr; /* count of performing single phase cal */
+ uint32 multiphasecalcntr; /* count of performing multi-phase cal */
+
+ uint32 macsusp_dur; /* mac suspend duration */
+
+ uint32 featureflag; /* Currently active feature flags */
+
+ uint16 chanspec; /* Current phy chanspec */
+ uint16 vbatmeas; /* Measured VBAT sense value */
+
+ /* HP2P related params */
+ uint16 shm_mpif_cnt_val;
+ uint16 shm_thld_cnt_val;
+ uint16 shm_nav_cnt_val;
+ uint16 shm_cts_cnt_val;
+ uint16 shm_m_prewds_cnt; /* Count of pre-wds fired in the ucode */
+
+ uint16 deaf_count; /* Depth of stay_in_carrier_search function */
+
+ uint16 ed20_crs0; /* ED-CRS status on core 0 */
+ uint16 ed20_crs1; /* ED-CRS status on core 1 */
+
+ uint16 dcc_attempt_counter; /* Number of DC cal attempts */
+ uint16 dcc_fail_counter; /* Number of DC cal failures */
+
+ uint16 btcxovrd_dur; /* Cumulative btcx overide between WDGs */
+ uint16 btcxovrd_err_cnt; /* BTCX override flagged errors */
+
+ uint16 femtemp_read_fail_counter; /* Fem temparature read fail counter */
+ uint16 phy_log_counter;
+ uint16 noise_mmt_overdue; /* Count up if ucode noise mmt is overdue for 5 sec */
+ uint16 chan_switch_tm; /* Channel switch time */
+
+ uint16 dcc_hcfail; /* dcc health check failure count */
+ uint16 dcc_calfail; /* dcc failure count */
+ uint16 crsmin_pwr_apply_cnt; /* Count of desense power threshold update to phy */
+
+ uint16 txpustatus; /* txpu off definations */
+ uint16 tempinvalid_count; /* Count no. of invalid temp. measurements */
+ uint16 log_event_id; /* logging event id */
+
+ /* Misc general purpose debug counters (will be used for future debugging) */
+ uint16 debug_01;
+ uint16 debug_02;
+ uint16 debug_03;
+ uint16 debug_04;
+ uint16 debug_05;
+
+ uint16 macsusp_cnt; /* mac suspend counter */
+ uint8 amtbitmap; /* AMT status bitamp */
+
+ int8 chiptemp; /* Chip temparature */
+ int8 femtemp; /* Fem temparature */
+
+ uint8 cal_phase_id; /* Current Multi phase cal ID */
+ uint8 rxchain; /* Rx Chain */
+ uint8 txchain; /* Tx Chain */
+ uint8 ofdm_desense; /* OFDM desense */
+
+ uint8 slice;
+ uint8 dbgfw_ver; /* version of fw/ucode for debug purposes */
+ uint8 bphy_desense; /* BPHY desense */
+ uint8 pll_lockstatus; /* PLL Lock status */
+
+ /* dccal dcoe & idacc */
+ uint8 dcc_err; /* dccal health check error status */
+ uint8 dcoe_num_tries; /* number of retries on dcoe cal */
+ uint8 idacc_num_tries; /* number of retries on idac cal */
+
+ uint8 dccal_phyrxchain; /* phy rxchain during dc calibration */
+ uint8 dccal_type; /* DC cal type: single/multi phase, chan change, etc. */
+
+ uint8 gbd_bphy_sleep_counter; /* gbd sleep counter */
+ uint8 gbd_ofdm_sleep_counter; /* gbd sleep counter */
+ uint8 curr_home_channel; /* gbd input channel from cca */
+
+ /* desense data */
+ int8 btcx_mode; /* btcoex desense mode */
+ int8 ltecx_mode; /* lte coex desense mode */
+ uint8 gbd_ofdm_desense; /* gbd ofdm desense level */
+ uint8 gbd_bphy_desense; /* gbd bphy desense level */
+ uint8 current_elna_bypass; /* init gain desense: elna bypass */
+ uint8 current_tia_idx; /* init gain desense: tia index */
+ uint8 current_lpf_idx; /* init gain desense: lpf index */
+ uint8 crs_auto_thresh; /* crs auto threshold after desense */
+
+ int8 weakest_rssi; /* weakest link RSSI */
+ uint8 noise_cal_mode; /* noisecal mode */
+
+ bool phycal_disable; /* Set if calibration is disabled */
+ bool hwpwrctrlen; /* tx hwpwrctrl enable */
+ int8 ed_threshold; /* Threshold applied for ED */
+ uint16 ed_crs_status; /* Status of ED and CRS during noise cal */
+ uint16 preempt_status1; /* status of preemption */
+ uint16 preempt_status2; /* status of preemption */
+ uint16 preempt_status3; /* status of preemption */
+ uint16 preempt_status4; /* status of preemption */
+ uint16 debug_06;
+ uint32 ed_duration; /* ccastats: ed_duration */
+} phy_periodic_log_cmn_v255_t;
typedef struct phy_periodic_log_core {
uint8 baseindxval; /* TPC Base index */
@@ -2223,6 +3091,90 @@
int16 psb; /* psb read during dccal health check */
int16 txcap; /* Txcap value */
+ uint16 curr_tssival; /* TxPwrCtrlInit_path[01].TSSIVal */
+ uint16 pwridx_init; /* TxPwrCtrlInit_path[01].pwrIndex_init_path[01] */
+ uint16 tpc_hc_tssi; /* RAM A HC TSSI value */
+ uint16 btcx_antmask; /* antenna to be used by BT */
+
+ uint8 pktproc; /* pktproc read during dccal health check */
+ uint8 baseindxval; /* TPC Base index */
+ int8 tgt_pwr; /* Programmed Target power */
+ int8 estpwradj; /* Current Est Power Adjust value */
+ int8 crsmin_pwr; /* CRS Min/Noise power */
+ int8 rssi_per_ant; /* RSSI Per antenna */
+ int8 snr_per_ant; /* SNR Per antenna */
+
+ int8 noise_level; /* noise pwr after filtering & averageing */
+ int8 noise_level_inst; /* instantaneous noise cal pwr */
+ int8 estpwr; /* tx powerDet value */
+ int8 crsmin_th_idx; /* idx used to lookup crs min thresholds */
+ int8 tpc_hc_bidx; /* RAM A HC base index */
+
+ int8 phy_noise_pwr_array[PHY_NOISE_PWR_ARRAY_SIZE]; /* noise buffer array */
+} phy_periodic_log_core_v6_t;
+
+typedef struct phy_periodic_log_core_v7 {
+ /* dccal dcoe & idacc */
+ uint16 dcoe_done_0; /* dccal control register 44 */
+ uint16 dcoe_done_1; /* dccal control register 45 */
+ uint16 dcoe_done_2; /* dccal control register 46 */
+ uint16 idacc_done_0; /* dccal control register 21 */
+ uint16 idacc_done_1; /* dccal control register 60 */
+ uint16 idacc_done_2; /* dccal control register 61 */
+ int16 psb; /* psb read during dccal health check */
+ int16 txcap; /* Txcap value */
+
+ /* Misc general purpose debug counters (will be used for future debugging) */
+ uint16 bad_txbaseidx_cnt; /* cntr for tx_baseidx=127 in healthcheck */
+ uint16 debug_02;
+ uint16 debug_03;
+ uint16 debug_04;
+
+ uint8 pktproc; /* pktproc read during dccal health check */
+ uint8 baseindxval; /* TPC Base index */
+ int8 tgt_pwr; /* Programmed Target power */
+ int8 estpwradj; /* Current Est Power Adjust value */
+ int8 crsmin_pwr; /* CRS Min/Noise power */
+ int8 rssi_per_ant; /* RSSI Per antenna */
+ int8 snr_per_ant; /* SNR Per antenna */
+
+ int8 noise_level; /* noise pwr after filtering & averageing */
+ int8 noise_level_inst; /* instantaneous noise cal pwr */
+ int8 estpwr; /* tx powerDet value */
+ int8 crsmin_th_idx; /* idx used to lookup crs min thresholds */
+ uint8 pad01;
+
+ uint16 curr_tssival; /* TxPwrCtrlInit_path[01].TSSIVal */
+ uint16 pwridx_init; /* TxPwrCtrlInit_path[01].pwrIndex_init_path[01] */
+ uint16 auxphystats;
+ uint16 phystatsgaininfo;
+ uint16 flexpwrAFE;
+ uint16 flexpwrdig1;
+ uint16 flexpwrdig2;
+ uint16 flexpwrdig3;
+ uint16 flexpwrdig4;
+ uint16 flexgaininfo_A;
+
+ /* Misc general purpose debug counters (will be used for future debugging) */
+ uint8 debug_05;
+ uint8 debug_06;
+ uint8 debug_07;
+ uint8 debug_08;
+
+ int8 phy_noise_pwr_array[PHY_NOISE_PWR_ARRAY_SIZE]; /* noise buffer array */
+} phy_periodic_log_core_v7_t;
+
+typedef struct phy_periodic_log_core_v255 {
+ /* dccal dcoe & idacc */
+ uint16 dcoe_done_0; /* dccal control register 44 */
+ uint16 dcoe_done_1; /* dccal control register 45 */
+ uint16 dcoe_done_2; /* dccal control register 46 */
+ uint16 idacc_done_0; /* dccal control register 21 */
+ uint16 idacc_done_1; /* dccal control register 60 */
+ uint16 idacc_done_2; /* dccal control register 61 */
+ int16 psb; /* psb read during dccal health check */
+ int16 txcap; /* Txcap value */
+
uint16 debug_01; /* multipurpose debug register */
uint16 debug_02; /* multipurpose debug register */
uint16 debug_03; /* multipurpose debug register */
@@ -2243,7 +3195,7 @@
int8 debug_05; /* multipurpose debug register */
int8 phy_noise_pwr_array[PHY_NOISE_PWR_ARRAY_SIZE]; /* noise buffer array */
-} phy_periodic_log_core_v6_t;
+} phy_periodic_log_core_v255_t;
typedef struct phy_periodic_log_core_v2 {
int32 rxs; /* FDIQ Slope coeffecient */
@@ -2286,6 +3238,38 @@
uint16 antgrant_ge60ms; /* Ant grant duration cnt 60~ms */
} wlc_btc_shared_stats_v1_t;
+#define BTCX_STATS_PHY_LOGGING_VER2 2u
+typedef struct wlc_btc_shared_stats_v2 {
+ uint32 bt_req_cnt; /* #BT antenna requests since last stats sampl */
+ uint32 bt_gnt_cnt; /* #BT antenna grants since last stats sample */
+ uint32 bt_gnt_dur; /* usec BT owns antenna since last stats sample */
+ uint16 bt_pm_attempt_cnt; /* PM1 attempts */
+ uint16 bt_succ_pm_protect_cnt; /* successful PM protection */
+ uint16 bt_succ_cts_cnt; /* successful CTS2A protection */
+ uint16 bt_wlan_tx_preempt_cnt; /* WLAN TX Preemption */
+ uint16 bt_wlan_rx_preempt_cnt; /* WLAN RX Preemption */
+ uint16 bt_ap_tx_after_pm_cnt; /* AP TX even after PM protection */
+ uint16 bt_crtpri_cnt; /* Ant grant by critical BT task */
+ uint16 bt_pri_cnt; /* Ant grant by high BT task */
+ uint16 antgrant_lt10ms; /* Ant grant duration cnt 0~10ms */
+ uint16 antgrant_lt30ms; /* Ant grant duration cnt 10~30ms */
+ uint16 antgrant_lt60ms; /* Ant grant duration cnt 30~60ms */
+ uint16 antgrant_ge60ms; /* Ant grant duration cnt 60~ms */
+ uint16 ackpwroffset; /* CoreMask (low8) and ack_pwr_offset (high8) */
+ uint8 prisel_ant_mask; /* antenna to be used by BT */
+
+ /* Misc general purpose debug counters (will be used for future debugging) */
+ uint8 debug_01;
+ uint16 debug_02;
+ uint16 debug_03;
+ uint16 debug_04;
+ uint16 debug_05;
+ uint8 debug_06;
+ uint8 debug_07;
+ uint8 debug_08;
+ uint8 debug_09;
+} wlc_btc_shared_stats_v2_t;
+
/* BTCX Statistics for PHY Logging */
typedef struct wlc_btc_stats_phy_logging {
uint16 ver;
@@ -2295,6 +3279,15 @@
wlc_btc_shared_stats_v1_t shared;
} phy_periodic_btc_stats_v1_t;
+/* BTCX Statistics for PHY Logging */
+typedef struct wlc_btc_stats_phy_logging_v2 {
+ uint16 ver;
+ uint16 length;
+ uint32 btc_status; /* btc status log */
+ uint32 bt_req_type_map; /* BT Antenna Req types since last stats sample */
+ wlc_btc_shared_stats_v2_t shared;
+} phy_periodic_btc_stats_v2_t;
+
/* OBSS Statistics for PHY Logging */
typedef struct phy_periodic_obss_stats_v1 {
uint32 obss_last_read_time; /* last stats read time */
@@ -2317,8 +3310,57 @@
*/
} phy_periodic_obss_stats_v1_t;
+/* OBSS Statistics for PHY Logging */
+typedef struct phy_periodic_obss_stats_v2 {
+ uint32 obss_last_read_time; /* last stats read time */
+ uint16 obss_mit_bw; /* selected mitigation BW */
+ uint16 obss_stats_cnt; /* stats count */
+ uint8 obss_need_updt; /* BW update needed flag */
+ uint8 obss_mit_status; /* obss mitigation status */
+ uint8 obss_curr_det[ACPHY_OBSS_SUBBAND_CNT]; /* obss curr detection */
+ uint16 dynbw_init_reducebw_cnt; /*
+ * bandwidth reduction cnt of
+ * initiator (txrts+rxcts)
+ */
+ uint16 dynbw_resp_reducebw_cnt; /*
+ * bandwidth reduction cnt of
+ * responder (rxrts+txcts)
+ */
+ uint16 dynbw_rxdata_reducebw_cnt; /*
+ * rx data cnt with reduced bandwidth
+ * as txcts requested
+ */
+ uint16 obss_mmt_skip_cnt; /* mmt skipped due to powersave */
+ uint16 obss_mmt_no_result_cnt; /* mmt with no result */
+ uint16 obss_mmt_intr_err_cnt; /* obss reg mismatch between ucode and fw */
+ uint8 obss_final_rec_bw; /* final recommended bw to wlc-Sent to SW */
+ uint8 debug01;
+ uint16 obss_det_stats[ACPHY_OBSS_SUBBAND_CNT];
+} phy_periodic_obss_stats_v2_t;
+
+typedef struct phy_periodic_obss_stats_v255 {
+ uint32 obss_last_read_time; /* last stats read time */
+ uint16 obss_mit_bw; /* selected mitigation BW */
+ uint16 obss_stats_cnt; /* stats count */
+ uint8 obss_mit_mode; /* mitigation mode */
+ uint8 obss_mit_status; /* obss mitigation status */
+ uint8 obss_curr_det[ACPHY_OBSS_SUBBAND_CNT]; /* obss curr detection */
+ uint16 dynbw_init_reducebw_cnt; /*
+ * bandwidth reduction cnt of
+ * initiator (txrts+rxcts)
+ */
+ uint16 dynbw_resp_reducebw_cnt; /*
+ * bandwidth reduction cnt of
+ * responder (rxrts+txcts)
+ */
+ uint16 dynbw_rxdata_reducebw_cnt; /*
+ * rx data cnt with reduced bandwidth
+ * as txcts requested
+ */
+} phy_periodic_obss_stats_v255_t;
+
/* SmartCCA related PHY Logging */
-typedef struct wlc_scca_stats_phy_logging {
+typedef struct phy_periodic_scca_stats_v1 {
uint32 asym_intf_cmplx_pwr[2];
uint32 asym_intf_ncal_time;
uint32 asym_intf_host_req_mit_turnon_time;
@@ -2376,6 +3418,183 @@
uint8 asym_intf_pending_host_req_type; /* Set request pending if clk not present */
} phy_periodic_scca_stats_v1_t;
+/* SmartCCA related PHY Logging */
+typedef struct phy_periodic_scca_stats_v2 {
+ uint32 asym_intf_cmplx_pwr[2];
+ uint32 asym_intf_ncal_time;
+ uint32 asym_intf_host_req_mit_turnon_time;
+ uint32 core1_smask_val_bk; /* bt fem control related */
+ int32 asym_intf_ed_thresh;
+
+ int16 crsminpoweru0; /* crsmin thresh */
+ int16 crsminpoweroffset0; /* ac_offset core0 */
+ int16 crsminpoweroffset1; /* ac_offset core1 */
+ int16 Core0InitGainCodeB; /* rx mitigation: eLNA bypass setting */
+ int16 Core1InitGainCodeB; /* rx mitigation: eLNA bypass setting */
+ int16 ed_crsEn; /* phyreg(ed_crsEn) */
+ int16 nvcfg0; /* LLR deweighting coefficient */
+ int16 SlnaRxMaskCtrl0;
+ int16 SlnaRxMaskCtrl1;
+ uint16 save_SlnaRxMaskCtrl0;
+ uint16 save_SlnaRxMaskCtrl1;
+ uint16 asym_intf_ncal_req_chspec; /* channel request noisecal */
+ /* asym_intf_stats includes the following bits:
+ * b[0]: bool asym_intf_rx_noise_mit_on;
+ * b[1]: bool asym_intf_tx_smartcca_on;
+ * b[3:2]: bool asym_intf_elna_bypass[2];
+ * b[4]: bool asym_intf_valid_noise_samp;
+ * b[5]: bool asym_intf_fill_noise_buf;
+ * b[6]: bool asym_intf_ncal_discard;
+ * b[7]: bool slna_reg_saved;
+ * b[8]: bool asym_intf_host_ext_usb; //Host control related variable
+ * b[9]: bool asym_intf_host_ext_usb_chg; // Host control related variable
+ * b[10]: bool asym_intf_host_en; // Host control related variable
+ * b[11]: bool asym_intf_host_enable;
+ * b[12]: bool asym_intf_pending_host_req; // Set request pending if clk not present
+ */
+ uint16 asym_intf_stats;
+
+ uint8 elna_bypass; /* from bt_desense.elna_bypass in gainovr_shm_config() */
+ uint8 btc_mode; /* from bt_desense in gainovr_shm_config() */
+ /* noise at antenna from phy_ac_noise_ant_noise_calc() */
+ int8 noise_dbm_ant[2];
+ /* in phy_ac_noise_calc(), also used by wl noise */
+ int8 noisecalc_cmplx_pwr_dbm[2];
+ uint8 gain_applied; /* from phy_ac_rxgcrs_set_init_clip_gain() */
+
+ int8 asym_intf_tx_smartcca_cm;
+ int8 asym_intf_rx_noise_mit_cm;
+ int8 asym_intf_avg_noise[2];
+ int8 asym_intf_latest_noise[2];
+ /* used to calculate noise_delta for rx mitigation on/off */
+ int8 asym_intf_prev_noise_lvl[2];
+ uint8 asym_intf_noise_calc_gain_2g[2];
+ uint8 asym_intf_noise_calc_gain_5g[2];
+ uint8 asym_intf_ant_noise_idx;
+ uint8 asym_intf_least_core_idx;
+ uint8 phy_crs_thresh_save[2];
+ uint8 asym_intf_initg_desense[2];
+ uint8 asym_intf_pending_host_req_type; /* Set request pending if clk not present */
+ uint16 asym_intf_ncal_crs_stat[12];
+ uint8 asym_intf_ncal_crs_stat_idx;
+} phy_periodic_scca_stats_v2_t;
+
+/* SmartCCA related PHY Logging - v3 NEWT SmartCCA based */
+typedef struct phy_periodic_scca_stats_v3 {
+ uint32 asym_intf_ncal_time;
+ uint32 asym_intf_host_req_mit_turnon_time;
+ int32 asym_intf_ed_thresh;
+
+ int16 crsminpoweru0; /* crsmin thresh */
+ int16 crsminpoweroffset0; /* ac_offset core0 */
+ int16 crsminpoweroffset1; /* ac_offset core1 */
+ int16 ed_crsEn; /* phyreg(ed_crsEn) */
+ int16 nvcfg0; /* LLR deweighting coefficient */
+ int16 SlnaRxMaskCtrl0;
+ int16 SlnaRxMaskCtrl1;
+ int16 CRSMiscellaneousParam;
+ int16 AntDivConfig2059;
+ int16 HPFBWovrdigictrl;
+ uint16 save_SlnaRxMaskCtrl0;
+ uint16 save_SlnaRxMaskCtrl1;
+ uint16 asym_intf_ncal_req_chspec; /* channel request noisecal */
+ /* asym_intf_stats includes the following bits:
+ * b[0]: bool asym_intf_rx_noise_mit_on; // SmartCCA Rx mititagion enabled
+ * b[1]: bool asym_intf_tx_smartcca_on; // SmartCCA Tx mititagion enabled
+ * b[2]: bool asym_intf_valid_noise_samp; // Latest noise sample is valid
+ * b[3]: bool asym_intf_fill_noise_buf; // Fill the same sample to entire buffer
+ * b[4]: bool asym_intf_ncal_discard; // Discard current noise sample
+ * b[5]: bool slna_reg_saved; // SLNA register values are saved
+ * b[6]: bool asym_intf_host_ext_usb; // Host control related variable
+ * b[7]: bool asym_intf_host_ext_usb_chg; // Host control related variable
+ * b[8]: bool asym_intf_host_en; // Host control related variable
+ * b[9]: bool asym_intf_host_enable; // Host control related variable
+ * b[10]: bool asym_intf_pending_host_req; // Set request pending if clk not present
+ */
+ uint16 asym_intf_stats;
+
+ uint8 btc_mode; /* from bt_desense in gainovr_shm_config() */
+
+ /* noise at antenna from phy_ac_noise_calc() */
+ int8 noisecalc_cmplx_pwr_dbm[2];
+ int8 asym_intf_ant_noise[2];
+
+ int8 asym_intf_tx_smartcca_cm;
+ int8 asym_intf_rx_noise_mit_cm;
+ int8 asym_intf_avg_noise[2];
+ int8 asym_intf_latest_noise[2];
+ /* used to calculate noise_delta for rx mitigation on/off */
+ int8 asym_intf_prev_noise_lvl[2];
+ uint8 asym_intf_ant_noise_idx;
+ uint8 asym_intf_least_core_idx;
+ uint8 asym_intf_pending_host_req_type;
+ /* Set request pending if clk not present */
+ uint16 asym_intf_ncal_crs_stat;
+ uint8 asym_intf_ncal_crs_stat_idx;
+ uint8 pad;
+} phy_periodic_scca_stats_v3_t;
+
+/* SmartCCA related PHY Logging */
+typedef struct phy_periodic_scca_stats_v255 {
+ uint32 asym_intf_cmplx_pwr[2];
+ uint32 asym_intf_ncal_time;
+ uint32 asym_intf_host_req_mit_turnon_time;
+ uint32 core1_smask_val_bk; /* bt fem control related */
+ int32 asym_intf_ed_thresh;
+
+ int16 crsminpoweru0; /* crsmin thresh */
+ int16 crsminpoweroffset0; /* ac_offset core0 */
+ int16 crsminpoweroffset1; /* ac_offset core1 */
+ int16 Core0InitGainCodeB; /* rx mitigation: eLNA bypass setting */
+ int16 Core1InitGainCodeB; /* rx mitigation: eLNA bypass setting */
+ int16 ed_crsEn; /* phyreg(ed_crsEn) */
+ int16 nvcfg0; /* LLR deweighting coefficient */
+ int16 SlnaRxMaskCtrl0;
+ int16 SlnaRxMaskCtrl1;
+ uint16 save_SlnaRxMaskCtrl0;
+ uint16 save_SlnaRxMaskCtrl1;
+ uint16 asym_intf_ncal_req_chspec; /* channel request noisecal */
+ /* asym_intf_stats includes the following bits:
+ * b[0]: bool asym_intf_rx_noise_mit_on;
+ * b[1]: bool asym_intf_tx_smartcca_on;
+ * b[3:2]: bool asym_intf_elna_bypass[2];
+ * b[4]: bool asym_intf_valid_noise_samp;
+ * b[5]: bool asym_intf_fill_noise_buf;
+ * b[6]: bool asym_intf_ncal_discard;
+ * b[7]: bool slna_reg_saved;
+ * b[8]: bool asym_intf_host_ext_usb; //Host control related variable
+ * b[9]: bool asym_intf_host_ext_usb_chg; // Host control related variable
+ * b[10]: bool asym_intf_host_en; // Host control related variable
+ * b[11]: bool asym_intf_host_enable;
+ * b[12]: bool asym_intf_pending_host_req; // Set request pending if clk not present
+ */
+ uint16 asym_intf_stats;
+
+ uint8 elna_bypass; /* from bt_desense.elna_bypass in gainovr_shm_config() */
+ uint8 btc_mode; /* from bt_desense in gainovr_shm_config() */
+ /* noise at antenna from phy_ac_noise_ant_noise_calc() */
+ int8 noise_dbm_ant[2];
+ /* in phy_ac_noise_calc(), also used by wl noise */
+ int8 noisecalc_cmplx_pwr_dbm[2];
+ uint8 gain_applied; /* from phy_ac_rxgcrs_set_init_clip_gain() */
+
+ int8 asym_intf_tx_smartcca_cm;
+ int8 asym_intf_rx_noise_mit_cm;
+ int8 asym_intf_avg_noise[2];
+ int8 asym_intf_latest_noise[2];
+ /* used to calculate noise_delta for rx mitigation on/off */
+ int8 asym_intf_prev_noise_lvl[2];
+ uint8 asym_intf_noise_calc_gain_2g[2];
+ uint8 asym_intf_noise_calc_gain_5g[2];
+ uint8 asym_intf_ant_noise_idx;
+ uint8 asym_intf_least_core_idx;
+ uint8 phy_crs_thresh_save[2];
+ uint8 asym_intf_initg_desense[2];
+ uint8 asym_intf_pending_host_req_type; /* Set request pending if clk not present */
+ uint16 asym_intf_ncal_crs_stat[12];
+ uint8 asym_intf_ncal_crs_stat_idx;
+} phy_periodic_scca_stats_v255_t;
+
#define PHY_PERIODIC_LOG_VER1 (1u)
typedef struct phy_periodic_log_v1 {
@@ -2453,6 +3672,14 @@
phycal_log_core_v3_t phycal_log_core[BCM_FLEX_ARRAY];
} phycal_log_v3_t;
+#define PHY_CAL_EVENTLOG_VER4 (4u)
+typedef struct phycal_log_v4 {
+ uint8 version; /* Logging structure version */
+ uint8 numcores; /* Number of cores for which core specific data present */
+ uint16 length; /* Length of the entire structure */
+ phy_phycal_v2_t phy_calibration;
+} phycal_log_v4_t;
+
/* Note: The version 2 is reserved for 4357 only. Future chips must not use this version. */
#define MAX_CORE_4357 (2u)
@@ -2538,10 +3765,12 @@
ROAM_LOG_NBR_REP = 5, /* EVT log for Neighbor REP */
ROAM_LOG_BCN_REQ = 6, /* EVT log for BCNRPT REQ */
ROAM_LOG_BCN_REP = 7, /* EVT log for BCNRPT REP */
- ROAM_LOG_BTM_REP = 8, /* EVT log for BTM REP */
+ ROAM_LOG_BTM_REP = 8, /* EVT log for BTM Response */
ROAM_LOG_WIPS_EVENT = 9, /* EVT log for WIPS Event */
ROAM_LOG_6G_NOVLP_REP = 10, /* EVT log for 6G NoVLP Report */
ROAM_LOG_WTC_BTM_REP = 11, /* EVT log for WTC BTM Req/Resp Report */
+ ROAM_LOG_BTM_QUERY = 12, /* EVT log for WTC BTM Query */
+ ROAM_LOG_BTM_REQ = 13, /* EVT log for BTM Request */
PRSV_PERIODIC_ID_MAX
} prsv_periodic_id_enum_t;
@@ -2554,6 +3783,7 @@
#define ROAM_LOG_VER_1 (1u)
#define ROAM_LOG_VER_2 (2u)
#define ROAM_LOG_VER_3 (3u)
+#define ROAM_LOG_VER_4 (4u)
#define ROAM_SSID_LEN (32u)
typedef struct roam_log_trig_v1 {
prsv_periodic_log_hdr_t hdr;
@@ -2608,7 +3838,8 @@
typedef struct roam_scan_ap_info {
int8 rssi;
uint8 cu;
- uint8 pad[2];
+ uint8 cu_avail;
+ uint8 pad;
uint32 score;
uint16 chanspec;
struct ether_addr addr;
@@ -2806,6 +4037,43 @@
};
} roam_log_wtc_btmrep_v3_t;
+typedef struct roam_log_btm_query_v3 {
+ prsv_periodic_log_hdr_t hdr;
+ uint8 token;
+ uint8 reason;
+ uint8 pad[2];
+} roam_log_btm_query_v3_t;
+
+/* ROAM_LOG_VER_4 specific structures */
+typedef struct roam_log_btm_resp_v4 {
+ prsv_periodic_log_hdr_t hdr;
+ uint8 req_mode; /* d11 BSSTRANS req mode */
+ uint8 status; /* d11 BSSTRANS response status code */
+ uint8 token; /* d11 BSSTRANS response token */
+ uint8 term_delay; /* d11 BSSTRANS response BSS Termination delay */
+ struct ether_addr target_addr; /* bssid to move */
+ uint16 pad[1];
+ int result;
+} roam_log_btm_resp_v4_t;
+
+#define ROAM_NBR_RPT_LIST_SIZE 4
+typedef struct roam_nbr_rpt_info {
+ struct ether_addr bssid;
+ uint8 preference;
+ uint8 pad[1];
+} roam_nbr_rpt_info_t;
+
+typedef struct roam_log_btm_req_v4 {
+ prsv_periodic_log_hdr_t hdr;
+ uint8 req_mode; /* d11 BSSTRANS req mode */
+ uint8 token; /* d11 BSSTRANS response token */
+ uint16 nbrlist_size; /* num of nbr in Preferred Candidate List */
+ uint32 disassoc_dur;
+ uint32 validity_dur;
+ uint32 bss_term_dur;
+ roam_nbr_rpt_info_t nbr_list[ROAM_NBR_RPT_LIST_SIZE];
+} roam_log_btm_req_v4_t;
+
#define EVENT_LOG_BUFFER_ID_PMK 0
#define EVENT_LOG_BUFFER_ID_ANONCE 1
#define EVENT_LOG_BUFFER_ID_SNONCE 2
@@ -3004,6 +4272,7 @@
uint8 version; /* Logging structure version */
uint8 numcores; /* Number of cores for which core specific data present */
uint16 length; /* Length of the entire structure */
+
/* Logs general PHY parameters */
phy_periodic_log_cmn_v6_t phy_perilog_cmn;
@@ -3036,7 +4305,10 @@
phy_periodic_btc_stats_v1_t phy_perilog_btc_stats;
/* Logs data pertaining to each core */
- phy_periodic_log_core_v6_t phy_perilog_core[];
+ phy_periodic_log_core_v6_t phy_perilog_core[2];
+
+ /* log data for smartCCA */
+ phy_periodic_scca_stats_v3_t scca_counters_peri_log;
} phy_periodic_log_v11_t;
#define AMT_MATCH_INFRA_BSSID (1 << 0)
@@ -3049,7 +4321,7 @@
uint16 length; /* Length of the structure */
/* Logs general PHY parameters */
- phy_periodic_log_cmn_v7_t phy_perilog_cmn;
+ phy_periodic_log_cmn_v9_t phy_perilog_cmn;
/* Logs ucode counters and NAVs */
phy_periodic_counters_v8_t counters_peri_log;
@@ -3061,6 +4333,141 @@
phy_periodic_obss_stats_v1_t phy_perilog_obss_stats;
/* Logs data pertaining to each core */
- phy_periodic_log_core_v4_t phy_perilog_core[BCM_FLEX_ARRAY];
+ phy_periodic_log_core_v6_t phy_perilog_core[2];
+
+ /* log data for smartCCA */
+ phy_periodic_scca_stats_v2_t scca_counters_peri_log;
} phy_periodic_log_v20_t;
+
+#define PHY_PERIODIC_LOG_VER21 21u
+typedef struct phy_periodic_log_v21 {
+ uint8 version; /* Logging structure version */
+ uint8 numcores; /* Number of cores for which core specific data present */
+ uint16 length; /* Length of the structure */
+
+ /* Logs general PHY parameters */
+ phy_periodic_log_cmn_v9_t phy_perilog_cmn;
+
+ /* Logs ucode counters and NAVs */
+ phy_periodic_counters_v8_t counters_peri_log;
+
+ /* log data for BTcoex */
+ phy_periodic_btc_stats_v1_t phy_perilog_btc_stats;
+
+ /* log data for obss/dynbw */
+ phy_periodic_obss_stats_v1_t phy_perilog_obss_stats;
+
+ /* Logs data pertaining to each core */
+ phy_periodic_log_core_v6_t phy_perilog_core[2];
+
+ /* log data for smartCCA */
+ phy_periodic_scca_stats_v2_t scca_counters_peri_log;
+} phy_periodic_log_v21_t;
+
+#define PHY_PERIODIC_LOG_VER22 22u
+typedef struct phy_periodic_log_v22 {
+ uint8 version; /* Logging structure version */
+ uint8 numcores; /* Number of cores for which core specific data present */
+ uint16 length; /* Length of the structure */
+
+ /* Logs general PHY parameters */
+ phy_periodic_log_cmn_v10_t phy_perilog_cmn;
+
+ /* Logs ucode counters and NAVs */
+ phy_periodic_counters_v9_t counters_peri_log;
+
+ /* log data for BTcoex */
+ phy_periodic_btc_stats_v2_t phy_perilog_btc_stats;
+
+ /* log data for obss/dynbw */
+ phy_periodic_obss_stats_v1_t phy_perilog_obss_stats;
+
+ /* Logs data pertaining to each core */
+ phy_periodic_log_core_v7_t phy_perilog_core[2];
+
+ /* log data for smartCCA */
+ phy_periodic_scca_stats_v2_t scca_counters_peri_log;
+} phy_periodic_log_v22_t;
+
+#define PHY_PERIODIC_LOG_VER23 23u
+typedef struct phy_periodic_log_v23 {
+ uint8 version; /* Logging structure version */
+ uint8 numcores; /* Number of cores for which core specific data present */
+ uint16 length; /* Length of the structure */
+
+ /* Logs general PHY parameters */
+ phy_periodic_log_cmn_v10_t phy_perilog_cmn;
+
+ /* Logs ucode counters and NAVs */
+ phy_periodic_counters_v9_t counters_peri_log;
+
+ /* log data for BTcoex */
+ phy_periodic_btc_stats_v2_t phy_perilog_btc_stats;
+
+ /* log data for obss/dynbw */
+ phy_periodic_obss_stats_v1_t phy_perilog_obss_stats;
+
+ /* Logs data pertaining to each core */
+ phy_periodic_log_core_v7_t phy_perilog_core[2];
+
+ /* log data for smartCCA */
+ phy_periodic_scca_stats_v3_t scca_counters_peri_log;
+} phy_periodic_log_v23_t;
+
+#define PHY_PERIODIC_LOG_VER24 24u
+typedef struct phy_periodic_log_v24 {
+ uint8 version; /* Logging structure version */
+ uint8 numcores; /* Number of cores for which core specific data present */
+ uint16 length; /* Length of the structure */
+
+ /* Logs general PHY parameters */
+ phy_periodic_log_cmn_v10_t phy_perilog_cmn;
+
+ /* Logs ucode counters and NAVs */
+ phy_periodic_counters_v9_t counters_peri_log;
+
+ /* log data for BTcoex */
+ phy_periodic_btc_stats_v2_t phy_perilog_btc_stats;
+
+ /* log data for obss/dynbw */
+ phy_periodic_obss_stats_v2_t phy_perilog_obss_stats;
+
+ /* Logs data pertaining to each core */
+ phy_periodic_log_core_v7_t phy_perilog_core[2];
+
+ /* log data for smartCCA */
+ phy_periodic_scca_stats_v3_t scca_counters_peri_log;
+} phy_periodic_log_v24_t;
+
+/* ************************************************** */
+/* The version 255 for the logging data structures */
+/* is for use in trunk ONLY. In release branches the */
+/* next available version for the particular data */
+/* structure should be used. */
+/* ************************************************** */
+
+#define PHY_PERIODIC_LOG_VER255 255u
+typedef struct phy_periodic_log_v255 {
+ uint8 version; /* Logging structure version */
+ uint8 numcores; /* Number of cores for which core specific data present */
+ uint16 length; /* Length of the structure */
+
+ /* Logs general PHY parameters */
+ phy_periodic_log_cmn_v255_t phy_perilog_cmn;
+
+ /* Logs ucode counters and NAVs */
+ phy_periodic_counters_v255_t counters_peri_log;
+
+ /* log data for BTcoex */
+ phy_periodic_btc_stats_v1_t phy_perilog_btc_stats;
+
+ /* log data for obss/dynbw */
+ phy_periodic_obss_stats_v255_t phy_perilog_obss_stats;
+
+ /* Logs data pertaining to each core */
+ phy_periodic_log_core_v255_t phy_perilog_core[2];
+
+ /* log data for smartCCA */
+ phy_periodic_scca_stats_v255_t scca_counters_peri_log;
+} phy_periodic_log_v255_t;
#endif /* _EVENT_LOG_PAYLOAD_H_ */
diff --git a/include/event_log_set.h b/include/event_log_set.h
index 88a9155..d166305 100644
--- a/include/event_log_set.h
+++ b/include/event_log_set.h
@@ -1,7 +1,7 @@
/*
* EVENT_LOG system definitions
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -135,6 +135,9 @@
#define EVENT_LOG_SET_CHRE_CHATTY (34u)
#endif /* CHRE */
+//For all BCM HAL logging.
+#define EVENT_LOG_SET_BCMHAL (38u)
+
#ifndef NUM_EVENT_LOG_SETS
/* Set a maximum number of sets here. It is not dynamic for
* efficiency of the EVENT_LOG calls. Old branches could define
@@ -143,9 +146,9 @@
*/
#ifdef NUM_EVENT_LOG_SETS_V2
/* for v2, everything has became unsigned */
-#define NUM_EVENT_LOG_SETS (35u)
+#define NUM_EVENT_LOG_SETS (39u)
#else /* NUM_EVENT_LOG_SETS_V2 */
-#define NUM_EVENT_LOG_SETS (35)
+#define NUM_EVENT_LOG_SETS (39)
#endif /* NUM_EVENT_LOG_SETS_V2 */
#endif /* NUM_EVENT_LOG_SETS */
diff --git a/include/event_log_tag.h b/include/event_log_tag.h
index be5865a..47f05bf 100644
--- a/include/event_log_tag.h
+++ b/include/event_log_tag.h
@@ -1,7 +1,7 @@
/*
* EVENT_LOG system definitions
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -231,12 +231,12 @@
#define EVENT_LOG_TAG_FILS_DBG 219
#define EVENT_LOG_TAG_FILS_INFO 220
#define EVENT_LOG_TAG_FILS_ERROR 221
-#define EVENT_LOG_TAG_UNUSED1 222
-#define EVENT_LOG_TAG_UNUSED2 223
+#define EVENT_LOG_TAG_BTCX_STATS_AUX 222
+#define EVENT_LOG_TAG_ROAM_TGT_EVAL 223
#define EVENT_LOG_TAG_PPR_ERROR 224
/* Arbitrator callback log tags */
-#define EVENT_LOG_TAG_STF_ARB_CB_TRACE 224
+#define EVENT_LOG_TAG_STF_ARB_CB_TRACE 225 /* Intentional duplicated value as ERROR */
#define EVENT_LOG_TAG_STF_ARB_CB_ERROR 225
#define EVENT_LOG_TAG_PHY_PERIODIC_SEC 226
#define EVENT_LOG_TAG_RTE_ERROR 227
@@ -533,16 +533,46 @@
#define EVENT_LOG_TAG_PASN_ERROR 423
#define EVENT_LOG_TAG_PASN_INFO 424
-#ifdef WLIGMPOE
-#define EVENT_LOG_TAG_IGMP_DBG 425
-#define EVENT_LOG_TAG_IGMP_INFO 426
-#define EVENT_LOG_TAG_IGMP_ERR 427
-#endif /* WLIGMPOE */
+#define EVENT_LOG_TAG_IGMP_DBG 425
+#define EVENT_LOG_TAG_IGMP_INFO 426
+#define EVENT_LOG_TAG_IGMP_ERR 427
#define EVENT_LOG_TAG_DNGL_CAPEXT_ERROR 428
+#define EVENT_LOG_TAG_DVFS_INFO 429
+#define EVENT_LOG_TAG_DVFS_ERROR 430
+
+#define EVENT_LOG_TAG_BTCX_ERR 431
+#define EVENT_LOG_TAG_BTCX_INFO 432
+#define EVENT_LOG_TAG_BTCX_TRACE 433
+
+#define EVENT_LOG_TAG_BCMHAL_SOCI_NCI_ERROR 434
+#define EVENT_LOG_TAG_BCMHAL_SOCI_NCI_TRACE 435
+#define EVENT_LOG_TAG_BCMHAL_SOCI_NCI_INFO 436
+#define EVENT_LOG_TAG_WL_TOSS 437
+
+/* 6GHz Client-to-Client (C2C) logging */
+#define EVENT_LOG_TAG_C2C_ERROR 438
+#define EVENT_LOG_TAG_C2C_DBG 439
+
+#define EVENT_LOG_TAG_OCT_INFO 440
+
+#define EVENT_LOG_TAG_PHY_AZ_INFO 441
+#define EVENT_LOG_TAG_PHY_AZ_INFO_DBG 442
+#define EVENT_LOG_TAG_PHY_AZ_INFO_CSI 443
+
+#define EVENT_LOG_TAG_WL_RATE_ERR 444
+
+#define EVENT_LOG_TAG_6GCHANPROF_ERROR 445
+#define EVENT_LOG_TAG_6GCHANPROF_INFO 446
+#define EVENT_LOG_TAG_6GCHANPROF_TRACE 447
+
+/* OWE STUFF */
+#define EVENT_LOG_TAG_OWE_DBG 448
+#define EVENT_LOG_TAG_OWE_INFO 449
+#define EVENT_LOG_TAG_OWE_ERR 450
/* EVENT_LOG_TAG_MAX = Set to the same value of last tag, not last tag + 1 */
-#define EVENT_LOG_TAG_MAX 428
+#define EVENT_LOG_TAG_MAX 450
typedef enum wl_el_set_type_def {
EVENT_LOG_SET_TYPE_DEFAULT = 0, /* flush the log buffer when it is full - Default option */
@@ -615,7 +645,8 @@
struct {
uint8 extended_tag; /* Extended tag, bits[7..4] are reserved */
uint8 extended_count; /* Extended count. Reserved for now. */
- uint16 rsvd; /* Reserved */
+ uint8 extended_fmtnum; /* bits[3..0] used. Rest reserved */
+ uint8 rsvd; /* Reserved */
};
uint32 t; /* Type cheat */
diff --git a/include/event_trace.h b/include/event_trace.h
index 606bf04..e760301 100644
--- a/include/event_trace.h
+++ b/include/event_trace.h
@@ -1,7 +1,7 @@
/*
* Trace log blocks sent over HBUS
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/fils.h b/include/fils.h
index 3be620a..935cd30 100644
--- a/include/fils.h
+++ b/include/fils.h
@@ -1,7 +1,7 @@
/*
* Fundamental types and constants relating to FILS AUTHENTICATION
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/frag.h b/include/frag.h
similarity index 61%
rename from frag.h
rename to include/frag.h
index c5127ab..f2f8abd 100644
--- a/frag.h
+++ b/include/frag.h
@@ -2,7 +2,7 @@
* IE/TLV (de)fragmentation declarations/definitions for
* Broadcom 802.11abgn Networking Device Driver
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -26,7 +26,21 @@
#ifndef __FRAG_H__
#define __FRAG_H__
+int bcm_tlv_dot11_defrag(const void *buf, uint buf_len, uint8 id, bool id_ext,
+ uint8 *out, uint *out_len, uint *data_len);
+
int bcm_tlv_dot11_frag_tot_len(const void *buf, uint buf_len,
uint8 id, bool id_ext, uint *ie_len);
+int bcm_tlv_dot11_frag_tot_data_len(const void *buf, uint buf_len,
+ uint8 id, bool id_ext, uint *ie_len, uint *data_len);
+/* To support IE fragmentation.
+ * data will be fit into a series of elements consisting of one leading element
+ * followed by Fragment elements if needed.
+ * data_len is in/out parameter, it has the length of all the elements, including
+ * the leading element header size.
+ * Caller can get elements length by passing dst as NULL.
+ */
+int bcm_tlv_dot11_frag(uint8 id, bool id_ext, const void *data, uint data_len,
+ uint8 *dst, uint *ie_len);
#endif /* __FRAG_H__ */
diff --git a/include/fwpkg_utils.h b/include/fwpkg_utils.h
index c7222ed..899b4fa 100644
--- a/include/fwpkg_utils.h
+++ b/include/fwpkg_utils.h
@@ -1,7 +1,7 @@
/*
* Firmware package defines
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/hnd_armtrap.h b/include/hnd_armtrap.h
index e70b129..370ded1 100644
--- a/include/hnd_armtrap.h
+++ b/include/hnd_armtrap.h
@@ -1,7 +1,7 @@
/*
* HND arm trap handling.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/hnd_cons.h b/include/hnd_cons.h
index 7a281b4..5482c27 100644
--- a/include/hnd_cons.h
+++ b/include/hnd_cons.h
@@ -1,7 +1,7 @@
/*
* Console support for RTE - for host use only.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/hnd_debug.h b/include/hnd_debug.h
index d1a2496..48440b2 100644
--- a/include/hnd_debug.h
+++ b/include/hnd_debug.h
@@ -1,7 +1,7 @@
/*
* HND Run Time Environment debug info area
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -231,6 +231,8 @@
#define DUMP_INFO_PTR_PTR_3 0xf8
#define DUMP_INFO_PTR_PTR_4 0x874
#define DUMP_INFO_PTR_PTR_5 0x878
+#define DUMP_INFO_PTR_PTR_6 0x4f0
+#define DUMP_INFO_PTR_PTR_7 0x4f8
#define DUMP_INFO_PTR_PTR_END 0xffffffff
#define DUMP_INFO_PTR_PTR_LIST DUMP_INFO_PTR_PTR_0, \
DUMP_INFO_PTR_PTR_1, \
@@ -238,6 +240,8 @@
DUMP_INFO_PTR_PTR_3, \
DUMP_INFO_PTR_PTR_4, \
DUMP_INFO_PTR_PTR_5, \
+ DUMP_INFO_PTR_PTR_6, \
+ DUMP_INFO_PTR_PTR_7, \
DUMP_INFO_PTR_PTR_END
extern bool hnd_debug_info_in_trap_context(void);
diff --git a/include/hnd_pktpool.h b/include/hnd_pktpool.h
index ac902d1..9e13174 100644
--- a/include/hnd_pktpool.h
+++ b/include/hnd_pktpool.h
@@ -1,7 +1,7 @@
/*
* HND generic packet pool operation primitives
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -155,6 +155,9 @@
pktpool_cbextn_info_t cb_haddr; /**< PCIe SPLITRX related */
pktpool_rxurb_cbinfo_t dmarxurb; /**< dma rx urb related */
+ uint32 pktpool_flags; /* different packet pool flags */
+ void *freelist_tail; /* free list tail, used only in specific rxlfrag pools */
+
#ifdef BCMDBG_POOL
uint8 dbg_cbcnt;
pktpool_cbinfo_t dbg_cbs[PKTPOOL_CB_MAX];
@@ -163,6 +166,8 @@
#endif
} pktpool_t;
+#define PKTPOOL_RXLFRAG_SORTED_INSERT 0x00000001u
+
pktpool_t *get_pktpools_registry(int id);
#define pktpool_get(pktp) (pktpool_get_ext((pktp), (pktp)->type, NULL))
@@ -256,26 +261,16 @@
#ifdef BCMFRAGPOOL
#define SHARED_FRAG_POOL (pktpool_shared_lfrag)
extern pktpool_t *pktpool_shared_lfrag;
-#endif
-
-#ifdef BCMALFRAGPOOL
#define SHARED_ALFRAG_POOL (pktpool_shared_alfrag)
extern pktpool_t *pktpool_shared_alfrag;
-
#define SHARED_ALFRAG_DATA_POOL (pktpool_shared_alfrag_data)
extern pktpool_t *pktpool_shared_alfrag_data;
-#endif
+#endif /* BCMFRAGPOOL */
#ifdef BCMRESVFRAGPOOL
-#ifdef APP
#define RESV_FRAG_POOL (NULL)
#define RESV_ALFRAG_POOL (pktpool_resv_alfrag)
#define RESV_ALFRAG_DATA_POOL (pktpool_resv_alfrag_data)
-#else
-#define RESV_FRAG_POOL (pktpool_resv_lfrag)
-#define RESV_ALFRAG_POOL (NULL)
-#define RESV_ALFRAG_DATA_POOL (NULL)
-#endif /* APP */
#define RESV_POOL_INFO (resv_pool_info)
#else
#define RESV_FRAG_POOL ((struct pktpool *)NULL)
@@ -295,12 +290,8 @@
void hnd_pktpool_refill(bool minimal);
#ifdef BCMRESVFRAGPOOL
-#ifdef APP
extern pktpool_t *pktpool_resv_alfrag;
extern pktpool_t *pktpool_resv_alfrag_data;
-#else
-extern pktpool_t *pktpool_resv_lfrag;
-#endif /* APP */
extern struct resv_info *resv_pool_info;
#endif /* BCMRESVFRAGPOOL */
diff --git a/include/hnd_pktq.h b/include/hnd_pktq.h
index acbcdd2..cea3241 100644
--- a/include/hnd_pktq.h
+++ b/include/hnd_pktq.h
@@ -1,7 +1,7 @@
/*
* HND generic pktq operation primitives
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/hnd_trap.h b/include/hnd_trap.h
index 622c372..47d6e85 100644
--- a/include/hnd_trap.h
+++ b/include/hnd_trap.h
@@ -1,7 +1,7 @@
/*
* HND Trap handling.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/hndchipc.h b/include/hndchipc.h
index 5fc9cdb..38664c9 100644
--- a/include/hndchipc.h
+++ b/include/hndchipc.h
@@ -1,7 +1,7 @@
/*
* HND SiliconBackplane chipcommon support - OS independent.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/hndlhl.h b/include/hndlhl.h
index bb2fab5..558aee0 100644
--- a/include/hndlhl.h
+++ b/include/hndlhl.h
@@ -1,7 +1,7 @@
/*
* HND SiliconBackplane PMU support.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/hndmem.h b/include/hndmem.h
index 8d244ba..fedc476 100644
--- a/include/hndmem.h
+++ b/include/hndmem.h
@@ -1,7 +1,7 @@
/*
* Utility routines for configuring different memories in Broadcom chips.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/hndoobr.h b/include/hndoobr.h
index 31c0580..919b847 100644
--- a/include/hndoobr.h
+++ b/include/hndoobr.h
@@ -1,7 +1,7 @@
/*
* HND OOBR interface header
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/hndpmu.h b/include/hndpmu.h
index 58c0bf7..da912c8 100644
--- a/include/hndpmu.h
+++ b/include/hndpmu.h
@@ -1,7 +1,7 @@
/*
* HND SiliconBackplane PMU support.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/hndsoc.h b/include/hndsoc.h
index 8e60b06..f2d9f59 100644
--- a/include/hndsoc.h
+++ b/include/hndsoc.h
@@ -1,7 +1,7 @@
/*
* Broadcom HND chip & on-chip-interconnect-related definitions.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/linux_osl.h b/include/linux_osl.h
index 73948c8..94903c5 100644
--- a/include/linux_osl.h
+++ b/include/linux_osl.h
@@ -1,7 +1,7 @@
/*
* Linux OS Independent Layer
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -185,6 +185,13 @@
#define VMALLOCZ(osh, size) osl_debug_vmallocz((osh), (size), __LINE__, __FILE__)
#define VMFREE(osh, addr, size) \
({osl_debug_vmfree((osh), ((void *)addr), (size), __LINE__, __FILE__);(addr) = NULL;})
+ /* From the linux kernel 4.12, kvmalloc introduced which tries basically to
+ * allocate even large blocks with kmalloc and falls back to vmalloc if fail.
+ */
+ #define KVMALLOC(osh, size) osl_debug_kvmalloc((osh), (size), __LINE__, __FILE__)
+ #define KVMALLOCZ(osh, size) osl_debug_kvmallocz((osh), (size), __LINE__, __FILE__)
+ #define KVMFREE(osh, addr, size) \
+ ({osl_debug_kvmfree((osh), ((void *)addr), (size), __LINE__, __FILE__);(addr) = NULL;})
#define MALLOCED(osh) osl_malloced((osh))
#define MEMORY_LEFTOVER(osh) osl_check_memleak(osh)
#define MALLOC_DUMP(osh, b) osl_debug_memdump((osh), (b))
@@ -194,6 +201,10 @@
extern void *osl_debug_vmalloc(osl_t *osh, uint size, int line, const char* file);
extern void *osl_debug_vmallocz(osl_t *osh, uint size, int line, const char* file);
extern void osl_debug_vmfree(osl_t *osh, void *addr, uint size, int line, const char* file);
+ extern void *osl_debug_kvmalloc(osl_t *osh, uint size, int line, const char* file);
+ extern void *osl_debug_kvmallocz(osl_t *osh, uint size, int line, const char* file);
+ extern void osl_debug_kvmfree(osl_t *osh, void *addr, uint size, int line,
+ const char* file);
extern uint osl_malloced(osl_t *osh);
struct bcmstrbuf;
extern int osl_debug_memdump(osl_t *osh, struct bcmstrbuf *b);
@@ -202,22 +213,39 @@
#define MALLOC(osh, size) osl_malloc((osh), (size))
#define MALLOCZ(osh, size) osl_mallocz((osh), (size))
#define MALLOC_RA(osh, size, callsite) osl_mallocz((osh), (size))
- #define MFREE(osh, addr, size) ({osl_mfree((osh), ((void *)addr), (size));(addr) = NULL;})
+ #define MFREE(osh, addr, size) \
+ ({osl_mfree((osh), ((void *)addr), (size));(addr) = NULL;})
#define VMALLOC(osh, size) osl_vmalloc((osh), (size))
#define VMALLOCZ(osh, size) osl_vmallocz((osh), (size))
- #define VMFREE(osh, addr, size) ({osl_vmfree((osh), ((void *)addr), (size));(addr) = NULL;})
+ #define VMFREE(osh, addr, size) \
+ ({osl_vmfree((osh), ((void *)addr), (size));(addr) = NULL;})
+ /* From the linux kernel 4.12, kvmalloc introduced which tries basically to
+ * allocate even large blocks with kmalloc and falls back to vmalloc if fail.
+ */
+ #define KVMALLOC(osh, size) osl_kvmalloc((osh), (size))
+ #define KVMALLOCZ(osh, size) osl_kvmallocz((osh), (size))
+ #define KVMFREE(osh, addr, size) \
+ ({osl_kvmfree((osh), ((void *)addr), (size));(addr) = NULL;})
#define MALLOCED(osh) osl_malloced((osh))
#define MEMORY_LEFTOVER(osh) osl_check_memleak(osh)
extern void *osl_vmalloc(osl_t *osh, uint size);
extern void *osl_vmallocz(osl_t *osh, uint size);
extern void osl_vmfree(osl_t *osh, void *addr, uint size);
+ extern void *osl_kvmalloc(osl_t *osh, uint size);
+ extern void *osl_kvmallocz(osl_t *osh, uint size);
+ extern void osl_kvmfree(osl_t *osh, void *addr, uint size);
extern uint osl_malloced(osl_t *osh);
extern uint osl_check_memleak(osl_t *osh);
#endif /* BCMDBG_MEM && !BINCMP */
+#define DMA_MALLOCZ(osh, size, dmable_size, dmah) osl_dma_mallocz((osh), (size), (dmable_size))
+#define DMA_MFREE(osh, addr, size, dmah) osl_dma_mfree((osh), (addr), (size))
+
extern void *osl_malloc(osl_t *osh, uint size);
extern void *osl_mallocz(osl_t *osh, uint size);
+extern void *osl_dma_mallocz(osl_t *osh, uint size, uint *dmable_size);
extern void osl_mfree(osl_t *osh, void *addr, uint size);
+extern void osl_dma_mfree(osl_t *osh, void *addr, uint size);
#define MALLOC_NODBG(osh, size) osl_malloc((osh), (size))
#define MALLOCZ_NODBG(osh, size) osl_mallocz((osh), (size))
#define MFREE_NODBG(osh, addr, size) ({osl_mfree((osh), ((void *)addr), (size));(addr) = NULL;})
@@ -274,6 +302,12 @@
#define OSL_SMP_WMB() smp_wmb()
+#if defined(__aarch64__)
+#define OSL_ISB() isb()
+#else
+#define OSL_ISB() do { /* noop */ } while (0)
+#endif /* __aarch64__ */
+
/* API for CPU relax */
extern void osl_cpu_relax(void);
#define OSL_CPU_RELAX() osl_cpu_relax()
@@ -816,6 +850,7 @@
#define OSL_ATOMIC_INIT(osh, v) atomic_set(v, 0)
#define OSL_ATOMIC_INC(osh, v) atomic_inc(v)
#define OSL_ATOMIC_INC_RETURN(osh, v) atomic_inc_return(v)
+#define OSL_ATOMIC_INC_AND_TEST(osh, v) atomic_inc_and_test(v)
#define OSL_ATOMIC_DEC(osh, v) atomic_dec(v)
#define OSL_ATOMIC_DEC_RETURN(osh, v) atomic_dec_return(v)
#define OSL_ATOMIC_READ(osh, v) atomic_read(v)
diff --git a/include/linux_pkt.h b/include/linux_pkt.h
index 2e5b587..8c4f22b 100644
--- a/include/linux_pkt.h
+++ b/include/linux_pkt.h
@@ -1,7 +1,7 @@
/*
* Linux Packet (skb) interface
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -198,6 +198,9 @@
#define PKTLITIDX_1(skb) ({BCM_REFERENCE(skb); 0;})
#define PKTSETLITIDX_1(skb, idx) ({BCM_REFERENCE(skb); BCM_REFERENCE(idx);})
#define PKTRESETLITIDX_1(skb) ({BCM_REFERENCE(skb);})
+#define PKTLITIDX_2(skb) ({BCM_REFERENCE(skb); 0;})
+#define PKTSETLITIDX_2(skb, idx) ({BCM_REFERENCE(skb); BCM_REFERENCE(idx);})
+#define PKTRESETLITIDX_2(skb) ({BCM_REFERENCE(skb);})
#define PKTRITIDX(skb) ({BCM_REFERENCE(skb); 0;})
#define PKTSETRITIDX(skb, idx) ({BCM_REFERENCE(skb); BCM_REFERENCE(idx);})
@@ -205,6 +208,9 @@
#define PKTRITIDX_1(skb) ({BCM_REFERENCE(skb); 0;})
#define PKTSETRITIDX_1(skb, idx) ({BCM_REFERENCE(skb); BCM_REFERENCE(idx);})
#define PKTRESETRITIDX_1(skb) ({BCM_REFERENCE(skb);})
+#define PKTRITIDX_2(skb) ({BCM_REFERENCE(skb); 0;})
+#define PKTSETRITIDX_2(skb, idx) ({BCM_REFERENCE(skb); BCM_REFERENCE(idx);})
+#define PKTRESETRITIDX_2(skb) ({BCM_REFERENCE(skb);})
#define PKTSETSKIPCT(osh, skb) ({BCM_REFERENCE(osh); BCM_REFERENCE(skb);})
#define PKTCLRSKIPCT(osh, skb) ({BCM_REFERENCE(osh); BCM_REFERENCE(skb);})
diff --git a/include/linuxver.h b/include/linuxver.h
index efdad33..248746b 100644
--- a/include/linuxver.h
+++ b/include/linuxver.h
@@ -2,7 +2,7 @@
* Linux-specific abstractions to gain some independence from linux kernel versions.
* Pave over some 2.2 versus 2.4 versus 2.6 kernel differences.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -349,11 +349,13 @@
}
return ret;
}
+
static inline void pci_free_consistent(struct pci_dev *hwdev, size_t size,
void *vaddr, dma_addr_t dma_handle)
{
free_pages((unsigned long)vaddr, get_order(size));
}
+
#ifdef ILSIM
extern uint pci_map_single(void *dev, void *va, uint size, int direction);
extern void pci_unmap_single(void *dev, uint pa, uint size, int direction);
@@ -467,6 +469,7 @@
tasklet->routine = (void (*)(void *))func;
tasklet->data = (void *)data;
}
+
#define tasklet_kill(tasklet) { do {} while (0); }
/* 2.4.x introduced del_timer_sync() */
@@ -956,4 +959,18 @@
}
#endif /* LINUX_VER >= 5.0 */
+#if (LINUX_VERSION_CODE < KERNEL_VERSION(5, 10, 0))
+#define GETFS_AND_SETFS_TO_KERNEL_DS(fs) \
+{ \
+ fs = get_fs(); \
+ set_fs(KERNEL_DS); \
+}
+
+#define SETFS(fs) set_fs(fs)
+#else
+/* From 5.10 kernel get/set_fs are obsolete and direct kernel_read/write operations can be used */
+#define GETFS_AND_SETFS_TO_KERNEL_DS(fs) BCM_REFERENCE(fs)
+#define SETFS(fs) BCM_REFERENCE(fs)
+#endif /* LINUX_VERSION_CODE < KERNEL_VERSION(5, 10, 0) */
+
#endif /* _linuxver_h_ */
diff --git a/include/lpflags.h b/include/lpflags.h
index 9889750..6ff882a 100644
--- a/include/lpflags.h
+++ b/include/lpflags.h
@@ -1,7 +1,7 @@
/*
* Chip related low power flags
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/mbo.h b/include/mbo.h
index 7ff397b..8a85158 100644
--- a/include/mbo.h
+++ b/include/mbo.h
@@ -1,7 +1,7 @@
/*
* Fundamental types and constants relating to WFA MBO
* (Multiband Operation)
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/miniopt.h b/include/miniopt.h
index b483768..60dc3b7 100644
--- a/include/miniopt.h
+++ b/include/miniopt.h
@@ -1,7 +1,7 @@
/*
* Command line options parser.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/msf.h b/include/msf.h
index 27d0ce7..77cabf6 100644
--- a/include/msf.h
+++ b/include/msf.h
@@ -1,7 +1,7 @@
/*
* Common interface to MSF (multi-segment format) definitions.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/msgtrace.h b/include/msgtrace.h
index 126f2f3..09585ce 100644
--- a/include/msgtrace.h
+++ b/include/msgtrace.h
@@ -1,7 +1,7 @@
/*
* Trace messages sent over HBUS
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/nan.h b/include/nan.h
index 416605a..d32c980 100644
--- a/include/nan.h
+++ b/include/nan.h
@@ -2,7 +2,7 @@
* Fundamental types and constants relating to WFA NAN
* (Neighbor Awareness Networking)
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -159,39 +159,44 @@
NAN_ATTR_COUNTRY_CODE = 11,
NAN_ATTR_RANGING = 12,
NAN_ATTR_CLUSTER_DISC = 13,
+
/* nan 2.0 */
- NAN_ATTR_SVC_DESC_EXTENSION = 14,
- NAN_ATTR_NAN_DEV_CAP = 15,
- NAN_ATTR_NAN_NDP = 16,
- NAN_ATTR_NAN_NMSG = 17,
- NAN_ATTR_NAN_AVAIL = 18,
- NAN_ATTR_NAN_NDC = 19,
- NAN_ATTR_NAN_NDL = 20,
- NAN_ATTR_NAN_NDL_QOS = 21,
- NAN_ATTR_MCAST_SCHED = 22,
- NAN_ATTR_UNALIGN_SCHED = 23,
- NAN_ATTR_PAGING_UCAST = 24,
- NAN_ATTR_PAGING_MCAST = 25,
- NAN_ATTR_RANGING_INFO = 26,
- NAN_ATTR_RANGING_SETUP = 27,
- NAN_ATTR_FTM_RANGE_REPORT = 28,
- NAN_ATTR_ELEMENT_CONTAINER = 29,
- NAN_ATTR_WLAN_INFRA_EXT = 30,
- NAN_ATTR_EXT_P2P_OPER = 31,
- NAN_ATTR_EXT_IBSS = 32,
- NAN_ATTR_EXT_MESH = 33,
- NAN_ATTR_CIPHER_SUITE_INFO = 34,
- NAN_ATTR_SEC_CTX_ID_INFO = 35,
- NAN_ATTR_SHARED_KEY_DESC = 36,
- NAN_ATTR_MCAST_SCHED_CHANGE = 37,
- NAN_ATTR_MCAST_SCHED_OWNER_CHANGE = 38,
- NAN_ATTR_PUBLIC_AVAILABILITY = 39,
- NAN_ATTR_SUB_SVC_ID_LIST = 40,
- NAN_ATTR_NDPE = 41,
+ NAN_ATTR_SVC_DESC_EXTENSION = 14,
+ NAN_ATTR_NAN_DEV_CAP = 15,
+ NAN_ATTR_NAN_NDP = 16,
+ NAN_ATTR_NAN_NMSG = 17,
+ NAN_ATTR_NAN_AVAIL = 18,
+ NAN_ATTR_NAN_NDC = 19,
+ NAN_ATTR_NAN_NDL = 20,
+ NAN_ATTR_NAN_NDL_QOS = 21,
+ NAN_ATTR_MCAST_SCHED = 22,
+ NAN_ATTR_UNALIGN_SCHED = 23,
+ NAN_ATTR_PAGING_UCAST = 24,
+ NAN_ATTR_PAGING_MCAST = 25,
+ NAN_ATTR_RANGING_INFO = 26,
+ NAN_ATTR_RANGING_SETUP = 27,
+ NAN_ATTR_FTM_RANGE_REPORT = 28,
+ NAN_ATTR_ELEMENT_CONTAINER = 29,
+ NAN_ATTR_WLAN_INFRA_EXT = 30,
+ NAN_ATTR_EXT_P2P_OPER = 31,
+ NAN_ATTR_EXT_IBSS = 32,
+ NAN_ATTR_EXT_MESH = 33,
+ NAN_ATTR_CIPHER_SUITE_INFO = 34,
+ NAN_ATTR_SEC_CTX_ID_INFO = 35,
+ NAN_ATTR_SHARED_KEY_DESC = 36,
+ NAN_ATTR_MCAST_SCHED_CHANGE = 37,
+ NAN_ATTR_MCAST_SCHED_OWNER_CHANGE = 38,
+ NAN_ATTR_PUBLIC_AVAILABILITY = 39,
+ NAN_ATTR_SUB_SVC_ID_LIST = 40,
+ NAN_ATTR_NDPE = 41,
+ NAN_ATTR_DEV_CAP_EXT = 42, /* NAN R4, Device Capability Extension */
+ NAN_ATTR_NIRA = 43, /* NAN R4, Identity Resolution Attribute */
+ NAN_ATTR_NPBA = 44, /* NAN R4, Pairing Bootstrapping Attribute */
+
/* change NAN_ATTR_MAX_ID to max ids + 1, excluding NAN_ATTR_VENDOR_SPECIFIC.
* This is used in nan_parse.c
*/
- NAN_ATTR_MAX_ID = NAN_ATTR_NDPE + 1,
+ NAN_ATTR_MAX_ID = NAN_ATTR_NPBA + 1,
NAN_ATTR_VENDOR_SPECIFIC = 221
};
@@ -786,6 +791,16 @@
#define NAN_CHAN_ENTRY_BW_LT_80MHZ 0
#define NAN_CHAN_ENTRY_BW_EQ_160MHZ 1
+/* Channel bitmap field for when opclass >=131 */
+#define NAN_CHAN_BITMAP_EXT_START_CHANNEL_MASK 0x00FF
+#define NAN_CHAN_BITMAP_EXT_START_CHANNEL_SHIFT 0
+#define NAN_CHAN_BITMAP_EXT_NUM_CHANNEL_MASK 0xFF00
+#define NAN_CHAN_BITMAP_EXT_NUM_CHANNEL_SHIFT 8
+#define NAN_CHAN_BITMAP_EXT_NUM_CHANNEL(bmap) (((bmap) & NAN_CHAN_BITMAP_EXT_NUM_CHANNEL_MASK) \
+ >> NAN_CHAN_BITMAP_EXT_NUM_CHANNEL_SHIFT)
+#define NAN_CHAN_BITMAP_EXT_START_CHANNEL(bmap) (((bmap) & NAN_CHAN_BITMAP_EXT_START_CHANNEL_MASK) \
+ >> NAN_CHAN_BITMAP_EXT_START_CHANNEL_SHIFT)
+
/*
* NDL Attribute WFA Tech. Spec ver 1.0.r12 (section 10.7.19.2)
*/
@@ -899,6 +914,51 @@
uint8 capabilities; /* DFS Master, Extended key id etc */
} BWL_POST_PACKED_STRUCT wifi_nan_dev_cap_t;
+/* Regulatory info - operation types in 6G band, Table 126, NAN R4 spec.
+ * Also, see Table E-12, REVme_D1.0
+ */
+typedef enum nan_mac_6g_op_type {
+ /* Indoor AP, i.e., LPI(Low Power Indoor) AP.
+ * AFC is not required but with some regulations to be indoor opeation.
+ */
+ NAN_MAC_6G_OP_INDOOR_AP = 0,
+
+ /* Standard Power AP, needs AFC coordination */
+ NAN_MAC_6G_OP_SP_AP = 1,
+
+ /* Very Low Power AP - VLP AP
+ * AFC is not required. Resticted with very low transmit power
+ * This is the default mode of all P2P devices.
+ */
+ NAN_MAC_6G_OP_VLP_AP = 2,
+
+ /* Indoor Enabled AP.
+ * Devices capable of receiving the "enabling signal" and configures itself to use
+ * C2C power level which is 10dB Higher than VLP AP.
+ */
+ NAN_MAC_6G_OP_INDOOR_ENABLED_AP = 3,
+
+ /* This is kind of hybrid mode (AFC in indoors).
+ * Devices opering in indoors and standard power mode with AFC.
+ */
+ NAN_MAC_6G_OP_INDOOR_SP_AP = 4
+} nan_mac_6g_op_type_e;
+
+/* First byte of the extended capabilities is the regulatory info */
+typedef struct nan_mac_dev_cap_ext_reg_info_s {
+ uint8 reg_info_6g_present:1; /* bit0 */
+ uint8 reg_info_6g:3; /* bits 1-3, see nan_mac_6g_op_type_e */
+ uint8 reserved:4; /* bits 4-7 */
+} nan_mac_dev_cap_ext_reg_info_t;
+
+/* NAN R4 - Device Capability Extension Attribute */
+typedef BWL_PRE_PACKED_STRUCT struct wifi_nan_dev_cap_ext_s {
+ uint8 id; /* 0x2A */
+ uint16 len; /* Length */
+ /* Bit field with variable length in octets as indicated in the len field */
+ uint8 data[];
+} BWL_POST_PACKED_STRUCT wifi_nan_dev_cap_ext_t;
+
/* map id related */
/* all maps */
@@ -937,12 +997,15 @@
#define NAN_DEV_CAP_COMMIT_DW_5G_SHIFT 3
#define NAN_DEV_CAP_COMMIT_DW_2G_OVERWRITE_SHIFT 6
#define NAN_DEV_CAP_COMMIT_DW_5G_OVERWRITE_SHIFT 10
+
/* Operation Mode */
#define NAN_DEV_CAP_OP_PHY_MODE_HT_ONLY 0x00
#define NAN_DEV_CAP_OP_PHY_MODE_VHT 0x01
#define NAN_DEV_CAP_OP_PHY_MODE_VHT_8080 0x02
#define NAN_DEV_CAP_OP_PHY_MODE_VHT_160 0x04
+#define NAN_DEV_CAP_OP_PHY_MODE_HE_160 0x04
#define NAN_DEV_CAP_OP_PAGING_NDL 0x08
+#define NAN_DEV_CAP_OP_PHY_MODE_HE 0x10
#define NAN_DEV_CAP_OP_MODE_VHT_MASK 0x01
#define NAN_DEV_CAP_OP_MODE_VHT_SHIFT 0
@@ -952,6 +1015,8 @@
#define NAN_DEV_CAP_OP_MODE_VHT160_SHIFT 2
#define NAN_DEV_CAP_OP_MODE_PAGING_NDL_MASK 0x08
#define NAN_DEV_CAP_OP_MODE_PAGING_NDL_SHIFT 3
+#define NAN_DEV_CAP_OP_MODE_HE_MASK 0x10
+#define NAN_DEV_CAP_OP_MODE_HE_SHIFT 4
#define NAN_DEV_CAP_RX_ANT_SHIFT 4
#define NAN_DEV_CAP_TX_ANT_MASK 0x0F
@@ -964,14 +1029,26 @@
/* DFS master capability */
#define NAN_DEV_CAP_DFS_MASTER_MASK 0x01
-#define NAN_DEV_CAP_DFS_MASTER_SHIFT 0
+#define NAN_DEV_CAP_DFS_MASTER_SHIFT 0u
/* extended iv cap */
#define NAN_DEV_CAP_EXT_KEYID_MASK 0x02
-#define NAN_DEV_CAP_EXT_KEYID_SHIFT 1
+#define NAN_DEV_CAP_EXT_KEYID_SHIFT 1u
+/* Simultaneous NDP data reception capability */
+#define NAN_DEV_CAP_SIMULTANEOUS_DATA_RECV_MASK 0x04
+#define NAN_DEV_CAP_SIMULTANEOUS_DATA_RECV_SHIFT 2u
/* NDPE attribute support */
#define NAN_DEV_CAP_NDPE_ATTR_SUPPORT_MASK 0x08
+#define NAN_DEV_CAP_NDPE_ATTR_SUPPORT_SHIFT 3u
#define NAN_DEV_CAP_NDPE_ATTR_SUPPORT(_cap) ((_cap) & NAN_DEV_CAP_NDPE_ATTR_SUPPORT_MASK)
+#ifdef NAN_REKEY
+#define NAN_DEV_CAP_PTK_REKEY_SUPPORT_MASK 0x10
+#define NAN_DEV_CAP_PTK_REKEY_SUPPORT_SHIFT 4u
+
+#define NAN_DEV_CAP_GTK_REKEY_SUPPORT_MASK 0x20
+#define NAN_DEV_CAP_GTK_REKEY_SUPPORT_SHIFT 5u
+#endif /* NAN_REKEY */
+
/* Band IDs */
enum {
NAN_BAND_ID_TVWS = 0,
@@ -980,14 +1057,28 @@
NAN_BAND_ID_3G = 3, /* 3.6 GHz */
NAN_BAND_ID_5G = 4, /* 4.9 & 5 GHz */
NAN_BAND_ID_60G = 5, /* 60 GHz */
- NAN_BAND_ID_6G = 6 /* 6 GHz (proprietary) */
+ NAN_BAND_ID_6G = 6 /* 6 GHz */
};
typedef uint8 nan_band_id_t;
/* NAN supported band in device capability */
#define NAN_DEV_CAP_SUPPORTED_BANDS_2G (1 << NAN_BAND_ID_2G)
#define NAN_DEV_CAP_SUPPORTED_BANDS_5G (1 << NAN_BAND_ID_5G)
+#define NAN_DEV_CAP_SUPPORTED_BANDS_6G (1 << NAN_BAND_ID_6G)
+/* NAN Supported Band ID bitmap, Table 72 in NAN R4 spec,
+ * bitmap of supported bands in the device capability attribute.
+ */
+typedef enum nan_mac_supp_band_flags {
+ NAN_MAC_SUPP_BAND_TV_WHITE_SPACES = (1u << 0u), /* bit0 */
+ NAN_MAC_SUPP_BAND_SUB_1GHZ = (1u << 1u),
+ NAN_MAC_SUPP_BAND_2G = (1u << 2u),
+ NAN_MAC_SUPP_BAND_3G = (1u << 3u),
+ NAN_MAC_SUPP_BAND_5G = (1u << 4u),
+ NAN_MAC_SUPP_BAND_60G = (1u << 5u),
+ NAN_MAC_SUPP_BAND_45G = (1u << 6u),
+ NAN_MAC_SUPP_BAND_6G = (1u << 7u) /* bit7 */
+} nan_mac_supp_band_flags_e;
/*
* Unaligned schedule attribute section 10.7.19.6 spec. ver r15
*/
@@ -1084,6 +1175,14 @@
#define NAN_MGMT_FRM_SUBTYPE_SCHED_CONF 12
/* Schedule Update */
#define NAN_MGMT_FRM_SUBTYPE_SCHED_UPD 13
+#ifdef NAN_REKEY
+/* Rekey Trigger frame */
+#define NAN_MGMT_FRM_SUBTYPE_REKEY_TRIGGER 14
+/* Group key request frame */
+#define NAN_MGMT_FRM_SUBTYPE_GRP_REKEY_REQ 15
+/* Group key response frame */
+#define NAN_MGMT_FRM_SUBTYPE_GRP_REKEY_RESP 16
+#endif /* NAN_REKEY */
/* Vendor specific NAN OOB AF subtype */
#define NAN_MGMT_FRM_SUBTYPE_NAN_OOB_AF 0xDD
@@ -1117,12 +1216,27 @@
/* NDP control bitmap defines */
#define NAN_NDP_CTRL_CONFIRM_REQUIRED 0x01
+#ifdef NAN_REKEY
+/* 0 = NDP setup, 1 = rekey handshake */
+#define NAN_NDP_CTRL_NDP_REKEY 0x02
+#endif /* NAN_REKEY */
#define NAN_NDP_CTRL_SECURTIY_PRESENT 0x04
#define NAN_NDP_CTRL_PUB_ID_PRESENT 0x08
#define NAN_NDP_CTRL_RESP_NDI_PRESENT 0x10
#define NAN_NDP_CTRL_SPEC_INFO_PRESENT 0x20
#define NAN_NDP_CTRL_RESERVED 0xA0
+#if defined(WL_NAN_GAF_PROTECT) || defined(NAN_GTK)
+/*
+ * NDPE control bitmap defines
+ * currently NDP & NDPE share same control bitmap before b5
+ * GTK/IGTK Required b5
+ * 0: GTK/IGTK protection is not required
+ * 1: GTK/IGTK protection is required
+ */
+#define NAN_NDPE_CTRL_GTK_REQUIRED 0x20
+#endif /* WL_NAN_GAF_PROTECT || NAN_GTK */
+
/* Used for both NDP Attribute and NDPE Attribute, since the structures are identical */
typedef BWL_PRE_PACKED_STRUCT struct wifi_nan_ndp_attr_s {
uint8 id; /* NDP: 0x10, NDPE: 0x29 */
@@ -1142,6 +1256,11 @@
#define NAN_NDP_TYPE_CONFIRM 0x2
#define NAN_NDP_TYPE_SECURITY 0x3
#define NAN_NDP_TYPE_TERMINATE 0x4
+#ifdef NAN_REKEY
+#define NAN_NDP_TYPE_REKEY 0x5
+#define NAN_NDP_TYPE_GRP_REKEY_REQ 0x6
+#define NAN_NDP_TYPE_GRP_REKEY_RESP 0x7
+#endif /* NAN_REKEY */
#define NAN_NDP_REQUEST(_ndp) (((_ndp)->type_status & NAN_NDP_TYPE_MASK) == NAN_NDP_TYPE_REQUEST)
#define NAN_NDP_RESPONSE(_ndp) (((_ndp)->type_status & NAN_NDP_TYPE_MASK) == NAN_NDP_TYPE_RESPONSE)
#define NAN_NDP_CONFIRM(_ndp) (((_ndp)->type_status & NAN_NDP_TYPE_MASK) == NAN_NDP_TYPE_CONFIRM)
@@ -1149,6 +1268,14 @@
NAN_NDP_TYPE_SECURITY)
#define NAN_NDP_TERMINATE(_ndp) (((_ndp)->type_status & NAN_NDP_TYPE_MASK) == \
NAN_NDP_TYPE_TERMINATE)
+#ifdef NAN_REKEY
+#define NAN_NDP_REKEY(_ndp) (((_ndp)->type_status & NAN_NDP_TYPE_MASK) == \
+ NAN_NDP_TYPE_REKEY)
+#define NAN_NDP_GRP_REKEY_REQ(_ndp) (((_ndp)->type_status & NAN_NDP_TYPE_MASK) == \
+ NAN_NDP_TYPE_GRP_REKEY_REQ)
+#define NAN_NDP_GRP_REKEY_RESP(_ndp) (((_ndp)->type_status & NAN_NDP_TYPE_MASK) == \
+ NAN_NDP_TYPE_GRP_REKEY_RESP)
+#endif /* NAN_REKEY */
#define NAN_NDP_STATUS_SHIFT 4
#define NAN_NDP_STATUS_MASK 0xF0
#define NAN_NDP_STATUS_CONT (0 << NAN_NDP_STATUS_SHIFT)
@@ -1306,6 +1433,9 @@
#define NAN_SDE_CF_RANGING_REQUIRED (1 << 7)
#define NAN_SDE_CF_RANGE_PRESENT (1 << 8)
#define NAN_SDE_CF_SVC_UPD_IND_PRESENT (1 << 9)
+#if defined(WL_NAN_GAF_PROTECT) || defined(NAN_GTK)
+#define NAN_SDE_CF_GTK_REQUIRED (1u << 10u)
+#endif /* WL_NAN_GAF_PROTECT || NAN_GTK */
/* Using Reserved Bits as per Spec */
#define NAN_SDE_CF_LIFE_CNT_PUB_RX (1 << 15)
#define NAN_SDE_FSD_REQUIRED(_sde) ((_sde)->control & NAN_SDE_CF_FSD_REQUIRED)
@@ -1343,6 +1473,46 @@
#define NAN_SEC_CIPHER_SUITE_CAP_REPLAY_4 0u
#define NAN_SEC_CIPHER_SUITE_CAP_REPLAY_16 (1u << 0u)
+#if defined(WL_NAN_GAF_PROTECT) || defined(NAN_GTK)
+/* Defines for GTK, IGTK and BIGTK */
+/*
+ * Bit 1 and 2:
+ * 00: GTKSA, IGTKSA, BIGTKSA are not supported;
+ * 01: GTKSA and IGTKSA are supported, and BIGTKSA is not supported;
+ * 10: GTKSA, IGTKSA, and BIGTKSA are supported;
+ * 11: Reserved;
+ */
+#define NAN_SEC_CIPHER_SUITE_CAP_DIS_GTK_IGTK_BIGTK (0 << 1)
+#define NAN_SEC_CIPHER_SUITE_CAP_DIS_BIGTK (1 << 1)
+#define NAN_SEC_CIPHER_SUITE_CAP_ENAB_GTK_IGTK_BIGTK (1 << 2)
+
+/*
+ * Bit 3 is 0 for 4 GTKSA replay counters, if GTKSA is supported
+ * Bit 3 is 1 for 16 GTKSA replay counters, if GTKSA is supported
+ */
+#define NAN_SEC_CIPHER_SUITE_CAP_GTK_REPLAY_4 (0 << 4)
+#define NAN_SEC_CIPHER_SUITE_CAP_GTK_REPLAY_16 (1 << 4)
+
+/*
+ * Bit 4 is 0: BIP-CMAC-128 is selected for transmit, if IGTKSA or BIGTKSA is supported
+ * Bit 4 is 1: BIP-GMAC-256 is selected for transmit, if IGTKSA or BIGTKSA is supported
+ */
+#define NAN_SEC_CIPHER_SUITE_CAP_BIP_CMAC_128 (0)
+#define NAN_SEC_CIPHER_SUITE_CAP_BIP_GMAC_256 (1 << 5)
+
+#define NAN_SEC_BIP_ENABLED(cap) ((cap) & \
+ (NAN_SEC_CIPHER_SUITE_CAP_ENAB_GTK_IGTK_BIGTK | \
+ NAN_SEC_CIPHER_SUITE_CAP_DIS_BIGTK))
+
+#define NAN_SEC_BIP_CAP_TO_CIPER(cap) \
+ (((cap) & NAN_SEC_CIPHER_SUITE_CAP_BIP_GMAC_256) ?\
+ CRYPTO_ALGO_BIP_GMAC256 : CRYPTO_ALGO_BIP)
+#define NAN_SEC_IGTK_ENABLED(cap) NAN_SEC_BIP_ENABLED(cap)
+
+#define NAN_SEC_BIGTK_ENABLED(cap) ((cap) & \
+ (NAN_SEC_CIPHER_SUITE_CAP_ENAB_GTK_IGTK_BIGTK))
+#endif /* WL_NAN_GAF_PROTECT || NAN_GTK */
+
/* enum security algo.
*/
enum nan_sec_csid {
diff --git a/include/osl.h b/include/osl.h
index feaff22..af46e73 100644
--- a/include/osl.h
+++ b/include/osl.h
@@ -1,7 +1,7 @@
/*
* OS Abstraction Layer
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -93,6 +93,25 @@
#define OR_REG(osh, r, v) W_REG(osh, (r), R_REG(osh, r) | (v))
#endif /* !OR_REG */
+/**
+ * @brief API to either read or read, modify, write, read a 32bit register.
+ * Modify the value in a register. If the mask or val are not zero, this will bitwise-or val into
+ * the register at the address after masking the value read from the register with the provided
+ * mask. This process is sometimes referred to as Read-Modify-Write (RMW). This replaces the
+ * functionality provided by si_corereg for the dongle. When mask and val are zero, this macro
+ * behaves the same as R_REG.
+ * @param addr Backplane address to perform an operation on as a uint32.
+ * @param mask Bitmask for the value that will be written.
+ * @param val Value to and into the register at the address.
+ * @return The value in the register at the provided address after the optional write.
+ */
+#define RMWR_REG(addr, mask, val) ({ \
+ if ((bool)(mask) || (bool)(val)) { \
+ SET_REG(NULL, (uint32 *)(addr), (mask), (val)); \
+ } \
+ R_REG(NULL, (uint32 *)(addr)); \
+})
+
#if !defined(OSL_SYSUPTIME)
#define OSL_SYSUPTIME() (0)
#define OSL_SYSUPTIME_NOT_DEFINED 1
@@ -161,29 +180,9 @@
#endif
#ifndef OSL_OBFUSCATE_BUF
-#if defined(_RTE_)
-#define OSL_OBFUSCATE_BUF(x) osl_obfuscate_ptr(x)
-#else
#define OSL_OBFUSCATE_BUF(x) (x)
-#endif /* _RTE_ */
#endif /* OSL_OBFUSCATE_BUF */
-#ifndef OSL_GET_HCAPISTIMESYNC
-#if defined(_RTE_)
-#define OSL_GET_HCAPISTIMESYNC() osl_get_hcapistimesync()
-#else
-#define OSL_GET_HCAPISTIMESYNC()
-#endif /* _RTE_ */
-#endif /* OSL_GET_HCAPISTIMESYNC */
-
-#ifndef OSL_GET_HCAPISPKTTXS
-#if defined(_RTE_)
-#define OSL_GET_HCAPISPKTTXS() osl_get_hcapispkttxs()
-#else
-#define OSL_GET_HCAPISPKTTXS()
-#endif /* _RTE_ */
-#endif /* OSL_GET_HCAPISPKTTXS */
-
#if !defined(PKTC_DONGLE)
#define PKTCGETATTR(skb) (0)
#define PKTCSETATTR(skb, f, p, b) BCM_REFERENCE(skb)
@@ -236,7 +235,6 @@
#define PKTSETPROFILEIDX(p, idx) BCM_REFERENCE(idx)
#endif
-#ifndef _RTE_
/* Lbuf with fraglist */
#ifndef PKTFRAGPKTID
#define PKTFRAGPKTID(osh, lb) (0)
@@ -411,7 +409,6 @@
#ifndef PKTSETUDR
#define PKTRESETUDR(osh, lb) BCM_REFERENCE(osh)
#endif
-#endif /* _RTE_ */
#if !defined(__linux__)
#define PKTLIST_INIT(x) BCM_REFERENCE(x)
@@ -437,14 +434,6 @@
#define MALLOC_RA(osh, size, callsite) MALLOCZ(osh, size)
#endif /* !MALLOC_RA */
-#ifndef MALLOC_PERSIST_ATTACH
- #define MALLOC_PERSIST_ATTACH MALLOC
-#endif /* !MALLOC_PERSIST_ATTACH */
-
-#ifndef MALLOCZ_PERSIST_ATTACH
- #define MALLOCZ_PERSIST_ATTACH MALLOCZ
-#endif /* !MALLOCZ_PERSIST_ATTACH */
-
#ifndef MALLOCZ_NOPERSIST
#define MALLOCZ_NOPERSIST MALLOCZ
#endif /* !MALLOCZ_NOPERSIST */
@@ -493,4 +482,33 @@
#define PKTSETQCALLER(lb, queue, caller_addr)
#define PKTSETQCALLER_LIST(head, npkts, queue, caller_addr)
#endif /* DBG_PKTLEAK */
+
+/* Memory breakup capturing macros */
+#ifdef BCMDBG_MEM_BREAKUP
+#define MB_START(var) \
+ uint mb_memuse_before_##var = MALLOCED(NULL)
+
+#define MB_END(var, fmt, ...) \
+ do { \
+ uint mb_memuse_##var = MALLOCED(NULL) - mb_memuse_before_##var; \
+ if (mb_memuse_##var) { \
+ printf("[MB] " fmt, ##__VA_ARGS__); \
+ printf(" %d\n", mb_memuse_##var); \
+ } \
+ } while (0)
+#else
+#define MB_START(var)
+#define MB_END(var, fmt, ...)
+#endif /* BCMDBG_MEM_BREAKUP */
+
+/* ASSERT NULL check should not be enabled for ROM build */
+#if defined(BCMROMBUILD) && defined(ENABLE_ASSERT_NULL)
+#error "Do not enable ENABLE_ASSERT_NULL for ROM builds..."
+#endif
+
+#ifdef ENABLE_ASSERT_NULL
+#define ASSERT_NULL(expr) ASSERT(expr)
+#else
+#define ASSERT_NULL(expr) // do nothing
+#endif /* ENABLE_ASSERT_NULL */
#endif /* _osl_h_ */
diff --git a/include/osl_decl.h b/include/osl_decl.h
index 16adf43..898fb0f 100644
--- a/include/osl_decl.h
+++ b/include/osl_decl.h
@@ -1,7 +1,7 @@
/*
* osl forward declarations
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/osl_ext.h b/include/osl_ext.h
index 6a04c2b..33084e3 100644
--- a/include/osl_ext.h
+++ b/include/osl_ext.h
@@ -2,7 +2,7 @@
* OS Abstraction Layer Extension - the APIs defined by the "extension" API
* are only supported by a subset of all operating systems.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/p2p.h b/include/p2p.h
index 7162a43..87d9057 100644
--- a/include/p2p.h
+++ b/include/p2p.h
@@ -1,7 +1,7 @@
/*
* Fundamental types and constants relating to WFA P2P (aka WiFi Direct)
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/packed_section_end.h b/include/packed_section_end.h
index a4ebd68..566b15c 100644
--- a/include/packed_section_end.h
+++ b/include/packed_section_end.h
@@ -15,7 +15,7 @@
* #include <packed_section_end.h>
*
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/packed_section_start.h b/include/packed_section_start.h
index 57a884f..1cda56d 100644
--- a/include/packed_section_start.h
+++ b/include/packed_section_start.h
@@ -15,7 +15,7 @@
* #include <packed_section_end.h>
*
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/pcicfg.h b/include/pcicfg.h
index 0266d09..54682e8 100644
--- a/include/pcicfg.h
+++ b/include/pcicfg.h
@@ -1,7 +1,7 @@
/*
* pcicfg.h: PCI configuration constants and structures.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/pcie_core.h b/include/pcie_core.h
index 299006e..d1d3cf4 100644
--- a/include/pcie_core.h
+++ b/include/pcie_core.h
@@ -1,7 +1,7 @@
/*
* BCM43XX PCIE core hardware definitions.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -1157,12 +1157,19 @@
#define DAR_SEC_STATUS(rev) OFFSETOF(sbpcieregs_t, u1.dar_64.dar_sec_stat)
#define DAR_SEC_JTAG_MASK 0x1u
+#define DAR_SEC_JTAG_SHIFT 0u
#define DAR_SEC_SBOOT_MASK 0x2u
#define DAR_SEC_SBOOT_SHIFT 1u
#define DAR_SEC_ARM_DBG_MASK 0x4u
#define DAR_SEC_ARM_DBG_SHIFT 2u
#define DAR_SEC_UNLOCK_MASK 0x8u
#define DAR_SEC_UNLOCK_SHIFT 3u
+#define DAR_SEC_ROM_PROT_MASK 0x10u
+#define DAR_SEC_ROM_PROT_SHIFT 4u
+#define DAR_SEC_NSEC_WR_MASK 0x20u
+#define DAR_SEC_NSEC_WR_SHIFT 5u
+#define DAR_SEC_NSEC_RD_MASK 0x40u
+#define DAR_SEC_NSEC_RD_SHIFT 6u
#define DAR_FIS_CTRL(rev) OFFSETOF(sbpcieregs_t, u1.dar_64.fis_ctrl)
diff --git a/include/sbchipc.h b/include/sbchipc.h
index 0b52717..6a836ae 100644
--- a/include/sbchipc.h
+++ b/include/sbchipc.h
@@ -5,7 +5,7 @@
* JTAG, 0/1/2 UARTs, clock frequency control, a watchdog interrupt timer,
* GPIO interface, extbus, and support for serial and parallel flashes.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -4162,6 +4162,7 @@
#define CR4_43752_RAM_BASE (0x170000)
#define CR4_4376_RAM_BASE (0x352000)
#define CR4_4378_RAM_BASE (0x352000)
+#define CR4_4381_RAM_BASE (0x740000)
#define CR4_4387_RAM_BASE (0x740000)
#define CR4_4385_RAM_BASE (0x740000)
#define CA7_4388_RAM_BASE (0x200000)
diff --git a/include/sbconfig.h b/include/sbconfig.h
index d8786d0..424a362 100644
--- a/include/sbconfig.h
+++ b/include/sbconfig.h
@@ -1,7 +1,7 @@
/*
* Broadcom SiliconBackplane hardware register definitions.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/sbgci.h b/include/sbgci.h
index fec5d46..55afc79 100644
--- a/include/sbgci.h
+++ b/include/sbgci.h
@@ -1,7 +1,7 @@
/*
* SiliconBackplane GCI core hardware definitions
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/sbhndarm.h b/include/sbhndarm.h
index 1c156fd..9266012 100644
--- a/include/sbhndarm.h
+++ b/include/sbhndarm.h
@@ -1,7 +1,7 @@
/*
* Broadcom SiliconBackplane ARM definitions
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/sbhnddma.h b/include/sbhnddma.h
index 8e7bca0..86422eb 100644
--- a/include/sbhnddma.h
+++ b/include/sbhnddma.h
@@ -2,7 +2,7 @@
* Generic Broadcom Home Networking Division (HND) DMA engine HW interface
* This supports the following chips: BCM42xx, 44xx, 47xx .
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/sbpcmcia.h b/include/sbpcmcia.h
index 87d6d09..297898f 100644
--- a/include/sbpcmcia.h
+++ b/include/sbpcmcia.h
@@ -1,7 +1,7 @@
/*
* BCM43XX Sonics SiliconBackplane PCMCIA core hardware definitions.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/sbsdio.h b/include/sbsdio.h
index 2e6ac10..18ba612 100644
--- a/include/sbsdio.h
+++ b/include/sbsdio.h
@@ -4,7 +4,7 @@
*
* SDIO core support 1bit, 4 bit SDIO mode as well as SPI mode.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/sbsdpcmdev.h b/include/sbsdpcmdev.h
index c2aa35b..91e0488 100644
--- a/include/sbsdpcmdev.h
+++ b/include/sbsdpcmdev.h
@@ -2,7 +2,7 @@
* Broadcom SiliconBackplane SDIO/PCMCIA hardware-specific
* device core support
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/sbsocram.h b/include/sbsocram.h
index 97eaa6f..a8802bf 100644
--- a/include/sbsocram.h
+++ b/include/sbsocram.h
@@ -1,7 +1,7 @@
/*
* BCM47XX Sonics SiliconBackplane embedded ram core
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/sbsysmem.h b/include/sbsysmem.h
index 1857fdd..dc7f8a7 100644
--- a/include/sbsysmem.h
+++ b/include/sbsysmem.h
@@ -1,7 +1,7 @@
/*
* SiliconBackplane System Memory core
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/sdio.h b/include/sdio.h
index 4bb72a9..70721f1 100644
--- a/include/sdio.h
+++ b/include/sdio.h
@@ -2,7 +2,7 @@
* SDIO spec header file
* Protocol and standard (common) device definitions
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/sdioh.h b/include/sdioh.h
index f1e8181..20200c1 100644
--- a/include/sdioh.h
+++ b/include/sdioh.h
@@ -2,7 +2,7 @@
* SDIO Host Controller Spec header file
* Register map and definitions for the Standard Host Controller
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/sdiovar.h b/include/sdiovar.h
index 90cfbc1..7d2a761 100644
--- a/include/sdiovar.h
+++ b/include/sdiovar.h
@@ -2,7 +2,7 @@
* Structure used by apps whose drivers access SDIO drivers.
* Pulled out separately so dhdu and wlu can both use it.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/sdspi.h b/include/sdspi.h
index 337b06e..1a06fe5 100644
--- a/include/sdspi.h
+++ b/include/sdspi.h
@@ -1,7 +1,7 @@
/*
* SD-SPI Protocol Standard
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/siutils.h b/include/siutils.h
index b1c9ef9..097fc59 100644
--- a/include/siutils.h
+++ b/include/siutils.h
@@ -2,7 +2,7 @@
* Misc utility routines for accessing the SOC Interconnects
* of Broadcom HNBU chips.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -960,8 +960,8 @@
* ARM, TCM, Main, Aux
* Host needs to power up
*/
-#define MULTIBP_CAP(sih) (BCM4378_CHIP(sih->chip) || \
- BCM4381_CHIP(sih->chip) || BCM4382_CHIP(sih->chip) || \
+#define MULTIBP_CAP(sih) (BCM4378_CHIP(sih->chip) || BCM4381_CHIP(sih->chip) || \
+ BCM43852_CHIP(sih->chip) || BCM4382_CHIP(sih->chip) || \
BCM4387_CHIP(sih->chip) || BCM4388_CHIP(sih->chip) || \
BCM4389_CHIP(sih->chip) || BCM4385_CHIP(sih->chip) || \
BCM4376_CHIP(sih->chip) || BCM4397_CHIP(sih->chip))
diff --git a/include/spid.h b/include/spid.h
index 63b76ce..bc635f4 100644
--- a/include/spid.h
+++ b/include/spid.h
@@ -1,7 +1,7 @@
/*
* SPI device spec header file
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/trxhdr.h b/include/trxhdr.h
index 7c7d365..f3599ca 100644
--- a/include/trxhdr.h
+++ b/include/trxhdr.h
@@ -1,7 +1,7 @@
/*
* TRX image file header format.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/typedefs.h b/include/typedefs.h
index 24b50fe..f071c73 100644
--- a/include/typedefs.h
+++ b/include/typedefs.h
@@ -1,5 +1,5 @@
/*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/vlan.h b/include/vlan.h
index e4c33e9..e22e190 100644
--- a/include/vlan.h
+++ b/include/vlan.h
@@ -1,7 +1,7 @@
/*
* 802.1Q VLAN protocol definitions
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/wldev_common.h b/include/wldev_common.h
index 2d60198..becb88a 100644
--- a/include/wldev_common.h
+++ b/include/wldev_common.h
@@ -1,7 +1,7 @@
/*
* Common function shared by Linux WEXT, cfg80211 and p2p drivers
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/wlfc_proto.h b/include/wlfc_proto.h
index f010718..f88afce 100644
--- a/include/wlfc_proto.h
+++ b/include/wlfc_proto.h
@@ -1,5 +1,5 @@
/*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -385,6 +385,8 @@
#define WLFC_CTL_PKTFLAG_DROPPED 7
/* Firmware free this packet */
#define WLFC_CTL_PKTFLAG_MKTFREE 8
+/* Firmware drop this packet due to AMPDU cleanup */
+#define WLFC_CTL_PKTFLAG_AMPDU_CLEANUP 8
/* Firmware dropped the frame after suppress retries reached max */
#define WLFC_CTL_PKTFLAG_MAX_SUP_RETR 9
@@ -475,6 +477,7 @@
#define FLOW_RING_GET_BUFFERED_TIME 15u
#define FLOW_RING_HP2P_TXQ_STRT 16u
#define FLOW_RING_HP2P_TXQ_STOP 17u
+#define FLOW_RING_GET_TXPARAMS 18u
/* bit 7, indicating if is TID(1) or AC(0) mapped info in tid field) */
#define PCIEDEV_IS_AC_TID_MAP_MASK 0x80
diff --git a/include/wlioctl.h b/include/wlioctl.h
index ab6108f..7c41c81 100644
--- a/include/wlioctl.h
+++ b/include/wlioctl.h
@@ -6,7 +6,7 @@
*
* Definitions subject to change without notice.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -56,7 +56,8 @@
#include <bcmerror.h>
#endif /* BCMUTILS_ERR_CODES */
#include <bcmtlv.h>
-#ifdef USE_NEW_RSPEC_DEFS
+
+#ifndef USE_LEGACY_RSPEC_DEFS
#include <bcmwifi_rspec.h>
#endif
@@ -95,7 +96,7 @@
#define INTF_NAME_SIZ 16
#endif
-#define WL_ASSOC_START_EVT_DATA_VERSION 1
+#define WL_ASSOC_START_EVT_DATA_VERSION_1 1
typedef struct assoc_event_data {
uint32 version;
@@ -112,7 +113,7 @@
} rem_ioctl_t;
#define REMOTE_SIZE sizeof(rem_ioctl_t)
-#define BCM_IOV_XTLV_VERSION 0
+#define BCM_IOV_XTLV_VERSION_0 0
#define MAX_NUM_D11CORES 2
@@ -157,12 +158,12 @@
#define ACTION_FRAME_SIZE 1800
#define WL_RAND_GAS_MAC (0x01 << 0u)
-struct wl_action_frame {
+typedef struct wl_action_frame_v1 {
struct ether_addr da;
uint16 len;
uint32 packetId;
uint8 data[ACTION_FRAME_SIZE];
-};
+} wl_action_frame_v1_t;
typedef struct wl_action_frame_v2 {
uint16 version;
@@ -177,29 +178,22 @@
uint8 data[];
} wl_action_frame_v2_t;
-#ifndef WL_AF_PARAMS_VERSION_SUPPORT
-/* actframe params LEGACY structure. DONOT extend this structure unless
- * there is a clear requirement. Use the versioned struct v2 onwards.
- */
-typedef struct wl_action_frame wl_action_frame_t;
-typedef struct wl_af_params wl_af_params_t;
-#define WL_WIFI_ACTION_FRAME_SIZE sizeof(struct wl_action_frame)
-#define WL_WIFI_AF_PARAMS_SIZE sizeof(struct wl_af_params)
-#endif /* WL_AF_PARAMS_VERSION_SUPPORT */
-
typedef struct ssid_info
{
uint8 ssid_len; /**< the length of SSID */
uint8 ssid[32]; /**< SSID string */
} ssid_info_t;
-struct wl_af_params {
+typedef struct wl_af_params_v1 {
uint32 channel;
int32 dwell_time;
struct ether_addr BSSID;
uint8 PAD[2];
- struct wl_action_frame action_frame;
-};
+ wl_action_frame_v1_t action_frame;
+} wl_af_params_v1_t;
+
+#define WL_WIFI_ACTION_FRAME_SIZE_V1 sizeof(wl_action_frame_v1_t)
+#define WL_WIFI_AF_PARAMS_SIZE_V1 sizeof(wl_af_params_v1_t)
typedef struct wl_af_params_v2 {
uint16 version;
@@ -267,7 +261,7 @@
#define WL_OBSS_DYN_BWSW_FLAG_TXOP_PERIOD (0x40)
/* OBSS IOVAR Version information */
-#define WL_PROT_OBSS_CONFIG_PARAMS_VERSION 1
+#define WL_PROT_OBSS_CONFIG_PARAMS_VERSION_1 1
#include <packed_section_start.h>
typedef BWL_PRE_PACKED_STRUCT struct {
@@ -350,7 +344,8 @@
* Cf PR53622
*/
-#define WL_BSS_INFO_VERSION 109 /**< current version of wl_bss_info struct */
+#define WL_BSS_INFO_VER_109 109
+#define WL_BSS_INFO_VER_114 114
/**
* BSS info structure
@@ -561,12 +556,31 @@
uint8 pad1[20];
} wl_bss_info_v112_t;
+/* EHT-MCS Map for the current operating channel width.
+ *
+ * The map consists of two parts:
+ *
+ * 1. EHT-MCS Map subfield defined in IEEE P802.11be D1.2 EHT-MCS Map (20MHz-Only Non-AP STA)
+ * for mcs 0 - 13
+ * 2. EHT-MCS Bitmap defined in this file for mcs 14 & 15 (See WL_EHT_MCS_BMP_MCS_x_POS)
+ */
+typedef struct wl_eht_mcsmap {
+ uint8 mcs_0_13[4]; /* mcs 0 - 13 mcsmap */
+ uint8 mcs_14_15[1]; /* mcs 14 & 15 bitmap */
+} wl_eht_mcsmap_t;
+
+/* EHT mcs 14 & 15 bit positions */
+#define WL_EHT_MCS_BMP_MCS_14_POS 0u
+#define WL_EHT_MCS_BMP_MCS_15_POS 1u
+/* EHT mcs 14 & 15 field width */
+#define WL_EHT_MCS_BMP_MCS_SZ 1u /* 1 bit per mcs */
+
/**
* BSS info structure
* Applications MUST CHECK ie_offset field and length field to access IEs and
* next bss_info structure in a vector (in wl_scan_results_t)
*/
-typedef struct wl_bss_info_v113 {
+typedef struct wl_bss_info_v114 {
uint32 version; /**< version field */
uint32 length; /**< byte length of data in this record,
* starting at version and including IEs
@@ -600,10 +614,10 @@
uint8 flags; /**< flags */
uint8 vht_cap; /**< BSS is vht capable */
uint8 flags2; /**< extended flags */
- uint8 RSVD2;
+ uint8 RSVD2[1];
uint8 basic_mcs[MCSSET_LEN]; /**< 802.11N BSS required MCS set */
uint16 ie_offset; /**< offset at which IEs start, from beginning */
- uint16 freespace2; /* making implicit padding explicit */
+ uint8 RSVD3[2]; /* making implicit padding explicit */
uint32 ie_length; /**< byte length of Information Elements */
int16 SNR; /**< average SNR of during frame reception */
uint16 vht_mcsmap; /**< STA's Associated vhtmcsmap */
@@ -614,18 +628,10 @@
uint32 he_txmcsmap; /**< HE tx mcs map (802.11ax) */
uint32 timestamp[2]; /* Beacon Timestamp for FAKEAP req */
uint8 eht_cap; /* BSS is EHT capable */
- uint8 RSVD3[3];
- uint32 eht_mcsmap_sta; /* EHT-MCS Map - use 20Mhz only STA encoding,
- * for the STA in associated state
- */
- uint32 eht_mcsmap; /* EHT-MCS Map - use 20Mhz only STA encoding,
- * for the BSS operating channel width
- */
-} wl_bss_info_v113_t;
-
-#ifndef WL_BSS_INFO_TYPEDEF_HAS_ALIAS
-typedef wl_bss_info_v109_t wl_bss_info_t;
-#endif
+ uint8 RSVD4[1];
+ wl_eht_mcsmap_t eht_mcsmap_sta; /* EHT-MCS Map for the STA in associated state */
+ wl_eht_mcsmap_t eht_mcsmap; /* EHT-MCS Map for the BSS operating chan width */
+} wl_bss_info_v114_t;
#define WL_GSCAN_FULL_RESULT_VERSION 2 /* current version of wl_gscan_result_t struct */
@@ -643,11 +649,6 @@
/* and variable length Information Elements to follow */
} wl_gscan_bss_info_v3_t;
-#ifndef WL_BSS_INFO_TYPEDEF_HAS_ALIAS
-typedef wl_gscan_bss_info_v2_t wl_gscan_bss_info_t;
-#define WL_GSCAN_INFO_FIXED_FIELD_SIZE (sizeof(wl_gscan_bss_info_t) - sizeof(wl_bss_info_t))
-#endif
-
typedef struct wl_bsscfg {
uint32 bsscfg_idx;
uint32 wsec;
@@ -719,9 +720,10 @@
#define DLOAD_FLAG_VER_MASK 0xf000 /**< Downloader version mask */
#define DLOAD_FLAG_VER_SHIFT 12 /**< Downloader version shift */
-#define DL_CRC_NOT_INUSE 0x0001
-#define DL_BEGIN 0x0002
-#define DL_END 0x0004
+#define DL_CRC_NOT_INUSE 0x0001u
+#define DL_BEGIN 0x0002u /* First BLOB fragment */
+#define DL_END 0x0004u /* Last BLOB fragment */
+#define DL_FORCE 0x0008u /* Force download */
/* Flags for Major/Minor/Date number shift and mask */
#define EPI_VER_SHIFT 16
@@ -768,6 +770,50 @@
};
typedef struct wl_clm_dload_info wl_clm_dload_info_t;
+/* Max size for MSF fw version field */
+#define WL_MSFVER_MAX_FW_VERSION_LEN (64u)
+
+/* Indication for an undefined MSF calibration content version */
+#define WL_MSFVER_UNDEFINED (0xFFFFFFFFu)
+
+typedef struct wl_msf_ver_s {
+ char fw_ver[WL_MSFVER_MAX_FW_VERSION_LEN]; /* FW Version */
+ uint32 main_rx_ver; /* Main core Rx MSF content version */
+ uint32 main_tx_ver; /* Main core Tx MSF content version */
+ uint32 aux_rx_ver; /* Aux core Rx MSF content version */
+ uint32 aux_tx_ver; /* Aux core Tx MSF content version */
+ uint32 scan_rx_ver; /* Scan core Rx MSF content version */
+ uint8 main_rx_is_generic; /* Flag - Main core Rx MSF content is generic */
+ uint8 main_tx_is_generic; /* Flag - Main core Tx MSF content is generic */
+ uint8 aux_rx_is_generic; /* Flag - Aux core Rx MSF content is generic */
+ uint8 aux_tx_is_generic; /* Flag - Aux core Tx MSF content is generic */
+ uint8 scan_rx_is_generic; /* Flag - Scan core Rx MSF content is generic */
+ uint8 PAD[3];
+} wl_msf_ver_t;
+
+/* CALLOAD IOVAR - uses bcm iov sub-command framework */
+#define WL_CAL_IOV_MAJOR_VER_1 1
+#define WL_CAL_IOV_MINOR_VER_1 1
+#define WL_CAL_IOV_MAJOR_VER_SHIFT 8
+#define WL_CAL_IOV_VERSION_1_1 ((WL_CAL_IOV_MAJOR_VER_1 << WL_CAL_IOV_MAJOR_VER_SHIFT) | \
+ WL_CAL_IOV_MINOR_VER_1)
+
+/* CALLOAD subcommand ids */
+enum wl_cal_subcmd_ids {
+ WL_CAL_SUBCMD_VERSION = 0u, /* Get cal iovar version */
+ WL_CAL_SUBCMD_LOAD = 1u, /* FW MSF calibration content version */
+ WL_CAL_SUBCMD_FW_VER = 2u, /* FW MSF calibration content version */
+ WL_CAL_SUBCMD_STATUS = 3u, /* MSF load status */
+ WL_CAL_SUBCMD_LAST
+};
+
+typedef struct wl_cal_status_ver_s {
+ uint32 status; /* calload status */
+ uint32 flags; /* Copy of calload flags - Mainly DL_FORCE */
+ wl_msf_ver_t fw_ver; /* FW MSF content versions for all cores */
+ wl_msf_ver_t msf_ver; /* Downloaded MSF content versions for all cores */
+} wl_cal_status_ver_t;
+
typedef struct wlc_ssid {
uint32 SSID_len;
uint8 SSID[DOT11_MAX_SSID_LEN];
@@ -821,11 +867,10 @@
chan_scandata_t channel_list[BCM_FLEX_ARRAY]; /**< list of chandata structs */
} wl_extdscan_params_t;
-#define WL_EXTDSCAN_PARAMS_FIXED_SIZE (sizeof(wl_extdscan_params_t) - sizeof(chan_scandata_t))
-
+#define WL_EXTDSCAN_PARAMS_FIXED_SIZE (OFFSETOF(wl_extdscan_params_t, channel_list))
#define WL_SCAN_PARAMS_SSID_MAX 10
-struct wl_scan_params {
+typedef struct wl_scan_params_v1 {
wlc_ssid_t ssid; /**< default: {0, ""} */
struct ether_addr bssid; /**< default: bcast */
int8 bss_type; /**< default: any,
@@ -857,7 +902,12 @@
* the fixed portion is ignored
*/
uint16 channel_list[BCM_FLEX_ARRAY];
-};
+} wl_scan_params_v1_t;
+
+/** size of wl_scan_params_v1 not including variable length array */
+#define WL_SCAN_PARAMS_V1_FIXED_SIZE (OFFSETOF(wl_scan_params_v1_t, channel_list))
+#define WL_MAX_ROAMSCAN_V1_DATSZ \
+ (WL_SCAN_PARAMS_V1_FIXED_SIZE + (WL_NUMCHANNELS * sizeof(uint16)))
/* changes in wl_scan_params_v2 as comapred to wl_scan_params (v1)
* unit8 scantype to uint32
@@ -909,8 +959,6 @@
/** size of wl_scan_params not including variable length array */
#define WL_SCAN_PARAMS_V2_FIXED_SIZE (OFFSETOF(wl_scan_params_v2_t, channel_list))
-#define WL_MAX_ROAMSCAN_DATSZ \
- (WL_SCAN_PARAMS_FIXED_SIZE + (WL_NUMCHANNELS * sizeof(uint16)))
#define WL_MAX_ROAMSCAN_V2_DATSZ \
(WL_SCAN_PARAMS_V2_FIXED_SIZE + (WL_NUMCHANNELS * sizeof(uint16)))
@@ -969,16 +1017,16 @@
#define WL_MAX_ROAMSCAN_V3_DATSZ \
(WL_SCAN_PARAMS_V3_FIXED_SIZE + (WL_NUMCHANNELS * sizeof(uint16)))
-#define ISCAN_REQ_VERSION 1
+#define ISCAN_REQ_VERSION_V1 1
#define ISCAN_REQ_VERSION_V2 2
/** incremental scan struct */
-struct wl_iscan_params {
+typedef struct wl_iscan_params_v1 {
uint32 version;
uint16 action;
uint16 scan_duration;
- struct wl_scan_params params;
-};
+ struct wl_scan_params_v1 params;
+} wl_iscan_params_v1_t;
/** incremental scan struct */
typedef struct wl_iscan_params_v2 {
@@ -1009,6 +1057,7 @@
uint32 count;
wl_bss_info_v109_t bss_info[BCM_FLEX_ARRAY];
} wl_scan_results_v109_t;
+#define WL_SCAN_RESULTS_V109_FIXED_SIZE (OFFSETOF(wl_scan_results_v109_t, bss_info))
typedef struct wl_scan_results_v2 {
uint32 buflen;
@@ -1016,12 +1065,7 @@
uint32 count;
uint8 bss_info[]; /* var length wl_bss_info_X structures */
} wl_scan_results_v2_t;
-
-#ifndef WL_BSS_INFO_TYPEDEF_HAS_ALIAS
-typedef wl_scan_results_v109_t wl_scan_results_t;
-/** size of wl_scan_results not including variable length array */
-#define WL_SCAN_RESULTS_FIXED_SIZE (sizeof(wl_scan_results_t) - sizeof(wl_bss_info_t))
-#endif
+#define WL_SCAN_RESULTS_V2_FIXED_SIZE (OFFSETOF(wl_scan_results_v2_t, bss_info))
#if defined(SIMPLE_ISCAN)
/** the buf length can be WLC_IOCTL_MAXLEN (8K) to reduce iteration */
@@ -1031,17 +1075,16 @@
int8 iscan_buf[WLC_IW_ISCAN_MAXLEN];
} iscan_buf_t;
#endif /* SIMPLE_ISCAN */
-#define ESCAN_REQ_VERSION 1
+#define ESCAN_REQ_VERSION_V1 1
#define ESCAN_REQ_VERSION_V2 2
#define ESCAN_REQ_VERSION_V3 3
-/** event scan reduces amount of SOC memory needed to store scan results */
-struct wl_escan_params {
+typedef struct wl_escan_params_v1 {
uint32 version;
uint16 action;
uint16 sync_id;
- struct wl_scan_params params;
-};
+ struct wl_scan_params_v1 params;
+} wl_escan_params_v1_t;
typedef struct wl_escan_params_v2 {
uint32 version;
@@ -1057,34 +1100,9 @@
wl_scan_params_v3_t params;
} wl_escan_params_v3_t;
-#define WL_ESCAN_PARAMS_FIXED_SIZE (OFFSETOF(wl_escan_params_t, params) + sizeof(wlc_ssid_t))
+#define WL_ESCAN_PARAMS_V1_FIXED_SIZE (OFFSETOF(wl_escan_params_v1_t, params) + sizeof(wlc_ssid_t))
#define WL_ESCAN_PARAMS_V2_FIXED_SIZE (OFFSETOF(wl_escan_params_v2_t, params) + sizeof(wlc_ssid_t))
#define WL_ESCAN_PARAMS_V3_FIXED_SIZE (OFFSETOF(wl_escan_params_v3_t, params) + sizeof(wlc_ssid_t))
-/* New scan version is defined then change old version of scan to
- * wl_scan_params_v1_t and new one to wl_scan_params_t
- */
-#if defined(WL_SCAN_PARAMS_V3)
-typedef struct wl_scan_params wl_scan_params_v1_t;
-typedef struct wl_escan_params wl_escan_params_v1_t;
-typedef struct wl_iscan_params wl_iscan_params_v1_t;
-typedef struct wl_scan_params_v3 wl_scan_params_t;
-typedef struct wl_escan_params_v3 wl_escan_params_t;
-typedef struct wl_iscan_params_v3 wl_iscan_params_t;
-#define WL_SCAN_PARAMS_FIXED_SIZE (OFFSETOF(wl_scan_params_t, channel_list))
-#elif defined(WL_SCAN_PARAMS_V2)
-typedef struct wl_scan_params wl_scan_params_v1_t;
-typedef struct wl_escan_params wl_escan_params_v1_t;
-typedef struct wl_iscan_params wl_iscan_params_v1_t;
-typedef struct wl_scan_params_v2 wl_scan_params_t;
-typedef struct wl_escan_params_v2 wl_escan_params_t;
-typedef struct wl_iscan_params_v2 wl_iscan_params_t;
-#define WL_SCAN_PARAMS_FIXED_SIZE (OFFSETOF(wl_scan_params_t, channel_list))
-#else
-typedef struct wl_scan_params wl_scan_params_t;
-typedef struct wl_escan_params wl_escan_params_t;
-typedef struct wl_iscan_params wl_iscan_params_t;
-#define WL_SCAN_PARAMS_FIXED_SIZE 64
-#endif /* WL_SCAN_PARAMS_V3 */
/** event scan reduces amount of SOC memory needed to store scan results */
typedef struct wl_escan_result_v109 {
@@ -1094,6 +1112,7 @@
uint16 bss_count;
wl_bss_info_v109_t bss_info[BCM_FLEX_ARRAY];
} wl_escan_result_v109_t;
+#define WL_ESCAN_RESULTS_V109_FIXED_SIZE (OFFSETOF(wl_escan_result_v109_t, bss_info))
/** event scan reduces amount of SOC memory needed to store scan results */
typedef struct wl_escan_result_v2 {
@@ -1103,11 +1122,7 @@
uint16 bss_count;
uint8 bss_info[]; /* var length wl_bss_info_X structures */
} wl_escan_result_v2_t;
-
-#ifndef WL_BSS_INFO_TYPEDEF_HAS_ALIAS
-typedef wl_escan_result_v109_t wl_escan_result_t;
-#define WL_ESCAN_RESULTS_FIXED_SIZE (sizeof(wl_escan_result_t) - sizeof(wl_bss_info_t))
-#endif
+#define WL_ESCAN_RESULTS_V2_FIXED_SIZE (OFFSETOF(wl_escan_result_v2_t, bss_info))
typedef struct wl_gscan_result_v2 {
uint32 buflen;
@@ -1123,11 +1138,6 @@
uint8 bss_info[]; /* var length wl_bss_info_X structures */
} wl_gscan_result_v2_1_t;
-#ifndef WL_BSS_INFO_TYPEDEF_HAS_ALIAS
-typedef wl_gscan_result_v2_t wl_gscan_result_t;
-#define WL_GSCAN_RESULTS_FIXED_SIZE (sizeof(wl_gscan_result_t) - sizeof(wl_gscan_bss_info_t))
-#endif
-
/** incremental scan results struct */
typedef struct wl_iscan_results {
uint32 status;
@@ -1140,13 +1150,6 @@
wl_scan_results_v2_t results;
} wl_iscan_results_v2_t;
-#ifndef WL_BSS_INFO_TYPEDEF_HAS_ALIAS
-typedef wl_iscan_results_v109_t wl_iscan_results_t;
-/** size of wl_iscan_results not including variable length array */
-#define WL_ISCAN_RESULTS_FIXED_SIZE \
- (WL_SCAN_RESULTS_FIXED_SIZE + OFFSETOF(wl_iscan_results_t, results))
-#endif
-
typedef struct wl_probe_params {
wlc_ssid_t ssid;
struct ether_addr bssid;
@@ -1181,11 +1184,6 @@
* [d] in wlc_types.h: in respective branch and trunk: redefine wl_rateset_args_t with
* new wl_rateset_args_vX_t
*/
-#ifndef RATESET_VERSION_ENABLED
-/* rateset structure before versioning. legacy. DONOT update anymore here */
-#define RATESET_ARGS_VERSION (RATESET_ARGS_V1)
-typedef wl_rateset_args_v1_t wl_rateset_args_t;
-#endif /* RATESET_VERSION_ENABLED */
/* Note: dependent structures: sta_info_vX_t. When any update to this structure happens,
* update sta_info_vX_t also.
@@ -1216,9 +1214,6 @@
* anyway...
*/
-/* EHT-MCS Map for all mcs ranges with no nss support */
-#define WL_EHT_MCS_MAP_MCS_NONE_ALL 0u
-
typedef struct wl_rateset_args_v3 {
uint16 version; /**< version. */
uint16 len; /**< length */
@@ -1231,10 +1226,12 @@
} wl_rateset_args_v3_t;
/* 20MHz only EHT-MCS Map mcs range bitmap */
-#define WL_EHT_MCS_BMP_MCS_0_7 0x00ffu
-#define WL_EHT_MCS_BMP_MCS_8_9 0x0300u
-#define WL_EHT_MCS_BMP_MCS_10_11 0x0c00u
-#define WL_EHT_MCS_BMP_MCS_12_13 0x3000u
+#define WL_EHT_MCS_BMP_MCS_0_7 0x00ffu /* mcs 0 - 7 */
+#define WL_EHT_MCS_BMP_MCS_8_9 0x0300u /* mcs 8 & 9 */
+#define WL_EHT_MCS_BMP_MCS_10_11 0x0c00u /* mcs 10 & 11 */
+#define WL_EHT_MCS_BMP_MCS_12_13 0x3000u /* mcs 12 & 13 */
+#define WL_EHT_MCS_BMP_MCS_14 0x4000u /* mcs 14 */
+#define WL_EHT_MCS_BMP_MCS_15 0x8000u /* mcs 15 */
#define TXBF_RATE_MCS_ALL 4
#define TXBF_RATE_VHT_ALL 4
@@ -1350,9 +1347,10 @@
} wl_assoc_params_v1_t;
/** Assoc params flags */
-#define ASSOC_HINT_BSSID_PRESENT (1 << 0)
+#define ASSOC_HINT_BSSID_PRESENT 0x0001u
/* FW to delete PMKSA of bssid listed in assoc params */
-#define WL_ASSOC_PARAM_FLAG_DEL_PMKSA (1 << 1)
+#define WL_ASSOC_PARAM_FLAG_DEL_PMKSA 0x0002u
+#define WL_ASSOC_PARAM_FLAG_ACTIVE6G 0x0004u
#define WL_ASSOC_PARAMS_FIXED_SIZE OFFSETOF(wl_assoc_params_t, chanspec_list)
#define WL_ASSOC_PARAMS_FIXED_SIZE_V1 OFFSETOF(wl_assoc_params_v1_t, chanspec_list)
@@ -1375,13 +1373,14 @@
} wl_ext_reassoc_params_t;
/* Flags field defined above in wl_ext_reassoc_params
- * The value in bits [2:0] is used to specify the type
+ * The below flag bit is used to specify the type
* of scan to be used for reassoc
*/
-#define WL_SCAN_MODE_HIGH_ACC 0u /**< use high accuracy scans for roam */
-#define WL_SCAN_MODE_LOW_SPAN 1u /**< use low span scans for roam */
-#define WL_SCAN_MODE_LOW_POWER 2u /**< use low power scans for roam */
+#define WL_SCAN_MODE_HIGH_ACC 0u /**< use high accuracy scans for roam */
+#define WL_SCAN_MODE_LOW_SPAN 1u /**< use low span scans for roam */
+#define WL_SCAN_MODE_LOW_POWER 2u /**< use low power scans for roam */
+#define WL_SCAN_MODE_NO_6GHZ_FOLLOWUP 4u /* 6G active scan not done due to RNR or FILS */
#define WL_EXTREASSOC_PARAMS_FIXED_SIZE (OFFSETOF(wl_ext_reassoc_params_t, params) + \
WL_REASSOC_PARAMS_FIXED_SIZE)
@@ -1430,10 +1429,8 @@
int16 a_band_max_boost;
} wlc_roam_exp_params_t;
-#define ROAM_EXP_CFG_VERSION 1
-
+#define ROAM_EXP_CFG_VERSION_1 1
#define ROAM_EXP_ENABLE_FLAG (1 << 0)
-
#define ROAM_EXP_CFG_PRESENT (1 << 1)
typedef struct wl_roam_exp_cfg {
@@ -1449,7 +1446,7 @@
int8 flags;
} wl_bssid_pref_list_t;
-#define BSSID_PREF_LIST_VERSION 1
+#define BSSID_PREF_LIST_VERSION_1 1
#define ROAM_EXP_CLEAR_BSSID_PREF (1 << 0)
typedef struct wl_bssid_pref_cfg {
@@ -1460,7 +1457,7 @@
wl_bssid_pref_list_t bssids[];
} wl_bssid_pref_cfg_t;
-#define SSID_WHITELIST_VERSION 1
+#define SSID_WHITELIST_VERSION_1 1
#define ROAM_EXP_CLEAR_SSID_WHITELIST (1 << 0)
@@ -1477,7 +1474,7 @@
wlc_ssid_t ssids[];
} wl_ssid_whitelist_t;
-#define ROAM_EXP_EVENT_VERSION 1
+#define ROAM_EXP_EVENT_VERSION_1 1
typedef struct wl_roam_exp_event {
@@ -1539,6 +1536,13 @@
#define WIFI_RADIO_STAT_VERSION_1 (1u)
#define WIFI_RADIO_STAT_VERSION_2 (2u)
+typedef enum wl_radiostats_slice_index {
+ WL_RADIOSTAT_SLICE_INDEX_MAIN = 0u,
+ WL_RADIOSTAT_SLICE_INDEX_AUX = 1u,
+ WL_RADIOSTAT_SLICE_INDEX_SCAN = 2u,
+ WL_RADIOSTAT_SLICE_INDEX_MAX = 3u
+} wl_radiostats_slice_index_t;
+
#define WIFI_RADIO_STAT_FIXED_LEN OFFSETOF(wifi_radio_stat, channels)
typedef struct wifi_radio_stat_v1 {
@@ -1696,6 +1700,9 @@
uint32 timestamp; /**< second timestamp */
} cca_congest_simple_t;
+// ED: Energy Detection Thresholds
+#define PHY_EDTHRESH_MAX_COUNT 2u /* WLC_API_VERSION_MAJOR >= 17u */
+
// Desense Reasons
#define BPHY_DESENSE_ACI_MASK (1 << 0u) // Desense due to GBD
#define OFDM_DESENSE_ACI_MASK (1 << 1u)
@@ -1822,7 +1829,7 @@
*/
} wl_country_t;
-#define CCODE_INFO_VERSION 1
+#define CCODE_INFO_VERSION_1 1
typedef enum wl_ccode_role {
WLC_CCODE_ROLE_ACTIVE = 0,
@@ -1933,6 +1940,28 @@
} wl_leap_list_t;
#endif /* BCMCCX */
+#define WL_SUP_IOV_VERSION_1 0x0001u
+enum {
+ WL_SUP_CMD_NONE = 0,
+ /* Get SUP IOVAR bersion */
+ WL_SUP_CMD_GET_VERSION = 1u,
+ /* IOVAR to send GTK rekey request */
+ WL_SUP_CMD_SEND_GTK_REQ = 2u,
+ /* Set/Get skip GTK M1 processing state */
+ WL_SUP_CMD_IGNORE_GTK_M1 = 3u
+};
+
+typedef uint16 wl_sup_cmd_t;
+
+typedef struct wl_sup_iov_v1 {
+ uint16 version; /* structure version will be incremented
+ * when header is changed.
+ */
+ uint16 len; /* data field lenth. */
+ wl_sup_cmd_t cmd; /* sub-command id. */
+ uint8 data[]; /* variable */
+} wl_sup_iov_v1_t;
+
typedef enum sup_auth_status {
/* Basic supplicant authentication states */
WLC_SUP_DISCONNECTED = 0,
@@ -2104,24 +2133,19 @@
pmkid_v2_t pmkid[BCM_FLEX_ARRAY];
} pmkid_list_v2_t;
-#define PMKDB_SET_IOVAR 1u
-#define PMKDB_GET_IOVAR 2u
-#define PMKDB_CLEAR_IOVAR 4u
+#define PMKDB_SET_IOVAR 0x0001u
+#define PMKDB_GET_IOVAR 0x0002u
+#define PMKDB_CLEAR_IOVAR 0x0004u
+#define PMKDB_ALL_CFGS 0x0008u /* option for PMKDB_GET_IOVAR */
typedef struct _pmkid_list_v3 {
uint16 version;
uint16 length;
uint16 count;
- uint16 flag;
+ uint16 flag;
pmkid_v3_t pmkid[];
} pmkid_list_v3_t;
-#ifndef PMKID_VERSION_ENABLED
-/* pmkid structure before versioning. legacy. DONOT update anymore here */
-typedef pmkid_v1_t pmkid_t;
-typedef pmkid_list_v1_t pmkid_list_t;
-#endif /* PMKID_VERSION_ENABLED */
-
typedef struct _pmkid_cand {
struct ether_addr BSSID;
uint8 preauth;
@@ -2511,14 +2535,13 @@
*/
#define WL_OLD_STAINFO_SIZE OFFSETOF(sta_info_t, tx_tot_pkts)
-#define WL_STA_VER_4 4
-#define WL_STA_VER_5 5
-#define WL_STA_VER_6 6
-/* FIXME: the user/branch should make the selection! */
-#define WL_STA_VER WL_STA_VER_4
+#define WL_STA_VER_4 4u
+#define WL_STA_VER_5 5u
+#define WL_STA_VER_6 6u
+#define WL_STA_VER_7 7u
-#define SWDIV_STATS_VERSION_2 2
-#define SWDIV_STATS_CURRENT_VERSION SWDIV_STATS_VERSION_2
+#define SWDIV_STATS_VERSION_1 1u
+#define SWDIV_STATS_VERSION_2 2u
struct wlc_swdiv_stats_v1 {
uint32 auto_en;
@@ -2556,8 +2579,8 @@
struct wlc_swdiv_stats_v2 {
uint16 version; /* version of the structure
- * as defined by SWDIV_STATS_CURRENT_VERSION
- */
+ * as defined by SWDIV_STATS_CURRENT_VERSION
+ */
uint16 length; /* length of the entire structure */
uint32 auto_en;
uint32 active_ant;
@@ -2886,6 +2909,7 @@
WL_MACFIFO_PLAY_LOAD = 0x02u, /* for set: load samples
for get: samples are loaded
*/
+ WL_MACFIFO_PLAY_CAL = 0x08u, /* macfifo play for calibration */
WL_MACFIFO_PLAY_GET_MAX_SIZE = 0x10u, /* get the macfifo buffer size */
WL_MACFIFO_PLAY_GET_STATUS = 0x20u, /* get macfifo play status */
};
@@ -3163,7 +3187,7 @@
uint8 PAD[2];
} wl_radar_args_t;
-#define WL_RADAR_ARGS_VERSION 2
+#define WL_RADAR_ARGS_VERSION_2 2
typedef struct {
uint32 version; /**< version */
@@ -3400,13 +3424,19 @@
/* curpower ppr types */
enum {
- PPRTYPE_TARGETPOWER = 1,
- PPRTYPE_BOARDLIMITS = 2,
- PPRTYPE_REGLIMITS = 3,
- PPRTYPE_RU_REGLIMITS = 4,
- PPRTYPE_RU_BOARDLIMITS = 5,
- PPRTYPE_RU_TARGETPOWER = 6,
- PPRTYPE_DYNAMIC_INFO = 7,
+ PPRTYPE_TARGETPOWER = 1u,
+ PPRTYPE_BOARDLIMITS = 2u,
+ PPRTYPE_REGLIMITS = 3u,
+ PPRTYPE_RU_REGLIMITS = 4u,
+ PPRTYPE_RU_BOARDLIMITS = 5u,
+ PPRTYPE_RU_TARGETPOWER = 6u,
+ PPRTYPE_DYNAMIC_INFO = 7u,
+ PPRTYPE_TGT_PWR_PSU = 8u,
+ PPRTYPE_BOARDLIMITS_PSU = 9u,
+ PPRTYPE_REGLIMITS_PSU = 10u,
+ PPRTYPE_TGT_PWR_MRU = 11u,
+ PPRTYPE_BOARDLIMITS_MRU = 12u,
+ PPRTYPE_REGLIMITS_MRU = 13u,
PPRTYPE_LAST
};
@@ -3415,8 +3445,8 @@
typedef struct chanspec_txpwr_max {
chanspec_t chanspec; /**< chanspec */
- uint8 txpwr_max; /**< max txpwr in all the rates */
- uint8 PAD;
+ int8 txpwr_max; /**< max txpwr in all the rates */
+ uint8 txpwr_cat; /**< txpwr category for 6g */
} chanspec_txpwr_max_t;
typedef struct wl_chanspec_txpwr_max {
@@ -3619,53 +3649,131 @@
wl_mimo_ps_learning_event_data_t mimops_learning_data;
} wl_mimops_learning_cfg_t;
-#define WL_OCL_STATUS_VERSION 1
+/* ocl status is reported per slice */
+#define WL_OCL_STATUS_VERSION_1 1
typedef struct ocl_status_info {
uint8 version;
uint8 len;
- uint16 fw_status; /* Bits representing FW disable reasons */
- uint8 hw_status; /* Bits for actual HW config and SISO/MIMO coremask */
- uint8 coremask; /* The ocl core mask (indicating listening core) */
+ uint16 fw_status; /* Bits representing FW disable reasons */
+ uint8 hw_status; /* Bits for actual HW config and SISO/MIMO coremask */
+ uint8 coremask; /* The ocl core mask (indicating listening core) */
} ocl_status_info_t;
+#define WL_OCL_STATUS_VERSION_2 2 /* v2 supports disable stats */
+typedef struct ocl_status_info_v2 {
+ uint8 version;
+ uint8 len;
+ uint8 hw_status; /* Bits for actual HW config and SISO/MIMO coremask */
+ uint8 coremask; /* The ocl core mask (indicating listening core) */
+ uint32 fw_status; /* Bits representing FW disable reasons */
+ uint32 disable_start_req; /* disable reason which triggered the ocl state change
+ * from enable to disable, afterwards there could be more
+ * disable reason(s) active before ocl state is enabled
+ * again. All current disable reason(s) are
+ * indicated in fw_status and at snapshot maynot include
+ * the disable reason which actually triggered ocl disable
+ * as reasons become active/inactive independently.
+ */
+ uint32 enable_start_req; /* disable reason which triggered the ocl state change
+ * from disable to enable. This is the reason which very
+ * recently turned off which caused the ocl to enable.
+ */
+ uint32 cur_ts; /* current timestamp (ms) */
+ uint32 disable_start_ts; /* disable_start_req timestamp (ms) */
+ uint32 enable_start_ts; /* enable_start_req timestamp (ms) */
+ uint32 disable_count_as; /* total effective-disable (i.e., ocl state changing
+ * from enable-to-disable) count since last assoc
+ */
+ uint32 disable_reqs_count_as; /* total disable requests since last assoc */
+ uint32 disable_dur_as; /* total disable duration (ms) since last assoc */
+ uint32 disable_count; /* total effective-disable count */
+ uint32 disable_reqs_count; /* total disable requests */
+ uint32 disable_dur; /* total disable duration (ms) */
+} ocl_status_info_v2_t;
+
+/* v3 shows per-chanspec OCL status, active link type
+ * on that chanspec, and user's ocl configuration
+ */
+#define WL_OCL_STATUS_VERSION_3 3
+typedef struct ocl_status_info_v3 {
+ uint8 version;
+ uint8 len;
+ uint8 hw_status; /* Bits for actual HW config and SISO/MIMO coremask */
+ uint8 coremask; /* The ocl core mask (indicating listening core) */
+ uint32 fw_status; /* Bits representing FW disable reasons */
+ uint32 disable_start_req; /* disable reason which triggered the ocl state change
+ * from enable to disable, afterwards there could be more
+ * disable reason(s) active before ocl state is enabled
+ * again. All current disable reason(s) are
+ * indicated in fw_status and at snapshot maynot include
+ * the disable reason which actually triggered ocl disable
+ * as reasons become active/inactive independently.
+ */
+ uint32 enable_start_req; /* disable reason which triggered the ocl state change
+ * from disable to enable. This is the reason which very
+ * recently turned off which caused the ocl to enable.
+ */
+ uint32 cur_ts; /* current timestamp (ms) */
+ uint32 disable_start_ts; /* disable_start_req timestamp (ms) */
+ uint32 enable_start_ts; /* enable_start_req timestamp (ms) */
+ uint32 disable_count_as; /* total effective-disable (i.e., ocl state changing
+ * from enable-to-disable) count since last assoc
+ */
+ uint32 disable_reqs_count_as; /* total disable requests since last assoc */
+ uint32 disable_dur_as; /* total disable duration (ms) since last assoc */
+ uint32 disable_count; /* total effective-disable count */
+ uint32 disable_reqs_count; /* total disable requests */
+ uint32 disable_dur; /* total disable duration (ms) */
+ uint16 chanspec; /* chanspec on which ocl_status is reported */
+ uint8 active_link; /* Bits showing which link is active */
+ uint8 ocl_en; /* user's configuation */
+} ocl_status_info_v3_t;
+
+#define OCL_SET_INFRA (1u << 0u) /* host OCL enable/disable for INFRA */
+#define OCL_SET_NAN (1u << 1u) /* host OCL enable/disable for NAN */
+#define OCL_SET_AWDL (1u << 2u) /* host OCL enable/disable for AWDL */
+
/* MWS OCL map */
-#define WL_MWS_OCL_OVERRIDE_VERSION 1
+#define WL_MWS_OCL_OVERRIDE_VERSION_1 1
typedef struct wl_mws_ocl_override {
- uint16 version; /* Structure version */
- uint16 bitmap_2g; /* bitmap for 2.4G channels bits 1-13 */
- uint16 bitmap_5g_lo; /* bitmap for 5G low channels by 2:
- *34-48, 52-56, 60-64, 100-102
- */
- uint16 bitmap_5g_mid; /* bitmap for 5G mid channels by 2:
- * 104, 108-112, 116-120, 124-128,
- * 132-136, 140, 149-151
- */
- uint16 bitmap_5g_high; /* bitmap for 5G high channels by 2
- * 153, 157-161, 165
- */
+ uint16 version; /* Structure version */
+ uint16 bitmap_2g; /* bitmap for 2.4G channels bits 1-13 */
+ uint16 bitmap_5g_lo; /* bitmap for 5G low channels by 2:
+ * 34-48, 52-56, 60-64, 100-102
+ */
+ uint16 bitmap_5g_mid; /* bitmap for 5G mid channels by 2:
+ * 104, 108-112, 116-120, 124-128,
+ * 132-136, 140, 149-151
+ */
+ uint16 bitmap_5g_high; /* bitmap for 5G high channels by 2
+ * 153, 157-161, 165
+ */
} wl_mws_ocl_override_t;
-/* Bits for fw_status */
-#define OCL_DISABLED_HOST 0x01 /* Host has disabled through ocl_enable */
-#define OCL_DISABLED_RSSI 0x02 /* Disabled because of ocl_rssi_threshold */
-#define OCL_DISABLED_LTEC 0x04 /* Disabled due to LTE Coex activity */
-#define OCL_DISABLED_SISO 0x08 /* Disabled while in SISO mode */
-#define OCL_DISABLED_CAL 0x10 /* Disabled during active calibration */
-#define OCL_DISABLED_CHANSWITCH 0x20 /* Disabled during active channel switch */
-#define OCL_DISABLED_ASPEND 0x40 /* Disabled due to assoc pending */
-#define OCL_DISABLED_SEQ_RANGE 0x80 /* Disabled during SEQ Ranging */
-#define OCL_DISABLED_RXIQ_EST_BTLOWAR 0x100 /* Disabled if the bt-lo-war is active */
-#define OCL_DISABLED_IDLE_TSSICAL 0x200
-#define OCL_DISABLED_TONE 0x400 /* Disabled if the tone is active */
-#define OCL_DISABLED_NOISECAL 0x800 /* Disabled if the noise cal is active */
-#define OCL_DISABLED_INIT 0x1000 /* Disabled during phy init */
-#define OCL_DISABLED_AZ 0x2000 /* Disabled during 802.11az ranging */
-#define OCL_DISABLED_PHYTS 0x4000 /* Disabled during PHYTS */
+/* Bits for fw_status and disable/enable start request */
+#define OCL_DISABLED_HOST (1u << 0u) /* Disabled by host through ocl_enable */
+#define OCL_DISABLED_RSSI (1u << 1u) /* Disabled because of ocl_rssi_threshold */
+#define OCL_DISABLED_LTEC (1u << 2u) /* Disabled due to LTE Coex activity */
+#define OCL_DISABLED_SISO (1u << 3u) /* Disabled while in SISO mode */
+#define OCL_DISABLED_CAL (1u << 4u) /* Disabled during active calibration */
+#define OCL_DISABLED_CHANSWITCH (1u << 5u) /* Disabled during channel switch */
+#define OCL_DISABLED_ASPEND (1u << 6u) /* Disabled due to assoc pending */
+#define OCL_DISABLED_SEQ_RANGE (1u << 7u) /* Disabled during SEQ Ranging */
+#define OCL_DISABLED_RXIQ_EST_BTLOWAR (1u << 8u) /* Disabled if the bt-lo-war is active */
+#define OCL_DISABLED_IDLE_TSSICAL (1u << 9u) /* Disabled if TSSI Cal in progress */
+#define OCL_DISABLED_TONE (1u << 10u) /* Disabled if the tone is active */
+#define OCL_DISABLED_NOISECAL (1u << 11u) /* Disabled if the noise cal is active */
+#define OCL_DISABLED_INIT (1u << 12u) /* Disabled during phy init */
+#define OCL_DISABLED_AZ (1u << 13u) /* Disabled during 802.11az ranging */
+#define OCL_DISABLED_PHYTS (1u << 14u) /* Disabled during PHYTS */
+#define OCL_DISABLED_SCPEND (1u << 15u) /* Disabled due to scan pending */
+#define OCL_DISABLED_EMLSR (1u << 16u) /* Disabled due to EMLSR enabled */
+#define OCL_DISABLED_BTBPHYWAR (1u << 17u) /* Disabled during BT eSCO traffic */
/* Bits for hw_status */
-#define OCL_HWCFG 0x01 /* State of OCL config bit in phy HW */
-#define OCL_HWMIMO 0x02 /* Set if current coremask is > 1 bit */
-#define OCL_COREDOWN 0x80 /* Set if core is currently down */
+#define OCL_HWCFG 0x01u /* State of OCL config bit in phy HW */
+#define OCL_HWMIMO 0x02u /* Set if current coremask is > 1 bit */
+#define OCL_COREDOWN 0x80u /* Set if core is currently down */
#define WL_OPS_CFG_VERSION_1 1
/* Common IOVAR struct */
@@ -3756,6 +3864,7 @@
#define OPS_DISABLED_UNASSOC 0x02 /* Disabled because the slice is in unassociated state */
#define OPS_DISABLED_SCAN 0x04 /* Disabled because the slice is in scan state */
#define OPS_DISABLED_BCN_MISS 0x08 /* Disabled because beacon missed for a duration */
+#define OPS_DISABLED_OBSS_MMT 0x10 /* Disabled because of OBSS measurement */
#define WL_PSBW_CFG_VERSION_1 1
/* Common IOVAR struct */
@@ -3880,6 +3989,7 @@
/* Bit value for DVFS status */
#define DVFS_STATUS_LDV 0u
#define DVFS_STATUS_NDV 1u
+#define DVFS_STATUS_HDV 3u
/* DVFS bits are for status, raw request and active request */
/* 4387b0 supports only status bits for aux, main, and bt */
/* 4387c0 supports all eight status and request bits */
@@ -3923,6 +4033,9 @@
#define DVFS_BIT_SYSMEM_SHIFT 9u
#define DVFS_BIT_SYSMEM_VAL(_val) (((_val) & DVFS_BIT_SYSMEM_MASK) \
>> DVFS_BIT_SYSMEM_SHIFT)
+
+#define DVFS_BIT_SAQM_SHIFT 10u
+
/* to convert voltage to volt from multiple of 10mVolt */
#define DVFS_CONVERT_TO_VOLT 100u
@@ -3986,6 +4099,90 @@
} dvfs_status_v4_t;
#define DVFS_STATUS_VER_4_LEN (sizeof(dvfs_status_v4_t))
+typedef struct dvfs_supply_stats_v5 {
+ uint16 version;
+ uint16 len;
+
+ uint16 supply_num; /* Supply num that has this dvfs supply stats. */
+ uint8 dvfs_status; /* current dvfs status LDV/NDV/HDV */
+ uint8 voltage; /* voltage (multiple of 10mV) */
+
+ uint32 state_change_count; /* total state (LDV/NDV) transition count */
+
+ uint32 fw_ldv_duration; /* total time (ms) in LDV */
+ uint32 hw_ldv_duration; /* total time (ms) in LDV reported by HW */
+ uint32 state_change_count_hw_ldv; /* HDV transition count by HW */
+
+ uint32 fw_ndv_duration; /* total time (ms) in LDV */
+ uint32 hw_ndv_duration; /* total time (ms) in LDV reported by HW */
+ uint32 state_change_count_hw_ndv; /* HDV transition count by HW */
+
+ uint32 fw_hdv_duration; /* total time (ms) in LDV */
+ uint32 hw_hdv_duration; /* total time (ms) in LDV reported by HW */
+ uint32 state_change_count_hw_hdv; /* HDV transition count by HW */
+} dvfs_supply_stats_v5_t;
+
+#define DVFS_STATUS_CORE_NAME_MASK 0x3Fu
+#define DVFS_STATUS_CORE_NAME_SHIFT 0u
+#define DVFS_STATUS_CORE_STATUS_MASK 0x3u
+#define DVFS_STATUS_CORE_STATUS_SHIFT 0x6u
+#define DVFS_STATUS_CORE_ACTIVE_REQ_MASK 0x3u
+#define DVFS_STATUS_CORE_ACTIVE_REQ_SHIFT 8u
+#define DVFS_STATUS_CORE_RAW_REQ_MASK 0x3u
+#define DVFS_STATUS_CORE_RAW_REQ_SHIFT 10u
+#define DVFS_STATUS_CORE_SUPPLY_NUM_MASK 0x3u
+#define DVFS_STATUS_CORE_SUPPLY_NUM_SHIFT 12u
+
+typedef struct dvfs_core_info_v5 {
+ uint16 version;
+ uint16 len;
+ uint8 num_cores;
+ uint8 PAD;
+ uint16 powercontrol; /* PowerControl from chipcommon */
+ uint16 dvfs_core_stats[]; /* Per core statistics,
+ * BITs 5:0 dvfs_core_name
+ * BITs 7:6 DVFS Status
+ * BITs 9:8 Active Request
+ * BITs 11:10 RAW Request
+ * BITs 13:12 Supply Num
+ * BIT 14:14 if set CoreReady rsrc is active
+ * BITs 15 reserved
+ */
+} dvfs_core_info_v5_t;
+
+typedef struct dvfs_freq_info_v5 {
+ uint16 version;
+ uint16 len;
+ uint32 freq_common_bp;
+ uint32 freq_wlan_bp;
+ uint32 freq_main_mac;
+ uint32 freq_aux_mac;
+ uint32 freq_scan_mac;
+ uint32 freq_saqm;
+} dvfs_freq_info_v5_t;
+
+typedef enum dvfs_tlv_id {
+ DVFS_SUPPLY_STATS_ID = 0u,
+ DVFS_CORE_STATUS_ID = 1u,
+ DVFS_FREQ_STATS_ID = 2u,
+ DVFS_XTLV_MAX = 3u
+} dvfs_tlv_id_s;
+
+#define DVFS_STATUS_CORE_INFO_VER 0
+#define DVFS_STATUS_FREQ_INFO_VER 0
+#define DVFS_STATUS_VERSION_5 5
+
+typedef struct dvfs_status_v5 {
+ uint16 version; /* version of dvfs_status */
+ uint16 len; /* total length including all fixed fields */
+
+ uint16 armfreq; /* arm clock frequency (in MHz) */
+ uint16 num_dvfs_supplies; /* Total number of supplies */
+ uint8 tlv_params[]; /* xtlvs for variable ext params, id dvfs_tlv_id_s */
+
+} dvfs_status_v5_t;
+#define DVFS_STATUS_VER_5_LEN (sizeof(dvfs_status_v5_t))
+
/* DVFS_SUBCMD_HIST */
#define DVFS_HIST_CMD_VERSION_1 1
typedef struct dvfs_hist_cmd_v1 {
@@ -4017,6 +4214,7 @@
#define WL_DVFS_REASON_ASSOC 0x0800u /* ASSOC */
#define WL_DVFS_REASON_WD 0x1000u /* WD */
#define WL_DVFS_REASON_SOFTAP 0x2000u /* SoftAP */
+#define WL_DVFS_REASON_PHYBW 0x4000u /* Channel BW Change */
/*
* Join preference iovar value is an array of tuples. Each tuple has a one-byte type,
@@ -4077,11 +4275,10 @@
#define RATE_LEGACY_OFDM_48MBPS 6
#define RATE_LEGACY_OFDM_54MBPS 7
-#define WL_BSSTRANS_RSSI_RATE_MAP_VERSION 1
-#define WL_BSSTRANS_RSSI_RATE_MAP_VERSION_V1 1
-#define WL_BSSTRANS_RSSI_RATE_MAP_VERSION_V2 2
-#define WL_BSSTRANS_RSSI_RATE_MAP_VERSION_V3 3
-#define WL_BSSTRANS_RSSI_RATE_MAP_VERSION_V4 4
+#define WL_BSSTRANS_RSSI_RATE_MAP_VERSION_V1 1
+#define WL_BSSTRANS_RSSI_RATE_MAP_VERSION_V2 2
+#define WL_BSSTRANS_RSSI_RATE_MAP_VERSION_V3 3
+#define WL_BSSTRANS_RSSI_RATE_MAP_VERSION_V4 4
#define WL_BSSTRANS_RSSI_VERSION_V1 1u
@@ -4157,7 +4354,7 @@
wl_bsstrans_rssi_t phy_ac[RSSI_RATE_MAP_MAX_STREAMS][WL_NUM_RATES_VHT]; /**< MCS0-9 */
} wl_bsstrans_rssi_rate_map_t;
-#define WL_CCA_CHAN_LOAD_VERSION 1
+#define WL_CCA_CHAN_LOAD_VERSION_1 1
#define CCA_LOAD_MAP_MAX_TABLE_ENTRY 16u
typedef struct wl_cca_chnl_load {
@@ -4172,7 +4369,7 @@
wl_cca_chnl_load_t cca_load[CCA_LOAD_MAP_MAX_TABLE_ENTRY];
} wl_cca_chnl_load_map_t;
-#define WL_BSSTRANS_ROAMTHROTTLE_VERSION 1
+#define WL_BSSTRANS_ROAMTHROTTLE_VERSION_1 1
/** Configure number of scans allowed per throttle period */
typedef struct wl_bsstrans_roamthrottle {
@@ -4280,7 +4477,6 @@
*/
#define REINIT_RSN_IDX_V2(_x) (((_x) <= WL_REINIT_RC_LAST_V2) ? (_x) : 0)
-#define WL_CNT_T_VERSION 30 /**< current version of wl_cnt_t struct */
#define WL_CNT_VERSION_6 6
#define WL_CNT_VERSION_7 7
#define WL_CNT_VERSION_11 11
@@ -4296,7 +4492,12 @@
/* Number of xtlv info as required to calculate subcounter offsets */
#define WL_CNT_XTLV_ID_NUM 12
-#define WL_TLV_IOV_VER 1
+#define WL_TLV_IOV_VERSION_1 1u
+#define WL_TLV_IOV_VERSION_2 2u
+
+#define WL_TLV_DATASET_V2_LEN 2u /* First 32 bit - TLV type
+ * Second 32 bit - TLV Len
+ */
/**
* tlv IDs uniquely identifies counter component
@@ -4311,7 +4512,6 @@
WL_CNT_XTLV_WLC_HE_OMI = 0x104, /* he omi counters */
WL_CNT_XTLV_WLC_RINIT_RSN_V2 = 0x105, /**< WLC layer reinitreason extension */
WL_CNT_XTLV_WLC_MESH_PKT_V1 = 0x106, /**< WLC layer Mesh pkt counters */
- WL_CNT_XTLV_WLC_DRR = 0x107, /* DRR core layer counters */
WL_CNT_XTLV_CNTV_LE10_UCODE = 0x200, /**< wl counter ver < 11 UCODE MACSTAT */
WL_CNT_XTLV_LT40_UCODE_V1 = 0x300, /**< corerev < 40 UCODE MACSTAT */
WL_CNT_XTLV_GE40_UCODE_V1 = 0x400, /**< corerev >= 40 UCODE MACSTAT */
@@ -4319,8 +4519,12 @@
WL_CNT_XTLV_GE80_UCODE_V1 = 0x900, /* corerev >= 80 UCODEX MACSTAT */
WL_CNT_XTLV_GE80_RXERR_UCODE_V1 = 0x901, /* corerev >= 80 UCODE RXERR mac stat */
WL_CNT_XTLV_GE80_TXFUNFL_UCODE_V1 = 0x1000, /* corerev >= 80 UCODEX MACSTAT */
- WL_CNT_XTLV_GE88_UCODE_TX_V1 = 0x1001, /* corerev >= 88 ucode macstats - tx */
- WL_CNT_XTLV_GE88_UCODE_RX_V1 = 0x1002, /* corerev >= 88 ucode macstats - rx */
+ WL_CNT_XTLV_GE88_UCODE_TX_V1 = 0x1001, /* corerev >= 88 ucode macstats V1 - tx */
+ WL_CNT_XTLV_GE88_UCODE_RX_V1 = 0x1002, /* corerev >= 88 ucode macstats V1 - rx */
+ WL_CNT_XTLV_GE88_UCODE_TX_V2 = 0x1003, /* corerev >= 88 ucode macstats V2 - tx */
+ WL_CNT_XTLV_GE88_UCODE_RX_V2 = 0x1004, /* corerev >= 88 ucode macstats V2 - rx */
+ WL_CNT_XTLV_GE88_UCODE_TX_U32_V1 = 0x1005, /* corerev >= 88 ucode macstats V1 - tx */
+ WL_CNT_XTLV_GE88_UCODE_RX_U32_V1 = 0x1006, /* corerev >= 88 ucode macstats V1 - rx */
};
/* tlv IDs uniquely identifies periodic state component */
@@ -4576,6 +4780,20 @@
uint8 PAD;
} bcnsim_status_v1_t;
+/* SFLASH iovar sub commands */
+#define WL_SFLASH_IOV_VERSION_V1 1u
+
+enum wl_sflash_subcmd_id {
+ WL_SFLASH_SUBCMD_CALWRITE = 0,
+ WL_SFLASH_SUBCMD_CALERASE = 1u,
+ WL_SFLASH_SUBCMD_WRITE = 2u,
+ WL_SFLASH_SUBCMD_ERASE = 3u,
+ WL_SFLASH_SUBCMD_DUMP = 4u,
+ WL_SFLASH_SUBCMD_DATASIZE = 5u,
+ WL_SFLASH_SUBCMD_SIZE = 6u,
+ WL_SFLASH_SUBCMD_READ = 7u
+};
+
/**
* The number of variables in wl macstat cnt struct.
* (wl_cnt_ge40mcst_v1_t, wl_cnt_lt40mcst_v1_t, wl_cnt_v_le10_mcst_t)
@@ -4593,7 +4811,7 @@
#define WL_CNT_MCXST_STRUCT_SZ ((uint32)sizeof(wl_cnt_ge64mcxst_v1_t))
-#define WL_CNT_HE_STRUCT_SZ ((uint32)sizeof(wl_he_cnt_wlc_t))
+#define WL_CNT_HE_STRUCT_V5_SZ ((uint32)sizeof(wl_he_cnt_wlc_v5_t))
#define WL_CNT_SECVLN_STRUCT_SZ ((uint32)sizeof(wl_secvln_cnt_t))
@@ -4904,6 +5122,11 @@
* BA policy and tossed by key mgmt as
* replays
*/
+ uint32 txnoalfdatabuf; /**< out of alfrag data buffers errors */
+ uint32 txalfdatabuf; /**< number of tx alfrag data buffers attepted for transmission */
+ uint32 txalfrag; /**< number of txalfrags attepted for transmission */
+ uint32 txlfrag; /**< number of txlfrags attepted for transmission */
+ uint32 rxunsolicitedproberesp; /**< number of "unsoliocited" probe responses RXed */
/* Do not remove or rename in the middle of this struct.
* All counter variables have to be of uint32.
@@ -5119,13 +5342,11 @@
*/
uint32 rxheru_2x996T;
uint32 he_txtbppdu_cnt[AC_COUNT];
+ uint32 he_rxtrig_ruidx_invalid; /* basic trigger with invalid RU index or RU size
+ * greater than BW
+ */
} wl_he_cnt_wlc_v5_t;
-#ifndef HE_COUNTERS_VERSION_ENABLED
-#define HE_COUNTERS_VERSION (HE_COUNTERS_V1)
-typedef wl_he_cnt_wlc_v1_t wl_he_cnt_wlc_t;
-#endif /* HE_COUNTERS_VERSION_ENABLED */
-
/* he omi counters Version 1 */
#define HE_OMI_COUNTERS_V1 (1)
typedef struct wl_he_omi_cnt_wlc_v1 {
@@ -5429,7 +5650,7 @@
} wl_cnt_lt40mcst_v1_t;
/* ==== REV GE88 Counter Structs === */
-/* Rev Ge88 RX specific macstats - version 1 */
+/* Rev Ge88 TX specific macstats - version 1 */
typedef struct {
uint32 txallfrm; /**< num of frames sent, incl. Data, ACK, RTS, CTS,
* Control Management (includes retransmissions)
@@ -5449,10 +5670,10 @@
uint32 txbfpoll; /**< Number of tx bfpolls */
uint32 txfbw; /**< transmit at fallback bw (dynamic bw) */
uint32 txampdu; /**< number of AMPDUs transmitted */
- uint32 txmampdu; /**< Number of tx m-ampdus */
+ uint32 he_txmampdu; /**< Number of tx m-ampdus */
uint32 txmpdu; /**< number of MPDUs transmitted */
uint32 txucast; /**< # of ucast tx expecting resp (not cts/cwcts) */
- uint32 txfrag; /**< Number of tx frags */
+ uint32 he_txfrag; /**< Number of tx frags */
uint32 he_txtbppdu; /**< increments on transmission of every TB PPDU */
uint32 he_txtbppdu_ack; /**< Number of tx HE TBPPDU acks */
uint32 txinrtstxop; /**< number of data frame tx during rts txop */
@@ -5501,10 +5722,10 @@
uint32 btcx_txconf_ctr_h; /**< btcx txconf counter high */
uint32 btcx_txconf_dur_ctr_l; /**< btcx txconf duration counter low */
uint32 btcx_txconf_dur_ctr_h; /**< btcx txconf duration counter high */
- uint32 txcgprssucc_cnt; /**< Tx Probe Response succ cnt */
- uint32 txsf_cnt; /**< # of Tx'd SF */
+ uint32 txcgprssuc; /**< Tx Probe Response succ cnt */
+ uint32 txsf; /**< # of Tx'd SF */
uint32 macsusp_cnt; /**< # of macsuspends */
- uint32 prewds_cnt; /**< # of pre wds */
+ uint32 prs_timeout; /**< # of pre wds */
uint32 emlsr_tx_nosrt; /**< # of no TX starts for eMLSR */
} wl_cnt_ge88mcst_tx_v1_t;
@@ -5525,46 +5746,44 @@
uint32 C_CCA_RXSEC40_HI; /**< SEC CCA RX 40mhz high */
uint32 C_CCA_RXSEC80_LO; /**< SEC CCA RX 80mhz low */
uint32 C_CCA_RXSEC80_HI; /**< SEC CCA RX 80mhz high */
- uint32 rxcfrmmcast; /**< # of RX ctrl mcast frames
- * (unlikely to see these)
- */
- uint32 rxmfrmmcast; /**< # of rx'd Management mcast frames */
- uint32 rxdfrmmcast; /**< # of rx'd Data mcast frames */
+ uint32 rxctlmcast; /**< # of RX ctrl mcast frames */
+ uint32 rxmgmcast; /**< # of rx'd Management mcast frames */
+ uint32 rxdtmcast; /**< # of rx'd Data mcast frames */
uint32 rxbeaconmbss; /**< beacons rx'd from member of BSS */
uint32 rxndpa_m; /**< number of RX NDPA Multicast */
uint32 rxrtsucast; /**< # of ucast RTS (good FCS) */
uint32 rxctsucast; /**< # of ucast CTS (good FCS) */
- uint32 rxcfrmucast; /**< # of rx'd CNTRL frames (good FCS & matching RA) */
- uint32 rxmfrmucastmbss; /**< # of rx'd mgmt frames (good FCS & matching RA) */
- uint32 rxdfrmucastmbss; /**< # of rx'd DATA frames (good FCS & matching RA) */
+ uint32 rxctlucast; /**< # of rx'd CNTRL frames (good FCS & matching RA) */
+ uint32 rxmgucastmbss; /**< # of rx'd mgmt frames (good FCS & matching RA) */
+ uint32 rxdtucastmbss; /**< # of rx'd DATA frames (good FCS & matching RA) */
uint32 rxackucast; /**< number of ucast ACKS received (good FCS) */
uint32 rxndpa_u; /**< number of unicast RX NDPAs */
- uint32 rxsfucast; /**< number of rxsfucast */
+ uint32 rxsf; /**< number of rxsfucast */
uint32 rxcwrts; /**< number of rx'd cw ucast rts */
uint32 rxcwcts; /**< number of rx'd cw ucast cts */
uint32 rxbfpoll; /**< number of rx'd BF ucast poll */
- uint32 rx_good_ucast; /**< number of rx'd good fcs ucast frames */
- uint32 rx_good_ocast; /**< number of rx'd good fcs ocast frames */
- uint32 rxdfrmocast; /**< # of rx'd DATA frames (good FCS & not matching RA) */
- uint32 rxmfrmocast; /**< # of rx'd MGMT frames (good FCS & not matching RA) */
- uint32 rxcfrmocast; /**< # of rx'd CNTRL frame (good FCS & not matching RA) */
+ uint32 pktengrxducast; /**< number of rx'd good fcs ucast frames */
+ uint32 pktengrxdmcast; /**< number of rx'd good fcs ocast frames */
+ uint32 rxdtocast; /**< # of rx'd DATA frames (good FCS & not matching RA) */
+ uint32 rxmgocast; /**< # of rx'd MGMT frames (good FCS & not matching RA) */
+ uint32 rxctlocast; /**< # of rx'd CNTRL frame (good FCS & not matching RA) */
uint32 rxrtsocast; /**< # of rx'd RTS not addressed */
uint32 rxctsocast; /**< # of rx'd CTS not addressed */
- uint32 rxdfrmucastobss; /**< number of unicast frames addressed to the MAC from
+ uint32 rxdtucastobss; /**< number of unicast frames addressed to the MAC from
* other BSS (WDS FRAME)
*/
uint32 rxbeaconobss; /* beacons rx'd from other BSS */
uint32 he_rx_ppdu_cnt; /**< rx'd HE PPDU cnt */
- uint32 he_rx_su_ppdu_cnt; /**< rx'd HE su PPDU cnt */
- uint32 he_rx_su_re_ppdu_cnt; /**< rx'd HE SU RE PPDU cnt */
- uint32 he_rx_mu_ppdu_cnt; /**< rx'd HE MU PPDU cnt */
+ uint32 he_rxstrt_hesuppdu_cnt; /**< rx'd HE su PPDU cnt */
+ uint32 he_rxstrt_hesureppdu_cnt; /**< rx'd HE SU RE PPDU cnt */
+ uint32 he_rxtsrt_hemuppdu_cnt; /**< rx'd HE MU PPDU cnt */
uint32 rxbar; /**< number of rx'd BARs */
uint32 rxback; /**< number of rx'd BARs */
uint32 he_rxmtid_back; /**< number of rx'd HE RX MultiTID BAs */
uint32 he_rxmsta_back; /**< number of rx'd HE RX MultiSTA BAs */
- uint32 bferpt_rdy; /**< number of rx'd BFE report ready cnts */
+ uint32 bferpt; /**< number of rx'd BFE report ready cnts */
uint32 goodfcs; /**< number of rx'd goodfcs cnts */
- uint32 colormiss; /**< HE BSS color mismatch counts cnts */
+ uint32 he_colormiss_cnt; /**< HE BSS color mismatch counts cnts */
uint32 he_rxdefrag; /**< number of rx'd HE dynamic fragmented pkts */
uint32 he_rxdlmu; /**< number of rx'd DL MU frames */
uint32 rxcgprqfrm; /**< number of received Probe requests that made it into
@@ -5584,7 +5803,7 @@
uint32 bphy_rxcrsglitch; /**< PHY count of bphy glitches */
uint32 rxdrop20s; /**< drop secondary cnt */
uint32 rxtoolate; /**< receive too late */
- uint32 rx_pfifo_drop; /**< # of pfifo dropped frames */
+ uint32 m_pfifo_drop; /**< # of pfifo dropped frames */
uint32 bphy_badplcp; /**< number of bad PLCP reception on BPHY rate */
uint32 phyovfl; /**< number of phy overflows */
uint32 rxf0ovfl; /**< number of rx fifo 0 overflows */
@@ -5606,13 +5825,13 @@
uint32 he_rxtrig_myaid; /**< number of rx'd valid trigger frame with myaid */
uint32 he_rxtrig_rand; /**< number of rx'd valid trigger frame with random aid */
uint32 he_rxtrig_basic; /**< number of rx'd of basic trigger frame */
- uint32 he_rxtrig_bfm_cnt; /**< number of rx'd trigger frame with bfm? */
+ uint32 he_rxtrig_bfm_cnt; /**< number of rx'd trigger frame with bfm */
uint32 he_rxtrig_mubar; /**< number of rx'd MUBAR trigger frame variant */
uint32 he_rxtrig_murts; /**< number of rx'd MU-RTS trigger frame variant */
uint32 he_rxtrig_bsrp; /**< number of rx'd of BSR poll trigger frame variant */
uint32 he_rxtrig_gcrmubar; /**< number of rx'd gcr mu bar trigger frame variant? */
uint32 he_rxtrig_bqrp; /**< number of rx'd bqrp trigger frame variant? */
- uint32 he_rxtrig_ndp_nbit; /**< Todo: check on functionality */
+ uint32 he_rxtrig_nfrp; /**< Todo: check on functionality */
uint32 he_rxtrig_basic_htpack; /**< triggers received with HTP ack policy */
uint32 he_cs_req_tx_cancel; /**< tx cancelled due to trigger rx or ch sw? */
uint32 he_rxtrig_rngpoll; /**< todo: check functionality */
@@ -5648,6 +5867,256 @@
wl_cnt_ge88mcst_tx_v1_t cnt[];
} wl_macst_tx_ge88mcst_v1_t;
+/* Rev Ge88 TX specific macstats - version 2 */
+typedef struct {
+ uint32 txallfrm; /**< num of frames sent, incl. Data, ACK, RTS, CTS,
+ * Control Management (includes retransmissions)
+ */
+ uint32 txrtsfrm; /**< number of RTS sent out by the MAC */
+ uint32 txctsfrm; /**< number of CTS sent out by the MAC */
+ uint32 txackfrm; /**< number of ACK frames sent out */
+ uint32 txback; /**< blockack txcnt */
+ uint32 he_txmtid_back; /**< number of mtid BAs */
+ uint32 txdnlfrm; /**< number of Null-Data tx from template */
+ uint32 txbcnfrm; /**< beacons transmitted */
+ uint32 txndpa; /**< Number of TX NDPAs */
+ uint32 txndp; /**< Number of TX NDPs */
+ uint32 txbfm; /**< Number of TX Bfm cnt */
+ uint32 txcwrts; /**< Number of tx cw rts */
+ uint32 txcwcts; /**< Number of tx cw cts */
+ uint32 txbfpoll; /**< Number of tx bfpolls */
+ uint32 txfbw; /**< transmit at fallback bw (dynamic bw) */
+ uint32 txampdu; /**< number of AMPDUs transmitted */
+ uint32 he_txmampdu; /**< Number of tx m-ampdus */
+ uint32 txucast; /**< # of ucast tx expecting resp (not cts/cwcts) */
+ uint32 he_txfrag; /**< Number of tx frags */
+ uint32 he_txtbppdu; /**< increments on transmission of every TB PPDU */
+ uint32 he_txtbppdu_ack; /**< Number of tx HE TBPPDU acks */
+ uint32 txinrtstxop; /**< number of data frame tx during rts txop */
+ uint32 null_txsts_empty; /**< Number empty null-txstatus' */
+ uint32 he_ulmu_disable; /**< # of ULMU disables handled in ucode */
+ uint32 he_ulmu_data_disable; /**< number of UL MU data disable scenarios
+ * handled in ucode
+ */
+ uint32 he_rxtrig_suppr_null_tbppdu; /**< count of null frame sent because of
+ * suppression scenarios
+ */
+ uint32 he_null_zero_agg; /**< nullAMPDU's transmitted in response to
+ * basic trigger because of zero aggregation
+ */
+ uint32 he_null_tbppdu; /**< null TBPPDU's sent as a response to
+ * basic trigger frame
+ */
+ uint32 he_null_bsrp_rsp; /**< null AMPDU's txed in response to BSR poll */
+ uint32 he_null_fifo_empty; /**< null AMPDU's in response to basic trigger
+ * because of no frames in fifo's
+ */
+ uint32 txrtsfail; /**< # of rts TX fails that reach retry limit */
+ uint32 txcgprsfail; /**< Tx Probe Response Fail.
+ * AP sent probe response but did not get ACK.
+ */
+ uint32 bcntxcancl; /**< TX bcns canceled due to rx of beacon (IBSS) */
+ uint32 txtplunfl; /**< Template unfl
+ * (mac too slow to tx ACK/CTS or BCN)
+ */
+ uint32 txphyerror; /**< TX phyerr - reported in txs for
+ * driver queued frames
+ */
+ uint32 txshmunfl_cnt; /**< TX SHM unfl cnt */
+ uint32 txfunfl[11]; /**< per-fifo tx underflows */
+ uint32 txfmlunfl[9]; /**< ML fifos underflow cnts */
+ uint32 bferpt_inv_cfg; /**< Invalid bfe report cfg */
+ uint32 bferpt_drop_cnt1; /**< bfe rpt drop cnt 1 */
+ uint32 bferpt_drop_cnt2; /**< bfe rpt drop cnt 2 */
+ uint32 bferot_txcrs_high; /**< bfe rpt tx crs high */
+ uint32 txbfm_errcnt; /**< TX bfm error cnt */
+ uint32 tx_murts_cnt; /**< Tx MURTS Count */
+ uint32 tx_noavail_cnt; /**< Tx Not avail Count */
+ uint32 tx_null_link_pref; /**< Null Link Pref */
+ uint32 btcx_rfact_ctr_l; /**< btcx rxfact counter low */
+ uint32 btcx_rfact_ctr_h; /**< btcx rxfact counter high */
+ uint32 btcx_txconf_ctr_l; /**< btcx txconf counter low */
+ uint32 btcx_txconf_ctr_h; /**< btcx txconf counter high */
+ uint32 btcx_txconf_dur_ctr_l; /**< btcx txconf duration counter low */
+ uint32 btcx_txconf_dur_ctr_h; /**< btcx txconf duration counter high */
+ uint32 txcgprssuc; /**< Tx Probe Response succ cnt */
+ uint32 txsf; /**< # of Tx'd SF */
+ uint32 macsusp_cnt; /**< # of macsuspends */
+ uint32 prs_timeout; /**< # of pre wds */
+ uint32 emlsr_tx_nosrt; /**< # of no TX starts for eMLSR */
+ uint32 rts_to_self_cnt; /**< # of RTS to self */
+ uint32 saqm_sendfrm_agg_cnt; /**< # SAQM Send frame aggregation */
+} wl_cnt_ge88mcst_tx_v2_t;
+
+/* Rev Ge88 RX specific macstats - version 2 */
+typedef struct {
+ uint32 rxstrt; /**< Number of received frames with a good PLCP
+ * (i.e. passing parity check)
+ */
+ uint32 rx20s_cnt; /**< Increments if RXFrame does not include primary 20 */
+ uint32 C_SECRSSI0; /**< SEC RSSI0 info */
+ uint32 C_SECRSSI1; /**< SEC RSSI1 info */
+ uint32 C_SECRSSI2; /**< SEC RSSI2 info */
+ uint32 C_CCA_RXPRI_LO; /**< SEC RXPRI Low */
+ uint32 C_CCA_RXPRI_HI; /**< SEC RXPRI High */
+ uint32 C_CCA_RXSEC20_LO; /**< SEC CCA RX 20mhz low */
+ uint32 C_CCA_RXSEC20_HI; /**< SEC CCA RX 20mhz high */
+ uint32 C_CCA_RXSEC40_LO; /**< SEC CCA RX 40mhz low */
+ uint32 C_CCA_RXSEC40_HI; /**< SEC CCA RX 40mhz high */
+ uint32 C_CCA_RXSEC80_LO; /**< SEC CCA RX 80mhz low */
+ uint32 C_CCA_RXSEC80_HI; /**< SEC CCA RX 80mhz high */
+ uint32 rxctlmcast; /**< # of RX ctrl mcast frames */
+ uint32 rxmgmcast; /**< # of rx'd Management mcast frames */
+ uint32 rxbeaconmbss; /**< beacons rx'd from member of BSS */
+ uint32 rxndpa_m; /**< number of RX NDPA Multicast */
+ uint32 rxrtsucast; /**< # of ucast RTS (good FCS) */
+ uint32 rxctsucast; /**< # of ucast CTS (good FCS) */
+ uint32 rxctlucast; /**< # of rx'd CNTRL frames (good FCS & matching RA) */
+ uint32 rxmgucastmbss; /**< # of rx'd mgmt frames (good FCS & matching RA) */
+ uint32 rxackucast; /**< number of ucast ACKS received (good FCS) */
+ uint32 rxndpa_u; /**< number of unicast RX NDPAs */
+ uint32 rxsf; /**< number of rxsfucast */
+ uint32 rxcwrts; /**< number of rx'd cw ucast rts */
+ uint32 rxcwcts; /**< number of rx'd cw ucast cts */
+ uint32 rxbfpoll; /**< number of rx'd BF ucast poll */
+ uint32 rxmgocast; /**< # of rx'd MGMT frames (good FCS & not matching RA) */
+ uint32 rxctlocast; /**< # of rx'd CNTRL frame (good FCS & not matching RA) */
+ uint32 rxrtsocast; /**< # of rx'd RTS not addressed */
+ uint32 rxctsocast; /**< # of rx'd CTS not addressed */
+ uint32 rxbeaconobss; /* beacons rx'd from other BSS */
+ uint32 he_rx_ppdu_cnt; /**< rx'd HE PPDU cnt */
+ uint32 he_rxstrt_hesuppdu_cnt; /**< rx'd HE su PPDU cnt */
+ uint32 he_rxstrt_hesureppdu_cnt; /**< rx'd HE SU RE PPDU cnt */
+ uint32 he_rxtsrt_hemuppdu_cnt; /**< rx'd HE MU PPDU cnt */
+ uint32 rxbar; /**< number of rx'd BARs */
+ uint32 rxback; /**< number of rx'd BARs */
+ uint32 he_rxmtid_back; /**< number of rx'd HE RX MultiTID BAs */
+ uint32 he_rxmsta_back; /**< number of rx'd HE RX MultiSTA BAs */
+ uint32 bferpt; /**< number of rx'd BFE report ready cnts */
+ uint32 he_colormiss_cnt; /**< HE BSS color mismatch counts cnts */
+ uint32 he_rxdefrag; /**< number of rx'd HE dynamic fragmented pkts */
+ uint32 he_rxdlmu; /**< number of rx'd DL MU frames */
+ uint32 rxcgprqfrm; /**< number of received Probe requests that made it into
+ * the PRQ fifo
+ */
+ uint32 rx_fp_shm_corrupt_cnt; /**< SHM corrupt count */
+ uint32 PAD[18]; /**< PAD Gap */
+ uint32 rxbadplcp; /**< parity check of the PLCP header failed */
+ uint32 rxcrsglitch; /**< PHY able to correlate the plcp but not the hdr */
+ uint32 rxfrmtoolong; /**< rx'd frame longer than legal limit (2346 bytes) */
+ uint32 rxfrmtooshrt; /**< rx'd frame not enough bytes for ft */
+ uint32 rxnodelim; /**< # of not valid delim -> ampdu parser */
+ uint32 rxbad_ampdu; /**< number of rx'd bad ampdus */
+ uint32 rxcgprsqovfl; /**< Rx Probe Request Que overflow in the AP */
+ uint32 bphy_rxcrsglitch; /**< PHY count of bphy glitches */
+ uint32 rxdrop20s; /**< drop secondary cnt */
+ uint32 rxtoolate; /**< receive too late */
+ uint32 m_pfifo_drop; /**< # of pfifo dropped frames */
+ uint32 bphy_badplcp; /**< number of bad PLCP reception on BPHY rate */
+ uint32 phyovfl; /**< number of phy overflows */
+ uint32 rxf0ovfl; /**< number of rx fifo 0 overflows */
+ uint32 rxf1ovfl; /**< number of rx fifo 1 overflows */
+ uint32 lenfovfl; /**< number of length overflows */
+ uint32 weppeof; /**< number of weppeof */
+ uint32 badplcp; /**< parity check of the PLCP header failed */
+ uint32 stsfifofull; /**< status fifo full */
+ uint32 stsfifoerr; /**< status fifo error */
+ uint32 ctx_fifo_full; /**< fw not draining frames fast enough */
+ uint32 ctx_fifo2_full; /**< fw not draining frames fast enough */
+ uint32 missbcn_dbg; /**< number of beacon missed to receive */
+ uint32 rxrsptmout; /**< number of response timeouts for tx'd frames */
+ uint32 laterx_cnt; /**< ucode sees frame 30us late */
+ uint32 bcn_drop_cnt; /**< number of BCNs dropped in ucode */
+ uint32 bfr_timeout; /**< number of bfr timeouts */
+ uint32 rxgaininfo_ant0; /**< ANT-0 phy RX gain info - main? */
+ uint32 rxauxgaininfo_ant0; /**< ANT-0 phy RX gain info - aux */
+ uint32 he_rxtrig_myaid; /**< number of rx'd valid trigger frame with myaid */
+ uint32 he_rxtrig_rand; /**< number of rx'd valid trigger frame with random aid */
+ uint32 he_rxtrig_basic; /**< number of rx'd of basic trigger frame */
+ uint32 he_rxtrig_bfm_cnt; /**< number of rx'd trigger frame with bfm */
+ uint32 he_rxtrig_mubar; /**< number of rx'd MUBAR trigger frame variant */
+ uint32 he_rxtrig_murts; /**< number of rx'd MU-RTS trigger frame variant */
+ uint32 he_rxtrig_bsrp; /**< number of rx'd of BSR poll trigger frame variant */
+ uint32 he_rxtrig_gcrmubar; /**< number of rx'd gcr mu bar trigger frame variant? */
+ uint32 he_rxtrig_bqrp; /**< number of rx'd bqrp trigger frame variant? */
+ uint32 he_rxtrig_nfrp; /**< Todo: check on functionality */
+ uint32 he_rxtrig_basic_htpack; /**< triggers received with HTP ack policy */
+ uint32 he_cs_req_tx_cancel; /**< tx cancelled due to trigger rx or ch sw? */
+ uint32 he_rxtrig_rngpoll; /**< todo: check functionality */
+ uint32 he_rxtrig_rngsnd; /**< todo: check functionality */
+ uint32 he_rxtrig_rngssnd; /**< todo: check functionality */
+ uint32 he_rxtrig_rngrpt; /**< todo: check functionality */
+ uint32 he_rxtrig_rngpasv; /**< todo: check functionality */
+ uint32 he_rxtrig_ru_2x996T; /**< Rx'd trigger frame with STA RU index 160mhz */
+ uint32 he_rxtrig_invalid_ru; /**< Rx'd trigger frame with invalid STA20 RU index */
+ uint32 he_rxtrig_inv_ru_cnt; /**< # of Rx'd trigger frames with invalid RU cnt */
+ uint32 he_rxtrig_drop_cnt; /**< # of trigger frames dropped */
+ uint32 ndp_fail_cnt; /**< # of NDP fails */
+ uint32 rxfrmtoolong2_cnt; /**< # of Rx'd too long pkts */
+ uint32 hwaci_status; /**< HW ACI status */
+ uint32 pmqovfl; /**< number of PMQ overflows */
+ uint32 sctrg_rxcrs_drop_cnt; /**< Number of scan trigger dropped due to rxcrs */
+ uint32 inv_punc_usig_cnt; /**< Number of invalid punctured USIG */
+ uint32 sctrg_drop_cnt; /**< Number of scan trigger drop */
+} wl_cnt_ge88mcst_rx_v2_t;
+
+/* Rev GE88 per ML link supportive wl counters (macstats) - version 1 */
+typedef struct wl_macst_rx_ge88mcst_v2 {
+ uint8 num_links; /* Number of per-link stats supported on slice */
+ uint8 pad[3];
+
+ /* Per ML Link RX macstats (esp. eMLSR) */
+ wl_cnt_ge88mcst_rx_v2_t cnt[];
+} wl_macst_rx_ge88mcst_v2_t;
+
+/* Rev GE88 per ML link supportive wl counters (macstats) - version 1 */
+typedef struct wl_macst_tx_ge88mcst_v2 {
+ uint8 num_links; /* Number of per-link stats supported on slice */
+ uint8 pad[3];
+
+ /* Per ML Link TX macstats (esp. eMLSR) */
+ wl_cnt_ge88mcst_tx_v2_t cnt[];
+} wl_macst_tx_ge88mcst_v2_t;
+
+/* Rev Ge88 TX 32 specific macstats - version 1 */
+typedef struct {
+ uint32 txmpdu; /**< number of MPDUs transmitted */
+ uint32 ctmode_ufc_cnt; /**< Number of UFCs with CT mode enabled */
+} wl_cnt_ge88mcst_tx_u32_v1_t;
+
+/* Rev Ge88 RX 32 specific macstats - version 1 */
+typedef struct {
+ uint32 rxdtucastmbss; /**< # of rx'd DATA frames (good FCS & matching RA) */
+ uint32 pktengrxducast; /**< number of rx'd good fcs ucast frames */
+ uint32 pktengrxdmcast; /**< number of rx'd good fcs mcast frames */
+ uint32 rxdtocast; /**< # of rx'd DATA frames (good FCS & not matching RA) */
+ uint32 rxdtucastobss; /**< number of unicast frames addressed to the MAC from
+ * other BSS (WDS FRAME)
+ */
+ uint32 goodfcs; /**< number of rx'd goodfcs cnts */
+ uint32 rxdtmcast; /**< # of rx'd Data mcast frames */
+ uint32 rxanyerr; /**< Any RX error that is not counted by other counters */
+ uint32 rxbadfcs; /**< # of frames with CRC check failed */
+} wl_cnt_ge88mcst_rx_u32_v1_t;
+
+/* Rev GE88 per ML link supportive wl counters (macstats) - version 1 */
+typedef struct wl_macst_rx_ge88mcst_u32 {
+ uint8 num_links; /* Number of per-link stats supported on slice */
+ uint8 pad[3];
+
+ /* Per ML Link RX macstats (esp. eMLSR) */
+ wl_cnt_ge88mcst_rx_u32_v1_t cnt[];
+} wl_macst_rx_ge88mcst_u32_v1_t;
+
+/* Rev GE88 per ML link supportive wl counters (macstats) - version 1 */
+typedef struct wl_macst_tx_ge88mcst_u32 {
+ uint8 num_links; /* Number of per-link stats supported on slice */
+ uint8 pad[3];
+
+ /* Per ML Link TX macstats (esp. eMLSR) */
+ wl_cnt_ge88mcst_tx_u32_v1_t cnt[];
+} wl_macst_tx_ge88mcst_u32_v1_t;
+
/** MACSTAT counters for ucode (corerev >= 80) */
typedef struct {
/* MAC counters: 32-bit version of d11.h's macstat_t */
@@ -5871,7 +6340,7 @@
} wl_cnt_v_le10_mcst_t;
#define MAX_RX_FIFO 3
-#define WL_RXFIFO_CNT_VERSION 1 /* current version of wl_rxfifo_cnt_t */
+#define WL_RXFIFO_CNT_VERSION_1 1 /* current version of wl_rxfifo_cnt_t */
typedef struct {
/* Counters for frames received from rx fifos */
uint16 version;
@@ -6785,8 +7254,8 @@
/* add another uint32 when full */
} wl_msglevel_v1_t;
-#define WL_ICMP_IPV6_CFG_VERSION 1
-#define WL_ICMP_IPV6_CLEAR_ALL (1 << 0)
+#define WL_ICMP_IPV6_CFG_VERSION_1 1u
+#define WL_ICMP_IPV6_CLEAR_ALL (1u << 0u)
typedef struct wl_icmp_ipv6_cfg {
uint16 version;
@@ -6818,12 +7287,7 @@
#define WL_MKEEP_ALIVE_PERIOD_MASK 0x7FFFFFFF
#define WL_MKEEP_ALIVE_IMMEDIATE 0x80000000
-#ifndef WL_MKEEP_ALIVE_TYPEDEF_HAS_ALIAS
-typedef wl_mkeep_alive_pkt_v1_t wl_mkeep_alive_pkt_t;
-#define WL_MKEEP_ALIVE_VERSION WL_MKEEP_ALIVE_VERSION_1
-#endif /* WL_MKEEP_ALIVE_TYPEDEF_HAS_ALIAS */
-
-#define WL_MKEEP_ALIVE_FIXED_LEN OFFSETOF(wl_mkeep_alive_pkt_t, data)
+#define WL_MKEEP_ALIVE_FIXED_LEN OFFSETOF(wl_mkeep_alive_pkt_v1_t, data)
typedef struct wl_mkeep_alive_pkt_v2 {
uint16 version; /* Version for mkeep_alive */
@@ -6905,7 +7369,7 @@
/* #ifdef WLBA */
-#define WLC_BA_CNT_VERSION 1 /**< current version of wlc_ba_cnt_t */
+#define WLC_BA_CNT_VERSION_1 1 /**< current version of wlc_ba_cnt_t */
/** block ack related stats */
typedef struct wlc_ba_cnt {
@@ -6952,7 +7416,6 @@
/** Support for ampdu_tx_ba_window_cfg */
#define WL_AMPDU_TX_BA_WINDOW_CFG_VER_1 1u
-#define WL_AMPDU_TX_BA_WINDOW_CFG_CUR_VER WL_AMPDU_TX_BA_WINDOW_CFG_VER_1
/* 16 bits Config (5 bits reserved) and Status (2 bits reserved) */
#define WL_AMPDU_TX_BA_WINDOW_CFG_BA_WSIZE_IDX 0u
@@ -7239,6 +7702,7 @@
#define ENABLE_NET_OFFLOAD_BIT 10
/** report found/lost events for SSID and BSSID networks seperately */
#define REPORT_SEPERATELY_BIT 11
+#define PFN_FULL_SCAN_RESULT_BIT 12
#define SORT_CRITERIA_MASK 0x0001
#define AUTO_NET_SWITCH_MASK 0x0002
@@ -7253,6 +7717,7 @@
#define ENABLE_NET_OFFLOAD_MASK 0x0400
/** report found/lost events for SSID and BSSID networks seperately */
#define REPORT_SEPERATELY_MASK 0x0800
+#define PFNFULLSCAN_RESULT_MASK 0x1000
#define PFN_COMPLETE 1
#define PFN_INCOMPLETE 0
@@ -7444,7 +7909,7 @@
int8 rssi[PFN_SWC_RSSI_WINDOW_MAX];
} wl_pfn_significant_net_t;
-#define PFN_SWC_SCANRESULT_VERSION 1
+#define PFN_SWC_SCANRESULT_VERSION_1 1
typedef struct wl_pfn_swc_results {
uint32 version;
@@ -7484,11 +7949,6 @@
wl_pfn_net_info_bssid_v3_t netinfo[BCM_FLEX_ARRAY];
} wl_pfn_scanhist_bssid_v3_t;
-#ifndef WL_PFN_NET_INFO_BSSID_TYPEDEF_HAS_ALIAS
-typedef wl_pfn_net_info_bssid_v1_t wl_pfn_net_info_bssid_t;
-typedef wl_pfn_scanhist_bssid_v1_t wl_pfn_scanhist_bssid_t;
-#endif /* WL_PFN_NET_INFO_BSSID_TYPEDEF_HAS_ALIAS */
-
/* Version 1 and 2 for various single scan result */
#define PFN_SCANRESULT_VERSION_V1 1
#define PFN_SCANRESULT_VERSION_V2 2
@@ -7591,11 +8051,6 @@
/* interleaved with HP PNO scan */
} wl_pfn_param_v3_t;
-#ifndef PFN_PARAM_HAS_ALIAS
-typedef wl_pfn_param_v2_t wl_pfn_param_t;
-#define PFN_VERSION PFN_VERSION_V2
-#endif
-
typedef struct wl_pfn_bssid {
struct ether_addr macaddr;
/* Bit4: suppress_lost, Bit3: suppress_found */
@@ -7681,7 +8136,7 @@
#define GSCAN_SEND_ALL_RESULTS_MASK (1 << 0)
#define GSCAN_ALL_BUCKETS_IN_FIRST_SCAN_MASK (1 << 3)
#define GSCAN_CFG_FLAGS_ONLY_MASK (1 << 7)
-#define WL_GSCAN_CFG_VERSION 1
+#define WL_GSCAN_CFG_VERSION_1 1
typedef struct wl_pfn_gscan_cfg {
uint16 version;
/**
@@ -7730,7 +8185,7 @@
wl_pfn_t pfn[BCM_FLEX_ARRAY];
} wl_pfn_list_t;
-#define PFN_SSID_EXT_VERSION 1
+#define PFN_SSID_EXT_VERSION_1 1
typedef struct wl_pfn_ext {
uint8 flags;
@@ -7780,7 +8235,7 @@
/* Dynamic scan configuration for motion profiles */
-#define WL_PFN_MPF_VERSION 1
+#define WL_PFN_MPF_VERSION_1 1
/* Valid group IDs, may be expanded in the future */
#define WL_PFN_MPF_GROUP_SSID 0
@@ -7830,9 +8285,9 @@
* Definitions for base MPF configuration
*/
-#define WL_MPF_VERSION 1
-#define WL_MPF_MAX_BITS 3
-#define WL_MPF_MAX_STATES (1 << WL_MPF_MAX_BITS)
+#define WL_MPF_VERSION_1 1
+#define WL_MPF_MAX_BITS 3
+#define WL_MPF_MAX_STATES (1 << WL_MPF_MAX_BITS)
#define WL_MPF_STATE_NAME_MAX 12
@@ -7920,10 +8375,11 @@
uint8 flags;
uint16 social_channels[BCM_FLEX_ARRAY]; /**< Variable length array of social channels */
} wl_p2po_find_config_t;
-#define WL_P2PO_FIND_CONFIG_VERSION 2 /**< value for version field */
+
+#define WL_P2PO_FIND_CONFIG_VERSION_2 2u /**< value for version field */
/** wl_p2po_find_config_t flags */
-#define P2PO_FIND_FLAG_SCAN_ALL_APS 0x01 /**< Whether to scan for all APs in the p2po_find
+#define P2PO_FIND_FLAG_SCAN_ALL_APS 0x01u /**< Whether to scan for all APs in the p2po_find
* periodic scans of all channels.
* 0 means scan for only P2P devices.
* 1 means scan for P2P devices plus non-P2P APs.
@@ -8036,11 +8492,6 @@
wl_anqpo_peer_v3_t peer[]; /**< max ANQPO_MAX_PEER_LIST */
} wl_anqpo_peer_list_v3_t;
-#ifndef WL_ANQPO_PEER_LIST_TYPEDEF_HAS_ALIAS
-typedef wl_anqpo_peer_list_v1_t wl_anqpo_peer_list_t;
-typedef wl_anqpo_peer_v1_t wl_anqpo_peer_t;
-#endif /* WL_ANQPO_PEER_LIST_TYPEDEF_HAS_ALIAS */
-
#define ANQPO_MAX_IGNORE_SSID 64
typedef struct {
uint8 is_clear; /**< set to clear list (not used on GET) */
@@ -8475,7 +8926,7 @@
};
/* IOVAR pkteng_sweep_counters response structure */
-#define WL_PKTENG_SWEEP_COUNTERS_VERSION 1
+#define WL_PKTENG_SWEEP_COUNTERS_VERSION_1 1
typedef struct wl_pkteng_sweep_ctrs {
uint16 version; /**< Version - 1 */
uint16 size; /**< Complete Size including sweep_counters */
@@ -8485,7 +8936,7 @@
} wl_pkteng_sweep_ctrs_t;
/* IOVAR pkteng_rx_pkt response structure */
-#define WL_PKTENG_RX_PKT_VERSION 1
+#define WL_PKTENG_RX_PKT_VERSION_1 1
typedef struct wl_pkteng_rx_pkt {
uint16 version; /**< Version - 1 */
uint16 size; /**< Complete Size including the packet */
@@ -8630,10 +9081,6 @@
int32 rssi_per_core_qdb[WL_RSSI_ANT_MAX];
} wl_pkteng_stats_v2_t;
-#ifndef WL_PKTENG_STATS_TYPEDEF_HAS_ALIAS
-typedef wl_pkteng_stats_v1_t wl_pkteng_stats_t;
-#endif /* WL_PKTENG_STATS_TYPEDEF_HAS_ALIAS */
-
typedef struct wl_txcal_params {
wl_pkteng_t pkteng;
uint8 gidx_start;
@@ -8774,7 +9221,7 @@
int8 PAD[3];
} wl_rssi_event_t;
-#define RSSI_MONITOR_VERSION 1
+#define RSSI_MONITOR_VERSION_1 1
#define RSSI_MONITOR_STOP (1 << 0)
typedef struct wl_rssi_monitor_cfg {
uint8 version;
@@ -9166,6 +9613,46 @@
uint32 count;
} pcie_bus_tput_stats_t;
+/* limits of dma length */
+#define DMA_LEN_MAX (65527u)
+#define DMA_LEN_MIN (8u)
+
+/* direction of DMA */
+#define BUS_TPUT_PARAMS_FLAG_DIR_H2D 0x0u
+#define BUS_TPUT_PARAMS_FLAG_DIR_D2H 0x1u
+
+#define BUS_TPUT_PARAMS_VERSION_1 (1u)
+#include <packed_section_start.h>
+BWL_PRE_PACKED_STRUCT struct bus_tput_params_v1 {
+ uint16 ver; /**<version */
+ uint16 len; /**<length */
+ uint32 flags; /**< param flags */
+ uint16 dma_descriptors; /**<total # of dma descs to be programmed by f/w */
+ uint16 host_buf_len; /**< length of host buffer */
+ uint32 host_buf_addr_lo; /**< physical address for bus_throughput_buf_lo */
+ uint32 host_buf_addr_hi; /**< physical address for bus_throughput_buf_hi */
+} BWL_POST_PACKED_STRUCT;
+#include <packed_section_end.h>
+
+/* direction of DMA */
+#define BUS_TPUT_STATS_FLAG_DIR_H2D 0x0u
+#define BUS_TPUT_STATS_FLAG_DIR_D2H 0x1u
+
+/* after stats, if buf is available with string to print */
+#define BUS_TPUT_STATS_FLAG_BUF_PRINT 0x2u
+
+#define BUS_TPUT_STATS_VERSION_1 (1u)
+#include <packed_section_start.h>
+BWL_PRE_PACKED_STRUCT struct bus_tput_stats_v1 {
+ uint16 ver; /**<version */
+ uint16 len; /**<length */
+ uint32 time_taken; /**< no of usecs the test is run */
+ uint16 count; /**< no of dma desc transferred */
+ uint16 nbytes_per_descriptor; /**< no of bytes of data dma ed per descriptor */
+ uint32 flags; /**< stats flags */
+} BWL_POST_PACKED_STRUCT;
+#include <packed_section_end.h>
+
#define HOST_WAKEUP_DATA_VER 1
#include <packed_section_start.h>
/* Bus interface host wakeup data */
@@ -9198,14 +9685,14 @@
#define PM_IGNORE_BCMC_ALL_DMS_ACCEPTED (1 << 1)
/* ##### HMAP section ##### */
-#define PCIE_MAX_HMAP_WINDOWS 8
-#define PCIE_HMAPTEST_VERSION 2
+#define PCIE_MAX_HMAP_WINDOWS 8u
+#define PCIE_HMAPTEST_VERSION_2 2u
#define HMAPTEST_INVALID_OFFSET 0xFFFFFFFFu
#define HMAPTEST_DEFAULT_WRITE_PATTERN 0xBABECAFEu
-#define HMAPTEST_ACCESS_ARM 0
-#define HMAPTEST_ACCESS_M2M 1
-#define HMAPTEST_ACCESS_D11 2
-#define HMAPTEST_ACCESS_NONE 3
+#define HMAPTEST_ACCESS_ARM 0u
+#define HMAPTEST_ACCESS_M2M 1u
+#define HMAPTEST_ACCESS_D11 2u
+#define HMAPTEST_ACCESS_NONE 3u
typedef struct pcie_hmaptest {
uint16 version; /* Version */
@@ -9228,7 +9715,7 @@
uint32 windowlength; /* Window Length */
} hmapwindow_t;
-#define PCIE_HMAP_VERSION 1
+#define PCIE_HMAP_VERSION_1 1u
typedef struct pcie_hmap {
uint16 version; /**< Version */
uint16 length; /**< Length of entire structure */
@@ -9676,6 +10163,24 @@
pcie_bus_metrics_t pcie; /**< stats from pcie bus driver */
} wl_pwr_pcie_stats_t;
+typedef struct scan_data_ext_v1 {
+ uint32 count; /**< Number of scans performed */
+ uint32 dur; /**< Total time (in us) used */
+ uint32 off_chan_dur; /**< Total time excluding home channel time */
+} scan_data_ext_v1_t;
+
+typedef struct wl_pwr_scan_stats_ext_v1 {
+ uint16 type; /**< WL_PWRSTATS_TYPE_SCAN_EXT */
+ uint16 len; /**< Up to 4K-1, top 4 bits are reserved */
+
+ /* Scan history */
+ scan_data_ext_v1_t user_scans; /**< User-requested scans: (i/e/p)scan */
+ scan_data_ext_v1_t assoc_scans; /**< Scans initiated by association requests */
+ scan_data_ext_v1_t roam_scans; /**< Scans initiated by the roam engine */
+ scan_data_ext_v1_t pno_scans[8]; /**< For future PNO bucketing (BSSID, SSID, etc) */
+ scan_data_ext_v1_t other_scans; /**< Scan engine usage not assigned to the above */
+} wl_pwr_scan_stats_ext_v1_t;
+
/** Scan information history per category */
typedef struct scan_data {
uint32 count; /**< Number of scans performed */
@@ -9683,19 +10188,19 @@
} scan_data_t;
typedef struct wl_pwr_scan_stats {
- uint16 type; /**< WL_PWRSTATS_TYPE_SCAN */
- uint16 len; /**< Up to 4K-1, top 4 bits are reserved */
+ uint16 type; /**< WL_PWRSTATS_TYPE_SCAN */
+ uint16 len; /**< Up to 4K-1, top 4 bits are reserved */
/* Scan history */
- scan_data_t user_scans; /**< User-requested scans: (i/e/p)scan */
- scan_data_t assoc_scans; /**< Scans initiated by association requests */
- scan_data_t roam_scans; /**< Scans initiated by the roam engine */
- scan_data_t pno_scans[8]; /**< For future PNO bucketing (BSSID, SSID, etc) */
- scan_data_t other_scans; /**< Scan engine usage not assigned to the above */
+ scan_data_t user_scans; /**< User-requested scans: (i/e/p)scan */
+ scan_data_t assoc_scans; /**< Scans initiated by association requests */
+ scan_data_t roam_scans; /**< Scans initiated by the roam engine */
+ scan_data_t pno_scans[8]; /**< For future PNO bucketing (BSSID, SSID, etc) */
+ scan_data_t other_scans; /**< Scan engine usage not assigned to the above */
} wl_pwr_scan_stats_t;
typedef struct wl_pwr_connect_stats {
- uint16 type; /**< WL_PWRSTATS_TYPE_SCAN */
+ uint16 type; /**< WL_PWRSTATS_TYPE_CONNECTION */
uint16 len; /**< Up to 4K-1, top 4 bits are reserved */
/* Connection (Association + Key exchange) data */
@@ -9808,6 +10313,18 @@
uint32 total_enable_dur; /* time(ms) psbw remains enabled total */
} wl_pwr_psbw_stats_t;
+typedef struct wl_pwr_scan_6E_stats {
+ uint16 type; /* WL_PWRSTATS_TYPE_SCAN_6E */
+ uint16 len; /* total length includes fixed fields */
+ uint32 rx_upr_processed; /* total unsolicited probe responses processed */
+ uint32 rx_upr_ignored; /* total unsolicited probe responses ignored */
+
+ uint32 rx_fils_processed; /* total FILS processed */
+ uint32 rx_fils_ignored; /* total FILS ignored */
+
+ uint32 referred_6g_scans; /* Referred scans to 6G channels due to RNR */
+} wl_pwr_scan_6E_stats_t;
+
/* ##### End of Power Stats section ##### */
/** IPV4 Arp offloads for ndis context */
@@ -9850,7 +10367,7 @@
#define MIN_PM_ALERT_LEN 9
/** Data sent in EXCESS_PM_WAKE event */
-#define WL_PM_ALERT_VERSION 3
+#define WL_PM_ALERT_VERSION_3 3
/** This structure is for version 3; version 2 will be deprecated in by FW */
#include <packed_section_start.h>
@@ -10248,7 +10765,8 @@
/* TLV ID for curpower report, ID <= 63 is reserved for ppr module */
typedef enum tx_pwr_tlv_id {
TX_PWR_RPT_RU_RATE_INFO_ID = 64u,
- TX_PWR_RPT_RUPDOFFSET_ID = 65u
+ TX_PWR_RPT_RUPDOFFSET_ID = 65u,
+ TX_PWR_RPT_DEV_CAT_ID = 66u
} tx_pwr_tlv_id_t;
#include <packed_section_start.h>
@@ -10267,7 +10785,7 @@
#define MAX_IBSS_ROUTE_TBL_ENTRY 64
-#define TXPWR_TARGET_VERSION 0
+#define TXPWR_TARGET_VERSION_0 0
#include <packed_section_start.h>
typedef BWL_PRE_PACKED_STRUCT struct {
int32 version; /**< version number */
@@ -10277,7 +10795,7 @@
} BWL_POST_PACKED_STRUCT txpwr_target_max_t;
#include <packed_section_end.h>
-#define BSS_PEER_INFO_PARAM_CUR_VER 0
+#define BSS_PEER_INFO_PARAM_VER_0 0u
/** Input structure for IOV_BSS_PEER_INFO */
#include <packed_section_start.h>
typedef BWL_PRE_PACKED_STRUCT struct {
@@ -10286,7 +10804,7 @@
} BWL_POST_PACKED_STRUCT bss_peer_info_param_t;
#include <packed_section_end.h>
-#define BSS_PEER_INFO_CUR_VER 0
+#define BSS_PEER_INFO_VER_0 0u
#include <packed_section_start.h>
typedef BWL_PRE_PACKED_STRUCT struct {
@@ -10300,7 +10818,7 @@
} BWL_POST_PACKED_STRUCT bss_peer_info_t;
#include <packed_section_end.h>
-#define BSS_PEER_LIST_INFO_CUR_VER 0
+#define BSS_PEER_LIST_INFO_VER_0 0u
#include <packed_section_start.h>
typedef BWL_PRE_PACKED_STRUCT struct {
@@ -10313,7 +10831,7 @@
#define BSS_PEER_LIST_INFO_FIXED_LEN OFFSETOF(bss_peer_list_info_t, peer_info)
-#define AIBSS_BCN_FORCE_CONFIG_VER_0 0
+#define AIBSS_BCN_FORCE_CONFIG_VER_0 0u
/** structure used to configure AIBSS beacon force xmit */
#include <packed_section_start.h>
@@ -10326,9 +10844,8 @@
} BWL_POST_PACKED_STRUCT aibss_bcn_force_config_t;
#include <packed_section_end.h>
-#define AIBSS_TXFAIL_CONFIG_VER_0 0
-#define AIBSS_TXFAIL_CONFIG_VER_1 1
-#define AIBSS_TXFAIL_CONFIG_CUR_VER AIBSS_TXFAIL_CONFIG_VER_1
+#define AIBSS_TXFAIL_CONFIG_VER_0 0u
+#define AIBSS_TXFAIL_CONFIG_VER_1 1u
/** structure used to configure aibss tx fail event */
#include <packed_section_start.h>
@@ -10368,6 +10885,110 @@
/* Version of wlc_btc_stats_t structure.
* Increment whenever a change is made to wlc_btc_stats_t
*/
+#define BTCX_STATS_VER_9 9
+typedef struct wlc_btc_stats_v9 {
+ uint16 version; /* version number of struct */
+ uint16 valid; /* Size of this struct */
+ uint32 stats_update_timestamp; /* tStamp when data is updated. */
+ uint32 btc_status; /* Hybrid/TDM indicator: Bit2:Hybrid, Bit1:TDM,Bit0:CoexEnabled */
+ uint32 bt_req_type_map; /* BT Antenna Req types since last stats sample */
+ uint32 bt_req_cnt; /* #BT antenna requests since last stats sampl */
+ uint32 bt_gnt_cnt; /* #BT antenna grants since last stats sample */
+ uint32 bt_gnt_dur; /* usec BT owns antenna since last stats sample */
+ uint16 bt_abort_cnt; /* #Times WL was preempted due to BT since WL up */
+ uint16 bt_rxf1ovfl_cnt; /* #Time PSNULL retry count exceeded since WL up */
+ uint16 bt_latency_cnt; /* #Time ucode high latency detected since WL up */
+ uint16 bt_pm_attempt_cnt; /* PM protection attempts */
+ uint16 bt_succ_pm_protect_cnt; /* successful PM protection */
+ uint16 bt_succ_cts_cnt; /* successful CTS2A protection */
+ uint16 bt_wlan_tx_preempt_cnt; /* WLAN TX Preemption */
+ uint16 bt_wlan_rx_preempt_cnt; /* WLAN RX Preemption */
+ uint16 bt_ap_tx_after_pm_cnt; /* AP TX even after PM protection */
+ uint16 bt_peraud_cumu_gnt_cnt; /* Grant cnt for periodic audio */
+ uint16 bt_peraud_cumu_deny_cnt; /* Deny cnt for periodic audio */
+ uint16 bt_a2dp_cumu_gnt_cnt; /* Grant cnt for A2DP */
+ uint16 bt_a2dp_cumu_deny_cnt; /* Deny cnt for A2DP */
+ uint16 bt_sniff_cumu_gnt_cnt; /* Grant cnt for Sniff */
+ uint16 bt_sniff_cumu_deny_cnt; /* Deny cnt for Sniff */
+ uint16 bt_crtpri_cnt; /* Ant grant by critical BT task */
+ uint16 bt_pri_cnt; /* Ant grant by high BT task */
+ uint16 antgrant_lt10ms; /* Ant grant duration cnt 0~10ms */
+ uint16 antgrant_lt30ms; /* Ant grant duration cnt 10~30ms */
+ uint16 antgrant_lt60ms; /* Ant grant duration cnt 30~60ms */
+ uint16 antgrant_ge60ms; /* Ant grant duration cnt 60~ms */
+ uint16 ap_leakiness; /* AP leakines, ms */
+ uint8 rr_cnt; /* WLAN rate recovery count */
+ uint8 rr_succ_cnt; /* WLAN successful rate recovery count */
+ uint8 slice_index; /* Slice to report */
+ uint8 PAD; /* Padding */
+} wlc_btc_stats_v9_t;
+
+#define BTCX_STATS_VER_8 8
+typedef struct wlc_btc_stats_v8 {
+ uint16 version; /* version number of struct */
+ uint16 valid; /* Size of this struct */
+ uint32 stats_update_timestamp; /* tStamp when data is updated. */
+ uint32 btc_status; /* btc status log */
+ uint32 bt_gcishm_active_task_bm; /* Active task bitmap of BT shared thru gci shm */
+ uint32 bt_gcishm_bt_tasks; /* BT Tasks info shared in GCI Shm */
+ uint32 bt_req_type_map; /* BT Antenna Req types since last stats sample */
+ uint32 bt_req_cnt; /* #BT antenna requests since last stats sampl */
+ uint32 bt_gnt_cnt; /* #BT antenna grants since last stats sample */
+ uint32 bt_gnt_dur; /* usec BT owns antenna since last stats sample */
+ uint16 bt_abort_cnt; /* #Times WL was preempted due to BT since WL up */
+ uint16 bt_latency_cnt; /* #Time ucode high latency detected since WL up */
+ uint16 bt_pm_protect_cnt; /* PM protection count requested by Coex */
+ uint16 bt_succ_pm_protect_cnt; /* successful PM protection */
+ uint16 bt_succ_cts_cnt; /* successful CTS2A protection */
+ uint16 bt_wlan_tx_preempt_cnt; /* WLAN TX Preemption */
+ uint16 bt_wlan_rx_preempt_cnt; /* WLAN RX Preemption */
+ uint16 bt_ap_tx_after_pm_cnt; /* AP TX even after PM protection */
+ uint16 bt_peraud_cumu_gnt_cnt; /* Grant cnt for periodic audio */
+ uint16 bt_peraud_cumu_deny_cnt; /* Deny cnt for periodic audio */
+ uint16 bt_a2dp_cumu_gnt_cnt; /* Grant cnt for A2DP */
+ uint16 bt_a2dp_cumu_deny_cnt; /* Deny cnt for A2DP */
+ uint16 bt_sniff_cumu_gnt_cnt; /* Grant cnt for Sniff */
+ uint16 bt_sniff_cumu_deny_cnt; /* Deny cnt for Sniff */
+ uint16 bt_frameburst_ack_cncl_cnt; /* Count of Ack Cancel for Frame Burst */
+ uint16 bt_le_scan_tx_intr_cnt; /* LE Scan Tx Interrupt Count */
+ uint16 bt_le_scan_intr_cnt; /* LE Scan INterrupt Count */
+ uint16 bt_a2dp_grant_ext_intr; /* A2DP Grant Extension Count */
+ uint16 bt_a2dp_grant_ext_prcsd_cnt; /* A2DP Grant Extension Processed Count */
+ uint16 bt_pred_out_of_sync_cnt; /* Predictor Out Of Sync Count */
+ uint16 bt_dcsn_map; /* Accumulated decision bitmap once Ant grant */
+ uint16 bt_dcsn_cnt; /* Accumulated decision bitmap counters once Ant grant */
+ uint16 bt_a2dp_hiwat_cnt; /* Ant grant by a2dp high watermark */
+ uint16 bt_datadelay_cnt; /* Ant grant by acl/a2dp datadelay */
+ uint16 bt_crtpri_cnt; /* Ant grant by critical BT task */
+ uint16 bt_pri_cnt; /* Ant grant by high BT task */
+ uint16 a2dpbuf1cnt; /* Ant request with a2dp buffercnt 1 */
+ uint16 a2dpbuf2cnt; /* Ant request with a2dp buffercnt 2 */
+ uint16 a2dpbuf3cnt; /* Ant request with a2dp buffercnt 3 */
+ uint16 a2dpbuf4cnt; /* Ant request with a2dp buffercnt 4 */
+ uint16 a2dpbuf5cnt; /* Ant request with a2dp buffercnt 5 */
+ uint16 a2dpbuf6cnt; /* Ant request with a2dp buffercnt 6 */
+ uint16 a2dpbuf7cnt; /* Ant request with a2dp buffercnt 7 */
+ uint16 a2dpbuf8cnt; /* Ant request with a2dp buffercnt 8 */
+ uint16 antgrant_lt10ms; /* Ant grant duration cnt 0~10ms */
+ uint16 antgrant_lt30ms; /* Ant grant duration cnt 10~30ms */
+ uint16 antgrant_lt60ms; /* Ant grant duration cnt 30~60ms */
+ uint16 antgrant_ge60ms; /* Ant grant duration cnt 60~ms */
+ uint16 wldurn_ge0ms; /* WL duration count between 0-5ms */
+ uint16 wldurn_ge5ms; /* WL duration count between 5-12ms */
+ uint16 wldurn_ge12ms; /* WL duration count between 12-21ms */
+ uint16 wldurn_ge21ms; /* WL duration count between 21-30ms */
+ uint16 wldurn_ge30ms; /* WL duration count between 30-65ms */
+ uint16 wldurn_ge65ms; /* WL Duration greater than 65ms */
+ uint16 nan_idle_cnt; /* Nan Idle Slot Count */
+ uint16 nan_pre_dw_cnt; /* Nan Pre Dw Slot Count */
+ uint16 nan_pre_data_cnt; /* Nan Pre Data Slot Count */
+ uint16 nan_post_dw_cnt; /* Nan Post Dw Slot Count */
+ uint16 nan_dw_cnt; /* Nan Dw Slot Count */
+ uint16 nan_data_p1_cnt; /* Nan P1 Data Slot Count */
+ uint16 nan_data_p2_cnt; /* Nan P2 Data Slot Count */
+ uint16 nan_pri_deny_cnt; /* Nan Priority Slot Denial Count */
+} wlc_btc_stats_v8_t;
+
#define BTCX_STATS_VER_7 7
typedef struct wlc_btc_stats_v7 {
uint16 version; /* version number of struct */
@@ -10587,6 +11208,8 @@
uint16 rsvd; /* pad to align struct to 32bit bndry */
} wlc_btc_stats_v2_t;
+#define TXCAL_MAX_PA_MODE 4 /* signed for assigning minus for undefined */
+
typedef struct phy_ecounter_v1 {
chanspec_t chanspec;
uint8 slice;
@@ -10609,6 +11232,23 @@
int8 phylog_noise_pwr_array[8]; /* noise buffer array */
} phy_ecounter_log_core_v2_t;
+typedef struct phy_ecounter_log_core_v3 {
+ uint16 bad_txbaseidx_cnt; /* cntr for tx_baseidx=127 in healthcheck */
+ uint16 curr_tssival; /* TxPwrCtrlInit_path[01].TSSIVal */
+ uint16 pwridx_init; /* TxPwrCtrlInit_path[01].pwrIndex_init_path[01] */
+ uint16 auxphystats; /* Indicates the PHY stats for aux slice */
+ uint16 phystatsgaininfo; /* Indicates the gain stats */
+ uint16 flexgaininfo_A; /* Indicates the gain settings */
+ uint8 crsmin_pwr_idx; /* Index to the crsminpower threshold array */
+ uint8 baseindxval; /* TPC Base index */
+ int8 crsmin_pwr; /* Noise level for applied desense */
+ int8 noise_level_inst; /* Instantaneous noise cal pwr */
+ int8 tgt_pwr; /* Programmed Target power */
+ int8 estpwradj; /* Current Est Power Adjust value */
+ uint8 PAD1[2];
+} phy_ecounter_log_core_v3_t;
+
+/* Do not remove phy_ecounter_v1_t parameters */
typedef struct phy_ecounter_v2 {
chanspec_t chanspec;
uint8 slice;
@@ -10651,6 +11291,7 @@
phy_ecounter_log_core_v2_t phy_ecounter_core[2];
} phy_ecounter_v2_t;
+/* Do not remove phy_ecounter_v1_t parameters */
typedef struct phy_ecounter_v3 {
chanspec_t chanspec;
uint16 phy_wdg; /* Count of times watchdog happened. */
@@ -10674,8 +11315,8 @@
int8 weakest_rssi; /* Weakest link RSSI */
int8 ed_threshold; /* Threshold applied for ED */
uint8 chan_switch_cnt; /* Count to track channel change */
- bool phycal_disable; /* Status of phy calibration */
- bool PAD[1]; /* Padding */
+ uint8 phycal_disable; /* Status of phy calibration */
+ uint8 scca_txstall_precondition; /* SmartCCA TX stall precondition */
uint16 featureflag; /* Currently active feature flags */
uint16 deaf_count; /* Count for RX stay in carrier search state */
uint16 noise_mmt_overdue; /* Noise measurement overdue status */
@@ -10694,6 +11335,305 @@
phy_ecounter_log_core_v1_t phy_ecounter_core[2];
} phy_ecounter_v3_t;
+#define ACPHY_OBSS_SUBBAND_CNT 8u /* Max sub band counts i.e., 160Mhz = 8 * 20MHZ */
+
+/* Do not remove phy_ecounter_v1_t parameters */
+typedef struct phy_ecounter_v4 {
+ chanspec_t chanspec;
+ uint16 phy_wdg; /* Count of times watchdog happened. */
+ uint16 noise_req; /* Count of phy noise sample requests. */
+ uint16 noise_crsbit; /* Count of CRS high during noisecal request. */
+ uint16 noise_apply; /* Count of applying noisecal result to crsmin. */
+ uint16 cal_counter; /* Count of performing single and multi phase cal. */
+ uint8 slice; /* Slice # 0 - MAIN, 1 - AUX, 2 - SCAN */
+ uint8 rxchain; /* Status of active RX chains */
+ uint8 txchain; /* Status of active TX chains */
+ uint8 gbd_bphy_sleep_counter; /* Sleep count for bphy GBD */
+ uint8 gbd_ofdm_sleep_counter; /* Sleep count for ofdm GBD */
+ uint8 curr_home_channel; /* Current home channel */
+ uint8 gbd_ofdm_desense; /* Glitch based desense level for ofdm reception */
+ uint8 gbd_bphy_desense; /* Glitch based desense level for bphy reception */
+ int8 chiptemp; /* Chip temperature */
+ int8 femtemp; /* Fem temperature */
+ int8 weakest_rssi; /* Weakest link RSSI */
+ int8 ltecx_mode; /* LTE coex desense mode */
+ int32 btcx_mode; /* BT coex desense mode */
+ int8 ed_threshold; /* Threshold applied for ED */
+ uint8 chan_switch_cnt; /* Count to track channel change */
+ uint8 phycal_disable; /* Status of phy calibration */
+ uint8 scca_txstall_precondition; /* SmartCCA TX stall precondition */
+ uint16 featureflag; /* Currently active feature flags */
+ uint16 deaf_count; /* Count for RX stay in carrier search state */
+ uint16 noise_mmt_overdue; /* Noise measurement overdue status */
+ uint16 crsmin_pwr_apply_cnt; /* Count for desense updates */
+ uint16 ed_crs_status; /* Status of ED and CRS during noise cal */
+ uint16 preempt_status1; /* status of preemption */
+ uint16 preempt_status2; /* status of preemption */
+ uint16 preempt_status3; /* status of preemption */
+ uint16 preempt_status4; /* status of preemption */
+ uint16 counter_noise_iqest_to; /* count of IQ_Est time out */
+ uint32 cca_stats_total_glitch; /* ccastats: count of total glitches */
+ uint32 cca_stats_bphy_glitch; /* ccastats: count of bphy glitches */
+ uint32 cca_stats_total_badplcp; /* ccastats: count of total badplcp */
+ uint32 cca_stats_bphy_badplcp; /* ccastats: count of bphy badplcp */
+ uint32 cca_stats_mbsstime; /* ccastats: monitor duration in msec */
+ uint32 cca_stats_ed_duration; /* ccastats: ed_duration */
+ uint32 measurehold; /* PHY hold activities */
+ uint32 rxsense_disable_req_ch; /* channel disable requests */
+ uint32 ocl_disable_reqs; /* OCL disable bitmap */
+ uint32 interference_mode; /* interference mitigation mode */
+ uint32 power_mode; /* power mode */
+ uint32 obss_last_read_time; /* last stats read time */
+ int32 asym_intf_ed_thresh; /* smartcca ed threshold %d */
+ uint16 obss_mit_bw; /* selected mitigation BW */
+ uint16 obss_stats_cnt; /* stats count */
+ uint16 dynbw_init_reducebw_cnt; /* BW reduction cnt of initiator */
+ uint16 dynbw_resp_reducebw_cnt; /* BW reduction cnt of responder */
+ uint16 dynbw_rxdata_reducebw_cnt; /* rx data cnt with reduced BW */
+ uint16 obss_mmt_skip_cnt; /* mmt skipped due to powersave */
+ uint16 obss_mmt_no_result_cnt; /* mmt with no result */
+ uint16 obss_mmt_intr_err_cnt; /* obss reg mismatch between ucode and fw */
+ uint16 gci_lst_inv_ctr; /* last gci invalid */
+ uint16 gci_lst_rst_ctr; /* last gci restore 0x%04x */
+ uint16 gci_lst_sem_ctr; /* last gci seq number 0x%04x */
+ uint16 gci_lst_rb_st; /* last gci status */
+ uint16 gci_dbg01; /* gci dbg1 readback */
+ uint16 gci_dbg02; /* gci dbg2 readback */
+ uint16 gci_dbg03; /* gci dbg3 readback */
+ uint16 gci_dbg04; /* gci dbg4 readback */
+ uint16 gci_dbg05; /* gci dbg5 readback */
+ uint16 gci_lst_st_msk; /* gci last status mask */
+ uint16 gci_inv_tx; /* invalid gci during tx */
+ uint16 gci_inv_rx; /* invalid gci during rx */
+ uint16 gci_rst_tx; /* gci restore during tx */
+ uint16 gci_rst_rx; /* gci restore during rx */
+ uint16 gci_sem_ctr; /* gci seq number ctr */
+ uint16 gci_invstate; /* gci status 0x%04x */
+ uint16 gci_ctl2; /* gci ctrl 2 */
+ uint16 gci_chan; /* channel during gci read 0x%04x */
+ uint16 gci_cm; /* channel during gci read */
+ uint16 gci_sc; /* gci read during scan */
+ uint16 gci_rst_sc; /* gci restore during scan */
+ uint16 gci_prdc_rx; /* periodic gci hc */
+ uint16 gci_wk_rx; /* gci hc during wake */
+ uint16 gci_rmac_rx; /* gci hc during mac read */
+ uint16 gci_tx_rx; /* gci hc during tx/rx */
+ uint16 asym_intf_stats; /* smartCCA status 0x%04x */
+ uint16 asym_intf_ncal_crs_stat; /* noise cal and crs status %d */
+ int16 ed_crsEn; /* ed enable 0x%04x */
+ int16 nvcfg0; /* noise update to hw 0x%04x */
+ uint8 cal_suppressed_cntr_ed; /* cnt including ss, mp cals, MSB is cur state */
+ uint8 sc_dccal_incc_cnt; /* scan dccal counter */
+ uint8 sc_noisecal_incc_cnt; /* scan noise cal counter */
+ uint8 obss_need_updt; /* BW update needed flag */
+ uint8 obss_mit_status; /* obss mitigation status */
+ uint8 obss_final_rec_bw; /* final recommended bw to wlc-Sent to SW */
+ uint8 btc_mode; /* btc mode */
+ uint8 asym_intf_ant_noise_idx; /* current noise storage index */
+ uint8 asym_intf_pending_host_req_type; /* usb plugin request */
+ uint8 asym_intf_ncal_crs_stat_idx; /* crs status storage index %d */
+ int8 rxsense_noise_idx; /* rxsense det thresh desense idx */
+ int8 rxsense_offset; /* rxsense min power desense idx */
+ int8 asym_intf_tx_smartcca_cm; /* smartCCA tx coremask %d */
+ int8 asym_intf_rx_noise_mit_cm; /* smartCCA rx coremask %d */
+ int8 asym_intf_avg_noise[2]; /* average noise %d */
+ int8 asym_intf_latest_noise[2]; /* current noise %d */
+ uint8 obss_curr_det[ACPHY_OBSS_SUBBAND_CNT]; /* obss curr detection */
+ phy_ecounter_log_core_v3_t phy_ecounter_core[2];
+} phy_ecounter_v4_t;
+
+typedef struct phy_ecounter_phycal_core_v1 {
+ /* RxIQ imbalance coeff */
+ int32 rxs;
+ int32 rxs_vpoff;
+ int32 rxs_ipoff;
+ /* OFDM and BPHY TxIQ imbalance coeff */
+ uint16 ofdm_txa;
+ uint16 ofdm_txb;
+ uint16 ofdm_txd; /* contain di & dq */
+ uint16 bphy_txa;
+ uint16 bphy_txb;
+ uint16 bphy_txd; /* contain di & dq */
+ /* the number of times the baseidx is
+ * greater than a certain threshold
+ */
+ uint16 txbaseidx_gtthres_cnt;
+ /* RxIQ imbalance coeff */
+ uint16 rxa;
+ uint16 rxb;
+ uint8 PAD2;
+ uint8 PAD3;
+ /* Rx IQ Cal coeff */
+ uint16 rxa_vpoff; /* not present in 4378 */
+ uint16 rxb_vpoff; /* not present in 4378 */
+ uint16 rxa_ipoff; /* not present in 4378 */
+ uint16 rxb_ipoff; /* not present in 4378 */
+ /* Tx IQ/LO calibration coeffs */
+ uint16 txiqlo_2g_a0;
+ uint16 txiqlo_2g_b0;
+ uint16 txiqlo_2g_a1;
+ uint16 txiqlo_2g_b1;
+ uint16 txiqlo_2g_a2;
+ uint16 txiqlo_2g_b2;
+ /* tx baseindex */
+ uint8 baseidx;
+ uint8 baseidx_cck;
+ /* adc cap cal */
+ uint8 adc_coeff_cap0_adcI;
+ uint8 adc_coeff_cap1_adcI;
+ uint8 adc_coeff_cap2_adcI;
+ uint8 adc_coeff_cap0_adcQ;
+ uint8 adc_coeff_cap1_adcQ;
+ uint8 adc_coeff_cap2_adcQ;
+} phy_ecounter_phycal_core_v1_t;
+
+typedef struct phy_phycal_core_v2 {
+ /* RxIQ imbalance coeff */
+ int32 rxs;
+
+ /* OFDM and BPHY TxIQ imbalance coeff */
+ uint16 ofdm_txa;
+ uint16 ofdm_txb;
+ uint16 ofdm_txd; /* contain di & dq */
+ uint16 bphy_txa;
+ uint16 bphy_txb;
+ uint16 bphy_txd;
+
+ /* RxIQ imbalance coeff */
+ uint16 rxa;
+ uint16 rxb;
+
+ /* Rx IQ Cal coeff */
+ uint16 rxa_vpoff;
+ uint16 rxb_vpoff;
+ uint16 rxa_ipoff;
+ uint16 rxb_ipoff;
+ int32 rxs_vpoff;
+ int32 rxs_ipoff;
+ /* Tx IQ/LO calibration coeffs */
+ uint16 txiqlo_2g_a0;
+ uint16 txiqlo_2g_b0;
+ uint16 txiqlo_2g_a1;
+ uint16 txiqlo_2g_b1;
+ uint16 txiqlo_2g_a2;
+ uint16 txiqlo_2g_b2;
+ /* tx baseindex */
+ uint8 baseidx;
+ uint8 baseidx_cck;
+ /* adc cap cal */
+ uint8 adc_coeff_cap0_adcI;
+ uint8 adc_coeff_cap1_adcI;
+ uint8 adc_coeff_cap2_adcI;
+ uint8 adc_coeff_cap0_adcQ;
+ uint8 adc_coeff_cap1_adcQ;
+ uint8 adc_coeff_cap2_adcQ;
+
+ int32 txs;
+ int16 txs_mean;
+ uint16 txbaseidx_gtthres_cnt; /* cntr for tx_baseidx > hi_thres in healthcheck */
+ uint16 txgain_rad_gain;
+ uint16 txgain_rad_gain_mi;
+ uint16 txgain_rad_gain_hi;
+ uint16 txgain_dac_gain;
+ uint16 txgain_bbmult;
+ int16 rxs_mean_vpoff;
+ int16 rxs_mean_ipoff;
+ int16 rxs_mean;
+ uint8 rxms;
+ uint8 rxms_vpoff;
+ uint8 rxms_ipoff;
+ uint8 ccktxgain_offset;
+ uint8 mppc_gain_offset_qdB[TXCAL_MAX_PA_MODE];
+
+ /* Misc general purpose debug counters (will be used for future debugging) */
+ uint8 debug_01;
+ uint8 debug_02;
+ uint8 debug_03;
+ uint8 debug_04;
+ uint16 debug_05;
+ uint16 debug_06;
+ uint16 debug_07;
+ uint16 debug_08;
+ uint32 debug_09;
+ uint32 debug_10;
+ uint32 debug_11;
+ uint32 debug_12;
+} phy_phycal_core_v2_t;
+
+typedef struct phy_ecounter_phycal_v1 {
+ uint32 last_cal_time; /* in [sec], covers 136 years if 32 bit */
+ chanspec_t chanspec;
+ int16 last_cal_temp;
+ bool txiqlocal_retry;
+ bool rxe;
+ uint8 cal_phase_id;
+ uint8 slice;
+ phy_ecounter_phycal_core_v1_t phy_ecounter_phycal_core[2];
+} phy_ecounter_phycal_v1_t;
+
+typedef struct phy_phycal_v2 {
+ uint32 last_cal_time; /* in [sec], covers 136 years if 32 bit */
+ chanspec_t chanspec;
+ int16 last_cal_temp;
+ bool txiqlocal_retry;
+ bool rxe;
+ uint8 cal_phase_id;
+ uint8 slice;
+ uint32 desense_reason;
+ uint16 dur; /* duration of cal in usec */
+
+ uint8 reason;
+ uint8 hc_retry_count_vpoff;
+ uint8 hc_retry_count_ipoff;
+ uint8 hc_retry_count_rx;
+ uint8 hc_dev_exceed_log_rx_vpoff;
+ uint8 hc_dev_exceed_log_rx_ipoff;
+ uint8 hc_dev_exceed_log_rx;
+ uint8 sc_rxiqcal_skip_cnt;
+
+ uint8 hc_retry_count_tx;
+ uint8 hc_dev_exceed_log_tx;
+ uint16 txiqcal_max_retry_cnt;
+ uint16 txiqcal_max_slope_cnt;
+ uint16 mppc_cal_failed_count;
+ uint16 pad01;
+ uint16 txiqlocal_coeffs[20];
+ bool is_mppc_gain_offset_cal_success;
+
+ /* Misc general purpose debug counters (will be used for future debugging) */
+ uint8 debug_01;
+ uint8 debug_02;
+ uint8 debug_03;
+ uint16 debug_04;
+ uint16 debug_05;
+ uint16 debug_06;
+ uint16 debug_07;
+ uint32 debug_08;
+ uint32 debug_09;
+ uint32 debug_10;
+ uint32 debug_11;
+
+ phy_phycal_core_v2_t phy_phycal_core[2];
+} phy_phycal_v2_t;
+
+#define PHY_ECOUNTERS_PHYCAL_STATS_VER1 1u
+typedef struct phy_ecounter_phycal_stats_v1 {
+ uint16 version;
+ uint16 length;
+ uint8 num_channel; /* Number of active channels. */
+ uint8 PAD[3];
+ phy_ecounter_phycal_v1_t phy_counter[];
+} phy_ecounter_phycal_stats_v1_t;
+
+#define PHY_ECOUNTERS_PHYCAL_STATS_VER2 2u
+typedef struct phy_ecounter_phycal_stats_v2 {
+ uint16 version;
+ uint16 length;
+ uint8 num_channel; /* Number of active channels. */
+ uint8 PAD[3];
+ phy_phycal_v2_t phy_counter[];
+} phy_ecounter_phycal_stats_v2_t;
+
#define PHY_ECOUNTERS_STATS_VER1 1u
typedef struct phy_ecounter_stats_v1 {
uint16 version;
@@ -10721,6 +11661,15 @@
phy_ecounter_v3_t phy_counter[];
} phy_ecounter_stats_v3_t;
+#define PHY_ECOUNTERS_STATS_VER4 4u
+typedef struct phy_ecounter_stats_v4 {
+ uint16 version;
+ uint16 length;
+ uint8 num_channel; /* Number of active channels. */
+ uint8 PAD[3];
+ phy_ecounter_v4_t phy_counter[];
+} phy_ecounter_stats_v4_t;
+
/* Durations for each bt task in millisecond */
#define WL_BTCX_DURSTATS_VER_2 (2u)
typedef struct wlc_btcx_durstats_v2 {
@@ -10758,7 +11707,7 @@
uint16 bt_task_pred_dur; /* prediction task duration in ms */
uint16 bt_multihid_dur; /* multihid duration in ms */
uint16 bt_scan_tx_dur; /* Scan Tx duration in ms */
- uint16 PAD;
+ uint16 bt_disable_dual_bt_dur; /* Duration of Dual BT disable */
} wlc_btcx_durstats_v2_t;
#define WL_BTCX_DURSTATS_VER_1 (1u)
@@ -10802,7 +11751,7 @@
#define WL_MAX_IPFO_ROUTE_TBL_ENTRY 64
/* Global ASSERT Logging */
-#define ASSERTLOG_CUR_VER 0x0100
+#define ASSERTLOG_VERSION_0x0100 0x0100u
#define MAX_ASSRTSTR_LEN 64
typedef struct assert_record {
@@ -10886,7 +11835,7 @@
uint8 PAD[3];
} chanim_stats_t;
-#define WL_CHANIM_STATS_VERSION 3
+#define WL_CHANIM_STATS_VERSION_3 3
typedef struct {
uint32 buflen;
uint32 version;
@@ -11210,7 +12159,7 @@
/* structure/defines for selective mgmt frame (smf) stats support */
-#define SMFS_VERSION 1
+#define SMFS_VERSION_1 1
/** selected mgmt frame (smf) stats element */
typedef struct wl_smfs_elem {
uint32 count;
@@ -11249,7 +12198,7 @@
/* #ifdef PHYMON */
-#define PHYMON_VERSION 1
+#define PHYMON_VERSION_1 1
typedef struct wl_phycal_core_state {
/* Tx IQ/LO calibration coeffs */
@@ -11431,7 +12380,6 @@
#define MIN_NUM_PWR_STEP 2u
#define MAX_NUM_PWR_STEP 40 /* leave it as signed for backward compatibility */
-#define TXCAL_MAX_PA_MODE 4 /* signed for assigning minus for undefined */
#define TXCAL_IOVAR_VERSION 0x1 /* need to leave it as signed one
* for backward compatibility
@@ -11633,14 +12581,13 @@
uint8 PAD;
} powersel_params_t;
-#define WL_LPC_PARAMS_VER_2 2
-#define WL_LPC_PARAMS_CURRENT_VERSION WL_LPC_PARAMS_VER_2
+#define WL_LPC_PARAMS_VER_2 2u
typedef struct lpc_params {
uint16 version;
uint16 length;
/* LPC Params exposed via IOVAR */
- uint8 rate_stab_thresh; /**< Thresh for rate stability based on nupd */
+ uint8 rate_stab_thresh; /**< Lowest power reached by algorithm */
uint8 pwr_stab_thresh; /**< Number of successes before power step down */
uint8 lpc_exp_time; /**< Time lapse for expiry of database */
uint8 pwrup_slow_step; /**< Step size for slow step up */
@@ -11686,7 +12633,7 @@
uint8 PAD;
} txdelay_params_t;
#define MAX_TXDELAY_STATS_SCBS 6
-#define TXDELAY_STATS_VERSION 1
+#define TXDELAY_STATS_VERSION_1 1
enum {
TXDELAY_STATS_PARTIAL_RESULT = 0,
@@ -12570,6 +13517,35 @@
/*
* proxd collect header with 160 MHz support
*/
+#define WL_PROXD_COLLECT_HEADER_VERSION_3 3u
+typedef struct wl_proxd_collect_header_v3 {
+ uint16 version;
+ uint16 len;
+ uint8 chiprev; /**< chip revision */
+ uint8 phyver; /**< phy version */
+ uint8 PAD[2]; /* Use this for any int8/16 uint8/16 ext in future */
+ uint16 total_frames; /**< The total frames for this collect. */
+ uint16 nfft; /**< nfft value */
+ uint16 bandwidth; /**< bandwidth */
+ uint16 channel; /**< channel number */
+ uint16 fpfactor_shift; /**< avb timer value shift bits */
+ uint16 chipnum; /**< chip type */
+ uint32 chanspec; /**< channel spec */
+ uint32 fpfactor; /**< avb timer value factor */
+ uint32 meanrtt; /**< mean of RTTs */
+ uint32 modertt; /**< mode of RTTs */
+ uint32 medianrtt; /**< median of RTTs */
+ uint32 sdrtt; /**< standard deviation of RTTs */
+ uint32 clkdivisor; /**< clock divisor */
+ int32 distance; /**< distance calculated by fw */
+ struct ether_addr localMacAddr; /**< local mac address */
+ uint16 PAD; /* Use this for any int8/16 uint8/16 ext in future */
+ struct ether_addr remoteMacAddr; /**< remote mac address */
+ uint16 PAD; /* Use this for any int8/16 uint8/16 ext in future */
+ wl_proxd_params_tof_tune_v5_t params; /* TOF tune params */
+ uint8 tlv_params[]; /* xtlvs for variable ext params */
+} wl_proxd_collect_header_v3_t;
+
#define WL_PROXD_COLLECT_HEADER_VERSION_2 2u
typedef struct wl_proxd_collect_header_v2 {
uint16 version;
@@ -13015,6 +13991,15 @@
WL_NAN_XTLV_CFG_FDISC_TBMP = NAN_CMD(WL_NAN_CMD_CFG_COMP_ID, 0x0F),
WL_NAN_XTLV_CFG_SEC_GTK_CSID = NAN_CMD(WL_NAN_CMD_CFG_COMP_ID, 0x10),
+ /* NAN R4, host constucted NPBA (NAN Pairing Bootstrapping Attribute), the entire
+ * NPBA attibute is in bcm_xlv_t:
+ * len: contains the NABA attribute length
+ * data: contains the NABA attrbute data, including id.
+ * The Host exchanges this attribute during the
+ * NAN pairing and bootstrapping in SDF Follow-ups and SDF Publish.
+ */
+ WL_NAN_XTLV_CFG_NPBA_INFO = NAN_CMD(WL_NAN_CMD_CFG_COMP_ID, 0x11),
+
WL_NAN_XTLV_SD_SVC_INFO = NAN_CMD(WL_NAN_CMD_SD_COMP_ID, 0x01),
WL_NAN_XTLV_SD_FOLLOWUP = NAN_CMD(WL_NAN_CMD_SD_COMP_ID, 0x02),
WL_NAN_XTLV_SD_SDF_RX = NAN_CMD(WL_NAN_CMD_SD_COMP_ID, 0x03),
@@ -13144,7 +14129,8 @@
WL_NAN_CMD_CFG_FSM_TIMEOUT = NAN_CMD(WL_NAN_CMD_CFG_COMP_ID, 0x1E),
WL_NAN_CMD_CFG_REKEY = NAN_CMD(WL_NAN_CMD_CFG_COMP_ID, 0x1F), /* REKEY */
WL_NAN_CMD_CFG_INSTANT_CHAN = NAN_CMD(WL_NAN_CMD_CFG_COMP_ID, 0x20),
- WL_NAN_CMD_CFG_MAX = WL_NAN_CMD_CFG_INSTANT_CHAN,
+ WL_NAN_CMD_CFG_TSF = NAN_CMD(WL_NAN_CMD_CFG_COMP_ID, 0x21),
+ WL_NAN_CMD_CFG_MAX = WL_NAN_CMD_CFG_TSF,
/* Add new commands before and update */
@@ -13357,6 +14343,22 @@
uint32 merge_scan_cnt_5g; /* 5G band merge scan cnt */
} wl_nan_mac_stats_v1_t;
+typedef struct wl_nan_mac_stats_v2 {
+ wl_nan_mac_band_stats_t band[NAN_MAX_BANDS]; /* MAC sync band specific stats */
+ uint32 naf_tx; /* NAN AF tx */
+ uint32 naf_rx; /* NAN AF rx */
+ uint32 sdf_tx; /* SDF tx */
+ uint32 sdf_rx; /* SDF rx */
+ uint32 cnt_sync_bcn_rx_tu[3]; /* delta bw */
+ uint32 cnt_bcn_tx_out_dw; /* TX sync beacon outside dw */
+ uint32 cnt_role_am_dw; /* anchor master role due to dw */
+ uint32 cnt_am_hop_err; /* wrong hopcount set for AM */
+ uint32 merge_scan_cnt_2g; /* 2G band merge scan cnt */
+ uint32 merge_scan_cnt_5g; /* 5G band merge scan cnt */
+ uint16 ucast_sdf_oth_bssid; /* ucast sdf sent by peer that is in other custer */
+ uint16 ucast_naf_oth_bssid; /* ucast naf sent by peer that is in other cluster */
+} wl_nan_mac_stats_v2_t;
+
/* NAN Sched stats */
/* Per core Sched stats */
typedef struct nan_sched_stats_core {
@@ -13393,6 +14395,8 @@
uint32 fup_rx; /* Followup rx */
uint32 pub_resp_ignored; /* response to incoming publish ignored */
uint32 sub_resp_ignored; /* response to incoming subscribe ignored */
+ uint32 auto_resp_ignored; /* response to incoming disc bcn ignored */
+ uint32 disc_cache_ovfl; /* Number of seen once disc cache overflows in system */
} nan_disc_stats_t;
/* NAN Discovery stats end */
@@ -13866,9 +14870,22 @@
/* Control flag to reject group addressed AFs w/o IGTK */
WL_NAN_CTRL2_FLAG1_IGTK_REJECT_UNPROT = 0x00400000,
/* Control flag to reject bcn w/o BIGTK */
- WL_NAN_CTRL2_FLAG1_BIGTK_REJECT_UNPROT = 0x00800000
+ WL_NAN_CTRL2_FLAG1_BIGTK_REJECT_UNPROT = 0x00800000,
+ /* Control flags to set infra slot duration.
+ * Two Bits[MSB:LSB], 00 -128ms, 01 - 64ms, 10 - 32ms, 11 - Reserved
+ */
+ WL_NAN_CTRL2_FLAG1_INFRA_SLOT_INTRVL_LSB = 0x01000000,
+ WL_NAN_CTRL2_FLAG1_INFRA_SLOT_INTRVL_MSB = 0x02000000,
+ /* Control flag to enable NAN EHT */
+ WL_NAN_CTRL2_FLAG1_EHT_ENABLE = 0x04000000,
+ /* Control flag to enable NAN STRML */
+ WL_NAN_CTRL2_FLAG1_STRML_ENABLE = 0x08000000,
+ /* Control flag to enable NAN EMLSR */
+ WL_NAN_CTRL2_FLAG1_EMLSR_ENABLE = 0x10000000,
+ /* Allow election (role change) outside of DW */
+ WL_NAN_CTRL2_FLAG1_ELECTION_OUTOF_DW = 0x40000000
};
-#define WL_NAN_CTRL2_FLAGS1_MASK 0x00FFFFFF
+#define WL_NAN_CTRL2_FLAGS1_MASK 0x7FFFFFFF
#define WL_NAN_CTRL2_FLAGS2_MASK 0x00000000
@@ -14002,6 +15019,14 @@
typedef uint8 wl_nan_host_enable_t;
/*
+ * WL_NAN_CMD_CFG_TSF
+ */
+typedef struct wl_nan_tsf_config {
+ uint32 tsf_hi;
+ uint32 tsf_lo;
+} wl_nan_tsf_config_t;
+
+/*
* WL_NAN_CMD_ELECTION_METRICS_CONFIG
*/
/* Set only */
@@ -14214,6 +15239,11 @@
/* If set, host wont rec event "terminated" */
#define WL_NAN_SVC_CTRL_SUPPRESS_EVT_TERMINATED 0x8000000
+/* NAN rekey types */
+#define NAN_REKEY_PTK 0x01
+#define NAN_REKEY_GTK 0x02
+#define NAN_REKEY_MAX (NAN_REKEY_PTK | NAN_REKEY_GTK)
+
/*
* WL_NAN_CMD_SD_PARAMS
*/
@@ -14266,6 +15296,12 @@
*/
typedef uint32 wl_nan_fsm_timeout_t;
+// nan rekey cfg iovar
+typedef struct wl_nan_rekey {
+ struct ether_addr ndi_addr;
+ uint8 rekey_ctrl;
+} wl_nan_rekey_t;
+
/*
* WL_NAN_CMD_CFG_SID_BEACON
*/
@@ -15118,7 +16154,8 @@
WL_NAN_FW_CAP_FLAG1_NDPE = 0x00080000,
WL_NAN_FW_CAP_FLAG1_OOB_AF = 0x00100000,
WL_NAN_FW_CAP_FLAG1_PMK_PER_NDP = 0x00200000,
- WL_NAN_FW_CAP_FLAG1_INSTANT_MODE = 0x00400000
+ WL_NAN_FW_CAP_FLAG1_INSTANT_MODE = 0x00400000,
+ WL_NAN_FW_CAP_FLAG1_SEC_ENHANCE = 0x00800000
};
/* WL_NAN_XTLV_GEN_FW_CAP */
@@ -15422,91 +16459,7 @@
/* ********************* end of NAN section ******************************** */
/* endif WL_NAN */
-#define P2P_NAN_IOC_BUFSZ 512 /* some sufficient ioc buff size */
-#define WL_P2P_NAN_IOCTL_VERSION 0x1
-
-/* container for p2p nan iovtls & events */
-typedef struct wl_p2p_nan_ioc {
- uint16 version; /* interface command or event version */
- uint16 id; /* p2p nan ioctl cmd ID */
- uint16 len; /* total length of data[] */
- uint16 PAD; /* padding */
- uint8 data []; /* var len payload of bcm_xtlv_t type */
-} wl_p2p_nan_ioc_t;
-
-/* p2p nan cmd IDs */
-enum wl_p2p_nan_cmds {
- /* p2p nan cfg ioctls */
- WL_P2P_NAN_CMD_ENABLE = 1,
- WL_P2P_NAN_CMD_CONFIG = 2,
- WL_P2P_NAN_CMD_DEL_CONFIG = 3,
- WL_P2P_NAN_CMD_GET_INSTS = 4
-};
-
-#define WL_P2P_NAN_CONFIG_VERSION 1
-
-#define WL_P2P_NAN_DEVICE_P2P 0x0
-#define WL_P2P_NAN_DEVICE_GO 0x1
-#define WL_P2P_NAN_DEVICE_GC 0x2
-#define WL_P2P_NAN_DEVICE_INVAL 0xFF
-
/* NAN P2P operation */
-typedef struct p2p_nan_config {
- uint16 version; /* wl_p2p_nan_config_t structure version */
- uint16 len; /* total length including version and variable IE */
- uint32 flags; /* 0x1 to NEW, 0x2 to ADD, 0x4 to DEL */
- uint8 inst_id; /* publisher/subscriber id */
- uint8 inst_type; /* publisher/subscriber */
- uint8 dev_role; /* P2P device role: 'P2P','GO' or 'GC' */
- uint8 PAD; /* padding */
- uint8 resolution; /* Availability bitmap resolution */
- uint8 repeat; /* Whether Availabilty repeat across DW */
- uint16 ie_len; /* variable ie len */
- struct ether_addr dev_mac; /* P2P device addres */
- uint16 PAD; /* Padding */
- uint32 avail_bmap; /* availability interval bitmap */
- uint32 chanspec; /* Chanspec */
- uint8 ie[]; /* hex ie data */
-} wl_p2p_nan_config_t;
-
-#define WL_P2P_NAN_SERVICE_LIST_VERSION 1
-typedef enum wl_nan_service_type {
- WL_NAN_SVC_INST_PUBLISHER = 1,
- WL_NAN_SVC_INST_SUBSCRIBER = 2
-} wl_nan_service_type_t;
-
-#define WL_P2P_NAN_CONFIG_NEW 0x1
-#define WL_P2P_NAN_CONFIG_ADD 0x2
-#define WL_P2P_NAN_CONFIG_DEL 0x4
-
-typedef struct wl_nan_svc_inst {
- uint8 inst_id; /* publisher/subscriber id */
- uint8 inst_type; /* publisher/subscriber */
-} wl_nan_svc_inst_t;
-
-typedef struct wl_nan_svc_inst_list {
- uint16 version; /* this structure version */
- uint16 len; /* total length including version and variable svc list */
- uint16 count; /* service instance count */
- uint16 PAD; /* padding */
- wl_nan_svc_inst_t svc[BCM_FLEX_ARRAY]; /* service instance list */
-} wl_nan_svc_inst_list_t;
-
-#define NAN_POST_DISC_P2P_DATA_VER 1
-/* This structure will be used send peer p2p data with
- * NAN discovery result
- */
-typedef struct nan_post_disc_p2p_data {
- uint8 ver; /* this structure version */
- uint8 dev_role; /* P2P Device role */
- uint8 resolution; /* Availability bitmap resolution */
- uint8 repeat; /* Whether Availabilty repeat across DW */
- struct ether_addr dev_mac; /* P2P device addres */
- uint16 PAD; /* Padding */
- uint32 chanspec; /* Chanspec */
- uint32 avl_bmp; /* availability interval bitmap */
-} nan_post_disc_p2p_data_t;
-
enum {
WL_AVAIL_NONE = 0x0000,
WL_AVAIL_LOCAL = 0x0001,
@@ -15921,7 +16874,7 @@
} wl_proxd_debug_data_t;
/** version of the wl_wsec_info structure */
-#define WL_WSEC_INFO_VERSION 0x01
+#define WL_WSEC_INFO_VERSION_1 0x01
/** start enum value for BSS properties */
#define WL_WSEC_INFO_BSS_BASE 0x0100
@@ -15957,6 +16910,10 @@
WL_WSEC_INFO_SAE_GROUPS = (WL_WSEC_INFO_BSS_BASE + 0xD),
WL_WSEC_INFO_OCV = (WL_WSEC_INFO_BSS_BASE + 0xE),
WL_WSEC_INFO_BSS_KEY_IDLE_TIME = (WL_WSEC_INFO_BSS_BASE + 0xF),
+ WL_WSEC_INFO_BSS_INCLUDE_RSNXE = (WL_WSEC_INFO_BSS_BASE + 0x10), /**<
+ Include RSNXE in pure
+ WPA-PSK mode
+ */
/*
* ADD NEW ENUM ABOVE HERE
@@ -16050,17 +17007,33 @@
#define AP_ALLOW_WPA2 0x00000001u /* Allow WPA2PSK AP during join or roam */
#define AP_ALLOW_TSN 0x00000002u /* Allow WPA3 transition AP during join or roam */
#define AP_ALLOW_WPA3_ONLY 0x00000004u /* Allow WPA3 only AP during join or roam */
+/* AP_ALLOW_WPA3_ONLY is write only
+** supports AP_ALLOW_WPA3_2G_5G_ONLY and AP_ALLOW_WPA3_6G_ONLY
+** DEPRECATED moving forward
+*/
/* Policy when WPA2 PSK, but not SAE is configured for the BSS */
#define AP_WPA2_PSK_NO_MIX_SEC 0x00000008u /* Disallow Mixed WPA/WPA2 security during roam */
+
+#define AP_ALLOW_WPA3_2G_5G_ONLY 0x00000010u /* Allow WPA3 only 2G/5G AP join or roam */
+#define AP_ALLOW_WPA3_6G_ONLY 0x00000020u /* Allow WPA3 only 6G AP during join or roam */
/* All flags */
#define AP_ALLOW_MAX (AP_ALLOW_WPA2 | AP_ALLOW_TSN | \
- AP_ALLOW_WPA3_ONLY | AP_WPA2_PSK_NO_MIX_SEC)
+ AP_ALLOW_WPA3_ONLY | AP_WPA2_PSK_NO_MIX_SEC) /* DEPRECATED moving forward */
+/* AP_ALLOW_MAX will be defined in the src component */
+
+/* OWE roaming policy bit definitions */
+
+#define AP_ALLOW_OPEN_ONLY 0x00010000u /* Allow roam to open APs (2G and 5G) */
+#define AP_ALLOW_OWE_TRANS_2G_5G 0x00020000u /* Allow roam to owe transition n/w */
+#define AP_ALLOW_OWE_ONLY_IN_2G_5G 0x00040000u /* Allow roam to owe only APs in 2G or 5G */
+#define AP_ALLOW_OWE_ONLY_IN_6G 0x00080000u /* Allow roam to owe only APs in 6g only */
typedef struct {
uint32 wpa_ap_restrict; /* set WPA2 / WPA3 AP restriction policy */
} wl_wsec_info_wpa_ap_restrict_t;
/* SAE PWE derivation method */
+#define SAE_PWE_INVALID 0x0u
#define SAE_PWE_LOOP 0x1u
#define SAE_PWE_H2E 0x2u
@@ -16274,15 +17247,7 @@
uint32 num_tlvs; /* no of chanspec list tlvs */
uint8 tlvs[BCM_FLEX_ARRAY];
} scan_event_data_v2_t;
-
-#ifdef WL_SCAN_EVENT_V2
-typedef scan_event_data_v2_t scan_event_data_t;
-#define WL_SCAN_EVENT_FIXED_LEN_V2 OFFSETOF(scan_event_data_t, tlvs)
-#define WL_SCAN_EVENT_VERSION WL_SCAN_EVENT_VER2
-#else
-#define WL_SCAN_EVENT_VERSION WL_SCAN_EVENT_VER1
-typedef scan_event_data_v1_t scan_event_data_t;
-#endif
+#define WL_SCAN_EVENT_FIXED_LEN_V2 OFFSETOF(scan_event_data_v2_t, tlvs)
/*
* bonjour dongle offload definitions
@@ -16800,7 +17765,7 @@
uint8 flags;
} wl_el_tag_params_t;
-#define EVENT_LOG_SET_TYPE_CURRENT_VERSION 0
+#define EVENT_LOG_SET_TYPE_VERSION_0 0u
typedef struct wl_el_set_type_s {
uint16 version;
uint16 len;
@@ -16809,7 +17774,7 @@
uint16 PAD;
} wl_el_set_type_t;
-#define EVENT_LOG_SET_TYPE_ALL_V1 1
+#define EVENT_LOG_SET_TYPE_ALL_V1 1u
typedef struct wl_el_set_type_s_v1 {
uint8 set_val;
@@ -16975,7 +17940,15 @@
GPAIO_ETSSI,
GPAIO_PAD5G_GM_BIAS_V,
GPAIO_PAD5G_GM_DRAIN_V,
- GPAIO_PAD5G_CAS_BIAS_V
+ GPAIO_PAD5G_CAS_BIAS_V,
+ GPAIO_PMU_LDO1P8,
+ GPAIO_RX_GM_VDD,
+ GPAIO_RX_TIA_FINAL_CM_V,
+ GPAIO_RX_TIA_FINAL_CM_V1,
+ GPAIO_RX_TIA_FINAL_CM_V2,
+ GPAIO_PA5G_GM_BIAS_V,
+ GPAIO_PA5G_GM_DRAIN_V,
+ GPAIO_PA5G_CAS_BIAS_V
} wl_gpaio_option_t;
/** IO Var Operations - the Value of iov_op In wlc_ap_doiovar */
@@ -17050,6 +18023,26 @@
uint16 combo[16]; /* mws ant selection 2nd */
} mws_ant_map_t_2nd;
+#define LTECX_MWS_ANTMAP_VERSION_V3 3u
+
+/** flags indicating changed field */
+enum {
+ WL_MWS_ANT_MAP_2G = 1, /* 2g filed updated */
+ WL_MWS_ANT_MAP_5G = 2, /* 5g filed updated */
+ WL_MWS_ANT_MAP_6G = 3 /* 6g filed updated */
+};
+
+/* MWS ANT map 3rd generation */
+typedef struct {
+ uint16 version; /* Structure version */
+ uint16 length; /* Length of whole struct */
+ uint16 band; /* 2G/5G/6G */
+ uint16 combo_2g[16]; /* mws ant selection 2g */
+ uint16 combo_5g[16]; /* mws ant selection 5g */
+ uint16 combo_6g[16]; /* mws ant selection 6g */
+ uint8 PAD[2]; /* Padding for 4byte alignment */
+} mws_ant_map_v3_t;
+
/* MWS Coex bitmap v2 map for Type0/Type6 */
typedef struct {
uint16 bitmap_2G; /* 2G Bitmap */
@@ -17058,6 +18051,77 @@
uint16 bitmap_5G_hi; /* 5G hi bitmap */
} mws_coex_bitmap_v2_t;
+/* MWS Coex bitmap v3 map for LTECX features */
+
+#define LTECX_COEX_BITMAP_VERSION_V3 3u
+
+/** flags indicating changed field */
+enum {
+ WL_MWS_COEX_BITMAP_2G = (1 << 0), /* 2g filed updated */
+ WL_MWS_COEX_BITMAP_5G = (1 << 1), /* 5g filed updated */
+ WL_MWS_COEX_BITMAP_6G = (1 << 2) /* 6g filed updated */
+};
+
+typedef struct {
+ uint16 version; /* Structure version */
+ uint16 length; /* Length of whole struct */
+ uint8 flags; /* Flags to indicate the updated field */
+ uint8 PAD;
+ uint16 bitmap_2G; /* 2G Bitmap */
+ uint16 bitmap_5G_lo; /* 5G lo bitmap */
+ uint16 bitmap_5G_mid; /* 5G mid bitmap */
+ uint16 bitmap_5G_hi; /* 5G hi bitmap */
+ uint16 bitmap_6G_lo_unii5; /* 6G lo bitmap UNII5 */
+ uint16 bitmap_6G_hi_unii5; /* 6G hi bitmap UNII5 */
+ uint16 bitmap_6G_unii6; /* 6G UNII6 bitmap */
+ uint16 bitmap_6G_unii7; /* 6G UNII7 bitmap */
+ uint16 bitmap_6G_unii8; /* 6G UNII8 bitmap */
+} mws_coex_bitmap_v3_t;
+
+/* MWS OCL bitmap v2 map for LTECX features */
+/* v2 map is for 4388 and future chips */
+/* to cover 6g Channels */
+/* The first generation map is defined */
+/* by wl_mws_ocl_override_t */
+/* Not a ltecoex sub commands */
+
+#define LTECX_OCL_BITMAP_VERSION_V2 2u
+
+/** flags indicating changed field */
+enum {
+ WL_MWS_OCL_BITMAP_2G = (1 << 0), /* 2g field updated */
+ WL_MWS_OCL_BITMAP_5G = (1 << 1), /* 5g field updated */
+ WL_MWS_OCL_BITMAP_6G = (1 << 2) /* 6g field updated */
+};
+
+typedef struct {
+ uint16 version; /* Structure version */
+ uint16 length; /* Length of whole struct */
+ uint8 flags; /* Flags to indicate the updated field */
+ uint8 PAD;
+ uint16 bitmap_2G; /* 2G Bitmap */
+ uint16 bitmap_5G_lo; /* 5G lo bitmap */
+ uint16 bitmap_5G_mid; /* 5G mid bitmap */
+ uint16 bitmap_5G_hi; /* 5G hi bitmap */
+ uint16 bitmap_6G_lo_unii5; /* 6G lo bitmap UNII5 */
+ uint16 bitmap_6G_hi_unii5; /* 6G hi bitmap UNII5 */
+ uint16 bitmap_6G_unii6; /* 6G UNII6 bitmap */
+ uint16 bitmap_6G_unii7; /* 6G UNII7 bitmap */
+ uint16 bitmap_6G_unii8; /* 6G UNII8 bitmap */
+} mws_ocl_bitmap_t;
+
+/* To define the ctrl map */
+/* to enable or disable spmi tx message */
+#define LTECX_SPMITX_CTRL_VER 1u
+
+typedef struct {
+ uint16 version; /* Structure version */
+ uint16 length; /* Length of whole struct */
+ uint16 spmimsg_type; /* SPMI MSG type */
+ uint16 spmimsg_id; /* SPMI MSG id */
+ uint16 spmimsg_dis; /* Disable or enable */
+} mws_spmitx_ctrl_v1_t;
+
/* MWS SCAN_REQ Bitmap */
typedef struct mws_scanreq_params {
uint16 idx;
@@ -17067,17 +18131,84 @@
uint16 bm_5g_hi;
} mws_scanreq_params_t;
+/* MWS BLNK bitmap v2 map for LTECX features */
+/* v2 map is for 4388 and future chips */
+/* to cover all 2g/5g/6g Channels */
+/* The first generation map is defined */
+/* by mws_scanreq_params_t */
+/* Not a ltecoex sub commands */
+
+#define LTECX_BLNK_BITMAP_VERSION_V2 2u
+
+/** flags indicating changed field */
+enum {
+ WL_MWS_BLNK_BITMAP_2G = (1 << 0), /* 2g field updated */
+ WL_MWS_BLNK_BITMAP_5G = (1 << 1), /* 5g field updated */
+ WL_MWS_BLNK_BITMAP_6G = (1 << 2) /* 6g field updated */
+};
+
+typedef struct {
+ uint16 version; /* Structure version */
+ uint16 length; /* Length of whole struct */
+ uint8 flags; /* Flags to indicate the updated field */
+ uint8 PAD;
+ uint16 idx;
+ uint16 bm_2G; /* 2G Bitmap */
+ uint16 bm_5G_lo; /* 5G lo bitmap */
+ uint16 bm_5G_mid; /* 5G mid bitmap */
+ uint16 bm_5G_hi; /* 5G hi bitmap */
+ uint16 bm_6G_lo_unii5; /* 6G lo bitmap UNII5 */
+ uint16 bm_6G_hi_unii5; /* 6G hi bitmap UNII5 */
+ uint16 bm_6G_unii6; /* 6G UNII6 bitmap */
+ uint16 bm_6G_unii7; /* 6G UNII7 bitmap */
+ uint16 bm_6G_unii8; /* 6G UNII8 bitmap */
+ uint8 PAD1[2]; /* Additional padding for 4byte alignment */
+} mws_blnk_bitmap_t;
+
/* Definitions for LTE coex iovar */
-#define WL_LTECX_VERSION 1
+#define WL_LTECX_VERSION_1 1
/* LTE coex IOV sub command IDs */
typedef enum ltecx_cmd_id {
- WL_LTECX_CMD_VER = 0, /* LTECX version sub command */
- WL_LTECX_TYPE7_2G_COEX_BITMAP = 1 /* Type7 enable/disable bitmap for 2G */
+ WL_LTECX_CMD_VER = 0, /* LTECX version sub command */
+ WL_LTECX_TYPE7_2G_COEX_BITMAP = 1, /* Type7 enable/disable bitmap for 2G */
+ WL_LTECX_COEX_BITMAP = 2, /* bitmaps to enable/disable Coex */
+ WL_LTECX_OCL_BITMAP = 3, /* bitmaps to enable/disable OCL by ltecoex */
+ WL_LTECX_ANT_MAP = 4, /* bitmaps for antenna selection */
+ WL_LTECX_SPMITX_CTRL = 5, /* to enable/disable SPMI TX MSG */
+ WL_LTECX_TYPE7_BITMAP = 6, /* bitmaps to enable/disable sending type7 */
+ WL_LTECX_BLNKREQ_BM = 7 /* to enable/disable blnk req */
} ltecx_cmd_id_t;
+/* MWS Type7 bitmap for LTECX feature */
+/* v1 bitmap is for 4388 and future chips */
+#define LTECX_TYPE7_BITMAP_VERSION_V1 1u
+
+/** flags indicating changed field */
+enum {
+ WL_MWS_TYPE7_BITMAP_2G = (1 << 0), /* 2g field updated */
+ WL_MWS_TYPE7_BITMAP_5G = (1 << 1), /* 5g field updated */
+ WL_MWS_TYPE7_BITMAP_6G = (1 << 2) /* 6g field updated */
+};
+
+typedef struct {
+ uint16 version; /* Structure version */
+ uint16 length; /* Length of whole struct */
+ uint8 flags; /* Flags to indicate the updated field */
+ uint8 PAD;
+ uint16 bitmap_2G; /* 2G Bitmap */
+ uint16 bitmap_5G_lo; /* 5G lo bitmap */
+ uint16 bitmap_5G_mid; /* 5G mid bitmap */
+ uint16 bitmap_5G_hi; /* 5G hi bitmap */
+ uint16 bitmap_6G_lo_unii5; /* 6G lo bitmap UNII5 */
+ uint16 bitmap_6G_hi_unii5; /* 6G hi bitmap UNII5 */
+ uint16 bitmap_6G_unii6; /* 6G UNII6 bitmap */
+ uint16 bitmap_6G_unii7; /* 6G UNII7 bitmap */
+ uint16 bitmap_6G_unii8; /* 6G UNII8 bitmap */
+} mws_type7_bitmap_v1_t;
+
/* MWS NR Coex Channel map */
-#define WL_MWS_NR_COEXMAP_VERSION 1
+#define WL_MWS_NR_COEXMAP_VERSION_1 1
typedef struct wl_mws_nr_coexmap {
uint16 version; /* Structure version */
uint16 bitmap_5g_lo; /* bitmap for 5G low channels by 2:
@@ -17106,7 +18237,7 @@
uint16 interval; /* interval between responses to the request */
} shub_req_t;
-#define WL_IF_STATS_T_VERSION 1 /**< current version of wl_if_stats structure */
+#define WL_IF_STATS_T_VERSION_1 1 /**< current version of wl_if_stats structure */
/** per interface counters */
typedef struct wl_if_stats {
@@ -17175,7 +18306,7 @@
uint16 PAD;
} wl_roam_stats_v1_t;
-#define WL_WLC_VERSION_T_VERSION 1 /**< current version of wlc_version structure */
+#define WL_WLC_VERSION_T_VERSION_1 1 /**< current version of wlc_version structure */
/** wlc interface version */
typedef struct wl_wlc_version {
@@ -17192,9 +18323,10 @@
uint16 wlc_ver_major; /**< wlc interface major version number */
uint16 wlc_ver_minor; /**< wlc interface minor version number */
}
+
wl_wlc_version_t;
-#define WL_SCAN_VERSION_T_VERSION 1 /**< current version of scan_version structure */
+#define WL_SCAN_VERSION_T_VERSION_1 1 /**< current version of scan_version structure */
/** scan interface version */
typedef struct wl_scan_version {
uint16 version; /**< version of the structure */
@@ -17207,13 +18339,13 @@
/* begin proxd definitions */
#include <packed_section_start.h>
-#define WL_PROXD_API_VERSION 0x0300u /**< version 3.0 */
+#define WL_PROXD_API_VERSION_3 0x0300u /**< version 3.0 */
/* proxd version with 11az */
#define WL_PROXD_11AZ_API_VERSION_1 0x0400u
/** Minimum supported API version */
-#define WL_PROXD_API_MIN_VERSION 0x0300u
+#define WL_PROXD_API_MIN_VERSION_3 0x0300u
/** proximity detection methods */
enum {
@@ -17241,7 +18373,8 @@
WL_PROXD_FLAG_MBURST_FOLLOWUP = 0x00000200, /* new multi-burst algorithm */
WL_PROXD_FLAG_SECURE = 0x00000400, /* per bsscfg option */
WL_PROXD_FLAG_NO_TSF_SYNC = 0x00000800, /* disable tsf sync */
- WL_PROXD_FLAG_SIGNED_RTT = 0x00002000, /* Send negative RTT/distance */
+ WL_PROXD_FLAG_AVB_TS = 0x00001000, /* Force AVB TimeStamping */
+ WL_PROXD_FLAG_SIGNED_RTT = 0x00002000, /* Send negative RTT to host */
WL_PROXD_FLAG_ALL = 0xffffffff
};
typedef uint32 wl_proxd_flags_t;
@@ -17410,7 +18543,9 @@
/** status - TBD BCME_ vs proxd status - range reserved for BCME_ */
enum {
- WL_PROXD_E_LAST = -1056,
+ WL_PROXD_E_LAST = -1058,
+ WL_PROXD_E_PKTFREED = -1058,
+ WL_PROXD_E_ASSOC_INPROG = -1057,
WL_PROXD_E_NOAVAIL = -1056,
WL_PROXD_E_EXT_SCHED = -1055,
WL_PROXD_E_NOT_BCM = -1054,
@@ -17507,7 +18642,7 @@
WL_PROXD_REQUEST_SENT = 0x0010, /* FTM request was sent */
WL_PROXD_REQUEST_ACKED = 0x0020, /* FTM request was acked */
WL_PROXD_LTFSEQ_STARTED = 0x0040, /* LTF sequence started */
- WL_PROXD_RESULT_SIGNED = 0x0080, /* RTT & Distance are negative */
+ WL_PROXD_RESULT_SIGNED = 0x0080, /* RTT result is negative */
WL_PROXD_RESULT_FLAG_ALL = 0xffff
};
typedef int16 wl_proxd_result_flags_t;
@@ -17647,7 +18782,7 @@
uint16 num_rtt; /* 0 if no detail */
uint16 num_meas; /* number of ftm frames seen OTA */
uint8 pad[2];
- wl_proxd_rtt_sample_v3_t rtt[BCM_FLEX_ARRAY]; /* variable len: first is avg_rtt */
+ wl_proxd_rtt_sample_v3_t rtt[]; /* variable len: first is avg_rtt */
} wl_proxd_rtt_result_v3_t;
/** aoa measurement result */
@@ -17895,6 +19030,9 @@
WL_PROXD_DEBUG_PKT = 0x00000100,
WL_PROXD_DEBUG_SEC = 0x00000200,
WL_PROXD_DEBUG_FSM = 0x00000400, /* BCM FSM log for FTM session */
+ WL_PROXD_DEBUG_CSI = 0x00000800, /* Enable CSI logging */
+ WL_PROXD_DEBUG_AZ_MEAS = 0x00001000, /* AZ measurement substate */
+ WL_PROXD_DEBUG_PM = 0x00002000,
WL_PROXD_DEBUG_EVENTLOG = 0x80000000, /* map/enable EVNET_LOG_TAG_PROXD_INFO */
WL_PROXD_DEBUG_ALL = 0xffffffff
};
@@ -18069,9 +19207,6 @@
#define WL_PROXD_EVENT_ENABLED(_mask, _event_type) (\
((_mask) & WL_PROXD_EVENT_MASK_EVENT(_event_type)) != 0)
-#define WL_FTM_EVENT_ENABLED(_mask, _event_type) \
- WL_PROXD_EVENT_ENABLED(_mask, _event_type)
-
/** proxd event - applies to proxd, method or session */
typedef struct wl_proxd_event {
uint16 version;
@@ -18216,17 +19351,35 @@
#define WL_ROAM_PROF_VER_2 2
#define WL_ROAM_PROF_VER_3 3
#define WL_ROAM_PROF_VER_4 4
+#define WL_ROAM_PROF_VER_5 5
#define WL_MAX_ROAM_PROF_VER WL_ROAM_PROF_VER_1
-#define WL_ROAM_PROF_NONE (0 << 0)
-#define WL_ROAM_PROF_LAZY (1 << 0)
-#define WL_ROAM_PROF_NO_CI (1 << 1)
-#define WL_ROAM_PROF_SUSPEND (1 << 2)
-#define WL_ROAM_PROF_EXTSCAN (1 << 3)
-#define WL_ROAM_FIND_HIGHER_BAND_ONLY (1 << 4) /* Flag to find better higher band AP */
-#define WL_ROAM_PROF_SYNC_DTIM (1 << 6)
-#define WL_ROAM_PROF_DEFAULT (1 << 7) /**< backward compatible single default profile */
+#define WL_ROAM_PROF_NONE (0u << 0u)
+#define WL_ROAM_PROF_LAZY (1u << 0u)
+#define WL_ROAM_PROF_NO_CI (1u << 1u)
+#define WL_ROAM_PROF_SUSPEND (1u << 2u)
+#define WL_ROAM_PROF_EXTSCAN (1u << 3u)
+#define WL_ROAM_FIND_HIGHER_BAND_ONLY (1u << 4u) /* Flag to find better higher band AP
+ * Not valid 4388 onwards
+ */
+#define WL_ROAM_PROF_SYNC_DTIM (1u << 6u)
+#define WL_ROAM_PROF_DEFAULT (1u << 7u) /* backward compatible single default profile */
+#define WL_ROAM_PROF_5G_PREF (1u << 8u) /* Flag to restrict low rssi roam scan to 5G */
+#define WL_ROAM_PROF_6G_PREF (1u << 9u) /* Flag to restrict low rssi roam scan to 6G */
+#define WL_ROAM_FORCE_6G_SC (1u << 10u) /* Force 6G lowrssi LP roam scan on Scan core */
+#define WL_ROAM_PROF_TIE_BREAKER_POLICY (1u << 11u) /* Prefer higher band target with same score */
+#define WL_ROAM_PROF_NONDFS_PREF (1u << 12u) /* Prefer non-DFS target with similar score */
+/* 2-bit flags to indicate AP with preferred TX power */
+#define WL_ROAM_PROF_POWER_PREF_BIT_OFFSET 13u /* Offset for Power Pref bit */
+#define WL_ROAM_PROF_POWER_PREF_BIT_MASK 0x3u /* Bit mask: bits 13 and 14 indicate power pref */
+#define WL_ROAM_PROF_SKIP_FILS (1u << 15u) /* Flag to skip FILS */
+
+typedef enum wl_roam_prof_power_pref {
+ WL_NO_POWER_PREF = 0x0u,
+ WL_LOW_POWER_PREF = 0x1u,
+ WL_HIGH_POWER_PREF = 0x2u
+} wl_roam_prof_power_pref_t;
#define WL_FACTOR_TABLE_MAX_LIMIT 5
@@ -18241,12 +19394,46 @@
#define WL_CU_PERCENTAGE_MAX 100
#define WL_CU_CALC_DURATION_DEFAULT 10 /* seconds */
#define WL_CU_CALC_DURATION_MAX 60 /* seconds */
+#define WL_CU_NOT_AVAIL -1
#define WL_ESTM_LOW_TRIGGER_DISABLE 0
#define WL_ESTM_LOW_TRIGGER_DEFAULT 5 /* Mbps */
#define WL_ESTM_LOW_TRIGGER_MAX 250 /* Mbps */
#define WL_ESTM_ROAM_DELTA_DEFAULT 10
+typedef struct wl_rssi_boost_v1 {
+ int8 thresh; /**< Min RSSI to qualify for RSSI boost */
+ int8 delta; /**< RSSI boost for AP in the other band */
+} wl_rssi_boost_v1_t;
+
+typedef struct wl_roam_prof_v6 {
+ uint32 roam_flags; /**< bit flags */
+ int8 roam_trigger; /**< RSSI trigger level per profile/RSSI bracket */
+ int8 rssi_lower;
+ int8 roam_delta;
+ int8 pad1;
+ /* if channel_usage if zero, roam_delta is rssi delta required for new AP */
+ /* if channel_usage if non-zero, roam_delta is score delta(%) required for new AP */
+ uint16 nfscan; /**< number of full scan to start with */
+ uint16 fullscan_period;
+ uint16 init_scan_period;
+ uint16 backoff_multiplier;
+ uint16 max_scan_period;
+ uint8 channel_usage;
+ uint8 cu_avg_calc_dur;
+ uint16 estm_low_trigger; /**< ESTM low throughput roam trigger */
+ int8 estm_roam_delta; /**< ESTM low throughput roam delta */
+ uint8 boost_bitmap; /* bitmap boost configuration for bands
+ * provided by user
+ */
+ uint16 cca_meas_span; /* cca meas start time in s before partial
+ * or full scan period
+ */
+ uint16 lp_roamscan_period;
+ uint16 max_fullscan_period;
+ wl_rssi_boost_v1_t rssi_boost[WL_BAND_MAX_CNT];
+} wl_roam_prof_v6_t;
+
typedef struct wl_roam_prof_v5 {
uint8 roam_flags; /**< bit flags */
int8 roam_trigger; /**< RSSI trigger level per profile/RSSI bracket */
@@ -18356,6 +19543,13 @@
uint16 max_scan_period;
} wl_roam_prof_v1_t;
+typedef struct wl_roam_prof_band_v6 {
+ uint32 band; /**< Must be just one band */
+ uint16 ver; /**< version of this struct */
+ uint16 len; /**< length in bytes of this structure */
+ wl_roam_prof_v6_t roam_prof[WL_MAX_ROAM_PROF_BRACKETS];
+} wl_roam_prof_band_v6_t;
+
typedef struct wl_roam_prof_band_v5 {
uint32 band; /**< Must be just one band */
uint16 ver; /**< version of this struct */
@@ -18392,7 +19586,7 @@
} wl_roam_prof_band_v1_t;
#define BSS_MAXTABLE_SIZE 10
-#define WNM_BSS_SELECT_FACTOR_VERSION 1
+#define WNM_BSS_SELECT_FACTOR_VERSION_1 1
typedef struct wnm_bss_select_factor_params {
uint8 low;
uint8 high;
@@ -18440,14 +19634,14 @@
#define WNM_BSS_SELECT_TYPE_CU 1
#define WNM_BSS_SELECT_TYPE_ESTM_DL 2
-#define WNM_BSSLOAD_MONITOR_VERSION 1
+#define WNM_BSSLOAD_MONITOR_VERSION_1 1
typedef struct wnm_bssload_monitor_cfg {
uint8 version;
uint8 band;
uint8 duration; /* duration between 1 to 20sec */
} wnm_bssload_monitor_cfg_t;
-#define WNM_ROAM_TRIGGER_VERSION 1
+#define WNM_ROAM_TRIGGER_VERSION_1 1
typedef struct wnm_roam_trigger_cfg {
uint8 version;
uint8 band;
@@ -18696,77 +19890,6 @@
wlc_btc_aibss_info_t aibss_info; // Structure definition above
} wlc_btc_aibss_status_t;
-typedef enum {
- STATE_NONE = 0,
-
- /* WLAN -> BT */
- W2B_DATA_SET = 21,
- B2W_ACK_SET = 22,
- W2B_DATA_CLEAR = 23,
- B2W_ACK_CLEAR = 24,
-
- /* BT -> WLAN */
- B2W_DATA_SET = 31,
- W2B_ACK_SET = 32,
- B2W_DATA_CLEAR = 33,
- W2B_ACK_CLEAR = 34
-} bwte_gci_intstate_t;
-
-#define WL_BWTE_STATS_VERSION 1 /* version of bwte_stats_t */
-typedef struct {
- uint32 version;
-
- bwte_gci_intstate_t inttobt;
- bwte_gci_intstate_t intfrombt;
-
- uint32 bt2wl_intrcnt; /* bt->wlan interrrupt count */
- uint32 wl2bt_intrcnt; /* wlan->bt interrupt count */
-
- uint32 wl2bt_dset_cnt;
- uint32 wl2bt_dclear_cnt;
- uint32 wl2bt_aset_cnt;
- uint32 wl2bt_aclear_cnt;
-
- uint32 bt2wl_dset_cnt;
- uint32 bt2wl_dclear_cnt;
- uint32 bt2wl_aset_cnt;
- uint32 bt2wl_aclear_cnt;
-
- uint32 state_error_1;
- uint32 state_error_2;
- uint32 state_error_3;
- uint32 state_error_4;
-} bwte_stats_t;
-
-#define TBOW_MAX_SSID_LEN 32
-#define TBOW_MAX_PASSPHRASE_LEN 63
-
-#define WL_TBOW_SETUPINFO_T_VERSION 1 /* version of tbow_setup_netinfo_t */
-typedef struct tbow_setup_netinfo {
- uint32 version;
- uint8 opmode;
- uint8 PAD;
- uint8 macaddr[ETHER_ADDR_LEN];
- uint32 ssid_len;
- uint8 ssid[TBOW_MAX_SSID_LEN];
- uint8 passphrase_len;
- uint8 passphrase[TBOW_MAX_PASSPHRASE_LEN];
- chanspec_t chanspec;
- uint8 PAD[2];
- uint32 channel;
-} tbow_setup_netinfo_t;
-
-typedef enum tbow_ho_opmode {
- TBOW_HO_MODE_START_GO = 0,
- TBOW_HO_MODE_START_STA,
- TBOW_HO_MODE_START_GC,
- TBOW_HO_MODE_TEST_GO,
- TBOW_HO_MODE_STOP_GO = 0x10,
- TBOW_HO_MODE_STOP_STA,
- TBOW_HO_MODE_STOP_GC,
- TBOW_HO_MODE_TEARDOWN
-} tbow_ho_opmode_t;
-
/* Beacon trim feature statistics */
/* configuration */
#define BCNTRIMST_PER 0 /* Number of beacons to trim (0: disable) */
@@ -18914,7 +20037,7 @@
#define TXPWRCAPSTATE_HOST_HIGH_WCI2_HIGH_CAP 3
/* IOVAR txcapconfig and txcapstate structure is shared: SET and GET */
-#define TXPWRCAPCTL_VERSION 2
+#define TXPWRCAPCTL_VERSION_2 2
#define TXPWRCAPCTL_VERSION_3 3
#define TXPWRCAPCTL_VERSION_4 4
@@ -18931,13 +20054,11 @@
typedef struct wl_txpwrcap_ctl_v4 {
uint8 version; /* TXPWRCAPCTL_VERSION_4 */
uint8 len; /* length of whole structure */
- uint8 ctl[]; /* variable length, one value per subgroup. Starts with legacy
- * 2 & 5G and continues with 6G
- */
+ uint8 ctl; /* one single value common for all subgroup. */
} wl_txpwrcap_ctl_v4_t;
/* IOVAR txcapdump structure: GET only */
-#define TXPWRCAP_DUMP_VERSION 2
+#define TXPWRCAP_DUMP_VERSION_2 2
typedef struct wl_txpwrcap_dump {
uint8 version;
uint8 pad0;
@@ -19148,6 +20269,58 @@
uint8 pwrs[][TXPWRCAP_MAX_NUM_CORES]; /* qdBm units */
} wl_txpwrcap_tbl_v2_t;
+/* Supported sar modes value for sar_enable IOVAR */
+typedef enum {
+ SAR_MODE_DISABLE = (0u),
+ SAR_MODE_HEAD = (1u << 0u),
+ SAR_MODE_GRIP = (1u << 1u),
+ SAR_MODE_NR_MW = (1u << 2u),
+ SAR_MODE_NR_SUB6 = (1u << 3u),
+ SAR_MODE_BT = (1u << 4u),
+ SAR_MODE_HS = (1u << 5u),
+ SAR_MODE_MHS = (1u << 6u),
+ SAR_MODE_MAX = (1u << 7u)
+} sar_modes_new;
+
+/* sub6 bandinfo valuse for s6bandinfo iovar */
+typedef enum {
+ NR_SUB6_BAND2 = 2u,
+ NR_SUB6_BAND25 = 25u,
+ NR_SUB6_BAND41 = 41u,
+ NR_SUB6_BAND48 = 48u,
+ NR_SUB6_BAND66 = 66u,
+ NR_SUB6_BAND77 = 77u,
+ NR_SUB6_BAND_UN = 0u
+} sar_sub6bandinfo_mode;
+
+/* sar cap states values */
+typedef enum {
+ SAR_CAP_AIR = (1u << 0u),
+ SAR_CAP_HEAD = (1u << 1u),
+ SAR_CAP_GRIP = (1u << 2u),
+ SAR_CAP_NRMW = (1u << 3u),
+ SAR_CAP_NRS6 = (1u << 4u),
+ SAR_CAP_BT = (1u << 5u),
+ SAR_CAP_HS = (1u << 6u),
+ SAR_CAP_RU = (1u << 7u),
+ SAR_CAP_MHS = (1u << 8u),
+ SAR_CAP_S6_BAND2 = (1u << 9u),
+ SAR_CAP_S6_BAND25 = (1u << 10u),
+ SAR_CAP_S6_BAND41 = (1u << 11u),
+ SAR_CAP_S6_BAND48 = (1u << 12u),
+ SAR_CAP_S6_BAND66 = (1u << 13u),
+ SAR_CAP_S6_BAND77 = (1u << 14u)
+} sar_caps;
+
+#define TXPWRCAP_SAR_STATE_SU 0u
+#define TXPWRCAP_SAR_MAX_STATES_SU_V3 1u
+
+#define TXPWRCAP_SAR_STATE_RU_26 1u
+#define TXPWRCAP_SAR_STATE_RU_56 2u
+#define TXPWRCAP_SAR_STATE_RU_106 3u
+#define TXPWRCAP_SAR_MAX_STATES_RU_V3 3u
+#define TXPWRCAP_SAR_MAX_STATES_SU_RU_V3 4u
+
typedef struct wl_txpwrcap_tbl_v3 {
uint8 version;
uint8 length; /* size of entire structure, including the pwrs */
@@ -19466,6 +20639,28 @@
uint8 opt_txdc_tgt; /* target txdc */
} dynsar_opt_profile_v1_t;
+typedef struct dynsar_opt_profile_v2 {
+ uint32 var_lim; /* variance limit */
+ uint32 var_off; /* hysterysis offset applied to variance while optimized */
+ uint8 pwr_off; /* power boost offset */
+ uint8 mode; /* DSA mode */
+ /* optimization parameters */
+ uint8 opt_dur; /* number of mon periods in future to predict optimization */
+ uint8 util_thrhd; /* Max history utilization before turning off optimization */
+ uint8 util_mean; /* Mean utilization percentage before turning off optimization */
+ /* failsafe parameters */
+ uint8 fs; /* historical util percentage to start failsafe */
+ uint8 util_mean_fs; /* Mean utilization to force failsafe */
+ uint8 avg_txdc_fs; /* mean txdc threshold for failsafe */
+ /* txdc limits */
+ uint8 util_mean_ddc; /* mean utilization threshold to apply avg_txdc_th */
+ uint8 opt_txdc; /* txdc cap when optimized */
+ uint8 avg_txdc_th; /* mean txdc threshold for throttling txdc */
+ uint8 opt_txdc_tgt; /* target txdc */
+ uint8 twin; /* Twin in seconds */
+ uint8 pad[3];
+} dynsar_opt_profile_v2_t;
+
typedef struct dynsar_opt_profiles_v1 {
uint16 ver;
uint16 len; /* length of this structure */
@@ -19474,6 +20669,16 @@
dynsar_opt_profile_v1_t profiles[];
} dynsar_opt_profiles_v1_t;
+typedef struct dynsar_opt_profiles_v2 {
+ uint16 ver;
+ uint16 len; /* length of this structure */
+ uint16 active; /* active profile */
+ uint16 num_profiles; /* number of profiles in variable length below */
+ dynsar_opt_profile_v2_t profiles[];
+} dynsar_opt_profiles_v2_t;
+
+typedef dynsar_opt_profiles_v2_t dynsar_opt_profiles_t;
+
typedef struct wl_dynsar_ioc {
uint16 id; /* ID of the sub-command */
uint16 len; /* total length of all data[] */
@@ -19491,6 +20696,7 @@
dynsar_var_info_t var;
dynsar_opt_profile_t profile;
dynsar_opt_profiles_v1_t profiles;
+ dynsar_opt_profiles_v2_t profilesv2;
} data;
} wl_dynsar_ioc_t;
@@ -20418,7 +21624,7 @@
/** IOVAR 'mu_group' parameter. Used to set and read MU group recommendation setting */
#define WL_MU_GROUP_AUTO_COMMAND -1
-#define WL_MU_GROUP_PARAMS_VERSION 3
+#define WL_MU_GROUP_PARAMS_VERSION_3 3
#define WL_MU_GROUP_METHOD_NAMELEN 64
#define WL_MU_GROUP_NGROUP_MAX 15
#define WL_MU_GROUP_NUSER_MAX 4
@@ -20477,7 +21683,7 @@
#define WL_MUPKTENG_PER_TX_STOP 0x20
/** IOVAR 'mu_policy' parameter. Used to configure MU admission control policies */
-#define WL_MU_POLICY_PARAMS_VERSION 1
+#define WL_MU_POLICY_PARAMS_VERSION_1 1
#define WL_MU_POLICY_SCHED_DEFAULT 60
#define WL_MU_POLICY_DISABLED 0
#define WL_MU_POLICY_ENABLED 1
@@ -20530,7 +21736,7 @@
} ulb_bw_type_t;
/* endif WL11ULB */
-#define WL_MESH_IOCTL_VERSION 1
+#define WL_MESH_IOCTL_VERSION_1 1
#define MESH_IOC_BUFSZ 512 /* sufficient ioc buff size for mesh */
#ifdef WLMESH
@@ -20554,7 +21760,7 @@
mesh_peer_info_ext_t mpi_ext[BCM_FLEX_ARRAY];
} mesh_peer_info_dump_t;
-#define WL_MESH_PEER_RES_FIXED_SIZE (sizeof(mesh_peer_info_dump_t) - sizeof(mesh_peer_info_ext_t))
+#define WL_MESH_PEER_RES_FIXED_SIZE (OFFSETOF(mesh_peer_info_dump_t, mpi_ext))
#endif /* WLMESH */
/* container for mesh ioctls & events */
@@ -20590,7 +21796,7 @@
/* endif WLMESH */
/* Fast BSS Transition parameter configuration */
-#define FBT_PARAM_CURRENT_VERSION 0
+#define FBT_PARAM_VERSION_0 0u
typedef struct _wl_fbt_params {
uint16 version; /* version of the structure
@@ -20613,7 +21819,7 @@
#define WL_FBT_PARAM_TYPE_FIRST_INVALID 0x7
/* Assoc Mgr commands for fine control of assoc */
-#define WL_ASSOC_MGR_CURRENT_VERSION 0x0
+#define WL_ASSOC_MGR_VERSION_0 0u
typedef struct {
uint16 version; /* version of the structure as
@@ -20777,8 +21983,8 @@
/* SensorHub Interworking mode */
-#define SHUB_CONTROL_VERSION 1
-#define SHUB_CONTROL_LEN 12
+#define SHUB_CONTROL_VERSION_1 1u
+#define SHUB_CONTROL_LEN 12u
typedef struct {
uint16 verison;
@@ -20899,7 +22105,7 @@
} rsdb_config_xtlv_t;
/* Definitions for slot_bss chanseq iovar */
-#define WL_SLOT_BSS_VERSION 1
+#define WL_SLOT_BSS_VERSION_1 1
/* critical slots max size */
#define WL_SLOTTED_BSS_CS_BMP_CFG_MAX_SZ 128 /* arbitrary */
@@ -20966,8 +22172,8 @@
#define WL_SLICE_CHAN_SEQ_FIXED_LEN OFFSETOF(slice_chan_seq_t, chanspecs)
/* Definitions for slotted_bss stats */
-#define SBSS_STATS_VERSION 1
-#define SBSS_STATS_CURRENT_VERSION SBSS_STATS_VERSION
+
+#define SBSS_STATS_VERSION_1 1
#define SBSS_MAX_CHAN_STATS 4
@@ -21028,6 +22234,7 @@
#define NAP_DISABLED_CHANSWITCH 0x0080 /* Disabled during channel switch */
#define NAP_DISABLED_AZ 0x0100 /* Disabled during 802.11az ranging */
#define NAP_DISABLED_PHYTS 0x0200 /* Disabled during PHYTS */
+#define NAP_DISABLED_CAL 0x0400 /* Disabled during rxiqcal */
/* Bits for hw_status */
#define NAP_HWCFG 0x01 /* State of NAP config bit in phy HW */
@@ -21398,6 +22605,7 @@
BCM_RX_HC_UNICAST_REPLAY = 4, /* Unicast replay */
BCM_RX_HC_BCMC_REPLAY = 5, /* BCMC replay */
BCM_RX_HC_AMPDU_DUP = 6, /* AMPDU DUP */
+ BCM_RX_HC_BCMC_KEYIDMATCH_FAIL = 7, /* BCMC decrypt fail due to key index mismatch */
BCM_RX_HC_MAX
} bcm_rx_hc_stall_reason_t;
@@ -21570,6 +22778,7 @@
uint16 param1;
uint8 event_count;
uint8 noa_invert;
+ uint32 pre_end_event_intmsk_bmp;
} wl_heb_blk_params_v1_t;
typedef struct wl_heb_int_status_v1 {
@@ -21648,16 +22857,10 @@
/* TWT Setup descriptor */
-/* Any change to wl_twt_sdesc is not possible without affecting this ROMed structure
- * in various current branches. Hence to use new updated structure wl_twt_sdesc_v1
- * typecast it to wl_twt_sdesc_t and define WL_TWT_SDESC_TYPEDEF_HAS_ALIAS
- * in required branches
- */
-#ifndef WL_TWT_SDESC_TYPEDEF_HAS_ALIAS
-typedef struct wl_twt_sdesc {
+typedef struct wl_twt_sdesc_v0 {
/* Setup Command. */
- uint8 setup_cmd; /* See TWT_SETUP_CMD_XXXX in 802.11ah.h */
- uint8 flow_flags; /* Flow attributes. See WL_TWT_FLOW_FLAG_XXXX below */
+ uint8 setup_cmd; /* See TWT_SETUP_CMD_XXXX in 802.11ah.h */
+ uint8 flow_flags; /* Flow attributes. See WL_TWT_FLOW_FLAG_XXXX below */
uint8 flow_id; /* must be between 0 and 7. Set 0xFF for auto assignment */
uint8 bid; /* must be between 0 and 31. Set 0xFF for auto assignment */
uint8 channel; /* Twt channel - Not used for now */
@@ -21674,13 +22877,11 @@
uint8 PAD;
/* deprecated - to be removed */
uint16 li;
-} wl_twt_sdesc_t;
-#endif /* WL_TWT_SDESC_TYPEDEF_HAS_ALIAS */
+} wl_twt_sdesc_v0_t;
#define WL_TWT_SETUP_DESC_VER 1u
-
/* TWT Setup descriptor (Version controlled) */
-struct wl_twt_sdesc_v1 {
+typedef struct wl_twt_sdesc_v1 {
/* structure control */
uint16 version; /* structure version */
uint16 length; /* data length (starting after this field) */
@@ -21701,7 +22902,7 @@
uint32 wake_int_min; /* Min. wake interval allowed for TWT Setup */
uint32 wake_dur_min; /* Min. wake duration allowed for TWT Setup */
uint32 wake_dur_max; /* Max. wake duration allowed for TWT Setup */
-};
+} wl_twt_sdesc_v1_t;
#define WL_TWT_CONFIG_DESC_VER 1u
@@ -21790,22 +22991,28 @@
#define WL_TWT_SETUP_VER 0u
/* HE TWT Setup command */
-typedef struct wl_twt_setup {
+typedef struct wl_twt_setup_v0 {
/* structure control */
uint16 version; /* structure version */
uint16 length; /* data length (starting after this field) */
struct ether_addr peer; /* Peer address - leave it all 0s' for AP */
uint8 PAD[2];
-#ifndef WL_TWT_SDESC_TYPEDEF_HAS_ALIAS /* Use either legacy structure or
- * the new versioned structure
- */
- wl_twt_sdesc_t desc; /* Setup Descriptor */
-#else
- struct wl_twt_sdesc_v1 desc;
-#endif /* WL_TWT_SDESC_TYPEDEF_HAS_ALIAS */
+ struct wl_twt_sdesc_v0 desc;
uint16 dialog; /* Deprecated - to be removed */
uint8 PAD[2];
-} wl_twt_setup_t;
+} wl_twt_setup_v0_t;
+
+/* HE TWT Setup command */
+typedef struct wl_twt_setup_v1 {
+ /* structure control */
+ uint16 version; /* structure version */
+ uint16 length; /* data length (starting after this field) */
+ struct ether_addr peer; /* Peer address - leave it all 0s' for AP */
+ uint8 PAD[2];
+ struct wl_twt_sdesc_v1 desc;
+ uint16 dialog; /* Deprecated - to be removed */
+ uint8 PAD[2];
+} wl_twt_setup_v1_t;
#define WL_TWT_CONFIG_VER 0u
@@ -21892,7 +23099,7 @@
#define WL_TWT_STATUS_FLAG_WAKE_STATE (1u << 1u)
#define WL_TWT_STATUS_FLAG_WAKE_OVERRIDE (1u << 2u)
-typedef struct wl_twt_status {
+typedef struct wl_twt_status_v0 {
uint8 state; /* TWT State */
uint8 heb_id; /* HEB ID */
uint8 configID; /* TWT Configuration ID */
@@ -21901,14 +23108,10 @@
uint8 PAD[2];
uint32 avg_pkt_num; /* Average Packet number per TWT SP Interval */
uint32 avg_pkt_size; /* Average Packet size for TWT SP */
-#ifndef WL_TWT_SDESC_TYPEDEF_HAS_ALIAS /* Use either legacy structure or
- * the new versioned structure
- */
- wl_twt_sdesc_t desc; /* Setup Descriptor */
-#else
- struct wl_twt_sdesc_v1 desc;
-#endif /* WL_TWT_SDESC_TYPEDEF_HAS_ALIAS */
-} wl_twt_status_t;
+ struct wl_twt_sdesc_v0 desc;
+} wl_twt_status_v0_t;
+
+typedef wl_twt_status_v0_t wl_twt_status_t;
/* wl twt status output */
typedef struct wl_twt_status_v1 {
@@ -21917,8 +23120,8 @@
uint8 num_fid; /* Number of individual TWT setup */
uint8 num_bid; /* Number of Broadcast TWT setup */
uint16 status_flags; /* see WL_TWT_STATUS_FLAGS_XX */
- wl_twt_status_t itwt_status[WL_TWT_MAX_ITWT];
- wl_twt_status_t btwt_status[WL_TWT_MAX_BTWT];
+ wl_twt_status_v0_t itwt_status[WL_TWT_MAX_ITWT];
+ wl_twt_status_v0_t btwt_status[WL_TWT_MAX_BTWT];
} wl_twt_status_v1_t;
/* wl twt status command input */
@@ -22059,6 +23262,11 @@
WL_EHT_CMD_ENAB = 0u, /* enable/disable EHT feature as a whole */
WL_EHT_CMD_FEATURES = 2u, /* configure EHT sub-features */
+ WL_EHT_CMD_SIGMCS = 3u, /* configure EHT SIG MCS Index */
+ WL_EHT_CMD_NUMLTF = 4u, /* configure EHT Number of LTFs */
+ WL_EHT_CMD_NONHT_PUNC_PATT = 5u, /* configure nonHT puncture pattern */
+ WL_EHT_CMD_PUNC_PAT = 6u, /* configure per BSS puncture pattern */
+
/* Add new sub command IDs here... */
/* debug/test related sub-commands, mogrify? */
@@ -22070,15 +23278,23 @@
WL_MLO_CMD_ENAB = 0u, /* enable/disable MLO feature as a whole */
WL_MLO_CMD_CONFIG = 1u, /* configure MLO feature - bsscfg specific */
WL_MLO_CMD_STATUS = 2u, /* status on MLO feature - interface specific */
+ WL_MLO_CMD_EMLSR_CTRL = 3u, /* emlsr control - interface specific */
+ WL_MLO_CMD_TID_MAP = 4u, /* configure TID-To-Link Mapping */
+ WL_MLO_CMD_CAP = 5u, /* capability of MLO feature as a whole */
/* Add new sub command IDs here... */
/* debug/test related sub-commands, mogrify? */
WL_MLO_CMD_MLD_PRB = 0x1000u, /* send a mld probe request frame */
+ WL_MLO_CMD_TID_MAP_NEG = 0x1001u, /* start a TID-to-Link Mapping negotiation */
+ WL_MLO_CMD_MLD_AP_OP = 0x1002u, /* add/remove MLD AP(s) to/from MLD */
WL_MLO_CMD_MLOSIM = 0x2000u, /* to set mlo simulation option */
};
/* MLO config Flags definition */
-#define WL_MLO_USE_FW_GEN_LINKADDR (1u << 0u)
+#define WL_MLO_USE_FW_GEN_LINKADDR (1u << 0u) /* fw generates the link addresses */
+#define WL_MLO_USE_FW_GEN_MLDADDR (1u << 1u) /* fw generates the mld address */
+#define WL_MLO_UPDATE_CHANNELS (1u << 2u) /* channels are present in the config req */
+#define WL_MLO_LINK_INTERFACES (1u << 3u) /* link existing interfaces as mlo links */
typedef struct wl_mlo_link_config_v1 {
struct ether_addr link_addr; /* Link specific address */
@@ -22092,6 +23308,7 @@
#define WL_MLO_MODE_INVALID (0xFFu)
#define WL_MLO_CONFIG_VER_1 (1u)
+
typedef struct wl_mlo_config_v1 {
uint16 version;
uint16 length;
@@ -22104,8 +23321,8 @@
/* mlo info structure per link */
typedef struct wl_mlo_link_status_v1 {
- uint8 link_id; /* link index */
- uint8 pad;
+ uint8 link_id; /* link ID - AP managed unique # */
+ uint8 link_idx; /* link index - link config idx */
struct ether_addr link_addr; /* Link specific address */
chanspec_t chanspec; /* Chanspec */
} wl_mlo_link_status_v1_t;
@@ -22137,8 +23354,149 @@
wl_mlo_link_status_v1_t link_status[]; /* status on operative links */
} wl_mlo_status_v1_t;
+/* mlo cap structure
+ *
+ * max_mlo_links : value 0 means MLO is unsupported
+ * max_str_links : value 0 means STR is unsupported
+ * max_emlsr_links : value 0 means EMLSR is unsupported
+ *
+ * The number of links is represented as the actual value similar to 'mlo config' IOVar and
+ * is not like how it is in the 11be MLO spec (num links - 1).
+ */
+#define WL_MLO_CAP_VER_1 (1u)
+
+typedef struct wl_mlo_cap_v1 {
+ uint16 version;
+ uint16 length;
+ uint8 max_mlo_links; /* Maximum number of MLO links supported */
+ uint8 max_str_links; /* Maximum number of STR links supported */
+ uint8 max_emlsr_links; /* Maximum number of EMLSR links supported */
+ uint8 PAD;
+} wl_mlo_cap_v1_t;
+
+// #ifdef EHT_MAC_SW_TEST
+/* IDs list/ID extensions list */
+typedef struct wl_mlo_prb_ids_reqs {
+ uint8 pad[3];
+ /* (Extended) Request parameters (max. 2 entries with max. 14 IDs each) */
+ uint8 num_req; /* # valid reqs */
+ struct {
+ uint8 id_base; /* 0 for Request IE; 255 for Extended Request IE */
+ uint8 ids_num; /* # valid IDs */
+ uint8 ids_list[14];
+ } req[2];
+} wl_mlo_prb_ids_reqs_t;
+
+/* Per-STA profile parameters */
+typedef struct wl_mlo_prb_psta_prfs {
+ uint8 pad[3];
+ /* Per-STA Profile parameters (max. 1 entry) */
+ uint8 num_prf; /* # valid prfs */
+ struct {
+ uint8 link_id;
+ uint8 cplt_sta_prf; /* complete/partial STA profile */
+ uint8 pad[2];
+ wl_mlo_prb_ids_reqs_t ids;
+ } prf[1];
+} wl_mlo_prb_psta_prfs_t;
+
+/* MLD probe parameters */
+typedef struct wl_probe_mld_parms {
+ uint8 flags; /* see WL_MLO_PRB_FLAG_x */
+ uint8 mld_id; /* spec. MLD ID of this ML prbreq */
+ uint8 pad[2];
+ wl_mlo_prb_ids_reqs_t ids; /* Request IDs in reporting STA */
+ wl_mlo_prb_psta_prfs_t psta; /* Per-STA profile for reported STA */
+} wl_probe_mld_parms_t;
+
+/* wl_probe_mld_parms_t.flags definitions */
+#define WL_MLO_PRB_FLAG_MLD_ID (1u << 0) /* mld_id field is present */
+
+/* current mld prb subcommand */
+typedef struct wl_mlo_mld_prb_parms {
+ wl_probe_params_t probe; /* destination parameters */
+ wl_probe_mld_parms_t mld; /* MLD probe parameters */
+} wl_mlo_mld_prb_parms_t;
+// #endif /* EHT_MAC_SW_TEST */
+
+/* TID-to-Link Mapping negotiation */
+typedef struct wl_mlo_tid_map_neg_v1 {
+ uint16 version;
+ uint16 length;
+ uint8 action; /* EHT_PAF_ACT_TID_MAP_x in 802.11be.h */
+ uint8 pad[3];
+ uint8 data[]; /* action specific data:
+ * - EHT_PAF_ACT_TID_MAP_REQ: struct ether_addr;
+ */
+} wl_mlo_tid_map_neg_v1_t;
+
+/* TID-to-Link mapping */
+#define WL_MLO_TID_MAP_VER_1 (1u)
+
+typedef struct wl_mlo_link_tid_map_v1 {
+ uint8 link_id; /* id of the link */
+ uint8 tid_map; /* tids mapped to the link (represented as bit position) */
+ uint8 pad[2];
+} wl_mlo_link_tid_map_v1_t;
+
+typedef struct wl_mlo_tid_map_v1 {
+ uint16 version;
+ uint16 length;
+ uint8 direction; /* direction */
+ uint8 num_links; /* number of links */
+ uint8 pad[2];
+ wl_mlo_link_tid_map_v1_t link_tid_map[]; /* TID to link mapping */
+} wl_mlo_tid_map_v1_t;
+
+#define TID_TO_LINK_MAP_SIZE(tid_map) \
+ (OFFSETOF(wl_mlo_tid_map_v1_t, link_tid_map) + \
+ (tid_map->num_links * sizeof(wl_mlo_link_tid_map_v1_t)))
+
+/* MLO emlsr ctrl shift definition */
+#define WL_MLO_EMLSR_CTRL_FLAGS_MURTS_EN_SHIFT (0u)
+#define WL_MLO_EMLSR_CTRL_FLAGS_SWITCH_EN_SHIFT (1u)
+#define WL_MLO_EMLSR_CTRL_FLAGS_GPIO_CFG_SHIFT (2u)
+
+/* MLO emlsr ctrl Flags definition */
+#define WL_MLO_EMLSR_CTRL_FLAGS_MURTS_EN (1u << WL_MLO_EMLSR_CTRL_FLAGS_MURTS_EN_SHIFT)
+#define WL_MLO_EMLSR_CTRL_FLAGS_SWITCH_EN (1u << WL_MLO_EMLSR_CTRL_FLAGS_SWITCH_EN_SHIFT)
+#define WL_MLO_EMLSR_CTRL_FLAGS_GPIO_CFG (1u << WL_MLO_EMLSR_CTRL_FLAGS_GPIO_CFG_SHIFT)
+
+/* setting values in params: note: reusing some of the flags */
+#define WL_MLO_EMLSR_CTRL_SET_MURTS_EN(val, en) \
+ (en) ? (val |= WL_MLO_EMLSR_CTRL_FLAGS_MURTS_EN) : \
+ (val &= ~WL_MLO_EMLSR_CTRL_FLAGS_MURTS_EN)
+#define WL_MLO_EMLSR_CTRL_SET_SWITCH_EN(val, en) \
+ (en) ? (val |= WL_MLO_EMLSR_CTRL_FLAGS_SWITCH_EN) : \
+ (val &= ~WL_MLO_EMLSR_CTRL_FLAGS_SWITCH_EN)
+
+/* Note: flags reused here for checking params also. DONOT use for mac addr */
+#define WL_MLO_EMLSR_CTRL_IS_SET(val, flag) (val & flag) ? 1u : 0u
+
+#define WL_MLO_EMLSR_CTRL_VER_1 (1u)
+typedef struct wl_mlo_emlsr_ctrl_v1 {
+ uint16 version;
+ uint16 length;
+ uint32 flags; /* Flags to enable/disable */
+ uint32 params; /* params corresponding to flags */
+ uint16 murts_ctrl; /* murts_ctrl value if murts_en is 1 */
+ uint16 PAD;
+ uint32 gpio_cfg; /* GPIO pin numbers used in EMLSR emulation */
+} wl_mlo_emlsr_ctrl_v1_t;
+
+/* WL_MLO_CMD_MLD_AP_OP opcode */
+#define WL_MLO_CMD_MLD_AP_OP_DEL 0u
+#define WL_MLO_CMD_MLD_AP_OP_ADD 1u
+
+/* MLD AP operation parameters */
+typedef struct wl_mlo_mld_ap_op {
+ uint8 op_code; /* WL_MLO_CMD_MLD_AP_OP_ADD/DEL */
+ uint8 link_id;
+ uint16 del_timer; /* delete timer in units of TBTT */
+} wl_mlo_mld_ap_op_t;
+
/* Current version for wlc_clm_power_limits_req_t structure and flags */
-#define WLC_CLM_POWER_LIMITS_REQ_VERSION 1
+#define WLC_CLM_POWER_LIMITS_REQ_VERSION_1 1
/* "clm_power_limits" iovar request structure */
typedef struct wlc_clm_power_limits_req {
/* Input. Structure and flags version */
@@ -22178,11 +23536,12 @@
/* Output. Limits taken from country-default (all-product) data */
#define WLC_CLM_POWER_LIMITS_OUTPUT_FLAG_DEFAULT_COUNTRY_LIMITS 0x00000004
-#define WL_MBO_IOV_MAJOR_VER 1
-#define WL_MBO_IOV_MINOR_VER 1
#define WL_MBO_IOV_MAJOR_VER_SHIFT 8
-#define WL_MBO_IOV_VERSION \
- ((WL_MBO_IOV_MAJOR_VER << WL_MBO_IOV_MAJOR_VER_SHIFT)| WL_MBO_IOV_MINOR_VER)
+#define WL_MBO_IOV_MAJOR_VER_1 1u
+#define WL_MBO_IOV_MINOR_VER_1 1u
+
+#define WL_MBO_IOV_VERSION_1_1 \
+ ((WL_MBO_IOV_MAJOR_VER_1 << WL_MBO_IOV_MAJOR_VER_SHIFT) | WL_MBO_IOV_MINOR_VER_1)
#define MBO_MAX_CHAN_PREF_ENTRIES 16
@@ -22276,11 +23635,13 @@
uint16 wifi_to_cell;
} wl_mbo_counters_t;
-#define WL_FILS_IOV_MAJOR_VER 1
-#define WL_FILS_IOV_MINOR_VER 1
-#define WL_FILS_IOV_MAJOR_VER_SHIFT 8
-#define WL_FILS_IOV_VERSION \
- ((WL_FILS_IOV_MAJOR_VER << WL_FILS_IOV_MAJOR_VER_SHIFT)| WL_FILS_IOV_MINOR_VER)
+#define WL_FILS_IOV_MAJOR_VER_SHIFT 8u
+
+#define WL_FILS_IOV_MAJOR_VER_1 1u
+#define WL_FILS_IOV_MINOR_VER_1 1u
+
+#define WL_FILS_IOV_VERSION_1_1 \
+ ((WL_FILS_IOV_MAJOR_VER_1 << WL_FILS_IOV_MAJOR_VER_SHIFT) | WL_FILS_IOV_MINOR_VER_1)
enum wl_fils_cmd_ids {
WL_FILS_CMD_ADD_IND_IE = 1,
@@ -22306,11 +23667,11 @@
WL_FILS_XTLV_PMKID = 0xb
};
-#define WL_OCE_IOV_MAJOR_VER 1
-#define WL_OCE_IOV_MINOR_VER 1
+#define WL_OCE_IOV_MAJOR_VER_1 1
+#define WL_OCE_IOV_MINOR_VER_1 1
#define WL_OCE_IOV_MAJOR_VER_SHIFT 8
-#define WL_OCE_IOV_VERSION \
- ((WL_OCE_IOV_MAJOR_VER << WL_OCE_IOV_MAJOR_VER_SHIFT)| WL_OCE_IOV_MINOR_VER)
+#define WL_OCE_IOV_VERSION_1_1 \
+ ((WL_OCE_IOV_MAJOR_VER_1 << WL_OCE_IOV_MAJOR_VER_SHIFT)| WL_OCE_IOV_MINOR_VER_1)
enum wl_oce_cmd_ids {
WL_OCE_CMD_VERSION = 0u,
@@ -22344,11 +23705,11 @@
OCE_FEATURE_FLAG_UCAST_PROBE_RESP = (1u << 0u) /* bit 0 */
} oce_feature_flags_t;
-#define WL_IGMPOE_IOV_MAJOR_VER 1
-#define WL_IGMPOE_IOV_MINOR_VER 1
+#define WL_IGMPOE_IOV_MAJOR_VER_1 1
+#define WL_IGMPOE_IOV_MINOR_VER_1 1
#define WL_IGMPOE_IOV_MAJOR_VER_SHIFT 8
-#define WL_IGMPOE_IOV_VERSION \
- ((WL_IGMPOE_IOV_MAJOR_VER << WL_IGMPOE_IOV_MAJOR_VER_SHIFT)| WL_IGMPOE_IOV_MINOR_VER)
+#define WL_IGMPOE_IOV_VERSION_1_1 \
+ ((WL_IGMPOE_IOV_MAJOR_VER_1 << WL_IGMPOE_IOV_MAJOR_VER_SHIFT)| WL_IGMPOE_IOV_MINOR_VER_1)
enum wl_igmpoe_cmd_ids {
WL_IGMPOE_CMD_VERSION = 0u,
@@ -22380,7 +23741,7 @@
wl_igmp_entry_t data[];
} wl_igmp_table_t;
-#define WL_IGMP_STATS_VERSION 1u /* igmpoe stats IOVAR version */
+#define WL_IGMP_STATS_VERSION_1 1u /* igmpoe stats IOVAR version */
typedef struct wl_igmp_stats_v1 {
uint16 version;
uint16 len;
@@ -22398,6 +23759,10 @@
uint32 igmp_tx_report; /* # of times igmp report is txed from fw */
uint32 igmp_nohostip; /* # of times igmp query is fwded to host */
+ uint32 igmp_del_source_succ; /* # of times igmp source entry delete succeeded */
+ uint32 igmp_del_source_fail; /* # of times igmp source entry delete failed */
+ uint32 igmp_add_source_succ; /* # of times igmp source entry add succeeded */
+ uint32 igmp_add_source_fail; /* # of times igmp source entry add failed */
} wl_igmp_stats_t;
/* qos commands */
@@ -22416,13 +23781,6 @@
WL_QOS_CMD_RAV_SCS_CT10 = 6u /* qos rav_scs ct10 */
} wl_qos_cmd_id_e;
-typedef enum wl_qos_xtlv_id {
- WL_QOS_XTLV_VERSION = 0u,
- WL_QOS_XTLV_ENABLE = 1u,
- WL_QOS_XTLV_RAV_MSCS = 2u,
- WL_QOS_XTLV_RAV_SCS = 3u
-} wl_qos_xtlv_id_e;
-
/* QoS enable subcommand flags */
typedef enum qos_cmd_enable_flags {
WL_QOS_CMD_ENABLE_FLAG_RAV_MSCS = (1u << 0u), /* bit 0 */
@@ -22446,6 +23804,10 @@
/* Unable to transmit the action frame */
WL_QOS_RAV_MSCS_STATUS_TX_FAILURE = (1u << 4u), /* bit 4 */
+
+ /* Indicates that the MSCS is active */
+ WL_QOS_RAV_MSCS_STATUS_ACTIVE = (1u << 5u), /* bit 5 */
+
} wl_qos_rav_mscs_status_flags_e;
#define WL_QOS_RAV_MSCS_SC_VERSION_1 1u /* rav_mscs subcommand version */
@@ -22462,49 +23824,6 @@
uint16 status_code; /* IEEE status code */
} wl_qos_rav_mscs_config_v1_t;
-/* Robust Audio Video (RAV), MSCS (Mirrored Stream Classification Service) commands */
-#define WL_RAV_MSCS_IOV_MAJOR_VER 1u
-#define WL_RAV_MSCS_IOV_MINOR_VER 1u
-#define WL_RAV_MSCS_IOV_MAJOR_VER_SHIFT 8u
-
-#define WL_RAV_MSCS_IOV_VERSION \
- ((WL_RAV_MSCS_IOV_MAJOR_VER << WL_RAV_MSCS_IOV_MAJOR_VER_SHIFT)| WL_RAV_MSCS_IOV_MINOR_VER)
-
-enum wl_rav_mscs_cmd_ids {
- WL_RAV_MSCS_CMD_CONFIG = 1u, /* MSCS configuration */
- WL_RAV_MSCS_CMD_ENABLE = 2u, /* Activate/deactivate MSCS */
- WL_RAV_MSCS_CMD_UP_BITMAP = 3u, /* User priority bitmap */
- WL_RAV_MSCS_CMD_UP_LIMIT = 4u, /* User priority limit */
- WL_RAV_MSCS_CMD_STREAM_TIMEOUT = 5u, /* Stream timeout for MSCS Request */
- WL_RAV_MSCS_CMD_FC_TYPE = 6u, /* Frame classifier type, IPv4, IPv6, etc. */
- WL_RAV_MSCS_CMD_FC_MASK = 7u, /* Specifies the frame classifier mask */
- WL_RAV_MSCS_CMD_REQ_TYPE = 8u, /* Indicates the MSCS Request type (add/remove) */
- WL_RAV_MSCS_CMD_ASSOC_NEG = 9u, /* MSCS negotiation in the association */
-
- /* Add before this !! */
- WL_RAV_MSCS_CMD_LAST
-};
-
-typedef enum wl_rav_mscs_xtlv_id {
- WL_RAV_MSCS_XTLV_CONFIG = 1u,
- WL_RAV_MSCS_XTLV_ENABLE = 2u,
- WL_RAV_MSCS_XTLV_UP_BITMAP = 3u,
- WL_RAV_MSCS_XTLV_UP_LIMIT = 4u,
- WL_RAV_MSCS_XTLV_STREAM_TIMEOUT = 5u,
- WL_RAV_MSCS_XTLV_FC_TYPE = 6u,
- WL_RAV_MSCS_XTLV_FC_MASK = 7u,
- WL_RAV_MSCS_XTLV_REQ_TYPE = 8u,
- WL_RAV_MSCS_XTLV_ASSOC_NEG = 9u
-} wl_rav_mscs_xtlv_id_t;
-
-/* Robust Audio Video (RAV), SCS(Stream Classification Service) commands */
-#define WL_RAV_SCS_IOV_MAJOR_VER 1u
-#define WL_RAV_SCS_IOV_MINOR_VER 1u
-#define WL_RAV_SCS_IOV_MAJOR_VER_SHIFT 8u
-
-#define WL_RAV_SCS_IOV_VERSION \
- ((WL_RAV_SCS_IOV_MAJOR_VER << WL_RAV_SCS_IOV_MAJOR_VER_SHIFT)| WL_RAV_SCS_IOV_MINOR_VER)
-
typedef enum wl_qos_rav_scs_flags {
/* If bit0 is 1 which indicates to send the SCS action frame to the AP */
WL_QOS_RAV_SCS_FLAGS_COMMIT = (1u << 0u) /* bit 0 */
@@ -22563,11 +23882,11 @@
wl_qos_rav_scsc_ct10_filter_data_t filter_data[];
} wl_qos_rav_scs_ct10_v1_t;
-#define WL_ESP_IOV_MAJOR_VER 1
-#define WL_ESP_IOV_MINOR_VER 1
+#define WL_ESP_IOV_MAJOR_VER_1 1
+#define WL_ESP_IOV_MINOR_VER_1 1
#define WL_ESP_IOV_MAJOR_VER_SHIFT 8
-#define WL_ESP_IOV_VERSION \
- ((WL_ESP_IOV_MAJOR_VER << WL_ESP_IOV_MAJOR_VER_SHIFT)| WL_ESP_IOV_MINOR_VER)
+#define WL_ESP_IOV_VERSION_1_1 \
+ ((WL_ESP_IOV_MAJOR_VER_1 << WL_ESP_IOV_MAJOR_VER_SHIFT)| WL_ESP_IOV_MINOR_VER_1)
enum wl_esp_cmd_ids {
WL_ESP_CMD_ENABLE = 1,
@@ -22663,11 +23982,11 @@
(bcm_bitcount((uint8 *)&(val), sizeof(uint8)) > 1)
/* otp command details */
-#define WL_OTP_IOV_MAJOR_VER 1u
-#define WL_OTP_IOV_MINOR_VER 1u
+#define WL_OTP_IOV_MAJOR_VER_1 1u
+#define WL_OTP_IOV_MINOR_VER_1 1u
#define WL_OTP_IOV_MAJOR_VER_SHIFT 8u
-#define WL_OTP_IOV_VERSION \
- ((WL_OTP_IOV_MAJOR_VER << WL_OTP_IOV_MAJOR_VER_SHIFT) | WL_OTP_IOV_MINOR_VER)
+#define WL_OTP_IOV_VERSION_1_1 \
+ ((WL_OTP_IOV_MAJOR_VER_1 << WL_OTP_IOV_MAJOR_VER_SHIFT) | WL_OTP_IOV_MINOR_VER_1)
/* OTP Regions HW/SW */
#define OTP_RGN_NONE 0u
@@ -22736,8 +24055,8 @@
} wlc_leaked_infra_packet_stat_t;
/* Wake timer structure definition */
-#define WAKE_TIMER_VERSION 1
-#define WAKE_TIMER_NOLIMIT 0xFFFF
+#define WAKE_TIMER_VERSION_1 1
+#define WAKE_TIMER_NOLIMIT 0xFFFF
typedef struct wake_timer {
uint16 ver;
@@ -22760,7 +24079,6 @@
#define MAX_UCM_CHAINS 5
#define MAX_UCM_PROFILES 10
-#define UCM_PROFILE_VERSION_1 1
/* UCM per chain attribute struct */
typedef struct wlc_btcx_chain_attr {
@@ -22773,6 +24091,31 @@
uint8 PAD[1]; /* additional bytes for alignment */
} wlc_btcx_chain_attr_t;
+#define WL_UCM_PER_CHAIN_ATTR_VERSION_V1 1
+/* UCM per chain attribute struct v1 (same structure to wlc_btcx_chain_attr_t) */
+typedef struct wlc_btcx_per_chain_attr_v1 {
+ uint16 length; /* chain attr length, version is same as profile version */
+ int8 desense_level; /* per chain desense level */
+ int8 ack_pwr_strong_rssi; /* per chain ack power at strong rssi */
+ int8 ack_pwr_weak_rssi; /* per chain ack power at weak rssi */
+ int8 tx_pwr_strong_rssi; /* per chain tx power at strong rssi */
+ int8 tx_pwr_weak_rssi; /* per chain tx power at weak rssi */
+ uint8 PAD[1]; /* additional bytes for alignment */
+} wlc_btcx_per_chain_attr_v1_t;
+
+#define WL_UCM_PER_CHAIN_ATTR_VERSION_V2 2
+/* UCM per chain attribute struct v2 */
+typedef struct wlc_btcx_per_chain_attr_v2 {
+ uint16 length; /* chain attr length, version is same as profile version */
+ uint8 desense_strong_rssi; /* per chain desense mode for strong rssi */
+ uint8 desense_weak_rssi; /* per chain desense mode for weak rssi */
+ int8 ack_pwr_strong_rssi; /* per chain ack power at strong rssi */
+ int8 ack_pwr_weak_rssi; /* per chain ack power at weak rssi */
+ int8 tx_pwr_strong_rssi; /* per chain tx power at strong rssi */
+ int8 tx_pwr_weak_rssi; /* per chain tx power at weak rssi */
+} wlc_btcx_per_chain_attr_v2_t;
+
+#define UCM_PROFILE_VERSION_1 1
typedef struct wlc_btcx_profile_v1 {
uint16 version; /* UCM profile version */
uint16 length; /* profile size */
@@ -22799,7 +24142,6 @@
} wlc_btcx_profile_v1_t;
#define UCM_PROFILE_VERSION_2 2u
-
typedef struct wlc_btcx_profile_v2 {
uint16 version; /* UCM profile version */
uint16 length; /* profile size */
@@ -22825,6 +24167,32 @@
wlc_btcx_chain_attr_t chain_attr[]; /* variable length array with chain attributes */
} wlc_btcx_profile_v2_t;
+#define UCM_PROFILE_VERSION_3 3u
+typedef struct wlc_btcx_profile_v3 {
+ uint16 version; /* UCM profile version */
+ uint16 length; /* profile size */
+ uint16 fixed_length; /* size of the fixed portion of the profile */
+ uint8 init; /* profile initialized or not */
+ uint8 chain_attr_count; /* Number of elements in chain_attr array */
+ uint8 profile_index; /* profile index */
+ uint8 mode_strong_wl_bt; /* Mode under strong WLAN and BT RSSI */
+ uint8 mode_weak_wl; /* Mode under weak WLAN RSSI */
+ uint8 mode_weak_bt; /* Mode under weak BT RSSI */
+ uint8 mode_weak_wl_bt; /* Mode under weak BT and WLAN RSSI */
+ int8 mode_wl_hi_lo_rssi_thresh; /* Strong to weak WLAN RSSI threshold for mode selection */
+ int8 mode_wl_lo_hi_rssi_thresh; /* Weak to strong WLAN RSSI threshold for mode selection */
+ int8 mode_bt_hi_lo_rssi_thresh; /* Strong to weak BT RSSI threshold for mode selection */
+ int8 mode_bt_lo_hi_rssi_thresh; /* Weak to strong BT RSSI threshold for mode selection */
+ int8 desense_wl_hi_lo_rssi_thresh; /* Strong to weak RSSI threshold for desense */
+ int8 desense_wl_lo_hi_rssi_thresh; /* Weak to strong RSSI threshold for desense */
+ int8 ack_pwr_wl_hi_lo_rssi_thresh; /* Strong to weak RSSI threshold for ACK power */
+ int8 ack_pwr_wl_lo_hi_rssi_thresh; /* Weak to strong RSSI threshold for ACK power */
+ int8 tx_pwr_wl_hi_lo_rssi_thresh; /* Strong to weak RSSI threshold for Tx power */
+ int8 tx_pwr_wl_lo_hi_rssi_thresh; /* Weak to strong RSSI threshold for Tx power */
+ uint8 hybrid_ant_core_config; /* Select antenna configuration for hybrid */
+ wlc_btcx_per_chain_attr_v2_t chain_attr[]; /* variable length array with chain attributes */
+} wlc_btcx_profile_v3_t;
+
#define SSSR_D11_RESET_SEQ_STEPS 5u
#define SSSR_HWA_RESET_SEQ_STEPS 8u
@@ -22832,6 +24200,7 @@
#define SSSR_REG_INFO_VER_1 1u
#define SSSR_REG_INFO_VER_2 2u
#define SSSR_REG_INFO_VER_3 3u
+#define SSSR_REG_INFO_VER_4 4u
typedef struct sssr_reg_info_v0 {
uint16 version;
@@ -23105,10 +24474,103 @@
} hwa_regs;
} sssr_reg_info_v3_t;
-#ifndef SSSR_REG_INFO_HAS_ALIAS
-typedef sssr_reg_info_v0_t sssr_reg_info_t;
-#define SSSR_REG_INFO_VER SSSR_REG_INFO_VER_0
-#endif
+typedef struct sssr_reg_info_v4 {
+ uint16 version;
+ uint16 length; /* length of the structure validated at host */
+ struct {
+ struct {
+ uint32 pmuintmask0;
+ uint32 pmuintmask1;
+ uint32 resreqtimer;
+ uint32 macresreqtimer;
+ uint32 macresreqtimer1;
+ uint32 macresreqtimer2;
+ } base_regs;
+ } pmu_regs;
+ struct {
+ struct {
+ uint32 intmask;
+ uint32 powerctrl;
+ uint32 clockcontrolstatus;
+ uint32 powerctrl_mask;
+ } base_regs;
+ } chipcommon_regs;
+ struct {
+ struct {
+ uint32 clockcontrolstatus;
+ uint32 clockcontrolstatus_val;
+ } base_regs;
+ struct {
+ uint32 extrsrcreq;
+ } oobr_regs;
+ } arm_regs;
+ struct {
+ struct {
+ uint32 ltrstate;
+ uint32 clockcontrolstatus;
+ uint32 clockcontrolstatus_val;
+ } base_regs;
+ struct {
+ uint32 extrsrcreq;
+ } oobr_regs;
+ } pcie_regs;
+ struct {
+ struct {
+ uint32 xmtaddress;
+ uint32 xmtdata;
+ uint32 clockcontrolstatus;
+ uint32 clockcontrolstatus_val;
+ } base_regs;
+ struct {
+ uint32 extrsrcreq;
+ } oobr_regs;
+ uint32 sr_size;
+ } mac_regs[MAX_NUM_D11_CORES_WITH_SCAN];
+
+ struct {
+ struct {
+ uint32 clockcontrolstatus;
+ uint32 clockcontrolstatus_val;
+ } base_regs;
+ struct {
+ uint32 extrsrcreq;
+ } oobr_regs;
+
+ uint32 saqm_sssr_addr;
+ uint32 saqm_sssr_size;
+
+ struct {
+ uint32 digsr_srcontrol1_addr; /* DIGSR engine sr control1 register */
+ uint32 digsr_srcontrol1_clrbit_val; /* clear these bits from srcontrol1 */
+
+ uint32 digsr_srcontrol2_addr; /* DIGSR engine sr control2 register */
+ uint32 digsr_srcontrol2_setbit_val; /* Value to set in the above address */
+
+ uint32 pmuchip_ctl_addr_reg;
+ uint32 pmuchip_ctl_val;
+ uint32 pmuchip_ctl_data_reg;
+ uint32 pmuchip_ctl_setbit_val;
+ } sssr_config_regs;
+ } saqm_sssr_info;
+
+ struct {
+ uint32 dig_sssr_addr;
+ uint32 dig_sssr_size;
+ } dig_mem_info;
+
+ struct {
+ uint32 fis_addr;
+ uint32 fis_size;
+ } fis_mem_info;
+
+ /* Start address and end address for SSSR collection by host. */
+ struct {
+ uint32 sysmem_sssr_addr;
+ uint32 sysmem_sssr_size;
+ } sssr_all_mem_info;
+
+ uint32 fis_enab;
+} sssr_reg_info_v4_t;
/* A wrapper structure for all versions of SSSR register information structures */
typedef union sssr_reg_info {
@@ -23116,6 +24578,7 @@
sssr_reg_info_v1_t rev1;
sssr_reg_info_v2_t rev2;
sssr_reg_info_v3_t rev3;
+ sssr_reg_info_v4_t rev4;
} sssr_reg_info_cmn_t;
/* ADaptive Power Save(ADPS) structure definition */
@@ -23303,6 +24766,8 @@
/* --- BTC ACK Counters (btc_ack_counters legacy command) --- */
#define BTC_ACK_CNTS_VER_1 1u
+#define BTC_ACK_CNTS_VER_2 2u
+
typedef struct wl_btc_ack_cnts_v1 {
uint16 ver;
uint16 len;
@@ -23314,6 +24779,18 @@
uint32 c1_ack_txpwr;
} wl_btc_ack_cnts_v1_t;
+typedef struct wl_btc_ack_cnts_v2 {
+ uint16 ver;
+ uint16 len;
+ uint8 slice_index;
+ uint8 PAD[3];
+ uint32 cdd_ack_cnt;
+ uint32 siso_ack_cnt;
+ uint32 c0_ack_txpwr;
+ uint32 c1_ack_txpwr;
+ uint32 cdd_ack_bt_cnt;
+} wl_btc_ack_cnts_v2_t;
+
typedef enum wl_btc_ack_cnts_command_e {
ACK_CNTS_CMD_CLEAR = 0u, /* To clear BTC Ack counters */
} wl_btc_ack_cnts_command_t;
@@ -23327,11 +24804,23 @@
/* --- End BTC ACK Counters --- */
-#define RPSNOA_IOV_MAJOR_VER 1
-#define RPSNOA_IOV_MINOR_VER 1
-#define RPSNOA_IOV_MAJOR_VER_SHIFT 8
-#define RPSNOA_IOV_VERSION \
- ((RPSNOA_IOV_MAJOR_VER << RPSNOA_IOV_MAJOR_VER_SHIFT)| RPSNOA_IOV_MINOR_VER)
+/* --- BTC STATUS (coex status from both 2G and 5G slices) --- */
+#define BTC_STATUS_VER_1 1u
+
+typedef struct wlc_btc_status_v1 {
+ uint16 ver;
+ uint16 len;
+ uint32 btc_status_5g;
+ uint32 btc_status_2g;
+ uint8 PAD[4]; /* For future enhancements */
+} wlc_btc_status_v1_t;
+/* --- End BTC STATUS --- */
+
+#define RPSNOA_IOV_MAJOR_VER_1 1u
+#define RPSNOA_IOV_MINOR_VER_1 1u
+#define RPSNOA_IOV_MAJOR_VER_SHIFT 8u
+#define RPSNOA_IOV_VERSION_1_1 \
+ ((RPSNOA_IOV_MAJOR_VER_1 << RPSNOA_IOV_MAJOR_VER_SHIFT) | RPSNOA_IOV_MINOR_VER_1)
enum wl_rpsnoa_cmd_ids {
WL_RPSNOA_CMD_ENABLE = 1,
@@ -23423,6 +24912,9 @@
/* PHY ecounters */
WL_STATS_XTLV_PHY_ECOUNTER = 0x10B,
+ /* PHYCAL ecounters */
+ WL_STATS_XTLV_PHYCAL_ECOUNTER = 0x10C,
+
/* Per-slice information
* Per-interface reporting could also include slice specific data
*/
@@ -23481,6 +24973,8 @@
WL_STATS_XTLV_WME_RX_CNT_WL_SLICE = 0x31C,
/* Per-slice UWBCX stats */
WL_IFSTATS_XTLV_WL_SLICE_UWBCX = 0x31D,
+ /* Per-slice UWBCX stats */
+ WL_IFSTATS_XTLV_WL_SLICE_PWRSTATS_SCAN_6E = 0x31E,
/* Per-interface */
/* XTLV container for reporting */
WL_IFSTATS_XTLV_IF = 0x501,
@@ -23730,19 +25224,18 @@
#define WL_BCN_RPT_ASSOC_SCAN_CACHE_COUNT_MAX (8)
#define WL_BCN_RPT_ASSOC_SCAN_CACHE_COUNT_DEFAULT (WL_BCN_RPT_ASSOC_SCAN_CACHE_COUNT_MAX)
-#define WL_BCN_REPORT_CMD_VERSION 1
-struct wl_bcn_report_cfg {
+#define WL_BCN_REPORT_CMD_VERSION_V1 1
+
+typedef struct wl_bcn_report_cfg_v1 {
uint32 flags; /**< Flags that defines the operation/setting information */
uint32 scan_cache_timeout; /**< scan cache timeout value in millisec */
uint32 scan_cache_timer_pend; /**< Read only pending time for timer expiry in millisec */
uint8 scan_cache_cnt; /**< scan cache count */
-};
-
-/* endif (WL_ASSOC_BCN_RPT) */
+ uint8 pad[3];
+} wl_bcn_report_cfg_v1_t;
/* Thermal, Voltage, and Power Mitigation */
-#define TVPM_REQ_VERSION_1 1
-#define TVPM_REQ_CURRENT_VERSION TVPM_REQ_VERSION_1
+#define TVPM_REQ_VERSION_1 1u
/* tvpm iovar data */
typedef struct {
@@ -23908,6 +25401,7 @@
#define WL_NAN_SLOT_ECOUNTERS_VERSION_1 1
#define WL_NAN_SLOT_ECOUNTERS_VERSION_2 2
#define WL_NAN_SLOT_ECOUNTERS_VERSION_3 3
+#define WL_NAN_SLOT_ECOUNTERS_VERSION_4 4
typedef struct wl_nan_slot_ecounters_v1 {
uint16 version; /* version field */
@@ -23957,6 +25451,25 @@
uint16 bcn_txfail_5g; /* sending 5G beacon failure count */
} wl_nan_slot_ecounters_v3_t;
+typedef struct wl_nan_slot_ecounters_v4 {
+ uint16 version; /* version field */
+ uint16 length; /* struct length starting from version */
+ uint32 chan[NAN_MAX_BANDS]; /* cur nan slot chanspec of both bands */
+ uint16 cur_slot_idx; /* cur nan slot index */
+ uint16 PAD;
+ nan_sched_stats_t sched; /* sched stats */
+ /* for v4 */
+ wl_nan_mac_stats_v2_t mac; /* mac stats */
+ uint16 bcn_rx_drop_rssi; /* Beacon received but ignored due to weak rssi */
+ uint16 bcn_rx_drop_rssi_5g; /* 5G Beacon received but ignored due to weak rssi */
+ uint16 cnt_rssi_close; /* cnt of beacon rssi > rssi_close received */
+ uint16 cnt_rssi_close_5g; /* cnt of 5G beacon rssi > rssi_close received */
+ uint16 cnt_rssi_mid; /* cnt of beacon rssi > rssi_middle received */
+ uint16 cnt_rssi_mid_5g; /* cnt of 5G beacon rssi > rssi_middle received */
+ uint16 bcn_txfail; /* Beacon sending failure count */
+ uint16 bcn_txfail_5g; /* sending 5G beacon failure count */
+} wl_nan_slot_ecounters_v4_t;
+
/* WL_STATS_XTLV_NDP_SESSION_STATUS for ecounters */
#define WL_NAN_SESSION_STATUS_EC_VERSION_1 1
typedef struct wl_nan_ndp_session_status_v1_s {
@@ -24140,10 +25653,12 @@
};
enum wl_rmc_report_xtlv_id {
- WL_RMC_RPT_XTLV_VER = 0x0,
- WL_RMC_RPT_XTLV_BSS_INFO = 0x1,
- WL_RMC_RPT_XTLV_CANDIDATE_INFO = 0x2,
- WL_RMC_RPT_XTLV_USER_CACHE_INFO = 0x3
+ WL_RMC_RPT_XTLV_VER = 0x0,
+ WL_RMC_RPT_XTLV_BSS_INFO = 0x1,
+ WL_RMC_RPT_XTLV_CANDIDATE_INFO = 0x2,
+ WL_RMC_RPT_XTLV_USER_CACHE_INFO = 0x3,
+ WL_RMC_RPT_XTLV_CANDIDATE_INFO_V2 = 0x4,
+ WL_RMC_RPT_XTLV_USER_CACHE_INFO_V2 = 0x5
};
/* WL_RMC_RPT_XTLV_BSS_INFO */
@@ -24161,10 +25676,18 @@
uint16 ctl_channel; /* channel */
uint32 time_last_seen; /* delta time (in ms) between cur time and last seen timestamp */
uint16 bss_load; /* BSS load */
- uint8 bssid [6]; /* padding to get 32 bits alignment */
+ uint8 bssid[6]; /* BSSID */
} rmc_candidate_info_v1_t;
-#define WL_FILTER_IE_VERSION 1 /* deprecated */
+/* WL_RMC_RPT_XTLV_CANDIDATE_INFO_V2 */
+typedef struct {
+ int16 rssi; /* last seen rssi */
+ chanspec_t ctl_channel; /* chanspec of primary channel */
+ uint32 time_last_seen; /* delta time (in ms) between cur time and last seen timestamp */
+ uint16 bss_load; /* BSS load */
+ struct ether_addr bssid; /* BSSID */
+} rmc_candidate_info_v2_t;
+
enum wl_filter_ie_options {
WL_FILTER_IE_CLEAR = 0, /* allow element id in packet.For suboption */
WL_FILTER_IE_SET = 1, /* filter element id in packet.For suboption */
@@ -24190,6 +25713,18 @@
uint8 tlvs[]; /* variable data (zero in for list ,clearall) */
} wl_filter_ie_iov_v1_t;
+#define WL_ASSOC_RESP_PARAMS_V1 (1u)
+typedef struct wl_assoc_resp_params_v1 {
+ uint16 version; /* Structure version */
+ uint16 len; /* Total length of the structure */
+ uint16 fixed_length; /* Total length of fixed fields */
+ uint8 mac_addr[ETHER_ADDR_LEN]; /* peer MAC address */
+ uint8 resp_ie_len; /* Assoc_resp IE's length */
+ uint8 pad; /* Pad for alignment */
+ uint16 status; /* AREQ status code from Host */
+ uint8 ies[]; /* Variable data (resp_ies) */
+} wl_assoc_resp_params_v1_t;
+
/* Event aggregation config */
#define EVENT_AGGR_CFG_VERSION 1
#define EVENT_AGGR_DISABLED 0x0
@@ -24210,17 +25745,8 @@
uint16 num_events_flush; /* Number of events aggregated before flush */
} event_aggr_config_t;
-#ifndef WL_TDMTX_TYPEDEF_HAS_ALIAS
-typedef tdmtx_cnt_v1_t tdmtx_cnt_t;
-typedef tdmtx_cnt_shm_v1_t tdmtx_cnt_shm_t;
-typedef wl_tdmtx_ecounters_v1_t wl_tdmtx_ecounters_t;
-#define WL_CNT_TDMTX_STRUCT_SZ (sizeof(tdmtx_cnt_t))
-#define WL_CNT_TDMTX_SHM_SZ (sizeof(tdmtx_cnt_shm_t))
-#endif
-
/** chanctxt related statistics */
-#define CHANCTXT_STATS_VERSION_1 1
-#define CHANCTXT_STATS_CURRENT_VERSION CHANCTXT_STATS_VERSION_1
+#define CHANCTXT_STATS_VERSION_1 1u
typedef struct wlc_chanctxt_stats {
uint32 excursionq_end_miss;
uint32 activeq_end_miss;
@@ -24342,7 +25868,7 @@
uint32 addr_high;
} dma_wl_addr_region_t;
-#define WL_ROAMSTATS_IOV_VERSION 1
+#define WL_ROAMSTATS_IOV_VERSION_1 1u
#define MAX_PREV_ROAM_EVENTS 16u
@@ -24422,11 +25948,11 @@
/** receive signal reporting module interface */
-#define WL_RXSIG_IOV_MAJOR_VER (1u)
-#define WL_RXSIG_IOV_MINOR_VER (1u)
+#define WL_RXSIG_IOV_MAJOR_VER_1 (1u)
+#define WL_RXSIG_IOV_MINOR_VER_1 (1u)
#define WL_RXSIG_IOV_MAJOR_VER_SHIFT (8u)
-#define WL_RXSIG_IOV_VERSION \
- ((WL_RXSIG_IOV_MAJOR_VER << WL_RXSIG_IOV_MAJOR_VER_SHIFT) | WL_RXSIG_IOV_MINOR_VER)
+#define WL_RXSIG_IOV_VERSION_1_1 \
+ ((WL_RXSIG_IOV_MAJOR_VER_1 << WL_RXSIG_IOV_MAJOR_VER_SHIFT) | WL_RXSIG_IOV_MINOR_VER_1)
#define WL_RXSIG_IOV_GET_MAJOR(x) (x >> WL_RXSIG_IOV_MAJOR_VER_SHIFT)
#define WL_RXSIG_IOV_GET_MINOR(x) (x & 0xFF)
@@ -24450,6 +25976,7 @@
WL_RXSIG_CMD_DUMP = 0xb,
WL_RXSIG_CMD_DUMPWIN = 0xc,
WL_RXSIG_CMD_RSSI_EXP = 0xd,
+ WL_RXSIG_CMD_RSSI_COMP = 0xe,
WL_RXSIG_CMD_TOTAL
};
@@ -24635,9 +26162,9 @@
#define WL_CLM_HAS_OFDM_EIRP 0x2000u /**< Flag for HAS_OFDM_EIRP */
#define WL_CLM_NO_160MHZ 0x4000u /**< Flag for NO_160MHZ */
#define WL_CLM_NO_80_80MHZ 0x8000u /**< Flag for NO_80_80MHZ */
-#define WL_CLM_NO_240MHZ 0x10000u /**< Flag for NO_240MHZ */
#define WL_CLM_NO_320MHZ 0x200000u /**< Flag for NO_320MHZ */
#define WL_CLM_NO_160_160MHZ 0x400000u /**< Flag for NO_160_160MHZ */
+#define WL_CLM_CBP_FCC 0x800000u /**< Flag for CBP_FCC */
#define WL_CLM_DFS_FCC WL_CLM_DFS_TPC /**< Flag for DFS FCC */
#define WL_CLM_DFS_EU (WL_CLM_DFS_TPC | WL_CLM_RADAR_TYPE_EU) /**< Flag for DFS EU */
@@ -24974,6 +26501,8 @@
uint8 cat; /* Transmit Power Info category */
uint8 intr; /* Transmit Power Info Interpretation */
uint8 cnt; /* Transmit Power Info count */
+ uint8 regcat; /* reg info power category */
+ uint8 PAD[3];
int8 txpwr[WL_TPE_TXPWR_MAX_LEN]; /* Maximum TX power */
} wl_tpe_txpwr_config_v1_t;
@@ -25160,9 +26689,7 @@
#define WL_WSEC_DEL_PMK_FIXED_LEN_V1 OFFSETOF(wl_wsec_del_pmk_t, xtlvs)
/* WTC */
-#define WLC_WTC_ROAM_VER_1 1
-
-#define WLC_WTC_ROAM_CUR_VER WLC_WTC_ROAM_VER_1
+#define WLC_WTC_ROAM_VER_1 1u
#define WLC_WTC_ROAM_CONFIG_HDRLEN 4u
typedef enum wtc_band_list {
@@ -25186,7 +26713,7 @@
} wlc_wtcconfig_info_v1_t;
/* RCROAM */
-#define WLC_RC_ROAM_VER_1 1
+#define WLC_RC_ROAM_VER_1 1u
typedef struct wlc_rcroam {
uint16 ver;
@@ -25202,7 +26729,6 @@
bool enab;
} wlc_rcroam_info_v1_t;
-#define WLC_RC_ROAM_CUR_VER WLC_RC_ROAM_VER_1
#define RCROAM_HDRLEN 4u
#define MAX_RCSCAN_TIMER 300u
@@ -25217,7 +26743,7 @@
#define WLC_RCROAM_RESET_WTCREQ 7 /* WTC request overriding rcroam */
#define WLC_RCROAM_RESET_RSN_ABORT 8 /* Reset RCROAM params due to roam abort */
-#define WLC_SILENT_ROAM_VER_1 1
+#define WLC_SILENT_ROAM_VER_1 1u
/* silent roam information struct */
typedef struct wlc_sroam_info_v1 {
/* Silent roam Set/Get value */
@@ -25245,17 +26771,16 @@
uint8 data[];
} wlc_sroam_t;
-#define WLC_SILENT_ROAM_CUR_VER WLC_SILENT_ROAM_VER_1
#define SROAM_HDRLEN 4u
#define DEF_SROAM_OFF 0
#define DEF_SROAM_MIN_RSSI -65
-#define DEF_SROAM_RSSI_RANGE 3u
-#define DEF_SROAM_SCORE_DELTA 1u
-#define DEF_SROAM_PERIOD_TIME 10u
-#define DEF_SROAM_INACT_CNT 5u
+#define DEF_SROAM_RSSI_RANGE 8u
+#define DEF_SROAM_SCORE_DELTA 0
+#define DEF_SROAM_PERIOD_TIME 5u
+#define DEF_SROAM_INACT_CNT 10u
#define MAX_SROAM_RSSI -70
-#define MAX_SROAM_RSSI_RANGE 5u
+#define MAX_SROAM_RSSI_RANGE 10u
#define MAX_SROAM_SCORE_DELTA 10u
#define MAX_SROAM_PERIOD_TIME 250u
#define SROAM_BAND_AUTO 3u
@@ -25669,6 +27194,7 @@
WL_RFFE_CMD_ELNABYP_MODE = 1,
WL_RFFE_CMD_REG = 2,
WL_RFFE_CMD_ELNA_VDD_MODE = 3,
+ WL_RFFE_CMD_DRV_STRENGTH = 4,
WL_RFFE_CMD_LAST
} wl_rffe_cmd_type_t;
@@ -25680,6 +27206,11 @@
uint32 value; /**< read/write value */
} rffe_reg_t;
+typedef struct {
+ uint32 slaveid; /**< rFEM SlaveID */
+ uint32 ds_val; /**< drive strength code */
+} rffe_drv_strength_t;
+
#ifndef BCMUTILS_ERR_CODES
/*
@@ -25870,6 +27401,7 @@
/* ifdef (WLC_OBSS_HW) */
/* OBSS HW specific Macros */
#define WLC_OBSS_HW_CMD_VERSION_1 1u
+#define WLC_OBSS_HW_CMD_VERSION_2 2u
/* OBSS HW config sub command identification flag */
#define OBSS_HW_CFG_SUB_CMD_ENABLE (1u << 0u)
@@ -25901,10 +27433,11 @@
#define WLC_OBSS_HW_TEST_MITI_TX_ONLY 2u /* Rx mitigation disabled, Tx mitigation */
#define WLC_OBSS_HW_TEST_MITI_TX_RX_FILT 3u /* Rx Tx mitigation enabled */
#define WLC_OBSS_HW_TEST_MITI_CHAN_CHANGE 4u /* Mitigation by chanspec change */
+#define WLC_OBSS_HW_TEST_MITI_RX_ONLY 5u /* Tx mitigation disabled, Rx mitigation */
+#define WLC_OBSS_HW_TEST_MITI_LAST WLC_OBSS_HW_TEST_MITI_RX_ONLY
#define WL_OBSS_ANT_MAX 2u /* Max Antennas */
#define ACPHY_OBSS_STATS_BIN_CNT 8u /* min 1 for default */
-#define ACPHY_OBSS_SUBBAND_CNT 8u /* Max sub band counts i.e., 160Mhz = 8 * 20MHZ */
enum wlc_obss_hw_cmd_id {
WLC_OBSS_HW_CMD_VER = 1u,
@@ -25936,6 +27469,31 @@
uint8 mitigation_mode; /* mitigation enabling/disabling options */
} wlc_obss_hw_test_v1_t;
+typedef struct wlc_obss_hw_cfg_v2 {
+ uint16 sub_cmd_flags; /* Flag bits to Identify configuring sub command */
+ uint8 is_enable; /* Feature is enabled or not */
+ uint8 sw_cache_interval; /* SW cache interval to cache OBSS stats in sec */
+ uint16 phy_sensing_duration; /* PHY OBSS sensing duration in msec */
+} wlc_obss_hw_cfg_v2_t;
+
+typedef struct wlc_obss_hw_stats_v2 {
+ uint16 avg_obss_stats[WL_OBSS_ANT_MAX][ACPHY_OBSS_SUBBAND_CNT][ACPHY_OBSS_STATS_BIN_CNT];
+ uint16 obss_det_stats[ACPHY_OBSS_SUBBAND_CNT];
+ uint16 stats_cnt; /* Stats count */
+ uint8 obss_mit_status; /* OBSS mitigation status */
+ uint8 mit_bw; /* Mitigation BW that got selected */
+ uint32 lifetime_expiry_cnt; /* count of lifetime expired pkts */
+ uint32 medium_access_delay; /* sum of medium access delay */
+ uint32 pkt_cnt; /* number of pkts for which Tx status stats are logged */
+ uint32 rts_pkts_cnt; /* number of packets sent with RTS */
+} wlc_obss_hw_stats_v2_t;
+
+typedef struct wlc_obss_hw_test_v2 {
+ uint16 sub_cmd_flags; /* Flag bits to Identify configuring sub command */
+ uint8 test_mode; /* To stop/start respective test mode */
+ uint8 mitigation_mode; /* mitigation enabling/disabling options */
+} wlc_obss_hw_test_v2_t;
+
#define STA_PM_SC_OFLD_CFG_VER_V1 1u
#define STA_PM_SC_OFLD_ENAB_FLAG (1u << 0u)
@@ -25986,7 +27544,10 @@
STA_PM_SC_OFLD_FAIL_SLOTTED_BSS_ENAB = (1u << 14u), /* Slotted BSS is enabled */
STA_PM_SC_OFLD_FAIL_BTMC_ACTIVE = (1u << 15u), /* BT Main Core is active */
STA_PM_SC_OFLD_FAIL_UNSUP_BASIC_RATE = (1u << 16u), /* SC Unsupported basic rate */
- STA_PM_SC_OFLD_FAIL_UNSUP_CHANSPEC = (1u << 17u) /* SC Unsupported chanspec */
+ STA_PM_SC_OFLD_FAIL_UNSUP_CHANSPEC = (1u << 17u), /* SC Unsupported chanspec */
+ STA_PM_SC_OFLD_FAIL_MLO_LINK_ACTIVE_IN_SC = (1u << 18u) /* One of the MLO link is
+ * already offloaded to sc
+ */
} wlc_sta_pm_sc_ofld_fail_reason_t;
typedef enum wlc_sta_pm_sc_ofld_exit_reason {
@@ -26011,6 +27572,7 @@
STA_PM_SC_OFLD_EXIT_TWT = 19u, /* Exit due to TWT active */
STA_PM_SC_OFLD_EXIT_SLOTTED_BSS = 20u, /* Exit due to Slotted BSS active */
STA_PM_SC_OFLD_EXIT_AP_BSS = 21u, /* Exit due to AP BSS active */
+ STA_PM_SC_OFLD_EXIT_MLO = 22u, /* Exit due to high priority MLO link */
STA_PM_SC_OFLD_EXIT_MAX = 255u /* Max, uint8 for now */
} wlc_sta_pm_sc_ofld_exit_reason_t;
@@ -26051,7 +27613,13 @@
SDTC_ID_MAINMAC = 0x5, /* HWL inside MAIN MAC */
SDTC_ID_LP = 0x6, /* HWL connected to Async APB bridge */
SDTC_ID_AUXMAC_AXL = 0x7, /* AXL between booker interconnect and AUX MAC */
- SDTC_ID_MAINMAC_AXL = 0x8 /* AXL between booker interconnect and MAIN MAC */
+ SDTC_ID_MAINMAC_AXL = 0x8, /* AXL between booker interconnect and MAIN MAC */
+ SDTC_ID_SCANMAC_HWL = 0x9, /* HWL inside SCAN MAC */
+ SDTC_ID_SCANMAC_AXL = 0xa, /* AXL between booker interconnect and SCAN MAC */
+ SDTC_ID_SAQM_AXL = 0xb, /* AXL between booker interconnect and SAQM */
+ SDTC_ID_SAQM_HWL = 0xc, /* HWL inside SAQM */
+ SDTC_ID_WL_AXL = 0xd, /* AXL for WL_SDTC */
+ SDTC_ID_LAST = 0xe
};
/* SDTC Iovars */
@@ -26253,10 +27821,6 @@
#define SC_SCAN_RETRY_CFG_PARAMS_BCN_DUR_5G (1u << 4u)
#define SC_SCAN_RETRY_CFG_PARAMS_BCN_DUR_6G (1u << 5u)
-#ifndef SC_SCAN_RETRY_CFG_HAS_ALIAS
-#define SC_SCAN_RETRY_CFG_VERSION SC_SCAN_RETRY_CFG_VERSION_1
-#endif
-
/* Input structure for sc_scan_retry_cfg IOVAR */
typedef struct sc_scan_retry_cfg_params_v1 {
uint16 version; /* config version. */
@@ -26452,6 +28016,45 @@
} wlc_uwbcx_stats_v1_t;
#endif /* UWBCX */
+#define WL_BTC_VER_V1 1u
+#define BTCX_ROAM_PROF_VERSION_V1 1u
+#define BTCX_ROAM_BW_VERSION_V1 1u
+
+/* BT coex IOV sub command IDs */
+typedef enum btc_cmd_id {
+ WL_BTC_CMD_VER = 0, /* BTCX version sub command */
+ WL_BTC_CMD_ROAM_PROFILE = 1,
+ WL_BTC_CMD_ROAM_BW = 2,
+ WL_BTC_CMD_ROAM_ON = 3,
+ WL_BTC_CMD_ROAM_BAND_FILTER = 4,
+ WL_BTC_CMD_ROAM_DELTA = 5,
+ WL_BTC_CMD_ROAM_RSSI = 6,
+ WL_BTC_CMD_ROAM_MODE = 7,
+ WL_BTC_CMD_ACK_CNTS = 8,
+ WL_BTC_CMD_RR_ENABLE = 9,
+ WL_BTC_CMD_HP_OVR_LESCAN = 10
+} btc_cmd_id_t;
+
+typedef struct btcx_roam_bandwidth {
+ uint16 version; /* version info */
+ uint8 len; /* btc roam profile length */
+ uint8 pad;
+ uint8 low_offset;
+ uint8 mid_offset;
+ uint8 high_offset;
+ uint8 pad1;
+} btcx_roam_bw_v1_t;
+
+typedef struct btcx_roam_profile {
+ uint16 version; /* version info */
+ uint8 len; /* btc roam profile length */
+ uint8 pad;
+ uint8 prof_id;
+ uint8 initialized;
+ uint16 offset;
+ uint32 task_bm;
+} btcx_roam_profile_v1_t;
+
enum phy_rxgcrs_ed_enhncd_cmd_id {
PHY_RXGCRS_ED_ENHNCD_CMD_EN = 1u,
PHY_RXGCRS_ED_ENHNCD_CMD_STATUS = 2u,
@@ -26542,7 +28145,7 @@
} bcm_trace_event_enab_v2_t;
/* rate_info command version */
-#define WL_RATE_INFO_VERSION 1
+#define WL_RATE_INFO_VERSION_1 1
typedef struct wl_rate_info {
uint16 version; /**< structure version */
uint16 length; /**< length of this struct */
@@ -26596,11 +28199,11 @@
#define WL_AML_F_ACKED 0x0002 /* This flag indicates the frame is acked */
/* Version for IOVAR 'aml' */
-#define WL_AML_IOV_MAJOR_VER 1u
-#define WL_AML_IOV_MINOR_VER 0u
+#define WL_AML_IOV_MAJOR_VER_1 1u
+#define WL_AML_IOV_MINOR_VER_0 0u
#define WL_AML_IOV_MAJOR_VER_SHIFT 8u
-#define WL_AML_IOV_VERSION \
- ((WL_AML_IOV_MAJOR_VER << WL_AML_IOV_MAJOR_VER_SHIFT) | WL_AML_IOV_MINOR_VER)
+#define WL_AML_IOV_VERSION_1_0 \
+ ((WL_AML_IOV_MAJOR_VER_1 << WL_AML_IOV_MAJOR_VER_SHIFT) | WL_AML_IOV_MINOR_VER_0)
/* Common header for IOVAR 'aml' */
typedef struct wl_aml_iov_cmnhdr {
@@ -26673,7 +28276,7 @@
wl_low_latency_config_v1_t config; /* config for latency mode */
} wl_low_latency_v1_t;
-#define WL_PASN_VERSION 0x0001u
+#define WL_PASN_VERSION_1 0x0001u
/* PASN subcommands ID. */
enum {
@@ -26748,7 +28351,10 @@
#define PASN_SID_FTM_START 1024u
#define PASN_SID_FTM_END 2047u
-#define PASN_SID_INTERNAL_START 2048u
+#define PASN_SID_NAN_START 2048u
+#define PASN_SID_NAN_END 3071u
+
+#define PASN_SID_INTERNAL_START 3072u
#define PASN_SID_INTERNAL_END 32767u
typedef struct wl_pasn_iov {
@@ -26840,8 +28446,10 @@
typedef uint8 wl_pasn_session_state_t;
typedef int32 wl_pasn_status_t;
+/* Global and bsscfg flags */
enum {
- WL_PASN_FLAG_ENABLED = 0x0001u
+ /* PASN is enabled on bsscfg */
+ WL_PASN_FLAG_BSSCFG_ENABLED = 0x0001u
};
typedef uint16 wl_pasn_flags_t;
@@ -26851,7 +28459,9 @@
/* PASN exchange will setup PMKSA by tunneling protocol data */
WL_PASN_SESSION_FLAG_TUNNELED_AKM = 0x0002u,
/* PASN session will be deleted if error occurs */
- WL_PASN_SESSION_FLAG_DELETE_ON_ERR = 0x0004u
+ WL_PASN_SESSION_FLAG_DELETE_ON_ERR = 0x0004u,
+ /* PASN session will issue scan with randmac */
+ WL_PASN_SESSION_FLAG_RANDMAC = 0x0008u
};
typedef uint16 wl_pasn_session_flags_t;
@@ -26879,7 +28489,7 @@
/* PASN global information. */
typedef struct wl_pasn_info {
- wl_pasn_flags_t flags; /* global flags. */
+ wl_pasn_flags_t flags; /* flags. */
wl_pasn_policy_t policy; /* authentication policy supported. */
uint8 auth_num_retries; /* authentication frame retry limit. */
uint8 num_groups; /* number of cyclic groups. */
@@ -26952,11 +28562,11 @@
/* amt command details */
/* non-batched command version = major|minor w/ major <= 127 */
-#define WL_AMT_IOV_MAJOR_VER 1u
-#define WL_AMT_IOV_MINOR_VER 1u
+#define WL_AMT_IOV_MAJOR_VER_1 1u
+#define WL_AMT_IOV_MINOR_VER_2 2u
#define WL_AMT_IOV_MAJOR_VER_SHIFT 8u
-#define WL_AMT_IOV_VERSION \
- ((WL_AMT_IOV_MAJOR_VER << WL_AMT_IOV_MAJOR_VER_SHIFT) | WL_AMT_IOV_MINOR_VER)
+#define WL_AMT_IOV_VERSION_1_2 \
+ ((WL_AMT_IOV_MAJOR_VER_1 << WL_AMT_IOV_MAJOR_VER_SHIFT) | WL_AMT_IOV_MINOR_VER_2)
enum wl_amt_cmd_ids {
WL_AMT_CMD_VER = 1u, /* Get AMT API VER */
@@ -26997,6 +28607,13 @@
uint16 fft_mask_ext;
} wlc_fft_entry_info_v1_t;
+/* struct for WL_AMT_XTLV_AFT xtlv version 2 */
+typedef struct wlc_aft_entry_info_v2 {
+ uint8 ds_bits;
+ uint8 fft_idx;
+ uint16 if_id;
+} wlc_aft_entry_info_v2_t;
+
/* subcommand ids for phy_tpc */
enum wl_tpc_subcmd_ids {
WL_TPC_SUBCMD_AV = 0u, /* AV */
@@ -27027,11 +28644,11 @@
#define WL_TPC_AVVMID_IOV_VER_1 1u
/* PTM */
-#define WL_PTM_IOV_MAJOR_VER 1u
-#define WL_PTM_IOV_MINOR_VER 1u
+#define WL_PTM_IOV_MAJOR_VER_1 1u
+#define WL_PTM_IOV_MINOR_VER_1 1u
#define WL_PTM_IOV_MAJOR_VER_SHIFT 8u
-#define WL_PTM_IOV_VERSION \
- ((WL_PTM_IOV_MAJOR_VER << WL_PTM_IOV_MAJOR_VER_SHIFT)| WL_PTM_IOV_MINOR_VER)
+#define WL_PTM_IOV_VERSION_1_1 \
+ ((WL_PTM_IOV_MAJOR_VER_1 << WL_PTM_IOV_MAJOR_VER_SHIFT)| WL_PTM_IOV_MINOR_VER_1)
/* subcommand ids */
enum wl_ptm_cmd_ids {
@@ -27049,6 +28666,7 @@
typedef struct wl_ptm_offset {
uint32 offset_high;
uint32 offset_low;
+ uint32 master_ahead;
} wl_ptm_offset_t;
typedef struct wl_ptm_time {
@@ -27060,6 +28678,11 @@
uint32 master_low;
} wl_ptm_time_t;
+typedef struct wl_ptm_master_time {
+ uint32 master_high;
+ uint32 master_low;
+} wl_ptm_master_time_t;
+
#define WL_TX_PER_TID_WME_ECNT_VER 1u
typedef struct tx_wme_eCounters
{
@@ -27104,7 +28727,7 @@
} trig_log_events_config_request_v1_t;
/** Dynamic Tx Power Control common interfaces */
-#define WL_DTPC_IOV_VERSION (1u)
+#define WL_DTPC_IOV_VERSION_1 (1u)
typedef enum wl_dtpc_iov {
WL_DTPC_CMD_EN = 0x0, /**< top control switch */
@@ -27169,11 +28792,13 @@
#define WL_CELL_AVOID_REMOVE_CH_INFO 0x8000u
#ifdef CHRE
-#define WL_CHRE_IOV_MAJOR_VER 1u
-#define WL_CHRE_IOV_MINOR_VER 1u
#define WL_CHRE_IOV_MAJOR_VER_SHIFT 8u
-#define WL_CHRE_IOV_VERSION \
- ((WL_CHRE_IOV_MAJOR_VER << WL_CHRE_IOV_MAJOR_VER_SHIFT) | WL_CHRE_IOV_MINOR_VER)
+
+#define WL_CHRE_IOV_MAJOR_VER_1 1u
+#define WL_CHRE_IOV_MINOR_VER_1 1u
+
+#define WL_CHRE_IOV_VERSION_1_1 \
+ ((WL_CHRE_IOV_MAJOR_VER_1 << WL_CHRE_IOV_MAJOR_VER_SHIFT) | WL_CHRE_IOV_MINOR_VER_1)
enum wl_chre_cmd_ids {
WL_CHRE_CMD_VERSION = 0u, /* Get firmware version string */
@@ -27205,7 +28830,620 @@
WLC_DYN_BW_XTLV_TX_ID = 3u,
WLC_DYN_BW_XTLV_BACKOFF_SB_ID = 4u,
WLC_DYN_BW_XTLV_PRICRS_MASK_ID = 5u,
+ WLC_DYN_BW_XTLV_SCRMBLR_WAR_ID = 6u,
WLC_DYN_BW_XTLV_LAST_ID
};
+/* CAPEXT WL partition */
+/* The features listed in the enumeration below have subfeatures
+ * If a new feature is added and that feature has sub-features that need to be reported,
+ * add that feature here
+ */
+#define CAPEXT_WL_FEATURE_ID_BASE (2048u)
+enum capext_wl_feature_id {
+ CAPEXT_WL_FEATURE_RSVD = (CAPEXT_WL_FEATURE_ID_BASE + 0),
+ /* WL top level feature id to hold and report bitmaps of features with and
+ * without sub-features.
+ */
+ CAPEXT_WL_FEATURE_WL_FEATURES = (CAPEXT_WL_FEATURE_ID_BASE + 1),
+ /* other wl features with sub-features that need to be reported */
+ CAPEXT_WL_FEATURE_AMPDU = (CAPEXT_WL_FEATURE_ID_BASE + 2),
+ CAPEXT_WL_FEATURE_AMSDU = (CAPEXT_WL_FEATURE_ID_BASE + 3),
+ CAPEXT_WL_FEATURE_STBC = (CAPEXT_WL_FEATURE_ID_BASE + 4),
+ CAPEXT_WL_FEATURE_NAN = (CAPEXT_WL_FEATURE_ID_BASE + 5),
+ CAPEXT_WL_FEATURE_COEX = (CAPEXT_WL_FEATURE_ID_BASE + 6),
+ CAPEXT_WL_FEATURE_FBT = (CAPEXT_WL_FEATURE_ID_BASE + 7),
+ CAPEXT_WL_FEATURE_MBSS = (CAPEXT_WL_FEATURE_ID_BASE + 8),
+ CAPEXT_WL_FEATURE_TXPWRCAP = (CAPEXT_WL_FEATURE_ID_BASE + 9),
+ CAPEXT_WL_FEATURE_PPR = (CAPEXT_WL_FEATURE_ID_BASE + 10),
+ CAPEXT_WL_FEATURE_PKT_FILTER = (CAPEXT_WL_FEATURE_ID_BASE + 11),
+ CAPEXT_WL_FEATURE_EHT = (CAPEXT_WL_FEATURE_ID_BASE + 12),
+ CAPEXT_WL_FEATURE_AP = (CAPEXT_WL_FEATURE_ID_BASE + 13),
+ CAPEXT_WL_FEATURE_MAX
+};
+
+/* MBSS cap sub-feature bit positions. These sub-features need to be reported */
+enum wlc_capext_mbss_subfeature_bitpos {
+ WLC_CAPEXT_MBSS_BITPOS_UCODE_BSS_0 = 0,
+ WLC_CAPEXT_MBSS_BITPOS_UCODE_BSS_1 = 1,
+ WLC_CAPEXT_MBSS_BITPOS_UCODE_BSS_2 = 2,
+ WLC_CAPEXT_MBSS_BITPOS_MAX
+};
+
+/* AMPDU cap sub-feature bit positions. These sub-features need to be reported */
+enum wlc_capext_ampdu_subfeature_bitpos {
+ WLC_CAPEXT_AMPDU_BITPOS_RX = 0,
+ WLC_CAPEXT_AMPDU_BITPOS_TX = 1,
+ WLC_CAPEXT_AMPDU_BITPOS_MAX
+};
+
+/* AMSDU cap sub-feature bit positions. These sub-features need to be reported */
+enum wlc_capext_amsdu_subfeature_bitpos {
+ WLC_CAPEXT_AMSDU_BITPOS_RX = 0,
+ WLC_CAPEXT_AMSDU_BITPOS_TX = 1,
+ WLC_CAPEXT_AMSDU_BITPOS_DYNLEN = 2,
+ WLC_CAPEXT_AMSDU_BITPOS_MAX
+};
+
+/* STBC cap sub-feature bit positions. These sub-features need to be reported */
+enum wlc_capext_stbc_subfeature_bitpos {
+ WLC_CAPEXT_STBC_BITPOS_TX = 0,
+ WLC_CAPEXT_STBC_BITPOS_RX_1SS = 1,
+ WLC_CAPEXT_STBC_BITPOS_MAX
+};
+
+/* TX power cap sub-feature bit positions. These sub-features need to be reported */
+enum wlc_capext_txpwrcap_subfeature_bitpos {
+ WLC_CAPEXT_TXPWRCAP_BITPOS_RSVD = 0,
+ WLC_CAPEXT_TXPWRCAP_BITPOS_TXPWRCAP_1 = 1,
+ WLC_CAPEXT_TXPWRCAP_BITPOS_TXPWRCAP_2 = 2,
+ WLC_CAPEXT_TXPWRCAP_BITPOS_TXPWRCAP_3 = 3,
+ WLC_CAPEXT_TXPWRCAP_BITPOS_TXPWRCAP_4 = 4,
+ WLC_CAPEXT_TXPWRCAP_BITPOS_MAX
+};
+
+/* PPR sub-feature bit positions. These sub-features need to be reported */
+enum wlc_capext_ppr_subfeature_bitpos {
+ WLC_CAPEXT_PPR_BITPOS_RSVD = 0,
+ WLC_CAPEXT_PPR_BITPOS_TLV_VER_1 = 1,
+ WLC_CAPEXT_PPR_BITPOS_TLV_VER_2 = 2,
+ WLC_CAPEXT_PPR_BITPOS_TLV_VER_3 = 3,
+ WLC_CAPEXT_PPR_BITPOS_TLV_VER_4 = 4,
+ WLC_CAPEXT_PPR_BITPOS_MAX
+};
+
+/* COEX sub-feature bit positions. These sub-features need to be reported */
+enum wlc_capext_coex_subfeature_bitpos {
+ WLC_CAPEXT_COEX_BITPOS_LTE = 0,
+ WLC_CAPEXT_COEX_BITPOS_LTECX_LBT = 1,
+ WLC_CAPEXT_COEX_BITPOS_BTC_WIFI_PROT = 2,
+ WLC_CAPEXT_COEX_BITPOS_RC1 = 3,
+ WLC_CAPEXT_COEX_BITPOS_SIB = 5,
+ WLC_CAPEXT_COEX_BITPOS_MAX
+};
+
+/* NAN sub-feature bit positions. These sub-features need to be reported */
+enum wlc_capext_nan_subfeature_bitpos {
+#ifdef NAN_DAM_ANDROID
+ WLC_CAPEXT_NAN_BITPOS_AUTODAM = 0,
+ WLC_CAPEXT_NAN_BITPOS_P2P = 1,
+#endif
+ WLC_CAPEXT_NAN_BITPOS_RANGE = 2,
+ WLC_CAPEXT_NAN_BITPOS_MESH = 3,
+ WLC_CAPEXT_NAN_BITPOS_MAX
+};
+
+/* FBT sub-feature bit positions. These sub-features need to be reported */
+enum wlc_capext_fbt_subfeature_bitpos {
+ WLC_CAPEXT_FBT_BITPOS_OVERDS = 0,
+ WLC_CAPEXT_FBT_BITPOS_ADPT = 1,
+ WLC_CAPEXT_FBT_BITPOS_MAX
+};
+
+/* Packet filter sub-feature bit positions. These sub-features need to be reported */
+enum wlc_capext_pkt_filter_subfeature_bitpos {
+ WLC_CAPEXT_PKT_FILTER_BITPOS_PKT_FILTER2 = 0,
+ WLC_CAPEXT_PKT_FILTER_BITPOS_PKT_FILTER6 = 1,
+ WLC_CAPEXT_PKT_FILTER_BITPOS_MAX
+};
+
+/* AP sub-feature bit positions. These sub-features need to be reported */
+enum wlc_capext_ap_subfeature_bitpos {
+ WLC_CAPEXT_AP_BITPOS_NONAX = 0,
+ WLC_CAPEXT_AP_BITPOS_AX_5G_ONLY = 1,
+ WLC_CAPEXT_AP_BITPOS_SAE = 2,
+ WLC_CAPEXT_AP_BITPOS_MAX
+};
+
+/* EHT sub-feature bit positions. These sub-features need to be reported */
+enum wlc_capext_eht_subfeature_bitpos {
+ WLC_CAPEXT_EHT_BITPOS_320MHZ = 0,
+ WLC_CAPEXT_EHT_BITPOS_MLO = 1,
+ WLC_CAPEXT_EHT_BITPOS_MAX
+};
+
+/* WLC features bit positions in top level WLC feature id. Features mentioned below are reported */
+enum wlc_capext_feature_bitpos {
+ WLC_CAPEXT_FEATURE_BITPOS_AP = 0, /* feature with sub-features */
+ WLC_CAPEXT_FEATURE_BITPOS_STA = 1,
+ WLC_CAPEXT_FEATURE_BITPOS_TOE = 2,
+ WLC_CAPEXT_FEATURE_BITPOS_WME = 3,
+ WLC_CAPEXT_FEATURE_BITPOS_802_11d = 4,
+
+ WLC_CAPEXT_FEATURE_BITPOS_802_11h = 5,
+ WLC_CAPEXT_FEATURE_BITPOS_RM = 6,
+ WLC_CAPEXT_FEATURE_BITPOS_CQA = 7,
+ WLC_CAPEXT_FEATURE_BITPOS_CAC = 8,
+ WLC_CAPEXT_FEATURE_BITPOS_MBSS = 9, /* feature with sub-features */
+
+ WLC_CAPEXT_FEATURE_BITPOS_DUALBAND = 10,
+ WLC_CAPEXT_FEATURE_BITPOS_AMPDU = 11, /* feature with sub-features */
+ WLC_CAPEXT_FEATURE_BITPOS_AMSDU = 12, /* feature with sub-features */
+ WLC_CAPEXT_FEATURE_BITPOS_TDLS = 13,
+ WLC_CAPEXT_FEATURE_BITPOS_WMF = 14,
+
+ WLC_CAPEXT_FEATURE_BITPOS_RXCHAIN_PWRSAVE = 15,
+ WLC_CAPEXT_FEATURE_BITPOS_RADIO_PWRSAVE = 16,
+ WLC_CAPEXT_FEATURE_BITPOS_P2P = 17,
+ WLC_CAPEXT_FEATURE_BITPOS_BCMDCS = 18,
+ WLC_CAPEXT_FEATURE_BITPOS_PROP_TXSTATUS = 19,
+
+ WLC_CAPEXT_FEATURE_BITPOS_MCHAN = 20,
+ WLC_CAPEXT_FEATURE_BITPOS_WDS = 21,
+ WLC_CAPEXT_FEATURE_BITPOS_DWDS = 22,
+ WLC_CAPEXT_FEATURE_BITPOS_CSO = 23,
+ WLC_CAPEXT_FEATURE_BITPOS_P2P0 = 24,
+
+ WLC_CAPEXT_FEATURE_BITPOS_ANQPO = 25,
+ WLC_CAPEXT_FEATURE_BITPOS_PROXD = 26,
+ WLC_CAPEXT_FEATURE_BITPOS_VHT_PROP_RATES = 27,
+ WLC_CAPEXT_FEATURE_BITPOS_MU_BEAMFORMER = 28,
+ WLC_CAPEXT_FEATURE_BITPOS_SU_BEAMFORMER = 29,
+
+ WLC_CAPEXT_FEATURE_BITPOS_MU_BEAMFORMEE = 30,
+ WLC_CAPEXT_FEATURE_BITPOS_SU_BEAMFORMEE = 31,
+ WLC_CAPEXT_FEATURE_BITPOS_160MHZ_SUPPORT = 32,
+ WLC_CAPEXT_FEATURE_BITPOS_HE = 33,
+ WLC_CAPEXT_FEATURE_BITPOS_EHT = 34, /* feature with sub-features */
+
+ WLC_CAPEXT_FEATURE_BITPOS_DFRTS = 35,
+ WLC_CAPEXT_FEATURE_BITPOS_LPAS = 36,
+ WLC_CAPEXT_FEATURE_BITPOS_TXPWRCACHE = 37,
+ WLC_CAPEXT_FEATURE_BITPOS_STBC = 38, /* feature with sub-features */
+ WLC_CAPEXT_FEATURE_BITPOS_PS_PRETEND = 39,
+
+ WLC_CAPEXT_FEATURE_BITPOS_MP2P = 40,
+ WLC_CAPEXT_FEATURE_BITPOS_RSDB = 41,
+ WLC_CAPEXT_FEATURE_BITPOS_PRBRESP_MAC_FLTR = 42,
+ WLC_CAPEXT_FEATURE_BITPOS_MFP = 43,
+ WLC_CAPEXT_FEATURE_BITPOS_NDOE = 44,
+
+ WLC_CAPEXT_FEATURE_BITPOS_RSSI_MON = 45,
+ WLC_CAPEXT_FEATURE_BITPOS_WNM = 46,
+ WLC_CAPEXT_FEATURE_BITPOS_BSSTRANS = 47,
+ WLC_CAPEXT_FEATURE_BITPOS_EPNO = 48,
+ WLC_CAPEXT_FEATURE_BITPOS_PFNX = 49,
+
+ WLC_CAPEXT_FEATURE_BITPOS_SCANMAC = 51,
+ WLC_CAPEXT_FEATURE_BITPOS_BDO = 52,
+ WLC_CAPEXT_FEATURE_BITPOS_PPR = 53, /* feature with sub-features */
+ WLC_CAPEXT_FEATURE_BITPOS_VE = 54,
+
+ WLC_CAPEXT_FEATURE_BITPOS_FBT = 55, /* feature with sub-features */
+ WLC_CAPEXT_FEATURE_BITPOS_CDEF = 56,
+ WLC_CAPEXT_FEATURE_BITPOS_TXPWRCAP = 58, /* feature with sub-features */
+ WLC_CAPEXT_FEATURE_BITPOS_MIMO_PS = 59,
+
+ WLC_CAPEXT_FEATURE_BITPOS_ARB = 60,
+ WLC_CAPEXT_FEATURE_BITPOS_OCL = 61,
+ WLC_CAPEXT_FEATURE_BITPOS_D11STATUS = 62,
+ WLC_CAPEXT_FEATURE_BITPOS_SCANCACHE = 63,
+ WLC_CAPEXT_FEATURE_BITPOS_APF = 64,
+
+ WLC_CAPEXT_FEATURE_BITPOS_ICMP = 65,
+ WLC_CAPEXT_FEATURE_BITPOS_IFVER = 66,
+ WLC_CAPEXT_FEATURE_BITPOS_TKO = 67,
+ WLC_CAPEXT_FEATURE_BITPOS_BGDFS = 68,
+ WLC_CAPEXT_FEATURE_BITPOS_IDAUTH = 69,
+
+ WLC_CAPEXT_FEATURE_BITPOS_IFST = 70,
+ WLC_CAPEXT_FEATURE_BITPOS_NAP = 71,
+ WLC_CAPEXT_FEATURE_BITPOS_UCM = 72,
+ WLC_CAPEXT_FEATURE_BITPOS_FIE = 73,
+ WLC_CAPEXT_FEATURE_BITPOS_TVPM = 74,
+
+ WLC_CAPEXT_FEATURE_BITPOS_TSYNC = 75,
+ WLC_CAPEXT_FEATURE_BITPOS_BCNTRIM = 76,
+ WLC_CAPEXT_FEATURE_BITPOS_LPR_SCAN = 77,
+ WLC_CAPEXT_FEATURE_BITPOS_BKOFF_EVT = 78,
+ WLC_CAPEXT_FEATURE_BITPOS_OPS = 79,
+
+ WLC_CAPEXT_FEATURE_BITPOS_CLM_RESTRICT = 80,
+ WLC_CAPEXT_FEATURE_BITPOS_EVT_EXT = 81,
+ WLC_CAPEXT_FEATURE_BITPOS_TDMTX = 83,
+ WLC_CAPEXT_FEATURE_BITPOS_NATOE = 84,
+
+ WLC_CAPEXT_FEATURE_BITPOS_MONITOR = 85,
+ WLC_CAPEXT_FEATURE_BITPOS_PSBW = 86,
+ WLC_CAPEXT_FEATURE_BITPOS_ROAMSTATS = 87,
+ WLC_CAPEXT_FEATURE_BITPOS_IDSUP = 88,
+ WLC_CAPEXT_FEATURE_BITPOS_GCMP = 89,
+
+ WLC_CAPEXT_FEATURE_BITPOS_MBO = 90,
+ WLC_CAPEXT_FEATURE_BITPOS_ESTM = 91,
+ WLC_CAPEXT_FEATURE_BITPOS_SC = 92,
+ WLC_CAPEXT_FEATURE_BITPOS_6G = 93,
+ WLC_CAPEXT_FEATURE_BITPOS_TX_PROF = 94,
+
+ WLC_CAPEXT_FEATURE_BITPOS_DSA = 95,
+ WLC_CAPEXT_FEATURE_BITPOS_ARPOE = 96,
+ WLC_CAPEXT_FEATURE_BITPOS_BCNPROT = 97,
+ WLC_CAPEXT_FEATURE_BITPOS_AVOID_BSSID = 98,
+ WLC_CAPEXT_FEATURE_BITPOS_IOT_BM = 99,
+
+ WLC_CAPEXT_FEATURE_BITPOS_IOT_BD = 100,
+ WLC_CAPEXT_FEATURE_BITPOS_HOST_SFHLLC = 101,
+ WLC_CAPEXT_FEATURE_BITPOS_RCO = 102,
+ WLC_CAPEXT_FEATURE_BITPOS_PMR = 103,
+ WLC_CAPEXT_FEATURE_BITPOS_SCR = 104,
+
+ WLC_CAPEXT_FEATURE_BITPOS_DTPC = 105,
+ WLC_CAPEXT_FEATURE_BITPOS_PASN = 106,
+ WLC_CAPEXT_FEATURE_BITPOS_QOS_MGMT = 107,
+ WLC_CAPEXT_FEATURE_BITPOS_LPC = 108,
+ WLC_CAPEXT_FEATURE_BITPOS_SAE = 109,
+
+ WLC_CAPEXT_FEATURE_BITPOS_EXTSAE = 110,
+ WLC_CAPEXT_FEATURE_BITPOS_D3CBUF = 111,
+ WLC_CAPEXT_FEATURE_BITPOS_PKT_FILTER = 112, /* feature with sub-features */
+ WLC_CAPEXT_FEATURE_BITPOS_COEX = 113, /* feature with sub-features */
+ WLC_CAPEXT_FEATURE_BITPOS_NAN = 114, /* feature with sub-features */
+
+ WLC_CAPEXT_FEATURE_BITPOS_IGMPOE = 115,
+ WLC_CAPEXT_FEATURE_BITPOS_OWE = 116,
+ WLC_CAPEXT_FEATURE_BITPOS_CSI = 117,
+ WLC_CAPEXT_FEATURE_BITPOS_SAE_H2E = 118,
+ WLC_CAPEXT_FEATURE_BITPOS_SAE_PK = 119,
+ WLC_CAPEXT_FEATURE_BITPOS_OBSS_HW = 120,
+ WLC_CAPEXT_FEATURE_BITPOS_DYN_BW = 121,
+ WLC_CAPEXT_FEATURE_BITPOS_MAX
+};
+
+#define WL_ROAM_PARAMS_IOV_MAJOR_VER_SHIFT 8u
+
+#define WL_ROAM_PARAMS_IOV_MAJOR_VER_1 1u
+#define WL_ROAM_PARAMS_IOV_MINOR_VER_1 1u
+
+#define WL_ROAM_PARAMS_IOV_VERSION_1_1 \
+ ((WL_ROAM_PARAMS_IOV_MAJOR_VER_1 << WL_ROAM_PARAMS_IOV_MAJOR_VER_SHIFT) | \
+ WL_ROAM_PARAMS_IOV_MINOR_VER_1)
+
+/* roam_params sub-command types */
+typedef enum {
+ WL_ROAM_PARAMS_NONE = 0,
+ WL_ROAM_PARAMS_ALLOWED_BAND = 1,
+ WL_ROAM_PARAMS_MAX
+} wl_roam_params_type_t;
+
+/* roam allowed band index */
+#define WLC_ROAM_ALLOW_BAND_AUTO WLC_BAND_AUTO /* auto-select */
+#define WLC_ROAM_ALLOW_BAND_2G (1<<0) /* 2.4 Ghz */
+#define WLC_ROAM_ALLOW_BAND_5G (1<<1) /* 5 Ghz */
+#if defined(WL_BAND6G) || defined(WL_6G_BAND)
+#define WLC_ROAM_ALLOW_BAND_6G (1<<2) /* 6 Ghz */
+#define WLC_ROAM_ALLOW_BAND_MAX (WLC_ROAM_ALLOW_BAND_2G | WLC_ROAM_ALLOW_BAND_5G | \
+ WLC_ROAM_ALLOW_BAND_6G)
+#else
+#define WLC_ROAM_ALLOW_BAND_MAX (WLC_ROAM_ALLOW_BAND_2G | WLC_ROAM_ALLOW_BAND_5G)
+#endif /* WL_BAND6G || WL_6G_BAND */
+
+/*
+ * Channel State Information (CSI) definitions
+ *
+ * IOVAR encoded in bcm_xtlv_t format with the subcommand as the TYPE field,
+ * length of subcommand data as the LENGTH field, followed by subcommand data
+ * structure as the DATA field.
+ */
+
+/* subcommand enum */
+typedef enum wl_csi_subcommand {
+ WL_CSI_SUBCMD_VERSION = 0u, /* CSI version */
+ WL_CSI_SUBCMD_DISABLE = 1u, /* disable CSI data */
+ WL_CSI_SUBCMD_ENABLE = 2u, /* enable CSI data */
+ WL_CSI_SUBCMD_DATA_INFO = 3u, /* get CSI data info */
+ WL_CSI_SUBCMD_GET_DATA = 4u, /* get CSI data fragment */
+} wl_csi_subcommand_t;
+
+/* current version */
+#define WL_CSI_VERSION_V1 1u
+
+/* WL_CSI_SUBCMD_VERSION GET subcommand data */
+typedef struct wl_csi_version {
+ uint16 version; /* CSI version */
+ uint8 pad[2u]; /* 4-byte struct alignment */
+} wl_csi_version_t;
+
+/* enable control bits */
+#define WL_CSI_ENABLE_CNTRL_TA (1u << 0u) /* match TA addr */
+#define WL_CSI_ENABLE_CNTRL_FRAME (1u << 1u) /* match frame type/subtype */
+#define WL_CSI_ENABLE_CNTRL_SUBCHANNEL (1u << 2u) /* enable subchannel index/width */
+#define WL_CSI_ENABLE_CNTRL_NSTREAM (1u << 3u) /* enable number of streams */
+
+/* WL_CSI_SUBCMD_ENABLE SET subcommand data */
+typedef struct wl_csi_enable {
+ uint16 enable_control; /* control bits */
+ uint8 subchannel_index; /* 0=1st, 1=2nd, etc */
+ uint8 subchannel_width; /* 0=20mhz, 1=40mhz, 2=80mhz, etc */
+ uint8 num_streams; /* 0=1 stream, 1=2 streams, etc */
+ uint8 frame; /* frame type (bits=0x0c) and subtype (bits=0xf0) */
+ chanspec_t chanspec; /* not currently used, reserved for future */
+ struct ether_addr ta; /* transmit address to match */
+ uint16 mode_timer; /* not currently used, reserved for future */
+} wl_csi_enable_t;
+
+/* WL_CSI_SUBCMD_DATA_INFO GET subcommand data info */
+typedef struct wl_csi_data_info {
+ struct ether_addr ta; /* transmit address */
+ struct ether_addr ra; /* receive address */
+ struct ether_addr bssid; /* bssid address */
+ uint16 num_tones; /* number of tones in data */
+ uint16 bw; /* bandwidth of frame */
+ uint8 frame; /* frame type (bits=0x0c) and subtype (bits=0xf0) */
+ uint8 nsts; /* num streams of frame */
+ uint8 slice; /* 0=main, 1=aux */
+ uint8 num_rx; /* number of rx cores in data */
+ uint8 num_streams; /* number of streams in data */
+ uint8 num_rssi; /* number of rssi in following array */
+ int8 rssi[BCM_FLEX_ARRAY]; /* variable length array of rssi of each core */
+} wl_csi_data_info_t;
+
+/* WL_CSI_SUBCMD_GET_DATA GET subcommand data fragment request */
+typedef struct wl_csi_get_data_req {
+ uint32 offset; /* CSI data offset to read */
+ uint32 length; /* request length */
+} wl_csi_get_data_req_t;
+
+/* WL_CSI_SUBCMD_GET_DATA GET subcommand data fragment response */
+typedef struct wl_csi_get_data_resp {
+ uint32 total_length; /* total length of CSI data */
+ uint32 offset; /* CSI data offset read */
+ uint32 length; /* length of CSI data in following array */
+ uint32 csi_data[BCM_FLEX_ARRAY]; /* variable length array of CSI data */
+} wl_csi_get_data_resp_t;
+
+/* User roam cache size updated 10 so that
+ * 4 slots are provided for 6G.
+ */
+#define USER_ROAM_CACHE_MAX_COUNT 10u
+
+#define WL_OCT_IOV_VERSION_1 1u
+
+enum wl_oct_iov_sub_cmd_v1 {
+ IOV_OCT_SUB_CMD_NONE = 0u,
+ IOV_OCT_SUB_CMD_ENAB = 1u,
+ IOV_OCT_SUB_CMD_STALE_RESET_TIMEOUT = 2u,
+ IOV_OCT_SUB_CMD_NO_DECISION_TIMEOUT = 3u,
+ IOV_OCT_SUB_CMD_CUR_CORE_MIN_DWELL_TIME = 4u,
+ IOV_OCT_SUB_CMD_EMA_WEIGHT_FACTOR = 5u,
+ IOV_OCT_SUB_CMD_MIN_NUM_VALID_CNT = 6u,
+ IOV_OCT_SUB_CMD_RSSI_DELTA_THRESH = 7u,
+ IOV_OCT_SUB_CMD_MIN_SAMPLING_FREQ = 8u,
+ IOV_OCT_SUB_CMD_VERSION = 9u,
+ IOV_OCT_SUB_CMD_STATUS = 10u,
+ IOV_OCT_SUB_CMD_RESET_STATUS = 11u,
+ IOV_OCT_SUB_CMD_TOTAL
+};
+
+enum wl_oct_xtlv_id_v1 {
+ WL_OCT_XTLV_NONE = 0x0u,
+ WL_OCT_XTLV_ENABLE = 0x1u,
+ WL_OCT_XTLV_STALE_RESET_TIMEOUT = 0x2u,
+ WL_OCT_XTLV_NO_DECISION_TIMEOUT = 0x3u,
+ WL_OCT_XTLV_CUR_CORE_MIN_DWELL_TIME = 0x4u,
+ WL_OCT_XTLV_EMA_WEIGHT_FACTOR = 0x5u,
+ WL_OCT_XTLV_MIN_NUM_VALID_CNT = 0x6u,
+ WL_OCT_XTLV_RSSI_DELTA_THRESH = 0x7u,
+ WL_OCT_XTLV_MIN_SAMPLING_FREQ = 0x8u,
+ WL_OCT_XTLV_VERSION = 0x9u,
+ WL_OCT_XTLV_STATUS = 0xau,
+ WL_OCT_XTLV_RESET_STATUS = 0xbu,
+ WL_OCT_XTLV_TOTAL
+};
+
+typedef enum wl_oct_status_xtlv_id {
+ WL_OCT_STATUS_CMN_ID = 0u,
+ WL_OCT_STATUS_SLICE_ID = 1u,
+ WL_OCT_STATUS_XTLV_MAX = 2u
+} wl_oct_status_xtlv_id_t;
+
+#define WL_OCT_STATUS_CMN_VER_1 1u /* status_cmn version */
+#define WL_OCT_STATUS_SLICE_VER_1 1u /* status_slice version */
+
+/* WL_OCT_STATUS_CMN_ID */
+typedef struct wl_oct_status_cmn_v1 {
+ uint8 version;
+ uint8 infra_assoced; /* primary infra assoced */
+ uint8 infra_assoc_slice; /* slice of primary infra assoced */
+ uint8 selected_txcm; /* currently selected txcm */
+} wl_oct_status_cmn_v1_t;
+
+/*
+ * Definitions for disable bits in the per slice status
+ */
+#define OCT_DISABLED_HOST (1u << 0u) /* Host disabled */
+#define OCT_DISABLED_NOINFRA (1u << 1u) /* Disabled due to
+ * no-infra or AS not-idle
+ */
+#define OCT_DISABLED_SCAN (1u << 2u) /* Disable due to Scan active */
+
+#define OCT_CORES_MAX 2u
+/* WL_OCT_STATUS_SLICE_ID */
+typedef struct wl_oct_status_slice_v1 {
+ uint8 version;
+ uint8 slice_id; /* slice identifier */
+ uint8 PAD[2]; /* 32-bit align */
+ uint32 disable_bits; /* current disable bits */
+ uint32 disable_dur; /* total disable duration (ms) */
+ uint32 enable_dur; /* total enable duration (ms) */
+ uint32 txcm_upd_cnt; /* total count of txcm decision updates
+ * due RSSI, TxPER, etc. blocks,
+ * currently RSSI block only
+ */
+ uint32 txcm_upd_cnt_rssi; /* total count of txcore updates
+ * due to RSSI delta
+ */
+ uint32 txcm_upd_cnt_rssi_aged; /* total count of txcore updates due to rssi aged */
+ uint32 override_dur; /* total dur (ms) oct decision is overriden */
+ uint32 txcm_dur[OCT_CORES_MAX]; /* per core txcm duration (ms) */
+ uint32 txcm_cnt[OCT_CORES_MAX]; /* per core txcm count */
+} wl_oct_status_slice_v1_t;
+
+/* ====== C2C definitions ===== */
+/* subcommand IDs */
+enum wl_c2c_cmd_id {
+ WL_C2C_CMD_PRE_EXPIRY,
+ WL_C2C_CMD_REG_RULES,
+ WL_C2C_CMD_STATUS,
+ WL_C2C_CMD_STATS,
+ WL_C2C_CMD_AP_CACHE,
+ WL_C2C_CMD_CTRL,
+ WL_C2C_CMD_EVTMASK,
+ WL_C2C_CMD_LAST
+};
+
+/* xtlvs */
+enum wl_c2c_tlv_id {
+ WL_C2C_XTLV_AP_ENTRY,
+ WL_C2C_XTLV_AP_INFO,
+ WL_C2C_XTLV_LAST
+};
+
+/* WL_C2C_XTLV_AP_ENTRY */
+typedef struct wl_c2c_ap_entry {
+ struct ether_addr bssid; /* ap bssid */
+ chanspec_t chanspec; /* ap chanspec */
+ uint32 last_rx_time; /* last esig rx time (GET only) */
+ uint32 num_esig_rx; /* esigs received from AP (GET only) */
+ int8 rssi; /* rssi (GET only) */
+ uint8 num_tlvs; /* number of tlvs included */
+ uint8 pad[2];
+ uint8 tlvs[];
+} wl_c2c_ap_entry_t;
+
+/* internal c2c states
+ *
+ * |----------ON----------|--ON(Pre-expiry)--|
+ * | |
+ * |<--------Enabling signal duration------->|
+ */
+#define C2C_STATE_OFF 1u /* c2c is inactive */
+#define C2C_STATE_ON 2u /* c2c active */
+#define C2C_STATE_ON_PRE_EXP 3u /* c2c active, in pre-expiry region */
+
+#define C2C_SCAN_STATE_OFF 1u /* no c2c-initiated scan */
+#define C2C_SCAN_STATE_IN_PROG 2u /* c2c-initiated scan in progress */
+
+#define C2C_SCAN_TYPE_DIRECT 1u /* direct scan to 6GHz AP */
+#define C2C_SCAN_TYPE_FULL 2u /* full scan */
+
+/* WL_C2C_CMD_PRE_EXPIRY */
+typedef uint32 wl_c2c_pre_exp_t; /* pre expiry time */
+
+/* WL_C2C_CMD_REG_RULES */
+#define WL_C2C_REG_RULES_VLP_ALLOWED 1u
+#define WL_C2C_REG_RULES_INV_TIMEOUT 0xFFFFFFFFu
+
+typedef struct wl_c2c_reg_rules {
+ uint32 esig_timeout; /* enabling signal timeout(ms) */
+ int8 min_rssi; /* enabling signal min rssi */
+ uint8 pad[3]; /* available for use */
+} wl_c2c_reg_rules_t;
+
+/* WL_C2C_CMD_STATUS */
+typedef struct wl_c2c_status {
+ uint8 cur_state; /* c2c state */
+ uint8 scan_state; /* scan state */
+ struct ether_addr esig_bssid; /* current enabling signal bssid */
+ chanspec_t esig_chanspec; /* current enabling signal chanspec */
+ int8 esig_rssi; /* current enabling signal rssi */
+ uint8 scan_type; /* scan type */
+ uint32 last_dscan; /* last direct scan start (FW) time */
+ uint32 last_fscan; /* last full scan start time */
+} wl_c2c_status_t;
+
+/* WL_C2C_CMD_CTRL */
+/* if set, enable scan requests from c2c module */
+#define WL_C2C_CTRL_C2C_SCAN 0x0001u
+/* if set, enable c2c functionality
+ * if clear, c2c functionality - enabling signal processing, scanning, etc is disabled
+ */
+#define WL_C2C_CTRL_ENAB 0x0002u
+#define WL_C2C_CTRL_ALLOWED_MASK (WL_C2C_CTRL_C2C_SCAN | WL_C2C_CTRL_ENAB)
+
+typedef uint32 wl_c2c_ctrl_t; /* c2c control bit masks */
+
+/* WL_C2C_CMD_AP_CACHE */
+/* WL_C2C_CMD_AP_CACHE operations */
+#define WL_C2C_CACHE_OP_GET 0u
+#define WL_C2C_CACHE_OP_ADD 1u
+#define WL_C2C_CACHE_OP_DEL 2u
+#define WL_C2C_CACHE_OP_CLR 3u
+
+typedef struct wl_c2c_ap_cache {
+ uint8 op; /* WL_C2C_CACHE_OP */
+ uint8 num_tlvs; /* number of tlvs */
+ uint8 pad[2];
+ uint8 tlvs[];
+} wl_c2c_ap_cache_t;
+
+/* WL_C2C_CMD_STATS */
+/* WL_C2C_CMD_STATS operations */
+#define WL_C2C_STATS_OP_CLEAR 0u
+
+typedef struct wl_c2c_stats {
+ uint32 esig_rx; /* total received enabling signals */
+ uint32 c2c_on_off; /* count of c2c on to off */
+ uint32 c2c_off_on; /* count of c2c off to on */
+ uint32 c2c_extn; /* c2c extension (due to new esig) */
+ uint32 dscan; /* number of directed scans */
+ uint32 fscan; /* number of full scans */
+ uint8 op; /* WL_C2C_STATS_OP */
+ uint8 num_tlvs; /* number of tlvs included */
+ uint8 pad[2]; /* available for use */
+ uint8 tlvs[];
+} wl_c2c_stats_t;
+
+/* WL_C2C_CMD_EVTMASK */
+typedef uint32 wl_c2c_evt_mask_t; /* event mask */
+
+/* events */
+#define WL_C2C_EVENT_AP_INFO_VER_1 1u
+/* WL_C2C_XTLV_AP_INFO */
+typedef struct wl_c2c_event_ap_info {
+ uint16 version; /* version */
+ uint16 len; /* total len */
+ struct ether_addr bssid; /* AP bssid */
+ chanspec_t chanspec; /* AP chanspec */
+ uint32 time_ms; /* esig receive time (FW time in ms) */
+ int8 rssi; /* rssi */
+ uint8 num_tlvs; /* number of tlvs */
+ uint8 pad[2];
+ uint8 tlvs[]; /* optional TLVs */
+} wl_c2c_event_ap_info_t;
+
+#define WL_CH6GPROF_VER_1 1
+enum wl_ch6gprof_cmd_id {
+ WL_CH6GPROF_CMD_VER = 0u,
+ WL_CH6GPROF_CMD_EXPIRY_TO = 1u,
+ WL_CH6GPROF_CMD_RESET_CACHE = 2u
+};
+
+/* scbrate iovar: txminrate */
+#define WL_SCBRATE_TXMINRATE_VER_1 1u
+typedef struct wl_scbrate_txminrate {
+ uint16 version;
+ uint16 len;
+ struct ether_addr peer_mac; /* mac addrss of peer */
+ uint16 txminrate; /* Tx min rate in 0.5mbps */
+} wl_scbrate_txminrate_t;
#endif /* _wlioctl_h_ */
diff --git a/include/wlioctl_defs.h b/include/wlioctl_defs.h
index 9b120b1..1551850 100644
--- a/include/wlioctl_defs.h
+++ b/include/wlioctl_defs.h
@@ -4,7 +4,7 @@
*
* Definitions subject to change without notice.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -40,7 +40,7 @@
#undef D11AC_IOTYPES
#define D11AC_IOTYPES
-#ifndef USE_NEW_RSPEC_DEFS
+#ifdef USE_LEGACY_RSPEC_DEFS
typedef uint32 ratespec_t;
/* Remove when no referencing branches exist.
@@ -83,7 +83,7 @@
#define HIGHEST_SINGLE_STREAM_MCS 7 /* MCS values greater than this enable multiple streams */
-#endif /* !USE_NEW_RSPEC_DEFS */
+#endif /* USE_LEGACY_RSPEC_DEFS */
/* Legacy defines for the nrate iovar */
#define OLD_NRATE_MCS_INUSE 0x00000080 /* MSC in use,indicates b0-6 holds an mcs */
@@ -236,21 +236,31 @@
* So, reserved flag definition removed.
*/
/* Use lower 16 bit for scan flags, the upper 16 bits are for internal use */
-#define WL_SCANFLAGS_PASSIVE 0x01U /* force passive scan */
-#define WL_SCANFLAGS_LOW_PRIO 0x02U /* Low priority scan */
-#define WL_SCANFLAGS_PROHIBITED 0x04U /* allow scanning prohibited channels */
-#define WL_SCANFLAGS_OFFCHAN 0x08U /* allow scanning/reporting off-channel APs */
-#define WL_SCANFLAGS_HOTSPOT 0x10U /* automatic ANQP to hotspot APs */
-#define WL_SCANFLAGS_SWTCHAN 0x20U /* Force channel switch for differerent bandwidth */
-#define WL_SCANFLAGS_FORCE_PARALLEL 0x40U /* Force parallel scan even when actcb_fn_t is on.
- * by default parallel scan will be disabled if actcb_fn_t
- * is provided.
- */
-#define WL_SCANFLAGS_SISO 0x40U /* Use 1 RX chain for scanning */
-#define WL_SCANFLAGS_MIMO 0x80U /* Force MIMO scanning */
+#define WL_SCANFLAGS_PASSIVE 0x01U /* force passive scan */
+#define WL_SCANFLAGS_LOW_PRIO 0x02U /* Low priority scan */
+#define WL_SCANFLAGS_PROHIBITED 0x04U /* allow scanning prohibited channels */
+#define WL_SCANFLAGS_OFFCHAN 0x08U /* allow scanning/reporting off-channel
+ * APs.
+ */
+#define WL_SCANFLAGS_HOTSPOT 0x10U /* automatic ANQP to hotspot APs */
+#define WL_SCANFLAGS_SWTCHAN 0x20U /* Force channel switch for differerent
+ * bandwidth.
+ */
+#define WL_SCANFLAGS_FORCE_PARALLEL 0x40U /* Force parallel scan even when actcb_fn_t
+ * is on.By default parallel scan will be
+ * disabled if actcb_fn_t is provided.
+ */
+#define WL_SCANFLAGS_SISO 0x40U /* Use 1 RX chain for scanning */
+#define WL_SCANFLAGS_MIMO 0x80U /* Force MIMO scanning */
-#define WL_SCANFLAGS_NOUPREQ 0x100U /* escan without sending unicast probe request */
-
+#define WL_SCANFLAGS_NO_6GHZ_FOLLOWUP 0x100U /* No 6G active scan due to RNR or FILS */
+#define WL_SCANFLAGS_INCL_FILS_DISC_FRAMES 0x200U /* Include Fils info as well in
+ * escan results.
+ */
+#define WL_SCANFLAGS_FORCE_SCAN_CORE_6G_SCAN 0x400U /* Force 6G scan on Scan core. */
+#define WL_SCANFLAGS_INCL_ORIG_RNR 0x800U /* Include scan results with
+ * matching RNR BSS
+ */
/* This is to re purpose the definition to firmware internal use.
* By repurposing these bit values can be used for host.
* These are moved to higher bits and defined in firmware.
@@ -281,6 +291,9 @@
/* BIT MASK for 6G_SCAN_TYPE */
#define WL_SCAN_SSIDFLAGS_SHORT_SSID 0x01U /* include short ssid */
#define WL_SCAN_INC_RNR 0x02U /* Include RNR channels for scan */
+#define WL_SCAN_SKIP_FILS_DISCOVERY_PERIOD 0x04U /* Skip FILS Discovery Period for 6G chans */
+#define WL_SCAN_ACTIVE_6GHZ 0x08U /* Force active scan for 6GHZ channel */
+
/* Value to decide scan type based on scqs */
#define WL_SC_RETRY_SCAN_MODE_NO_SCAN 0x0u /* Do not reschedule scan */
#define WL_SC_RETRY_SCAN_MODE_HIGH_ACC 0x1u /* Reschedule scan as HighAccuracy */
@@ -436,6 +449,8 @@
#define WL_BSS_FLAGS_QBSS_LOAD 0x02 /* QBSS load value present */
#define WL_BSS2_FLAGS_FROM_FILS 0x04 /* values are based on FILS frame */
#define WL_BSS2_FLAGS_SHORT_SSID 0x08 /* values ssid is indicating as short ssid */
+#define WL_BSS2_FLAGS_RNR_MATCH 0x10 /* To report original BSS that has RNR match */
+#define WL_BSS2_FLAGS_HE_BCN_PRBRSP 0x20u /* BSS update to indiacte HE bcn or prb rsp. */
/* bit definitions for bcnflags in wl_bss_info */
#define WL_BSS_BCNFLAGS_INTERWORK_PRESENT 0x01 /* beacon had IE, accessnet valid */
@@ -638,7 +653,6 @@
#define WPA3_AUTH_1X_SUITE_B_SHA384 0x400000 /* Suite B-192 SHA384 */
#define WPA3_AUTH_PSK_SHA384 0x800000 /* PSK with SHA384 key derivation */
#define WPA3_AUTH_SAE_AP_ONLY 0x1000000 /* SAE restriction to connect to pure SAE APs */
-#define WPA3_AUTH_PASN 0x2000000 /* PASN */
/* WPA2_AUTH_SHA256 not used anymore. Just kept here to avoid build issue in DINGO */
#define WPA2_AUTH_SHA256 0x8000
#define WPA_AUTH_PFN_ANY 0xffffffff /* for PFN, match only ssid */
@@ -647,8 +661,8 @@
#define MAXPMKID 16 /* max # PMKID cache entries NDIS */
#ifdef MACOSX
-/* Macos limits ioctl maxlen to 2k */
-#define WLC_IOCTL_MAXLEN 2048u /* "max" length ioctl buffer */
+/* Macos limits ioctl maxlen for TX to 1864 and for RX to 2004 */
+#define WLC_IOCTL_MAXLEN 2000 /* "max" length ioctl buffer */
#else
#define WLC_IOCTL_MAXLEN 8192u /* "max" length ioctl buffer */
#endif /* MACOSX */
@@ -659,8 +673,8 @@
#define WLC_SAMPLECOLLECT_MAXLEN 10240u /* Max Sample Collect buffer for two cores */
-#define WLC_IOCTL_NANRESP_MAXLEN 4096u /* "max" length nan ioctl resp buffer */
-#define WLC_IOCTL_NANRESP_MEDLEN 800u /* "med" length nan ioctl resp buffer */
+#define WLC_IOCTL_NANRESP_MAXLEN 4096u /* "max" length nan ioctl resp buffer */
+#define WLC_IOCTL_NANRESP_MEDLEN WLC_IOCTL_MEDLEN /* "med" length nan ioctl resp buffer */
/* common ioctl definitions */
#define WLC_GET_MAGIC 0
@@ -1226,7 +1240,7 @@
#define WLC_BW_40MHZ_BIT (1<<1)
#define WLC_BW_80MHZ_BIT (1<<2)
#define WLC_BW_160MHZ_BIT (1<<3)
-#define WLC_BW_320MHZ_BIT (1u<<5u)
+#define WLC_BW_320MHZ_BIT (1u<<4u)
/* Bandwidth capabilities */
#define WLC_BW_CAP_20MHZ (WLC_BW_20MHZ_BIT)
@@ -1238,16 +1252,12 @@
#define WLC_BW_CAP_320MHZ (WLC_BW_320MHZ_BIT| \
WLC_BW_160MHZ_BIT|WLC_BW_80MHZ_BIT| \
WLC_BW_40MHZ_BIT|WLC_BW_20MHZ_BIT)
-#define WLC_BW_CAP_240MHZ (WLC_BW_240MHZ_BIT| \
- WLC_BW_160MHZ_BIT|WLC_BW_80MHZ_BIT| \
- WLC_BW_40MHZ_BIT|WLC_BW_20MHZ_BIT)
#define WLC_BW_CAP_UNRESTRICTED 0xFF
#define WL_BW_CAP_20MHZ(bw_cap) (((bw_cap) & WLC_BW_20MHZ_BIT) ? TRUE : FALSE)
#define WL_BW_CAP_40MHZ(bw_cap) (((bw_cap) & WLC_BW_40MHZ_BIT) ? TRUE : FALSE)
#define WL_BW_CAP_80MHZ(bw_cap) (((bw_cap) & WLC_BW_80MHZ_BIT) ? TRUE : FALSE)
#define WL_BW_CAP_160MHZ(bw_cap) (((bw_cap) & WLC_BW_160MHZ_BIT) ? TRUE : FALSE)
-#define WL_BW_CAP_240MHZ(bw_cap) (((bw_cap) & WLC_BW_240MHZ_BIT) ? TRUE : FALSE)
#define WL_BW_CAP_320MHZ(bw_cap) (((bw_cap) & WLC_BW_320MHZ_BIT) ? TRUE : FALSE)
/* values to force tx/rx chain */
@@ -1451,13 +1461,10 @@
#define WL_FBT_VAL 0x00800000
#define WL_RRM_VAL 0x00800000 /* reuse */
#define WL_MQ_VAL 0x01000000
-/* This level is currently used in Phoenix2 only */
-#define WL_SRSCAN_VAL 0x02000000
+#define WL_RANDMAC_VAL 0x02000000
#define WL_WNM_VAL 0x04000000
/* re-using WL_WNM_VAL for MBO */
#define WL_MBO_VAL 0x04000000
-/* re-using WL_SRSCAN_VAL */
-#define WL_RANDMAC_VAL 0x02000000
#define WL_NET_DETECT_VAL 0x20000000
#define WL_OCE_VAL 0x20000000 /* reuse */
@@ -1485,12 +1492,27 @@
#define WL_EVENTING_MASK_EXT_LEN ROUNDUP(WLC_E_LAST, NBBY)/NBBY
/* join preference types */
-#define WL_JOIN_PREF_RSSI 1u /* by RSSI */
-#define WL_JOIN_PREF_WPA 2u /* by akm and ciphers */
-#define WL_JOIN_PREF_BAND 3u /* by 802.11 band */
-#define WL_JOIN_PREF_RSSI_DELTA 4u /* by 802.11 band only if RSSI delta condition matches */
-#define WL_JOIN_PREF_TRANS_PREF 5u /* defined by requesting AP */
-#define WL_JOIN_PREF_RSN_PRIO 6u /* by RSNE/RSNXE related security priority */
+#define WL_JOIN_PREF_RSSI 1u /* by RSSI */
+#define WL_JOIN_PREF_WPA 2u /* by akm and ciphers */
+#define WL_JOIN_PREF_BAND 3u /* by 802.11 band */
+#define WL_JOIN_PREF_RSSI_DELTA 4u /* by 802.11 band only if RSSI
+ * delta condition matches
+ */
+#define WL_JOIN_PREF_TRANS_PREF 5u /* defined by requesting AP */
+#define WL_JOIN_PREF_RSN_PRIO 6u /* by RSNE/RSNXE related security priority */
+#define WL_JOIN_PREF_RSSI_PER_BAND 7u /* RSSI boost value per band */
+#define WL_JOIN_PREF_SKIP_PSC 8u /* Used to set flag to filter PSC channel scan */
+#define WL_JOIN_PREF_6G_DISABLE 9u /* Used to disable join/roam 6G BSS target */
+
+/* Join preference 6G disable Flag definition */
+#define WL_JP_6G_DISABLE_ROAM (1u << 0u) /* Used to set flag to disable join/roam to
+ 6G BSS target
+ */
+
+/* Join preference skip PSC Flag definition */
+#define WL_JP_SKIP_PSC_ROAM (1u << 0u) /* Used to set flag to filter PSC channel
+ during full band roam scan
+ */
/* Join preference RSN priority */
#define WL_JP_RSN_SAE_PK 1u /* SAE-PK higher priority over non SAE-PK APs */
@@ -1532,6 +1554,8 @@
#define WL_CHAN_BAND_6G (1u << 9) /* 6GHz-band channel */
#define WL_CHAN_BAND_6G_VLP (1u << 10u) /* 6GHz VLP channel */
#define WL_CHAN_BAND_6G_PSC (1u << 11u) /* 6GHz PSC channel */
+#define WL_CHAN_BAND_6G_LPI (1u << 12u) /* 6GHz LPI channel */
+#define WL_CHAN_BAND_6G_SP (1u << 13u) /* 6GHz SP channel */
#define WL_CHAN_OOS_SHIFT 24u /* shift for OOS field */
#define WL_CHAN_OOS_MASK 0xFF000000u /* field specifying minutes remaining for this
@@ -1541,17 +1565,22 @@
/* BTC mode used by "btc_mode" iovar */
#define WL_BTC_DISABLE 0 /* disable BT coexistence */
-#define WL_BTC_FULLTDM 1 /* full TDM COEX */
-#define WL_BTC_ENABLE 1 /* full TDM COEX to maintain backward compatiblity */
-#define WL_BTC_PREMPT 2 /* full TDM COEX with preemption */
-#define WL_BTC_LITE 3 /* light weight coex for large isolation platform */
-#define WL_BTC_PARALLEL 4 /* BT and WLAN run in parallel with separate antenna */
-#define WL_BTC_HYBRID 5 /* hybrid coex, only ack is allowed to transmit in BT slot */
+#define WL_BTC_FULLTDM 1 /* full TDM COEX */
+#define WL_BTC_ENABLE 1 /* full TDM COEX to maintain backward compatiblity */
+#define WL_BTC_PREMPT 2 /* full TDM COEX with preemption */
+#define WL_BTC_LITE 3 /* light weight coex for large isolation platform */
+#define WL_BTC_PARALLEL 4 /* BT and WLAN run in parallel with separate antenna */
+#define WL_BTC_HYBRID 5 /* hybrid coex, only ack allowed to transmit in BT slot */
+#define WL_BTC_HYBRID_WLTX 6 /* hybrid coex HPP mode w WL data Tx during BT grant */
#define WL_BTC_DEFAULT 8 /* set the default mode for the device */
#define WL_INF_BTC_DISABLE 0
#define WL_INF_BTC_ENABLE 1
#define WL_INF_BTC_AUTO 3
+#define WL_BTC_MODE_IOV_2G_MASK 0xFFu
+#define WL_BTC_MODE_IOV_5G_MASK 0xFF00u
+#define WL_BTC_MODE_IOV_5G_SHIFT 0x8u
+
/* BTC wire used by "btc_wire" iovar */
#define WL_BTC_DEFWIRE 0 /* use default wire setting */
#define WL_BTC_2WIRE 2 /* use 2-wire BTC */
@@ -1753,9 +1782,6 @@
#define MAX_RSSI_LEVELS 8
-/* **** EXTLOG **** */
-#define EXTLOG_CUR_VER 0x0100
-
#define MAX_ARGSTR_LEN 18 /* At least big enough for storing ETHER_ADDR_STR_LEN */
/* log modules (bitmap) */
@@ -2150,7 +2176,7 @@
#define PFN_SCANRESULT_VERSION 1
#endif /* PFN_SCANRESULT_2 */
#ifndef MAX_PFN_LIST_COUNT
-#define MAX_PFN_LIST_COUNT 16
+#define MAX_PFN_LIST_COUNT 64
#endif /* MAX_PFN_LIST_COUNT */
#define PFN_COMPLETE 1
@@ -2182,7 +2208,7 @@
#define WL_PFN_CFG_FLAGS_PROHIBITED 0x00000001 /* Accept and use prohibited channels */
#define WL_PFN_CFG_FLAGS_HISTORY_OFF 0x00000002 /* Scan history suppressed */
/* Set to avoid sending direct probe in 6G channels */
-#define WL_PFN_CFG_FLAGS_NOUPREQ_6G 0x00000004
+#define WL_PFN_CFG_FLAGS_NO_6GHZ_FOLLOWUP 0x00000004
#define WL_PFN_HIDDEN_BIT 2
#define PNO_SCAN_MAX_FW 508*1000 /* max time scan time in msec */
@@ -2454,6 +2480,8 @@
#define WL_PWRSTATS_TYPE_SLICE_INDEX_BAND_INFO 14 /* wl_pwr_slice_index_band_t */
#define WL_PWRSTATS_TYPE_PSBW_STATS 15 /* struct wl_pwr_psbw_stats_t */
#define WL_PWRSTATS_TYPE_PM_ACCUMUL 16 /* struct wl_pwr_pm_accum_stats_v1_t */
+#define WL_PWRSTATS_TYPE_SCAN_6E 17 /* struct wl_pwr_scan_6E_stats_v1 */
+#define WL_PWRSTATS_TYPE_SCAN_EXT 18 /**< struct wl_pwr_scan_stats_v1 */
/* IOV AWD DATA */
#define AWD_DATA_JOIN_INFO 0
diff --git a/include/wlioctl_utils.h b/include/wlioctl_utils.h
index 93b369c..9558938 100644
--- a/include/wlioctl_utils.h
+++ b/include/wlioctl_utils.h
@@ -1,7 +1,7 @@
/*
* Custom OID/ioctl related helper functions.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/wpa.h b/include/wpa.h
index b508577..a2f2670 100644
--- a/include/wpa.h
+++ b/include/wpa.h
@@ -1,7 +1,7 @@
/*
* Fundamental types and constants relating to WPA
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/include/wps.h b/include/wps.h
index 13c8dfc..734e8aa 100644
--- a/include/wps.h
+++ b/include/wps.h
@@ -1,7 +1,7 @@
/*
* WPS IE definitions
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/linux_osl.c b/linux_osl.c
old mode 100755
new mode 100644
index 703341d..cd68d33
--- a/linux_osl.c
+++ b/linux_osl.c
@@ -1,7 +1,7 @@
/*
* Linux OS Independent Layer
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -155,12 +155,15 @@
-EINVAL, /* BCME_ROAM */
-EOPNOTSUPP, /* BCME_NO_SIG_FILE */
-EOPNOTSUPP, /* BCME_RESP_PENDING */
+ -EINVAL, /* BCME_ACTIVE */
+ -EINVAL, /* BCME_IN_PROGRESS */
+ -EINVAL, /* BCME_NOP */
/* When an new error code is added to bcmutils.h, add os
* specific error translation here as well
*/
/* check if BCME_LAST changed since the last time this function was updated */
-#if BCME_LAST != BCME_RESP_PENDING
+#if BCME_LAST != BCME_NOP
#error "You need to add a OS error translation in the linuxbcmerrormap \
for new error code defined in bcmutils.h"
#endif
@@ -271,6 +274,7 @@
/* Array bounds covered by ASSERT in osl_attach */
return linuxbcmerrormap[-bcmerror];
}
+
#ifdef SHARED_OSL_CMN
osl_t *
osl_attach(void *pdev, uint bustype, bool pkttag, void **osl_cmn)
@@ -288,7 +292,7 @@
if (!(osh = kmalloc(sizeof(osl_t), flags)))
return osh;
- ASSERT(osh);
+ ASSERT_NULL(osh);
bzero(osh, sizeof(osl_t));
@@ -315,8 +319,10 @@
atomic_add(1, &osh->cmn->refcount);
bcm_object_trace_init();
+
/* Check that error map has the right number of entries in it */
ASSERT(ABS(BCME_LAST) == (ARRAYSIZE(linuxbcmerrormap) - 1));
+
osh->failed = 0;
osh->pdev = pdev;
osh->pub.pkttag = pkttag;
@@ -471,7 +477,8 @@
uint val = 0;
uint retry = PCI_CFG_RETRY; /* PR15065: faulty cardbus controller bug */
- ASSERT((osh && (osh->magic == OS_HANDLE_MAGIC)));
+ ASSERT_NULL(osh);
+ ASSERT(osh->magic == OS_HANDLE_MAGIC);
/* only 4byte access supported */
ASSERT(size == 4);
@@ -496,7 +503,8 @@
{
uint retry = PCI_CFG_RETRY; /* PR15065: faulty cardbus controller bug */
- ASSERT((osh && (osh->magic == OS_HANDLE_MAGIC)));
+ ASSERT_NULL(osh);
+ ASSERT(osh->magic == OS_HANDLE_MAGIC);
/* only 4byte access supported */
ASSERT(size == 4);
@@ -525,7 +533,9 @@
uint
osl_pci_bus(osl_t *osh)
{
- ASSERT(osh && (osh->magic == OS_HANDLE_MAGIC) && osh->pdev);
+ ASSERT_NULL(osh);
+ ASSERT(osh->magic == OS_HANDLE_MAGIC)
+ ASSERT_NULL(osh->pdev);
#if defined(__ARM_ARCH_7A__)
return pci_domain_nr(((struct pci_dev *)osh->pdev)->bus);
@@ -538,7 +548,9 @@
uint
osl_pci_slot(osl_t *osh)
{
- ASSERT(osh && (osh->magic == OS_HANDLE_MAGIC) && osh->pdev);
+ ASSERT_NULL(osh);
+ ASSERT(osh->magic == OS_HANDLE_MAGIC);
+ ASSERT_NULL(osh->pdev);
#if defined(__ARM_ARCH_7A__)
return PCI_SLOT(((struct pci_dev *)osh->pdev)->devfn) + 1;
@@ -551,7 +563,9 @@
uint
osl_pcie_domain(osl_t *osh)
{
- ASSERT(osh && (osh->magic == OS_HANDLE_MAGIC) && osh->pdev);
+ ASSERT_NULL(osh);
+ ASSERT(osh->magic == OS_HANDLE_MAGIC);
+ ASSERT_NULL(osh->pdev);
return pci_domain_nr(((struct pci_dev *)osh->pdev)->bus);
}
@@ -560,7 +574,9 @@
uint
osl_pcie_bus(osl_t *osh)
{
- ASSERT(osh && (osh->magic == OS_HANDLE_MAGIC) && osh->pdev);
+ ASSERT_NULL(osh);
+ ASSERT(osh->magic == OS_HANDLE_MAGIC);
+ ASSERT_NULL(osh->pdev);
return ((struct pci_dev *)osh->pdev)->bus->number;
}
@@ -569,7 +585,9 @@
struct pci_dev *
osl_pci_device(osl_t *osh)
{
- ASSERT(osh && (osh->magic == OS_HANDLE_MAGIC) && osh->pdev);
+ ASSERT_NULL(osh);
+ ASSERT(osh->magic == OS_HANDLE_MAGIC);
+ ASSERT_NULL(osh->pdev);
return osh->pdev;
}
@@ -644,6 +662,46 @@
return ptr;
}
+#if defined(L1_CACHE_BYTES)
+#define DMA_PAD (L1_CACHE_BYTES)
+#else
+#define DMA_PAD (128u)
+#endif
+void *
+osl_dma_mallocz(osl_t *osh, uint size, uint *dmable_size)
+{
+ void *addr = NULL;
+ gfp_t flags = 0;
+ uint16 align = 0;
+ uint32 dmapad = 0;
+
+ if (osh)
+ ASSERT(osh->magic == OS_HANDLE_MAGIC);
+ if (!size || !dmable_size)
+ return NULL;
+
+ *dmable_size = size;
+ align = *dmable_size % DMA_PAD;
+ dmapad = align ? (DMA_PAD - align) : 0;
+ *dmable_size += dmapad;
+
+ flags = CAN_SLEEP() ? GFP_KERNEL: GFP_ATOMIC;
+ flags |= GFP_DMA;
+ addr = kmalloc(*dmable_size, flags);
+ if (addr != NULL) {
+ bzero(addr, *dmable_size);
+ if (osh && osh->cmn) {
+ atomic_add(*dmable_size, &osh->cmn->malloced);
+ }
+ } else {
+ if (osh) {
+ osh->failed++;
+ }
+ }
+
+ return addr;
+}
+
void
osl_mfree(osl_t *osh, void *addr, uint size)
{
@@ -685,6 +743,23 @@
kfree(addr);
}
+void
+osl_dma_mfree(osl_t *osh, void *addr, uint size)
+{
+ if (addr == NULL) {
+ return;
+ }
+
+ if (osh && osh->cmn) {
+ ASSERT(osh->magic == OS_HANDLE_MAGIC);
+ ASSERT(size <= osl_malloced(osh));
+ atomic_sub(size, &osh->cmn->malloced);
+ }
+
+ kfree(addr);
+ addr = NULL;
+}
+
#ifdef BCMDBG_MEM
/* In BCMDBG_MEM configurations osl_vmalloc is only used internally in
* the implementation of osl_debug_vmalloc. Because we are using the GCC
@@ -751,10 +826,88 @@
vfree(addr);
}
+#ifdef BCMDBG_MEM
+/* In BCMDBG_MEM configurations osl_kvmalloc is only used internally in
+ * the implementation of osl_debug_kvmalloc. Because we are using the GCC
+ * -Wstrict-prototypes compile option, we must always have a prototype
+ * for a global/external function. So make osl_kvmalloc static in
+ * the BCMDBG_MEM case.
+ */
+static
+#endif
+void *
+osl_kvmalloc(osl_t *osh, uint size)
+{
+ void *addr;
+ gfp_t flags;
+
+ /* only ASSERT if osh is defined */
+ if (osh)
+ ASSERT(osh->magic == OS_HANDLE_MAGIC);
+
+ flags = CAN_SLEEP() ? GFP_KERNEL: GFP_ATOMIC;
+#if (LINUX_VERSION_CODE < KERNEL_VERSION(4, 12, 0))
+ if ((addr = kmalloc(size, flags)) == NULL) {
+#else
+ if ((addr = kvmalloc(size, flags)) == NULL) {
+#endif /* LINUX_VERSION_CODE < KERNEL_VERSION(4, 12, 0) */
+ if (osh)
+ osh->failed++;
+ return (NULL);
+ }
+ if (osh && osh->cmn)
+ atomic_add(size, &osh->cmn->malloced);
+
+ return (addr);
+}
+
+#ifndef BCMDBG_MEM
+void *
+osl_kvmallocz(osl_t *osh, uint size)
+{
+ void *ptr;
+
+ ptr = osl_kvmalloc(osh, size);
+
+ if (ptr != NULL) {
+ bzero(ptr, size);
+ }
+
+ return ptr;
+}
+#endif
+
+#ifdef BCMDBG_MEM
+/* In BCMDBG_MEM configurations osl_kvmfree is only used internally in
+ * the implementation of osl_debug_kvmfree. Because we are using the GCC
+ * -Wstrict-prototypes compile option, we must always have a prototype
+ * for a global/external function. So make osl_kvmfree static in
+ * the BCMDBG_MEM case.
+ */
+static
+#endif
+void
+osl_kvmfree(osl_t *osh, void *addr, uint size)
+{
+ if (osh && osh->cmn) {
+ ASSERT(osh->magic == OS_HANDLE_MAGIC);
+
+ ASSERT(size <= osl_malloced(osh));
+
+ atomic_sub(size, &osh->cmn->malloced);
+ }
+#if (LINUX_VERSION_CODE < KERNEL_VERSION(4, 12, 0))
+ kfree(addr);
+#else
+ kvfree(addr);
+#endif /* LINUX_VERSION_CODE < KERNEL_VERSION(4, 12, 0) */
+}
+
uint
osl_check_memleak(osl_t *osh)
{
- ASSERT((osh && (osh->magic == OS_HANDLE_MAGIC)));
+ ASSERT_NULL(osh);
+ ASSERT(osh->magic == OS_HANDLE_MAGIC);
if (atomic_read(&osh->cmn->refcount) == 1)
return (atomic_read(&osh->cmn->malloced));
else
@@ -764,14 +917,16 @@
uint
osl_malloced(osl_t *osh)
{
- ASSERT((osh && (osh->magic == OS_HANDLE_MAGIC)));
+ ASSERT_NULL(osh);
+ ASSERT(osh->magic == OS_HANDLE_MAGIC);
return (atomic_read(&osh->cmn->malloced));
}
uint
osl_malloc_failed(osl_t *osh)
{
- ASSERT((osh && (osh->magic == OS_HANDLE_MAGIC)));
+ ASSERT_NULL(osh);
+ ASSERT(osh->magic == OS_HANDLE_MAGIC);
return (osh->failed);
}
@@ -1008,13 +1163,126 @@
osl_vmfree(osh, p, size + sizeof(bcm_mem_link_t));
}
+void *
+osl_debug_kvmalloc(osl_t *osh, uint size, int line, const char* file)
+{
+ bcm_mem_link_t *p;
+ const char* basename;
+ unsigned long flags = 0;
+ if (!size) {
+ OSL_PRINT(("%s: allocating zero sized mem at %s line %d\n",
+ __FUNCTION__, file, line));
+ ASSERT(0);
+ }
+
+ if ((p = (bcm_mem_link_t*)osl_kvmalloc(osh, sizeof(bcm_mem_link_t) + size)) == NULL) {
+ return (NULL);
+ }
+
+ if (osh) {
+ OSL_MEMLIST_LOCK(&osh->cmn->dbgmem_lock, flags);
+ }
+
+ p->size = size;
+ p->line = line;
+ p->osh = (void *)osh;
+
+ basename = strrchr(file, '/');
+ /* skip the '/' */
+ if (basename)
+ basename++;
+
+ if (!basename)
+ basename = file;
+
+ strlcpy(p->file, basename, sizeof(p->file));
+
+ /* link this block */
+ if (osh) {
+ p->prev = NULL;
+ p->next = osh->cmn->dbgvmem_list;
+ if (p->next)
+ p->next->prev = p;
+ osh->cmn->dbgvmem_list = p;
+ OSL_MEMLIST_UNLOCK(&osh->cmn->dbgmem_lock, flags);
+ }
+
+ return p + 1;
+}
+
+void *
+osl_debug_kvmallocz(osl_t *osh, uint size, int line, const char* file)
+{
+ void *ptr;
+
+ ptr = osl_debug_kvmalloc(osh, size, line, file);
+
+ if (ptr != NULL) {
+ bzero(ptr, size);
+ }
+
+ return ptr;
+}
+
+void
+osl_debug_kvmfree(osl_t *osh, void *addr, uint size, int line, const char* file)
+{
+ bcm_mem_link_t *p = (bcm_mem_link_t *)((int8*)addr - sizeof(bcm_mem_link_t));
+ unsigned long flags = 0;
+
+ ASSERT(osh == NULL || osh->magic == OS_HANDLE_MAGIC);
+
+ if (p->size == 0) {
+ OSL_PRINT(("osl_debug_mfree: double free on addr %p size %d at line %d file %s\n",
+ addr, size, line, file));
+ ASSERT(p->size);
+ return;
+ }
+
+ if (p->size != size) {
+ OSL_PRINT(("%s: dealloca size does not match alloc size\n", __FUNCTION__));
+ OSL_PRINT(("Dealloc addr %p size %d at line %d file %s\n", addr, size, line, file));
+ OSL_PRINT(("Alloc size %d line %d file %s\n", p->size, p->line, p->file));
+ ASSERT(p->size == size);
+ return;
+ }
+
+ if (osh && ((osl_t*)p->osh)->cmn != osh->cmn) {
+ OSL_PRINT(("osl_debug_mfree: alloc osh %p does not match dealloc osh %p\n",
+ ((osl_t*)p->osh)->cmn, osh->cmn));
+ OSL_PRINT(("Dealloc addr %p size %d at line %d file %s\n", addr, size, line, file));
+ OSL_PRINT(("Alloc size %d line %d file %s\n", p->size, p->line, p->file));
+ ASSERT(((osl_t*)p->osh)->cmn == osh->cmn);
+ return;
+ }
+
+ /* unlink this block */
+ if (osh && osh->cmn) {
+ OSL_MEMLIST_LOCK(&osh->cmn->dbgmem_lock, flags);
+ if (p->prev)
+ p->prev->next = p->next;
+ if (p->next)
+ p->next->prev = p->prev;
+ if (osh->cmn->dbgvmem_list == p)
+ osh->cmn->dbgvmem_list = p->next;
+ p->next = p->prev = NULL;
+ }
+ p->size = 0;
+
+ if (osh && osh->cmn) {
+ OSL_MEMLIST_UNLOCK(&osh->cmn->dbgmem_lock, flags);
+ }
+ osl_kvmfree(osh, p, size + sizeof(bcm_mem_link_t));
+}
+
int
osl_debug_memdump(osl_t *osh, struct bcmstrbuf *b)
{
bcm_mem_link_t *p;
unsigned long flags = 0;
- ASSERT((osh && (osh->magic == OS_HANDLE_MAGIC)));
+ ASSERT_NULL(osh);
+ ASSERT(osh->magic == OS_HANDLE_MAGIC);
OSL_MEMLIST_LOCK(&osh->cmn->dbgmem_lock, flags);
@@ -1091,7 +1359,8 @@
{
void *va;
uint16 align = (1 << align_bits);
- ASSERT((osh && (osh->magic == OS_HANDLE_MAGIC)));
+ ASSERT_NULL(osh);
+ ASSERT(osh->magic == OS_HANDLE_MAGIC);
if (!ISALIGNED(DMA_CONSISTENT_ALIGN, align))
size += align;
@@ -1133,7 +1402,8 @@
#ifdef BCMDMA64OSL
dma_addr_t paddr;
#endif /* BCMDMA64OSL */
- ASSERT((osh && (osh->magic == OS_HANDLE_MAGIC)));
+ ASSERT_NULL(osh);
+ ASSERT(osh->magic == OS_HANDLE_MAGIC);
#if (defined(__ARM_ARCH_7A__) && !defined(DHD_USE_COHERENT_MEM_FOR_RING))
kfree(va);
@@ -1172,7 +1442,8 @@
DMA_LOCK(osh);
- ASSERT((osh && (osh->magic == OS_HANDLE_MAGIC)));
+ ASSERT_NULL(osh);
+ ASSERT(osh->magic == OS_HANDLE_MAGIC);
/* For Rx buffers, keep direction as bidirectional to handle packet fetch cases */
dir = (direction == DMA_RX)? DMA_RXTX: direction;
@@ -1207,7 +1478,8 @@
dma_addr_t paddr;
#endif /* BCMDMA64OSL */
- ASSERT((osh && (osh->magic == OS_HANDLE_MAGIC)));
+ ASSERT_NULL(osh);
+ ASSERT(osh->magic == OS_HANDLE_MAGIC);
DMA_LOCK(osh);
@@ -1387,7 +1659,7 @@
ktime_get_real_ts64(&ts);
/* apply timezone */
- tzusec = (uint64)((ts.tv_sec - (sys_tz.tz_minuteswest * 60u)) * USEC_PER_SEC);
+ tzusec = (uint64)((ts.tv_sec - (sys_tz.tz_minuteswest * 60L)) * USEC_PER_SEC);
tzusec += ts.tv_nsec / NSEC_PER_USEC;
return tzusec;
@@ -1402,7 +1674,7 @@
memset_s(timebuf, RTC_TIME_BUF_LEN, 0, RTC_TIME_BUF_LEN);
ktime_get_real_ts64(&ts);
- rtc_time_to_tm(ts.tv_sec - (sys_tz.tz_minuteswest * 60), &tm);
+ rtc_time_to_tm(ts.tv_sec - (sys_tz.tz_minuteswest * 60L), &tm);
scnprintf(timebuf, RTC_TIME_BUF_LEN,
"%02d:%02d:%02d.%06lu",
tm.tm_hour, tm.tm_min, tm.tm_sec, ts.tv_nsec/NSEC_PER_USEC);
@@ -1905,7 +2177,7 @@
t->set = FALSE;
if (t->timer) {
del_timer(t->timer);
- MFREE(NULL, t->timer, sizeof(struct timer_list));
+ MFREE(NULL, t->timer, sizeof(timer_list_compat_t));
}
#ifdef BCMDBG
if (t->name) {
@@ -1941,6 +2213,7 @@
spin_lock_init(lock);
return ((void *)lock);
}
+
void
osl_spin_lock_deinit(osl_t *osh, void *lock)
{
diff --git a/linux_osl_priv.h b/linux_osl_priv.h
index eb4655e..db73a0d 100644
--- a/linux_osl_priv.h
+++ b/linux_osl_priv.h
@@ -1,7 +1,7 @@
/*
* Private header file for Linux OS Independent Layer
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/linux_pkt.c b/linux_pkt.c
index a123149..504823a 100644
--- a/linux_pkt.c
+++ b/linux_pkt.c
@@ -1,7 +1,7 @@
/*
* Linux Packet (skb) interface
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -134,11 +134,11 @@
if (bcm_static_buf) {
bcm_static_buf = 0;
}
-#ifdef BCMSDIO
+#if defined(BCMSDIO) || defined(DHD_USE_STATIC_CTRLBUF)
if (bcm_static_skb) {
bcm_static_skb = 0;
}
-#endif /* BCMSDIO */
+#endif /* BCMSDIO || DHD_USE_STATIC_CTRLBUF */
#endif /* CONFIG_DHD_USE_STATIC_BUF */
return 0;
}
diff --git a/pcie_core.c b/pcie_core.c
index 824174b..bc3e4be 100644
--- a/pcie_core.c
+++ b/pcie_core.c
@@ -3,7 +3,7 @@
* Contains PCIe related functions that are shared between different driver models (e.g. firmware
* builds, DHD builds, BMAC builds), in order to avoid code duplication.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/sbutils.c b/sbutils.c
index 6f6bd63..bb8b6a1 100644
--- a/sbutils.c
+++ b/sbutils.c
@@ -2,7 +2,7 @@
* Misc utility routines for accessing chip-specific features
* of the SiliconBackplane-based Broadcom chips.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/siutils.c b/siutils.c
index 85a4e40..db2df02 100644
--- a/siutils.c
+++ b/siutils.c
@@ -2,7 +2,7 @@
* Misc utility routines for accessing chip-specific features
* of the SiliconBackplane-based Broadcom chips.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/siutils_priv.h b/siutils_priv.h
index 2268af5..f57c41c 100644
--- a/siutils_priv.h
+++ b/siutils_priv.h
@@ -1,7 +1,7 @@
/*
* Include file private to the SOC Interconnect support files.
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/wb_regon_coordinator.c b/wb_regon_coordinator.c
index 17e39a1..571d972 100644
--- a/wb_regon_coordinator.c
+++ b/wb_regon_coordinator.c
@@ -1,7 +1,7 @@
/*
* DHD BT WiFi Coex RegON Coordinator
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -109,8 +109,8 @@
int wbrc_wl2bt_reset(void);
int wbrc_bt_reset_ack(struct wbrc_pvt_data *wbrc_data);
-int wbrc_bt2wl_reset(void);
-int wbrc_wl_reset_ack(struct wbrc_pvt_data *wbrc_data);
+static int wbrc_bt2wl_reset(void);
+static int wbrc_wl_reset_ack(struct wbrc_pvt_data *wbrc_data);
static int wbrc_bt_dev_open(struct inode *, struct file *);
static int wbrc_bt_dev_release(struct inode *, struct file *);
@@ -193,10 +193,11 @@
if (message[2] == TYPE_BT_CMD) {
switch (message[3]) {
case CMD_RESET_WIFI:
- pr_info("RCVD CMD_RESET_WIFI\n");
+ pr_info("RCVD TYPE_BT_CMD: CMD_RESET_WIFI\n");
break;
case CMD_RESET_WIFI_WITH_ACK:
- pr_info("RCVD CMD_RESET_WIFI_WITH_ACK\n");
+ pr_info("RCVD TYPE_BT_CMD: CMD_RESET_WIFI_WITH_ACK\n");
+ wbrc_bt2wl_reset();
break;
}
}
@@ -226,6 +227,7 @@
return mask;
}
+
int wbrc_reset_wait_on_condition(wait_queue_head_t *reset_waitq, uint *var, uint condition);
static int wbrc_bt_dev_open(struct inode *inodep, struct file *filep)
@@ -417,6 +419,7 @@
return 0;
}
+
/* WBRC_LOCK should be held from caller */
int wbrc_bt_reset_ack(struct wbrc_pvt_data *wbrc_data)
{
@@ -459,32 +462,53 @@
}
EXPORT_SYMBOL(wbrc_wl2bt_reset);
-int wbrc_signal_wlan_reset(struct wbrc_pvt_data *wbrc_data)
+#ifdef WBRC_BT2WL_RESET
+extern void dhd_wbrc_wl_trap(void);
+#endif /* WBRC_BT2WL_RESET */
+
+/* WBRC_LOCK should be held from caller */
+static int
+wbrc_signal_wlan_reset(struct wbrc_pvt_data *wbrc_data)
{
- /* TODO call dhd reset, right now just send ack from here */
+#ifdef WBRC_BT2WL_RESET
+ /* Force trap wl */
+ dhd_wbrc_wl_trap();
+#endif /* WBRC_BT2WL_RESET */
wbrc_wl_reset_ack(wbrc_data);
return 0;
}
-/* WBRC_LOCK should be held from caller, this will be called from DHD */
-int wbrc_wl_reset_ack(struct wbrc_pvt_data *wbrc_data)
+/* WBRC_LOCK should be held from caller */
+static int
+wbrc_wl_reset_ack(struct wbrc_pvt_data *wbrc_data)
{
pr_info("%s\n", __func__);
wbrc_data->wlan_reset_ack = TRUE;
+
+ /* Below message will be read by userspace using .read */
+ wbrc_data->wl2bt_message[0] = HEADER_DIR_WL2BT; // Minimal Header
+ wbrc_data->wl2bt_message[1] = 2; // Length
+ wbrc_data->wl2bt_message[2] = TYPE_WIFI_ACK; // Type
+ wbrc_data->wl2bt_message[3] = ACK_RESET_WIFI_COMPLETE; // Value
+ wbrc_data->read_data_available = TRUE;
+
+ smp_wmb();
+ wake_up_interruptible(&wbrc_data->outmsg_waitq);
+
smp_wmb();
wake_up(&wbrc_data->wlan_reset_waitq);
return 0;
}
-EXPORT_SYMBOL(wbrc_wl_reset_ack);
-int wbrc_bt2wl_reset(void)
+/* WBRC_LOCK should be held from caller */
+static int
+wbrc_bt2wl_reset(void)
{
int ret = 0;
struct wbrc_pvt_data *wbrc_data = g_wbrc_data;
pr_info("%s\n", __func__);
- WBRC_LOCK(wbrc_data);
wbrc_data->wlan_reset_ack = FALSE;
wbrc_signal_wlan_reset(wbrc_data);
/* Wait till WLAN reset is done */
@@ -494,7 +518,5 @@
pr_err("%s: WLAN reset timeout\n", __func__);
ret = -1;
}
- WBRC_UNLOCK(wbrc_data);
return ret;
}
-EXPORT_SYMBOL(wbrc_bt2wl_reset);
diff --git a/wifi_stats.h b/wifi_stats.h
index 458edee..8a3c71b 100644
--- a/wifi_stats.h
+++ b/wifi_stats.h
@@ -2,7 +2,7 @@
* Common stats definitions for clients of dongle
* ports
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -31,6 +31,10 @@
#include <ethernet.h>
#include <802.11.h>
+#ifdef CONFIG_COMPAT
+#include <linux/compat.h>
+#endif /* CONFIG_COMPAT */
+
typedef int32 wifi_radio;
typedef int32 wifi_channel;
typedef int32 wifi_rssi;
@@ -76,20 +80,18 @@
/* Filter channels that are unsafe due to cellular coexistence */
WIFI_USABLE_CHANNEL_FILTER_CELLULAR_COEXISTENCE = 1 << 0,
/* Filter channels due to concurrency state */
- WIFI_USABLE_CHANNEL_FILTER_CONCURRENCY = 1 << 1
+ WIFI_USABLE_CHANNEL_FILTER_CONCURRENCY = 1 << 1,
+ /* Filter the channels out for non nan and non instant mode usable */
+ /* This Filter queries Wifi channels and bands that are supported for
+ * NAN3.1 Instant communication mode. This filter should only be applied to NAN interface.
+ * If 5G is supported default discovery channel 149/44 is considered,
+ * If 5G is not supported then channel 6 has to be considered.
+ * Based on regulatory domain if channel 149 and 44 are restricted, channel 6 should
+ * be considered for instant communication channel
+ */
+ WIFI_USABLE_CHANNEL_FILTER_NAN_INSTANT_MODE = 1 << 2
} wifi_usable_channel_filter;
-typedef enum {
- /* WLAN MAC Operates in 2.4 GHz Band */
- WLAN_MAC_2_4_BAND = 1 << 0,
- /* WLAN MAC Operates in 5 GHz Band */
- WLAN_MAC_5_0_BAND = 1 << 1,
- /* WLAN MAC Operates in 6 GHz Band */
- WLAN_MAC_6_0_BAND = 1 << 2,
- /* WLAN MAC Operates in 60 GHz Band */
- WLAN_MAC_60_0_BAND = 1 << 3
-} wlan_mac_band;
-
#define WIFI_CAPABILITY_QOS 0x00000001 /* set for QOS association */
#define WIFI_CAPABILITY_PROTECTED 0x00000002 /* set for protected association (802.11
* beacon frame control protected bit set)
@@ -205,6 +207,28 @@
uint32 num_channels;
} wifi_radio_stat_h;
+typedef struct {
+ wifi_radio radio;
+ uint32 on_time;
+ uint32 tx_time;
+ uint32 num_tx_levels;
+ uint32 *tx_time_per_levels;
+ uint32 rx_time;
+ uint32 on_time_scan;
+ uint32 on_time_nbd;
+ uint32 on_time_gscan;
+ uint32 on_time_roam_scan;
+ uint32 on_time_pno_scan;
+ uint32 on_time_hs20;
+ uint32 num_channels;
+} wifi_radio_stat_h_v2;
+
+/* radio statistics */
+typedef struct {
+ wifi_radio_stat_h_v2 radio_stats;
+ wifi_channel_stat channels[]; // channel statistics
+} wifi_radio_stat;
+
/* per rate statistics */
typedef struct {
wifi_rate_v1 rate; /* rate information */
diff --git a/wl_android.c b/wl_android.c
index a4c2af6..3aa7844 100644
--- a/wl_android.c
+++ b/wl_android.c
@@ -1,7 +1,7 @@
/*
* Linux cfg80211 driver - Android related functions
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -21,6 +21,8 @@
* <<Broadcom-WL-IPTag/Dual:>>
*/
+#define CLEANED_UP_IOCTL 1
+
#include <linux/module.h>
#include <linux/netdevice.h>
#include <net/netlink.h>
@@ -49,6 +51,7 @@
#include <wl_cfg80211.h>
#include <wl_cfgscan.h>
#include <wl_cfgvif.h>
+#include <dhd_cfg80211.h>
#endif
#ifdef WL_NAN
#include <wl_cfgnan.h>
@@ -166,7 +169,7 @@
#define CMD_TEST_GET_TX_POWER "TEST_GET_TX_POWER"
#endif /* TEST_TX_POWER_CONTROL */
#define CMD_SARLIMIT_TX_CONTROL "SET_TX_POWER_CALLING"
-#define CMD_SARLIMIT_NR_SUB6_BANDINFO "SET_TX_POWER_NRSUB6_BAND"
+#define CMD_SARLIMIT_NR_SUB6_BANDINFO "SET_TX_POWER_SUB6_BAND"
#ifdef SUPPORT_SET_TID
#define CMD_SET_TID "SET_TID"
#define CMD_GET_TID "GET_TID"
@@ -187,6 +190,8 @@
#endif /* PNO_SUPPORT */
#define CMD_HAPD_SET_AX_MODE "HAPD_SET_AX_MODE"
+#define CMD_SET_HOTSPOT_ANTENNA_MODE "SET_HOTSPOT_ANTENNA_MODE"
+#define CMD_GET_HOTSPOT_ANTENNA_MODE "GET_HOTSPOT_ANTENNA_MODE"
#define CMD_HAPD_MAC_FILTER "HAPD_MAC_FILTER"
@@ -265,6 +270,8 @@
#define CMD_SETWESMODE "SETWESMODE"
#define CMD_GETNCHOMODE "GETNCHOMODE"
#define CMD_SETNCHOMODE "SETNCHOMODE"
+#define CMD_GETROAMALLOWBAND "GETROAMBAND"
+#define CMD_SETROAMALLOWBAND "SETROAMBAND"
/* Customer requested to Remove OKCMODE command */
#define CMD_GETOKCMODE "GETOKCMODE"
@@ -465,10 +472,6 @@
#define CMD_DEL_WFDS_HASH "DEL_WFDS_HASH"
#endif /* WLWFDS */
-#ifdef BT_WIFI_HANDOVER
-#define CMD_TBOW_TEARDOWN "TBOW_TEARDOWN"
-#endif /* BT_WIFI_HANDOVER */
-
#define CMD_MURX_BFE_CAP "MURX_BFE_CAP"
#ifdef SUPPORT_RSSI_SUM_REPORT
@@ -572,12 +575,6 @@
#define MAX_NUM_SUITES 10
#define WIDTH_AKM_SUITE 8
#define JOIN_PREF_RSSI_LEN 0x02
-#define JOIN_PREF_RSSI_SIZE 4 /* RSSI pref header size in bytes */
-#define JOIN_PREF_WPA_HDR_SIZE 4 /* WPA pref header size in bytes */
-#define JOIN_PREF_WPA_TUPLE_SIZE 12 /* Tuple size in bytes */
-#define JOIN_PREF_MAX_WPA_TUPLES 16
-#define MAX_BUF_SIZE (JOIN_PREF_RSSI_SIZE + JOIN_PREF_WPA_HDR_SIZE + \
- (JOIN_PREF_WPA_TUPLE_SIZE * JOIN_PREF_MAX_WPA_TUPLES))
#endif /* BCMFW_ROAM_ENABLE */
#if defined(CONFIG_TIZEN)
@@ -941,6 +938,7 @@
CMD_GETDFSSCANMODE,
CMD_SETJOINPREFER,
CMD_GETWESMODE, CMD_SETWESMODE,
+ CMD_GETROAMALLOWBAND, CMD_SETROAMALLOWBAND,
"\0"
};
#endif /* WES_SUPPORT */
@@ -989,7 +987,7 @@
} android_restore_scan_params_t;
/* function prototypes of private command handler */
-static int wl_android_default_set_scan_params(struct net_device *dev, char *command, int total_len);
+int wl_android_default_set_scan_params(struct net_device *dev, char *command, int total_len);
static int wl_android_set_roam_trigger(struct net_device *dev, char* command);
int wl_android_set_roam_delta(struct net_device *dev, char* command);
int wl_android_set_roam_scan_period(struct net_device *dev, char* command);
@@ -1002,6 +1000,8 @@
static int wl_android_set_band(struct net_device *dev, char *command);
int wl_android_set_wes_mode(struct net_device *dev, char *command);
int wl_android_set_okc_mode(struct net_device *dev, char *command);
+int wl_android_set_scan_passive_time(struct net_device *dev, char *command);
+int wl_android_set_roam_allowed_band(struct net_device *dev, char *command);
/* default values */
#ifdef ROAM_API
@@ -1018,11 +1018,10 @@
#else
#define DEFAULT_SCANHOMETIME 45
#endif /* BCM4361_CHIP */
-#define DEFAULT_SCANHOMEAWAYTIME 100
-#define DEFAULT_SCANPROBES 2
-#define DEFAULT_DFSSCANMODE 1
-#define DEFAULT_WESMODE 0
-#define DEFAULT_OKCMODE 1
+#define DEFAULT_SCANPROBES 2
+#define DEFAULT_DFSSCANMODE 1
+#define DEFAULT_WESMODE 0
+#define DEFAULT_OKCMODE 1
#endif /* WES_SUPPORT */
#define DEFAULT_BAND 0
#ifdef WBTEXT
@@ -1054,12 +1053,16 @@
RESTORE_TYPE_PRIV_CMD, .cmd_handler = wl_android_set_scan_channel_time},
{ CMD_SETSCANHOMETIME, DEFAULT_SCANHOMETIME,
RESTORE_TYPE_PRIV_CMD, .cmd_handler = wl_android_set_scan_home_time},
- { CMD_GETSCANHOMEAWAYTIME, DEFAULT_SCANHOMEAWAYTIME,
+ { CMD_GETSCANHOMEAWAYTIME, DHD_SCAN_HOME_AWAY_TIME,
RESTORE_TYPE_PRIV_CMD, .cmd_handler = wl_android_set_scan_home_away_time},
{ CMD_SETSCANNPROBES, DEFAULT_SCANPROBES,
RESTORE_TYPE_PRIV_CMD, .cmd_handler = wl_android_set_scan_nprobes},
{ CMD_SETWESMODE, DEFAULT_WESMODE,
RESTORE_TYPE_PRIV_CMD, .cmd_handler = wl_android_set_wes_mode},
+ { CMD_SETSCANPASSIVETIME, DHD_SCAN_PASSIVE_TIME,
+ RESTORE_TYPE_PRIV_CMD, .cmd_handler = wl_android_set_scan_passive_time},
+ { CMD_SETROAMALLOWBAND, WLC_ROAM_ALLOW_BAND_AUTO,
+ RESTORE_TYPE_PRIV_CMD, .cmd_handler = wl_android_set_roam_allowed_band},
#endif /* WES_SUPPORT */
{ CMD_SETBAND, DEFAULT_BAND,
RESTORE_TYPE_PRIV_CMD, .cmd_handler = wl_android_set_band},
@@ -1074,6 +1077,7 @@
#ifdef SUPPORT_LATENCY_CRITICAL_DATA
#define CMD_GET_LATENCY_CRITICAL_DATA "GET_LATENCY_CRT_DATA"
#define CMD_SET_LATENCY_CRITICAL_DATA "SET_LATENCY_CRT_DATA"
+int wl_android_set_latency_crt_data(struct net_device *dev, int mode);
#endif /* SUPPORT_LATENCY_CRITICAL_DATA */
#ifdef WL_LATENCY_CONFIG
@@ -1115,6 +1119,15 @@
#define CMD_SET_PRIMARY_INET "SET_PRIMARY_INET"
#endif /* WL_DUAL_STA */
+#define CMD_SETWSECINFO "SETWSECINFO"
+
+#if defined(LIMIT_AP_BW)
+#define CMD_SET_SOFTAP_BW "CMD_SET_SOFTAP_BW"
+#define CMD_GET_SOFTAP_BW "CMD_GET_SOFTAP_BW"
+static int wl_android_set_softap_bw(struct net_device *ndev, char *command);
+static int wl_android_get_softap_bw(struct net_device *ndev, char *command, int total_len);
+#endif /* LIMIT_AP_BW */
+
/**
* Local (static) functions and variables
*/
@@ -1339,19 +1352,26 @@
{
int ret = 0;
-#if (!defined(CONFIG_HAS_EARLYSUSPEND) || !defined(DHD_USE_EARLYSUSPEND)) && \
- !defined(DHD_USE_PM_SLEEP)
+#if (!defined(CONFIG_HAS_EARLYSUSPEND) || !defined(DHD_USE_EARLYSUSPEND)) || \
+ defined(DHD_USE_PM_SLEEP)
int suspend_flag;
suspend_flag = *(command + strlen(CMD_SETSUSPENDMODE) + 1) - '0';
- if (suspend_flag != 0)
+ if (suspend_flag != 0) {
suspend_flag = 1;
+#if defined(DHD_USE_PM_SLEEP)
+ /* The suspend setting is handled in linux pm_nofi callback. */
+ DHD_INFO(("wl_android_set_suspendmode: Suspend Mode %d doesn't set\n",
+ suspend_flag));
+ return ret;
+#endif /* DHD_USE_PM_SLEEP */
+ }
if (!(ret = net_os_set_suspend(dev, suspend_flag, 0)))
DHD_INFO(("wl_android_set_suspendmode: Suspend Mode %d\n", suspend_flag));
else
DHD_ERROR(("wl_android_set_suspendmode: failed %d\n", ret));
-#endif /* (!CONFIG_HAS_EARLYSUSPEND || !DHD_USE_EARLYSUSPEND) && !DHD_USE_PM_SLEEP */
+#endif /* (!CONFIG_HAS_EARLYSUSPEND || !DHD_USE_EARLYSUSPEND) || DHD_USE_PM_SLEEP */
return ret;
}
@@ -1461,6 +1481,7 @@
bytes_written = snprintf(command, total_len, "%s %d", CMD_DATARATE, (datarate/2));
return bytes_written;
}
+
int wl_android_get_assoclist(struct net_device *dev, char *command, int total_len)
{
int error = 0;
@@ -1501,6 +1522,7 @@
}
return bytes_written;
}
+
extern chanspec_t
wl_chspec_host_to_driver(chanspec_t chanspec);
static int wl_android_set_csa(struct net_device *dev, char *command)
@@ -2800,8 +2822,8 @@
{
int error = -1;
android_wifi_af_params_t *params = NULL;
- wl_action_frame_t *action_frame = NULL;
- wl_af_params_t *af_params = NULL;
+ wl_action_frame_v1_t *action_frame = NULL;
+ wl_af_params_v1_t *af_params = NULL;
char *smbuf = NULL;
struct ether_addr tmp_bssid;
int tmp_channel = 0;
@@ -2829,7 +2851,7 @@
goto send_action_frame_out;
}
- af_params = (wl_af_params_t *)MALLOCZ(cfg->osh, WL_WIFI_AF_PARAMS_SIZE);
+ af_params = (wl_af_params_v1_t *)MALLOCZ(cfg->osh, WL_WIFI_AF_PARAMS_SIZE_V1);
if (af_params == NULL) {
DHD_ERROR(("wl_android_send_action_frame: unable to allocate frame\n"));
goto send_action_frame_out;
@@ -2875,7 +2897,7 @@
memcpy(action_frame->data, params->data, action_frame->len);
error = wldev_iovar_setbuf(dev, "actframe", af_params,
- sizeof(wl_af_params_t), smbuf, WLC_IOCTL_MAXLEN, NULL);
+ sizeof(wl_af_params_v1_t), smbuf, WLC_IOCTL_MAXLEN, NULL);
if (error) {
DHD_ERROR(("wl_android_send_action_frame: failed to set action frame,"
" error=%d\n", error));
@@ -2883,7 +2905,7 @@
send_action_frame_out:
if (af_params) {
- MFREE(cfg->osh, af_params, WL_WIFI_AF_PARAMS_SIZE);
+ MFREE(cfg->osh, af_params, WL_WIFI_AF_PARAMS_SIZE_V1);
}
if (smbuf) {
@@ -3082,6 +3104,59 @@
return error;
}
+int
+wl_android_get_roam_allowed_band(struct net_device *dev, char *command, int total_len)
+{
+ int error = BCME_OK;
+ int bytes_written = 0;
+ uint32 band = WLC_ROAM_ALLOW_BAND_AUTO;
+ struct bcm_cfg80211 *cfg = wl_get_cfg(dev);
+
+ error = wl_cfg80211_get_roam_params(dev, &band, sizeof(band), WL_ROAM_PARAMS_ALLOWED_BAND);
+ if (error) {
+ WL_ERR(("Failed to get ROAM allowed Band %d, error = %d\n", band, error));
+ return error;
+ }
+
+ if (cfg->roam_allowed_band != band) {
+ WL_ERR(("Mis-match ROAM allowed Band %d != %d\n", cfg->roam_allowed_band, band));
+ cfg->roam_allowed_band = band;
+ }
+ bytes_written = snprintf(command, total_len, "%s %d", CMD_GETROAMALLOWBAND, band);
+
+ return bytes_written;
+}
+
+int
+wl_android_set_roam_allowed_band(struct net_device *dev, char *command)
+{
+ int error = BCME_OK;
+ uint32 band = WLC_ROAM_ALLOW_BAND_AUTO;
+ struct bcm_cfg80211 *cfg = wl_get_cfg(dev);
+
+ if (sscanf(command, "%*s %d", &band) != 1) {
+ WL_ERR(("Failed to get ROAM allowed Band Parameter\n"));
+ error = BCME_ERROR;
+ goto exit;
+ }
+
+ if (band > WLC_ROAM_ALLOW_BAND_MAX) {
+ WL_ERR(("Invalied ROAM allowed Band %d\n", band));
+ error = BCME_BADARG;
+ goto exit;
+ }
+
+ error = wl_cfg80211_set_roam_params(dev, &band, sizeof(band), WL_ROAM_PARAMS_ALLOWED_BAND);
+ if (error) {
+ WL_ERR(("Failed to set ROAM allowed Band %d, error = %d\n", band, error));
+ goto exit;
+ }
+ cfg->roam_allowed_band = band;
+
+exit:
+ return error;
+}
+
static int
wl_android_set_pmk(struct net_device *dev, char *command, int total_len)
{
@@ -3309,8 +3384,8 @@
bytes_written = wl_android_set_scan_home_away_time(net, command);
}
else {
- WL_ERR(("Unknown NCHO PRIVATE command %s - ignored\n", command));
- bytes_written = scnprintf(command, sizeof("FAIL"), "FAIL");
+ WL_ERR(("Unknown Legacy PRIVATE command %s - ignored\n", command));
+ bytes_written = BCME_UNSUPPORTED;
}
return bytes_written;
@@ -3460,9 +3535,15 @@
else if (strnicmp(command, CMD_SETWESMODE, strlen(CMD_SETWESMODE)) == 0) {
bytes_written = wl_android_set_wes_mode(net, command);
}
+ else if (strnicmp(command, CMD_GETROAMALLOWBAND, strlen(CMD_GETROAMALLOWBAND)) == 0) {
+ bytes_written = wl_android_get_roam_allowed_band(net, command, total_len);
+ }
+ else if (strnicmp(command, CMD_SETROAMALLOWBAND, strlen(CMD_SETROAMALLOWBAND)) == 0) {
+ bytes_written = wl_android_set_roam_allowed_band(net, command);
+ }
else {
WL_ERR(("Unknown NCHO PRIVATE command %s - ignored\n", command));
- bytes_written = scnprintf(command, sizeof("FAIL"), "FAIL");
+ bytes_written = BCME_UNSUPPORTED;
}
return bytes_written;
@@ -3470,7 +3551,7 @@
#endif /* WES_SUPPORT */
#if defined(SUPPORT_RESTORE_SCAN_PARAMS) || defined(WES_SUPPORT)
-static int
+int
wl_android_default_set_scan_params(struct net_device *dev, char *command, int total_len)
{
int error = 0;
@@ -3651,7 +3732,7 @@
goto done;
}
- psroam->ver = WLC_SILENT_ROAM_CUR_VER;
+ psroam->ver = WLC_SILENT_ROAM_VER_1;
psroam->len = sizeof(*sroam);
sroam = (wlc_sroam_info_t *)psroam->data;
@@ -3729,10 +3810,10 @@
goto done;
}
- if (psroam->ver != WLC_SILENT_ROAM_CUR_VER) {
+ if (psroam->ver != WLC_SILENT_ROAM_VER_1) {
ret = BCME_VERSION;
WL_ERR(("Ver(%d:%d). mismatch silent roam info(%d)\n",
- psroam->ver, WLC_SILENT_ROAM_CUR_VER, ret));
+ psroam->ver, WLC_SILENT_ROAM_VER_1, ret));
goto done;
}
@@ -3844,6 +3925,7 @@
uint32 delta2g = 0, delta5g = 0, delta = 0;
dhd_pub_t *dhdp = wl_cfg80211_get_dhdp(dev);
+ /* Requirement Range is 0 ~ 100. IOVAR Range is 0 ~ 10000 */
argc = sscanf(command, CMD_ROAM_MIN_DELTA " %d\n", &delta);
if (!argc) {
@@ -3853,13 +3935,14 @@
WL_ERR(("Failed to Get roam_min_delta (%d)\n", ret));
return ret;
}
- bytes_written = snprintf(command, total_len, "%d, %d\n", delta2g, delta5g);
+ bytes_written = snprintf(command, total_len, "%d/%d\n",
+ (delta2g/100), (delta5g/100));
return bytes_written;
} else {
/* Set Minimum ROAM score delta
* Framework set one parameter # wpa_cli driver ROAMMINSCOREDELTA <value>
*/
- ret = dhd_roam_min_delta_set(dhdp, delta, delta);
+ ret = dhd_roam_min_delta_set(dhdp, (delta*100), (delta*100));
if (ret) {
WL_ERR(("Failed to Set roam_min_delta (%d)\n", ret));
return ret;
@@ -4395,16 +4478,16 @@
goto done;
}
- if (prcroam->ver != WLC_RC_ROAM_CUR_VER) {
+ if (prcroam->ver != WLC_RC_ROAM_VER_1) {
ret = BCME_VERSION;
WL_ERR(("Ver(%d:%d). mismatch RCROAM info(%d)\n",
- prcroam->ver, WLC_RC_ROAM_CUR_VER, ret));
+ prcroam->ver, WLC_RC_ROAM_VER_1, ret));
goto done;
}
/* Set RCROAM param */
rcroam = (wlc_rcroam_info_v1_t *)prcroam->data;
- prcroam->ver = WLC_RC_ROAM_CUR_VER;
+ prcroam->ver = WLC_RC_ROAM_VER_1;
prcroam->len = sizeof(*rcroam);
rcroam->enab = rcroam_enab;
@@ -4713,10 +4796,11 @@
exit:
return err;
}
+
#ifndef WL_SCHED_SCAN
static int wl_android_set_pno_setup(struct net_device *dev, char *command, int total_len)
{
- wlc_ssid_ext_t ssids_local[MAX_PFN_LIST_COUNT];
+ wlc_ssid_ext_t *ssids_local = NULL;
int res = -1;
int nssid = 0;
cmd_tlv_t *cmd_tlv_temp;
@@ -4725,6 +4809,7 @@
int pno_time = 0;
int pno_repeat = 0;
int pno_freq_expo_max = 0;
+ struct bcm_cfg80211 *cfg = wl_get_cfg(dev);
#ifdef PNO_SET_DEBUG
int i;
@@ -4760,7 +4845,12 @@
tlv_size_left = total_len - strlen(CMD_PNOSETUP_SET);
cmd_tlv_temp = (cmd_tlv_t *)str_ptr;
- bzero(ssids_local, sizeof(ssids_local));
+ ssids_local = (wlc_ssid_ext_t *)MALLOCZ(cfg->osh,
+ sizeof(wlc_ssid_ext_t) * MAX_PFN_LIST_COUNT);
+ if (!ssids_local) {
+ DHD_ERROR(("wl_android_set_pno_setup: No memory\n"));
+ return -ENOMEM;
+ }
if ((cmd_tlv_temp->prefix == PNO_TLV_PREFIX) &&
(cmd_tlv_temp->version == PNO_TLV_VERSION) &&
@@ -4813,6 +4903,10 @@
res = dhd_dev_pno_set_for_ssid(dev, ssids_local, nssid, pno_time, pno_repeat,
pno_freq_expo_max, NULL, 0);
exit_proc:
+ if (ssids_local) {
+ MFREE(cfg->osh, ssids_local,
+ sizeof(wlc_ssid_ext_t) * MAX_PFN_LIST_COUNT);
+ }
return res;
}
#endif /* !WL_SCHED_SCAN */
@@ -6087,7 +6181,7 @@
uint16 buflen = 0, buflen_start = 0;
memset_s(iov_buf, iov_buf_len, 0, iov_buf_len);
- iov_buf->version = WL_MBO_IOV_VERSION;
+ iov_buf->version = WL_MBO_IOV_VERSION_1_1;
iov_buf->id = WL_MBO_CMD_SEND_NOTIF;
buflen = buflen_start = iov_buf_len - sizeof(bcm_iov_buf_t);
pxtlv = (uint8 *)&iov_buf->data[0];
@@ -6163,7 +6257,7 @@
}
/* fill header */
- iov_buf->version = WL_MBO_IOV_VERSION;
+ iov_buf->version = WL_MBO_IOV_VERSION_1_1;
iov_buf->id = WL_MBO_CMD_CELLULAR_DATA_CAP;
ret = wldev_iovar_getbuf(dev, "mbo", iov_buf, WLC_IOCTL_MEDLEN, iov_resp,
@@ -6178,7 +6272,7 @@
if (*pcmd == WL_IOCTL_ACTION_GET) {
/* Check for version */
version = dtoh16(*(uint16 *)iov_resp);
- if (version != WL_MBO_IOV_VERSION) {
+ if (version != WL_MBO_IOV_VERSION_1_1) {
ret = -EINVAL;
}
if (p_resp->id == WL_MBO_CMD_CELLULAR_DATA_CAP) {
@@ -6339,7 +6433,7 @@
/* get */
if (*pcmd == WL_IOCTL_ACTION_GET) {
/* fill header */
- iov_buf->version = WL_MBO_IOV_VERSION;
+ iov_buf->version = WL_MBO_IOV_VERSION_1_1;
iov_buf->id = WL_MBO_CMD_LIST_CHAN_PREF;
ret = wldev_iovar_getbuf(dev, "mbo", iov_buf, WLC_IOCTL_MEDLEN, iov_resp,
@@ -6350,9 +6444,9 @@
p_resp = (bcm_iov_buf_t *)iov_resp;
/* Check for version */
version = dtoh16(*(uint16 *)iov_resp);
- if (version != WL_MBO_IOV_VERSION) {
+ if (version != WL_MBO_IOV_VERSION_1_1) {
WL_ERR(("Version mismatch. returned ver %u expected %u\n",
- version, WL_MBO_IOV_VERSION));
+ version, WL_MBO_IOV_VERSION_1_1));
ret = -EINVAL;
}
if (p_resp->id == WL_MBO_CMD_LIST_CHAN_PREF) {
@@ -6374,7 +6468,7 @@
str = bcmstrtok(&pcmd, " ", NULL);
if (!(strnicmp(str, "set", 3)) || (!strnicmp(str, "clear", 5))) {
/* delete all configurations */
- iov_buf->version = WL_MBO_IOV_VERSION;
+ iov_buf->version = WL_MBO_IOV_VERSION_1_1;
iov_buf->id = WL_MBO_CMD_DEL_CHAN_PREF;
iov_buf->len = 0;
iovlen = sizeof(bcm_iov_buf_t) + iov_buf->len;
@@ -6431,7 +6525,7 @@
}
WL_ERR(("len %u\n", (buflen_start - buflen)));
/* Now set the new non pref channels */
- iov_buf->version = WL_MBO_IOV_VERSION;
+ iov_buf->version = WL_MBO_IOV_VERSION_1_1;
iov_buf->id = WL_MBO_CMD_ADD_CHAN_PREF;
iov_buf->len = buflen_start - buflen;
iovlen = sizeof(bcm_iov_buf_t) + iov_buf->len;
@@ -6500,12 +6594,12 @@
#endif /* SUPPORT_AMPDU_MPDU_CMD */
#endif /* CUSTOMER_HW4_PRIVATE_CMD */
-#if defined(CONFIG_WLAN_BEYONDX) || defined(CONFIG_SEC_5GMODEL)
+#ifdef WL_CP_COEX
extern int wl_cfg80211_send_msg_to_ril(void);
extern void wl_cfg80211_register_dev_ril_bridge_event_notifier(void);
extern void wl_cfg80211_unregister_dev_ril_bridge_event_notifier(void);
-extern int g_mhs_chan_for_cpcoex;
-#endif /* CONFIG_WLAN_BEYONDX || defined(CONFIG_SEC_5GMODEL) */
+extern struct wl_cp_coex g_cx;
+#endif /* WL_CP_COEX */
#if defined(WL_SUPPORT_AUTO_CHANNEL)
static s32
@@ -6564,9 +6658,24 @@
break;
freq = bcm_atoi(token);
+ chanspec = wl_freq_to_chanspec(freq);
/* Convert chanspec from frequency */
- if ((freq > 0) &&
- ((chanspec = wl_freq_to_chanspec(freq)) != INVCHANSPEC)) {
+ if ((freq > 0) && (chanspec != INVCHANSPEC)) {
+#ifdef WL_UNII4_CHAN
+ /* Skip UNII-4 frequencies */
+ if (CHSPEC_IS5G(chanspec) &&
+ IS_UNII4_CHANNEL(wf_chspec_primary20_chan(chanspec))) {
+ WL_DBG(("Skipped UNII-4 chanspec 0x%x\n", chanspec));
+ continue;
+ }
+#endif /* WL_UNII4_CHAN */
+#ifdef WL_5G_SOFTAP_ONLY_ON_DEF_CHAN
+ if (CHSPEC_IS5G(chanspec) &&
+ !(IS_5G_APCS_CHANNEL(wf_chspec_primary20_chan(chanspec)))) {
+ WL_DBG(("Skipped unsupported 5G chanspec 0x%x\n", chanspec));
+ continue;
+ }
+#endif /* WL_5G_SOFTAP_ONLY_ON_DEF_CHAN */
WL_DBG(("%s:Adding chanspec in list : 0x%x at the index %d\n",
__FUNCTION__, chanspec, i));
/* mark all the bands found */
@@ -6574,24 +6683,9 @@
list->element[i] = chanspec;
len -= sizeof(list->element[i]);
i++;
-#ifdef WL_5G_SOFTAP_ONLY_ON_DEF_CHAN
- /* Android includes 2g channels even for 5g band configuration. For
- * customers using only single channel 5G AP, set the channel and
- * return without doing ACS
- */
- if (CHSPEC_BAND(chanspec) == WL_CHANSPEC_BAND_5G) {
- WL_INFORM_MEM(("Pick default channnel from 5g\n"));
- if (!sta_channel) {
- list->element[0] = chanspec;
- list->count = 1;
- return ret;
- }
- break;
- } else {
- WL_DBG(("chspec[%d]: 0x%x (band=0x%x)\n",
- i, chanspec, CHSPEC_BAND(chanspec)));
- }
-#endif /* WL_5G_SOFTAP_ONLY_ON_DEF_CHAN */
+
+ WL_DBG(("chspec[%d]: 0x%x (band=0x%x)\n",
+ i, chanspec, CHSPEC_BAND(chanspec)));
}
WL_DBG(("** freq_bands=0x%x\n", freq_bands));
}
@@ -6603,6 +6697,7 @@
* Frequency list is order of lower to higher band.
* check with the highest band entry.
*/
+ list->count = 1;
chanspec = list->element[i-1];
if (sta_acs_band == WL_CHANSPEC_BAND_2G) {
#ifdef WL_6G_BAND
@@ -6621,9 +6716,9 @@
}
} else if (sta_acs_band == WL_CHANSPEC_BAND_5G) {
if (freq_bands & WLC_BAND_5G) {
- if (sta_channel == APCS_DEFAULT_5G_CH) {
- list->element[0] =
- wl_freq_to_chanspec(APCS_DEFAULT_5G_FREQ);
+ if (IS_5G_APCS_CHANNEL(sta_channel)) {
+ freq = wl_channel_to_frequency(sta_channel, sta_acs_band);
+ list->element[0] = wl_freq_to_chanspec(freq);
} else {
list->element[0] =
wl_freq_to_chanspec(APCS_DEFAULT_2G_FREQ);
@@ -6648,10 +6743,14 @@
#endif /* WL_6G_BAND */
{
WL_ERR(("ACS: Invalid sta acs band: sta_acs_band = 0x%x\n", sta_acs_band));
+ list->count = 0;
return BCME_ERROR;
}
}
- list->count = 1;
+
+ if (!list->count)
+ return BCME_ERROR;
+
return ret;
}
@@ -6698,13 +6797,22 @@
if (CHSPEC_IS5G(chanspec) && (CHANNEL_IS_RADAR(channel) ||
#ifndef ALLOW_5G_ACS
- ((acs_req == true) && (CHSPEC_CHANNEL(chanspec) != APCS_DEFAULT_5G_CH)) ||
+ ((acs_req == true) &&
+ !(IS_5G_APCS_CHANNEL(wf_chspec_primary20_chan(chanspec)))) ||
#endif /* !ALLOW_5G_ACS */
(0))) {
continue;
} else if (!(CHSPEC_IS2G(chanspec) || CHSPEC_IS5G(chanspec)) &&
!(CHSPEC_IS_6G_PSC(chanspec))) {
continue;
+#ifdef WL_UNII4_CHAN
+ } else if (CHSPEC_IS5G(chanspec) &&
+ IS_UNII4_CHANNEL(wf_chspec_primary20_chan(chanspec))) {
+ /* Skip UNII-4 channels */
+ WL_INFORM_MEM(("Skip UNII-4 chanspec from list : %x\n",
+ chanspec));
+ continue;
+#endif /* WL_UNII4_CHAN */
}
else {
list->element[j] = list->element[i];
@@ -6995,6 +7103,7 @@
bool acs_freq_list_present = false;
char *pcmd;
int freq = 0;
+ wl_ap_oper_data_t ap_oper_data = {0};
if (cmd_str) {
WL_INFORM(("Command: %s len:%d \n", cmd_str, (int)strlen(cmd_str)));
@@ -7033,35 +7142,66 @@
}
WL_INFORM(("HAPD_AUTO_CHANNEL = %d, band=%d \n", channel, band));
-#if defined(CONFIG_WLAN_BEYONDX) || defined(CONFIG_SEC_5GMODEL)
- wl_cfg80211_register_dev_ril_bridge_event_notifier();
+#ifdef WL_CP_COEX
if (band == WLC_BAND_2G) {
+ (void)memset_s(&g_cx, sizeof(g_cx), 0, sizeof(g_cx));
+ wl_cfg80211_register_dev_ril_bridge_event_notifier();
+ /* wait 500ms for receiving packet from CP */
wl_cfg80211_send_msg_to_ril();
+ wl_cfg80211_unregister_dev_ril_bridge_event_notifier();
- if (g_mhs_chan_for_cpcoex) {
- channel = g_mhs_chan_for_cpcoex;
- g_mhs_chan_for_cpcoex = 0;
+ WL_ERR(("[CP_COEX] - Channel:%u\n", g_cx.ch_cpcoex));
+ if (g_cx.ch_cpcoex) {
+ channel = g_cx.ch_cpcoex;
+ acs_band = WL_CHANSPEC_BAND_2G;
goto done2;
}
}
- wl_cfg80211_unregister_dev_ril_bridge_event_notifier();
-#endif /* CONFIG_WLAN_BEYONDX || defined(CONFIG_SEC_5GMODEL) */
+#endif /* WL_CP_COEX */
+
+ /* Check whether AP is already operational */
+ wl_get_ap_chanspecs(cfg, &ap_oper_data);
+ if (ap_oper_data.count >= MAX_AP_IFACES) {
+ WL_ERR(("ACS request in multi AP case!! count:%d\n",
+ ap_oper_data.count));
+ return -EINVAL;
+ }
+
+ if (ap_oper_data.count == 1) {
+ chanspec_t ch = ap_oper_data.iface[0].chspec;
+ u16 ap_band;
+
+ /* Single AP case. Bring up the AP in the other band */
+ ap_band = CHSPEC_TO_WLC_BAND(ch);
+ WL_INFORM_MEM(("AP operational in band:%d and incoming band:%d\n",
+ ap_band, band));
+ /* if incoming and operational AP band is same, it is invalid case */
+ if (ap_band == band) {
+ WL_ERR(("DUAL AP not allowed on same band\n"));
+ goto done2;
+ }
+ }
/* If STA is connected, return is STA chanspec, else ACS can be issued,
* set spect to 0 and proceed with ACS
*/
sta_chanspec = wl_cfg80211_get_sta_chanspec(cfg);
if (sta_chanspec) {
- sta_channel = wf_chspec_ctlchan((chanspec_t)sta_chanspec);
- sta_band = CHSPEC_BAND((chanspec_t)sta_chanspec);
- WL_DBG(("sta_chanspec= 0x%x, sta_channel = %d, sta_band = 0x%x, sap band = %d\n",
- sta_chanspec, sta_channel, sta_band, band));
+ if (wf_chspec_valid(sta_chanspec)) {
+ sta_channel = wf_chspec_ctlchan((chanspec_t)sta_chanspec);
+ sta_band = CHSPEC_BAND((chanspec_t)sta_chanspec);
+ WL_DBG(("sta_chanspec = 0x%x, sta_channel = %d, sta_band = 0x%x, "
+ "sap band = %d\n", sta_chanspec, sta_channel, sta_band, band));
+ } else {
+ WL_ERR(("Invalid sta chanspec 0x%x\n", sta_chanspec));
+ return -EINVAL;
+ }
}
if ((sta_band != WLC_ACS_BAND_INVALID) && sta_chanspec && (band != WLC_BAND_INVALID)) {
switch (sta_band) {
case (WL_CHANSPEC_BAND_5G): {
- if ((sta_channel == APCS_DEFAULT_5G_CH) &&
+ if ((IS_5G_APCS_CHANNEL(sta_channel)) &&
(band == WLC_BAND_5G || band == WLC_BAND_AUTO)) {
/* SCC is allowed only for DEF_5G Channel */
channel = sta_channel;
@@ -7223,16 +7363,21 @@
chosen = dtoh32(chosen);
}
- if (chosen) {
+ if (wf_chspec_valid((chanspec_t)chosen)) {
#ifdef WL_6G_BAND
if (CHSPEC_BAND((chanspec_t)chosen) == WL_CHANSPEC_BAND_6G &&
cfg->band_6g_supported) {
/* Cache the chanspec for 6g, as fw will choose the BW */
- cfg->acs_chspec = chosen;
+#if defined(LIMIT_AP_BW)
+ chosen = (int) wl_cfg80211_get_ap_bw_limited_chspec(cfg,
+ WL_CHANSPEC_BAND_6G, (chanspec_t) chosen);
+
+#endif /* LIMIT_AP_BW */
+ cfg->acs_chspec = (chanspec_t)chosen;
}
#endif /* WL_6G_BAND */
- channel = wf_chspec_ctlchan(chosen);
- acs_band = CHSPEC_BAND(chosen);
+ channel = wf_chspec_ctlchan((chanspec_t)chosen);
+ acs_band = CHSPEC_BAND((chanspec_t)chosen);
break;
}
WL_DBG(("%d tried, ret = %d, chosen = 0x%x, acs_band = 0x%x\n",
@@ -7713,6 +7858,7 @@
return error;
}
+
#ifdef TEST_TX_POWER_CONTROL
static int
wl_android_set_tx_power(struct net_device *dev, const char* string_num)
@@ -7771,12 +7917,39 @@
{
int err = BCME_ERROR;
int setval = 0;
- s32 mode = bcm_atoi(string_num);
- s32 mode_bit = 0;
- int enab = 0;
+ int idx, n_ctls;
+ s32 sar_event = bcm_atoi(string_num);
+ wl_sar_ctl_tbl_t sar_tbl[] = {
+ {HEAD_SAR_BACKOFF_DISABLE, 1,
+ {{FALSE, SAR_MODE_BIT_HEAD}, }},
+ {HEAD_SAR_BACKOFF_ENABLE, 1,
+ {{TRUE, SAR_MODE_BIT_HEAD}, }},
+ {GRIP_SAR_BACKOFF_DISABLE, 1,
+ {{FALSE, SAR_MODE_BIT_GRIP}, }},
+ {GRIP_SAR_BACKOFF_ENABLE, 1,
+ {{TRUE, SAR_MODE_BIT_GRIP}, }},
+ {NR_mmWave_SAR_BACKOFF_DISABLE, 1,
+ {{FALSE, SAR_MODE_BIT_NR_MW}, }},
+ {NR_mmWave_SAR_BACKOFF_ENABLE, 2,
+ {{FALSE, SAR_MODE_BIT_NR_S6}, {TRUE, SAR_MODE_BIT_NR_MW}}},
+ {NR_Sub6_SAR_BACKOFF_DISABLE, 1,
+ {{FALSE, SAR_MODE_BIT_NR_S6}, }},
+ {NR_Sub6_SAR_BACKOFF_ENABLE, 2,
+ {{FALSE, SAR_MODE_BIT_NR_MW}, {TRUE, SAR_MODE_BIT_NR_S6}}},
+ {NR_MMWAVE_NR_SUB6_SAR_BACKOFF_DISABLE, 1,
+ {{FALSE, SAR_MODE_BIT_NR_MWS6}, }},
+ {NR_MMWAVE_NR_SUB6_SAR_BACKOFF_ENABLE, 1,
+ {{TRUE, SAR_MODE_BIT_NR_MWS6}, }},
+ {MHS_SAR_BACKOFF_DISABLE, 1,
+ {{FALSE, SAR_MODE_BIT_MHS}, }},
+ {MHS_SAR_BACKOFF_ENABLE, 1,
+ {{TRUE, SAR_MODE_BIT_MHS}, }},
+ {SAR_BACKOFF_DISABLE_ALL, 1,
+ {{FALSE, SAR_MODE_DIS_ALL}, }}
+ };
/* As Samsung specific and their requirement,
- * the mode set as the following form.
+ * the sar_event set as the following form.
* -1 : HEAD SAR disabled
* 0 : HEAD SAR enabled
* 1 : GRIP SAR disabled
@@ -7785,35 +7958,38 @@
* 4 : NR mmWave SAR enabled
* 5 : NR Sub6 SAR disabled
* 6 : NR Sub6 SAR enabled
- * 7 : SAR BACKOFF disabled all
- * The 'SAR BACKOFF disabled all' index should be the end of the mode.
+ * 7 : MHS SAR disabled
+ * 8 : MHS SAR enabled
+ * 9 : NR mmWave & NR Sub6 SAR disabled
+ * 10 : NR mmWave & NR Sub6 SAR enabled
+ * 11 : SAR BACKOFF disabled all
+ * The 'SAR BACKOFF disabled all' index should be the end of the sar_event.
*/
- if ((mode < HEAD_SAR_BACKOFF_DISABLE) || (mode > SAR_BACKOFF_DISABLE_ALL)) {
+ if ((sar_event < HEAD_SAR_BACKOFF_DISABLE) || (sar_event > SAR_BACKOFF_DISABLE_ALL)) {
DHD_ERROR(("%s: Request for Unsupported:%d\n", __FUNCTION__, bcm_atoi(string_num)));
err = BCME_RANGE;
goto error;
}
- mode_bit = mode + 1;
- enab = mode_bit % 2;
- mode_bit = mode_bit / 2;
-
err = wldev_iovar_getint(dev, "sar_enable", &setval);
if (unlikely(err)) {
DHD_ERROR(("%s: Failed to get sar_enable - error (%d)\n", __FUNCTION__, err));
goto error;
}
- if (mode == SAR_BACKOFF_DISABLE_ALL) {
- DHD_ERROR(("%s: SAR limit control all mode disable!\n", __FUNCTION__));
- setval = 0;
- } else {
- DHD_ERROR(("%s: SAR limit control mode %d enab %d\n",
- __FUNCTION__, mode_bit, enab));
- if (enab) {
- setval |= (1 << mode_bit);
- } else {
- setval &= ~(1 << mode_bit);
+ for (idx = 0; idx <= SAR_BACKOFF_EVENT_MAX; idx++) {
+ if (sar_event == sar_tbl[idx].sar_evt_id) {
+ for (n_ctls = 0; n_ctls < sar_tbl[idx].num_ctls; n_ctls++) {
+ if (sar_tbl[idx].sar_mode[n_ctls].enab) {
+ setval |= sar_tbl[idx].sar_mode[n_ctls].setval;
+ } else {
+ setval &= ~(sar_tbl[idx].sar_mode[n_ctls].setval);
+ }
+ DHD_ERROR(("%s: SAR limit control event %d enab %d setval %d\n",
+ __FUNCTION__, sar_event,
+ sar_tbl[idx].sar_mode[n_ctls].enab, setval));
+ }
+ break;
}
}
@@ -7832,9 +8008,23 @@
{
int err = BCME_ERROR;
s32 bandinfo = bcm_atoi(string_num);
+ int getval = 0;
+
+ /* check if sub6 sar is enabled */
+ err = wldev_iovar_getint(dev, "sar_enable", &getval);
+ if (unlikely(err)) {
+ DHD_ERROR(("%s: Failed to get sar_enable - error (%d)\n", __FUNCTION__, err));
+ goto error;
+ }
+
+ if ((getval & SAR_MODE_BIT_NR_S6) != SAR_MODE_BIT_NR_S6) {
+ err = BCME_NOTREADY;
+ DHD_ERROR(("%s: sub6 sar is not enabled (%d)\n", __FUNCTION__, getval));
+ goto error;
+ }
/* As Samsung specific and their requirement,
- * the bandinfo set as the following form.
+ * the bandinfo set as the following form. Wrong band will work as -1 in FW.
* -1 : Disabled bandinfo control
* 2 : NR Sub6 band2 tx power backoff
* 25 : NR Sub6 band25 tx power backoff
@@ -7844,22 +8034,6 @@
* 77 : NR Sub6 band77 tx power backoff
*/
- if ((bandinfo < SAR_NR_SUB6_BANDINFO_DISABLE) ||
- (bandinfo > SAR_NR_SUB6_BANDINFO_BAND77)) {
- DHD_ERROR(("%s: Request for Unsupported:%d\n",
- __FUNCTION__, bcm_atoi(string_num)));
- err = BCME_RANGE;
- goto error;
- }
-
- //Set SAR_ENABLE as Sub6
- err = wl_android_set_sarlimit_txctrl(dev, NRSUB6_SAR_ENABLE);
- if (unlikely(err)) {
- DHD_ERROR(("%s: Failed to set sar_enable as 6(NR_Sub6 enable) - error (%d)\n",
- __FUNCTION__, err));
- goto error;
- }
-
if (bandinfo == SAR_NR_SUB6_BANDINFO_DISABLE) {
DHD_ERROR(("%s: SAR NR Sub6 bandinfo disable!\n", __FUNCTION__));
} else {
@@ -7879,7 +8053,7 @@
}
#ifdef SUPPORT_SET_TID
-static int
+int
wl_android_set_tid(struct net_device *dev, char* command)
{
int err = BCME_ERROR;
@@ -7939,8 +8113,8 @@
}
} else {
dhdp->tid_mode = SET_TID_OFF;
- dhdp->target_uid = 0;
- dhdp->target_tid = 0;
+ dhdp->target_uid = DEFAULT_SET_TID_TARGET_UID;
+ dhdp->target_tid = DEFAULT_SET_TID_TARGET_PRIO;
}
WL_DBG(("%s mode [%d], uid [%d], tid [%d]\n", __FUNCTION__,
@@ -8111,7 +8285,7 @@
{
int error = 0;
char smbuf[WLC_IOCTL_SMLEN];
- uint8 buf[MAX_BUF_SIZE];
+ uint8 buf[JOIN_PREF_MAX_BUF_SIZE];
uint8 *pref = buf;
char *pcmd;
int num_ucipher_suites = 0;
@@ -8340,6 +8514,7 @@
MFREE(cfg->osh, config, sizeof(struct io_cfg));
}
}
+
static int
wl_android_set_miracast(struct net_device *dev, char *command)
{
@@ -8543,7 +8718,7 @@
int wl_keep_alive_set(struct net_device *dev, char* extra)
{
- wl_mkeep_alive_pkt_t mkeep_alive_pkt;
+ wl_mkeep_alive_pkt_v1_t mkeep_alive_pkt;
int ret;
uint period_msec = 0;
char *buf;
@@ -8559,10 +8734,10 @@
}
DHD_ERROR(("wl_keep_alive_set: period_msec is %d\n", period_msec));
- bzero(&mkeep_alive_pkt, sizeof(wl_mkeep_alive_pkt_t));
+ bzero(&mkeep_alive_pkt, sizeof(wl_mkeep_alive_pkt_v1_t));
mkeep_alive_pkt.period_msec = period_msec;
- mkeep_alive_pkt.version = htod16(WL_MKEEP_ALIVE_VERSION);
+ mkeep_alive_pkt.version = htod16(WL_MKEEP_ALIVE_VERSION_1);
mkeep_alive_pkt.length = htod16(WL_MKEEP_ALIVE_FIXED_LEN);
/* Setup keep alive zero for null packet generation */
@@ -8583,6 +8758,7 @@
MFREE(cfg->osh, buf, WLC_IOCTL_SMLEN);
return ret;
}
+
#ifdef P2PRESP_WFDIE_SRC
static int wl_android_get_wfdie_resp(struct net_device *dev, char *command, int total_len)
{
@@ -8620,34 +8796,14 @@
}
#endif /* P2PRESP_WFDIE_SRC */
-#ifdef BT_WIFI_HANDOVER
-static int
-wl_tbow_teardown(struct net_device *dev)
-{
- int err = BCME_OK;
- char buf[WLC_IOCTL_SMLEN];
- tbow_setup_netinfo_t netinfo;
- bzero(&netinfo, sizeof(netinfo));
- netinfo.opmode = TBOW_HO_MODE_TEARDOWN;
-
- err = wldev_iovar_setbuf_bsscfg(dev, "tbow_doho", &netinfo,
- sizeof(tbow_setup_netinfo_t), buf, WLC_IOCTL_SMLEN, 0, NULL);
- if (err < 0) {
- WL_ERR(("tbow_doho iovar error %d\n", err));
- return err;
- }
- return err;
-}
-#endif /* BT_WIFI_HANOVER */
-
static int wl_android_get_link_status(struct net_device *dev, char *command,
int total_len)
{
int bytes_written, error, result = 0, single_stream, stf = -1, i, nss = 0, mcs_map;
uint32 rspec;
uint encode, txexp;
- wl_bss_info_t *bi;
- int datalen = sizeof(uint32) + sizeof(wl_bss_info_t);
+ wl_bss_info_v109_t *bi;
+ int datalen = sizeof(uint32) + sizeof(wl_bss_info_v109_t);
char buf[WLC_IOCTL_SMLEN];
if (datalen > WLC_IOCTL_SMLEN) {
@@ -8664,7 +8820,7 @@
return -1;
}
- bi = (wl_bss_info_t*) (buf + sizeof(uint32));
+ bi = (wl_bss_info_v109_t*) (buf + sizeof(uint32));
for (i = 0; i < ETHER_ADDR_LEN; i++) {
if (bi->BSSID.octet[i] > 0) {
@@ -8806,6 +8962,7 @@
return ret;
}
+
s32
wl_cfg80211_p2plo_listen_start(struct net_device *dev, u8 *buf, int len)
{
@@ -8884,6 +9041,7 @@
exit :
return ret;
}
+
s32
wl_cfg80211_p2plo_listen_stop(struct net_device *dev)
{
@@ -8919,6 +9077,7 @@
}
return ret;
}
+
void
wl_cfg80211_cancel_p2plo(struct bcm_cfg80211 *cfg)
{
@@ -9221,6 +9380,11 @@
bytes_written = snprintf(command, total_len, "%s %d",
CMD_GET_LQCM_REPORT, lqcm_report);
+#ifdef RPM_FAST_TRIGGER
+ WL_INFORM(("Trgger RPM Fast\n"));
+ dhd_trigger_rpm_fast(wl_get_cfg(dev));
+#endif /* RPM_FAST_TRIGGER */
+
return bytes_written;
}
#endif /* SUPPORT_LQCM */
@@ -10318,7 +10482,10 @@
MFREE(cfg->osh, command, (buf_size + 1));
return ret;
}
+
#ifdef WLADPS_PRIVATE_CMD
+#define ADPS_MULTIMODE_PM2 3
+
static int
wl_android_set_adps_mode(struct net_device *dev, const char* string_num)
{
@@ -10337,6 +10504,9 @@
WL_ERR(("wl_android_set_adps_mode: Invalid value %d.\n", adps_mode));
return -EINVAL;
}
+#ifdef WLADPS_MULTIMODE
+ adps_mode = adps_mode == 0 ? ADPS_MULTIMODE_PM2 : adps_mode;
+#endif /* WLADPS_MULTIMODE */
err = dhd_enable_adps(dhdp, adps_mode);
if (err != BCME_OK) {
@@ -10345,6 +10515,7 @@
}
return err;
}
+
static int
wl_android_get_adps_mode(
struct net_device *dev, char *command, int total_len)
@@ -10708,7 +10879,7 @@
#endif /* WL_BCNRECV */
#ifdef SUPPORT_LATENCY_CRITICAL_DATA
-static int
+int
wl_android_set_latency_crt_data(struct net_device *dev, int mode)
{
int ret;
@@ -11128,6 +11299,110 @@
}
#endif /* SUPPORT_SOFTAP_ELNA_BYPASS */
+#ifdef CUSTOM_SOFTAP_SET_ANT
+#define HOTSPOT_ANTENNA_MODE_MIMO 1
+#define HOTSPOT_ANTENNA_MODE_SISO 2
+
+static int
+wl_android_set_softap_antenna(struct net_device *dev, char *command)
+{
+ char *ifname = NULL;
+ char *pos, *token;
+ int err = BCME_OK;
+ int mimo_siso = 0;
+ int set_chain = 0;
+
+ /*
+ * DRIVER SET_HOTSPOT_ANTENNA_MODE <ifname> <MIMO/SISO>
+ * MIMO:1, SISO:2
+ */
+ pos = command;
+
+ /* drop command */
+ token = bcmstrtok(&pos, " ", NULL);
+
+ /* get the interface name */
+ token = bcmstrtok(&pos, " ", NULL);
+ if (!token) {
+ WL_ERR(("%s: Invalid arguments about interface name\n", __FUNCTION__));
+ return -EINVAL;
+ }
+ ifname = token;
+
+ /* get mimo_siso value */
+ token = bcmstrtok(&pos, " ", NULL);
+ if (!token) {
+ WL_ERR(("%s: Invalid arguments about MIMO/SISO\n", __FUNCTION__));
+ return -EINVAL;
+ }
+ mimo_siso = bcm_atoi(token);
+
+ if (mimo_siso == HOTSPOT_ANTENNA_MODE_SISO) {
+ /* Set SISO mode */
+ set_chain = 1;
+ } else {
+ /* Set MIMO mode for other cases */
+ set_chain = 3;
+ }
+
+ WL_ERR(("[Test Mode] %s: Set Antenna for SoftAP [%d]\n", __FUNCTION__, set_chain));
+ err = wl_set_softap_antenna(dev, ifname, set_chain);
+ if (unlikely(err)) {
+ WL_ERR(("%s: Failed to set Antenna of SoftAP mode[%d], err=%d\n",
+ __FUNCTION__, mimo_siso, err));
+ return -EIO;
+ }
+
+ return err;
+}
+
+static int
+wl_android_get_softap_antenna(struct net_device *dev, char *command, int total_len)
+{
+ char *ifname = NULL;
+ char *pos, *token;
+ int err = BCME_OK;
+ int bytes_written = 0;
+ int mimo_siso = 0;
+ uint32 cur_rxchain;
+
+ /*
+ * DRIVER GET_HOTSPOT_ANTENNA_MODE <ifname>
+ */
+ pos = command;
+
+ /* drop command */
+ token = bcmstrtok(&pos, " ", NULL);
+
+ /* get the interface name */
+ token = bcmstrtok(&pos, " ", NULL);
+ if (!token) {
+ WL_ERR(("%s: Invalid arguments about interface name\n", __FUNCTION__));
+ return -EINVAL;
+ }
+ ifname = token;
+
+ err = wl_get_softap_antenna(dev, ifname, &cur_rxchain);
+ if (unlikely(err)) {
+ WL_ERR(("%s: Failed to get MIMO/SISO info of SoftAP mode, err=%d\n",
+ __FUNCTION__, err));
+ return -EIO;
+ } else {
+ if (cur_rxchain == 3) {
+ mimo_siso = HOTSPOT_ANTENNA_MODE_MIMO;
+ } else {
+ mimo_siso = HOTSPOT_ANTENNA_MODE_SISO;
+ }
+ WL_DBG(("[Test Mode] %s: SoftAP antenna status is %d\n",
+ __FUNCTION__, mimo_siso));
+ bytes_written = snprintf(command, total_len, "%s %d",
+ CMD_GET_HOTSPOT_ANTENNA_MODE, mimo_siso);
+ }
+
+ return bytes_written;
+}
+#endif /* CUSTOM_SOFTAP_SET_ANT */
+
#ifdef WL_NAN
int
wl_android_get_nan_status(struct net_device *dev, char *command, int total_len)
@@ -11643,7 +11918,7 @@
wl_android_twt_status_display_v1(wl_twt_status_v1_t *status, char *command, int total_len)
{
uint i;
- wl_twt_sdesc_t *desc = NULL;
+ wl_twt_sdesc_v0_t *desc = NULL;
u64 wake_time = 0;
int rem_len = 0, bytes_written = 0;
@@ -11662,7 +11937,7 @@
if (status->itwt_status[i].configID != WL_TWT_INV_CONFIG_ID) {
desc = &status->itwt_status[i].desc;
bytes_written = scnprintf(command, rem_len,
- "%d %u %u\n",
+ "%d %d %u %u\n", status->itwt_status[i].configID,
status->itwt_status[i].state, desc->wake_dur,
desc->wake_int);
CHECK_SCNPRINTF_RET_VAL(bytes_written);
@@ -11696,7 +11971,7 @@
if (status->btwt_status[i].configID != WL_TWT_INV_CONFIG_ID) {
desc = &status->btwt_status[i].desc;
bytes_written = scnprintf(command, rem_len,
- "%d %u %u\n",
+ "%d %d %u %u\n", status->btwt_status[i].configID,
status->btwt_status[i].state, desc->wake_dur,
desc->wake_int);
CHECK_SCNPRINTF_RET_VAL(bytes_written);
@@ -11729,7 +12004,7 @@
if ((total_len - rem_len) > 0) {
return (total_len - rem_len);
} else {
- return BCME_ERROR;
+ return BCME_OK;
}
}
@@ -12174,6 +12449,39 @@
#endif /* WL_DUAL_STA */
int
+wl_android_set_wsec_info(struct net_device *dev, char *command)
+{
+ int error = BCME_OK;
+ uint32 wsec_info;
+#ifdef DHD_PM_CONTROL_FROM_FILE
+ if (g_pm_control) {
+ WL_ERR(("Ignored Set wsec_info\n"));
+ return BCME_UNSUPPORTED;
+ }
+#endif /* DHD_PM_CONTROL_FROM_FILE */
+
+ if (sscanf(command, "%*s %d", &wsec_info) != 1) {
+ WL_ERR(("Failed to get Parameter\n"));
+ return BCME_ERROR;
+ }
+
+ if ((wsec_info != 0) && (wsec_info != 1)) {
+ WL_ERR(("Invalid wsec info value %d\n", wsec_info));
+ return BCME_ERROR;
+ }
+
+ error = wl_cfg80211_set_wsec_info(dev, &wsec_info, sizeof(wsec_info),
+ WL_WSEC_INFO_6G_LEGACY_SEC);
+ if (error) {
+ WL_ERR(("Failed to set wsec info %d, error = %d\n", wsec_info, error));
+ } else {
+ WL_ERR(("Succeeded to set wsec info %d,error = %d\n", wsec_info, error));
+ }
+
+ return error;
+}
+
+int
wl_handle_private_cmd(struct net_device *net, char *command, u32 cmd_len)
{
int bytes_written = 0;
@@ -12756,11 +13064,6 @@
bytes_written = wl_android_set_wfds_hash(net, command, 0);
}
#endif /* WLWFDS */
-#ifdef BT_WIFI_HANDOVER
- else if (strnicmp(command, CMD_TBOW_TEARDOWN, strlen(CMD_TBOW_TEARDOWN)) == 0) {
- bytes_written = wl_tbow_teardown(net);
- }
-#endif /* BT_WIFI_HANDOVER */
#ifdef CUSTOMER_HW4_PRIVATE_CMD
#ifdef FCC_PWR_LIMIT_2G
else if (strnicmp(command, CMD_GET_FCC_PWR_LIMIT_2G,
@@ -13055,6 +13358,16 @@
wl_android_get_softap_elna_bypass(net, command, priv_cmd.total_len);
}
#endif /* SUPPORT_SOFTAP_ELNA_BYPASS */
+#ifdef CUSTOM_SOFTAP_SET_ANT
+ else if (strnicmp(command, CMD_SET_HOTSPOT_ANTENNA_MODE,
+ strlen(CMD_SET_HOTSPOT_ANTENNA_MODE)) == 0) {
+ bytes_written = wl_android_set_softap_antenna(net, command);
+ }
+ else if (strnicmp(command, CMD_GET_HOTSPOT_ANTENNA_MODE,
+ strlen(CMD_GET_HOTSPOT_ANTENNA_MODE)) == 0) {
+ bytes_written = wl_android_get_softap_antenna(net, command, priv_cmd.total_len);
+ }
+#endif /* CUSTOM_SOFTAP_SET_ANT */
#ifdef WL_NAN
else if (strnicmp(command, CMD_GET_NAN_STATUS,
strlen(CMD_GET_NAN_STATUS)) == 0) {
@@ -13152,9 +13465,26 @@
command, priv_cmd.total_len);
}
#endif /* WL_DUAL_STA */
+ else if (strnicmp(command, CMD_SETWSECINFO, strlen(CMD_SETWSECINFO)) == 0) {
+ bytes_written = wl_android_set_wsec_info(net, command);
+ }
+#if defined(LIMIT_AP_BW)
+ else if (strnicmp(command, CMD_SET_SOFTAP_BW,
+ strlen(CMD_SET_SOFTAP_BW)) == 0) {
+ bytes_written = wl_android_set_softap_bw(net, command);
+ } else if (strnicmp(command, CMD_GET_SOFTAP_BW,
+ strlen(CMD_GET_SOFTAP_BW)) == 0) {
+ bytes_written = wl_android_get_softap_bw(net, command,
+ priv_cmd.total_len);
+ }
+#endif /* LIMIT_AP_BW */
else {
DHD_ERROR(("Unknown PRIVATE command %s - ignored\n", command));
+#ifdef CUSTOMER_HW4_DEBUG
+ bytes_written = BCME_UNSUPPORTED;
+#else
bytes_written = scnprintf(command, sizeof("FAIL"), "FAIL");
+#endif /* CUSTOMER_HW4_DEBUG */
}
return bytes_written;
@@ -13293,11 +13623,6 @@
event = BCM_E_DEV_LOST;
break;
/* Above events are supported from BCM Supp ver 47 Onwards */
-#ifdef BT_WIFI_HANDOVER
- case WLC_E_BT_WIFI_HANDOVER_REQ:
- event = BCM_E_DEV_BT_WIFI_HO_REQ;
- break;
-#endif /* BT_WIFI_HANDOVER */
default:
WL_ERR(("Event not supported\n"));
@@ -13498,6 +13823,8 @@
struct ether_addr ea_addr;
#endif /* DHD_USE_RANDMAC */
+ BCM_REFERENCE(primary_ndev);
+
WL_INFORM_MEM(("[STATIC_IF] Enter (%s) iftype:%d\n", ifname, iftype));
if (!cfg) {
@@ -13623,6 +13950,7 @@
return ret;
}
+
struct net_device *
wl_cfg80211_post_static_ifcreate(struct bcm_cfg80211 *cfg,
wl_if_event_info *event, u8 *addr, s32 iface_type)
@@ -13645,6 +13973,7 @@
event->name, NDEV_STATE_FW_IF_CREATED);
return new_ndev;
}
+
s32
wl_cfg80211_post_static_ifdel(struct bcm_cfg80211 *cfg, struct net_device *ndev)
{
@@ -14185,7 +14514,7 @@
err = -ENOMEM;
goto exit;
}
- bwcfg->version = WNM_BSSLOAD_MONITOR_VERSION;
+ bwcfg->version = WNM_BSSLOAD_MONITOR_VERSION_1;
bwcfg->type = 0;
bwcfg->weight = 0;
@@ -14272,7 +14601,7 @@
goto exit;
}
- btcfg->version = WNM_BSS_SELECT_FACTOR_VERSION;
+ btcfg->version = WNM_BSS_SELECT_FACTOR_VERSION_1;
btcfg->band = WLC_BAND_AUTO;
btcfg->type = 0;
btcfg->count = 0;
@@ -14676,3 +15005,92 @@
return err;
}
#endif /* CUSTOM_CONTROL_HE_6G_FEATURES */
+
+#if defined(LIMIT_AP_BW)
+static int
+wl_android_set_softap_bw(struct net_device *ndev, char *command)
+{
+ struct bcm_cfg80211 *cfg = NULL;
+ uint32 bw;
+ char *token, *pos;
+ int err = BCME_OK;
+
+ if (!ndev || (!(cfg = wl_get_cfg(ndev)))) {
+ err = BCME_NOTFOUND;
+ return err;
+ }
+ pos = command;
+
+ /* drop command */
+ token = bcmstrtok(&pos, " ", NULL);
+
+ /* get band */
+ token = bcmstrtok(&pos, " ", NULL);
+ if (!token) {
+ WL_ERR((CMD_SET_SOFTAP_BW ": band is not specified\n"));
+ return -EINVAL;
+ }
+ if (strncmp(token, "6g", strlen("6g"))) {
+ WL_ERR((CMD_SET_SOFTAP_BW " support 6G only\n"));
+ return -EINVAL;
+ }
+
+ /* get bandwidth */
+ token = bcmstrtok(&pos, " ", NULL);
+ if (!token) {
+ WL_ERR((CMD_SET_SOFTAP_BW ": bandwidth is not specified\n"));
+ return -EINVAL;
+ }
+ bw = (uint32)bcm_atoi(token);
+ err = wl_cfg80211_set_softap_bw(cfg, WL_CHANSPEC_BAND_6G, bw);
+ if (err != BCME_OK) {
+ return -EINVAL;
+ }
+
+ WL_INFORM(("SOFTAP BANDWITH LIMIT: %d\n", bw));
+ return BCME_OK;
+}
+
+static int
+wl_android_get_softap_bw(struct net_device *ndev, char *command, int total_len)
+{
+ struct bcm_cfg80211 *cfg = NULL;
+ int err = BCME_OK;
+ char *token, *pos;
+ uint32 bw = 0;
+ int rem_len = 0, bytes_written = 0;
+
+ if (!ndev || (!(cfg = wl_get_cfg(ndev)))) {
+ err = BCME_NOTFOUND;
+ goto exit;
+ return err;
+ }
+
+ pos = command;
+
+ /* drop command */
+ token = bcmstrtok(&pos, " ", NULL);
+
+ /* get band */
+ token = bcmstrtok(&pos, " ", NULL);
+ if (!token) {
+ WL_ERR((CMD_GET_SOFTAP_BW ": band is not specified\n"));
+ err = -EINVAL;
+ goto exit;
+ }
+ if (strncmp(token, "6g", strlen("6g"))) {
+ WL_ERR((CMD_GET_SOFTAP_BW " support 6G only\n"));
+ err = -EINVAL;
+ goto exit;
+ }
+
+ bw = wl_cfg80211_get_ap_bw_limit_bit(cfg, WL_CHANSPEC_BAND_6G);
+ bytes_written = scnprintf(command, rem_len, "%s = %d ",
+ CMD_GET_SOFTAP_BW, bw);
+ CHECK_SCNPRINTF_RET_VAL(bytes_written);
+
+exit:
+ WL_INFORM_MEM(("%s ret:%d bw:%d\n", CMD_GET_SOFTAP_BW, err, bw));
+ return bytes_written;
+}
+#endif /* SUPPORT_AP_INIT_BWCONF */
diff --git a/wl_android.h b/wl_android.h
index 169fc9b..5e330f3 100644
--- a/wl_android.h
+++ b/wl_android.h
@@ -1,7 +1,7 @@
/*
* Linux cfg80211 driver - Android related functions
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -28,7 +28,7 @@
/* If any feature uses the Generic Netlink Interface, put it here to enable WL_GENL
* automatically
*/
-#if defined(WL_SDO) || defined(BT_WIFI_HANDOVER)
+#if defined(WL_SDO)
#define WL_GENL
#endif
@@ -36,6 +36,11 @@
#include <net/genetlink.h>
#endif
+#if !defined(WL_MBO_IOV_VERSION)
+/* MBO IOV API version */
+#define WL_MBO_IOV_VERSION WL_MBO_IOV_VERSION_1_1
+#endif
+
typedef struct _android_wifi_priv_cmd {
char *buf;
int used_len;
@@ -108,9 +113,6 @@
BCM_E_SVC_FOUND,
BCM_E_DEV_FOUND,
BCM_E_DEV_LOST,
-#ifdef BT_WIFI_HANDOVER
- BCM_E_DEV_BT_WIFI_HO_REQ,
-#endif
BCM_E_MAX
};
diff --git a/wl_cfg80211.c b/wl_cfg80211.c
old mode 100755
new mode 100644
index 247e91b..046e684
--- a/wl_cfg80211.c
+++ b/wl_cfg80211.c
@@ -1,7 +1,7 @@
/*
* Linux cfg80211 driver
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -113,10 +113,10 @@
#include <bcmtlv.h>
#endif /* DNGL_AXI_ERROR_LOGGING && REPORT_AXI_ERROR */
-#if defined(CONFIG_WLAN_BEYONDX) || defined(CONFIG_SEC_5GMODEL)
+#ifdef WL_CP_COEX
#include <linux/dev_ril_bridge.h>
#include <linux/notifier.h>
-#endif /* CONFIG_WLAN_BEYONDX || defined(CONFIG_SEC_5GMODEL) */
+#endif /* WL_CP_COEX */
#ifdef WL_CELLULAR_CHAN_AVOID
#include <wl_cfg_cellavoid.h>
@@ -145,6 +145,16 @@
#endif /* WL_REASSOC */
module_param(wl_reassoc_support, uint, 0660);
+#ifdef WL_RAV_MSCS_NEG_IN_ASSOC
+/* Call IOVs to enable MSCS OFFLOAD
+ * and set default MSCS configuration.
+ */
+uint mscs_offload = true;
+#else
+uint mscs_offload = false;
+#endif /* WL_REASSOC */
+module_param(mscs_offload, uint, 0660);
+
static struct device *cfg80211_parent_dev = NULL;
static struct bcm_cfg80211 *g_bcmcfg = NULL;
/*
@@ -201,7 +211,6 @@
#define DNGL_FUNC(func, parameters)
#else
#define DNGL_FUNC(func, parameters) func parameters
-#define COEX_DHCP
#endif /* defined(BCMDONGLEHOST) */
@@ -245,13 +254,13 @@
*/
REG_RULE(2484-10, 2484+10, 20, 6, 20, 0),
/* IEEE 802.11a, channel 36..64 */
- REG_RULE(5150-10, 5350+10, 40, 6, 20, 0),
+ REG_RULE(5150-10, 5350+10, 80, 6, 20, 0),
#ifdef WL_5P9G
/* IEEE 802.11a, channel 100..181 */
- REG_RULE(5470-10, 5910+10, 40, 6, 20, 0),
+ REG_RULE(5470-10, 5910+10, 80, 6, 20, 0),
#else
/* IEEE 802.11a, channel 100..165 */
- REG_RULE(5470-10, 5850+10, 40, 6, 20, 0),
+ REG_RULE(5470-10, 5850+10, 80, 6, 20, 0),
#endif /* WL_5P9G */
#ifdef WL_6G_BAND
REG_RULE(6025-80, 6985+80, 160, 6, 20, 0),
@@ -454,6 +463,10 @@
};
#endif /* WL_ANALYTICS */
+#ifdef WL_RAV_MSCS_NEG_IN_ASSOC
+static s32 wl_cfg80211_enable_rav_mscs_params(struct bcm_cfg80211 *cfg,
+ struct net_device *ndev, bool mscs_offload);
+#endif /* WL_RAV_MSCS_NEG_IN_ASSOC */
static void wl_cfg80211_recovery_handler(struct work_struct *work);
static int wl_vndr_ies_get_vendor_oui(struct bcm_cfg80211 *cfg,
struct net_device *ndev, char *vndr_oui, u32 vndr_oui_len);
@@ -657,10 +670,6 @@
#endif /* DHD_LOSSLESS_ROAMING || !DHD_NONFT_ROAMING */
static s32 wl_notify_mic_status(struct bcm_cfg80211 *cfg, bcm_struct_cfgdev *cfgdev,
const wl_event_msg_t *e, void *data);
-#ifdef BT_WIFI_HANDOVER
-static s32 wl_notify_bt_wifi_handover_req(struct bcm_cfg80211 *cfg,
- bcm_struct_cfgdev *cfgdev, const wl_event_msg_t *e, void *data);
-#endif /* BT_WIFI_HANDOVER */
#ifdef GSCAN_SUPPORT
static s32 wl_handle_roam_exp_event(struct bcm_cfg80211 *wl, bcm_struct_cfgdev *cfgdev,
const wl_event_msg_t *e, void *data);
@@ -750,7 +759,7 @@
static s32 wl_set_set_cipher(struct net_device *dev,
struct cfg80211_connect_params *sme);
static s32 wl_set_key_mgmt(struct net_device *dev,
- struct cfg80211_connect_params *sme);
+ struct cfg80211_connect_params *sme, wlcfg_assoc_info_t *assoc_info);
static s32 wl_set_set_sharedkey(struct net_device *dev,
struct cfg80211_connect_params *sme);
#ifdef WL_FILS
@@ -917,6 +926,24 @@
static void wl_cfg80211_handle_set_ssid_complete(struct bcm_cfg80211 *cfg, wl_assoc_status_t *as,
const wl_event_msg_t *event, wl_assoc_state_t assoc_state);
+#ifdef WL_CFGVENDOR_CUST_ADVLOG
+static void wl_cfgvendor_custom_advlog_conn(struct bcm_cfg80211 *cfg, struct net_device *dev,
+ struct cfg80211_connect_params *sme);
+static void wl_cfgvendor_custom_advlog_disconn(struct bcm_cfg80211 *cfg, wl_assoc_status_t *as);
+static void wl_cfgvendor_custom_advlog_connfail(struct bcm_cfg80211 *cfg,
+ const wl_event_msg_t *event, wl_assoc_status_t *as);
+void wl_cfgvendor_advlog_disassoc_tx(struct bcm_cfg80211 *cfg, struct net_device *ndev,
+ uint32 reason, int rssi);
+#endif /* WL_CFGVENDOR_CUST_ADVLOG */
+
+#ifdef WL_NAN_INSTANT_MODE
+static int wl_cfg80211_get_nan_instant_chan(struct bcm_cfg80211 *cfg,
+ wl_chanspec_list_v1_t *chan_list, uint32 band_mask,
+ chanspec_t *nan_inst_mode_chspec);
+#endif /* WL_NAN_INSTANT_MODE */
+#line 967
+
+// MOG-ON: CHRE
#ifdef CHRE
#define WL_CFG_CHRE_DISABLE 0u
#define WL_CFG_CHRE_ENABLE 1u
@@ -1226,7 +1253,10 @@
.rx_mcs_160 = cpu_to_le16((0xfffa)),
.tx_mcs_160 = cpu_to_le16((0xfffa)),
}
- }
+ },
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(5, 8, 0))
+ .he_6ghz_capa = {.capa = cpu_to_le16(0x3038)},
+#endif /* LINUX_VERSION_CODE >= KERNEL_VERSION(5, 8, 0) */
};
#endif /* LINUX_VERSION_CODE >= KERNEL_VERSION(4, 19, 0) */
#endif /* WL_CAP_HE */
@@ -2036,7 +2066,7 @@
struct bcm_cfg80211 *cfg = wiphy_priv(wiphy);
struct net_device *dev = bcmcfg_to_prmry_ndev(cfg);
struct ether_addr bssid;
- wl_bss_info_t *bss = NULL;
+ wl_bss_info_v109_t *bss = NULL;
u16 channel = WL_P2P_TEMP_CHAN;
char *buf;
@@ -2070,7 +2100,7 @@
chspec = wl_ch_host_to_driver(channel);
}
else {
- bss = (wl_bss_info_t *) (buf + 4);
+ bss = (wl_bss_info_v109_t *) (buf + 4);
chspec = bss->chanspec;
#ifdef WL_6G_BAND
/* Avoid p2p bring up in 6G based on bssinfo */
@@ -2243,6 +2273,64 @@
return NULL;
}
+static int
+wl_iovar_fn(struct bcm_cfg80211 *cfg, struct net_device *ndev, struct preinit_iov *data)
+{
+ preinit_iov_t *vi = (preinit_iov_t *)data;
+
+ return wldev_iovar_setint(ndev, vi->cmd_name, vi->value);
+}
+
+static int
+wl_ioctl_fn(struct bcm_cfg80211 *cfg, struct net_device *ndev, struct preinit_iov *data)
+{
+ preinit_iov_t *vi = (preinit_iov_t *)data;
+
+ return wldev_ioctl_set(ndev, vi->cmd_id, &(vi->value), sizeof(int));
+}
+
+static preinit_iov_t init_sta_role_iovars[] = {
+ {wl_iovar_fn, WLC_SET_VAR, DEFAULT_ASSOC_LISTEN, "assoc_listen"},
+ {wl_iovar_fn, WLC_SET_VAR, 0, "roam_off"},
+ {wl_ioctl_fn, WLC_SET_ROAM_SCAN_PERIOD, DEFAULT_ROAM_SCAN_PRD, ""},
+ {wl_iovar_fn, WLC_SET_VAR, DEFAULT_FULL_ROAM_PRD, "fullroamperiod"},
+ {wl_iovar_fn, WLC_SET_VAR, AP_ENV_INDETERMINATE, "roam_env_detection"},
+ {wl_iovar_fn, WLC_SET_PM, 0x2, ""},
+ {wl_iovar_fn, WLC_SET_VAR, DEFAULT_BCN_TIMEOUT, "bcn_timeout"},
+ {wl_iovar_fn, WLC_SET_VAR, DEFAULT_ASSOC_RETRY, "assoc_retry_max"},
+ {wl_ioctl_fn, WLC_SET_FAKEFRAG, 0x1, ""},
+ {wl_iovar_fn, WLC_SET_VAR, 0x1, "buf_key_b4_m4"},
+ {wl_iovar_fn, WLC_SET_VAR, 0x1, "interworking"},
+ {wl_iovar_fn, WLC_SET_VAR, DEFAULT_WNM_CONF, "wnm"},
+ {wl_iovar_fn, WLC_SET_VAR, DEFAULT_RECREATE_BI_TIMEOUT, "recreate_bi_timeout"},
+ {wl_iovar_fn, WLC_SET_VAR, 0, "wnm_btmdelta"},
+ {NULL, 0, 0, NULL}
+};
+
+static void
+wl_apply_vif_sta_config(struct bcm_cfg80211 *cfg,
+ struct net_device *ndev)
+{
+ s32 ret;
+ preinit_iov_t *vi;
+
+#ifdef WL_RAV_MSCS_NEG_IN_ASSOC
+ ret = wl_cfg80211_enable_rav_mscs_params(cfg, ndev, mscs_offload);
+ if (ret) {
+ WL_INFORM(("enable rav_mscs failed ,err(%d)\n", ret));
+ }
+#endif /* WL_RAV_MSCS_NEG_IN_ASSOC */
+
+ for (vi = init_sta_role_iovars; vi->fn != NULL; vi++) {
+ ret = vi->fn(cfg, ndev, vi);
+ if ((ret != BCME_OK) && (ret != BCME_UNSUPPORTED)) {
+ WL_ERR(("dualsta_exec_initiovars: iov %s status %d\n",
+ vi->cmd_name, ret));
+ }
+ WL_DBG(("iov: %s ret: %d\n", vi->cmd_name, ret));
+ }
+}
+
void
wl_cfg80211_iface_state_ops(struct wireless_dev *wdev,
wl_interface_state_t state,
@@ -2327,6 +2415,9 @@
/* Enable firmware key buffering before sent 4-way M4 */
wldev_iovar_setint(ndev, "buf_key_b4_m4", 1);
}
+ if (wl_iftype == WL_IF_TYPE_STA) {
+ wl_apply_vif_sta_config(cfg, ndev);
+ }
if (wl_iftype == WL_IF_TYPE_P2P_GC) {
/* Disable firmware roaming for P2P interface */
wldev_iovar_setint(ndev, "roam_off", 1);
@@ -2648,6 +2739,10 @@
if (!dhd) {
return NULL;
}
+
+ if (wl_iftype == WL_IF_TYPE_P2P_DISC) {
+ dhd->p2p_disc_busy_cnt = 0;
+ }
#endif /* BCMDONGLEHOST */
if ((wl_mode = wl_iftype_to_mode(wl_iftype)) < 0) {
@@ -2717,7 +2812,7 @@
break;
case WL_IF_TYPE_P2P_DISC:
case WL_IF_TYPE_P2P_GO:
- /* Intentional fall through */
+ /* falls through */
case WL_IF_TYPE_P2P_GC:
if (cfg->p2p_supported) {
wdev = wl_cfg80211_p2p_if_add(cfg, wl_iftype,
@@ -2727,6 +2822,7 @@
/* Intentionally fall through for unsupported interface
* handling when firmware doesn't support p2p
*/
+ /* falls through */
default:
WL_ERR(("Unsupported interface type\n"));
err = -ENOTSUPP;
@@ -2828,6 +2924,18 @@
mutex_lock(&cfg->if_sync);
ret = _wl_cfg80211_del_if(cfg, primary_ndev, wdev, ifname);
mutex_unlock(&cfg->if_sync);
+
+ if ((ret == BCME_OK) && (cfg->vif_count == 0) && !(primary_ndev->flags & IFF_UP) &&
+ !(IS_CFG80211_STATIC_IF_ACTIVE(cfg)) &&
+ (wl_cfgvif_get_iftype_count(cfg, WL_IF_TYPE_AP) == 0) &&
+ (wl_cfgvif_get_iftype_count(cfg, WL_IF_TYPE_STA) == 0)) {
+ /* DHD cleanup in case wlan0 down was already called but was not
+ * done due to a virtual interface still running
+ */
+ WL_INFORM(("Calling dhd_stop for DHD cleanup as all interfaces are down\n"));
+ dhd_stop(primary_ndev);
+ }
+
return ret;
}
@@ -2929,6 +3037,13 @@
dhd_net_del_flowrings_sta(dhd, wdev->netdev);
#endif /* PCIE_FULL_DONGLE */
+#ifdef WL_CELLULAR_CHAN_AVOID
+ if (wl_iftype == WL_IF_TYPE_AP) {
+ wl_cellavoid_clear_requested_freq_bands(wdev->netdev,
+ cfg->cellavoid_info);
+ }
+#endif /* WL_CELLULAR_CHAN_AVOID */
+
switch (wl_iftype) {
case WL_IF_TYPE_P2P_GO:
case WL_IF_TYPE_P2P_GC:
@@ -4068,6 +4183,7 @@
}
return ret;
}
+
/* Create a Generic Network Interface and initialize it depending up on
* the interface type
*/
@@ -4896,6 +5012,7 @@
sec->fw_wsec = wsec_val;
return err;
}
+
#ifdef WL_GCMP
static s32
wl_set_wsec_info_algos(struct net_device *dev, uint32 algos, uint32 mask)
@@ -4925,7 +5042,7 @@
return BCME_NOMEM;
}
wsec_info = (wl_wsec_info_t *)buf;
- wsec_info->version = WL_WSEC_INFO_VERSION;
+ wsec_info->version = WL_WSEC_INFO_VERSION_1;
wsec_info_tlv = (bcm_xtlv_t *)(buf + OFFSETOF(wl_wsec_info_t, tlvs));
wsec_info->num_tlvs++;
@@ -4981,7 +5098,7 @@
wsec_info = (wl_wsec_info_t *)buf;
bzero(wsec_info, sizeof(wl_wsec_info_t) + data_len);
- wsec_info->version = WL_WSEC_INFO_VERSION;
+ wsec_info->version = WL_WSEC_INFO_VERSION_1;
bcm_info_tlv = (bcm_xtlv_t *)(buf + OFFSETOF(wl_wsec_info_t, tlvs));
wsec_info->num_tlvs++;
@@ -5031,19 +5148,14 @@
/* Parse the wpa2ie to decode the MFP capablity */
if (((wpa2_ie = bcm_parse_tlvs((const u8 *)sme->ie, sme->ie_len,
- DOT11_MNG_RSN_ID)) != NULL) &&
- (wl_cfg80211_get_rsn_capa(wpa2_ie, &rsn_cap) == 0) && rsn_cap) {
+ DOT11_MNG_RSN_ID)) != NULL) &&
+ (wl_cfg80211_get_rsn_capa(wpa2_ie, &rsn_cap) == 0) && rsn_cap) {
WL_DBG(("rsn_cap 0x%x%x\n", rsn_cap[0], rsn_cap[1]));
/* Check for MFP cap in the RSN capability field */
-#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 9, 0))
- if (sme->mfp)
-#endif
- {
- if (rsn_cap[0] & RSN_CAP_MFPR) {
- mfp = WL_MFP_REQUIRED;
- } else if (rsn_cap[0] & RSN_CAP_MFPC) {
- mfp = WL_MFP_CAPABLE;
- }
+ if (rsn_cap[0] & RSN_CAP_MFPR) {
+ mfp = WL_MFP_REQUIRED;
+ } else if (rsn_cap[0] & RSN_CAP_MFPC) {
+ mfp = WL_MFP_CAPABLE;
}
/*
* eptr --> end/last byte addr of wpa2_ie
@@ -5052,13 +5164,18 @@
eptr = (const u8*)wpa2_ie + (wpa2_ie->len + TLV_HDR_LEN);
/* pointing ptr to the next byte after rns_cap */
ptr = (const u8*)rsn_cap + RSN_CAP_LEN;
- if (mfp && (eptr - ptr) >= WPA2_PMKID_COUNT_LEN) {
+ /* If sme->mfp is not set, the bip iovar will not be fired. */
+ if (mfp &&
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 9, 0))
+ (sme->mfp) &&
+#endif
+ (eptr - ptr) >= WPA2_PMKID_COUNT_LEN) {
/* pmkid now to point to 1st byte addr of pmkid in wpa2_ie */
pmkid = (const wpa_pmkid_list_t*)ptr;
count = pmkid->count.low | (pmkid->count.high << 8);
/* ptr now to point to last byte addr of pmkid */
ptr = (const u8*)pmkid + (count * WPA2_PMKID_LEN
- + WPA2_PMKID_COUNT_LEN);
+ + WPA2_PMKID_COUNT_LEN);
if ((eptr - ptr) >= WPA_SUITE_LEN) {
/* group_mgmt_cs now to point to first byte addr of bip */
group_mgmt_cs = ptr;
@@ -5105,7 +5222,7 @@
}
if (group_mgmt_cs && bcmp((const uint8 *)WPA2_OUI,
- group_mgmt_cs, (WPA_SUITE_LEN - 1)) == 0) {
+ group_mgmt_cs, (WPA_SUITE_LEN - 1)) == 0) {
WL_DBG(("BIP is found\n"));
err = wldev_iovar_setbuf(dev, "bip",
group_mgmt_cs, WPA_SUITE_LEN, cfg->ioctl_buf,
@@ -5144,7 +5261,7 @@
u8 ioctl_buf[WLC_IOCTL_SMLEN] = {0};
bcm_iov_buf_t *iov_buf = (bcm_iov_buf_t *)ioctl_buf;
- iov_buf->version = WL_FILS_IOV_VERSION;
+ iov_buf->version = WL_FILS_IOV_VERSION_1_1;
err = wldev_iovar_getbuf(ndev, "fils", (uint8*)iov_buf, sizeof(bcm_iov_buf_t),
iov_buf, WLC_IOCTL_SMLEN, NULL);
if (err == BCME_UNSUPPORTED) {
@@ -5193,7 +5310,7 @@
err = BCME_NOMEM;
goto exit;
}
- iov_buf->version = WL_FILS_IOV_VERSION;
+ iov_buf->version = WL_FILS_IOV_VERSION_1_1;
iov_buf->id = WL_FILS_CMD_ADD_CONNECT_PARAMS;
/* check if this should be len w/o headers */
err = bcm_xtlv_buf_init(&tbuf, (uint8*)&iov_buf->data[0],
@@ -5346,8 +5463,101 @@
return err;
}
+static void
+wl_prepare_joinpref_tuples(uint8 **pref_buf, u32 akm, u32 pairwise_cipher, u32 mcast_cipher)
+{
+ u32 val = 0;
+
+ /* Update AKM in tuple */
+ val = bcmswap32(akm);
+ /* memcpy_s return is typecast to void since we have JOIN_PREF_MAX_WPA_TUPLES check */
+ (void)memcpy_s(*pref_buf, sizeof(u32), (uint8 *)&val, sizeof(u32));
+ *pref_buf += WPA_SUITE_LEN;
+ /* Set unicast cipher in tuple */
+ val = bcmswap32(pairwise_cipher);
+ (void)memcpy_s(*pref_buf, sizeof(u32), (uint8 *)&val, sizeof(u32));
+ *pref_buf += WPA_SUITE_LEN;
+ /* Set multicast cipher tuple */
+ val = bcmswap32(mcast_cipher);
+ (void)memcpy_s(*pref_buf, sizeof(u32), (uint8 *)&val, sizeof(u32));
+ *pref_buf += WPA_SUITE_LEN;
+
+}
+
static s32
-wl_set_key_mgmt(struct net_device *dev, struct cfg80211_connect_params *sme)
+wl_set_multi_akm(struct net_device *dev, struct bcm_cfg80211 *cfg,
+ struct cfg80211_connect_params *sme, wlcfg_assoc_info_t *assoc_info)
+{
+ int num_tuples = 0;
+ char smbuf[WLC_IOCTL_SMLEN];
+ uint8 buf[JOIN_PREF_MAX_BUF_SIZE];
+ uint8 *pref = buf;
+ int j;
+ int total_bytes = 0;
+ u32 multi_akm = 0;
+ s32 err = 0;
+
+ /* Check for valid set AKM combinations */
+ for (j = 0; j < sme->crypto.n_akm_suites; j++) {
+ multi_akm |= wl_rsn_akm_wpa_auth_lookup(sme->crypto.akm_suites[j]);
+ }
+
+ /* Currently supplicant layer multi-AKM is support is restricted to
+ * SAE and WPA2PSK for seamless roaming
+ */
+ if (multi_akm == (WPA3_AUTH_SAE_PSK | WPA2_AUTH_PSK)) {
+ /* Set auto_wpa_enabled to avoid wpa ie plumb */
+ assoc_info->auto_wpa_enabled = TRUE;
+ /* Update seamless_psk for AKMs needing psk plumb */
+ assoc_info->seamless_psk = TRUE;
+ } else {
+ WL_ERR(("Invalid MultiAKM combination 0x%x\n", multi_akm));
+ return -EINVAL;
+ }
+
+ bzero(buf, sizeof(buf));
+ /* Increment the num_tuples value whenever new joinpref tuple is added */
+ num_tuples = 2;
+
+ if (num_tuples <= JOIN_PREF_MAX_WPA_TUPLES) {
+ *pref++ = WL_JOIN_PREF_WPA;
+ *pref++ = (JOIN_PREF_WPA_TUPLE_SIZE * num_tuples) + 2;
+ *pref++ = 0;
+ *pref++ = (uint8)num_tuples;
+ total_bytes = JOIN_PREF_WPA_HDR_SIZE +
+ (JOIN_PREF_WPA_TUPLE_SIZE * num_tuples);
+ } else {
+ WL_ERR(("Too many wpa configs for join_pref\n"));
+ return -EINVAL;
+ }
+
+ /* Update tuples in akm-ucipher-mcipher format required for join_pref, the order of
+ * tuple defines the AKM preference, the first addition being the highest preference
+ */
+ wl_prepare_joinpref_tuples(&pref, WLAN_AKM_SUITE_SAE,
+ WLAN_CIPHER_SUITE_CCMP, WLAN_CIPHER_SUITE_CCMP);
+ wl_prepare_joinpref_tuples(&pref, WLAN_AKM_SUITE_PSK,
+ WLAN_CIPHER_SUITE_CCMP, WLAN_CIPHER_SUITE_CCMP);
+
+#ifdef MFP
+ if ((err = wl_cfg80211_set_mfp(cfg, dev, sme)) < 0) {
+ WL_ERR(("MFP set failed err:%d\n", err));
+ return -EINVAL;
+ }
+#endif /* MFP */
+
+ err = wldev_iovar_setbuf(dev, "join_pref", buf, total_bytes,
+ smbuf, sizeof(smbuf), NULL);
+ if (err) {
+ WL_ERR(("Failed to set join_pref, error = %d\n", err));
+ }
+
+ return err;
+}
+
+static s32
+wl_set_key_mgmt(struct net_device *dev, struct cfg80211_connect_params *sme,
+ wlcfg_assoc_info_t *assoc_info)
{
struct bcm_cfg80211 *cfg = wl_get_cfg(dev);
struct wl_security *sec;
@@ -5361,118 +5571,134 @@
}
if (sme->crypto.n_akm_suites) {
- err = wldev_iovar_getint(dev, "wpa_auth", &val);
- if (unlikely(err)) {
- WL_ERR(("could not get wpa_auth (%d)\n", err));
- return err;
- }
- if (val & (WPA_AUTH_PSK |
- WPA_AUTH_UNSPECIFIED)) {
- switch (sme->crypto.akm_suites[0]) {
- case WLAN_AKM_SUITE_8021X:
- val = WPA_AUTH_UNSPECIFIED;
- break;
- case WLAN_AKM_SUITE_PSK:
- val = WPA_AUTH_PSK;
- break;
- default:
- WL_ERR(("invalid akm suite (0x%x)\n",
- sme->crypto.akm_suites[0]));
- return -EINVAL;
+ WL_DBG(("No of akms %d 0x%x 0x%x\n", sme->crypto.n_akm_suites,
+ sme->crypto.akm_suites[0], sme->crypto.akm_suites[1]));
+ if (sme->crypto.n_akm_suites > 1) {
+ err = wl_set_multi_akm(dev, cfg, sme, assoc_info);
+ if (unlikely(err)) {
+ WL_ERR(("Failed to set multi akm key mgmt err = %d\n", err));
+ return err;
}
- } else if (val & (WPA2_AUTH_PSK |
- WPA2_AUTH_UNSPECIFIED)) {
- switch (sme->crypto.akm_suites[0]) {
+ } else {
+ err = wldev_iovar_getint(dev, "wpa_auth", &val);
+ if (unlikely(err)) {
+ WL_ERR(("could not get wpa_auth (%d)\n", err));
+ return err;
+ }
+ if (val & (WPA_AUTH_PSK |
+ WPA_AUTH_UNSPECIFIED)) {
+ switch (sme->crypto.akm_suites[0]) {
+ case WLAN_AKM_SUITE_8021X:
+ val = WPA_AUTH_UNSPECIFIED;
+ break;
+ case WLAN_AKM_SUITE_PSK:
+ val = WPA_AUTH_PSK;
+ break;
+ default:
+ WL_ERR(("invalid akm suite (0x%x)\n",
+ sme->crypto.akm_suites[0]));
+ return -EINVAL;
+ }
+ } else if (val & (WPA2_AUTH_PSK |
+ WPA2_AUTH_UNSPECIFIED)) {
+ switch (sme->crypto.akm_suites[0]) {
#ifdef MFP
- case WL_AKM_SUITE_SHA256_1X:
- val = WPA2_AUTH_1X_SHA256;
- break;
- case WL_AKM_SUITE_SHA256_PSK:
- val = WPA2_AUTH_PSK_SHA256;
- break;
+ case WL_AKM_SUITE_SHA256_1X:
+ val = WPA2_AUTH_1X_SHA256;
+ break;
+ case WL_AKM_SUITE_SHA256_PSK:
+ val = WPA2_AUTH_PSK_SHA256;
+ break;
#endif /* MFP */
- case WLAN_AKM_SUITE_8021X:
- case WLAN_AKM_SUITE_PSK:
+ case WLAN_AKM_SUITE_8021X:
+ case WLAN_AKM_SUITE_PSK:
#if defined(WLFBT) && defined(WLAN_AKM_SUITE_FT_8021X)
- case WLAN_AKM_SUITE_FT_8021X:
+ case WLAN_AKM_SUITE_FT_8021X:
#endif
#if defined(WLFBT) && defined(WLAN_AKM_SUITE_FT_PSK)
- case WLAN_AKM_SUITE_FT_PSK:
+ case WLAN_AKM_SUITE_FT_PSK:
#endif
- case WLAN_AKM_SUITE_FILS_SHA256:
- case WLAN_AKM_SUITE_FILS_SHA384:
- case WLAN_AKM_SUITE_8021X_SUITE_B:
- case WLAN_AKM_SUITE_8021X_SUITE_B_192:
+ case WLAN_AKM_SUITE_FILS_SHA256:
+ case WLAN_AKM_SUITE_FILS_SHA384:
+ case WLAN_AKM_SUITE_8021X_SUITE_B:
+ case WLAN_AKM_SUITE_8021X_SUITE_B_192:
#ifdef WL_OWE
- case WLAN_AKM_SUITE_OWE:
+ case WLAN_AKM_SUITE_OWE:
#endif /* WL_OWE */
#if defined(WL_SAE) || defined(WL_CLIENT_SAE)
- case WLAN_AKM_SUITE_SAE:
+ case WLAN_AKM_SUITE_SAE:
#endif /* WL_SAE || WL_CLIENT_SAE */
#ifdef WL_SAE_FT
- case WLAN_AKM_SUITE_FT_OVER_SAE:
+ case WLAN_AKM_SUITE_FT_OVER_SAE:
#endif /* WL_SAE_FT */
- case WLAN_AKM_SUITE_DPP:
- case WLAN_AKM_SUITE_FT_8021X_SHA384:
- val = wl_rsn_akm_wpa_auth_lookup(sme->crypto.akm_suites[0]);
- break;
- case WLAN_AKM_SUITE_FT_FILS_SHA256:
- val = WPA2_AUTH_FILS_SHA256 | WPA2_AUTH_FT;
- break;
- case WLAN_AKM_SUITE_FT_FILS_SHA384:
- val = WPA2_AUTH_FILS_SHA384 | WPA2_AUTH_FT;
- break;
- default:
- WL_ERR(("invalid akm suite (0x%x)\n",
- sme->crypto.akm_suites[0]));
- return -EINVAL;
+ case WLAN_AKM_SUITE_DPP:
+ case WLAN_AKM_SUITE_FT_8021X_SHA384:
+ val = wl_rsn_akm_wpa_auth_lookup(sme->crypto.akm_suites[0]);
+ break;
+ case WLAN_AKM_SUITE_FT_FILS_SHA256:
+ val = WPA2_AUTH_FILS_SHA256 | WPA2_AUTH_FT;
+ break;
+ case WLAN_AKM_SUITE_FT_FILS_SHA384:
+ val = WPA2_AUTH_FILS_SHA384 | WPA2_AUTH_FT;
+ break;
+ default:
+ WL_ERR(("invalid akm suite (0x%x)\n",
+ sme->crypto.akm_suites[0]));
+ return -EINVAL;
+ }
}
- }
#ifdef BCMWAPI_WPI
- else if (val & (WAPI_AUTH_PSK | WAPI_AUTH_UNSPECIFIED)) {
- switch (sme->crypto.akm_suites[0]) {
- case WLAN_AKM_SUITE_WAPI_CERT:
- val = WAPI_AUTH_UNSPECIFIED;
- break;
- case WLAN_AKM_SUITE_WAPI_PSK:
- val = WAPI_AUTH_PSK;
- break;
- default:
- WL_ERR(("invalid akm suite (0x%x)\n",
- sme->crypto.akm_suites[0]));
- return -EINVAL;
+ else if (val & (WAPI_AUTH_PSK | WAPI_AUTH_UNSPECIFIED)) {
+ switch (sme->crypto.akm_suites[0]) {
+ case WLAN_AKM_SUITE_WAPI_CERT:
+ val = WAPI_AUTH_UNSPECIFIED;
+ break;
+ case WLAN_AKM_SUITE_WAPI_PSK:
+ val = WAPI_AUTH_PSK;
+ break;
+ default:
+ WL_ERR(("invalid akm suite (0x%x)\n",
+ sme->crypto.akm_suites[0]));
+ return -EINVAL;
+ }
}
- }
#endif
#ifdef WL_FILS
#if !defined(WL_FILS_ROAM_OFFLD)
- err = wl_fils_toggle_roaming(dev, val);
- if (unlikely(err)) {
- return err;
- }
+ err = wl_fils_toggle_roaming(dev, val);
+ if (unlikely(err)) {
+ return err;
+ }
#endif /* !WL_FILS_ROAM_OFFLD */
#endif /* !WL_FILS */
#ifdef MFP
- if ((err = wl_cfg80211_set_mfp(cfg, dev, sme)) < 0) {
- WL_ERR(("MFP set failed err:%d\n", err));
- return -EINVAL;
- }
+ if ((err = wl_cfg80211_set_mfp(cfg, dev, sme)) < 0) {
+ WL_ERR(("MFP set failed err:%d\n", err));
+ return -EINVAL;
+ }
#endif /* MFP */
- WL_DBG_MEM(("[%s] wl wpa_auth to 0x%x\n", dev->name, val));
- err = wldev_iovar_setint_bsscfg(dev, "wpa_auth", val, bssidx);
- if (unlikely(err)) {
- WL_ERR(("could not set wpa_auth (0x%x)\n", err));
- return err;
+ WL_DBG_MEM(("[%s] wl wpa_auth to 0x%x\n", dev->name, val));
+ err = wldev_iovar_setint_bsscfg(dev, "wpa_auth", val, bssidx);
+ if (unlikely(err)) {
+ WL_ERR(("could not set wpa_auth (0x%x)\n", err));
+ return err;
+ }
}
}
sec = wl_read_prof(cfg, dev, WL_PROF_SEC);
- sec->wpa_auth = sme->crypto.akm_suites[0];
- sec->fw_wpa_auth = val;
+ if (assoc_info->auto_wpa_enabled == TRUE) {
+ /* Set to value 0 indicating multi-akm configuration */
+ sec->wpa_auth = 0;
+ sec->fw_wpa_auth = 0;
+ } else {
+ sec->wpa_auth = sme->crypto.akm_suites[0];
+ sec->fw_wpa_auth = val;
+ }
return err;
}
@@ -5585,6 +5811,9 @@
scb_val_t scbval;
int err = TRUE;
int wait_cnt;
+#ifdef WL_CFGVENDOR_CUST_ADVLOG
+ scb_val_t scb_rssi;
+#endif /* WL_CFGVENDOR_CUST_ADVLOG */
if (disassociate) {
#ifdef BCMDONGLEHOST
@@ -5598,6 +5827,16 @@
scbval.val = DOT11_RC_DISASSOC_LEAVING;
scbval.val = htod32(scbval.val);
+#ifdef WL_CFGVENDOR_CUST_ADVLOG
+ /* get rssi before sending DISASSOC to avoid getting zero */
+ bzero(&scb_rssi, sizeof(scb_val_t));
+ err = wldev_get_rssi(dev, &scb_rssi);
+ if (unlikely(err)) {
+ WL_ERR(("get_rssi error (%d)\n", err));
+ scb_rssi.val = WLC_RSSI_INVALID;
+ }
+#endif /* WL_CFGVENDOR_CUST_ADVLOG */
+
err = wldev_ioctl_set(dev, WLC_DISASSOC, &scbval,
sizeof(scb_val_t));
if (unlikely(err)) {
@@ -5606,6 +5845,11 @@
return err;
}
wait_cnt = 500/10;
+
+#ifdef WL_CFGVENDOR_CUST_ADVLOG
+ wl_cfgvendor_advlog_disassoc_tx(cfg, dev, DOT11_RC_DISASSOC_LEAVING,
+ scb_rssi.val);
+#endif /* WL_CFGVENDOR_CUST_ADVLOG */
} else {
wait_cnt = 200/10;
WL_ERR(("Waiting for previous DISCONNECTING status!\n"));
@@ -5672,7 +5916,7 @@
memcpy(((bcm_xtlv_t*)pxtlv)->data, hlp_ie, ((bcm_xtlv_t*)pxtlv)->len);
- iov_buf->version = WL_FILS_IOV_VERSION;
+ iov_buf->version = WL_FILS_IOV_VERSION_1_1;
iov_buf->id = WL_FILS_CMD_ADD_HLP_IE;
iov_buf->len = ((sizeof(bcm_xtlv_t)-1) + ((bcm_xtlv_t*)pxtlv)->len);
@@ -5748,7 +5992,7 @@
s32 roam_trigger[2] = {0, 0};
s32 err = BCME_OK;
- if (dhdp->roam_env_detection && (dev == bcmcfg_to_prmry_ndev(cfg))) {
+ if (dhdp->roam_env_detection && (IS_STA_IFACE(ndev_to_wdev(dev)))) {
bool is_roamtrig_reset = TRUE;
bool is_roam_env_ok = (wldev_iovar_setint(dev, "roam_env_detection",
AP_ENV_DETECT_NOT_USED) == BCME_OK);
@@ -5861,8 +6105,8 @@
}
static s32
-wl_config_assoc_security(struct bcm_cfg80211 *cfg,
- struct net_device *dev, struct cfg80211_connect_params *sme)
+wl_config_assoc_security(struct bcm_cfg80211 *cfg, struct net_device *dev,
+ struct cfg80211_connect_params *sme, wlcfg_assoc_info_t *assoc_info)
{
s32 err = BCME_OK;
struct wl_security *sec;
@@ -5890,14 +6134,16 @@
}
}
#endif /* WL_FILS */
-
- err = wl_set_set_cipher(dev, sme);
- if (unlikely(err)) {
- WL_ERR(("Invalid ciper\n"));
- goto exit;
+ /* Avoid cipher setting for multi-AKM, cipher combinations for multi-AKM predefined */
+ if (!(sme->crypto.n_akm_suites > 1)) {
+ err = wl_set_set_cipher(dev, sme);
+ if (unlikely(err)) {
+ WL_ERR(("Invalid ciper\n"));
+ goto exit;
+ }
}
- err = wl_set_key_mgmt(dev, sme);
+ err = wl_set_key_mgmt(dev, sme, assoc_info);
if (unlikely(err)) {
WL_ERR(("Invalid key mgmt\n"));
goto exit;
@@ -5906,7 +6152,8 @@
BCM_REFERENCE(wl_set_passphrase);
#ifdef WL_SAE
sec = wl_read_prof(cfg, dev, WL_PROF_SEC);
- if (sec->fw_wpa_auth & WPA3_AUTH_SAE_PSK) {
+ if ((sec->fw_wpa_auth & WPA3_AUTH_SAE_PSK) ||
+ (assoc_info->seamless_psk == TRUE)) {
err = wl_set_passphrase(dev, sme);
if (unlikely(err)) {
WL_ERR(("Unable to set passphrase\n"));
@@ -5948,10 +6195,10 @@
err = wldev_ioctl_set(dev, WLC_SET_WSEC_PMK, &pmk, sizeof(pmk));
if (err) {
- WL_ERR(("pmk set with WLC_SET_WSEC_PMK failed, error:%d", err));
+ WL_ERR(("pmk set with WLC_SET_WSEC_PMK failed, error:%d\n", err));
goto exit;
} else {
- WL_DBG(("pmk added succesfully\n"));
+ WL_INFORM(("pmk added succesfully\n"));
}
}
#endif /* WL_PSK_OFFLOAD */
@@ -6011,10 +6258,13 @@
wpaie_len = 0;
}
- err = wldev_iovar_setbuf(dev, "wpaie", wpaie, wpaie_len,
- cfg->ioctl_buf, WLC_IOCTL_MAXLEN, &cfg->ioctl_buf_sync);
- if (unlikely(err)) {
- WL_ERR(("wpaie set error (%d)\n", err));
+ /* In case of auto_wpa FW prepares the wpaie */
+ if (info->auto_wpa_enabled == FALSE) {
+ err = wldev_iovar_setbuf(dev, "wpaie", wpaie, wpaie_len,
+ cfg->ioctl_buf, WLC_IOCTL_MAXLEN, &cfg->ioctl_buf_sync);
+ if (unlikely(err)) {
+ WL_ERR(("wpaie set error (%d)\n", err));
+ }
}
return err;
@@ -6626,7 +6876,7 @@
goto fail;
}
} else {
- err = wl_config_assoc_security(cfg, dev, sme);
+ err = wl_config_assoc_security(cfg, dev, sme, &assoc_info);
if (unlikely(err)) {
WL_ERR(("config assoc security failed\n"));
goto fail;
@@ -6647,6 +6897,9 @@
if ((err = wl_handle_join(cfg, dev, &assoc_info)) != BCME_OK) {
goto fail;
}
+#ifdef WL_CFGVENDOR_CUST_ADVLOG
+ wl_cfgvendor_custom_advlog_conn(cfg, dev, sme);
+#endif /* WL_CFGVENDOR_CUST_ADVLOG */
}
/* Store the minium idx expected */
cfg->eidx.min_connect_idx = cfg->eidx.enqd;
@@ -6723,7 +6976,9 @@
#ifdef BCMDONGLEHOST
dhd_pub_t *dhdp = (dhd_pub_t *)(cfg->pub);
#endif /* BCMDONGLEHOST */
-
+#ifdef WL_CFGVENDOR_CUST_ADVLOG
+ scb_val_t scb_rssi;
+#endif /* WL_CFGVENDOR_CUST_ADVLOG */
RETURN_EIO_IF_NOT_UP(cfg);
#ifdef BCMDONGLEHOST
@@ -6778,6 +7033,18 @@
in all exit paths
*/
wl_set_drv_status(cfg, DISCONNECTING, dev);
+ /* clear connecting state */
+ wl_clr_drv_status(cfg, CONNECTING, dev);
+
+#ifdef WL_CFGVENDOR_CUST_ADVLOG
+ /* get rssi before sending DISASSOC to avoid getting zero */
+ bzero(&scb_rssi, sizeof(scb_val_t));
+ err = wldev_get_rssi(dev, &scb_rssi);
+ if (unlikely(err)) {
+ WL_ERR(("get_rssi error (%d)\n", err));
+ scb_rssi.val = WLC_RSSI_INVALID;
+ }
+#endif /* WL_CFGVENDOR_CUST_ADVLOG */
err = wldev_ioctl_set(dev, WLC_DISASSOC, &scbval,
sizeof(scb_val_t));
if (unlikely(err)) {
@@ -6785,6 +7052,11 @@
WL_ERR(("error (%d)\n", err));
goto exit;
}
+#ifdef WL_CFGVENDOR_CUST_ADVLOG
+ wl_cfgvendor_advlog_disassoc_tx(cfg, dev,
+ reason_code, scb_rssi.val);
+#endif /* WL_CFGVENDOR_CUST_ADVLOG */
+
}
#ifdef WL_WPS_SYNC
/* If are in WPS reauth state, then we would be
@@ -6815,7 +7087,6 @@
CFG80211_DISCONNECTED(dev, 0, NULL, 0, false, GFP_KERNEL);
}
}
-
/* Kill CMD_BTCOEXMODE timer/handler if those are enabled */
wl_cfg80211_btcoex_kill_handler();
@@ -7922,8 +8193,8 @@
}
return ret;
}
-#undef IF_COUNTERS_PARAM_CONTAINER_LEN_MAX
+#undef IF_COUNTERS_PARAM_CONTAINER_LEN_MAX
#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 16, 0))
static s32
wl_cfg80211_get_station(struct wiphy *wiphy, struct net_device *dev,
@@ -8077,6 +8348,7 @@
WL_DBG(("RX Rate %d Mbps\n", (sta->rx_rate / 1000)));
}
/* go through to get another information */
+ /* falls through */
case WL_IF_TYPE_P2P_GC:
case WL_IF_TYPE_P2P_DISC:
if ((err = wl_cfg80211_get_rssi(dev, cfg, &rssi)) != BCME_OK) {
@@ -8106,6 +8378,7 @@
}
#endif /* SUPPORT_RSSI_SUM_REPORT && (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 11, 0)) */
/* go through to get another information */
+ /* falls through */
case WL_IF_TYPE_P2P_GO:
#ifdef WL_RATE_INFO
/* Get the current tx/rx rate */
@@ -8126,7 +8399,7 @@
rates = (wl_rate_info_t *)buf;
rates->version = dtoh32(rates->version);
rates->length = dtoh32(rates->length);
- if (rates->version != WL_RATE_INFO_VERSION) {
+ if (rates->version != WL_RATE_INFO_VERSION_1) {
WL_ERR(("RATE_INFO version mismatch\n"));
err = BCME_VERSION;
goto error;
@@ -8280,6 +8553,11 @@
MFREE(cfg->osh, buf, WLC_IOCTL_MEDLEN);
}
+#ifdef RPM_FAST_TRIGGER
+ WL_INFORM(("Trgger RPM Fast\n"));
+ dhd_trigger_rpm_fast(cfg);
+#endif /* RPM_FAST_TRIGGER */
+
return err;
}
@@ -8596,7 +8874,7 @@
}
err = wldev_iovar_setint_no_wl(dev, "lpas", lpas);
- if (err < 0) {
+ if ((err < 0) && (err != BCME_UNSUPPORTED)) {
WL_ERR(("set lpas failed %d\n", err));
}
@@ -8676,10 +8954,6 @@
#ifdef ENABLE_IPMCAST_FILTER
{
int l2_filter = suspend ? TRUE : FALSE;
- if (dhd->op_mode & DHD_FLAG_HOSTAP_MODE) {
- /* If AP operates, ipmcast_l2filter is not allowed. */
- l2_filter = FALSE;
- }
err = wldev_iovar_setint_no_wl(dev, "ipmcast_l2filter", l2_filter);
if (err < 0) {
WL_ERR(("failed to set ipmcast_l2filter (%d)\n", err));
@@ -8705,47 +8979,24 @@
}
#endif /* DHD_BCN_TIMEOUT_IN_SUSPEND */
-#ifdef CUSTOM_EVENT_PM_WAKE
- {
- char *iovar_name;
- u32 iovar_val = 0;
-
-#ifdef CUSTOM_EVENT_PM_PERCENT
- iovar_name = "excess_pm_period";
-#else
- iovar_name = "const_awake_thresh";
- iovar_val = CUSTOM_EVENT_PM_WAKE;
-#endif /* CUSTOM_EVENT_PM_PERCENT */
-
- if (suspend) {
- iovar_val = (CUSTOM_EVENT_PM_WAKE * 4);
- }
-
- WL_DBG(("configure %s with val:%d\n", iovar_name, iovar_val));
- err = wldev_iovar_setint_no_wl(dev, iovar_name, iovar_val);
- if (err < 0) {
- WL_ERR(("excess_pm_period/awake_thresh failed %d\n", err));
- }
- }
-#endif /* CUSTOM_EVENT_PM_WAKE */
-
#ifdef WL_BCNRECV
wl_apply_bcn_recv(cfg, dev, suspend);
#endif /* WL_BCNRECV */
#ifdef CONFIG_SILENT_ROAM
{
- bool sroam = FALSE;
if (suspend) {
- if (!cfg->sroamed && (dev == cfg->inet_ndev)) {
- /* sroam enable applicable only for primary interface.
- * roam_off will be 1 for non-primary interfaces
- */
- sroam = TRUE;
+ if (!cfg->sroamed && IS_INET_LINK_NDEV(cfg, dev)) {
+ /* sroam enable applicable only for primary interface.
+ * roam_off will be 1 for non-primary interfaces
+ */
+ cfg->sroamed = TRUE;
+ wl_cfg80211_sroam_config(cfg, dev, TRUE);
}
+ } else {
+ cfg->sroamed = FALSE;
+ wl_cfg80211_sroam_config(cfg, dev, FALSE);
}
- cfg->sroamed = FALSE;
- wl_cfg80211_sroam_config(cfg, dev, sroam);
}
#endif /* CONFIG_SILENT_ROAM */
return BCME_OK;
@@ -9153,7 +9404,7 @@
* as false, since sec->wpa_auth is not available in the
* Wi-Fi toggle context.
*/
- wl_cfg80211_set_okc_pmkinfo(cfg, dev, pmk, FALSE);
+ wl_cfg80211_set_okc_pmkinfo(cfg, dev, pmk, TRUE);
}
if (pmksa->ssid) {
err = memcpy_s(&pmk_list->pmkid->ssid, sizeof(pmk_list->pmkid->ssid),
@@ -9360,7 +9611,7 @@
cfg->afx_hdl->is_active = TRUE;
if (cfg->afx_hdl->pending_tx_act_frm) {
- wl_action_frame_t *action_frame;
+ wl_action_frame_v1_t *action_frame;
action_frame = &(cfg->afx_hdl->pending_tx_act_frm->action_frame);
if (wl_cfgp2p_is_p2p_gas_action(action_frame->data, action_frame->len))
is_p2p_gas = true;
@@ -9430,7 +9681,7 @@
static s32
wl_cfg80211_config_p2p_pub_af_tx(struct wiphy *wiphy,
- wl_action_frame_t *action_frame, wl_af_params_t *af_params,
+ wl_action_frame_v1_t *action_frame, wl_af_params_v1_t *af_params,
struct p2p_config_af_params *config_af_params)
{
s32 err = BCME_OK;
@@ -9556,11 +9807,11 @@
#if defined(WL11U) && defined(WL_HOST_AF_DFS_CHECK)
static bool
-wl_cfg80211_check_DFS_channel(struct bcm_cfg80211 *cfg, wl_af_params_t *af_params,
+wl_cfg80211_check_DFS_channel(struct bcm_cfg80211 *cfg, wl_af_params_v1_t *af_params,
void *frame, u16 frame_len)
{
wl_scan_results *bss_list;
- wl_bss_info_t *bi = NULL;
+ wl_bss_info_v109_t *bi = NULL;
bool result = false;
s32 i;
chanspec_t chanspec;
@@ -9590,6 +9841,7 @@
return result;
}
#endif /* WL11U && WL_HOST_AF_DFS_CHECK */
+
static bool
wl_cfg80211_check_dwell_overflow(int32 requested_dwell, ulong dwell_jiffies)
{
@@ -9604,8 +9856,8 @@
static bool
wl_cfg80211_send_action_frame(struct wiphy *wiphy, struct net_device *dev,
- bcm_struct_cfgdev *cfgdev, wl_af_params_t *af_params,
- wl_action_frame_t *action_frame, u16 action_frame_len, s32 bssidx, const u8 *sa)
+ bcm_struct_cfgdev *cfgdev, wl_af_params_v1_t *af_params,
+ wl_action_frame_v1_t *action_frame, u16 action_frame_len, s32 bssidx, const u8 *sa)
{
#ifdef WL11U
struct net_device *ndev = NULL;
@@ -9972,7 +10224,7 @@
}
cmd = (wl_assoc_mgr_cmd_t*)ambuf;
- cmd->version = WL_ASSOC_MGR_CURRENT_VERSION;
+ cmd->version = WL_ASSOC_MGR_VERSION_0;
cmd->length = len;
cmd->cmd = WL_ASSOC_MGR_CMD_SEND_AUTH;
err = memcpy_s(&cmd->params, len, buf, len);
@@ -10020,8 +10272,8 @@
u64 *cookie)
#endif /* LINUX_VERSION_CODE >= KERNEL_VERSION(3, 14, 0) */
{
- wl_action_frame_t *action_frame;
- wl_af_params_t *af_params;
+ wl_action_frame_v1_t *action_frame;
+ wl_af_params_v1_t *af_params;
scb_val_t scb_val;
#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 14, 0))
struct ieee80211_channel *channel = params->chan;
@@ -10176,7 +10428,7 @@
goto exit;
}
- af_params = (wl_af_params_t *)MALLOCZ(cfg->osh, WL_WIFI_AF_PARAMS_SIZE);
+ af_params = (wl_af_params_v1_t *)MALLOCZ(cfg->osh, WL_WIFI_AF_PARAMS_SIZE_V1);
if (af_params == NULL)
{
WL_ERR(("unable to allocate frame\n"));
@@ -10220,7 +10472,7 @@
cfg80211_mgmt_tx_status(cfgdev, *cookie, buf, len, ack, GFP_KERNEL);
WL_DBG(("txstatus notified for cookie:%llu. ack:%d\n", *cookie, ack));
- MFREE(cfg->osh, af_params, WL_WIFI_AF_PARAMS_SIZE);
+ MFREE(cfg->osh, af_params, WL_WIFI_AF_PARAMS_SIZE_V1);
exit:
return err;
}
@@ -10363,6 +10615,7 @@
return err;
}
+
void
wl_init_listen_timer(struct bcm_cfg80211 *cfg)
{
@@ -10371,7 +10624,6 @@
}
}
-#ifdef WL_CFG80211_VSDB_PRIORITIZE_SCAN_REQUEST
struct net_device *
wl_cfg80211_get_remain_on_channel_ndev(struct bcm_cfg80211 *cfg)
{
@@ -10386,7 +10638,6 @@
return NULL;
}
-#endif /* WL_CFG80211_VSDB_PRIORITIZE_SCAN_REQUEST */
bool
wl_cfg80211_macaddr_sync_reqd(struct net_device *dev)
@@ -11002,6 +11253,35 @@
}
static bool
+wl_is_ccode_change_allowed(struct net_device *net)
+{
+ struct wireless_dev *wdev = ndev_to_wdev(net);
+ struct wiphy *wiphy = wdev->wiphy;
+ struct bcm_cfg80211 *cfg = wiphy_priv(wiphy);
+ struct net_info *iter, *next;
+
+ /* Country code isn't allowed change on AP/GO, NDP established */
+ GCC_DIAGNOSTIC_PUSH_SUPPRESS_CAST();
+ for_each_ndev(cfg, iter, next) {
+ GCC_DIAGNOSTIC_POP();
+ if (iter->ndev) {
+ if (wl_get_drv_status(cfg, AP_CREATED, iter->ndev)) {
+ WL_ERR(("AP active. skip coutry ccode change"));
+ return false;
+ }
+ }
+ }
+
+#ifdef WL_NAN
+ if (wl_cfgnan_is_enabled(cfg) && wl_cfgnan_is_dp_active(net)) {
+ WL_ERR(("NDP established. skip coutry ccode change"));
+ return false;
+ }
+#endif /* WL_NAN */
+ return true;
+}
+
+static bool
wl_is_ccode_change_required(struct net_device *net,
char *country_code, int revinfo)
{
@@ -11038,22 +11318,13 @@
struct wiphy *wiphy = wdev->wiphy;
struct bcm_cfg80211 *cfg = wiphy_priv(wiphy);
struct net_info *iter, *next;
- scb_val_t scbval;
+ BCM_REFERENCE(ret);
GCC_DIAGNOSTIC_PUSH_SUPPRESS_CAST();
for_each_ndev(cfg, iter, next) {
GCC_DIAGNOSTIC_POP();
if (iter->ndev) {
- if (wl_get_drv_status(cfg, AP_CREATED, iter->ndev)) {
- memset(scbval.ea.octet, 0xff, ETHER_ADDR_LEN);
- scbval.val = DOT11_RC_DEAUTH_LEAVING;
- if ((ret = wldev_ioctl_set(iter->ndev,
- WLC_SCB_DEAUTHENTICATE_FOR_REASON,
- &scbval, sizeof(scb_val_t))) != 0) {
- WL_ERR(("Failed to disconnect STAs %d\n", ret));
- }
-
- } else if (wl_get_drv_status(cfg, CONNECTED, iter->ndev)) {
+ if (wl_get_drv_status(cfg, CONNECTED, iter->ndev)) {
if ((iter->ndev == net) && !user_enforced)
continue;
wl_cfg80211_disassoc(iter->ndev, WLAN_REASON_DEAUTH_LEAVING);
@@ -11070,6 +11341,7 @@
#ifdef WL_NAN
if (wl_cfgnan_is_enabled(cfg)) {
mutex_lock(&cfg->if_sync);
+ cfg->nancfg->notify_user = true;
ret = wl_cfgnan_check_nan_disable_pending(cfg, true, true);
mutex_unlock(&cfg->if_sync);
if (ret != BCME_OK) {
@@ -11079,6 +11351,74 @@
#endif /* WL_NAN */
}
+static int wl_copy_regd(const struct ieee80211_regdomain *regd_orig,
+ struct ieee80211_regdomain *regd_copy)
+{
+ int i;
+
+ if (memcpy_s(regd_copy, sizeof(*regd_copy), regd_orig, sizeof(*regd_orig))) {
+ return BCME_ERROR;
+ }
+ for (i = 0; i < regd_orig->n_reg_rules; i++) {
+ if (memcpy_s(®d_copy->reg_rules[i], sizeof(regd_copy->reg_rules[i]),
+ ®d_orig->reg_rules[i], sizeof(regd_orig->reg_rules[i]))) {
+ return BCME_ERROR;
+ }
+ }
+ return BCME_OK;
+}
+
+static void wl_notify_regd(struct wiphy *wiphy, char *country_code)
+{
+ struct ieee80211_regdomain *regd_copy = NULL;
+ int regd_len;
+ struct bcm_cfg80211 *cfg = wiphy_priv(wiphy);
+
+ regd_len = sizeof(brcm_regdom) + (brcm_regdom.n_reg_rules *
+ sizeof(struct ieee80211_reg_rule));
+
+ regd_copy = (struct ieee80211_regdomain *)MALLOCZ(cfg->osh, regd_len);
+ if (!regd_copy) {
+ WL_ERR(("failed to alloc regd_copy\n"));
+ return;
+ }
+
+ /* the upper layer function below requires non-const type */
+ if (wl_copy_regd(&brcm_regdom, regd_copy)) {
+ WL_ERR(("failed to copy new regd\n"));
+ goto exit;
+ }
+
+ if (country_code) {
+ if (memcpy_s(regd_copy->alpha2, sizeof(regd_copy->alpha2),
+ country_code, WL_CCODE_LEN)) {
+ WL_ERR(("failed to copy new ccode:%s\n", country_code));
+ goto exit;
+ }
+ }
+
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(4, 0, 0))
+ if (rtnl_is_locked()) {
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(5, 12, 0))
+ wiphy_lock(wiphy);
+ regulatory_set_wiphy_regd_sync(wiphy, regd_copy);
+ wiphy_unlock(wiphy);
+#else
+ regulatory_set_wiphy_regd_sync_rtnl(wiphy, regd_copy);
+#endif /* LINUX_VERSION >= 5.12.0 */
+ } else {
+ regulatory_set_wiphy_regd(wiphy, regd_copy);
+ }
+#else
+ /* for 3.10 OEM_HW40 build */
+ wiphy_apply_custom_regulatory(wiphy, regd_copy);
+#endif /* LINUX_VERSION >= 4.0.0 */
+
+exit:
+ MFREE(cfg->osh, regd_copy, regd_len);
+ return;
+}
+
s32
wl_cfg80211_set_country_code(struct net_device *net, char *country_code,
bool notify, bool user_enforced, int revinfo)
@@ -11100,6 +11440,12 @@
goto exit;
}
+ if (wl_is_ccode_change_allowed(net) == false) {
+ WL_ERR(("country code change isn't allowed during AP role/NAN connected\n"));
+ ret = BCME_EPERM;
+ goto exit;
+ }
+
wl_cfg80211_cleanup_connection(net, user_enforced);
/* Store before applying - so that if event comes earlier that is handled properly */
@@ -11122,10 +11468,12 @@
*/
if (!IS_REGDOM_SELF_MANAGED(wiphy)) {
regulatory_hint(wiphy, country_code);
+ } else {
+ wl_notify_regd(wiphy, country_code);
}
exit:
- return ret;
+ return OSL_ERROR(ret);
}
#ifdef CONFIG_CFG80211_INTERNAL_REGDB
@@ -11216,7 +11564,6 @@
/* Use self managed regulatory domain */
wiphy->regulatory_flags |= REGULATORY_WIPHY_SELF_MANAGED |
REGULATORY_IGNORE_STALE_KICKOFF;
- wiphy->regd = &brcm_regdom;
WL_DBG(("Self managed regdom\n"));
return;
#else /* WL_SELF_MANAGED_REGDOM && KERNEL >= 4.0 */
@@ -11230,7 +11577,7 @@
#else /* KERNEL VER >= 3.14 */
wiphy->flags |= WIPHY_FLAG_CUSTOM_REGULATORY;
#endif /* LINUX_VERSION_CODE >= KERNEL_VERSION(3, 14, 0) */
- wiphy_apply_custom_regulatory(wiphy, &brcm_regdom);
+ wl_notify_regd(wiphy, NULL);
WL_DBG(("apply custom regulatory\n"));
#endif /* WL_SELF_MANAGED_REGDOM && KERNEL >= 4.0 */
}
@@ -11485,8 +11832,18 @@
if (unlikely(err < 0)) {
WL_ERR(("Couldn not register wiphy device (%d)\n", err));
wiphy_free(wdev->wiphy);
+ return err;
}
+ /* set wiphy->regd through reg_process_self_managed_hints
+ * need to call it after wiphy_register
+ * since wiphy_register adds rdev to cfg80211_rdev_list
+ */
+ if (IS_REGDOM_SELF_MANAGED(wdev->wiphy)) {
+ rtnl_lock();
+ wl_notify_regd(wdev->wiphy, NULL);
+ rtnl_unlock();
+ }
return err;
}
@@ -11975,7 +12332,7 @@
}
else {
WL_DBG(("no action (IBSS mode)\n"));
-}
+ }
return err;
}
@@ -11983,6 +12340,10 @@
{
scb_val_t scbval;
s32 err;
+#ifdef WL_CFGVENDOR_CUST_ADVLOG
+ scb_val_t scb_rssi;
+#endif /* WL_CFGVENDOR_CUST_ADVLOG */
+
#ifdef BCMDONGLEHOST
struct bcm_cfg80211 *cfg = wl_get_cfg(ndev);
dhd_pub_t *dhdp = (dhd_pub_t *)(cfg->pub);
@@ -11993,6 +12354,16 @@
dhd_net2idx(dhdp->info, ndev), WLAN_REASON_DEAUTH_LEAVING);
#endif /* BCMDONGLEHOST */
+#ifdef WL_CFGVENDOR_CUST_ADVLOG
+ /* get rssi before sending DISASSOC to avoid getting zero */
+ bzero(&scb_rssi, sizeof(scb_val_t));
+ err = wldev_get_rssi(ndev, &scb_rssi);
+ if (unlikely(err)) {
+ WL_ERR(("get_rssi error (%d)\n", err));
+ scb_rssi.val = WLC_RSSI_INVALID;
+ }
+#endif /* WL_CFGVENDOR_CUST_ADVLOG */
+
memset_s(&scbval, sizeof(scb_val_t), 0x0, sizeof(scb_val_t));
scbval.val = htod32(reason);
err = wldev_ioctl_set(ndev, WLC_DISASSOC, &scbval, sizeof(scb_val_t));
@@ -12000,8 +12371,12 @@
WL_ERR(("WLC_DISASSOC error %d\n", err));
} else {
WL_INFORM_MEM(("wl disassoc. reason:%d\n", reason));
+#ifdef WL_CFGVENDOR_CUST_ADVLOG
+ wl_cfgvendor_advlog_disassoc_tx(cfg, ndev, reason, scb_rssi.val);
+#endif /* WL_CFGVENDOR_CUST_ADVLOG */
}
}
+
void wl_cfg80211_del_all_sta(struct net_device *ndev, uint32 reason)
{
struct net_device *dev;
@@ -12057,6 +12432,7 @@
return;
}
+
/* API to handle the Deauth from the AP.
* For now we are deleting the PMKID cache in DHD/FW
* in case of current connection is using SAE authnetication
@@ -12204,12 +12580,11 @@
break;
case WL_STATE_ASSOC_IDLE:
/* link up/down while cfg80211 state is not in
- * 'ASSOCIATING/ASSOCIATED. Sync up the fw
- * by disconnecting.
+ * 'ASSOCIATING/ASSOCIATED. Do nothing,
*/
- WL_ERR(("Unexpected link %s in assoc idle state\n",
+ WL_ERR(("Unexpected link %s in assoc idle state, do nothing\n",
link_up ? "UP" : "DOWN"));
- action = WL_LINK_FORCE_DEAUTH;
+ action = WL_LINK_NONE;
break;
default:
WL_ERR(("unknown state:%d\n", assoc_state));
@@ -12237,15 +12612,28 @@
}
}
+#if defined(SUPPORT_RESTORE_SCAN_PARAMS) && defined(WES_SUPPORT)
+extern int wl_android_default_set_scan_params(struct net_device *dev, char *command, int total_len);
+#endif /* SUPPORT_RESTORE_SCAN_PARAMS && WES_SUPPORT */
+
+#ifdef SUPPORT_LATENCY_CRITICAL_DATA
+extern int wl_android_set_latency_crt_data(struct net_device *dev, int mode);
+#endif /* SUPPORT_LATENCY_CRITICAL_DATA */
+
+#ifdef SUPPORT_SET_TID
+extern int wl_android_set_tid(struct net_device *ndev, char* command);
+#endif /* SUPPORT_SET_TID */
static s32
wl_post_linkdown_ops(struct bcm_cfg80211 *cfg,
wl_assoc_status_t *as, struct net_device *ndev)
{
s32 ret = BCME_OK;
dhd_pub_t *dhdp = (dhd_pub_t *)(cfg->pub);
+ char cmd[WLC_IOCTL_SMLEN];
/* Common Code for connect failure & link down */
BCM_REFERENCE(dhdp);
+ BCM_REFERENCE(cmd);
WL_INFORM_MEM(("link down. connection state bit status: [%u:%u:%u:%u]\n",
wl_get_drv_status(cfg, CONNECTING, ndev),
@@ -12280,6 +12668,14 @@
/* Turn off NCHO mode */
wl_android_set_ncho_mode(ndev, FALSE);
}
+#ifdef SUPPORT_RESTORE_SCAN_PARAMS
+ else {
+
+ bzero(cmd, WLC_IOCTL_SMLEN);
+ snprintf(cmd, WLC_IOCTL_SMLEN, "%s", "RESTORE_SCAN_PARAMS");
+ wl_android_default_set_scan_params(ndev, cmd, WLC_IOCTL_SMLEN);
+ }
+#endif /* SUPPORT_RESTORE_SCAN_PARAMS */
#endif /* WES_SUPPORT */
#ifdef WLTDLS
@@ -12314,6 +12710,21 @@
}
#endif /* defined(KEEP_ALIVE) && defined(DHD_CLEANUP_KEEP_ALIVE) */
+#ifdef SUPPORT_LATENCY_CRITICAL_DATA
+ if (cfg->latency_mode) {
+ wl_android_set_latency_crt_data(ndev, LATENCY_CRT_DATA_MODE_OFF);
+ }
+#endif /* SUPPORT_LATENCY_CRITICAL_DATA */
+
+#ifdef SUPPORT_SET_TID
+ if (dhdp->tid_mode) {
+ bzero(cmd, WLC_IOCTL_SMLEN);
+ snprintf(cmd, WLC_IOCTL_SMLEN, "%d %d %d", SET_TID_OFF,
+ DEFAULT_SET_TID_TARGET_UID, DEFAULT_SET_TID_TARGET_PRIO);
+ wl_android_set_tid(ndev, cmd);
+ }
+#endif /* SUPPORT_SET_TID */
+
return ret;
}
@@ -12539,8 +12950,7 @@
ie_len = datalen - DOT11_DISCONNECT_RC;
}
}
- else if ((event == WLC_E_LINK) &&
- (reason == WLC_E_LINK_BCN_LOSS)) {
+ else if ((event == WLC_E_LINK) && (reason == WLC_E_LINK_BCN_LOSS)) {
if (ndev == bcmcfg_to_prmry_ndev(cfg)) {
#ifdef WL_ANALYTICS
if (wl_vndr_ies_find_vendor_oui(cfg, ndev,
@@ -12554,6 +12964,9 @@
dhdp->alert_reason = ALERT_BCN_LOST;
dhd_os_send_alert_message(dhdp);
#endif /* WL_CFGVENDOR_SEND_ALERT_EVENT */
+#ifdef WL_CFGVENDOR_CUST_ADVLOG
+ wl_cfgvendor_custom_advlog_disconn(cfg, as);
+#endif /* WL_CFGVENDOR_CUST_ADVLOG */
}
/* force reset reason code to prevent autoreconnect in bcnloss case */
reason = 0;
@@ -12584,17 +12997,17 @@
wl_init_prof(cfg, ndev);
if (wl_get_drv_status(cfg, DISCONNECTING, ndev)) {
- WL_DBG_MEM(("locally generated disassoc\n"));
+ /* If DISCONNECTING bit is set, mark locally generated */
loc_gen = 1;
}
CFG80211_DISCONNECTED(ndev, reason, ie_ptr, ie_len,
loc_gen, GFP_KERNEL);
WL_INFORM_MEM(("[%s] Disconnect event sent to upper layer"
- "event:%d e->reason=%d reason=%d ie_len=%d "
+ "event:%d e->reason=%d reason=%d ie_len=%d loc_gen=%d"
"from " MACDBG "\n",
ndev->name, event, ntoh32(as->reason), reason, ie_len,
- MAC2STRDBG((const u8*)(&as->addr))));
+ loc_gen, MAC2STRDBG((const u8*)(&as->addr))));
/* clear connected state */
wl_clr_drv_status(cfg, CONNECTED, ndev);
@@ -12722,6 +13135,216 @@
return ret;
}
+#ifdef WL_CFGVENDOR_CUST_ADVLOG
+extern const char* get_advlog_val(dhd_advlog_map_entry_t *arr, uint32 arr_len, int tag);
+
+static dhd_advlog_map_entry_t wl_advlog_auth_assoc_req[] = {
+ /* do not print to the kernel, only for framework (MACDBG_FULL) */
+ {WLC_E_AUTH, "[CONN] AUTH REQ bssid="MACDBG_FULL" rssi=%d auth_algo=%u tx_status=%s"},
+ {WLC_E_ASSOC, "[CONN] ASSOC REQ bssid="MACDBG_FULL" rssi=%d auth_algo=%u tx_status=%s"},
+};
+
+static dhd_advlog_map_entry_t wl_advlog_auth_assoc_resp[] = {
+ /* do not print to the kernel, only for framework (MACDBG_FULL) */
+ {WLC_E_AUTH, "[CONN] AUTH RESP bssid="MACDBG_FULL" auth_algo=%u status=%u"},
+ {WLC_E_ASSOC, "[CONN] ASSOC RESP bssid="MACDBG_FULL" auth_algo=%u status=%u"},
+};
+
+static dhd_advlog_map_entry_t wl_advlog_tx_status[] = {
+ {WLC_E_STATUS_SUCCESS, "ACK"},
+ {WLC_E_STATUS_TIMEOUT, "ACK"},
+ {WLC_E_STATUS_FAIL, "ACK"},
+ {WLC_E_STATUS_NO_ACK, "NO_ACK"},
+ {WLC_E_STATUS_SUPPRESS, "TX_FAIL"},
+};
+
+static dhd_advlog_map_entry_t wl_advlog_deauth_disassoc[] = {
+ /* do not print to the kernel, only for framework (MACDBG_FULL) */
+ {WLC_E_DEAUTH_IND, "[CONN] DEAUTH RX bssid="MACDBG_FULL" rssi=%d reason=%u"},
+ {WLC_E_DEAUTH, "[CONN] DEAUTH TX bssid="MACDBG_FULL" rssi=%d reason=%u"},
+ {WLC_E_DISASSOC_IND, "[CONN] DISASSOC RX bssid="MACDBG_FULL" rssi=%d reason=%u"},
+ {WLC_E_DISASSOC, "[CONN] DISASSOC TX bssid="MACDBG_FULL" rssi=%d reason=%u"},
+};
+
+static void
+wl_cfgvendor_advlog_deauth_disassoc(wl_assoc_status_t *as, int rssi)
+{
+ const char *fmt_str = NULL;
+
+ fmt_str = get_advlog_val(wl_advlog_deauth_disassoc,
+ ARRAY_SIZE(wl_advlog_deauth_disassoc), as->event_type);
+ if (fmt_str) {
+ /* do not print to the kernel, only for framework (MACDBG_FULL) */
+ SUPP_ADVLOG((fmt_str, MAC2STRDBG_FULL((const u8*)(&as->addr)),
+ rssi, as->reason));
+ }
+}
+
+static void
+wl_cfgvendor_advlog_auth_assoc(wl_assoc_status_t *as, uint32 rssi)
+{
+ const char *req_str = NULL;
+ const char *resp_str = NULL;
+ const char *status_str = NULL;
+ const wl_event_msg_t *e;
+
+ e = as->event_msg;
+
+ if (as->status == WLC_E_STATUS_ABORT ||
+ as->status == WLC_E_STATUS_UNSOLICITED) {
+ WL_DBG(("This event was aborted or unsolicited for Auth/Assoc.\n"));
+ return;
+ }
+
+ req_str = get_advlog_val(wl_advlog_auth_assoc_req,
+ ARRAY_SIZE(wl_advlog_auth_assoc_req), as->event_type);
+
+ status_str = get_advlog_val(wl_advlog_tx_status,
+ ARRAY_SIZE(wl_advlog_tx_status), as->status);
+ if (!req_str || !status_str) {
+ WL_ERR(("map arr not found type:%d status:%d\n", as->event_type, as->status));
+ return;
+ }
+
+ /* do not print to the kernel, only for framework (MACDBG_FULL) */
+ SUPP_ADVLOG((req_str, MAC2STRDBG_FULL((const u8*)(&e->addr)),
+ rssi, ntoh32(e->auth_type), status_str));
+
+ if (as->status == WLC_E_STATUS_SUCCESS ||
+ as->status == WLC_E_STATUS_FAIL) {
+ resp_str = get_advlog_val(wl_advlog_auth_assoc_resp,
+ ARRAY_SIZE(wl_advlog_auth_assoc_resp), as->event_type);
+ if (!resp_str) {
+ WL_ERR(("resp map arr not found type:%d\n", as->event_type));
+ return;
+ }
+ /* do not print to the kernel, only for framework (MACDBG_FULL) */
+ SUPP_ADVLOG((resp_str, MAC2STRDBG_FULL((const u8*)(&e->addr)),
+ ntoh32(e->auth_type), as->reason));
+ }
+
+ return;
+}
+
+void
+wl_cfgvendor_advlog_connect_event(wl_assoc_status_t *as, bool query_rssi, int pre_rssi)
+{
+ s32 err = BCME_OK;
+ scb_val_t scbval;
+
+ if (!as->ndev) {
+ WL_ERR(("ndev is null\n"));
+ return;
+ }
+
+ if (query_rssi == TRUE && pre_rssi == WLC_RSSI_INVALID) {
+ /* get rssi value */
+ bzero(&scbval, sizeof(scb_val_t));
+ err = wldev_get_rssi(as->ndev, &scbval);
+ if (unlikely(err)) {
+ WL_ERR(("get_rssi error (%d)\n", err));
+ scbval.val = WLC_RSSI_INVALID;
+ }
+ } else {
+ scbval.val = pre_rssi;
+ }
+
+ /* Handle FW events */
+ switch (as->event_type) {
+ case WLC_E_AUTH:
+ case WLC_E_ASSOC:
+ wl_cfgvendor_advlog_auth_assoc(as, scbval.val);
+ break;
+ case WLC_E_DISASSOC:
+ case WLC_E_DISASSOC_IND:
+ case WLC_E_DEAUTH:
+ case WLC_E_DEAUTH_IND:
+ wl_cfgvendor_advlog_deauth_disassoc(as, scbval.val);
+ break;
+ default:
+ WL_DBG(("Ignore event:%d\n", as->event_type));
+ }
+}
+
+void
+wl_cfgvendor_advlog_disassoc_tx(struct bcm_cfg80211 *cfg, struct net_device *ndev,
+ uint32 reason, int rssi)
+{
+ dhd_pub_t *dhdp = (dhd_pub_t *)(cfg->pub);
+ wl_assoc_status_t as;
+ s32 ifidx = DHD_BAD_IF;
+ u8 *curbssid = wl_read_prof(cfg, ndev, WL_PROF_BSSID);
+ struct ether_addr fw_bssid;
+ int err;
+
+ /* In DEAUTH_IND or Beacon loss cases, we already lost contact */
+ bzero(&fw_bssid, sizeof(fw_bssid));
+ err = wldev_ioctl_get(ndev, WLC_GET_BSSID, &fw_bssid, ETHER_ADDR_LEN);
+ if (err) {
+ WL_ERR(("not inform disassoc for already disconnected\n"));
+ return;
+ }
+
+ if (!curbssid) {
+ WL_ERR(("No bssid found\n"));
+ return;
+ }
+
+ ifidx = dhd_net2idx(dhdp->info, ndev);
+ /* Advanced Logging supports only STA mode */
+ if (!DHD_IF_ROLE_STA(dhdp, ifidx)) {
+ return;
+ }
+
+ bzero(&as, sizeof(wl_assoc_status_t));
+ as.ndev = ndev;
+ if (memcpy_s(as.addr, ETH_ALEN, curbssid, ETH_ALEN)) {
+ WL_ERR(("failed to memcpy bssid\n"));
+ return;
+ }
+
+ /* Nomally, FW sends WLC_E_DISASSOC event twice
+ * to avoid printing twice, move it in WLC_DISASSOC sending path
+ * Set WLC_E_DISASSOC forcely instead of WLC_DISASSOC
+ */
+ as.event_type = WLC_E_DISASSOC;
+ as.reason = reason;
+ wl_cfgvendor_advlog_connect_event(&as, FALSE, rssi);
+}
+
+static s32
+wl_cfgvendor_advlog_get_target_rssi(struct bcm_cfg80211 *cfg, struct net_device *ndev,
+ int *rssi)
+{
+ s32 err = BCME_OK;
+ wl_bss_info_v109_t *bi;
+ char *buf = NULL;
+
+ buf = (char *)MALLOCZ(cfg->osh, WL_EXTRA_BUF_MAX);
+ if (!buf) {
+ WL_ERR(("buffer alloc failed.\n"));
+ return BCME_NOMEM;
+ }
+
+ *(u32 *)buf = htod32(WL_EXTRA_BUF_MAX);
+ err = wldev_iovar_getbuf(ndev, "target_bss_info", NULL, 0,
+ buf, WL_EXTRA_BUF_MAX, NULL);
+ if (unlikely(err)) {
+ WL_ERR(("Could not get bss info %d\n", err));
+ err = BCME_ERROR;
+ goto exit;
+ }
+
+ bi = (wl_bss_info_v109_t *)(buf + sizeof(uint32));
+ *rssi = bi->RSSI;
+
+exit:
+ MFREE(cfg->osh, buf, WL_EXTRA_BUF_MAX);
+ return err;
+}
+
+#endif /* WL_CFGVENDOR_CUST_ADVLOG */
+
static s32
wl_handle_assoc_events(struct bcm_cfg80211 *cfg,
struct wireless_dev *wdev, const wl_event_msg_t *e,
@@ -12729,6 +13352,13 @@
{
s32 err = BCME_OK;
wl_assoc_status_t as;
+ s32 advlog_err = BCME_OK;
+ int target_rssi = WLC_RSSI_INVALID;
+ bool query_rssi = TRUE;
+
+ BCM_REFERENCE(advlog_err);
+ BCM_REFERENCE(target_rssi);
+ BCM_REFERENCE(query_rssi);
if (!wdev || !e) {
WL_ERR(("wrong input\n"));
@@ -12752,6 +13382,22 @@
as.ndev->name, as.assoc_state, as.event_type, as.status, as.reason,
cfg->eidx.in_progress, MAC2STRDBG((const u8*)(&e->addr))));
+#ifdef WL_CFGVENDOR_CUST_ADVLOG
+ if (as.event_type == WLC_E_AUTH || as.event_type == WLC_E_ASSOC) {
+ /* In AUTH/ASSOC REQ, FW doesn't have rssi in moving average windows
+ * so, WLC_GET_RSSI(IOVAR) result will return zero
+ * Try to get rssi from target_bss when state is not ASSOCIATED
+ * If it failed, allow to get rssi from WLC_GET_RSSI
+ */
+ advlog_err = wl_cfgvendor_advlog_get_target_rssi(cfg, wdev->netdev,
+ &target_rssi);
+ if (advlog_err == BCME_OK) {
+ query_rssi = FALSE;
+ }
+ }
+ wl_cfgvendor_advlog_connect_event(&as, query_rssi, target_rssi);
+#endif /* WL_CFGVENDOR_CUST_ADVLOG */
+
/* Handle FW events */
switch (as.event_type) {
case WLC_E_AUTH:
@@ -12788,7 +13434,6 @@
case WLC_E_DISASSOC_IND:
wl_cfg80211_handle_deauth_ind(cfg, &as);
/* intentional fall through */
- case WLC_E_DISASSOC:
case WLC_E_DEAUTH:
as.link_action = wl_set_link_action(assoc_state, false);
break;
@@ -12812,6 +13457,26 @@
return err;
}
+void
+wl_handle_unexpected_assoc_states(struct bcm_cfg80211 *cfg,
+ struct wireless_dev *wdev, const wl_event_msg_t *e,
+ void *data, wl_assoc_state_t assoc_state)
+{
+ struct net_device *ndev = wdev->netdev;
+ u32 event = ntoh32(e->event_type);
+ u16 flags = ntoh16(e->flags);
+
+ if ((assoc_state == WL_STATE_ASSOC_IDLE) &&
+ (((event == WLC_E_LINK) && (flags & WLC_EVENT_MSG_LINK)) ||
+ (event == WLC_E_ROAM) || (event == WLC_E_BSSID))) {
+ /* If link up/roam events are received, issue disassoc to
+ * firwmware to sync up the states.
+ */
+ WL_ERR(("event_type:%d in assoc idle state. force sync fw state\n", event));
+ wl_cfg80211_disassoc(ndev, WLAN_REASON_DEAUTH_LEAVING);
+ }
+}
+
#define IS_OBSOLETE_EVENT(cur_idx, marker_idx) ((s32)(cur_idx - marker_idx) < 0)
static s32
wl_notify_connect_status_sta(struct bcm_cfg80211 *cfg,
@@ -12821,19 +13486,21 @@
wl_assoc_state_t assoc_state;
struct net_device *ndev;
s32 ret = BCME_OK;
- wl_event_idx_t *idx = &cfg->eidx;
+ wl_event_idx_t *idx;
if (!wdev || !e) {
WL_ERR(("wrong input\n"));
return -EINVAL;
}
+ mutex_lock(&cfg->connect_sync);
+ idx = &cfg->eidx;
event_type = ntoh32(e->event_type);
if (IS_OBSOLETE_EVENT(idx->in_progress, idx->min_connect_idx)) {
/* If this event is enqd before the connect req, discard */
WL_ERR(("discard obsolete event:%d. cur_idx:%d min_idx:%d\n",
event_type, idx->in_progress, idx->min_connect_idx));
- return -EINVAL;
+ goto exit;
}
ndev = wdev->netdev;
@@ -12853,10 +13520,18 @@
} else {
WL_ERR(("Unexpected event:%d in assoc idle state\n", event_type));
assoc_state = WL_STATE_ASSOC_IDLE;
+ wl_handle_unexpected_assoc_states(cfg, wdev, e, data, assoc_state);
+ ret = -EINVAL;
+ goto exit;
}
- ret = wl_handle_assoc_events(cfg, wdev, e, data, assoc_state);
+ /* Free up lock so that there is no conflict with post processing */
+ mutex_unlock(&cfg->connect_sync);
+
+ return wl_handle_assoc_events(cfg, wdev, e, data, assoc_state);
+
exit:
+ mutex_unlock(&cfg->connect_sync);
return ret;
}
@@ -12944,7 +13619,7 @@
if (datalen) {
wl_roam_exp_event_t *evt_data = (wl_roam_exp_event_t *)data;
- if (evt_data->version == ROAM_EXP_EVENT_VERSION) {
+ if (evt_data->version == ROAM_EXP_EVENT_VERSION_1) {
wlc_ssid_t *ssid = &evt_data->cur_ssid;
struct wireless_dev *wdev;
ndev = cfgdev_to_wlc_ndev(cfgdev, cfg);
@@ -12959,7 +13634,7 @@
}
} else {
WL_ERR(("Version mismatch %d, expected %d", evt_data->version,
- ROAM_EXP_EVENT_VERSION));
+ ROAM_EXP_EVENT_VERSION_1));
}
}
return BCME_OK;
@@ -12978,7 +13653,7 @@
if (datalen) {
wl_rssi_monitor_evt_t *evt_data = (wl_rssi_monitor_evt_t *)data;
- if (evt_data->version == RSSI_MONITOR_VERSION) {
+ if (evt_data->version == RSSI_MONITOR_VERSION_1) {
dhd_rssi_monitor_evt_t monitor_data;
monitor_data.version = DHD_RSSI_MONITOR_EVT_VERSION;
monitor_data.cur_rssi = evt_data->cur_rssi;
@@ -12988,7 +13663,7 @@
&monitor_data, sizeof(monitor_data));
} else {
WL_ERR(("Version mismatch %d, expected %d", evt_data->version,
- RSSI_MONITOR_VERSION));
+ RSSI_MONITOR_VERSION_1));
}
}
#endif /* WL_VENDOR_EXT_SUPPORT || CONFIG_BCMDHD_VENDOR_EXT */
@@ -13147,6 +13822,7 @@
#define DPM_MAX_CONT_EVT_CNT (5u) /* 120sec * 5times = 10min */
#define DPM_MIN_CONT_EVT_INTV (1000u) /* 1000ms */
#define DPM_MAX_INACT_CNT (CUSTOM_EVENT_PM_WAKE * 4 * 6) /* 6 pkts/sec */
+#define DPM_LMT_RSSI -80 /* dbm */
static void
wl_check_pmstatus_memdump(struct bcm_cfg80211 *cfg, struct net_device *ndev,
@@ -13156,6 +13832,8 @@
int val = 0, core_idx = -1;
dhd_pub_t *dhd = NULL;
+ BCM_REFERENCE(dhd);
+
val = wl_return_from_ndev_to_coreidx(cfg, ndev);
if (val < BCME_OK) {
return;
@@ -13177,28 +13855,32 @@
if (cur_pm_dur - dpm_info->dpm_prev_pmdur < DPM_MIN_CONT_EVT_INTV) {
dpm_info->dpm_cont_evt_cnt++;
- WL_INFORM(("Updated DPM event counter for %s(%d)\n",
+ WL_INFORM(("Updated DPM event counter for %s(%d).\n",
ndev->name, dpm_info->dpm_cont_evt_cnt));
- if (dpm_info->dpm_cont_evt_cnt >= DPM_MAX_CONT_EVT_CNT) {
-#if defined(CUSTOM_EVENT_PM_WAKE_MEMDUMP_DISABLED)
- WL_ERR(("[%s] Force Disassoc due to updated DPM event (PM)\n",
- ndev->name));
- wl_cfg80211_disassoc(ndev, WLAN_REASON_DEAUTH_LEAVING);
-#else /* CUSTOM_EVENT_PM_WAKE_MEMDUMP_DISABLED */
-#if defined(DHD_FW_COREDUMP)
- if (dhd->memdump_enabled) {
+ if (dpm_info->dpm_cont_evt_cnt == DPM_MAX_CONT_EVT_CNT) {
+ scb_val_t scb_val;
+ s32 rssi = DPM_LMT_RSSI;
+
+ val = wldev_ioctl_get(ndev, WLC_GET_RSSI, &scb_val, sizeof(scb_val_t));
+ if (val) {
+ WL_ERR(("Could not get rssi(%d)\n", val));
+ } else {
+ rssi = wl_rssi_offset(dtoh32(scb_val.val));
+ }
+
+ WL_INFORM(("DPM event RSSI (%d)\n", rssi));
+#if defined(DHD_FW_COREDUMP) && !defined(CUSTOM_EVENT_PM_WAKE_MEMDUMP_DISABLED)
+ if (dhd->memdump_enabled && (rssi > DPM_LMT_RSSI)) {
dhd->memdump_type = DUMP_TYPE_CONT_EXCESS_PM_AWAKE;
dhd_bus_mem_dump(dhd);
}
-#endif /* DHD_FW_COREDUMP */
- WL_ERR(("[%s] Force hang event due to updated DPM event.\n",
+#endif /* DHD_FW_COREDUMP && !CUSTOM_EVENT_PM_WAKE_MEMDUMP_DISABLED */
+ }
+ if (dpm_info->dpm_cont_evt_cnt > DPM_MAX_CONT_EVT_CNT) {
+ WL_ERR(("[%s] Force Disassoc due to updated DPM event.\n",
ndev->name));
-#if defined(BCMDONGLEHOST)
- dhd->hang_reason = HANG_REASON_SLEEP_FAILURE;
- net_os_send_hang_message(bcmcfg_to_prmry_ndev(cfg));
-#endif /* BCMDONGLEHOST && OEM_ANDROID */
-#endif /* CUSTOM_EVENT_PM_WAKE_MEMDUMP_DISABLED */
+ wl_cfg80211_disassoc(ndev, WLAN_REASON_DEAUTH_LEAVING);
dpm_info->dpm_cont_evt_cnt = 0;
}
} else {
@@ -13270,9 +13952,7 @@
total_pkts = dtoh32(wlc_cnt->txfrmsnt) +
dtoh32(wlc_cnt->rxframe) + dtoh32(wlc_cnt->rxmulti);
- if (dhd->early_suspended) {
- wl_check_pmstatus_memdump(cfg, ndev, pm_dur, total_pkts);
- }
+ wl_check_pmstatus_memdump(cfg, ndev, pm_dur, total_pkts);
exit:
if (iovar_buf) {
@@ -13296,10 +13976,10 @@
wl_pmalert_t *pm_alert = (wl_pmalert_t *) data;
wdev = wl_get_wdev_by_fw_idx(cfg, e->bsscfgidx, e->ifidx);
- WL_INFORM_MEM(("wl_check_pmstatus: wdev found! bssidx: %d, ifidx: %d\n",
+ WL_INFORM_MEM(("wl_check_pmstatus: wdev found! bssidx: %d, ifidx: %d",
e->bsscfgidx, e->ifidx));
if (wdev == NULL || wdev->netdev == NULL) {
- WL_ERR(("No wdev/ndev corresponding to bssidx: 0x%x found!\n",
+ WL_ERR(("No wdev/ndev corresponding to bssidx: 0x%x found!",
e->bsscfgidx));
return -EINVAL;
}
@@ -13331,12 +14011,9 @@
}
#endif /* DHD_FW_COREDUMP */
-#if defined(BCMDONGLEHOST)
- dhd->hang_reason = HANG_REASON_SLEEP_FAILURE;
- net_os_send_hang_message(bcmcfg_to_prmry_ndev(cfg));
-#endif /* BCMDONGLEHOST && OEM_ANDROID */
+ wl_cfg80211_handle_hang_event(ndev,
+ HANG_REASON_SLEEP_FAILURE, DUMP_TYPE_DONGLE_HOST_EVENT);
#endif /* CUSTOM_EVENT_PM_WAKE_MEMDUMP_DISABLED */
- return err;
}
/* Dump PM status */
@@ -13467,6 +14144,7 @@
wl_assoc_info_t assoc_info;
struct wl_connect_info *conn_info = wl_to_conn(cfg);
s32 err = 0;
+ struct wl_security *sec;
#ifdef QOS_MAP_SET
bcm_tlv_t * qos_map_ie = NULL;
#endif /* QOS_MAP_SET */
@@ -13517,6 +14195,12 @@
conn_info->req_ie_len, MAX_REQ_LINE));
return err;
}
+ sec = wl_read_prof(cfg, ndev, WL_PROF_SEC);
+ /* Update security wpa_auth for seamless roam, wpa_auth was earlier set to 0 */
+ if (sec->wpa_auth == 0) {
+ wl_update_akm_from_assoc_ie(cfg, ndev, conn_info->req_ie,
+ conn_info->req_ie_len);
+ }
} else {
conn_info->req_ie_len = 0;
}
@@ -13578,7 +14262,7 @@
bool update_ssid, u8 *target_bssid)
{
struct cfg80211_bss *bss;
- wl_bss_info_t *bi;
+ wl_bss_info_v109_t *bi;
struct wlc_ssid *ssid;
const struct bcm_tlv *tim;
s32 beacon_interval;
@@ -13621,8 +14305,14 @@
WL_ERR(("Could not get bss info %d\n", err));
goto update_bss_info_out;
}
- bi = (wl_bss_info_t *)(buf + 4);
+ bi = (wl_bss_info_v109_t *)(buf + 4);
chspec = wl_chspec_driver_to_host(bi->chanspec);
+ /* chanspec queried for ASSOCIATED BSSID needs to be valid */
+ if (!(target_bssid) && !wf_chspec_valid(chspec)) {
+ WL_ERR(("Invalid chanspec from get bss info %x\n", chspec));
+ err = BCME_BADCHAN;
+ goto update_bss_info_out;
+ }
wl_update_prof(cfg, ndev, NULL, &chspec, WL_PROF_CHAN);
if (!bss) {
@@ -13701,7 +14391,6 @@
s32 err = 0;
u8 *curbssid;
chanspec_t *chanspec;
- scb_val_t scbval;
#if (LINUX_VERSION_CODE > KERNEL_VERSION(2, 6, 39)) || defined(WL_COMPAT_WIRELESS)
struct wiphy *wiphy = bcmcfg_to_wiphy(cfg);
struct ieee80211_channel *notify_channel = NULL;
@@ -13768,17 +14457,6 @@
#endif /* BCMDONGLEHOST */
WL_ERR(("Fetching Assoc IEs failed, Skipping roamed event to"
" upper layer\n"));
- /* To make sure disconnect, and fw sync, explictly send dissassoc
- * for BSSID 00:00:00:00:00:00 issue
- */
- bzero(&scbval, sizeof(scb_val_t));
- scbval.val = WLAN_REASON_DEAUTH_LEAVING;
- memcpy(&scbval.ea, curbssid, ETHER_ADDR_LEN);
- scbval.val = htod32(scbval.val);
- if (wldev_ioctl_set(ndev, WLC_DISASSOC, &scbval,
- sizeof(scb_val_t)) < 0) {
- WL_ERR(("WLC_DISASSOC error\n"));
- }
goto fail;
}
@@ -13794,8 +14472,18 @@
chanspec = (chanspec_t *)wl_read_prof(cfg, ndev, WL_PROF_CHAN);
#if (LINUX_VERSION_CODE > KERNEL_VERSION(2, 6, 39)) || defined(WL_COMPAT_WIRELESS)
/* channel info for cfg80211_roamed introduced in 2.6.39-rc1 */
+ if (!wf_chspec_valid(*chanspec)) {
+ WL_ERR(("Invalid chanspec (%x) for roam, triggering a disassoc\n", *chanspec));
+ err = BCME_BADCHAN;
+ goto fail;
+ }
freq = wl_channel_to_frequency(wf_chspec_ctlchan(*chanspec), CHSPEC_BAND(*chanspec));
notify_channel = ieee80211_get_channel(wiphy, freq);
+ if (notify_channel == NULL) {
+ WL_ERR(("Invalid roam notify channel\n"));
+ err = BCME_BADCHAN;
+ goto fail;
+ }
#endif /* LINUX_VERSION > 2.6.39 || WL_COMPAT_WIRELESS */
#ifdef WLFBT
/* back up the given FBT key for the further supplicant request,
@@ -13862,6 +14550,10 @@
return err;
fail:
+ /* Trigger a disassoc to avoid state mismatch between driver and upper
+ * layers, since we skip roam indication to upper layers in fail: handling
+ */
+ wl_cfg80211_disassoc(ndev, WLAN_REASON_DEAUTH_LEAVING);
#ifdef DHD_LOSSLESS_ROAMING
wl_del_roam_timeout(cfg);
#endif /* DHD_LOSSLESS_ROAMING */
@@ -13922,7 +14614,7 @@
err = BCME_NOMEM;
goto exit;
}
- iov_buf_out.version = WL_FILS_IOV_VERSION;
+ iov_buf_out.version = WL_FILS_IOV_VERSION_1_1;
iov_buf_out.id = WL_FILS_CMD_GET_CONNECT_PARAMS;
err = wldev_iovar_getbuf(ndev, "fils", (uint8*)&iov_buf_out, sizeof(bcm_iov_buf_t),
iov_buf_in, WLC_IOCTL_SMLEN, &cfg->ioctl_buf_sync);
@@ -14101,7 +14793,10 @@
* For cases, there is no match available,
* need to update the cache based on bss info from fw.
*/
- wl_update_bss_info(cfg, ndev, true, NULL);
+ if ((err = wl_update_bss_info(cfg, ndev, true, NULL)) != BCME_OK) {
+ WL_ERR(("failed to update bss info, err=%d\n", err));
+ goto exit;
+ }
if (cfg->wlc_ver.wlc_ver_major < PMKDB_WLC_VER) {
wl_update_pmklist(ndev, cfg->pmk_list, err);
}
@@ -14140,7 +14835,6 @@
} else {
status = WLAN_STATUS_UNSPECIFIED_FAILURE;
}
-
#ifdef WL_FILS
if ((sec->auth_type == NL80211_AUTHTYPE_FILS_SK_PFS) ||
(sec->auth_type == NL80211_AUTHTYPE_FILS_SK)) {
@@ -14217,27 +14911,9 @@
return 0;
}
-#ifdef BT_WIFI_HANDOVER
-static s32
-wl_notify_bt_wifi_handover_req(struct bcm_cfg80211 *cfg, bcm_struct_cfgdev *cfgdev,
- const wl_event_msg_t *e, void *data)
-{
- struct net_device *ndev = NULL;
- u32 event = ntoh32(e->event_type);
- u32 datalen = ntoh32(e->datalen);
- s32 err;
-
- WL_ERR(("wl_notify_bt_wifi_handover_req: event_type : %d, datalen : %d\n", event, datalen));
- ndev = cfgdev_to_wlc_ndev(cfgdev, cfg);
- err = wl_genl_send_msg(ndev, event, data, (u16)datalen, 0, 0);
-
- return err;
-}
-#endif /* BT_WIFI_HANDOVER */
-
#ifdef WL_CFG80211_GON_COLLISION
static void
-wl_gon_req_collision(struct bcm_cfg80211 *cfg, wl_action_frame_t *tx_act_frm,
+wl_gon_req_collision(struct bcm_cfg80211 *cfg, wl_action_frame_v1_t *tx_act_frm,
wifi_p2p_pub_act_frame_t *rx_act_frm, struct net_device *ndev,
struct ether_addr sa, struct ether_addr da)
{
@@ -14501,19 +15177,22 @@
freq = wl_channel_to_frequency(wf_chspec_ctlchan(chspec), CHSPEC_BAND(chspec));
#endif
if (event == WLC_E_ACTION_FRAME_RX) {
- u8 ioctl_buf[WLC_IOCTL_SMLEN];
- if ((err = wldev_iovar_getbuf_bsscfg(ndev, "cur_etheraddr",
- NULL, 0, ioctl_buf, sizeof(ioctl_buf), bsscfgidx,
- NULL)) != BCME_OK) {
- WL_ERR(("WLC_GET_CUR_ETHERADDR failed, error %d\n", err));
- goto exit;
+ {
+ u8 ioctl_buf[WLC_IOCTL_SMLEN];
+ if ((err = wldev_iovar_getbuf_bsscfg(ndev, "cur_etheraddr",
+ NULL, 0, ioctl_buf, sizeof(ioctl_buf), bsscfgidx,
+ NULL)) != BCME_OK) {
+ WL_ERR(("WLC_GET_CUR_ETHERADDR failed, error %d\n", err));
+ goto exit;
+ }
+ eacopy(ioctl_buf, da.octet);
}
-
- err = wldev_ioctl_get(ndev, WLC_GET_BSSID, &bssid, ETHER_ADDR_LEN);
- if ((err < 0) && (err != BCME_NOTASSOCIATED)) {
- WL_ERR(("WLC_GET_BSSID error %d\n", err));
+ {
+ err = wldev_ioctl_get(ndev, WLC_GET_BSSID, &bssid, ETHER_ADDR_LEN);
+ if ((err < 0) && (err != BCME_NOTASSOCIATED)) {
+ WL_ERR(("WLC_GET_BSSID error %d\n", err));
+ }
}
- memcpy(da.octet, ioctl_buf, ETHER_ADDR_LEN);
if ((ndev->ieee80211_ptr->iftype == NL80211_IFTYPE_STATION) &&
cfg->randomized_gas_tx) {
@@ -14991,9 +15670,14 @@
#ifdef PNO_SUPPORT
cfg->evt_handler[WLC_E_PFN_NET_FOUND] = wl_notify_pfn_status;
#endif /* PNO_SUPPORT */
+#ifdef WL_SCHED_SCAN
+ cfg->evt_handler[WLC_E_PFN_PARTIAL_RESULT] = wl_cfgscan_pfn_scanresult_handler;
+#endif /* WL_SCHED_SCAN */
+#if defined(GSCAN_SUPPORT) || defined(WL_SCHED_SCAN)
+ cfg->evt_handler[WLC_E_PFN_SCAN_COMPLETE] = wl_cfgscan_notify_pfn_complete;
+#endif /* GSCAN_SUPPORT || WL_SCHED_SCAN */
#ifdef GSCAN_SUPPORT
cfg->evt_handler[WLC_E_PFN_BEST_BATCHING] = wl_notify_gscan_event;
- cfg->evt_handler[WLC_E_PFN_SCAN_COMPLETE] = wl_notify_gscan_event;
cfg->evt_handler[WLC_E_PFN_GSCAN_FULL_RESULT] = wl_notify_gscan_event;
cfg->evt_handler[WLC_E_PFN_BSSID_NET_FOUND] = wl_notify_gscan_event;
cfg->evt_handler[WLC_E_PFN_BSSID_NET_LOST] = wl_notify_gscan_event;
@@ -15016,9 +15700,6 @@
#ifdef WL_RELMCAST
cfg->evt_handler[WLC_E_RMC_EVENT] = wl_notify_rmc_status;
#endif /* WL_RELMCAST */
-#ifdef BT_WIFI_HANDOVER
- cfg->evt_handler[WLC_E_BT_WIFI_HANDOVER_REQ] = wl_notify_bt_wifi_handover_req;
-#endif
#ifdef WL_NAN
cfg->evt_handler[WLC_E_NAN_CRITICAL] = wl_cfgnan_notify_nan_status;
cfg->evt_handler[WLC_E_NAN_NON_CRITICAL] = wl_cfgnan_notify_nan_status;
@@ -15127,7 +15808,7 @@
{
WL_DBG(("Enter \n"));
- cfg->scan_results = (wl_scan_results_t *)MALLOCZ(cfg->osh,
+ cfg->scan_results = (wl_scan_results_v109_t *)MALLOCZ(cfg->osh,
WL_SCAN_BUF_MAX);
if (unlikely(!cfg->scan_results)) {
WL_ERR(("Scan results alloc failed\n"));
@@ -15319,10 +16000,20 @@
#endif /* DHD_LOSSLESS_ROAMING */
-#if defined(CONFIG_WLAN_BEYONDX) || defined(CONFIG_SEC_5GMODEL)
+#ifdef WL_CP_COEX
#define CP_CHAN_INFO_RAT_MODE_LTE 3
#define CP_CHAN_INFO_RAT_MODE_NR5G 7
-int g_mhs_chan_for_cpcoex = 0;
+struct wl_cp_coex g_cx;
+
+#define CP_N40_FREQ_STR 460000u
+#define CP_N40_FREQ_END 480000u
+#define CP_N41_FREQ_STR 499200u
+#define CP_N41_FREQ_END 537999u
+
+#define CP_B40_FREQ_STR 38650u
+#define CP_B40_FREQ_END 39649u
+#define CP_B41_FREQ_STR 39650u
+#define CP_B41_FREQ_END 41589u
struct __packed cam_cp_noti_info {
u8 rat;
@@ -15331,13 +16022,13 @@
};
int
-wl_cfg80211_send_msg_to_ril()
+wl_cfg80211_send_msg_to_ril(void)
{
int id, buf = 1;
id = IPC_SYSTEM_CP_CHANNEL_INFO;
dev_ril_bridge_send_msg(id, sizeof(int), &buf);
- WL_ERR(("[BeyondX] send message to ril.\n"));
+ WL_ERR(("[CP_COEX] send message to ril.\n"));
OSL_SLEEP(500);
return 0;
@@ -15349,10 +16040,8 @@
{
struct dev_ril_bridge_msg *msg;
struct cam_cp_noti_info *cp_noti_info;
- static int mhs_channel_for_4g, mhs_channel_for_5g;
- static int recv_msg_4g, recv_msg_5g;
- WL_ERR(("[BeyondX] receive message from ril.\n"));
+ WL_ERR(("[CP_COEX] receive message from ril.\n"));
msg = (struct dev_ril_bridge_msg *)buf;
if (msg->dev_id == IPC_SYSTEM_CP_CHANNEL_INFO &&
@@ -15369,42 +16058,45 @@
/* LTE/5G Band/Freq information => Mobile Hotspot channel mapping.
* LTE/B40: 38650~39649 => Ch.11
* LTE/B41: 39650~41589 => Ch.1
+ * 5G/N40: 460000~480000 => Ch.11
* 5G/N41: 499200~537999 => Ch.1
*/
if (rat == CP_CHAN_INFO_RAT_MODE_LTE) {
- recv_msg_4g = 1;
- if (channel >= 38650 && channel <= 39649) {
- mhs_channel_for_4g = 11;
- } else if (channel >= 39650 && channel <= 41589) {
- mhs_channel_for_4g = 1;
+ if (channel >= CP_B40_FREQ_STR && channel <= CP_B40_FREQ_END) {
+ g_cx.ch_4g = 11;
+ } else if (channel >= CP_B41_FREQ_STR && channel <= CP_B41_FREQ_END) {
+ g_cx.ch_4g = 1;
}
- }
- if (rat == CP_CHAN_INFO_RAT_MODE_NR5G) {
- recv_msg_5g = 1;
- if (channel >= 499200 && channel <= 537999) {
- mhs_channel_for_5g = 1;
+ } else if (rat == CP_CHAN_INFO_RAT_MODE_NR5G) {
+ if (channel >= CP_N40_FREQ_STR && channel <= CP_N40_FREQ_END) {
+ g_cx.ch_5g = 11;
+ } else if (channel >= CP_N41_FREQ_STR && channel <= CP_N41_FREQ_END) {
+ g_cx.ch_5g = 1;
}
+ } else {
+ WL_ERR(("[CP_COEX] Not interested packet. rat:%u, band:%u, channel:%u\n",
+ rat, band, channel));
+ return 0;
}
- WL_DBG(("[BeyondX] rat: %u, band: %u, channel: %u, mhs_channel_for_4g: %u, "
- "mhs_channel_for_5g: %u\n", rat, band, channel,
- mhs_channel_for_4g, mhs_channel_for_5g));
+ WL_ERR(("[CP_COEX] rat:%u, band:%u, channel:%u, ch_4g:%d, ch_5g:%d\n",
+ rat, band, channel, g_cx.ch_4g, g_cx.ch_5g));
- if (recv_msg_4g && recv_msg_5g) {
- if (mhs_channel_for_4g && mhs_channel_for_5g) {
- /* if 4G/B40 + 5G/N41, select channel 6 for MHS */
- if (mhs_channel_for_4g == 11 && mhs_channel_for_5g == 1) {
- g_mhs_chan_for_cpcoex = 6;
- /* if 4G(except for B40) + 5G/N41, select channel 1 for MHS */
- } else {
- g_mhs_chan_for_cpcoex = 1;
- }
+ /* only consider 4G or 5G */
+ if (g_cx.ch_4g && g_cx.ch_5g) {
+ /* if 4G/B40 + 5G/N41 or 4G/B41 + 5GN40, select channel 6 for MHS
+ * if ch_4g != ch_5g then select Ch.6 else then Ch.1
+ */
+ if ((g_cx.ch_4g == 11 && g_cx.ch_5g == 1) ||
+ (g_cx.ch_4g == 1 && g_cx.ch_5g == 11)) {
+ g_cx.ch_cpcoex = 6;
+ /* select channel 1 for other case */
} else {
- g_mhs_chan_for_cpcoex = mhs_channel_for_4g ? mhs_channel_for_4g :
- mhs_channel_for_5g ? mhs_channel_for_5g : 0;
+ g_cx.ch_cpcoex = 1;
}
- mhs_channel_for_4g = mhs_channel_for_5g = 0;
- recv_msg_4g = recv_msg_5g = 0;
+ } else {
+ g_cx.ch_cpcoex = g_cx.ch_4g ? g_cx.ch_4g :
+ g_cx.ch_5g ? g_cx.ch_5g : 0;
}
}
@@ -15416,7 +16108,7 @@
};
static bool wl_cfg80211_ril_bridge_notifier_registered = FALSE;
-#endif /* CONFIG_WLAN_BEYONDX || defined(CONFIG_SEC_5GMODEL) */
+#endif /* WL_CP_COEX */
static s32
wl_cfg80211_netdev_notifier_call(struct notifier_block * nb,
@@ -15610,7 +16302,7 @@
(s32 *)&chanspec) == BCME_OK) {
chanspec = wl_chspec_driver_to_host(chanspec);
ctl_chan = wf_chspec_ctlchan(chanspec);
- band = CHSPEC_BAND(chanspec);
+ band = CHSPEC_TO_WLC_BAND(CHSPEC_BAND(chanspec));
wl_update_prof(cfg, iter->ndev, NULL,
&chanspec, WL_PROF_CHAN);
}
@@ -15639,7 +16331,7 @@
u32 band = 0;
u32 pre_band = INVCHANSPEC;
bool is_rsdb_supported = FALSE;
- bool rsdb_or_scc_mode = FALSE;
+ bool rsdb_or_scc_mode = TRUE;
#ifdef BCMDONGLEHOST
is_rsdb_supported = DHD_OPMODE_SUPPORTED(cfg->pub, DHD_FLAG_RSDB_MODE);
@@ -15660,7 +16352,7 @@
if (wldev_iovar_getint(iter->ndev, "chanspec",
(s32 *)&chanspec) == BCME_OK) {
chanspec = wl_chspec_driver_to_host(chanspec);
- band = CHSPEC_BAND(chanspec);
+ band = CHSPEC_TO_WLC_BAND(CHSPEC_BAND(chanspec));
}
if (pre_band == INVCHANSPEC && chanspec) {
@@ -15670,9 +16362,6 @@
if ((pre_band == band) && (pre_chanspec != chanspec)) {
/* VSDB case */
rsdb_or_scc_mode = FALSE;
- } else {
- /* RSDB/SCC case */
- rsdb_or_scc_mode = TRUE;
}
}
}
@@ -16037,7 +16726,6 @@
}
}
}
- wl_set_drv_status(cfg, READY, ndev);
fail:
return err;
}
@@ -16147,11 +16835,9 @@
}
}
-#if defined(COEX_DHCP)
cfg->btcoex_info = wl_cfg80211_btcoex_init(cfg->wdev->netdev);
if (!cfg->btcoex_info)
goto cfg80211_attach_out;
-#endif
#if defined(SUPPORT_RANDOM_MAC_SCAN)
cfg->random_mac_enabled = FALSE;
@@ -16222,10 +16908,8 @@
*/
wl_add_remove_pm_enable_work(cfg, WL_PM_WORKQ_DEL);
-#if defined(COEX_DHCP)
wl_cfg80211_btcoex_deinit();
cfg->btcoex_info = NULL;
-#endif
wl_setup_rfkill(cfg, FALSE);
@@ -16270,8 +16954,8 @@
WL_DBG(("Exit\n"));
}
-#if defined(CONFIG_WLAN_BEYONDX) || defined(CONFIG_SEC_5GMODEL)
-void wl_cfg80211_register_dev_ril_bridge_event_notifier()
+#ifdef WL_CP_COEX
+void wl_cfg80211_register_dev_ril_bridge_event_notifier(void)
{
WL_DBG(("Enter\n"));
if (!wl_cfg80211_ril_bridge_notifier_registered) {
@@ -16285,7 +16969,7 @@
}
}
-void wl_cfg80211_unregister_dev_ril_bridge_event_notifier()
+void wl_cfg80211_unregister_dev_ril_bridge_event_notifier(void)
{
WL_DBG(("Enter\n"));
if (wl_cfg80211_ril_bridge_notifier_registered) {
@@ -16293,7 +16977,7 @@
unregister_dev_ril_bridge_event_notifier(&wl_cfg80211_ril_bridge_notifier);
}
}
-#endif /* CONFIG_WLAN_BEYONDX || defined(CONFIG_SEC_5GMODEL) */
+#endif /* WL_CP_COEX */
static void wl_print_event_data(struct bcm_cfg80211 *cfg,
uint32 event_type, const wl_event_msg_t *e)
@@ -16404,7 +17088,7 @@
*/
s32
wl_cfg80211_handle_critical_events(struct bcm_cfg80211 *cfg,
- struct wireless_dev *wdev, const wl_event_msg_t * e)
+ struct wireless_dev *wdev, const wl_event_msg_t * e, void *data)
{
s32 ret = BCME_ERROR;
u32 event_type = ntoh32(e->event_type);
@@ -16464,7 +17148,8 @@
}
/* Handle wl_cfg80211_critical_events */
- if (wl_cfg80211_handle_critical_events(cfg, netinfo->wdev, e) == BCME_OK) {
+ if (wl_cfg80211_handle_critical_events(cfg,
+ netinfo->wdev, e, data) == BCME_OK) {
return;
}
@@ -16927,12 +17612,14 @@
/* assuming the order is HT20, HT40 Upper,
* HT40 lower from chanspecs
*/
- u32 ht40_flag = band_chan_arr[index].flags & IEEE80211_CHAN_NO_HT40;
+ u32 ht40_flag =
+ band_chan_arr[index].flags & IEEE80211_CHAN_NO_HT40;
if (CHSPEC_SB_UPPER(chspec)) {
if (ht40_flag == IEEE80211_CHAN_NO_HT40)
band_chan_arr[index].flags &=
~IEEE80211_CHAN_NO_HT40;
- band_chan_arr[index].flags |= IEEE80211_CHAN_NO_HT40PLUS;
+ band_chan_arr[index].flags |=
+ IEEE80211_CHAN_NO_HT40PLUS;
} else {
/* It should be one of
* IEEE80211_CHAN_NO_HT40 or IEEE80211_CHAN_NO_HT40PLUS
@@ -16961,6 +17648,12 @@
}
+ WL_CHANNEL_COPY_FLAG(__wl_2ghz_channels);
+ WL_CHANNEL_COPY_FLAG(__wl_5ghz_a_channels);
+#ifdef CFG80211_6G_SUPPORT
+ WL_CHANNEL_COPY_FLAG(__wl_6ghz_channels);
+#endif /* CFG80211_6G_SUPPORT */
+
__wl_band_2ghz.n_channels = ARRAYSIZE(__wl_2ghz_channels);
__wl_band_5ghz_a.n_channels = ARRAYSIZE(__wl_5ghz_a_channels);
#ifdef CFG80211_6G_SUPPORT
@@ -17016,6 +17709,7 @@
s32 cur_band = -1;
struct ieee80211_supported_band *bands[IEEE80211_NUM_BANDS] = {NULL, };
+ WL_INFORM(("%s: Enter\n", __FUNCTION__));
bzero(bandlist, sizeof(bandlist));
err = wldev_ioctl_get(dev, WLC_GET_BANDLIST, bandlist,
sizeof(bandlist));
@@ -17327,7 +18021,7 @@
if (notify) {
if (!IS_REGDOM_SELF_MANAGED(wiphy)) {
WL_UPDATE_CUSTOM_REGULATORY(wiphy);
- wiphy_apply_custom_regulatory(wiphy, &brcm_regdom);
+ wl_notify_regd(wiphy, NULL);
}
}
@@ -17349,6 +18043,145 @@
return err;
}
+#ifdef WL_RAV_MSCS_NEG_IN_ASSOC
+static s32 wl_cfg80211_config_rav_mscs_params(struct bcm_cfg80211 *cfg,
+ struct net_device *ndev)
+{
+ int err = BCME_OK;
+ bcm_iov_buf_t *iov_buf = NULL;
+ uint16 buflen = 0, buflen_start = 0;
+ char *ioctl_buf = NULL;
+ uint16 iovlen;
+ wl_qos_rav_mscs_config_v1_t rav_mscs_cfg;
+ uint8 *data;
+
+ ioctl_buf = (char *)MALLOCZ(cfg->osh, WLC_IOCTL_MEDLEN);
+ if (!ioctl_buf) {
+ WL_ERR(("ioctl memory alloc failed\n"));
+ err = BCME_NOMEM;
+ goto fail;
+ }
+
+ bzero(&rav_mscs_cfg, sizeof(rav_mscs_cfg));
+ rav_mscs_cfg.version = WL_QOS_RAV_MSCS_SC_VERSION_1;
+ rav_mscs_cfg.length = (uint16) sizeof(wl_qos_rav_mscs_config_v1_t);
+
+ iov_buf = (bcm_iov_buf_t *)MALLOCZ(cfg->osh, WLC_IOCTL_MEDLEN);
+ if (!iov_buf) {
+ WL_ERR(("No memory"));
+ err = BCME_NOMEM;
+ goto fail;
+ }
+
+ /* Fill the bcm_iov_buf_t, IOVAR header */
+ iov_buf->version = WL_QOS_VERSION_1;
+ iov_buf->id = WL_QOS_CMD_RAV_MSCS;
+
+ data = (uint8 *)&iov_buf->data[0];
+ buflen = buflen_start = WLC_IOCTL_MEDLEN - sizeof(bcm_iov_buf_t);
+
+ rav_mscs_cfg.up_bitmap = MSCS_CFG_DEF_FC_MASK;
+ rav_mscs_cfg.up_limit = MSCS_CFG_DEF_UP_LIMIT;
+ rav_mscs_cfg.stream_timeout = MSCS_CFG_DEF_STREAM_TIMEOUT;
+ rav_mscs_cfg.fc_type = DOT11_TCLAS_FC_4_IP_HIGHER;
+ rav_mscs_cfg.fc_mask = MSCS_CFG_DEF_TCLAS_MASK;
+ rav_mscs_cfg.req_type = DOT11_MSCS_REQ_TYPE_ADD;
+
+ *(wl_qos_rav_mscs_config_v1_t *) data = rav_mscs_cfg;
+ buflen -= sizeof(wl_qos_rav_mscs_config_v1_t);
+
+ iov_buf->len = buflen_start - buflen;
+ iovlen = sizeof(bcm_iov_buf_t) + iov_buf->len;
+
+ err = wldev_iovar_setbuf(ndev, "qos_mgmt", iov_buf, iovlen,
+ ioctl_buf, WLC_IOCTL_MEDLEN, NULL);
+ if (unlikely(err)) {
+ WL_ERR(("set qos_mgmt failed ,err(%d)\n", err));
+ }
+fail:
+ if (ioctl_buf) {
+ MFREE(cfg->osh, ioctl_buf, WLC_IOCTL_MEDLEN);
+ }
+
+ if (iov_buf) {
+ MFREE(cfg->osh, iov_buf, WLC_IOCTL_MEDLEN);
+ }
+
+ return err;
+}
+
+static s32 wl_cfg80211_enable_rav_mscs_params(struct bcm_cfg80211 *cfg,
+ struct net_device *ndev, bool mscs_offload)
+{
+ s32 err = BCME_OK;
+ bcm_iov_buf_t *iov_buf = NULL;
+ char *ioctl_buf = NULL;
+ uint16 buflen = 0, buflen_start = 0;
+ uint16 iovlen = 0;
+ uint8 *data;
+
+ if (!cfg) {
+ return BCME_ERROR;
+ }
+
+ if (mscs_offload) {
+ err = wl_cfg80211_config_rav_mscs_params(cfg, ndev);
+ if (err) {
+ WL_INFORM(("config rav_mscs failed ,err(%d)\n", err));
+ return err;
+ }
+ }
+
+ ioctl_buf = (char *)MALLOCZ(cfg->osh, WLC_IOCTL_MEDLEN);
+ if (!ioctl_buf) {
+ WL_ERR(("ioctl memory alloc failed\n"));
+ err = BCME_NOMEM;
+ goto exit;
+ }
+
+ iov_buf = (bcm_iov_buf_t *)MALLOCZ(cfg->osh, WLC_IOCTL_MEDLEN);
+ if (!iov_buf) {
+ WL_ERR(("No memory"));
+ err = BCME_NOMEM;
+ goto exit;
+ }
+
+ /* fill header */
+ iov_buf->version = WL_QOS_VERSION_1;
+ iov_buf->id = WL_QOS_CMD_ENABLE;
+
+ data = (uint8 *)&iov_buf->data[0];
+ buflen = buflen_start = WLC_IOCTL_MEDLEN - sizeof(bcm_iov_buf_t);
+ *((uint16 *)data) = WL_QOS_CMD_ENABLE_FLAG_RAV_MSCS;
+
+ if (mscs_offload) {
+ *((uint16 *)data) |= WL_QOS_CMD_ENABLE_FLAG_RAV_MSCS_NEG_IN_ASSOC;
+ }
+
+ buflen -= sizeof(uint16);
+
+ iov_buf->len = buflen_start - buflen;
+ iovlen = sizeof(bcm_iov_buf_t) + iov_buf->len;
+
+ err = wldev_iovar_setbuf(ndev, "qos_mgmt", iov_buf, iovlen,
+ ioctl_buf, WLC_IOCTL_MEDLEN, NULL);
+ if (unlikely(err)) {
+ WL_ERR(("set qos_mgmt failed ,err(%d)\n", err));
+ }
+
+exit:
+ if (ioctl_buf) {
+ MFREE(cfg->osh, ioctl_buf, WLC_IOCTL_MEDLEN);
+ }
+
+ if (iov_buf) {
+ MFREE(cfg->osh, iov_buf, WLC_IOCTL_MEDLEN);
+ }
+
+ return err;
+}
+#endif /* WL_RAV_MSCS_NEG_IN_ASSOC */
+
static s32 __wl_cfg80211_up(struct bcm_cfg80211 *cfg)
{
s32 err = 0;
@@ -17520,6 +18353,14 @@
return BCME_ERROR;
}
}
+
+#ifdef WL_RAV_MSCS_NEG_IN_ASSOC
+ ret = wl_cfg80211_enable_rav_mscs_params(cfg, ndev, mscs_offload);
+ if (ret) {
+ WL_INFORM(("enable rav_mscs failed ,err(%d)\n", ret));
+ }
+#endif /* WL_RAV_MSCS_NEG_IN_ASSOC */
+
#ifdef DHD_LOSSLESS_ROAMING
del_timer_sync(&cfg->roam_timeout);
#endif /* DHD_LOSSLESS_ROAMING */
@@ -17588,6 +18429,8 @@
#endif /* WL_SAR_TX_POWER_CONFIG */
#endif /* WL_SAR_TX_POWER */
+ cfg->scan_request = NULL;
+
#if defined(DHCP_SCAN_SUPPRESS)
/* wlan scan_supp timer and work thread info */
init_timer_compat(&cfg->scan_supp_timer, wl_cfg80211_scan_supp_timerfunc, cfg);
@@ -17595,7 +18438,6 @@
#endif /* DHCP_SCAN_SUPPRESS */
INIT_DELAYED_WORK(&cfg->pm_enable_work, wl_cfg80211_work_handler);
- wl_set_drv_status(cfg, READY, ndev);
#ifdef WL_MBO_HOST
cfg->btmreq = NULL;
@@ -17616,7 +18458,15 @@
cfg->sroam_turn_on = TRUE;
cfg->sroamed = FALSE;
#endif /* CONFIG_SILTENT_ROAM */
-
+ cfg->roam_allowed_band = WLC_ROAM_ALLOW_BAND_AUTO;
+ if (FW_SUPPORTED(dhd, rsdb)) {
+ cfg->num_radios = 2;
+ } else {
+ cfg->num_radios = 1;
+ }
+ if (FW_SUPPORTED(dhd, sc)) {
+ cfg->num_radios += 1;
+ }
return err;
}
@@ -17972,6 +18822,7 @@
}
}
#endif /* WL_USE_RANDOMIZED_SCAN */
+
#if defined(FORCE_DISABLE_SINGLECORE_SCAN)
dhd_force_disable_singlcore_scan(dhd);
#endif /* FORCE_DISABLE_SINGLECORE_SCAN */
@@ -17999,6 +18850,11 @@
bcm_cfg80211_add_ibss_if(cfg->wdev->wiphy, IBSS_IF_NAME);
#endif /* WLAIBSS_MCHAN */
cfg->spmk_info_list->pmkids.count = 0;
+
+ if (err == BCME_OK) {
+ wl_set_drv_status(cfg, READY, net);
+ }
+
return err;
}
@@ -18318,6 +19174,7 @@
return 0;
}
+
s32 wl_cfg80211_set_p2p_noa(struct net_device *net, char* buf, int len)
{
struct bcm_cfg80211 *cfg = wl_get_cfg(net);
@@ -18387,12 +19244,12 @@
int err = 0;
u32 event = ntoh32(e->event_type);
wl_cfg80211_dev_info_t info;
- wl_bss_info_t *bi = NULL;
+ wl_bss_info_v109_t *bi = NULL;
struct net_device *ndev = NULL;
u8 *buf = NULL;
u32 buflen = 0;
u16 channel = 0;
- wl_escan_result_t *escan_result;
+ wl_escan_result_v109_t *escan_result;
chanspec_t chspec = INVCHANSPEC;
WL_SD(("Enter. type:%d \n", event));
@@ -18410,7 +19267,7 @@
err = wl_genl_send_msg(ndev, event, (const u8 *)e->addr.octet, ETH_ALEN, 0, 0);
} else {
- escan_result = (wl_escan_result_t *) data;
+ escan_result = (wl_escan_result_v109_t *) data;
if (dtoh16(escan_result->bss_count) != 1) {
WL_ERR(("Invalid bss_count %d: ignoring\n", escan_result->bss_count));
@@ -20428,7 +21285,7 @@
ret = -EINVAL;
return ret;
} else {
- WL_DBG(("pmk added for mac:"MACDBG"\n", MAC2STRDBG(conf->aa)));
+ WL_INFORM_MEM(("pmk added for mac:"MACDBG"\n", MAC2STRDBG(conf->aa)));
}
return 0;
}
@@ -20778,6 +21635,7 @@
return BCME_OK;
}
#endif /* WBTEXT */
+
#ifdef SUPPORT_SET_CAC
void
wl_cfg80211_set_cac(struct bcm_cfg80211 *cfg, int enable)
@@ -20897,6 +21755,7 @@
return err;
}
#endif /* SUPPORT_RSSI_SUM_REPORT */
+
/* Function to flush the FW preserve buffer content
* The buffer content is sent to host in form of events.
*/
@@ -20927,6 +21786,7 @@
}
}
}
+
#ifdef USE_WFA_CERT_CONF
extern int g_frameburst;
#endif /* USE_WFA_CERT_CONF */
@@ -20950,6 +21810,8 @@
WL_ERR(("Failed set frameburst, ret=%d\n", ret));
} else {
WL_INFORM_MEM(("frameburst is %s\n", enable ? "enabled" : "disabled"));
+ /* Track disabled state */
+ cfg->frameburst_disabled = (enable ? FALSE : TRUE);
}
return ret;
@@ -21834,6 +22696,9 @@
u32 status = ntoh32(event->status);
struct net_device *ndev = bcmcfg_to_prmry_ndev(cfg);
u32 reason = ntoh32(event->reason);
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(4, 15, 0))
+ const u8 *curbssid = (const u8 *)event->addr.octet;
+#endif /* LINUX_VERSION_CODE > KERNEL_VERSION(4, 15, 0) */
if (!wl_get_drv_status(cfg, CFG80211_CONNECT, ndev)) {
/* Join attempt via non-cfg80211 interface.
@@ -21845,10 +22710,19 @@
return BCME_OK;
}
+ WL_INFORM_MEM(("idsup status:%d reason:%d\n", status, reason));
if ((status == WLC_SUP_KEYED || status == WLC_SUP_KEYXCHANGE_WAIT_G1) &&
reason == WLC_E_SUP_OTHER) {
#if (LINUX_VERSION_CODE >= KERNEL_VERSION(4, 15, 0))
- cfg80211_port_authorized(ndev, (const u8 *)&event->addr, GFP_KERNEL);
+ if (!ETHER_ISNULLADDR(curbssid)) {
+ WL_DBG(("Authorizing Port with BSSID from FW event " MACDBG" \n",
+ MAC2STRDBG(curbssid)));
+ } else {
+ curbssid = wl_read_prof(cfg, ndev, WL_PROF_BSSID);
+ WL_DBG(("Authorizing Port with BSSID from DHD profile " MACDBG" \n",
+ MAC2STRDBG(curbssid)));
+ }
+ cfg80211_port_authorized(ndev, (const u8 *)curbssid, GFP_KERNEL);
#elif (LINUX_VERSION_CODE > KERNEL_VERSION(3, 14, 0)) || defined(WL_VENDOR_EXT_SUPPORT)
err = wl_cfgvendor_send_async_event(bcmcfg_to_wiphy(cfg), ndev,
BRCM_VENDOR_EVENT_PORT_AUTHORIZED, NULL, 0);
@@ -22221,6 +23095,7 @@
exit:
return cmode;
}
+
#ifdef WL_CHAN_UTIL
static s32
wl_cfg80211_bssload_report_event_handler(struct bcm_cfg80211 *cfg, bcm_struct_cfgdev *cfgdev,
@@ -22629,18 +23504,25 @@
#define GAS_RESP_LEN 2
#define DOUBLE_TLV_BODY_OFF 4
-bool wl_cfg80211_find_gas_subtype(u8 subtype, u16 adv_id, u8* data, u32 len)
+bool wl_cfg80211_find_gas_subtype(u8 subtype, u16 adv_id, u8* data, s32 len)
{
const bcm_tlv_t *ie = (bcm_tlv_t *)data;
const u8 *frame = NULL;
u16 id, flen;
+ if (len <= 0) {
+ return false;
+ }
/* Skipped first ANQP Element, if frame has anqp elemnt */
ie = bcm_parse_tlvs(ie, len, DOT11_MNG_ADVERTISEMENT_ID);
if (ie == NULL)
return false;
+ if (len < (ie->len + TLV_HDR_LEN + GAS_RESP_LEN + DOUBLE_TLV_BODY_OFF)) {
+ return false;
+ }
+
frame = (const uint8 *)ie + ie->len + TLV_HDR_LEN + GAS_RESP_LEN;
id = ((u16) (((frame)[1] << 8) | (frame)[0]));
flen = ((u16) (((frame)[3] << 8) | (frame)[2]));
@@ -22702,8 +23584,8 @@
const int ETHERTYPE_LEN = 2;
char *pbuf = NULL;
const char *str;
- wl_mkeep_alive_pkt_t mkeep_alive_pkt;
- wl_mkeep_alive_pkt_t *mkeep_alive_pktp = NULL;
+ wl_mkeep_alive_pkt_v1_t mkeep_alive_pkt;
+ wl_mkeep_alive_pkt_v1_t *mkeep_alive_pktp = NULL;
uint16 buf_len = 0;
u8 str_len = 0;
int res = BCME_ERROR;
@@ -22751,7 +23633,7 @@
goto exit;
} else {
/* Check available ID whether it is occupied */
- mkeep_alive_pktp = (wl_mkeep_alive_pkt_t *) pbuf;
+ mkeep_alive_pktp = (wl_mkeep_alive_pkt_v1_t *) pbuf;
if (dtoh32(mkeep_alive_pktp->period_msec != 0)) {
WL_ERR(("%s: Get mkeep_alive failed, ID %u is in use.\n",
__FUNCTION__, mkeep_alive_id));
@@ -22777,7 +23659,7 @@
}
/* Request the specified ID */
- bzero(&mkeep_alive_pkt, sizeof(wl_mkeep_alive_pkt_t));
+ bzero(&mkeep_alive_pkt, sizeof(wl_mkeep_alive_pkt_v1_t));
bzero(pbuf, KA_TEMP_BUF_SIZE);
str = "mkeep_alive";
str_len = strlen(str);
@@ -22785,9 +23667,9 @@
buf_len = str_len + 1;
pbuf_len -= buf_len;
- mkeep_alive_pktp = (wl_mkeep_alive_pkt_t *) (pbuf + buf_len);
+ mkeep_alive_pktp = (wl_mkeep_alive_pkt_v1_t *) (pbuf + buf_len);
mkeep_alive_pkt.period_msec = htod32(period_msec);
- mkeep_alive_pkt.version = htod16(WL_MKEEP_ALIVE_VERSION);
+ mkeep_alive_pkt.version = htod16(WL_MKEEP_ALIVE_VERSION_1);
mkeep_alive_pkt.length = htod16(WL_MKEEP_ALIVE_FIXED_LEN);
len_bytes = (ETHER_ADDR_LEN*2) + ETHERTYPE_LEN + ip_pkt_len;
mkeep_alive_pkt.len_bytes = htod16(len_bytes);
@@ -22872,8 +23754,8 @@
wl_cfg80211_stop_mkeep_alive(struct bcm_cfg80211 *cfg, uint8 mkeep_alive_id)
{
char *pbuf = NULL;
- wl_mkeep_alive_pkt_t mkeep_alive_pkt;
- wl_mkeep_alive_pkt_t *mkeep_alive_pktp = NULL;
+ wl_mkeep_alive_pkt_v1_t mkeep_alive_pkt;
+ wl_mkeep_alive_pkt_v1_t *mkeep_alive_pktp = NULL;
int res = BCME_ERROR;
int i = 0;
struct net_device *primary_ndev = NULL;
@@ -22905,7 +23787,7 @@
goto exit;
} else {
/* Check occupied ID */
- mkeep_alive_pktp = (wl_mkeep_alive_pkt_t *) pbuf;
+ mkeep_alive_pktp = (wl_mkeep_alive_pkt_v1_t *) pbuf;
WL_DBG(("%s: mkeep_alive\n", __FUNCTION__));
WL_DBG((" Id : %d\n"
" Period: %d msec\n"
@@ -22924,10 +23806,10 @@
/* Make it stop if available */
if (dtoh32(mkeep_alive_pktp->period_msec != 0)) {
WL_INFORM_MEM(("stop mkeep_alive on ID %d\n", mkeep_alive_id));
- bzero(&mkeep_alive_pkt, sizeof(wl_mkeep_alive_pkt_t));
+ bzero(&mkeep_alive_pkt, sizeof(wl_mkeep_alive_pkt_v1_t));
mkeep_alive_pkt.period_msec = 0;
- mkeep_alive_pkt.version = htod16(WL_MKEEP_ALIVE_VERSION);
+ mkeep_alive_pkt.version = htod16(WL_MKEEP_ALIVE_VERSION_1);
mkeep_alive_pkt.length = htod16(WL_MKEEP_ALIVE_FIXED_LEN);
mkeep_alive_pkt.keep_alive_id = mkeep_alive_id;
@@ -23115,6 +23997,9 @@
sec->auth_assoc_res_status = AUTH_ASSOC_STATUS_NO_NETWORKS;
}
#endif /* AUTH_ASSOC_STATUS_EXT */
+#ifdef WL_CFGVENDOR_CUST_ADVLOG
+ wl_cfgvendor_custom_advlog_connfail(cfg, event, as);
+#endif /* WL_CFGVENDOR_CUST_ADVLOG */
/* Report connect failure */
as->link_action = wl_set_link_action(assoc_state, false);
@@ -23129,7 +24014,7 @@
{
s32 err = BCME_OK;
const wl_twt_setup_cplt_t *setup_cplt = (wl_twt_setup_cplt_t *)event_data;
- const wl_twt_sdesc_t *sdesc = (const wl_twt_sdesc_t *)&setup_cplt[1];
+ const wl_twt_sdesc_v0_t *sdesc = (const wl_twt_sdesc_v0_t *)&setup_cplt[1];
WL_DBG(("TWT_SETUP: status %d, reason %d, configID %d, setup_cmd %d, flow_flags 0x%x,"
" flow_id %d, channel %d, negotiation_type %d, wake_time_h %u, wake_time_l %u,"
@@ -23317,7 +24202,7 @@
gfp_t kflags;
struct wiphy *wiphy = bcmcfg_to_wiphy(cfg);
int err = BCME_OK;
- struct net_device *ndev = bcmcfg_to_prmry_ndev(cfg);
+ struct net_device *ndev = cfgdev_to_wlc_ndev(cfgdev, cfg);
const wl_twt_event_t *twt_event = (wl_twt_event_t *)data;
kflags = in_atomic() ? GFP_ATOMIC : GFP_KERNEL;
@@ -23447,6 +24332,20 @@
return len;
}
+void
+wl_cfg80211_wdev_lock(struct wireless_dev *wdev)
+{
+ mutex_lock(&wdev->mtx);
+ __acquire(wdev->mtx);
+}
+
+void
+wl_cfg80211_wdev_unlock(struct wireless_dev *wdev)
+{
+ __release(wdev->mtx);
+ mutex_unlock(&wdev->mtx);
+}
+
#ifdef WL_CLIENT_SAE
static bool
wl_is_pmkid_available(struct net_device *dev, const u8 *bssid)
@@ -23476,7 +24375,6 @@
wl_auth_start_evt_t *evt_data = (wl_auth_start_evt_t *)data;
wl_assoc_mgr_cmd_t cmd;
struct wireless_dev *wdev = ndev->ieee80211_ptr;
- int retry = 3;
int err = BCME_OK;
WL_DBG(("Enter \n"));
@@ -23505,23 +24403,16 @@
WL_INFORM_MEM(("call cfg80211_external_auth_request, BSSID:"MACDBG"\n",
MAC2STRDBG(&evt_data->bssid)));
- /* Wait for conn_owner_nlportid been assigned in nl80211_connect */
- for (retry = 3; retry > 0; retry--) {
- if (wdev->conn_owner_nlportid) {
- break;
- }
-
- wl_delay(10);
- }
-
+ wl_cfg80211_wdev_lock(wdev);
err = cfg80211_external_auth_request(ndev, &ext_auth_param, GFP_KERNEL);
+ wl_cfg80211_wdev_unlock(wdev);
if (err) {
WL_ERR(("Send external auth request failed, ret %d\n", err));
err = BCME_ERROR;
goto fail;
}
- cmd.version = WL_ASSOC_MGR_CURRENT_VERSION;
+ cmd.version = WL_ASSOC_MGR_VERSION_0;
cmd.length = sizeof(cmd);
cmd.cmd = WL_ASSOC_MGR_CMD_PAUSE_ON_EVT;
cmd.params = WL_ASSOC_MGR_PARAMS_PAUSE_EVENT_AUTH_RESP;
@@ -23675,7 +24566,7 @@
goto done;
}
- cmd.version = WL_ASSOC_MGR_CURRENT_VERSION;
+ cmd.version = WL_ASSOC_MGR_VERSION_0;
cmd.length = sizeof(cmd);
cmd.cmd = WL_ASSOC_MGR_CMD_PAUSE_ON_EVT;
cmd.params = WL_ASSOC_MGR_PARAMS_EVENT_NONE;
@@ -24210,26 +25101,59 @@
int
wl_cfg80211_reassoc(struct net_device *dev, struct ether_addr *bssid, chanspec_t chanspec)
{
+ struct bcm_cfg80211 *cfg = wl_get_cfg(dev);
int error = BCME_OK;
u32 params_size;
- wl_reassoc_params_t reassoc_params;
- bzero(&reassoc_params, WL_REASSOC_PARAMS_FIXED_SIZE);
- bcopy(bssid, &reassoc_params.bssid, ETHER_ADDR_LEN);
+ void *iovar_params;
+ wl_reassoc_params_t *reassoc_params_info;
+ wl_reassoc_params_t reassoc_params_v0;
+ wl_reassoc_params_cvt_v1_t reassoc_params_v1;
+ wl_ext_reassoc_params_cvt_v1_t reassoc_params_v2;
- if (chanspec) {
- reassoc_params.chanspec_num = 1;
- reassoc_params.chanspec_list[0] = chanspec;
- params_size = WL_REASSOC_PARAMS_FIXED_SIZE + sizeof(chanspec_t);
- } else {
- params_size = ETHER_ADDR_LEN;
+ switch (cfg->join_iovar_ver) {
+ case WL_REASSOC_VERSION_V0 :
+ /* wl_reassoc_params */
+ params_size = WL_REASSOC_PARAMS_FIXED_SIZE + sizeof(chanspec_t);
+ iovar_params = &reassoc_params_v0;
+ reassoc_params_info = &reassoc_params_v0;
+ break;
+ case WL_REASSOC_VERSION_V1 :
+ /* wl_reassoc_params_v1 */
+ params_size = WL_REASSOC_PARAMS_FIXED_SIZE_V1 + sizeof(chanspec_t);
+ iovar_params = &reassoc_params_v1;
+ reassoc_params_v1.version = WL_REASSOC_VERSION_V1;
+ reassoc_params_v1.flags = WL_SCAN_MODE_HIGH_ACC;
+ reassoc_params_info = &reassoc_params_v1.params;
+ break;
+ case WL_REASSOC_VERSION_V2 :
+ /* wl_ext_reassoc_params */
+ params_size = WL_EXTREASSOC_PARAMS_FIXED_SIZE_V1 + sizeof(chanspec_t);
+ iovar_params = &reassoc_params_v2;
+ reassoc_params_v2.version = WL_REASSOC_VERSION_V2;
+ reassoc_params_v2.length = params_size;
+ reassoc_params_v2.flags = WL_SCAN_MODE_HIGH_ACC;
+ reassoc_params_v2.params.version = WL_REASSOC_VERSION_V2;
+ reassoc_params_v2.params.flags = WL_SCAN_MODE_HIGH_ACC;
+ reassoc_params_info = &reassoc_params_v2.params.params;
+ break;
+ default :
+ error = BCME_VERSION;
+ goto exit;
}
- error = wldev_ioctl_set(dev, WLC_REASSOC, &reassoc_params, params_size);
+ bzero(reassoc_params_info, WL_REASSOC_PARAMS_FIXED_SIZE);
+ bcopy(bssid, (void *)&reassoc_params_info->bssid, ETHER_ADDR_LEN);
+
+ reassoc_params_info->chanspec_num = 1;
+ reassoc_params_info->chanspec_list[0] = chanspec;
+
+ error = wldev_ioctl_set(dev, WLC_REASSOC, iovar_params, params_size);
if (error) {
WL_ERR(("failed to reassoc, error=%d\n", error));
- return error;
}
+
+exit:
return error;
}
@@ -24249,7 +25173,9 @@
usable_channel_info_t *u_info, uint32 *conn,
chanspec_t sta_chspec)
{
+#ifdef WL_CELLULAR_CHAN_AVOID
wifi_interface_mode mode;
+#endif /* WL_CELLULAR_CHAN_AVOID */
drv_acs_params_t param = { 0 };
int ret;
uint32 cur_band;
@@ -24331,6 +25257,60 @@
}
+#ifdef WL_NAN_INSTANT_MODE
+static int wl_cfg80211_get_nan_instant_chan(struct bcm_cfg80211 *cfg,
+ wl_chanspec_list_v1_t *chan_list, uint32 band_mask,
+ chanspec_t *nan_inst_mode_chspec)
+{
+ int err = BCME_OK;
+ int band = 0;
+ uint32 channel;
+ uint8 nan_2g = 0, nan_pri_5g = 0, nan_sec_5g = 0;
+
+ wl_cfgnan_inst_chan_support(cfg, chan_list,
+ band_mask, &nan_2g, &nan_pri_5g, &nan_sec_5g);
+ if (!nan_2g && !nan_pri_5g && !nan_sec_5g) {
+ WL_ERR(("Failed to retrieve the soc channels for nan:"
+ "nan_2g: %d, nan_pri_5g: %d, nan_sec_5g: %d\n",
+ nan_2g, nan_pri_5g, nan_sec_5g));
+ err = BCME_NOTFOUND;
+ goto exit;
+ }
+ /* Skip if chanspec does not match the interested band_mask */
+ if (!((band_mask & WLAN_MAC_2_4_BAND) ||
+ (band_mask & WLAN_MAC_5_0_BAND))) {
+ WL_ERR(("Unsupported band mask in unsupported for nan\n"));
+ err = BCME_UNSUPPORTED;
+ goto exit;
+ }
+
+ if ((band_mask & WLAN_MAC_5_0_BAND) && (nan_pri_5g)) {
+ channel = nan_pri_5g;
+ band = WL_CHANSPEC_BAND_5G;
+ } else if ((band_mask & WLAN_MAC_5_0_BAND) && (nan_sec_5g)) {
+ channel = nan_sec_5g;
+ band = WL_CHANSPEC_BAND_5G;
+ } else if ((band_mask & WLAN_MAC_2_4_BAND) && (nan_2g)) {
+ channel = nan_2g;
+ band = WL_CHANSPEC_BAND_2G;
+ } else {
+ WL_ERR(("No usable channels for nan\n"));
+ err = BCME_NOTFOUND;
+ goto exit;
+ }
+ if ((*nan_inst_mode_chspec =
+ wl_freq_to_chanspec(wl_channel_to_frequency(channel, band))) == INVCHANSPEC) {
+ WL_ERR(("Invalid instant mode usable channel: %d, band: %d\n", channel, band));
+ err = BCME_ERROR;
+ goto exit;
+ }
+ WL_INFORM_MEM(("Instant mode usable channel for nan: %d\n", channel));
+exit:
+ return err;
+}
+#endif /* WL_NAN_INSTANT_MODE */
+#line 27247
+
int wl_get_usable_channels(struct bcm_cfg80211 *cfg, usable_channel_info_t *u_info)
{
usable_channel_t *cur_ch = NULL;
@@ -24343,12 +25323,18 @@
u16 list_count;
int found_idx = BCME_NOTFOUND;
bool ch_160mhz_5g;
- u32 restrict_chan, vlp_psc_include;
+ u32 restrict_chan;
+#ifdef WL_SOFTAP_6G
+ u32 vlp_psc_include;
+#endif /* WL_SOFTAP_6G */
uint32 conn[WL_IF_TYPE_MAX] = {0};
struct net_device *p2p_ndev = NULL;
- uint32 sta_band = 0;
chanspec_t sta_chanspec;
- u32 sta_assoc_freq = 0;
+ uint32 sta_assoc_freq = 0;
+ bool is_unii4 = false;
+#ifdef WL_NAN_INSTANT_MODE
+ chanspec_t nan_inst_mode_chspec = INVCHANSPEC;
+#endif /* WL_NAN_INSTANT_MODE */
bzero(u_info->channels, sizeof(*u_info->channels) * u_info->max_size);
/* Get chan_info_list or chanspec from FW */
@@ -24370,9 +25356,21 @@
goto exit;
}
+#ifdef WL_NAN_INSTANT_MODE
+ if ((u_info->iface_mode_mask & (1 << WIFI_INTERFACE_NAN)) &&
+ (u_info->filter_mask & WIFI_USABLE_CHANNEL_FILTER_NAN_INSTANT_MODE)) {
+ if (wl_cfg80211_get_nan_instant_chan(cfg, (wl_chanspec_list_v1_t *)chan_list,
+ u_info->band_mask, &nan_inst_mode_chspec) != BCME_OK) {
+ WL_ERR(("Failed to get the instant nan mode chanspec!!\n"));
+ }
+ }
+#endif /* WL_NAN_INSTANT_MODE */
+#line 27304
+
+ /* TDLS is supported only for single STA associated case */
if (cfg->stas_associated == 1) {
sta_chanspec = wl_cfg80211_get_sta_chanspec(cfg);
- band = CHSPEC_BAND(sta_chanspec);
+ band = CHSPEC_TO_WLC_BAND(CHSPEC_BAND(sta_chanspec));
channel = CHSPEC_CHANNEL(sta_chanspec);
sta_assoc_freq = wl_channel_to_frequency(channel, band);
}
@@ -24392,9 +25390,9 @@
freq = wl_channel_to_frequency(channel, band);
width = wl_chanspec_to_host_bw_map(chspec);
- WL_DBG(("chspec:%x chaninfo:%x freq:%u band:%u"
+ WL_DBG(("chspec:%x channel:%u chaninfo:%x freq:%u band:%u "
"req_band:%u req_iface_mode:%u filter:%u\n",
- chspec, chaninfo, freq, band,
+ chspec, channel, chaninfo, freq, CHSPEC_TO_WLC_BAND(band),
u_info->band_mask, u_info->iface_mode_mask, u_info->filter_mask));
/* Skip if it is not interested */
@@ -24405,16 +25403,23 @@
}
restrict_chan = ((chaninfo & WL_CHAN_RADAR) ||
- (chaninfo & WL_CHAN_PASSIVE) ||
+ (chaninfo & WL_CHAN_PASSIVE)||
(chaninfo & WL_CHAN_CLM_RESTRICTED));
+#ifdef WL_SOFTAP_6G
vlp_psc_include = ((chaninfo & WL_CHAN_BAND_6G_PSC) &&
- (chaninfo & WL_CHAN_BAND_6G_VLP));
+ (chaninfo & WL_CHAN_BAND_6G_VLP));
+#endif /* WL_SOFTAP_6G */
+#line 27347
+#ifdef WL_UNII4_CHAN
+ is_unii4 = (CHSPEC_IS5G(chspec) &&
+ IS_UNII4_CHANNEL(wf_chspec_primary20_chan(chspec)));
+#endif /* WL_UNII4_CHAN */
/* STA set all chanspec but can be filtered out in filter function */
mask = (1 << WIFI_INTERFACE_STA);
if (sta_assoc_freq && (sta_assoc_freq == freq) &&
- (!CHSPEC_IS6G(chspec))) {
+ (!CHSPEC_IS6G(chspec) && !is_unii4)) {
if (CHSPEC_IS5G(chspec) && (chaninfo & WL_CHAN_CLM_RESTRICTED)) {
/* if restricted channel, specifically allow only DFS channel
* (radar+passive). TDLS operates on STA channel and
@@ -24437,25 +25442,45 @@
}
if (!restrict_chan && !ch_160mhz_5g) {
- /* consider only VLP and PSC channel in 6g */
- if (CHSPEC_IS6G(chspec) && !vlp_psc_include) {
- continue;
- }
- if (!CHSPEC_IS6G(chspec)) {
- mask |= ((1 << WIFI_INTERFACE_P2P_GO) |
- (1 << WIFI_INTERFACE_SOFTAP) |
- (1 << WIFI_INTERFACE_NAN));
- } else {
+ if (!is_unii4)
+ {
+ if (CHSPEC_IS6G(chspec)) {
#ifdef WL_NAN_6G
- mask |= (1 << WIFI_INTERFACE_NAN);
+ mask |= (1 << WIFI_INTERFACE_NAN);
#endif /* WL_NAN_6G */
+#line 27385
#ifdef WL_SOFTAP_6G
- mask |= (1 << WIFI_INTERFACE_SOFTAP);
+ /* consider only VLP and PSC channel in 6g for softap */
+ if (vlp_psc_include) {
+ mask |= (1 << WIFI_INTERFACE_SOFTAP);
+ }
#endif /* WL_SOFTAP_6G */
+#line 27391
+ } else {
+ /* handle 2G and 5G channels */
+ mask |= ((1 << WIFI_INTERFACE_P2P_GO) |
+ (1 << WIFI_INTERFACE_SOFTAP));
+#ifdef WL_NAN_INSTANT_MODE
+ /* handle nan instant mode filter mask case separately */
+ if ((u_info->iface_mode_mask & (1 << WIFI_INTERFACE_NAN)) &&
+ (u_info->filter_mask &
+ WIFI_USABLE_CHANNEL_FILTER_NAN_INSTANT_MODE)) {
+ if (chspec == nan_inst_mode_chspec) {
+ mask |= (1 << WIFI_INTERFACE_NAN);
+ }
+ } else
+#endif /* WL_NAN_INSTANT_MODE */
+#line 27405
+ {
+ mask |= (1 << WIFI_INTERFACE_NAN);
+ }
+ }
}
}
+
/* Supplicant does scan passive channel but not for DFS channel */
- if (!(chaninfo & WL_CHAN_RADAR) && !ch_160mhz_5g && !CHSPEC_IS6G(chspec)) {
+ if (!(chaninfo & WL_CHAN_RADAR) && !ch_160mhz_5g &&
+ !CHSPEC_IS6G(chspec) && (!is_unii4)) {
mask |= (1 << WIFI_INTERFACE_P2P_CLIENT);
}
@@ -24466,7 +25491,8 @@
/* Return only primary channel and max bandwidth.
* If freq is already added and found bigger bandwidth
- * replace bandwidth with found one */
+ * replace bandwidth with found one
+ */
found_idx = wl_check_exist_freq_in_list(u_info->channels, idx, freq);
if (found_idx != BCME_NOTFOUND) {
if (width > u_info->channels[found_idx].width) {
@@ -24491,9 +25517,6 @@
if (u_info->filter_mask) {
/* Get conneceted bands to clear STA bit when Dual STA is connected */
sta_chanspec = wl_cfg80211_get_sta_chanspec(cfg);
- if (sta_chanspec) {
- sta_band = CHSPEC_TO_WLC_BAND(CHSPEC_BAND(sta_chanspec));
- }
/* Get connected STA, AP, P2P and NAN interface count */
conn[WL_IF_TYPE_STA] = wl_cfgvif_get_iftype_count(cfg, WL_IF_TYPE_STA);
@@ -24558,7 +25581,7 @@
}
/* fill header */
- iov_req->version = WL_CHRE_IOV_VERSION;
+ iov_req->version = WL_CHRE_IOV_VERSION_1_1;
iov_req->id = WL_CHRE_CMD_ENABLE;
pxtlv = (bcm_xtlv_t *)&iov_req->data[0];
@@ -24633,7 +25656,7 @@
goto done;
}
- if (psroam->ver != WLC_SILENT_ROAM_CUR_VER) {
+ if (psroam->ver != WLC_SILENT_ROAM_VER_1) {
ret = BCME_VERSION;
goto done;
}
@@ -24655,3 +25678,210 @@
return ret;
}
#endif /* CONFIG_SILENT_ROAM */
+
+#ifdef WL_CFGVENDOR_CUST_ADVLOG
+static void
+wl_cfgvendor_custom_advlog_conn(struct bcm_cfg80211 *cfg, struct net_device *dev,
+ struct cfg80211_connect_params *sme)
+{
+ struct wl_security *sec = wl_read_prof(cfg, dev, WL_PROF_SEC);
+ char advlog[SUPP_LOG_LEN] = {'\0'};
+ int buf_pos = 0;
+ char ssid_str[DOT11_MAX_SSID_LEN + 1];
+
+ if (!sec) {
+ WL_ERR(("sec is NULL"));
+ return;
+ }
+
+ bzero(advlog, SUPP_LOG_LEN);
+
+ if (memcpy_s(ssid_str, DOT11_MAX_SSID_LEN,
+ sme->ssid, sme->ssid_len) != BCME_OK) {
+ WL_ERR(("ssid cpy failed\n"));
+ return;
+ }
+ ssid_str[sme->ssid_len] = '\0';
+
+ buf_pos = snprintf(advlog, SUPP_LOG_LEN, "[CONN] CONNECTING ssid=\"%s\" ",
+ ssid_str);
+
+ if (sme->bssid && !ETHER_ISBCAST(sme->bssid)) {
+ /* do not print to the kernel, only for framework (MACDBG_FULL) */
+ buf_pos += snprintf(&advlog[buf_pos], SUPP_LOG_LEN - buf_pos,
+ "bssid="MACDBG_FULL" ", MAC2STRDBG_FULL(sme->bssid));
+ }
+ if (sme->bssid_hint && !ETHER_ISBCAST(sme->bssid_hint)) {
+ /* do not print to the kernel, only for framework (MACDBG_FULL) */
+ buf_pos += snprintf(&advlog[buf_pos], SUPP_LOG_LEN - buf_pos,
+ "bssid_hint="MACDBG_FULL" ", MAC2STRDBG_FULL(sme->bssid_hint));
+ }
+ if (sme->channel) {
+ buf_pos += snprintf(&advlog[buf_pos], SUPP_LOG_LEN - buf_pos,
+ "freq=%d ", sme->channel->center_freq);
+ }
+ if (sme->channel_hint) {
+ buf_pos += snprintf(&advlog[buf_pos], SUPP_LOG_LEN - buf_pos,
+ "freq_hint=%d ", sme->channel_hint->center_freq);
+ }
+ buf_pos += snprintf(&advlog[buf_pos], SUPP_LOG_LEN - buf_pos,
+ "pairwise=0x%x group=0x%x akm=0x%x auth_type=%d ",
+ sec->cipher_pairwise, sec->cipher_group, sec->wpa_auth, sec->auth_type);
+ if (sec->fw_mfp == WL_MFP_REQUIRED) {
+ buf_pos += snprintf(&advlog[buf_pos], SUPP_LOG_LEN - buf_pos,
+ "group_mgmt=0x%x", sme->crypto.akm_suites[0]);
+ }
+
+ SUPP_ADVLOG(("%s", advlog));
+
+ return;
+}
+
+static void
+wl_cfgvendor_custom_advlog_connfail(struct bcm_cfg80211 *cfg, const wl_event_msg_t *event,
+ wl_assoc_status_t *as)
+{
+ BCM_REFERENCE(cfg);
+ /* do not print to the kernel, only for framework (MACDBG_FULL) */
+ SUPP_ADVLOG(("[CONN] CONNECTING FAIL bssid=" MACDBG_FULL " [status=%d]\n",
+ MAC2STRDBG_FULL((const u8*)(&event->addr)), as->status));
+
+ return;
+}
+
+static void
+wl_cfgvendor_custom_advlog_disconn(struct bcm_cfg80211 *cfg, wl_assoc_status_t *as)
+{
+ int err = 0;
+ scb_val_t scbval;
+
+ bzero(&scbval, sizeof(scb_val_t));
+ err = wldev_get_rssi(bcmcfg_to_prmry_ndev(cfg), &scbval);
+ if (unlikely(err)) {
+ WL_ERR(("get_rssi error (%d)\n", err));
+ scbval.val = 0;
+ }
+ /* Beacon loss link down */
+ /* do not print to the kernel, only for framework (MACDBG_FULL) */
+ SUPP_ADVLOG(("[CONN] DISCONN bssid=" MACDBG_FULL " rssi=%d reason=0\n",
+ MAC2STRDBG_FULL((const u8*)(&as->addr)), scbval.val));
+
+ return;
+}
+#endif /* WL_CFGVENDOR_CUST_ADVLOG */
+
+int
+wl_cfg80211_get_roam_params(struct net_device *dev, uint32 *data, uint16 data_len, uint16 id)
+{
+ struct bcm_cfg80211 *cfg = wl_get_cfg(dev);
+ s32 err = BCME_OK;
+ bcm_iov_buf_t *iov_buf = NULL;
+ bcm_iov_buf_t *ioctl_buf = NULL;
+ const uint8 *pxtlv = NULL;
+
+ ioctl_buf = (bcm_iov_buf_t *)MALLOCZ(cfg->osh, WLC_IOCTL_MEDLEN);
+ if (!ioctl_buf) {
+ WL_ERR(("ioctl memory alloc failed\n"));
+ err = BCME_NOMEM;
+ goto exit;
+ }
+
+ iov_buf = (bcm_iov_buf_t *)MALLOCZ(cfg->osh, WLC_IOCTL_MEDLEN);
+ if (!iov_buf) {
+ WL_ERR(("No memory"));
+ err = BCME_NOMEM;
+ goto exit;
+ }
+
+ /* fill header */
+ iov_buf->version = WL_ROAM_PARAMS_IOV_VERSION_1_1;
+ iov_buf->id = id;
+
+ err = wldev_iovar_getbuf(dev, "roam_params", iov_buf, sizeof(bcm_iov_buf_t),
+ ioctl_buf, WLC_IOCTL_MEDLEN, NULL);
+ if (unlikely(err)) {
+ WL_ERR(("get roam_params id %d error %d\n", id, err));
+ }
+
+ pxtlv = (const uint8 *)&ioctl_buf->data[0];
+ err = bcm_unpack_xtlv_entry(&pxtlv, id,
+ data_len, (uint8 *)data, BCM_XTLV_OPTION_ALIGN32);
+
+exit:
+ if (ioctl_buf) {
+ MFREE(cfg->osh, ioctl_buf, WLC_IOCTL_MEDLEN);
+ }
+
+ if (iov_buf) {
+ MFREE(cfg->osh, iov_buf, WLC_IOCTL_MEDLEN);
+ }
+
+ return err;
+}
+
+int
+wl_cfg80211_set_roam_params(struct net_device *dev, uint32 *data, uint16 data_len, uint16 id)
+{
+ struct bcm_cfg80211 *cfg = wl_get_cfg(dev);
+ s32 err = BCME_OK;
+ bcm_iov_buf_t *iov_buf = NULL;
+ char *ioctl_buf = NULL;
+ uint8 *pxtlv = NULL;
+ uint16 iovlen = 0;
+ uint16 buflen = 0, buflen_start = 0;
+
+ if (!cfg) {
+ return BCME_ERROR;
+ }
+
+ if (data_len > WLC_IOCTL_MEDLEN) {
+ err = BCME_BADLEN;
+ goto exit;
+ }
+
+ ioctl_buf = (char *)MALLOCZ(cfg->osh, WLC_IOCTL_MEDLEN);
+ if (!ioctl_buf) {
+ WL_ERR(("ioctl memory alloc failed\n"));
+ err = BCME_NOMEM;
+ goto exit;
+ }
+
+ iov_buf = (bcm_iov_buf_t *)MALLOCZ(cfg->osh, WLC_IOCTL_MEDLEN);
+ if (!iov_buf) {
+ WL_ERR(("No memory"));
+ err = BCME_NOMEM;
+ goto exit;
+ }
+
+ /* fill header */
+ iov_buf->version = WL_ROAM_PARAMS_IOV_VERSION_1_1;
+ iov_buf->id = id;
+ pxtlv = (uint8 *)&iov_buf->data[0];
+ buflen = buflen_start = WLC_IOCTL_MEDLEN - sizeof(bcm_iov_buf_t);
+
+ err = bcm_pack_xtlv_entry(&pxtlv, &buflen, id,
+ data_len, (uint8 *)data, BCM_XTLV_OPTION_ALIGN32);
+
+ if (err != BCME_OK) {
+ WL_ERR(("failed to pack roam_params id %d, err %d\n", id, err));
+ goto exit;
+ }
+ iov_buf->len = buflen_start - buflen;
+ iovlen = sizeof(bcm_iov_buf_t) + iov_buf->len;
+
+ err = wldev_iovar_setbuf(dev, "roam_params", iov_buf, iovlen,
+ ioctl_buf, WLC_IOCTL_MEDLEN, NULL);
+ if (unlikely(err)) {
+ WL_ERR(("set roam_params id %d error %d\n", id, err));
+ }
+
+exit:
+ if (ioctl_buf) {
+ MFREE(cfg->osh, ioctl_buf, WLC_IOCTL_MEDLEN);
+ }
+
+ if (iov_buf) {
+ MFREE(cfg->osh, iov_buf, WLC_IOCTL_MEDLEN);
+ }
+ return err;
+}
diff --git a/wl_cfg80211.h b/wl_cfg80211.h
old mode 100755
new mode 100644
index 9259fa7..dfb0404
--- a/wl_cfg80211.h
+++ b/wl_cfg80211.h
@@ -1,7 +1,7 @@
/*
* Linux cfg80211 driver
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -41,9 +41,15 @@
#include <dhd.h>
#ifdef DHD_LOG_DUMP
#include <dhd_log_dump.h>
+#include <dhd_debug.h>
#endif
#endif /* BCMDONGLEHOST */
+#if !defined(WL_FILS_IOV_VERSION)
+/* WL FILS IOV API version */
+#define WL_FILS_IOV_VERSION WL_FILS_IOV_VERSION_1_1
+#endif /* WL_FILS_IOV_VERSION */
+
#define WL_CFG_DRV_LOCK(lock, flags) (flags) = osl_spin_lock(lock)
#define WL_CFG_DRV_UNLOCK(lock, flags) osl_spin_unlock((lock), (flags))
@@ -135,6 +141,23 @@
#define WL_STAINFO_VER WL_STA_VER_4
#endif /* USE_STA_INFO_V6 */
+/* MSCS default configuration values */
+#ifndef MSCS_CFG_DEF_STREAM_TIMEOUT
+#define MSCS_CFG_DEF_STREAM_TIMEOUT 60000u /* TUs */
+#endif /* MSCS_CFG_DEF_STREAM_TIMEOUT */
+
+#ifndef MSCS_CFG_DEF_UP_LIMIT
+#define MSCS_CFG_DEF_UP_LIMIT 7u /* up limit */
+#endif /* MSCS_CFG_DEF_UP_LIMIT */
+
+#ifndef MSCS_CFG_DEF_FC_MASK
+#define MSCS_CFG_DEF_FC_MASK 0xF0u /* frame classifier mask */
+#endif /* MSCS_CFG_DEF_FC_MASK */
+
+#ifndef MSCS_CFG_DEF_TCLAS_MASK
+#define MSCS_CFG_DEF_TCLAS_MASK 0x5Fu /* TCLAS mask */
+#endif /* MSCS_CFG_DEF_TCLAS_MASK */
+
#define CH_TO_CHSPC(band, _channel) \
((_channel | band) | WL_CHANSPEC_BW_20 | WL_CHANSPEC_CTL_SB_NONE)
#define CHAN2G(_channel, _freq, _flags) { \
@@ -455,6 +478,12 @@
#define WL_CONS_ONLY(args) do { printf args; } while (0)
#endif /* defined(CUSTOMER_DBG_PREFIX_ENABLE) */
+#ifdef DBG_PRINT_SSID
+#define SSID_DBG(_ssid_) _ssid_
+#else /* DBG_PNO_SSID */
+#define SSID_DBG(_ssid_) "*****"
+#endif /* DBG_PRINT_SSID */
+
#ifdef DHD_DEBUG
#ifdef DHD_LOG_DUMP
#define WL_ERR(args) \
@@ -684,7 +713,11 @@
#define WL_MED_DWELL_TIME 400
#define WL_MIN_DWELL_TIME 100
#define WL_LONG_DWELL_TIME 1000
+#ifdef WL_MLO
+#define IFACE_MAX_CNT 7
+#else
#define IFACE_MAX_CNT 5
+#endif /* WL_MLO */
#define WL_SCAN_CONNECT_DWELL_TIME_MS 200
#define WL_SCAN_JOIN_PROBE_INTERVAL_MS 20
#define WL_SCAN_JOIN_ACTIVE_DWELL_TIME_MS 320
@@ -825,6 +858,14 @@
#define IS_RADAR_CHAN(flags) (flags & (IEEE80211_CHAN_RADAR | IEEE80211_CHAN_NO_IR))
#endif
+/* Join pref defines */
+#define JOIN_PREF_RSSI_SIZE 4 /* RSSI pref header size in bytes */
+#define JOIN_PREF_WPA_HDR_SIZE 4 /* WPA pref header size in bytes */
+#define JOIN_PREF_WPA_TUPLE_SIZE 12 /* Tuple size in bytes */
+#define JOIN_PREF_MAX_WPA_TUPLES 16 /* Max no of tuples */
+#define JOIN_PREF_MAX_BUF_SIZE (JOIN_PREF_RSSI_SIZE + JOIN_PREF_WPA_HDR_SIZE + \
+ (JOIN_PREF_WPA_TUPLE_SIZE * JOIN_PREF_MAX_WPA_TUPLES))
+
#if defined(STRICT_GCC_WARNINGS) && defined(__GNUC__) && (__GNUC__ > 4 || (__GNUC__ == \
4 && __GNUC_MINOR__ >= 6))
#define BCM_SET_LIST_FIRST_ENTRY(entry, ptr, type, member) \
@@ -896,6 +937,23 @@
typedef wifi_p2psd_gas_pub_act_frame_t wl_dpp_gas_af_t;
+#define DEFAULT_ASSOC_LISTEN 0xau
+#define DEFAULT_ROAM_SCAN_PRD 10u
+#define DEFAULT_FULL_ROAM_PRD 0x78u
+#define DEFAULT_ASSOC_RETRY 0x3u
+#define DEFAULT_WNM_CONF 0x505u
+#define DEFAULT_RECREATE_BI_TIMEOUT 20u
+
+struct preinit_iov;
+typedef int (*wl_iov_fn) (struct bcm_cfg80211 *cfg, struct net_device *dev, struct preinit_iov *v);
+
+typedef struct preinit_iov {
+ wl_iov_fn fn;
+ uint16 cmd_id; /* preinit iovar/ioctl cmd id */
+ int32 value; /* preinit iovar input value */
+ s8 *cmd_name; /* preinit ioctl cmd name */
+} preinit_iov_t;
+
/* driver status */
enum wl_status {
WL_STATUS_READY = 0,
@@ -952,6 +1010,8 @@
WL_IF_TYPE_IBSS = 8,
WL_IF_TYPE_MONITOR = 9,
WL_IF_TYPE_AIBSS = 10,
+ WL_IF_TYPE_MLO_STA_LINK = 11,
+ WL_IF_TYPE_MLO_AP_LINK = 12,
WL_IF_TYPE_MAX
} wl_iftype_t;
@@ -1059,6 +1119,7 @@
u32 reason;
wl_link_action_t link_action;
u8 curbssid[ETH_ALEN];
+ u8 ml_event;
u8 addr[ETH_ALEN];
u16 data_len;
void *data;
@@ -1395,7 +1456,7 @@
#endif /* ESCAN_BUF_OVERFLOW_MGMT */
struct afx_hdl {
- wl_af_params_t *pending_tx_act_frm;
+ wl_af_params_v1_t *pending_tx_act_frm;
struct ether_addr tx_dst_addr;
struct net_device *dev;
struct work_struct work;
@@ -1661,7 +1722,7 @@
struct wireless_dev *wdev; /* interface on which listen is requested */
} wl_loc_info_t;
-typedef enum wl_sar_modes {
+typedef enum wl_sar_events {
HEAD_SAR_BACKOFF_DISABLE = -1,
HEAD_SAR_BACKOFF_ENABLE = 0,
GRIP_SAR_BACKOFF_DISABLE,
@@ -1670,8 +1731,31 @@
NR_mmWave_SAR_BACKOFF_ENABLE,
NR_Sub6_SAR_BACKOFF_DISABLE,
NR_Sub6_SAR_BACKOFF_ENABLE,
- SAR_BACKOFF_DISABLE_ALL
-} wl_sar_modes_t;
+ NR_MMWAVE_NR_SUB6_SAR_BACKOFF_DISABLE,
+ NR_MMWAVE_NR_SUB6_SAR_BACKOFF_ENABLE,
+ MHS_SAR_BACKOFF_DISABLE,
+ MHS_SAR_BACKOFF_ENABLE,
+ SAR_BACKOFF_DISABLE_ALL,
+ SAR_BACKOFF_EVENT_MAX
+} wl_sar_events_t;
+
+#define SAR_MODE_DIS_ALL 0xff
+#define SAR_MODE_BIT_HEAD 0x01 /* bit 0 */
+#define SAR_MODE_BIT_GRIP 0x02 /* bit 1 */
+#define SAR_MODE_BIT_NR_MW 0x04 /* bit 2 */
+#define SAR_MODE_BIT_NR_S6 0x08 /* bit 3 */
+#define SAR_MODE_BIT_NR_MWS6 0x0C /* bits 3:2 */
+#define SAR_MODE_BIT_MHS 0x40 /* bit 6 */
+
+#define MAX_NUM_CONTROL 2
+typedef struct wl_sar_ctl_tbl {
+ wl_sar_events_t sar_evt_id;
+ int num_ctls;
+ struct {
+ bool enab;
+ uint8 setval;
+ } sar_mode[MAX_NUM_CONTROL];
+} wl_sar_ctl_tbl_t;
typedef enum
{
@@ -1755,6 +1839,8 @@
s32 bssidx;
u32 chan_cnt;
chanspec_t chanspecs[MAX_ROAM_CHANNEL];
+ bool auto_wpa_enabled; /* auto_wpa enabled for multi AKM */
+ bool seamless_psk; /* Multi-AKMs needing seamless PSK */
} wlcfg_assoc_info_t;
#define MAX_NUM_OF_ASSOCIATED_DEV 64
@@ -1865,8 +1951,8 @@
struct mutex usr_sync; /* maily for up/down synchronization */
struct mutex if_sync; /* maily for iface op synchronization */
struct mutex scan_sync; /* scan sync from different scan contexts */
- wl_scan_results_t *bss_list;
- wl_scan_results_t *scan_results;
+ wl_scan_results_v109_t *bss_list;
+ wl_scan_results_v109_t *scan_results;
/* scan request object for internal purpose */
struct wl_scan_req *scan_req_int;
@@ -2148,6 +2234,11 @@
bool sroam_turn_on;
bool sroamed;
#endif /* CONFIG_SILTENT_ROAM */
+ uint32 roam_allowed_band; /* roam allow band in order to purne roam candidate */
+ uint8 num_radios; /* number of active radios */
+ uint32 ap_bw_limit;
+ uint32 ap_bw_chspec;
+ bool frameburst_disabled;
};
/* Max auth timeout allowed in case of EAP is 70sec, additional 5 sec for
@@ -2205,8 +2296,38 @@
int16 deauth_RSSI;
} wl_wips_event_info_t;
-/* Added for HOSTAPD required ACS action */
+/* defined for hw_mode in hostapd.conf */
+enum hostapd_hw_mode {
+ HOSTAPD_MODE_IEEE80211B,
+ HOSTAPD_MODE_IEEE80211G,
+ HOSTAPD_MODE_IEEE80211A,
+ HOSTAPD_MODE_IEEE80211AD,
+ HOSTAPD_MODE_IEEE80211ANY,
+ NUM_HOSTAPD_MODES
+};
+
+typedef struct drv_acs_params {
+ enum hostapd_hw_mode hw_mode;
+ u32 band; /* band derived from hw_mode */
+ u32 ht_enabled;
+ u32 ht40_enabled;
+ u32 vht_enabled;
+ u32 he_enabled;
+ u16 ch_width;
+ unsigned int ch_list_len;
+ const u8 *ch_list;
+ const u32 *freq_list;
+ u32 freq_bands; /* band derived from freq list */
+ chanspec_t scc_chspec;
+} drv_acs_params_t;
+
+#define IS_5G_APCS_CHANNEL(channel) ((channel == 149) || \
+ (channel == 153) || \
+ (channel == 157) || \
+ (channel == 161))
+
#ifdef WL_SOFTAP_ACS
+/* Added for HOSTAPD required ACS action */
#define APCS_MAX_RETRY 10
#define APCS_DEFAULT_2G_CH 1
#define APCS_DEFAULT_5G_CH 149
@@ -2228,16 +2349,6 @@
BRCM_VENDOR_ATTR_ACS_LAST
};
-/* defined for hw_mode in hostapd.conf */
-enum hostapd_hw_mode {
- HOSTAPD_MODE_IEEE80211B,
- HOSTAPD_MODE_IEEE80211G,
- HOSTAPD_MODE_IEEE80211A,
- HOSTAPD_MODE_IEEE80211AD,
- HOSTAPD_MODE_IEEE80211ANY,
- NUM_HOSTAPD_MODES
-};
-
typedef struct acs_selected_channels {
u32 pri_freq; /* save slelcted primary frequency */
u32 sec_freq; /* save slelcted secondary frequency */
@@ -2247,21 +2358,6 @@
enum hostapd_hw_mode hw_mode;
} acs_selected_channels_t;
-typedef struct drv_acs_params {
- enum hostapd_hw_mode hw_mode;
- u32 band; /* band derived from hw_mode */
- u32 ht_enabled;
- u32 ht40_enabled;
- u32 vht_enabled;
- u32 he_enabled;
- u16 ch_width;
- unsigned int ch_list_len;
- const u8 *ch_list;
- const u32 *freq_list;
- u32 freq_bands; /* band derived from freq list */
- chanspec_t scc_chspec;
-} drv_acs_params_t;
-
typedef struct acs_delay_work {
struct delayed_work acs_delay_work;
u32 init_flag;
@@ -2293,11 +2389,11 @@
list_for_each_entry_safe((pos), (next), (head), member)
extern int ioctl_version;
-static inline wl_bss_info_t
-*next_bss(wl_scan_results_t *list, wl_bss_info_t *bss)
+static inline wl_bss_info_v109_t
+*next_bss(wl_scan_results_v109_t *list, wl_bss_info_v109_t *bss)
{
return bss = bss ?
- (wl_bss_info_t *)((uintptr) bss + dtoh32(bss->length)) : list->bss_info;
+ (wl_bss_info_v109_t *)((uintptr) bss + dtoh32(bss->length)) : list->bss_info;
}
static inline void
@@ -2319,12 +2415,10 @@
}
static inline struct net_info *
-wl_get_netinfo_by_fw_idx(struct bcm_cfg80211 *cfg, s32 bssidx, u8 ifidx)
+_wl_get_netinfo_by_fw_idx(struct bcm_cfg80211 *cfg, s32 bssidx, u8 ifidx)
{
struct net_info *_net_info, *next, *info = NULL;
- unsigned long int flags;
- WL_CFG_NET_LIST_SYNC_LOCK(&cfg->net_list_sync, flags);
GCC_DIAGNOSTIC_PUSH_SUPPRESS_CAST();
BCM_LIST_FOR_EACH_ENTRY_SAFE(_net_info, next, &cfg->net_list, list) {
GCC_DIAGNOSTIC_POP();
@@ -2334,7 +2428,19 @@
break;
}
}
+ return info;
+}
+
+static inline struct net_info *
+wl_get_netinfo_by_fw_idx(struct bcm_cfg80211 *cfg, s32 bssidx, u8 ifidx)
+{
+ unsigned long int flags;
+ struct net_info *info = NULL;
+
+ WL_CFG_NET_LIST_SYNC_LOCK(&cfg->net_list_sync, flags);
+ info = _wl_get_netinfo_by_fw_idx(cfg, bssidx, ifidx);
WL_CFG_NET_LIST_SYNC_UNLOCK(&cfg->net_list_sync, flags);
+
return info;
}
@@ -2407,13 +2513,15 @@
* already present which shouldn't have been the case.
* Attempt recovery.
*/
- WL_ERR(("Duplicate entry for bssidx=%d ifidx=%d present."
- " Can't add new entry\n", bssidx, ifidx));
- wl_probe_wdev_all(cfg);
+ if (bssidx != (u8)WL_INVALID) {
+ WL_ERR(("**Duplicate entry for bssidx=%d ifidx=%d present."
+ " Can't add new entry\n", bssidx, ifidx));
+ wl_probe_wdev_all(cfg);
#ifdef DHD_DEBUG
- ASSERT(0);
+ ASSERT(0);
#endif /* DHD_DEBUG */
- return -EINVAL;
+ return -EINVAL;
+ }
}
if (cfg->iface_cnt == IFACE_MAX_CNT)
return -ENOMEM;
@@ -2486,6 +2594,7 @@
cfg->iface_cnt = 0;
WL_CFG_NET_LIST_SYNC_UNLOCK(&cfg->net_list_sync, flags);
}
+
static inline u32
wl_get_status_all(struct bcm_cfg80211 *cfg, s32 status)
@@ -2505,6 +2614,7 @@
WL_CFG_NET_LIST_SYNC_UNLOCK(&cfg->net_list_sync, flags);
return cnt;
}
+
static inline void
wl_set_status_all(struct bcm_cfg80211 *cfg, s32 status, u32 op)
{
@@ -2769,6 +2879,7 @@
WL_CFG_NET_LIST_SYNC_UNLOCK(&cfg->net_list_sync, flags);
return prof;
}
+
static inline struct net_info *
wl_get_netinfo_by_netdev(struct bcm_cfg80211 *cfg, struct net_device *ndev)
{
@@ -2789,12 +2900,10 @@
}
static inline struct net_info *
-wl_get_netinfo_by_wdev(struct bcm_cfg80211 *cfg, struct wireless_dev *wdev)
+_wl_get_netinfo_by_wdev(struct bcm_cfg80211 *cfg, struct wireless_dev *wdev)
{
struct net_info *_net_info, *next, *info = NULL;
- unsigned long int flags;
- WL_CFG_NET_LIST_SYNC_LOCK(&cfg->net_list_sync, flags);
GCC_DIAGNOSTIC_PUSH_SUPPRESS_CAST();
BCM_LIST_FOR_EACH_ENTRY_SAFE(_net_info, next, &cfg->net_list, list) {
GCC_DIAGNOSTIC_POP();
@@ -2803,6 +2912,17 @@
break;
}
}
+ return info;
+}
+
+static inline struct net_info *
+wl_get_netinfo_by_wdev(struct bcm_cfg80211 *cfg, struct wireless_dev *wdev)
+{
+ struct net_info *info = NULL;
+ unsigned long int flags;
+
+ WL_CFG_NET_LIST_SYNC_LOCK(&cfg->net_list_sync, flags);
+ info = _wl_get_netinfo_by_wdev(cfg, wdev);
WL_CFG_NET_LIST_SYNC_UNLOCK(&cfg->net_list_sync, flags);
return info;
}
@@ -3001,7 +3121,7 @@
/* Enable PSK key mgmt offload */
#define WL_PSK_OFFLOAD
#define WL_SUPP_PMK_LEN 32u
-#endif /* LINUX_VERSION_CODE >= 4, 13, 0 && OEM_ANDROID && BCMSUP_4WAY_HANDSHAKE */
+#endif /* LINUX_VERSION_CODE >= 4, 13, 0 && BCMSUP_4WAY_HANDSHAKE */
extern s32 wl_cfg80211_attach(struct net_device *ndev, void *context);
extern void wl_cfg80211_detach(struct bcm_cfg80211 *cfg);
@@ -3009,7 +3129,7 @@
extern void wl_cfg80211_event(struct net_device *ndev, const wl_event_msg_t *e,
void *data);
extern s32 wl_cfg80211_handle_critical_events(struct bcm_cfg80211 *cfg,
- struct wireless_dev *wdev, const wl_event_msg_t * e);
+ struct wireless_dev *wdev, const wl_event_msg_t * e, void *data);
void wl_cfg80211_set_parent_dev(void *dev);
struct device *wl_cfg80211_get_parent_dev(void);
@@ -3157,9 +3277,7 @@
extern u8 wl_get_action_category(void *frame, u32 frame_len);
extern int wl_get_public_action(void *frame, u32 frame_len, u8 *ret_action);
-#ifdef WL_CFG80211_VSDB_PRIORITIZE_SCAN_REQUEST
struct net_device *wl_cfg80211_get_remain_on_channel_ndev(struct bcm_cfg80211 *cfg);
-#endif /* WL_CFG80211_VSDB_PRIORITIZE_SCAN_REQUEST */
#ifdef WL_SUPPORT_ACS
#define ACS_MSRMNT_DELAY 1000 /* dump_obss delay in ms */
@@ -3173,6 +3291,17 @@
#define IDLE_TOKEN_IDX 12
#endif /* WL_SUPPORT_ACS */
+#ifdef WL_UNII4_CHAN
+#define IS_5G_UNII4_165_CHANNEL(chspec) (CHSPEC_IS5G(chspec) && \
+ (wf_chspec_primary20_chan(chspec) == 165))
+#define UINII4_169 169
+#define UINII4_173 173
+#define UINII4_177 177
+#define IS_UNII4_CHANNEL(channel) ((channel == UINII4_169) || \
+ (channel == UINII4_173) || \
+ (channel == UINII4_177))
+#endif /* WL_UNII4_CHAN */
+
#ifdef BCMWAPI_WPI
#define is_wapi(cipher) (cipher == WLAN_CIPHER_SUITE_SMS4) ? 1 : 0
#endif /* BCMWAPI_WPI */
@@ -3331,7 +3460,7 @@
bool wl_cfg80211_is_dpp_frame(void *frame, u32 frame_len);
const char *get_dpp_pa_ftype(enum wl_dpp_ftype ftype);
bool wl_cfg80211_is_dpp_gas_action(void *frame, u32 frame_len);
-extern bool wl_cfg80211_find_gas_subtype(u8 subtype, u16 adv_id, u8* data, u32 len);
+extern bool wl_cfg80211_find_gas_subtype(u8 subtype, u16 adv_id, u8* data, s32 len);
#ifdef ESCAN_CHANNEL_CACHE
extern void update_roam_cache(struct bcm_cfg80211 *cfg, int ioctl_ver);
#endif /* ESCAN_CHANNEL_CACHE */
@@ -3351,6 +3480,15 @@
} \
} while (0)
+#define WL_CHANNEL_COPY_FLAG(band_chan_arr) \
+do { \
+ u32 arr_size, k; \
+ arr_size = ARRAYSIZE(band_chan_arr); \
+ for (k = 0; k < arr_size; k++) { \
+ band_chan_arr[k].orig_flags = band_chan_arr[k].flags; \
+ } \
+} while (0)
+
#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 9, 0))
#define CFG80211_PUT_BSS(wiphy, bss) cfg80211_put_bss(wiphy, bss);
#else
@@ -3495,4 +3633,38 @@
#ifdef CONFIG_SILENT_ROAM
int wl_cfg80211_sroam_config(struct bcm_cfg80211 *cfg, struct net_device *dev, bool set);
#endif /* CONFIG_SILENT_ROAM */
+
+int wl_cfg80211_get_roam_params(struct net_device *dev, uint32 *data, uint16 data_len, uint16 id);
+int wl_cfg80211_set_roam_params(struct net_device *dev, uint32 *data, uint16 data_len, uint16 id);
+
+extern void wl_cfg80211_wdev_lock(struct wireless_dev *wdev);
+extern void wl_cfg80211_wdev_unlock(struct wireless_dev *wdev);
+
+/* Added wl_reassoc_params_cvt_v1 due to mis-sync between DHD and FW
+ * Because Dongle use wl_reassoc_params_v1_t for WLC_REASSOC
+ * Legacy FW use wl_reassoc_params_t
+ */
+typedef struct wl_reassoc_params_cvt_v1 {
+ uint16 version;
+ uint16 flags;
+ wl_reassoc_params_t params;
+} wl_reassoc_params_cvt_v1_t;
+
+typedef struct wl_ext_reassoc_params_cvt_v1 {
+ uint16 version;
+ uint16 length;
+ uint32 flags;
+ wl_reassoc_params_cvt_v1_t params;
+} wl_ext_reassoc_params_cvt_v1_t;
+
+#define WL_REASSOC_VERSION_V0 0u
+#define WL_REASSOC_VERSION_V1 WL_EXTJOIN_VERSION_V1
+#define WL_REASSOC_VERSION_V2 WL_EXT_REASSOC_VER_1
+#ifdef WL_CP_COEX
+struct wl_cp_coex {
+ int ch_cpcoex;
+ int ch_4g;
+ int ch_5g;
+};
+#endif /* WL_CP_COEX */
#endif /* _wl_cfg80211_h_ */
diff --git a/wl_cfg_btcoex.c b/wl_cfg_btcoex.c
index 891762a..c7d3482 100644
--- a/wl_cfg_btcoex.c
+++ b/wl_cfg_btcoex.c
@@ -1,7 +1,7 @@
/*
* Linux cfg80211 driver - Dongle Host Driver (DHD) related
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -686,7 +686,7 @@
uint16 tlvs_len;
version = dtoh16(*(uint16 *)resp);
- if (version & (BCM_IOV_XTLV_VERSION | BCM_IOV_BATCH_MASK)) {
+ if (version & (BCM_IOV_XTLV_VERSION_0 | BCM_IOV_BATCH_MASK)) {
if (!resp->count) {
return BCME_RANGE;
} else {
@@ -748,7 +748,7 @@
bcm_iov_batch_subcmd_t *sub_cmd;
/* Fill the header */
- b_buf->version = htol16(BCM_IOV_XTLV_VERSION | BCM_IOV_BATCH_MASK);
+ b_buf->version = htol16(BCM_IOV_XTLV_VERSION_0 | BCM_IOV_BATCH_MASK);
b_buf->count = 1;
b_buf->is_set = is_set;
len = OFFSETOF(bcm_iov_batch_buf_t, cmds[0]);
@@ -794,9 +794,6 @@
{
int i;
uwbcx_coex_bitmap_t *coex_bitmap = (uwbcx_coex_bitmap_t *) (&coex_bitmap_cfg->coex_bitmap);
- coex_bitmap_cfg->version = UWBCX_COEX_BITMAP_VERSION_V2;
- coex_bitmap_cfg->len = sizeof(*coex_bitmap_cfg);
- coex_bitmap_cfg->band = UWBCX_BAND_6G;
for (i = start_ch_idx; i <= end_ch_idx; i++) {
if (i < 16u) {
@@ -880,6 +877,9 @@
}
bzero(&coex_bitmap_cfg, sizeof(uwbcx_coex_bitmap_v2_t));
+ coex_bitmap_cfg.version = UWBCX_COEX_BITMAP_VERSION_V2;
+ coex_bitmap_cfg.len = sizeof(coex_bitmap_cfg);
+ coex_bitmap_cfg.band = UWBCX_BAND_6G;
/* Validate UWB Coex channel in case of turnning on */
if (enable && (((start_ch_idx = wl_cfg_uwb_coex_get_ch_idx(start_ch)) < 0) ||
diff --git a/wl_cfg_cellavoid.c b/wl_cfg_cellavoid.c
index 7499908..28fd28d 100755
--- a/wl_cfg_cellavoid.c
+++ b/wl_cfg_cellavoid.c
@@ -1,7 +1,7 @@
/*
* Cellular channel avoidance implementation
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -155,7 +155,7 @@
wl_cellavoid_info_t *cellavoid_info;
int ret = BCME_OK;
- WL_INFORM(("%s: Enter\n", __FUNCTION__));
+ WL_MEM(("%s: Enter\n", __FUNCTION__));
cellavoid_info = (wl_cellavoid_info_t *)
MALLOCZ(cfg->osh, sizeof(*cellavoid_info));
if (cellavoid_info == NULL) {
@@ -191,7 +191,7 @@
{
wl_cellavoid_info_t *cellavoid_info = cfg->cellavoid_info;
- WL_INFORM(("%s: Enter\n", __FUNCTION__));
+ WL_MEM(("%s: Enter\n", __FUNCTION__));
if (!cellavoid_info) {
return;
}
@@ -249,7 +249,7 @@
wl_cellavoid_info_t *cellavoid_info = cfg->cellavoid_info;
int ret = BCME_ERROR;
- WL_INFORM(("%s: Enter\n", __FUNCTION__));
+ WL_MEM(("%s: Enter\n", __FUNCTION__));
if (!cellavoid_info) {
return ret;
}
@@ -472,7 +472,7 @@
{
wl_cellavoid_chan_info_t *chan_info, *next;
- WL_INFORM(("%s: Enter\n", __FUNCTION__));
+ WL_MEM(("%s: Enter\n", __FUNCTION__));
GCC_DIAGNOSTIC_PUSH_SUPPRESS_CAST();
list_for_each_entry_safe(chan_info, next, &cellavoid_info->cell_chan_info_list, list) {
GCC_DIAGNOSTIC_POP();
@@ -493,7 +493,7 @@
{
wl_cellavoid_chan_info_t *chan_info, *next;
- WL_INFORM(("%s: Enter\n", __FUNCTION__));
+ WL_MEM(("%s: Enter\n", __FUNCTION__));
GCC_DIAGNOSTIC_PUSH_SUPPRESS_CAST();
list_for_each_entry_safe(chan_info, next, &cellavoid_info->avail_chan_info_list, list) {
GCC_DIAGNOSTIC_POP();
@@ -513,14 +513,15 @@
{
wl_cellavoid_chan_info_t *chan_info, *next;
wl_cellavoid_chan_info_t *ret = NULL;
+ char chanspec_str[CHANSPEC_STR_LEN];
GCC_DIAGNOSTIC_PUSH_SUPPRESS_CAST();
list_for_each_entry_safe(chan_info, next, &cellavoid_info->avail_chan_info_list, list) {
GCC_DIAGNOSTIC_POP();
if (chan_info->chanspec == chanspec) {
list_del(&chan_info->list);
- WL_INFORM(("%s: removed in list, chanspec: %x\n",
- __FUNCTION__, chanspec));
+ wf_chspec_ntoa(chanspec, chanspec_str);
+ WL_INFORM(("removed %s (0x%x) in avail list\n", chanspec_str, chanspec));
ret = chan_info;
break;
}
@@ -546,6 +547,22 @@
return CELLAVOID_STATE_CH_SAFE;
}
+static cellavoid_ch_state_t
+wl_cellavoid_get_chan_info_overlap(wl_cellavoid_info_t *cellavoid_info, chanspec_t chanspec)
+{
+ wl_cellavoid_chan_info_t *chan_info, *next;
+
+ GCC_DIAGNOSTIC_PUSH_SUPPRESS_CAST();
+ list_for_each_entry_safe(chan_info, next, &cellavoid_info->cell_chan_info_list, list) {
+ GCC_DIAGNOSTIC_POP();
+ if (wf_chspec_overlap(chan_info->chanspec, chanspec)) {
+ return CELLAVOID_STATE_CH_UNSAFE;
+ }
+ }
+
+ return CELLAVOID_STATE_CH_SAFE;
+}
+
bool
wl_cellavoid_is_safe(void *cai, chanspec_t chanspec)
{
@@ -559,6 +576,19 @@
}
bool
+wl_cellavoid_is_safe_overlap(void *cai, chanspec_t chanspec)
+{
+ wl_cellavoid_info_t *cellavoid_info = cai;
+
+ if (wl_cellavoid_get_chan_info_overlap(cellavoid_info, chanspec)
+ == CELLAVOID_STATE_CH_UNSAFE) {
+ return FALSE;
+ } else {
+ return TRUE;
+ }
+}
+
+bool
wl_cellavoid_mandatory_isset(void *cai, enum nl80211_iftype type)
{
bool mandatory = FALSE;
@@ -640,7 +670,11 @@
* narrower bw, small channel number comes later after sorting
*/
static int
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(5, 10, 70))
+wl_cellavoid_chan_info_compare(void *priv, const struct list_head *a, const struct list_head *b)
+#else
wl_cellavoid_chan_info_compare(void *priv, struct list_head *a, struct list_head *b)
+#endif
{
uint8 i1_chan, i2_chan;
uint16 i1_bw, i2_bw;
@@ -689,13 +723,16 @@
{
wl_cellavoid_chan_info_t *chan_info, *next;
char chanspec_str[CHANSPEC_STR_LEN];
+ int cell_chan_info_cnt = 0, avail_chan_info_cnt = 0;
+ WL_MEM(("%s: Enter\n", __FUNCTION__));
GCC_DIAGNOSTIC_PUSH_SUPPRESS_CAST();
list_for_each_entry_safe(chan_info, next, &cellavoid_info->cell_chan_info_list, list) {
GCC_DIAGNOSTIC_POP();
wf_chspec_ntoa(chan_info->chanspec, chanspec_str);
WL_MEM(("Cellular : chanspec %s(%x), pwrcap %d\n",
chanspec_str, chan_info->chanspec, chan_info->pwr_cap));
+ cell_chan_info_cnt++;
}
GCC_DIAGNOSTIC_PUSH_SUPPRESS_CAST();
@@ -704,8 +741,49 @@
wf_chspec_ntoa(chan_info->chanspec, chanspec_str);
WL_MEM(("Avail : chanspec %s(%x), pwrcap %d\n",
chanspec_str, chan_info->chanspec, chan_info->pwr_cap));
+ avail_chan_info_cnt++;
}
+ WL_INFORM_MEM(("%s: cellavoid_info->cell_chan_info_cnt(%d), mandatory_flag(%d), "
+ "cell_chan_info_cnt(%d), avail_chan_info_cnt(%d)\n",
+ __FUNCTION__, cellavoid_info->cell_chan_info_cnt,
+ cellavoid_info->mandatory_flag, cell_chan_info_cnt, avail_chan_info_cnt));
+}
+
+void wl_cellavoid_sanity_check_chan_info_list(void *cai)
+{
+ wl_cellavoid_info_t *cellavoid_info = cai;
+ wl_cellavoid_chan_info_t *chan_info, *next;
+ char chanspec_str[CHANSPEC_STR_LEN];
+ int cell_chan_info_cnt = 0, avail_chan_info_cnt = 0;
+
+ WL_MEM(("%s: Enter\n", __FUNCTION__));
+ GCC_DIAGNOSTIC_PUSH_SUPPRESS_CAST();
+ list_for_each_entry_safe(chan_info, next, &cellavoid_info->cell_chan_info_list, list) {
+ GCC_DIAGNOSTIC_POP();
+ wf_chspec_ntoa(chan_info->chanspec, chanspec_str);
+ WL_MEM(("Cellular : chanspec %s(%x), pwrcap %d\n",
+ chanspec_str, chan_info->chanspec, chan_info->pwr_cap));
+ cell_chan_info_cnt++;
+ }
+
+ GCC_DIAGNOSTIC_PUSH_SUPPRESS_CAST();
+ list_for_each_entry_safe(chan_info, next, &cellavoid_info->avail_chan_info_list, list) {
+ GCC_DIAGNOSTIC_POP();
+ wf_chspec_ntoa(chan_info->chanspec, chanspec_str);
+ WL_MEM(("Avail : chanspec %s(%x), pwrcap %d\n",
+ chanspec_str, chan_info->chanspec, chan_info->pwr_cap));
+ avail_chan_info_cnt++;
+ }
+
+ WL_INFORM_MEM(("%s: cellavoid_info->cell_chan_info_cnt(%d), mandatory_flag(%d), "
+ "cell_chan_info_cnt(%d), avail_chan_info_cnt(%d)\n",
+ __FUNCTION__, cellavoid_info->cell_chan_info_cnt,
+ cellavoid_info->mandatory_flag, cell_chan_info_cnt, avail_chan_info_cnt));
+
+ if ((cell_chan_info_cnt == 0) && (avail_chan_info_cnt == 0)) {
+ WL_ERR(("### both cell&avail channel list are zero!! ###\n"));
+ }
}
#endif /* WL_CELLULAR_CHAN_AVOID_DUMP */
@@ -756,6 +834,7 @@
if (chan_info == NULL) {
goto free_list;
}
+ WL_MEM(("chanspec %x is added to avail_chan_list\n", channel->hw_value));
/* Move allocated channel item(20Mhz)
* to the safe channel list (avail channel list)
@@ -785,6 +864,7 @@
if (chan_info == NULL) {
goto free_list;
}
+ WL_MEM(("chanspec %x is added to avail_chan_list\n", chanspec));
/* Add 40/80 chanspec item to the available channel list */
wl_cellavoid_move_chan_info_to_avail_chan_list(cellavoid_info,
@@ -818,6 +898,7 @@
int i, err;
chanspec_t chanspec = 0;
char chanspec_str[CHANSPEC_STR_LEN];
+ uint32 restrict_chan, chaninfo;
/* Get chan_info_list or chanspec from FW */
#define LOCAL_BUF_LEN 4096
@@ -861,12 +942,19 @@
if (legacy_chan_info) {
chanspec = (chanspec_t)
dtoh32(((wl_uint32_list_t *)dngl_chan_list)->element[i]);
+ restrict_chan = 0x0;
} else {
chanspec = (chanspec_t)dtoh32
(((wl_chanspec_list_v1_t *)dngl_chan_list)->chspecs[i].chanspec);
+
+ chaninfo = dtoh32
+ (((wl_chanspec_list_v1_t *)dngl_chan_list)->chspecs[i].chaninfo);
+ restrict_chan = ((chaninfo & WL_CHAN_RADAR) ||
+ (chaninfo & WL_CHAN_PASSIVE) ||
+ (chaninfo & WL_CHAN_CLM_RESTRICTED));
}
- if (chan_info->chanspec == chanspec) {
+ if ((!restrict_chan) && (chan_info->chanspec == chanspec)) {
found = TRUE;
break;
}
@@ -895,6 +983,7 @@
struct ieee80211_supported_band *sband;
int ret;
+ WL_MEM(("%s: Enter\n", __FUNCTION__));
sband = wiphy->bands[IEEE80211_BAND_2GHZ];
if (!sband || !sband->n_channels) {
WL_ERR(("No 2ghz channel exists\n"));
@@ -951,7 +1040,7 @@
subcmd->flags = htod16(WL_CELL_AVOID_REMOVE_CH_INFO);
ret = wldev_iovar_setbuf(bcmcfg_to_prmry_ndev(cfg), "cellavoid", (char *)iov_buf,
- total_size, cfg->ioctl_buf, WLC_IOCTL_SMLEN, NULL);
+ total_size, cfg->ioctl_buf, WLC_IOCTL_SMLEN, &cfg->ioctl_buf_sync);
if (ret != BCME_OK) {
WL_ERR(("fail to restore txpwrcap ret : %d\n", ret));
}
@@ -1010,7 +1099,7 @@
ASSERT(cellavoid_info->cell_chan_info_cnt == i);
ret = wldev_iovar_setbuf(bcmcfg_to_prmry_ndev(cfg), "cellavoid", (char *)iov_buf,
- total_size, cfg->ioctl_buf, WLC_IOCTL_MEDLEN, NULL);
+ total_size, cfg->ioctl_buf, WLC_IOCTL_MEDLEN, &cfg->ioctl_buf_sync);
if (ret != BCME_OK) {
WL_ERR(("fail to set txpwrcap ret : %d\n", ret));
}
@@ -1033,10 +1122,8 @@
}
if (i == MAX_AP_INTERFACE) {
+ WL_ERR(("No empty slot, reset all slots.\n"));
for (i = 0; i < MAX_AP_INTERFACE; i++) {
- WL_ERR(("No empty slot, name %s, req_band %x in slot %d\n",
- cellavoid_info->req_band[i].ndev->name,
- cellavoid_info->req_band[i].req_band, i));
cellavoid_info->req_band[i].ndev = NULL;
cellavoid_info->req_band[i].req_band = WLC_BAND_INVALID;
}
@@ -1058,6 +1145,13 @@
WL_INFORM_MEM(("name %s, req_band %x is in slot %d\n",
cellavoid_info->req_band[i].ndev->name, cellavoid_info->req_band[i].req_band, i));
+#ifndef WL_SOFTAP_6G
+ if (cellavoid_info->req_band[i].req_band == WLC_BAND_6G) {
+ WL_INFORM_MEM(("6G softap is not supported\n"));
+ return BCME_UNSUPPORTED;
+ }
+#endif /* !WL_SOFTAP_6G */
+
return BCME_OK;
}
@@ -1074,11 +1168,7 @@
}
if (i == MAX_AP_INTERFACE) {
- for (i = 0; i < MAX_AP_INTERFACE; i++) {
- WL_ERR(("No empty slot, id %d, name %s, req_band %x\n",
- i, cellavoid_info->req_band[i].ndev->name,
- cellavoid_info->req_band[i].req_band));
- }
+ WL_ERR(("No matched slot, ignore.\n"));
return;
}
@@ -1176,9 +1266,16 @@
* so the first one is the widest one
*/
if (wf_chspec_ctlchan(chan_info->chanspec) == wf_chspec_ctlchan(chanspec)) {
- ret = chan_info;
- WL_INFORM_MEM(("chanspec %x found in avail list\n", chan_info->chanspec));
- goto exit;
+ /* check the overlap for 5G band only */
+ if (CHSPEC_IS2G(chan_info->chanspec) ||
+ wl_cellavoid_is_safe_overlap(cellavoid_info,
+ chan_info->chanspec)) {
+ ret = chan_info;
+ WL_INFORM_MEM(("ctrl channel %d (0x%x) found in avail list\n",
+ wf_chspec_ctlchan(chan_info->chanspec),
+ chan_info->chanspec));
+ goto exit;
+ }
}
}
@@ -1199,8 +1296,8 @@
*/
if (wf_chspec_ctlchan(chan_info->chanspec) == wf_chspec_ctlchan(chanspec)) {
ret = chan_info;
- WL_INFORM_MEM(("chanspec %x found in cellular list\n",
- chan_info->chanspec));
+ WL_INFORM_MEM(("ctrl channel %d (0x%x) found in cellular list\n",
+ wf_chspec_ctlchan(chan_info->chanspec), chan_info->chanspec));
goto exit;
}
}
@@ -1294,6 +1391,7 @@
return chanspec;
}
+
chanspec_t
wl_cellavoid_find_widechspec_fromchspec(void *cai, chanspec_t chanspec)
{
@@ -1578,62 +1676,6 @@
return BCME_OK;
}
-static chanspec_bw_t
-wl_cellavoid_next_bw(chanspec_bw_t bw)
-{
- /* cell avoidance supports upto bw80 */
- switch (bw) {
- case WL_CHANSPEC_BW_20:
- bw = WL_CHANSPEC_BW_40;
- break;
- case WL_CHANSPEC_BW_40:
- bw = WL_CHANSPEC_BW_80;
- break;
- default:
- bw = INVCHANSPEC;
- break;
- }
- return bw;
-}
-
-static void
-wl_cellavoid_update_cell_channels(wl_cellavoid_info_t *cellavoid_info,
- chanspec_band_t band, int ch, chanspec_bw_t start_bw, int8 pwr_cap)
-{
- chanspec_bw_t bw;
- chanspec_t chspec_upper;
- wl_cellavoid_chan_info_t *chan_info;
-
- if (band == WL_CHANSPEC_BAND_5G && ch != 165) {
- for (bw = start_bw; bw != INVCHANSPEC; bw = wl_cellavoid_next_bw(bw)) {
- chspec_upper = wf_create_chspec_from_primary(ch, bw, band);
- if (!wf_chspec_valid(chspec_upper)) {
- continue;
- }
- if (wl_cellavoid_get_chan_info(cellavoid_info, chspec_upper)
- == CELLAVOID_STATE_CH_SAFE) {
- /* get chan_info for moving to cell list from avail list */
- chan_info =
- wl_cellavoid_get_chan_info_from_avail_chan_list(
- cellavoid_info, chspec_upper);
- if (chan_info == NULL) {
- /* create new one if the chan_info doesn't exist */
- chan_info =
- wl_cellavoid_alloc_chan_info(
- cellavoid_info, chspec_upper);
- }
- if (chan_info != NULL) {
- chan_info->pwr_cap = pwr_cap;
- wl_cellavoid_move_chan_info_to_cell_chan_list(
- cellavoid_info, chan_info);
- WL_INFORM_MEM(("added chanspec 0x%x to cell list\n",
- chspec_upper));
- }
- }
- }
- }
-}
-
static int
wl_cellavoid_set_cell_channels(struct bcm_cfg80211 *cfg, wl_cellavoid_param_t *param)
{
@@ -1645,7 +1687,7 @@
wl_cellavoid_chan_info_t *chan_info;
chanspec_t chspecs[WF_NUM_SIDEBANDS_160MHZ];
- WL_INFORM(("%s: Enter\n", __FUNCTION__));
+ WL_MEM(("%s: Enter\n", __FUNCTION__));
if (!cellavoid_info || !param) {
return -EPERM;
}
@@ -1700,10 +1742,6 @@
/* Move this chan info to the unsafe channel list(cellular channel list */
wl_cellavoid_move_chan_info_to_cell_chan_list(cellavoid_info, chan_info);
-
- /* update all possible channels if there is missing channel from host */
- wl_cellavoid_update_cell_channels(cellavoid_info,
- param_band, param_ch, param_bw, param->chan_param[i].pwr_cap);
}
}
@@ -1768,6 +1806,7 @@
BCM_REFERENCE(wdev);
+ WL_INFORM(("%s: Enter\n", __FUNCTION__));
bzero(¶m, sizeof(param));
if (len <= 0) {
WL_ERR(("Length of the nlattr is not valid len : %d\n", len));
diff --git a/wl_cfg_cellavoid.h b/wl_cfg_cellavoid.h
index ab6bc0b..f35905c 100644
--- a/wl_cfg_cellavoid.h
+++ b/wl_cfg_cellavoid.h
@@ -1,7 +1,7 @@
/*
* Cellular channel avoidance implementation
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -50,6 +50,9 @@
extern void wl_cellavoid_set_csa_done(void *cai);
extern bool wl_cellavoid_mandatory_isset(void *cai, enum nl80211_iftype type);
extern bool wl_cellavoid_is_safe(void *cai, chanspec_t chanspec);
+extern bool wl_cellavoid_is_safe_overlap(void *cai, chanspec_t chanspec);
extern wifi_interface_mode wl_cellavoid_mandatory_to_usable_channel_filter(void *cai);
-
+#ifdef WL_CELLULAR_CHAN_AVOID_DUMP
+extern void wl_cellavoid_sanity_check_chan_info_list(void *cai);
+#endif /* WL_CELLULAR_CHAN_AVOID_DUMP */
#endif /* _wl_cfg_cellavoid_h_ */
diff --git a/wl_cfgnan.c b/wl_cfgnan.c
old mode 100755
new mode 100644
index 8c8ed56..badb453
--- a/wl_cfgnan.c
+++ b/wl_cfgnan.c
@@ -1,7 +1,7 @@
/*
* Neighbor Awareness Networking
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -57,6 +57,8 @@
static int wl_cfgnan_cache_disc_result(struct bcm_cfg80211 *cfg, void * data,
u16 *disc_cache_update_flags);
static int wl_cfgnan_remove_disc_result(struct bcm_cfg80211 * cfg, uint8 local_subid);
+static int wl_cfgnan_reset_disc_result(struct bcm_cfg80211 *cfg,
+ nan_disc_result_cache *disc_res);
static nan_disc_result_cache * wl_cfgnan_get_disc_result(struct bcm_cfg80211 *cfg,
uint8 remote_pubid, struct ether_addr *peer);
#endif /* WL_NAN_DISC_CACHE */
@@ -105,6 +107,21 @@
nan_ranging_inst_t *ranging_inst);
#endif /* RTT_SUPPORT */
static void wl_cfgnan_periodic_nmi_rand_addr(struct work_struct *work);
+static uint8 wl_cfgnan_map_nan_prot_csid_to_host_csid(uint8 prot_csid);
+static uint8 wl_cfgnan_map_host_csid_to_nan_prot_csid(uint8 host_csid);
+
+typedef struct nan_csid_map {
+ uint16 fw_csid;
+ uint16 host_csid;
+} nan_csid_map_t;
+
+nan_csid_map_t nan_csid_map_table[] = {
+ {NAN_SEC_ALGO_NONE, 0},
+ {NAN_SEC_ALGO_NCS_SK_CCM_128, WL_NAN_CIPHER_SUITE_SHARED_KEY_128_MASK},
+ {NAN_SEC_ALGO_NCS_SK_GCM_256, WL_NAN_CIPHER_SUITE_SHARED_KEY_256_MASK},
+ {NAN_SEC_ALGO_NCS_PK_CCM_128, WL_NAN_CIPHER_SUITE_PUBLIC_KEY_128_MASK},
+ {NAN_SEC_ALGO_NCS_PK_GCM_256, WL_NAN_CIPHER_SUITE_PUBLIC_KEY_256_MASK}
+};
static const char *
nan_role_to_str(u8 role)
@@ -371,6 +388,7 @@
clrbit(cfg->nancfg->svc_inst_id_mask, inst_id-1);
return ret;
}
+
s32 wl_cfgnan_parse_sdea_data(osl_t *osh, const uint8 *p_attr,
uint16 len, nan_event_data_t *tlv_data)
{
@@ -713,8 +731,124 @@
}
static s32
+wl_cfgnan_parse_scid_info(osl_t *osh, const uint8 *p_attr,
+ uint16 len, nan_event_data_t *tlv_data)
+{
+ s32 ret = BCME_OK;
+ s8 buf_end = 0;
+ const wifi_nan_sec_ctx_id_info_attr_t *scid_info_attr;
+ wifi_nan_sec_ctx_id_field_t *p = NULL;
+ uint16 scid_len;
+
+ /* security context id attribute */
+ scid_info_attr = (const wifi_nan_sec_ctx_id_info_attr_t *)p_attr;
+ /* attribute ID */
+ WL_TRACE(("> attr id: 0x%02x\n", scid_info_attr->attr_id));
+
+ /* attribute length */
+ WL_TRACE(("> attr len: 0x%x\n", scid_info_attr->len));
+
+ scid_len = scid_info_attr->len;
+
+ if (scid_len > NAN_MAX_SCID_BUF_LEN) {
+ WL_ERR(("Invalid scid len\n"));
+ ret = BCME_BADLEN;
+ goto fail;
+ }
+ buf_end = sizeof(*scid_info_attr) + scid_len;
+ if (buf_end > len) {
+ WL_ERR(("Invalid event buffer len\n"));
+ ret = BCME_BUFTOOSHORT;
+ goto fail;
+ }
+
+ p = (wifi_nan_sec_ctx_id_field_t *)(scid_info_attr->var);
+ scid_len = p->sec_ctx_id_type_len;
+
+ tlv_data->scid.dlen = scid_len;
+ tlv_data->scid.data = MALLOCZ(osh, scid_len);
+ if (!tlv_data->scid.data) {
+ WL_ERR(("%s: memory allocation failed\n", __FUNCTION__));
+ tlv_data->scid.dlen = 0;
+ ret = BCME_NOMEM;
+ goto fail;
+ }
+
+ (void)memcpy_s(tlv_data->scid.data, tlv_data->scid.dlen, p->var, scid_len);
+ return ret;
+fail:
+ if (tlv_data->scid.data) {
+ MFREE(osh, tlv_data->scid.data, tlv_data->scid.dlen);
+ tlv_data->scid.data = NULL;
+ }
+
+ WL_DBG(("Parse SCID event data, status = %d\n", ret));
+ return ret;
+}
+
+static s32
+wl_cfgnan_parse_csid_data(osl_t *osh, const uint8 *p_attr,
+ uint16 len, nan_event_data_t *tlv_data, uint16 type)
+{
+ s32 ret = BCME_OK;
+ const wifi_nan_sec_cipher_suite_info_attr_t *csid_info_attr;
+ const wifi_nan_sec_cipher_suite_field_t *csid_field = NULL;
+ uint8 csid_len, csid_offset;
+
+ /* security context id attribute */
+ csid_info_attr = (const wifi_nan_sec_cipher_suite_info_attr_t *)p_attr;
+ /* attribute ID */
+ WL_TRACE(("> attr id: 0x%02x\n", csid_info_attr->attr_id));
+
+ /* attribute length */
+ WL_TRACE(("> attr len: 0x%x\n", csid_info_attr->len));
+
+ csid_len = csid_info_attr->len;
+
+ if (csid_len > len) {
+ WL_ERR(("Invalid event buffer len\n"));
+ ret = BCME_BUFTOOSHORT;
+ goto fail;
+ }
+
+ csid_offset = (OFFSETOF(wifi_nan_sec_cipher_suite_info_attr_t, var) -
+ NAN_ATTR_HDR_LEN);
+
+ csid_field = (wifi_nan_sec_cipher_suite_field_t *)(csid_info_attr->var);
+ csid_len -= csid_offset;
+
+ if (type == WL_NAN_XTLV_SD_DISC_RESULTS) {
+ while (csid_len >= sizeof(*csid_field)) {
+ if (csid_field->inst_id == tlv_data->pub_id) {
+ tlv_data->peer_cipher_suite = csid_field->cipher_suite_id;
+ break;
+ } else {
+ csid_field++;
+ csid_len -= sizeof(*csid_field);
+ }
+ }
+ } else {
+ if (csid_len != sizeof(*csid_field)) {
+ ret = BCME_BADLEN;
+ goto fail;
+ }
+ tlv_data->peer_cipher_suite = csid_field->cipher_suite_id;
+ }
+
+ /* Default csid is zero, if peer_cipher_suite is not updated */
+ tlv_data->peer_cipher_suite =
+ wl_cfgnan_map_nan_prot_csid_to_host_csid(tlv_data->peer_cipher_suite);
+
+ return ret;
+fail:
+ WL_DBG(("Parse CSID event data, status = %d\n", ret));
+ return ret;
+}
+
+static s32
wl_cfgnan_parse_sd_attr_data(osl_t *osh, uint16 len, const uint8 *data,
- nan_event_data_t *tlv_data, uint16 type) {
+ nan_event_data_t *tlv_data, uint16 type)
+{
const uint8 *p_attr = data;
uint16 offset = 0;
s32 ret = BCME_OK;
@@ -780,6 +914,26 @@
goto fail;
}
}
+
+ if ((uint8)*p_attr == NAN_ATTR_SEC_CTX_ID_INFO) {
+ WL_TRACE(("> attr id: 0x%02x\n", (uint8)*p_attr));
+ ret = wl_cfgnan_parse_scid_info(osh, p_attr, len, tlv_data);
+ if (unlikely(ret)) {
+ WL_ERR(("wl_cfgnan_parse_scid_info failed,"
+ "error = %d \n", ret));
+ goto fail;
+ }
+ }
+
+ if ((uint8)*p_attr == NAN_ATTR_CIPHER_SUITE_INFO) {
+ WL_TRACE(("> attr id: 0x%02x\n", (uint8)*p_attr));
+ ret = wl_cfgnan_parse_csid_data(osh, p_attr, len, tlv_data, type);
+ if (unlikely(ret)) {
+ WL_ERR(("wl_cfgnan_parse_csid_data failed,"
+ "error = %d \n", ret));
+ goto fail;
+ }
+ }
offset = (sizeof(*p_attr) +
sizeof(ev_disc->attr_list_len) +
(p_attr[1] | (p_attr[2] << 8)));
@@ -935,6 +1089,7 @@
nan_parse_event_ctx_t *ctx_tlv_data = ((nan_parse_event_ctx_t *)(ctx));
nan_event_data_t *tlv_data = ((nan_event_data_t *)(ctx_tlv_data->nan_evt_data));
int ret = BCME_OK;
+ uint8 csid;
if (!data || !len) {
WL_ERR(("data length is invalid\n"));
@@ -1038,6 +1193,21 @@
case WL_NAN_XTLV_DAM_NA_ATTR:
/* No action -intentionally added to avoid prints when these events are rcvd */
break;
+ case WL_NAN_XTLV_CFG_SEC_PMKID:
+ tlv_data->scid.data = MALLOCZ(ctx_tlv_data->cfg->osh, len);
+ if (!tlv_data->scid.data) {
+ WL_ERR(("%s: memory allocation failed\n", __FUNCTION__));
+ tlv_data->scid.dlen = 0;
+ ret = BCME_NOMEM;
+ goto fail;
+ }
+ tlv_data->scid.dlen = len;
+ (void)memcpy_s(tlv_data->scid.data, tlv_data->scid.dlen, data, len);
+ break;
+ case WL_NAN_XTLV_CFG_SEC_CSID:
+ csid = *(uint8 *)data;
+ tlv_data->peer_cipher_suite = wl_cfgnan_map_nan_prot_csid_to_host_csid(csid);
+ break;
case WL_NAN_XTLV_GEN_AVAIL_STATS_SCHED:
ret = wl_nan_print_stats_tlvs(ctx, data, type, len);
break;
@@ -1128,8 +1298,9 @@
nan_buf->count = 1;
if (disable_events) {
- WL_DBG(("Disabling all nan events..except stop event\n"));
+ WL_DBG(("Disabling all nan events..except start/stop events\n"));
setbit(event_mask, NAN_EVENT_MAP(WL_NAN_EVENT_STOP));
+ setbit(event_mask, NAN_EVENT_MAP(WL_NAN_EVENT_START));
} else {
/*
* Android framework event mask configuration.
@@ -1166,6 +1337,7 @@
setbit(event_mask, NAN_EVENT_MAP(WL_NAN_EVENT_RECEIVE));
setbit(event_mask, NAN_EVENT_MAP(WL_NAN_EVENT_TERMINATED));
setbit(event_mask, NAN_EVENT_MAP(WL_NAN_EVENT_STOP));
+ setbit(event_mask, NAN_EVENT_MAP(WL_NAN_EVENT_START));
setbit(event_mask, NAN_EVENT_MAP(WL_NAN_EVENT_TXS));
setbit(event_mask, NAN_EVENT_MAP(WL_NAN_EVENT_PEER_DATAPATH_IND));
setbit(event_mask, NAN_EVENT_MAP(WL_NAN_EVENT_DATAPATH_ESTB));
@@ -1177,6 +1349,7 @@
clrbit(event_mask, NAN_EVENT_MAP(WL_NAN_EVENT_PEER_SCHED_UPD_NOTIF));
clrbit(event_mask, NAN_EVENT_MAP(WL_NAN_EVENT_RNG_RPT_IND));
clrbit(event_mask, NAN_EVENT_MAP(WL_NAN_EVENT_DW_END));
+ clrbit(event_mask, NAN_EVENT_MAP(WL_NAN_EVENT_REPLIED));
}
nan_buf->is_set = true;
@@ -2148,7 +2321,7 @@
return ret;
}
-static int
+int
wl_cfgnan_check_for_valid_5gchan(struct net_device *ndev, uint8 chan)
{
s32 ret = BCME_OK;
@@ -3149,7 +3322,8 @@
}
/* enable events */
- ret = wl_cfgnan_config_eventmask(ndev, cfg, cmd_data->disc_ind_cfg, false);
+ ret = wl_cfgnan_config_eventmask(ndev, cfg, cmd_data->disc_ind_cfg,
+ cmd_data->chre_req ? true : false);
if (unlikely(ret)) {
WL_ERR(("Failed to config disc ind flag in event_mask, ret = %d\n", ret));
goto fail;
@@ -3317,13 +3491,9 @@
nancfg->nan_enable = true;
WL_INFORM_MEM(("[NAN] Enable successfull \n"));
+ goto done;
fail:
- /* Enable back TDLS if connected interface is <= 1 */
- wl_cfg80211_tdls_config(cfg, TDLS_STATE_IF_DELETE, false);
-
- /* reset conditon variable */
- nancfg->nan_event_recvd = false;
if (unlikely(ret) || unlikely(cmd_data->status)) {
mutex_lock(&cfg->if_sync);
ret = wl_cfg80211_delete_iface(cfg, WL_IF_TYPE_NAN);
@@ -3349,7 +3519,19 @@
if (ret != BCME_OK) {
WL_ERR(("failed to stop nan[%d]\n", ret));
}
+ ret = wl_cfgnan_deinit(cfg, dhdp->up);
+ if (ret != BCME_OK) {
+ WL_ERR(("failed to de-initialize NAN[%d]\n", ret));
+ }
+
}
+done:
+ /* Enable back TDLS if connected interface is <= 1 */
+ wl_cfg80211_tdls_config(cfg, TDLS_STATE_IF_DELETE, false);
+
+ /* reset conditon variable */
+ nancfg->nan_event_recvd = false;
+
if (nan_buf) {
MFREE(cfg->osh, nan_buf, NAN_IOCTL_BUF_SIZE);
}
@@ -3381,16 +3563,15 @@
ret = wl_cfgnan_stop_handler(ndev, cfg);
if (ret == -ENODEV) {
- WL_ERR(("Bus is down, no need to proceed\n"));
+ WL_ERR(("Bus is down, proceed to cleanup\n"));
} else if (ret != BCME_OK) {
WL_ERR(("failed to stop nan, error[%d]\n", ret));
}
ret = wl_cfgnan_deinit(cfg, dhdp->up);
- if (ret != BCME_OK) {
+ if (ret == -ENODEV) {
+ WL_ERR(("Bus is down, proceed to cleanup\n"));
+ } else if (ret != BCME_OK) {
WL_ERR(("failed to de-initialize NAN[%d]\n", ret));
- if (!dhd_query_bus_erros(dhdp)) {
- ASSERT(0);
- }
}
wl_cfgnan_disable_cleanup(cfg);
}
@@ -3510,9 +3691,8 @@
} else {
WL_INFORM_MEM(("nan is in disabled state\n"));
}
- rtnl_unlock();
-
DHD_NAN_WAKE_UNLOCK(cfg->pub);
+ rtnl_unlock();
return;
}
@@ -4516,7 +4696,6 @@
WL_MEM(("Suspending all geofence sessions: "
"suspend_reason = %d\n", suspend_reason));
- cancel_flags |= NAN_RNG_TERM_FLAG_IMMEDIATE;
for (i = 0; i < NAN_MAX_RANGING_INST; i++) {
ranging_inst = &cfg->nancfg->nan_ranging_info[i];
/* Cancel Ranging if in progress for rang_inst */
@@ -5554,6 +5733,7 @@
/* Security elements */
if (cmd_data->csid) {
WL_TRACE(("Cipher suite type is present, pack it\n"));
+ cmd_data->csid = wl_cfgnan_map_host_csid_to_nan_prot_csid(cmd_data->csid);
ret = bcm_pack_xtlv_entry(&pxtlv, nan_buf_size,
WL_NAN_XTLV_CFG_SEC_CSID, sizeof(nan_sec_csid_e),
(uint8*)&cmd_data->csid, BCM_XTLV_OPTION_ALIGN32);
@@ -5563,17 +5743,17 @@
}
}
- if (cmd_data->ndp_cfg.security_cfg) {
+ if (cmd_data->sde_control_flag & NAN_SDE_CF_SECURITY_REQUIRED) {
if ((cmd_data->key_type == NAN_SECURITY_KEY_INPUT_PMK) ||
- (cmd_data->key_type == NAN_SECURITY_KEY_INPUT_PASSPHRASE)) {
+ (cmd_data->key_type == NAN_SECURITY_KEY_INPUT_PASSPHRASE)) {
if (cmd_data->key.data && cmd_data->key.dlen) {
WL_TRACE(("optional pmk present, pack it\n"));
ret = bcm_pack_xtlv_entry(&pxtlv, nan_buf_size,
- WL_NAN_XTLV_CFG_SEC_PMK, cmd_data->key.dlen,
- cmd_data->key.data, BCM_XTLV_OPTION_ALIGN32);
+ WL_NAN_XTLV_CFG_SEC_PMK, cmd_data->key.dlen,
+ cmd_data->key.data, BCM_XTLV_OPTION_ALIGN32);
if (unlikely(ret)) {
WL_ERR(("%s: fail to pack WL_NAN_XTLV_CFG_SEC_PMK\n",
- __FUNCTION__));
+ __FUNCTION__));
goto fail;
}
}
@@ -5586,10 +5766,13 @@
if (cmd_data->scid.data && cmd_data->scid.dlen) {
WL_TRACE(("optional scid present, pack it\n"));
- ret = bcm_pack_xtlv_entry(&pxtlv, nan_buf_size, WL_NAN_XTLV_CFG_SEC_SCID,
+#ifdef WL_NAN_DEBUG
+ prhex("SCID: ", cmd_data->scid.data, cmd_data->scid.dlen);
+#endif /* WL_NAN_DEBUG */
+ ret = bcm_pack_xtlv_entry(&pxtlv, nan_buf_size, WL_NAN_XTLV_CFG_SEC_PMKID,
cmd_data->scid.dlen, cmd_data->scid.data, BCM_XTLV_OPTION_ALIGN32);
if (unlikely(ret)) {
- WL_ERR(("%s: fail to pack WL_NAN_XTLV_CFG_SEC_SCID\n", __FUNCTION__));
+ WL_ERR(("%s: fail to pack WL_NAN_XTLV_CFG_SEC_PMKID\n", __FUNCTION__));
goto fail;
}
}
@@ -5668,14 +5851,20 @@
*data_size += ALIGN_SIZE(cmd_data->svc_info.dlen + NAN_XTLV_ID_LEN_SIZE, 4);
}
}
- if (cmd_data->key.dlen)
+ if (cmd_data->key.dlen) {
*data_size += ALIGN_SIZE(cmd_data->key.dlen + NAN_XTLV_ID_LEN_SIZE, 4);
- if (cmd_data->csid)
+ }
+ if (cmd_data->csid) {
*data_size += ALIGN_SIZE(sizeof(nan_sec_csid_e) + NAN_XTLV_ID_LEN_SIZE, 4);
+ }
+ if (cmd_data->scid.dlen) {
+ *data_size += ALIGN_SIZE(cmd_data->scid.dlen + NAN_XTLV_ID_LEN_SIZE, 4);
+ }
*data_size += ALIGN_SIZE(WL_NAN_SVC_HASH_LEN + NAN_XTLV_ID_LEN_SIZE, 4);
return ret;
}
+
int
wl_cfgnan_svc_get_handler(struct net_device *ndev,
struct bcm_cfg80211 *cfg, uint16 cmd_id, nan_discover_cmd_data_t *cmd_data)
@@ -6457,10 +6646,13 @@
NAN_DBG_ENTER();
+ RETURN_EIO_IF_NOT_UP(cfg);
+
/* Do not query fw about nan if feature is not supported */
if (!FW_SUPPORTED(dhdp, nan)) {
WL_DBG(("NAN is not supported\n"));
- return ret;
+ ret = BCME_NOTUP;
+ goto fail;
}
if (cfg->nancfg->nan_init_state) {
@@ -6510,7 +6702,10 @@
capabilities->max_sdea_service_specific_info_len = MAX_SDEA_SVC_INFO_LEN;
capabilities->max_subscribe_address = MAX_SUBSCRIBE_ADDRESS;
capabilities->cipher_suites_supported = WL_NAN_CIPHER_SUITE_SHARED_KEY_128_MASK;
- capabilities->max_scid_len = MAX_SCID_LEN;
+#ifdef WL_NAN_INSTANT_MODE
+ capabilities->cipher_suites_supported |= (WL_NAN_CIPHER_SUITE_PUBLIC_KEY_128_MASK);
+#endif /* WL_NAN_INSTANT_MODE */
+ capabilities->max_scid_len = NAN_MAX_SCID_BUF_LEN;
capabilities->is_ndp_security_supported = true;
capabilities->ndp_supported_bands = NDP_SUPPORTED_BANDS;
capabilities->ndpe_attr_supported = false;
@@ -6904,6 +7099,38 @@
return;
}
+/* Converts NAN Andrid host Cipher Suite type to NAN protocol Cipher type format */
+static uint8
+wl_cfgnan_map_host_csid_to_nan_prot_csid(uint8 host_csid)
+{
+ uint8 idx = 0;
+ uint8 prot_csid = NAN_SEC_ALGO_NONE;
+
+ for (idx = 0; idx < ARRAYSIZE(nan_csid_map_table); idx++) {
+ if (nan_csid_map_table[idx].host_csid == host_csid) {
+ prot_csid = nan_csid_map_table[idx].fw_csid;
+ break;
+ }
+ }
+ return prot_csid;
+}
+
+/* Converts NAN protocol Cipher type to NAN Andrid host Cipher Suite format */
+static uint8
+wl_cfgnan_map_nan_prot_csid_to_host_csid(uint8 prot_csid)
+{
+ uint8 idx = 0;
+ uint8 host_csid = NAN_SEC_ALGO_NONE;
+
+ for (idx = 0; idx < ARRAYSIZE(nan_csid_map_table); idx++) {
+ if (nan_csid_map_table[idx].fw_csid == prot_csid) {
+ host_csid = nan_csid_map_table[idx].host_csid;
+ break;
+ }
+ }
+ return host_csid;
+}
+
int
wl_cfgnan_data_path_request_handler(struct net_device *ndev,
struct bcm_cfg80211 *cfg, nan_datapath_cmd_data_t *cmd_data,
@@ -7082,6 +7309,7 @@
if (cmd_data->csid) {
WL_TRACE(("Cipher suite type is present, pack it\n"));
+ cmd_data->csid = wl_cfgnan_map_host_csid_to_nan_prot_csid(cmd_data->csid);
ret = bcm_pack_xtlv_entry(&pxtlv, &nan_buf_size,
WL_NAN_XTLV_CFG_SEC_CSID, sizeof(nan_sec_csid_e),
(uint8*)&cmd_data->csid, BCM_XTLV_OPTION_ALIGN32);
@@ -7090,6 +7318,20 @@
goto fail;
}
}
+ if (cmd_data->scid.dlen && cmd_data->scid.data) {
+ WL_TRACE(("SCID present, pack it\n"));
+#ifdef WL_NAN_DEBUG
+ prhex("SCID: ", cmd_data->scid.data, cmd_data->scid.dlen);
+#endif /* WL_NAN_DEBUG */
+ ret = bcm_pack_xtlv_entry(&pxtlv, &nan_buf_size,
+ WL_NAN_XTLV_CFG_SEC_PMKID, cmd_data->scid.dlen,
+ cmd_data->scid.data,
+ BCM_XTLV_OPTION_ALIGN32);
+ if (ret != BCME_OK) {
+ WL_ERR(("unable to process scid info: %d\n", ret));
+ goto fail;
+ }
+ }
if (cmd_data->ndp_cfg.security_cfg) {
if ((cmd_data->key_type == NAN_SECURITY_KEY_INPUT_PMK) ||
@@ -7379,6 +7621,7 @@
/* Security elements */
if (cmd_data->csid) {
WL_TRACE(("Cipher suite type is present, pack it\n"));
+ cmd_data->csid = wl_cfgnan_map_host_csid_to_nan_prot_csid(cmd_data->csid);
ret = bcm_pack_xtlv_entry(&pxtlv, &nan_buf_size,
WL_NAN_XTLV_CFG_SEC_CSID, sizeof(nan_sec_csid_e),
(uint8*)&cmd_data->csid, BCM_XTLV_OPTION_ALIGN32);
@@ -7387,6 +7630,17 @@
goto fail;
}
}
+ if (cmd_data->scid.dlen && cmd_data->scid.data) {
+ WL_ERR(("SCID present, pack it\n"));
+ ret = bcm_pack_xtlv_entry(&pxtlv, &nan_buf_size,
+ WL_NAN_XTLV_CFG_SEC_PMKID, cmd_data->scid.dlen,
+ cmd_data->scid.data,
+ BCM_XTLV_OPTION_ALIGN32);
+ if (ret != BCME_OK) {
+ WL_ERR(("unable to process scid info: %d\n", ret));
+ goto fail;
+ }
+ }
if (cmd_data->ndp_cfg.security_cfg) {
if ((cmd_data->key_type == NAN_SECURITY_KEY_INPUT_PMK) ||
@@ -7813,6 +8067,7 @@
nan_event_data->pub_id = ev_dp->pub_id;
WL_TRACE(("security: %d\n", ev_dp->security));
nan_event_data->security = ev_dp->security;
+ WL_INFORM_MEM(("dp status: %d\n", ev_dp->status));
/* Store initiator_ndi, required for data_path_response_request */
ret = memcpy_s(&cfg->nancfg->initiator_ndi, ETHER_ADDR_LEN,
@@ -7838,7 +8093,7 @@
}
} else {
/* type is multicast */
- WL_INFORM_MEM(("NDP ID: %d\n", ev_dp->mc_id));
+ WL_INFORM_MEM(("MC ID: %d\n", ev_dp->mc_id));
nan_event_data->ndp_id = ev_dp->mc_id;
WL_TRACE(("PEER NMI: " MACDBG "\n",
MAC2STRDBG(ev_dp->peer_nmi.octet)));
@@ -7957,11 +8212,11 @@
}
#endif /* WL_NAN_DISC_CACHE */
/* Remove peer from data ndp peer list */
+ WL_INFORM_MEM(("DP_END for NDP ID %d REMOTE_NMI: " MACDBG " with %s\n",
+ nan_event_data->ndp_id, MAC2STRDBG(&ev_dp->peer_nmi),
+ nan_event_cause_to_str(ev_dp->event_cause)));
wl_cfgnan_data_remove_peer(cfg, &ev_dp->peer_nmi);
wl_cfgnan_update_dp_info(cfg, false, nan_event_data->ndp_id);
- WL_INFORM_MEM(("DP_END for REMOTE_NMI: " MACDBG " with %s\n",
- MAC2STRDBG(&ev_dp->peer_nmi),
- nan_event_cause_to_str(ev_dp->event_cause)));
#ifdef RTT_SUPPORT
rng_inst = wl_cfgnan_check_for_ranging(cfg, &ev_dp->peer_nmi);
if (rng_inst) {
@@ -8309,6 +8564,11 @@
nan_event_data->sde_svc_info.dlen);
nan_event_data->sde_svc_info.data = NULL;
}
+ if (nan_event_data->scid.data) {
+ MFREE(cfg->osh, nan_event_data->scid.data,
+ nan_event_data->scid.dlen);
+ nan_event_data->scid.data = NULL;
+ }
MFREE(cfg->osh, nan_event_data, sizeof(*nan_event_data));
}
@@ -8576,8 +8836,8 @@
UNUSED_PARAMETER(status);
NAN_DBG_ENTER();
- if (!event || !event_data) {
- WL_ERR(("event data is NULL\n"));
+ if (!event) {
+ WL_ERR(("event is NULL\n"));
return -EINVAL;
}
@@ -8585,6 +8845,15 @@
event_num = ntoh32(event->reason);
data_len = ntoh32(event->datalen);
+ if (!event_data) {
+ WL_ERR(("event data is NULL for event: %d\n", event_num));
+ return -EINVAL;
+ }
+ if (!data_len) {
+ WL_ERR(("Invalid event data len for event: %d\n", event_num));
+ return -EINVAL;
+ }
+
#ifdef RTT_SUPPORT
if (event_num == WL_NAN_EVENT_RNG_REQ_IND)
{
@@ -8615,7 +8884,8 @@
#endif /* WL_NAN_DEBUG */
if (!cfg->nancfg->nan_init_state) {
- WL_ERR(("nan is not in initialized state, dropping nan related events\n"));
+ WL_ERR(("nan is not in initialized state, dropping nan related event num: %d, "
+ "type: %d\n", event_num, event_type));
ret = BCME_OK;
goto exit;
}
@@ -9177,21 +9447,17 @@
u16 *disc_cache_update_flags)
{
nan_event_data_t* disc = (nan_event_data_t*)data;
- int i, add_index = 0;
+ int i, add_index = NAN_MAX_CACHE_DISC_RESULT;
int ret = BCME_OK;
wl_nancfg_t *nancfg = cfg->nancfg;
nan_disc_result_cache *disc_res = nancfg->nan_disc_cache;
- *disc_cache_update_flags = 0;
+ bool new_entry = TRUE;
+ *disc_cache_update_flags = 0;
if (!nancfg->nan_enable) {
WL_DBG(("nan not enabled"));
return BCME_NOTENABLED;
}
- if (nancfg->nan_disc_count == NAN_MAX_CACHE_DISC_RESULT) {
- WL_DBG(("cache full"));
- ret = BCME_NORESOURCE;
- goto done;
- }
for (i = 0; i < NAN_MAX_CACHE_DISC_RESULT; i++) {
if (!disc_res[i].valid) {
@@ -9199,77 +9465,104 @@
continue;
}
if (!memcmp(&disc_res[i].peer, &disc->remote_nmi, ETHER_ADDR_LEN) &&
- !memcmp(disc_res[i].svc_hash, disc->svc_name, WL_NAN_SVC_HASH_LEN)) {
+ !memcmp(disc_res[i].svc_hash, disc->svc_name, WL_NAN_SVC_HASH_LEN) &&
+ (disc_res[i].pub_id == disc->pub_id) &&
+ (disc_res[i].sub_id == disc->sub_id)) {
WL_DBG(("cache entry already present, i = %d", i));
/* Update needed parameters here */
if (disc_res[i].sde_control_flag != disc->sde_control_flag) {
- disc_res[i].sde_control_flag = disc->sde_control_flag;
*disc_cache_update_flags |= NAN_DISC_CACHE_PARAM_SDE_CONTROL;
}
- ret = BCME_OK; /* entry already present */
- goto done;
+ add_index = i;
+ new_entry = FALSE;
+ break;
}
}
- WL_DBG(("adding cache entry: add_index = %d\n", add_index));
- disc_res[add_index].valid = 1;
- disc_res[add_index].pub_id = disc->pub_id;
- disc_res[add_index].sub_id = disc->sub_id;
- disc_res[add_index].publish_rssi = disc->publish_rssi;
- disc_res[add_index].peer_cipher_suite = disc->peer_cipher_suite;
- disc_res[add_index].sde_control_flag = disc->sde_control_flag;
- ret = memcpy_s(&disc_res[add_index].peer, ETHER_ADDR_LEN,
- &disc->remote_nmi, ETHER_ADDR_LEN);
- if (ret != BCME_OK) {
- WL_ERR(("Failed to copy remote nmi\n"));
- goto done;
- }
- ret = memcpy_s(disc_res[add_index].svc_hash, WL_NAN_SVC_HASH_LEN,
- disc->svc_name, WL_NAN_SVC_HASH_LEN);
- if (ret != BCME_OK) {
- WL_ERR(("Failed to copy svc hash\n"));
+
+ if (add_index == NAN_MAX_CACHE_DISC_RESULT) {
+ WL_DBG(("cache full"));
+ ret = BCME_NORESOURCE;
goto done;
}
+ if (new_entry) {
+ WL_DBG(("adding cache entry: add_index = %d\n", add_index));
+ disc_res[add_index].valid = 1;
+ disc_res[add_index].pub_id = disc->pub_id;
+ disc_res[add_index].sub_id = disc->sub_id;
+
+ eacopy(&disc->remote_nmi, &disc_res[add_index].peer);
+ eacopy(disc->svc_name, disc_res[add_index].svc_hash);
+ }
+
+ disc_res[add_index].publish_rssi = disc->publish_rssi;
+ disc_res[add_index].peer_cipher_suite = disc->peer_cipher_suite;
+ disc_res[add_index].sde_control_flag = disc->sde_control_flag;
if (disc->svc_info.dlen && disc->svc_info.data) {
- disc_res[add_index].svc_info.dlen = disc->svc_info.dlen;
- disc_res[add_index].svc_info.data =
- MALLOCZ(cfg->osh, disc_res[add_index].svc_info.dlen);
+ if (disc_res[add_index].svc_info.dlen != disc->svc_info.dlen) {
+ if (disc_res[add_index].svc_info.data) {
+ MFREE(cfg->osh, disc_res[add_index].svc_info.data,
+ disc_res[add_index].svc_info.dlen);
+ }
+ disc_res[add_index].svc_info.dlen = disc->svc_info.dlen;
+ disc_res[add_index].svc_info.data =
+ MALLOCZ(cfg->osh, disc_res[add_index].svc_info.dlen);
+ }
if (!disc_res[add_index].svc_info.data) {
WL_ERR(("%s: memory allocation failed\n", __FUNCTION__));
disc_res[add_index].svc_info.dlen = 0;
ret = BCME_NOMEM;
- goto done;
+ goto reset_entry;
}
ret = memcpy_s(disc_res[add_index].svc_info.data, disc_res[add_index].svc_info.dlen,
disc->svc_info.data, disc->svc_info.dlen);
if (ret != BCME_OK) {
WL_ERR(("Failed to copy svc info\n"));
- goto done;
+ goto reset_entry;
}
}
if (disc->tx_match_filter.dlen && disc->tx_match_filter.data) {
- disc_res[add_index].tx_match_filter.dlen = disc->tx_match_filter.dlen;
- disc_res[add_index].tx_match_filter.data =
- MALLOCZ(cfg->osh, disc_res[add_index].tx_match_filter.dlen);
+ if (disc_res[add_index].tx_match_filter.dlen != disc->tx_match_filter.dlen) {
+ if (disc_res[add_index].tx_match_filter.data) {
+ MFREE(cfg->osh, disc_res[add_index].tx_match_filter.data,
+ disc_res[add_index].tx_match_filter.dlen);
+ }
+ disc_res[add_index].tx_match_filter.dlen = disc->tx_match_filter.dlen;
+ disc_res[add_index].tx_match_filter.data =
+ MALLOCZ(cfg->osh, disc_res[add_index].tx_match_filter.dlen);
+ }
if (!disc_res[add_index].tx_match_filter.data) {
WL_ERR(("%s: memory allocation failed\n", __FUNCTION__));
disc_res[add_index].tx_match_filter.dlen = 0;
ret = BCME_NOMEM;
- goto done;
+ goto reset_entry;
}
ret = memcpy_s(disc_res[add_index].tx_match_filter.data,
disc_res[add_index].tx_match_filter.dlen,
disc->tx_match_filter.data, disc->tx_match_filter.dlen);
if (ret != BCME_OK) {
WL_ERR(("Failed to copy tx match filter\n"));
- goto done;
+ goto reset_entry;
}
}
- nancfg->nan_disc_count++;
+ if (new_entry) {
+ nancfg->nan_disc_count++;
+ }
WL_DBG(("cfg->nan_disc_count = %d\n", nancfg->nan_disc_count));
done:
return ret;
+
+reset_entry:
+ if (!new_entry) {
+ nancfg->nan_disc_count--;
+ *disc_cache_update_flags = 0;
+ }
+ WL_ERR(("resetting cache entry: %d, cfg->nan_disc_count = %d\n", add_index,
+ nancfg->nan_disc_count));
+ wl_cfgnan_reset_disc_result(cfg, &disc_res[add_index]);
+
+ return ret;
}
#ifdef RTT_SUPPORT
@@ -9364,6 +9657,31 @@
return ret;
}
+static int wl_cfgnan_reset_disc_result(struct bcm_cfg80211 *cfg,
+ nan_disc_result_cache *disc_res)
+{
+ int ret = BCME_OK;
+
+ if (!cfg->nancfg->nan_enable) {
+ WL_DBG(("nan not enabled\n"));
+ ret = BCME_NOTENABLED;
+ goto done;
+ }
+
+ if (disc_res->tx_match_filter.data) {
+ MFREE(cfg->osh, disc_res->tx_match_filter.data,
+ disc_res->tx_match_filter.dlen);
+ }
+ if (disc_res->svc_info.data) {
+ MFREE(cfg->osh, disc_res->svc_info.data,
+ disc_res->svc_info.dlen);
+ }
+ bzero(disc_res, sizeof(*disc_res));
+
+done:
+ return ret;
+}
+
static nan_disc_result_cache *
wl_cfgnan_get_disc_result(struct bcm_cfg80211 *cfg, uint8 remote_pubid,
struct ether_addr *peer)
@@ -9792,8 +10110,13 @@
}
#ifdef WL_NMI_IF
+
/* AWARE NMI interface name */
-#define NMI_IFNAME "aware_nmi0"
+#ifndef CUSTOM_NMI_IFNAME
+#define NMI_IFNAME "aware_nmi0"
+#else
+#define NMI_IFNAME CUSTOM_NMI_IFNAME
+#endif /* !CUSTOM_NMI_IFNAME */
static int
wl_cfgnan_nmi_if_dummy_open(struct net_device *net)
@@ -10075,4 +10398,63 @@
/* As FW is busy, retry NMI change after 60sec */
schedule_delayed_work(&cfg->nancfg->nan_nmi_rand, msecs_to_jiffies(60 * 1000));
}
+#ifdef WL_NAN_INSTANT_MODE
+void wl_cfgnan_inst_chan_support(struct bcm_cfg80211 *cfg,
+ wl_chanspec_list_v1_t *chan_list, u32 band_mask,
+ uint8 *nan_2g, uint8 *nan_pri_5g, uint8 *nan_sec_5g)
+{
+ int ret = BCME_OK;
+ uint16 list_count = 0, i = 0;
+ uint8 channel = 0;
+ chanspec_t chanspec = INVCHANSPEC;
+
+ list_count = chan_list->count;
+ for (i = 0; i < list_count; i++) {
+ chanspec = dtoh32(((wl_chanspec_list_v1_t *)chan_list)->chspecs[i].chanspec);
+ chanspec = wl_chspec_driver_to_host(chanspec);
+
+ if (!wf_chspec_malformed(chanspec)) {
+ channel = CHSPEC_CHANNEL(chanspec);
+
+ if ((band_mask & WLAN_MAC_5_0_BAND) &&
+ (channel == NAN_DEF_SOCIAL_CHAN_5G)) {
+ /* Check nan operatability in the current locale */
+ ret = wl_cfgnan_check_for_valid_5gchan(bcmcfg_to_prmry_ndev(cfg),
+ channel);
+ if (ret != BCME_OK) {
+ WL_DBG_MEM(("Current locale doesn't support 5G op"
+ "continuing with 2G only operation\n"));
+ *nan_pri_5g = 0;
+ } else {
+ WL_DBG_MEM(("Found prim inst mode 5g chan!!\n"));
+ *nan_pri_5g = channel;
+ }
+ }
+
+ if ((band_mask & WLAN_MAC_5_0_BAND) &&
+ (channel == NAN_DEF_SEC_SOCIAL_CHAN_5G)) {
+ /* Check nan operatability in the current locale */
+ ret = wl_cfgnan_check_for_valid_5gchan(bcmcfg_to_prmry_ndev(cfg),
+ channel);
+ if (ret != BCME_OK) {
+ WL_DBG_MEM(("Current locale doesn't support 5G op"
+ "continuing with 2G only operation\n"));
+ *nan_sec_5g = 0;
+ } else {
+ WL_DBG_MEM(("Found sec inst mode 5g chan!!\n"));
+ *nan_sec_5g = channel;
+ }
+ }
+
+ if ((band_mask & WLAN_MAC_2_4_BAND) &&
+ (channel == NAN_DEF_SOCIAL_CHAN_2G)) {
+ WL_DBG_MEM(("Found instant mode 2g channel!!\n"));
+ *nan_2g = channel;
+ }
+ }
+ }
+ return;
+}
+#endif /* WL_NAN_INSTANT_MODE */
+#line 10447
#endif /* WL_NAN */
diff --git a/wl_cfgnan.h b/wl_cfgnan.h
index 63aeec4..1851118 100644
--- a/wl_cfgnan.h
+++ b/wl_cfgnan.h
@@ -1,7 +1,7 @@
/*
* Neighbor Awareness Networking
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -134,6 +134,7 @@
#define NAN_SRF_MAX_MAC (NAN_BLOOM_LENGTH_DEFAULT / ETHER_ADDR_LEN)
#define NAN_MAX_PMK_LEN 32u
#define NAN_ERROR_STR_LEN 255u
+#define NAN_MAX_SCID_BUF_LEN 1024u
/* NAN related Capabilities */
#define MAX_CONCURRENT_NAN_CLUSTERS 1u
@@ -481,6 +482,7 @@
uint8 num_ndp_instances;
uint8 duration;
char ndp_iface[IFNAMSIZ+1];
+ nan_str_data_t scid; /* security context information */
} nan_datapath_cmd_data_t;
typedef struct nan_rssi_cmd_data {
@@ -540,6 +542,7 @@
uint32 dw_early_termination;
uint32 instant_mode_en;
uint32 instant_chan;
+ uint8 chre_req;
} nan_config_cmd_data_t;
typedef struct nan_event_hdr {
@@ -677,7 +680,12 @@
#ifdef WL_NAN_DISC_CACHE
-#define NAN_MAX_CACHE_DISC_RESULT 16
+#ifndef CUSTOM_NAN_MAX_CACHE_DISC_RESULT
+#define NAN_MAX_CACHE_DISC_RESULT 40
+#else
+#define NAN_MAX_CACHE_DISC_RESULT CUSTOM_NAN_MAX_CACHE_DISC_RESULT
+#endif /* CUSTOM_NAN_MAX_CACHE_DISC_RESULT */
+
typedef struct {
bool valid;
wl_nan_instance_id_t pub_id;
@@ -714,10 +722,21 @@
struct net_device *nan_ndev;
} wl_ndi_data_t;
+/* Google mobile platforms have 2 processors which can request NAN
+ * APP - main application processor
+ * CHRE - Low power processor
+ * We need to differentiate the request for handling (non)concurrency
+ */
+typedef enum {
+ ENABLE_FOR_APP = 0,
+ ENABLE_FOR_CHRE = 1
+} nan_enab_reason;
+
typedef struct wl_nancfg
{
struct bcm_cfg80211 *cfg;
bool nan_enable;
+ nan_enab_reason enab_reason;
nan_svc_inst_t nan_inst_ctrl[NAN_ID_CTRL_SIZE];
struct ether_addr initiator_ndi;
uint8 nan_dp_state;
@@ -810,6 +829,14 @@
int wl_cfgnan_attach(struct bcm_cfg80211 *cfg);
void wl_cfgnan_detach(struct bcm_cfg80211 *cfg);
int wl_cfgnan_get_status(struct net_device *ndev, wl_nan_conf_status_t *nan_status);
+#ifdef WL_NAN_INSTANT_MODE
+extern void wl_cfgnan_inst_chan_support(struct bcm_cfg80211 *cfg,
+ wl_chanspec_list_v1_t *chan_list, uint32 band_mask,
+ uint8 *nan_2g, uint8 *nan_pri_5g, uint8* nan_sec_5g);
+#endif /* WL_NAN_INSTANT_MODE */
+#line 825
+int
+wl_cfgnan_check_for_valid_5gchan(struct net_device *ndev, uint8 chan);
#ifdef RTT_SUPPORT
int wl_cfgnan_trigger_ranging(struct net_device *ndev,
@@ -981,7 +1008,8 @@
NAN_ATTRIBUTE_NUM_CHANNELS = 229,
NAN_ATTRIBUTE_INSTANT_MODE_ENABLE = 230,
NAN_ATTRIBUTE_INSTANT_COMM_CHAN = 231,
- NAN_ATTRIBUTE_MAX = 232
+ NAN_ATTRIBUTE_CHRE_REQUEST = 232,
+ NAN_ATTRIBUTE_MAX = 233
} NAN_ATTRIBUTE;
enum geofence_suspend_reason {
diff --git a/wl_cfgp2p.c b/wl_cfgp2p.c
index 8c5c3bc..39ba37d 100644
--- a/wl_cfgp2p.c
+++ b/wl_cfgp2p.c
@@ -1,7 +1,7 @@
/*
* Linux cfgp2p driver
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -151,27 +151,6 @@
return true;
}
-#ifdef WL11U
- /* Hotspot2.0 STA mode can receive only response
- * SoftAP mode cannot run Hotspot2.0 compliant Ap because
- * Hotspot2.0 support only Enterprise mode
- */
- if (sd_act_frm->action == P2PSD_ACTION_ID_GAS_IRESP) {
- return wl_cfg80211_find_gas_subtype(P2PSD_GAS_OUI_SUBTYPE, P2PSD_GAS_NQP_INFOID,
- (u8 *)sd_act_frm->query_data + GAS_RESP_OFFSET,
- frame_len - (P2P_GAS_ACT_FRAME_FIXED_SIZE + GAS_RESP_OFFSET));
-
- } else if (sd_act_frm->action == P2PSD_ACTION_ID_GAS_CRESP) {
- return wl_cfg80211_find_gas_subtype(P2PSD_GAS_OUI_SUBTYPE, P2PSD_GAS_NQP_INFOID,
- (u8 *)sd_act_frm->query_data + GAS_CRESP_OFFSET,
- frame_len - (P2P_GAS_ACT_FRAME_FIXED_SIZE + GAS_CRESP_OFFSET));
- } else if (sd_act_frm->action == P2PSD_ACTION_ID_GAS_IREQ ||
- sd_act_frm->action == P2PSD_ACTION_ID_GAS_CREQ) {
- return true;
- } else {
- return false;
- }
-#else
if (sd_act_frm->action == P2PSD_ACTION_ID_GAS_IREQ ||
sd_act_frm->action == P2PSD_ACTION_ID_GAS_IRESP ||
sd_act_frm->action == P2PSD_ACTION_ID_GAS_CREQ ||
@@ -179,7 +158,6 @@
return true;
else
return false;
-#endif /* WL11U */
}
bool wl_cfgp2p_is_p2p_gas_action(void *frame, u32 frame_len)
@@ -317,15 +295,13 @@
s32
wl_cfgp2p_init_priv(struct bcm_cfg80211 *cfg)
{
- struct ether_addr primary_mac;
cfg->p2p = MALLOCZ(cfg->osh, sizeof(struct p2p_info));
if (cfg->p2p == NULL) {
CFGP2P_ERR(("struct p2p_info allocation failed\n"));
return -ENOMEM;
}
- get_primary_mac(cfg, &primary_mac);
- wl_cfgp2p_generate_bss_mac(cfg, &primary_mac);
+ wl_cfgp2p_generate_bss_mac(cfg);
wl_to_p2p_bss_ndev(cfg, P2PAPI_BSSCFG_PRIMARY) = bcmcfg_to_prmry_ndev(cfg);
wl_to_p2p_bss_bssidx(cfg, P2PAPI_BSSCFG_PRIMARY) = 0;
@@ -338,6 +314,7 @@
return BCME_OK;
}
+
/*
* Deinitialize variables related to P2P
*
@@ -352,6 +329,7 @@
}
cfg->p2p_supported = 0;
}
+
/*
* Set P2P functions into firmware
*/
@@ -561,70 +539,80 @@
return ret;
}
-#define DISCOVERY_EBUSY_RETRY_LIMIT 5
+#ifdef BCMDONGLEHOST
+#define DISCOVERY_EBUSY_RETRY_LIMIT 5u
static void
-wl_cfgp2p_handle_discovery_busy(struct bcm_cfg80211 *cfg, s32 err)
+wl_cfgp2p_handle_discovery_busy(struct bcm_cfg80211 *cfg)
{
- static u32 busy_count = 0;
dhd_pub_t *dhdp = (dhd_pub_t *)(cfg->pub);
+ struct ether_addr *p2p_dev_addr = wl_to_p2p_bss_macaddr(cfg, P2PAPI_BSSCFG_DEVICE);
- if (err != BCME_BUSY) {
- busy_count = 0;
- return;
+ if (dhdp->dhd_induce_error == DHD_INDUCE_P2P_DISC_BUSY) {
+ /* force hang for p2p disc busy to be triggered */
+ dhdp->p2p_disc_busy_cnt = DISCOVERY_EBUSY_RETRY_LIMIT;
+ CFGP2P_ERR(("P2P disc busy hang forcily\n"));
}
- busy_count++;
+ if (++dhdp->p2p_disc_busy_cnt < DISCOVERY_EBUSY_RETRY_LIMIT) {
+ goto done;
+ }
- if (busy_count >= DISCOVERY_EBUSY_RETRY_LIMIT) {
- struct ether_addr *p2p_dev_addr = wl_to_p2p_bss_macaddr(cfg, P2PAPI_BSSCFG_DEVICE);
+ CFGP2P_ERR(("p2p disc busy!!!\n"));
- CFGP2P_ERR(("p2p disc busy!!!\n"));
+ if (ETHER_ISNULLADDR(p2p_dev_addr)) {
+ CFGP2P_ERR(("NULL p2p_dev_addr\n"));
+ } else {
+ CFGP2P_ERR(("p2p disc mac : "MACDBG"\n", MAC2STRDBG(p2p_dev_addr->octet)));
+ }
- if (ETHER_ISNULLADDR(p2p_dev_addr)) {
- CFGP2P_ERR(("NULL p2p_dev_addr\n"));
- } else {
- CFGP2P_ERR(("p2p disc mac : "MACDBG"\n", MAC2STRDBG(p2p_dev_addr->octet)));
- }
+ if (dhd_query_bus_erros(dhdp)) {
+ CFGP2P_ERR(("bus error\n"));
+ goto done;
+ }
- if (dhd_query_bus_erros(dhdp)) {
- CFGP2P_ERR(("bus error\n"));
- return;
- }
+ dhdp->p2p_disc_busy_occurred = TRUE;
- dhdp->p2p_disc_busy_occurred = TRUE;
- busy_count = 0;
-
-#ifdef BCMDONGLEHOST
#if defined(DHD_DEBUG) && defined(DHD_FW_COREDUMP)
- if (dhdp->memdump_enabled) {
- dhdp->memdump_type = DUMP_TYPE_P2P_DISC_BUSY;
- dhd_bus_mem_dump(dhdp);
- }
+ if (dhdp->memdump_enabled) {
+ dhdp->memdump_type = DUMP_TYPE_P2P_DISC_BUSY;
+ dhd_bus_mem_dump(dhdp);
+ }
#endif /* DHD_DEBUG && DHD_FW_COREDUMP */
- dhdp->hang_reason = HANG_REASON_P2P_DISC_BUSY;
- dhd_os_send_hang_message(dhdp);
+ dhdp->hang_reason = HANG_REASON_P2P_DISC_BUSY;
+ dhd_os_send_hang_message(dhdp);
-#endif /* BCMDONGLEHOST */
- }
+done:
+ return;
}
+#endif /* BCMDONGLEHOST */
static s32
wl_cfgp2p_set_discovery(struct bcm_cfg80211 *cfg, s32 on)
{
s32 ret = BCME_OK;
struct net_device *ndev = bcmcfg_to_prmry_ndev(cfg);
+#ifdef BCMDONGLEHOST
+ dhd_pub_t *dhdp = (dhd_pub_t *)(cfg->pub);
+#endif /* BCMDONGLEHOST */
CFGP2P_DBG(("enter\n"));
ret = wldev_iovar_setint(ndev, "p2p_disc", on);
if (unlikely(ret < 0)) {
CFGP2P_ERR(("p2p_disc %d error %d\n", on, ret));
+ }
- if (on) {
- wl_cfgp2p_handle_discovery_busy(cfg, ret);
+#ifdef BCMDONGLEHOST
+ if (on) {
+ if (ret == BCME_BUSY ||
+ dhdp->dhd_induce_error == DHD_INDUCE_P2P_DISC_BUSY) {
+ wl_cfgp2p_handle_discovery_busy(cfg);
+ } else {
+ dhdp->p2p_disc_busy_cnt = 0;
}
}
+#endif /* BCMDONGLEHOST */
return ret;
}
@@ -839,6 +827,7 @@
return ret;
}
+
/* Enable P2P Discovery
* Parameters:
* @cfg : wl_private data
@@ -984,7 +973,7 @@
u32 i;
s8 *memblk;
wl_p2p_scan_t *p2p_params;
- wl_escan_params_t *eparams;
+ wl_escan_params_v1_t *eparams;
wl_escan_params_v3_t *eparams_v3;
wlc_ssid_t ssid;
u32 sync_id = 0;
@@ -1001,8 +990,8 @@
OFFSETOF(wl_escan_params_v3_t, params)) +
num_chans * sizeof(eparams->params.channel_list[0]);
} else {
- eparams_size = (WL_SCAN_PARAMS_FIXED_SIZE +
- OFFSETOF(wl_escan_params_t, params)) +
+ eparams_size = (WL_SCAN_PARAMS_V1_FIXED_SIZE +
+ OFFSETOF(wl_escan_params_v1_t, params)) +
num_chans * sizeof(eparams->params.channel_list[0]);
}
@@ -1111,8 +1100,8 @@
sizeof(wlc_ssid_t), &ssid, sizeof(wlc_ssid_t));
sync_id = eparams_v3->sync_id;
} else {
- eparams = (wl_escan_params_t*) (p2p_params + 1);
- eparams->version = htod32(ESCAN_REQ_VERSION);
+ eparams = (wl_escan_params_v1_t*) (p2p_params + 1);
+ eparams->version = htod32(ESCAN_REQ_VERSION_V1);
eparams->action = htod16(action);
eparams->params.bss_type = DOT11_BSSTYPE_ANY;
eparams->params.scan_type = htod32(scan_type);
@@ -1179,7 +1168,7 @@
chan_cnt = SOCIAL_CHAN_CNT;
if (cfg->afx_hdl->pending_tx_act_frm && cfg->afx_hdl->is_active) {
- wl_action_frame_t *action_frame;
+ wl_action_frame_v1_t *action_frame;
action_frame = &(cfg->afx_hdl->pending_tx_act_frm->action_frame);
if (wl_cfgp2p_is_p2p_gas_action(action_frame->data, action_frame->len)) {
chan_cnt = 1;
@@ -1392,6 +1381,7 @@
exit:
return ndev;
}
+
/*
* Search the driver array idx based on bssidx argument
* Parameters: Note that this idx is applicable only
@@ -1560,6 +1550,7 @@
}
wl_cfg80211_event(ndev, &msg, NULL);
}
+
/*
* Routine for cancelling the P2P LISTEN
*/
@@ -1592,6 +1583,7 @@
}
return 0;
}
+
/*
* Do a P2P Listen on the given channel for the given duration.
* A listen consists of sitting idle and responding to P2P probe requests
@@ -1741,7 +1733,7 @@
static s32
wl_actframe_fillup_v2(struct bcm_cfg80211 *cfg, bcm_struct_cfgdev *cfgdev,
struct net_device *dev, wl_af_params_v2_t *af_params_v2_p,
- wl_af_params_t *af_params, const u8 *sa, uint16 wl_af_params_size)
+ wl_af_params_v1_t *af_params, const u8 *sa, uint16 wl_af_params_size)
{
s32 err = 0;
wl_action_frame_v2_t *action_frame_v2_p;
@@ -1809,7 +1801,7 @@
*/
s32
wl_cfgp2p_tx_action_frame(struct bcm_cfg80211 *cfg, bcm_struct_cfgdev *cfgdev,
- struct net_device *dev, wl_af_params_t *af_params, s32 bssidx, const u8 *sa)
+ struct net_device *dev, wl_af_params_v1_t *af_params, s32 bssidx, const u8 *sa)
{
s32 ret = BCME_OK;
s32 evt_ret = BCME_OK;
@@ -1880,7 +1872,6 @@
timeout = wait_for_completion_timeout(&cfg->send_af_done,
msecs_to_jiffies(af_params->dwell_time + WL_AF_TX_EXTRA_TIME_MAX));
-
if (timeout == 0) {
CFGP2P_DBG(("action frame dwell timeout completed\n"));
/* Call actframe_abort to cleanup FW state, when
@@ -1921,7 +1912,7 @@
* MAC address.
*/
void
-wl_cfgp2p_generate_bss_mac(struct bcm_cfg80211 *cfg, struct ether_addr *primary_addr)
+wl_cfgp2p_generate_bss_mac(struct bcm_cfg80211 *cfg)
{
struct ether_addr *mac_addr = wl_to_p2p_bss_macaddr(cfg, P2PAPI_BSSCFG_DEVICE);
struct ether_addr *int_addr = NULL;
@@ -1934,8 +1925,8 @@
/* When p2p rand is enabled, use randomized mac by default */
wl_cfg80211_generate_mac_addr(mac_addr);
#else
- (void)memcpy_s(mac_addr, sizeof(struct ether_addr),
- primary_addr, sizeof(struct ether_addr));
+ (void)memcpy_s(mac_addr->octet, ETHER_ADDR_LEN,
+ bcmcfg_to_prmry_ndev(cfg)->perm_addr, ETHER_ADDR_LEN);
mac_addr->octet[0] |= 0x02;
#endif /* WL_P2P_RAND */
WL_INFORM_MEM(("P2P Discovery address:"MACDBG "\n", MAC2STRDBG(mac_addr->octet)));
@@ -2025,6 +2016,7 @@
}
return p2p_supported;
}
+
/* Cleanup P2P resources */
s32
wl_cfgp2p_down(struct bcm_cfg80211 *cfg)
@@ -2158,6 +2150,7 @@
}
return ret;
}
+
s32
wl_cfgp2p_get_p2p_noa(struct bcm_cfg80211 *cfg, struct net_device *ndev, char* buf, int buf_len)
{
@@ -2201,6 +2194,7 @@
}
return len * 2;
}
+
s32
wl_cfgp2p_set_p2p_ps(struct bcm_cfg80211 *cfg, struct net_device *ndev, char* buf, int len)
{
@@ -2427,7 +2421,7 @@
}
const u8 *
-wl_cfgp2p_retreive_p2p_dev_addr(wl_bss_info_t *bi, u32 bi_length)
+wl_cfgp2p_retreive_p2p_dev_addr(wl_bss_info_v109_t *bi, u32 bi_length)
{
const u8 *capability = NULL;
bool p2p_go = 0;
@@ -2591,6 +2585,7 @@
return 0;
}
+
static netdev_tx_t wl_cfgp2p_start_xmit(struct sk_buff *skb, struct net_device *ndev)
{
diff --git a/wl_cfgp2p.h b/wl_cfgp2p.h
index 9f218eb..e27d6af 100644
--- a/wl_cfgp2p.h
+++ b/wl_cfgp2p.h
@@ -1,7 +1,7 @@
/*
* Linux cfgp2p driver
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -340,10 +340,10 @@
extern s32
wl_cfgp2p_tx_action_frame(struct bcm_cfg80211 *cfg, bcm_struct_cfgdev *cfgdev,
- struct net_device *dev, wl_af_params_t *af_params, s32 bssidx, const u8 *sa);
+ struct net_device *dev, wl_af_params_v1_t *af_params, s32 bssidx, const u8 *sa);
extern void
-wl_cfgp2p_generate_bss_mac(struct bcm_cfg80211 *cfg, struct ether_addr *primary_addr);
+wl_cfgp2p_generate_bss_mac(struct bcm_cfg80211 *cfg);
extern void
wl_cfg80211_change_ifaddr(u8* buf, struct ether_addr *p2p_int_addr, u8 element_id);
@@ -376,7 +376,7 @@
wl_cfgp2p_find_attrib_in_all_p2p_Ies(const u8 *parse, u32 len, u32 attrib);
extern const u8 *
-wl_cfgp2p_retreive_p2p_dev_addr(wl_bss_info_t *bi, u32 bi_length);
+wl_cfgp2p_retreive_p2p_dev_addr(wl_bss_info_v109_t *bi, u32 bi_length);
extern s32
wl_cfgp2p_register_ndev(struct bcm_cfg80211 *cfg);
diff --git a/wl_cfgscan.c b/wl_cfgscan.c
old mode 100755
new mode 100644
index ef0c864..78a23a7
--- a/wl_cfgscan.c
+++ b/wl_cfgscan.c
@@ -1,7 +1,7 @@
/*
* Linux cfg80211 driver scan related code
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -135,14 +135,6 @@
static void wl_cfgscan_scan_abort(struct bcm_cfg80211 *cfg);
static void _wl_cfgscan_cancel_scan(struct bcm_cfg80211 *cfg);
-#ifdef ESCAN_CHANNEL_CACHE
-void reset_roam_cache(struct bcm_cfg80211 *cfg);
-void add_roam_cache(struct bcm_cfg80211 *cfg, wl_bss_info_t *bi);
-int get_roam_channel_list(struct bcm_cfg80211 *cfg, chanspec_t target_chan, chanspec_t *channels,
- int n_channels, const wlc_ssid_t *ssid, int ioctl_ver);
-void set_roam_band(int band);
-#endif /* ESCAN_CHANNEL_CACHE */
-
#ifdef WL_SCHED_SCAN
void wl_cfg80211_stop_pno(struct bcm_cfg80211 *cfg, struct net_device *dev);
#endif /* WL_SCHED_SCAN */
@@ -154,7 +146,7 @@
extern int passive_channel_skip;
#ifdef DUAL_ESCAN_RESULT_BUFFER
-static wl_scan_results_t *
+static wl_scan_results_v109_t *
wl_escan_get_buf(struct bcm_cfg80211 *cfg, bool aborted)
{
u8 index;
@@ -168,8 +160,9 @@
index = (cfg->escan_info.cur_sync_id)%SCAN_BUF_CNT;
}
- return (wl_scan_results_t *)cfg->escan_info.escan_buf[index];
+ return (wl_scan_results_v109_t *)cfg->escan_info.escan_buf[index];
}
+
static int
wl_escan_check_sync_id(struct bcm_cfg80211 *cfg, s32 status, u16 result_id, u16 wl_id)
{
@@ -188,17 +181,18 @@
return 0;
}
}
+
#ifdef SYNCID_MISMATCH_DEBUG
#define wl_escan_increment_sync_id(a, b) \
- ((u8)((a)->escan_info.cur_sync_id + (b)) == 0 ? \
- ((a)->escan_info.cur_sync_id = 1) : ((a)->escan_info.cur_sync_id += (b)))
+ ((u8)((a)->escan_info.cur_sync_id + b) == 0 ? \
+ ((a)->escan_info.cur_sync_id = 1) : ((a)->escan_info.cur_sync_id += b))
#define wl_escan_init_sync_id(a) ((a)->escan_info.cur_sync_id = 1)
#else
-#define wl_escan_increment_sync_id(a, b) ((a)->escan_info.cur_sync_id += (b))
+#define wl_escan_increment_sync_id(a, b) ((a)->escan_info.cur_sync_id += b)
#define wl_escan_init_sync_id(a) ((a)->escan_info.cur_sync_id = 0)
#endif /* SYNCID_MISMATCH_DEBUG */
#else
-#define wl_escan_get_buf(a, b) ((wl_scan_results_t *) (a)->escan_info.escan_buf)
+#define wl_escan_get_buf(a, b) ((wl_scan_results_v109_t *) (a)->escan_info.escan_buf)
#define wl_escan_check_sync_id(a, b, c, d) 0
#define wl_escan_increment_sync_id(a, b)
#define wl_escan_init_sync_id(a)
@@ -215,8 +209,8 @@
bzero(ie->buf, sizeof(ie->buf));
}
-static void wl_update_hidden_ap_ie(wl_bss_info_t *bi, const u8 *ie_stream, u32 *ie_size,
- bool update_ssid)
+static void wl_update_hidden_ap_ie(wl_bss_info_v109_t *bi, const u8 *ie_stream, u32 *ie_size,
+ bool update_ssid, u32 *ssid_len_from_ie)
{
u8 *ssidie;
int32 ssid_len = MIN(bi->SSID_len, DOT11_MAX_SSID_LEN);
@@ -237,6 +231,8 @@
if (!ssidie) {
return;
}
+ *ssid_len_from_ie = (u32)ssidie[1];
+
available_buffer_len = ((int)(*ie_size)) - (ssidie + 2 - ie_stream);
remaining_ie_buf_len = available_buffer_len - (int)ssidie[1];
unused_buf_len = WL_EXTRA_BUF_MAX - (4 + bi->length + *ie_size);
@@ -316,7 +312,7 @@
return ie->offset;
}
-s32 wl_inform_single_bss(struct bcm_cfg80211 *cfg, wl_bss_info_t *bi, bool update_ssid)
+s32 wl_inform_single_bss(struct bcm_cfg80211 *cfg, wl_bss_info_v109_t *bi, bool update_ssid)
{
struct wiphy *wiphy = bcmcfg_to_wiphy(cfg);
struct ieee80211_mgmt *mgmt;
@@ -336,6 +332,7 @@
s32 err = 0;
gfp_t aflags;
u8 tmp_buf[IEEE80211_MAX_SSID_LEN + 1];
+ u32 ssid_len_from_ie = 0;
if (unlikely(dtoh32(bi->length) > WL_BSS_INFO_MAX)) {
WL_DBG(("Beacon is larger than buffer. Discarding\n"));
@@ -384,7 +381,13 @@
beacon_proberesp->beacon_int = cpu_to_le16(bi->beacon_period);
beacon_proberesp->capab_info = cpu_to_le16(bi->capability);
wl_rst_ie(cfg);
- wl_update_hidden_ap_ie(bi, ((u8 *) bi) + bi->ie_offset, &bi->ie_length, update_ssid);
+ wl_update_hidden_ap_ie(bi, ((u8 *) bi) + bi->ie_offset, &bi->ie_length,
+ update_ssid, &ssid_len_from_ie);
+ if (ssid_len_from_ie > IEEE80211_MAX_SSID_LEN) {
+ WL_ERR(("wrong SSID len from ie: %d\n", ssid_len_from_ie));
+ err = -EINVAL;
+ goto out_err;
+ }
wl_mrg_ie(cfg, ((u8 *) bi) + bi->ie_offset, bi->ie_length);
wl_cp_ie(cfg, beacon_proberesp->variable, WL_BSS_INFO_MAX -
offsetof(struct wl_cfg80211_bss_info, frame_buf));
@@ -489,8 +492,8 @@
static s32
wl_inform_bss(struct bcm_cfg80211 *cfg)
{
- wl_scan_results_t *bss_list;
- wl_bss_info_t *bi = NULL; /* must be initialized */
+ wl_scan_results_v109_t *bss_list;
+ wl_bss_info_v109_t *bi = NULL; /* must be initialized */
s32 err = 0;
s32 i;
@@ -560,7 +563,7 @@
s32 err = BCME_OK;
s32 buf_len;
ie_setbuf_t *ie_setbuf;
- ie_getbuf_t ie_getbufp;
+ ie_getbuf_t ie_getbufp = {0, 0};
char getbuf[WLC_IOCTL_SMLEN];
if (ie_id != DOT11_MNG_INTERWORKING_ID) {
@@ -709,7 +712,7 @@
#endif /* WL_6G_BAND */
static void
-wl_cfg80211_find_removal_candidate(wl_bss_info_t *bss, removal_element_t *candidate)
+wl_cfg80211_find_removal_candidate(wl_bss_info_v109_t *bss, removal_element_t *candidate)
{
int idx;
for (idx = 0; idx < BUF_OVERFLOW_MGMT_COUNT; idx++) {
@@ -733,18 +736,18 @@
}
static void
-wl_cfg80211_remove_lowRSSI_info(wl_scan_results_t *list, removal_element_t *candidate,
- wl_bss_info_t *bi)
+wl_cfg80211_remove_lowRSSI_info(wl_scan_results_v109_t *list, removal_element_t *candidate,
+ wl_bss_info_v109_t *bi)
{
int idx1, idx2;
int total_delete_len = 0;
for (idx1 = 0; idx1 < BUF_OVERFLOW_MGMT_COUNT; idx1++) {
- int cur_len = WL_SCAN_RESULTS_FIXED_SIZE;
- wl_bss_info_t *bss = NULL;
+ int cur_len = WL_SCAN_RESULTS_V109_FIXED_SIZE;
+ wl_bss_info_v109_t *bss = NULL;
if (candidate[idx1].RSSI >= BSSRSSI(bi))
continue;
for (idx2 = 0; idx2 < list->count; idx2++) {
- bss = bss ? (wl_bss_info_t *)((uintptr)bss + dtoh32(bss->length)) :
+ bss = bss ? (wl_bss_info_v109_t *)((uintptr)bss + dtoh32(bss->length)) :
list->bss_info;
if (!bss) {
continue;
@@ -781,15 +784,15 @@
{
s32 err = BCME_OK;
s32 status = ntoh32(e->status);
- wl_escan_result_t *escan_result;
+ wl_escan_result_v109_t *escan_result;
struct net_device *ndev = NULL;
#ifndef WL_DRV_AVOID_SCANCACHE
- wl_bss_info_t *bi;
+ wl_bss_info_v109_t *bi;
u32 bi_length;
const wifi_p2p_ie_t * p2p_ie;
const u8 *p2p_dev_addr = NULL;
- wl_scan_results_t *list;
- wl_bss_info_t *bss = NULL;
+ wl_scan_results_v109_t *list;
+ wl_bss_info_v109_t *bss = NULL;
u32 i;
#endif /* WL_DRV_AVOID_SCANCACHE */
@@ -820,7 +823,7 @@
else
ndev = cfg->escan_info.ndev;
}
- escan_result = (wl_escan_result_t *)data;
+ escan_result = (wl_escan_result_v109_t *)data;
if (!escan_result) {
WL_ERR(("Invalid escan result (NULL data)\n"));
goto exit;
@@ -857,7 +860,7 @@
WL_DBG(("WLC_E_STATUS_PARTIAL \n"));
DBG_EVENT_LOG((dhd_pub_t *)cfg->pub, WIFI_EVENT_DRIVER_SCAN_RESULT_FOUND);
if ((dtoh32(escan_result->buflen) > (int)ESCAN_BUF_SIZE) ||
- (dtoh32(escan_result->buflen) < sizeof(wl_escan_result_t))) {
+ (dtoh32(escan_result->buflen) < sizeof(wl_escan_result_v109_t))) {
WL_ERR(("Invalid escan buffer len:%d\n", dtoh32(escan_result->buflen)));
goto exit;
}
@@ -871,7 +874,8 @@
goto exit;
}
bi_length = dtoh32(bi->length);
- if (bi_length != (dtoh32(escan_result->buflen) - WL_ESCAN_RESULTS_FIXED_SIZE)) {
+ if (bi_length != (dtoh32(escan_result->buflen)
+ - WL_ESCAN_RESULTS_V109_FIXED_SIZE)) {
WL_ERR(("Invalid bss_info length %d: ignoring\n", bi_length));
goto exit;
}
@@ -905,7 +909,7 @@
}
} else {
- int cur_len = WL_SCAN_RESULTS_FIXED_SIZE;
+ int cur_len = WL_SCAN_RESULTS_V109_FIXED_SIZE;
#ifdef ESCAN_BUF_OVERFLOW_MGMT
removal_element_t candidate[BUF_OVERFLOW_MGMT_COUNT];
int remove_lower_rssi = FALSE;
@@ -952,8 +956,8 @@
#endif /* ESCAN_BUF_OVERFLOW_MGMT */
for (i = 0; i < list->count; i++) {
- bss = bss ? (wl_bss_info_t *)((uintptr)bss + dtoh32(bss->length))
- : list->bss_info;
+ bss = bss ? (wl_bss_info_v109_t *)
+ ((uintptr)bss + dtoh32(bss->length)): list->bss_info;
if (!bss) {
WL_ERR(("bss is NULL\n"));
goto exit;
@@ -1146,7 +1150,7 @@
if (cfg->afx_hdl->peer_chan == WL_INVALID)
complete(&cfg->act_frm_scan);
} else if ((likely(cfg->scan_request)) || (cfg->sched_scan_running)) {
- WL_INFORM_MEM(("ESCAN ABORTED\n"));
+ WL_INFORM_MEM(("ESCAN ABORTED - reason:%d\n", status));
if (cfg->escan_info.ndev != ndev) {
/* Ignore events coming for older scan reqs */
@@ -1231,6 +1235,115 @@
return err;
}
+#ifdef WL_SCHED_SCAN
+s32 wl_cfgscan_pfn_handler(struct bcm_cfg80211 *cfg, wl_pfn_scanresult_v3_1_t *pfn_scanresult)
+{
+ s32 err = BCME_OK;
+ wl_bss_info_v109_t *bi = NULL;
+
+ bi = (wl_bss_info_v109_t *)pfn_scanresult->bss_info;
+ if (!bi) {
+ WL_ERR(("Invalid pfn bss info (NULL pointer)"
+ "or invalid bss_info length\n"));
+ goto exit;
+ }
+ preempt_disable();
+#ifdef ESCAN_CHANNEL_CACHE
+ add_roam_cache(cfg, bi);
+#endif /* ESCAN_CHANNEL_CACHE */
+ err = wl_inform_single_bss(cfg, bi, false);
+ if (unlikely(err)) {
+ WL_ERR(("bss inform failed\n"));
+ }
+ preempt_enable();
+ WL_MEM(("cfg80211 scan cache updated\n"));
+exit:
+ return err;
+}
+
+s32
+wl_cfgscan_pfn_scanresult_handler(struct bcm_cfg80211 *cfg, bcm_struct_cfgdev *cfgdev,
+ const wl_event_msg_t *e, void *data)
+{
+ s32 err = BCME_OK;
+ wl_pfn_scanresult_v3_1_t *pfn_scanresult;
+
+ WL_DBG_MEM(("event type : %d, status : %d \n",
+ ntoh32(e->event_type), ntoh32(e->status)));
+
+ mutex_lock(&cfg->scan_sync);
+
+ pfn_scanresult = (wl_pfn_scanresult_v3_1_t *)data;
+ if (!pfn_scanresult) {
+ WL_ERR(("Invalid pfn scan result (NULL data)\n"));
+ goto exit;
+ }
+
+ if (cfg->sched_scan_req) {
+ err = wl_cfgscan_pfn_handler(cfg, pfn_scanresult);
+ }
+exit:
+ mutex_unlock(&cfg->scan_sync);
+ return err;
+}
+#endif /* WL_SCHED_SCAN */
+
+#if defined(GSCAN_SUPPORT) || defined(WL_SCHED_SCAN)
+/* sched scan done and stop pno upon receiving the pfn scan complete event */
+s32
+wl_cfgscan_notify_pfn_complete(struct bcm_cfg80211 *cfg, bcm_struct_cfgdev *cfgdev,
+ const wl_event_msg_t *e, void *data)
+{
+ s32 err = BCME_OK;
+ struct net_device *dev;
+ s32 status = ntoh32(e->status);
+ dhd_pub_t *dhdp = (dhd_pub_t *)(cfg->pub);
+ struct wiphy *wiphy = NULL;
+
+ dev = cfgdev_to_wlc_ndev(cfgdev, cfg);
+ WL_DBG_MEM(("Enter \n"));
+ BCM_REFERENCE(dhdp);
+
+#ifdef GSCAN_SUPPORT
+ err = wl_notify_gscan_event(cfg, cfgdev, e, data);
+ return err;
+#endif
+ mutex_lock(&cfg->scan_sync);
+
+ if (!cfg->sched_scan_req) {
+ WL_INFORM_MEM(("No sched scan req is in progress.\n"));
+ goto exit;
+ }
+
+ wiphy = cfg->sched_scan_req->wiphy;
+ /* If new sched scan triggered, wiphy set as NULL.
+ * In this case, drop this event to avoid kernel state schew up
+ */
+ if (!wiphy) {
+ WL_INFORM_MEM(("wiphy of sched_scan_req is NULL.\n"));
+ goto exit;
+ }
+
+ if (status == WLC_E_STATUS_SUCCESS) {
+ WL_INFORM_MEM(("[%s] Report sched scan done.\n", dev->name));
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(4, 11, 0))
+ cfg80211_sched_scan_results(wiphy,
+ cfg->sched_scan_req->reqid);
+#else
+ cfg80211_sched_scan_results(wiphy);
+#endif /* LINUX_VER > 4.11 */
+ } else if (status != WLC_E_STATUS_SUCCESS) {
+ WL_INFORM_MEM(("bss list empty. report sched_scan_stop\n"));
+ wl_cfg80211_stop_pno(cfg, bcmcfg_to_prmry_ndev(cfg));
+ /* schedule the work to indicate sched scan stop to cfg layer */
+ schedule_delayed_work(&cfg->sched_scan_stop_work, 0);
+ }
+exit:
+ mutex_unlock(&cfg->scan_sync);
+ return err;
+}
+#endif /* GSCAN_SUPPORT || WL_SCHED_SCAN */
+
#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 19, 0)) && \
defined(SUPPORT_RANDOM_MAC_SCAN)
static const u8 *
@@ -1508,6 +1621,14 @@
continue;
}
#endif /* P2P_SKIP_DFS */
+#ifdef WL_UNII4_CHAN
+ /* Skip UNII-4 frequencies */
+ if (CHSPEC_IS5G(chanspec) &&
+ IS_UNII4_CHANNEL(wf_chspec_primary20_chan(chanspec))) {
+ WL_DBG(("Skip UNII-4 chanspec 0x%x\n", chanspec));
+ continue;
+ }
+#endif /* WL_UNII4_CHAN */
}
if (use_chanspecs) {
@@ -1577,7 +1698,7 @@
wl_scan_prep(struct bcm_cfg80211 *cfg, void *scan_params, u32 len,
struct cfg80211_scan_request *request)
{
- wl_scan_params_t *params = NULL;
+ wl_scan_params_v1_t *params = NULL;
wl_scan_params_v3_t *params_v3 = NULL;
u32 scan_type = 0;
u32 scan_param_size = 0;
@@ -1602,9 +1723,9 @@
scan_param_size = sizeof(wl_scan_params_v3_t);
channel_offset = offsetof(wl_scan_params_v3_t, channel_list);
} else {
- params = (wl_scan_params_t *)scan_params;
- scan_param_size = sizeof(wl_scan_params_t);
- channel_offset = offsetof(wl_scan_params_t, channel_list);
+ params = (wl_scan_params_v1_t *)scan_params;
+ scan_param_size = sizeof(wl_scan_params_v1_t);
+ channel_offset = offsetof(wl_scan_params_v1_t, channel_list);
}
if (params_v3) {
@@ -1772,7 +1893,7 @@
u32 n_channels = 0;
u32 n_ssids;
s32 params_size;
- wl_escan_params_t *eparams = NULL;
+ wl_escan_params_v1_t *eparams = NULL;
wl_escan_params_v3_t *eparams_v3 = NULL;
u8 *scan_params = NULL;
u8 *params = NULL;
@@ -1791,14 +1912,16 @@
if (!cfg || !request) {
err = -EINVAL;
+ WL_ERR(("invalid escan parameter\n"));
goto exit;
}
if (IS_SCAN_PARAMS_V3_V2(cfg)) {
params_size = (WL_SCAN_PARAMS_V3_FIXED_SIZE +
- OFFSETOF(wl_escan_params_v3_t, params));
+ OFFSETOF(wl_escan_params_v3_t, params));
} else {
- params_size = (WL_SCAN_PARAMS_FIXED_SIZE + OFFSETOF(wl_escan_params_t, params));
+ params_size = (WL_SCAN_PARAMS_V1_FIXED_SIZE
+ + OFFSETOF(wl_escan_params_v1_t, params));
}
if (!cfg->p2p_supported || !p2p_scan(cfg)) {
@@ -1875,11 +1998,12 @@
else
params_size += sizeof(u16) * n_channels;
- /* Allocate space for populating ssids in wl_escan_params_t struct */
+ /* Allocate space for populating ssids in wl_escan_params_v1_t struct */
params_size += sizeof(struct wlc_ssid) * n_ssids;
params = MALLOCZ(cfg->osh, params_size);
if (params == NULL) {
err = -ENOMEM;
+ WL_ERR(("malloc failure for escan params\n"));
goto exit;
}
@@ -1891,9 +2015,9 @@
eparams_v3->action = htod16(action);
eparams_v3->sync_id = sync_id;
} else {
- eparams = (wl_escan_params_t *)params;
+ eparams = (wl_escan_params_v1_t *)params;
scan_params = (u8 *)&eparams->params;
- eparams->version = htod32(ESCAN_REQ_VERSION);
+ eparams->version = htod32(ESCAN_REQ_VERSION_V1);
eparams->action = htod16(action);
eparams->sync_id = sync_id;
}
@@ -2000,6 +2124,11 @@
cfg->p2p->search_state = search_state;
MFREE(cfg->osh, default_chan_list, chan_mem);
+ } else {
+ WL_ERR(("escan not triggered - p2p_supported=%d, p2p_scan=%d, p2p_is_on=%d\n",
+ cfg->p2p_supported, p2p_scan(cfg), p2p_is_on(cfg)));
+ err = -EINVAL;
+ goto exit;
}
exit:
if (unlikely(err)) {
@@ -2020,13 +2149,13 @@
s32 passive_scan;
s32 passive_scan_time;
s32 passive_scan_time_org;
- wl_scan_results_t *results;
+ wl_scan_results_v109_t *results;
WL_SCAN(("Enter \n"));
results = wl_escan_get_buf(cfg, FALSE);
results->version = 0;
results->count = 0;
- results->buflen = WL_SCAN_RESULTS_FIXED_SIZE;
+ results->buflen = WL_SCAN_RESULTS_V109_FIXED_SIZE;
cfg->escan_info.ndev = ndev;
cfg->escan_info.wiphy = wiphy;
@@ -2063,6 +2192,10 @@
}
err = wl_run_escan(cfg, ndev, request, WL_SCAN_ACTION_START);
+ if (unlikely(err)) {
+ WL_ERR(("escan failed (%d)\n", err));
+ goto exit;
+ }
if (passive_channel_skip) {
err = wldev_ioctl_set(ndev, WLC_SET_SCAN_PASSIVE_TIME,
@@ -2333,6 +2466,11 @@
}
}
+ if (wl_get_drv_status(cfg, CONNECTING, ndev)) {
+ WL_ERR(("Association is in progress, skip new scan\n"));
+ return FALSE;
+ }
+
if (wl_get_drv_status(cfg, SCAN_ABORTING, ndev)) {
WL_ERR(("Scanning being aborted. skip new scan\n"));
return FALSE;
@@ -2623,6 +2761,15 @@
struct wireless_dev *wdev = NULL;
struct net_device *ndev = NULL;
+ ndev = wl_cfg80211_get_remain_on_channel_ndev(cfg);
+ if (wl_get_drv_status(cfg, REMAINING_ON_CHANNEL, ndev)) {
+ /* Cancel P2P listen */
+ if (cfg->p2p_supported && cfg->p2p) {
+ wl_cfgp2p_set_p2p_mode(cfg, WL_P2P_DISC_ST_SCAN, 0, 0,
+ wl_to_p2p_bss_bssidx(cfg, P2PAPI_BSSCFG_DEVICE));
+ }
+ }
+
if (!cfg->scan_request && !cfg->sched_scan_req) {
/* No scans in progress */
WL_INFORM_MEM(("No scan in progress\n"));
@@ -2639,6 +2786,7 @@
/* Check if any scan in progress only then abort */
if (wl_get_drv_status_all(cfg, SCANNING)) {
+ WL_MEM(("Called by %pS\n", CALL_SITE));
wl_cfgscan_scan_abort(cfg);
/* Indicate escan completion to upper layer */
@@ -2650,6 +2798,7 @@
/* Wrapper function for cancel_scan with scan_sync mutex */
void wl_cfgscan_cancel_scan(struct bcm_cfg80211 *cfg)
{
+ WL_MEM(("Called by %pS\n", CALL_SITE));
mutex_lock(&cfg->scan_sync);
_wl_cfgscan_cancel_scan(cfg);
mutex_unlock(&cfg->scan_sync);
@@ -2671,7 +2820,7 @@
if (IS_SCAN_PARAMS_V3_V2(cfg)) {
params_size = WL_SCAN_PARAMS_V3_FIXED_SIZE + (1 * sizeof(uint16));
} else {
- params_size = WL_SCAN_PARAMS_FIXED_SIZE + (1 * sizeof(uint16));
+ params_size = WL_SCAN_PARAMS_V1_FIXED_SIZE + (1 * sizeof(uint16));
}
params = MALLOCZ(cfg->osh, params_size);
@@ -2690,7 +2839,7 @@
params_v3->channel_num = channel_num;
params_v3->length = htod16(sizeof(wl_scan_params_v3_t));
} else {
- wl_scan_params_t *params_v1 = (wl_scan_params_t *)params;
+ wl_scan_params_v1_t *params_v1 = (wl_scan_params_v1_t *)params;
params_v1->channel_list[0] = channel;
params_v1->channel_num = channel_num;
}
@@ -2960,7 +3109,7 @@
}
#ifdef WL_DRV_AVOID_SCANCACHE
-static u32 wl_p2p_find_peer_channel(struct bcm_cfg80211 *cfg, s32 status, wl_bss_info_t *bi,
+static u32 wl_p2p_find_peer_channel(struct bcm_cfg80211 *cfg, s32 status, wl_bss_info_v109_t *bi,
u32 bi_length)
{
u32 ret;
@@ -3000,11 +3149,13 @@
return ret;
}
-static s32 wl_escan_without_scan_cache(struct bcm_cfg80211 *cfg, wl_escan_result_t *escan_result,
- struct net_device *ndev, const wl_event_msg_t *e, s32 status)
+static s32 wl_escan_without_scan_cache(struct bcm_cfg80211 *cfg,
+ wl_escan_result_v109_t *escan_result,
+ struct net_device *ndev,
+ const wl_event_msg_t *e, s32 status)
{
s32 err = BCME_OK;
- wl_bss_info_t *bi;
+ wl_bss_info_v109_t *bi;
u32 bi_length;
bool aborted = false;
bool fw_abort = false;
@@ -3034,7 +3185,7 @@
bi = escan_result->bss_info;
bi_length = dtoh32(bi->length);
if ((!bi) ||
- (bi_length != (dtoh32(escan_result->buflen) - WL_ESCAN_RESULTS_FIXED_SIZE))) {
+ (bi_length != (dtoh32(escan_result->buflen) - WL_ESCAN_RESULTS_V109_FIXED_SIZE))) {
WL_ERR(("Invalid escan bss info (NULL pointer)"
"or invalid bss_info length\n"));
goto exit;
@@ -3099,11 +3250,10 @@
(status == WLC_E_STATUS_NEWASSOC)) {
/* Handle all cases of scan abort */
- WL_DBG(("ESCAN ABORT reason: %d\n", status));
+ WL_INFORM_MEM(("ESCAN ABORT reason: %d\n", status));
if (wl_p2p_find_peer_channel(cfg, status, NULL, 0)) {
goto exit;
}
- WL_INFORM_MEM(("ESCAN ABORTED\n"));
/* Update escan complete status */
aborted = true;
@@ -3148,7 +3298,7 @@
const wl_event_msg_t *e, void *data)
{
struct channel_info channel_inform;
- wl_scan_results_t *bss_list;
+ wl_scan_results_v109_t *bss_list;
struct net_device *ndev = NULL;
u32 len = WL_SCAN_BUF_MAX;
s32 err = 0;
@@ -3457,6 +3607,7 @@
return err;
}
+
/*
* This is new interface for mac randomization. It takes randmac and randmask
* as arg and it uses scanmac iovar to offload the mac randomization to firmware.
@@ -3616,11 +3767,6 @@
return -EOPNOTSUPP;
}
#endif /* WL_DUAL_STA */
- /* Avoid PNO trigger in connected state */
- if (wl_get_drv_status(cfg, CONNECTED, dev)) {
- WL_ERR(("Sched scan not supported in connected state\n"));
- return -EINVAL;
- }
if (!request) {
WL_ERR(("Sched scan request was NULL\n"));
return -EINVAL;
@@ -3658,15 +3804,18 @@
pno_time = request->scan_plans->interval;
}
+ if (!request->n_ssids || !request->n_match_sets) {
+ WL_ERR(("Invalid sched scan req!! n_ssids:%d, request->n_match_sets:%d \n",
+ request->n_ssids, request->n_match_sets));
+ return -EINVAL;
+ }
+
+ mutex_lock(&cfg->scan_sync);
+
WL_INFORM_MEM(("[%s] Enter. ssids:%d match_sets:%d pno_time:%d pno_repeat:%d "
"channels:%d adaptive:%d\n", dev->name, request->n_ssids, request->n_match_sets,
pno_time, pno_repeat, request->n_channels, adaptive_pno));
- if (!request->n_ssids || !request->n_match_sets) {
- WL_ERR(("Invalid sched scan req!! n_ssids:%d \n", request->n_ssids));
- return -EINVAL;
- }
-
ssids_local = (wlc_ssid_ext_t *)MALLOCZ(cfg->osh,
sizeof(wlc_ssid_ext_t) * MAX_PFN_LIST_COUNT);
if (!ssids_local) {
@@ -3789,6 +3938,7 @@
if (event_data) {
MFREE(cfg->osh, event_data, alloc_len);
}
+ mutex_unlock(&cfg->scan_sync);
return ret;
}
@@ -3831,7 +3981,7 @@
if (cfg->sched_scan_running && wl_get_drv_status(cfg, SCANNING, pri_ndev)) {
/* If targetted escan for PNO is running, abort it */
WL_INFORM_MEM(("abort targetted escan\n"));
- wl_cfgscan_scan_abort(cfg);
+ _wl_cfgscan_cancel_scan(cfg);
wl_clr_drv_status(cfg, SCANNING, pri_ndev);
} else {
WL_INFORM_MEM(("pno escan state:%d\n",
@@ -3932,6 +4082,7 @@
wl_scan_timeout_dbg_enabled = 1;
}
+
void wl_scan_timeout_dbg_clear(void)
{
WL_ERR(("Enter \n"));
@@ -3948,8 +4099,8 @@
struct bcm_cfg80211 *cfg = (struct bcm_cfg80211 *)data;
struct wireless_dev *wdev = NULL;
struct net_device *ndev = NULL;
- wl_scan_results_t *bss_list;
- wl_bss_info_t *bi = NULL;
+ wl_scan_results_v109_t *bss_list;
+ wl_bss_info_v109_t *bi = NULL;
s32 i;
u32 channel;
u64 cur_time = OSL_LOCALTIME_NS();
@@ -4304,8 +4455,9 @@
(void)memcpy_s(ssid_buf, IEEE80211_MAX_SSID_LEN,
ssid[i].ssid, ssid_len);
ssid_buf[ssid_len] = '\0';
- WL_INFORM_MEM(("[PNO] SSID:%s chanspec:0x%x freq:%d band:%d\n",
- ssid_buf, netinfo->pfnsubnet.chanspec,
+ WL_INFORM_MEM(("[PNO] SSID:%s SSID length:%d"
+ " chanspec:0x%x freq:%d band:%d\n",
+ SSID_DBG(ssid_buf), ssid_len, netinfo->pfnsubnet.chanspec,
channel[i].center_freq, channel[i].band));
if (DBG_RING_ACTIVE(dhdp, DHD_EVENT_RING_ID)) {
payload_len = sizeof(log_conn_event_t);
@@ -4384,6 +4536,7 @@
return err;
}
+
/* If target scan is not reliable, set the below define to "1" to do a
* full escan
*/
@@ -4948,9 +5101,9 @@
u32 scan_type, u32 action, u32 passive_time)
{
u32 sync_id = 0;
- wl_escan_params_t *eparams = NULL;
+ wl_escan_params_v1_t *eparams = NULL;
wl_escan_params_v3_t *eparams_v3 = NULL;
- wl_scan_params_t *scanparams = NULL;
+ wl_scan_params_v1_t *scanparams = NULL;
wl_scan_params_v3_t *scanparams_v3 = NULL;
wl_escan_set_sync_id(sync_id, cfg);
@@ -4971,11 +5124,11 @@
scanparams_v3->home_time = htod32(-1);
bzero(&scanparams_v3->ssid, sizeof(wlc_ssid_t));
} else {
- eparams = (wl_escan_params_t *)params;
- eparams->version = htod32(ESCAN_REQ_VERSION);
+ eparams = (wl_escan_params_v1_t *)params;
+ eparams->version = htod32(ESCAN_REQ_VERSION_V1);
eparams->action = htod16(action);
eparams->sync_id = sync_id;
- scanparams = (wl_scan_params_t *)&eparams->params;
+ scanparams = (wl_scan_params_v1_t *)&eparams->params;
(void)memcpy_s(&scanparams->bssid, ETHER_ADDR_LEN, ðer_bcast, ETHER_ADDR_LEN);
scanparams->bss_type = DOT11_BSSTYPE_ANY;
scanparams->scan_type = 0;
@@ -5029,9 +5182,9 @@
s32 err = 0;
struct net_device *ndev = NULL;
u8 *params = NULL;
- wl_escan_params_t *eparams = NULL;
+ wl_escan_params_v1_t *eparams = NULL;
wl_escan_params_v3_t *eparams_v3 = NULL;
- wl_scan_params_t *scanparams = NULL;
+ wl_scan_params_v1_t *scanparams = NULL;
wl_scan_params_v3_t *scanparams_v3 = NULL;
u16 *chanspec_list = NULL;
u32 channel_num = 0, scan_type = 0;
@@ -5067,14 +5220,15 @@
params_size = (WL_SCAN_PARAMS_V3_FIXED_SIZE +
OFFSETOF(wl_escan_params_v3_t, params));
} else {
- params_size = (WL_SCAN_PARAMS_FIXED_SIZE + OFFSETOF(wl_escan_params_t, params));
+ params_size = (WL_SCAN_PARAMS_V1_FIXED_SIZE
+ + OFFSETOF(wl_escan_params_v1_t, params));
}
/* Single channel for listen case. Add a padd of u16 for alignment */
chanspec_num = 1;
params_size += (chanspec_num + 1);
- /* Allocate space for populating single ssid in wl_escan_params_t struct */
+ /* Allocate space for populating single ssid in wl_escan_params_v1_t struct */
params_size += ((u32) sizeof(struct wlc_ssid));
params = MALLOCZ(cfg->osh, params_size);
@@ -5096,8 +5250,8 @@
chanspec_list = scanparams_v3->channel_list;
scanparams_v3->channel_num = channel_num;
} else {
- eparams = (wl_escan_params_t *)params;
- scanparams = (wl_scan_params_t *)&eparams->params;
+ eparams = (wl_escan_params_v1_t *)params;
+ scanparams = (wl_scan_params_v1_t *)&eparams->params;
chanspec_list = scanparams->channel_list;
scanparams->channel_num = channel_num;
}
@@ -5195,6 +5349,11 @@
return -EINVAL;
}
+ if (wl_get_drv_status(cfg, AP_CREATING, ndev)) {
+ err = BCME_BADARG;
+ goto exit;
+ }
+
ndev = cfgdev_to_wlc_ndev(cfgdev, cfg);
target_channel = ieee80211_frequency_to_channel(channel->center_freq);
@@ -5996,39 +6155,21 @@
return 0;
}
- /* bw160 */
- if ((bw == 160) && (pParameter->he_enabled)) {
- chspec = wf_create_chspec_from_primary(channel,
- WL_CHANSPEC_BW_160, chspec_band);
-#ifdef WL_CELLULAR_CHAN_AVOID
- if (!wl_cellavoid_is_safe(cfg->cellavoid_info, chspec)) {
- chspec = INVCHANSPEC;
- }
-#endif /* WL_CELLULAR_CHAN_AVOID */
- if (chspec != INVCHANSPEC) {
- WL_INFORM_MEM(("added %d/160 (0x%x)\n", channel, chspec));
- wl_cfgscan_acs_parse_parameter_save(&qty, pList, chspec);
- } else {
- WL_INFORM_MEM(("failed %d/160 (0x%x)\n", channel, chspec));
- bw = 80; /* downgrade if not found proper chanspec */
- }
- }
-
+ /* Handle 5G band (from bw20 to bw80) */
/* bw80 */
if ((bw == 80) &&
(pParameter->vht_enabled || pParameter->he_enabled)) {
chspec = wf_create_chspec_from_primary(channel,
WL_CHANSPEC_BW_80, chspec_band);
#ifdef WL_CELLULAR_CHAN_AVOID
- if (!wl_cellavoid_is_safe(cfg->cellavoid_info, chspec)) {
+ if (!wl_cellavoid_is_safe_overlap(cfg->cellavoid_info, chspec)) {
chspec = INVCHANSPEC;
}
#endif /* WL_CELLULAR_CHAN_AVOID */
if (chspec != INVCHANSPEC) {
- WL_INFORM_MEM(("added %d/80 (0x%x)\n", channel, chspec));
+ WL_INFORM_MEM(("set %d/80 (0x%x)\n", channel, chspec));
wl_cfgscan_acs_parse_parameter_save(&qty, pList, chspec);
} else {
- WL_INFORM_MEM(("failed %d/80 (0x%x)\n", channel, chspec));
bw = 40; /* downgrade if not found proper chanspec */
}
}
@@ -6040,15 +6181,14 @@
chspec = wf_create_chspec_from_primary(channel,
WL_CHANSPEC_BW_40, chspec_band);
#ifdef WL_CELLULAR_CHAN_AVOID
- if (!wl_cellavoid_is_safe(cfg->cellavoid_info, chspec)) {
+ if (!wl_cellavoid_is_safe_overlap(cfg->cellavoid_info, chspec)) {
chspec = INVCHANSPEC;
}
#endif /* WL_CELLULAR_CHAN_AVOID */
if (chspec != INVCHANSPEC) {
- WL_INFORM_MEM(("added %d/40 (0x%x)\n", channel, chspec));
+ WL_INFORM_MEM(("set %d/40 (0x%x)\n", channel, chspec));
wl_cfgscan_acs_parse_parameter_save(&qty, pList, chspec);
} else {
- WL_INFORM_MEM(("failed %d/40 (0x%x)\n", channel, chspec));
bw = 20; /* downgrade if not found proper chanspec */
}
}
@@ -6060,15 +6200,13 @@
chspec = wf_create_chspec_from_primary(channel,
WL_CHANSPEC_BW_20, chspec_band);
#ifdef WL_CELLULAR_CHAN_AVOID
- if (!wl_cellavoid_is_safe(cfg->cellavoid_info, chspec)) {
+ if (!wl_cellavoid_is_safe_overlap(cfg->cellavoid_info, chspec)) {
chspec = INVCHANSPEC;
}
#endif /* WL_CELLULAR_CHAN_AVOID */
if (chspec != INVCHANSPEC) {
- WL_INFORM_MEM(("added %d/20 (0x%x)\n", channel, chspec));
+ WL_INFORM_MEM(("set %d/20 (0x%x)\n", channel, chspec));
wl_cfgscan_acs_parse_parameter_save(&qty, pList, chspec);
- } else {
- WL_INFORM_MEM(("failed %d/20 (0x%x)\n", channel, chspec));
}
}
@@ -6210,20 +6348,6 @@
u32 band = parameter->band;
struct bcm_cfg80211 *cfg = wl_get_cfg(dev);
-#if defined(CONFIG_WLAN_BEYONDX) || defined(CONFIG_SEC_5GMODEL)
- wl_cfg80211_register_dev_ril_bridge_event_notifier();
- if (band == WLC_BAND_2G) {
- wl_cfg80211_send_msg_to_ril();
-
- if (g_mhs_chan_for_cpcoex) {
- chosen = CH20MHZ_CHSPEC(g_mhs_chan_for_cpcoex);
- g_mhs_chan_for_cpcoex = 0;
- goto done2;
- }
- }
- wl_cfg80211_unregister_dev_ril_bridge_event_notifier();
-#endif /* CONFIG_WLAN_BEYONDX || defined(CONFIG_SEC_5GMODEL) */
-
if (parameter->scc_chspec) {
chosen = parameter->scc_chspec;
WL_INFORM_MEM(("sta connected case. chosen:0x%x\n", chosen));
@@ -6245,6 +6369,9 @@
goto done2;
}
+ /* Make sure any scan is not running before ACS trigged. */
+ wl_cfgscan_cancel_scan(cfg);
+
ret = wldev_ioctl_set(dev, WLC_START_CHANNEL_SEL, (void *)pBuffer, buf_len);
if (ret) {
WL_ERR(("autochannel trigger failed. ret=%d\n", ret));
@@ -6321,53 +6448,6 @@
return ret;
}
-inline bool
-is_chanspec_dfs(struct bcm_cfg80211 *cfg, chanspec_t chspec)
-{
- u32 ch;
- s32 err;
- u8 buf[WLC_IOCTL_SMLEN];
- struct net_device *ndev = bcmcfg_to_prmry_ndev(cfg);
-
- ch = (u32)chspec;
- err = wldev_iovar_getbuf_bsscfg(ndev, "per_chan_info", (void *)&ch,
- sizeof(u32), buf, WLC_IOCTL_SMLEN, 0, NULL);
- if (unlikely(err)) {
- WL_ERR(("get per chan info failed:%d\n", err));
- return FALSE;
- }
-
- /* Check the channel flags returned by fw */
- if (*((u32 *)buf) & WL_CHAN_PASSIVE) {
- return TRUE;
- }
- return FALSE;
-}
-
-static bool wl_find_matching_chanspec(chanspec_t sta_chanspec,
- int qty, uint32 *pList)
-{
- uint32 i = qty;
-
- if (!qty) {
- WL_ERR(("Invalid qty\n"));
- return false;
- }
-
- while (i--) {
- if (pList[i]) {
- if (wf_chspec_ctlchspec((pList[i])) == wf_chspec_ctlchspec(sta_chanspec)) {
- WL_INFORM_MEM(("Found sta chanspec in the list:0x%x\n",
- sta_chanspec));
- return true;
- }
- WL_INFORM_MEM(("skipped chanspec:0x%x\n", pList[i]));
- }
- }
-
- return false;
-}
-
#ifdef DHD_ACS_CHECK_SCC_2G_ACTIVE_CH
bool wl_check_active_2g_chan(struct bcm_cfg80211 *cfg, drv_acs_params_t *parameter,
chanspec_t sta_chanspec)
@@ -6412,160 +6492,6 @@
}
#endif /* DHD_ACS_CHECK_SCC_2G_ACTIVE_CH */
-static bool
-wl_acs_check_scc(struct bcm_cfg80211 *cfg, drv_acs_params_t *parameter,
- chanspec_t sta_chanspec, int qty, uint32 *pList)
-{
- bool scc = FALSE;
-
- if (!(parameter->freq_bands & CHSPEC_TO_WLC_BAND(sta_chanspec))) {
- return scc;
- }
-
- if (wl_find_matching_chanspec(sta_chanspec, qty, pList)) {
- scc = TRUE;
- }
-
-#ifdef DHD_ACS_CHECK_SCC_2G_ACTIVE_CH
- /*
- * For the corner case when STA is running in Ch12 or Ch13
- * and Framework may give the Ch [1-11] to ACS algorithm.
- * In this case, SoftAP will be failed to run.
- * To allow SoftAP to run in that channel as SCC mode,
- * get active channels and check it
- */
- if (scc == FALSE && CHSPEC_IS2G(sta_chanspec)) {
- scc = wl_check_active_2g_chan(cfg, parameter, sta_chanspec);
- }
-#endif /* DHD_ACS_CHECK_SCC_2G_ACTIVE_CH */
-
- if (scc == TRUE) {
- parameter->scc_chspec = sta_chanspec;
- parameter->freq_bands = CHSPEC_TO_WLC_BAND(sta_chanspec);
- WL_INFORM_MEM(("SCC case, ACS pick up STA chanspec:0x%x\n", sta_chanspec));
- }
- return scc;
-}
-
-int
-wl_handle_acs_concurrency_cases(struct bcm_cfg80211 *cfg, drv_acs_params_t *parameter,
- int qty, uint32 *pList)
-{
- chanspec_t chspec = 0;
- wl_ap_oper_data_t ap_oper_data = {0};
-
- /* If STA is connected, figure out the STA connected band and applly
- * following rules:
- * If STA is in DFS channel or there is an AP already in that band, check
- * whether the AP can be started in the other band
- * If STA band and incoming Band matches, attempt SCC
- */
-
- /* Check whether AP is already operational */
- wl_get_ap_chanspecs(cfg, &ap_oper_data);
-
- if (ap_oper_data.count >= MAX_AP_IFACES) {
- WL_ERR(("ACS request in multi AP case!! count:%d\n",
- ap_oper_data.count));
- return -EINVAL;
- }
-
- if (ap_oper_data.count == 1) {
- chanspec_t ch = ap_oper_data.iface[0].chspec;
- u16 ap_band;
-
- /* Single AP case. Bring up the AP in the other band */
- ap_band = CHSPEC_TO_WLC_BAND(ch);
- if ((ap_band == WLC_BAND_5G) || (ap_band == WLC_BAND_6G)) {
- WL_INFORM_MEM(("AP operational in band:%d\n", ap_band));
- if (!(parameter->freq_bands & WLC_BAND_2G)) {
- WL_ERR(("2G band not present in ACS list. fail ACS\n"));
- return -EINVAL;
- } else {
- /* Force set 2g and clear other bands for ACS */
- parameter->freq_bands = WLC_BAND_2G;
- }
- } else if (ap_band == WLC_BAND_2G) {
- WL_INFORM_MEM(("AP operational in 2G band\n"));
- if (!(parameter->freq_bands & WLC_BAND_5G) &&
- !(parameter->freq_bands & WLC_BAND_6G)) {
- WL_ERR(("5G/6G freqs not available in the ACS list. FAIL ACS\n"));
- return -EINVAL;
- } else {
- /* 6g/5g freqlist available. Clear 2g */
- parameter->freq_bands &= ~WLC_BAND_2G;
- }
- }
- WL_INFORM_MEM(("AP band:0x%x Trimmed ACS band:0x%x\n",
- ap_band, parameter->freq_bands));
- }
-
- /* Check STA concurrency cases */
- if (wl_cfgvif_get_iftype_count(cfg, WL_IF_TYPE_STA) >= 2) {
- /* Dual sta operational. Invalid use case */
- WL_ERR(("Dual sta operational. ACS request not expected.\n"));
- return -EINVAL;
- }
-
- chspec = wl_cfg80211_get_sta_chanspec(cfg);
-
- if (chspec) {
- bool scc_case = false;
- u32 sta_band = CHSPEC_TO_WLC_BAND(chspec);
- if (sta_band == WLC_BAND_2G) {
- if (parameter->freq_bands & (WLC_BAND_5G | WLC_BAND_6G)) {
- /* Remove the 2g band from incoming ACS bands */
- parameter->freq_bands &= ~WLC_BAND_2G;
- } else if (wl_acs_check_scc(cfg, parameter, chspec, qty, pList)) {
- scc_case = TRUE;
- } else {
- WL_ERR(("STA connected in 2G,"
- " but no 2G channel available. Fail ACS\n"));
- return -EINVAL;
- }
- } else if (sta_band == WLC_BAND_5G) {
- if (is_chanspec_dfs(cfg, chspec)) {
- /* If STA is in DFS, check for 2G availability in ACS list */
- if (!(parameter->freq_bands & WLC_BAND_2G)) {
- WL_ERR(("STA connected in 5G DFS."
- " but no 2G channel available. Fail ACS\n"));
- return -EINVAL;
- }
- /* Remove the 5g/6g band from incoming ACS bands */
- parameter->freq_bands &= ~(WLC_BAND_5G | WLC_BAND_6G);
- } else if (wl_acs_check_scc(cfg, parameter, chspec, qty, pList)) {
- scc_case = TRUE;
- } else if (parameter->freq_bands & WLC_BAND_2G) {
- parameter->freq_bands = WLC_BAND_2G;
- } else {
- WL_ERR(("STA connected in 5G %x, but no channel available "
- "for ACS %x\n", chspec, parameter->freq_bands));
- return -EINVAL;
- }
- } else if (sta_band == WLC_BAND_6G) {
- if (wl_acs_check_scc(cfg, parameter, chspec, qty, pList)) {
- scc_case = TRUE;
- } else if (parameter->freq_bands & WLC_BAND_2G) {
- parameter->freq_bands = WLC_BAND_2G;
- } else {
- WL_ERR(("STA connected in 6G %x, but no channel available "
- "for ACS %x\n", chspec, parameter->freq_bands));
- return -EINVAL;
- }
- } else {
- WL_ERR(("Invalid sta band. Fail ACS\n"));
- return -EINVAL;
- }
-
- if (!scc_case) {
- WL_INFORM_MEM(("sta_band:%d chanspec:0x%x."
- " Attempt rsdb ACS for band/s:0x%x\n",
- sta_band, chspec, parameter->freq_bands));
- }
- }
- return BCME_OK;
-}
-
#define MAX_ACS_FREQS 256u
static int
wl_convert_freqlist_to_chspeclist(struct bcm_cfg80211 *cfg,
@@ -6577,6 +6503,7 @@
s32 ret = -EINVAL;
u32 *chspeclist = NULL;
u32 *p_chspec_list = NULL;
+ char chanspec_str[CHANSPEC_STR_LEN];
#ifdef WL_CELLULAR_CHAN_AVOID
int safe_chspec_cnt = 0;
u32 *safe_chspeclist = NULL;
@@ -6615,11 +6542,22 @@
continue;
}
+#ifdef WL_UNII4_CHAN
+ /* Skip UNII-4 frequencies */
+ if (CHSPEC_IS5G(chspeclist[j]) &&
+ IS_UNII4_CHANNEL(CHSPEC_CHANNEL(chspeclist[j]))) {
+ WL_DBG(("Skipped UNII-4 chanspec 0x%x\n", chspeclist[j]));
+ continue;
+ }
+#endif /* WL_UNII4_CHAN */
+
#ifdef WL_CELLULAR_CHAN_AVOID
if (wl_cellavoid_is_safe(cfg->cellavoid_info, chspeclist[j])) {
safe_chspeclist[safe_chspec_cnt++] = chspeclist[j];
safe_param.freq_bands |= CHSPEC_TO_WLC_BAND(CHSPEC_BAND(chspeclist[j]));
- WL_INFORM_MEM(("Adding safe chanspec %x to the list\n", chspeclist[j]));
+ wf_chspec_ntoa(chspeclist[j], chanspec_str);
+ WL_INFORM_MEM(("Adding %s (0x%x) to the safe list\n",
+ chanspec_str, chspeclist[j]));
}
#endif /* WL_CELLULAR_CHAN_AVOID */
@@ -6717,7 +6655,8 @@
continue;
}
- WL_INFORM_MEM(("ACS chanspec:0x%x\n", p_chspec_list[i]));
+ wf_chspec_ntoa(p_chspec_list[i], chanspec_str);
+ WL_INFORM_MEM(("ACS : %s (0x%x)\n", chanspec_str, p_chspec_list[i]));
wl_cfgscan_acs_parse_parameter(cfg, req_len, pList,
p_chspec_list[i], parameter);
}
@@ -6964,6 +6903,7 @@
return ret;
}
#endif /* WL_SOFTAP_ACS */
+
void
wl_get_ap_chanspecs(struct bcm_cfg80211 *cfg, wl_ap_oper_data_t *ap_data)
{
@@ -6986,3 +6926,212 @@
}
}
}
+
+inline bool
+is_chanspec_dfs(struct bcm_cfg80211 *cfg, chanspec_t chspec)
+{
+ u32 ch;
+ s32 err;
+ u8 buf[WLC_IOCTL_SMLEN];
+ struct net_device *ndev = bcmcfg_to_prmry_ndev(cfg);
+
+ ch = (u32)chspec;
+ err = wldev_iovar_getbuf_bsscfg(ndev, "per_chan_info", (void *)&ch,
+ sizeof(u32), buf, WLC_IOCTL_SMLEN, 0, NULL);
+ if (unlikely(err)) {
+ WL_ERR(("get per chan info failed:%d\n", err));
+ return FALSE;
+ }
+
+ /* Check the channel flags returned by fw */
+ if (*((u32 *)buf) & WL_CHAN_PASSIVE) {
+ return TRUE;
+ }
+ return FALSE;
+}
+
+static bool wl_find_matching_chanspec(chanspec_t sta_chanspec,
+ int qty, uint32 *pList)
+{
+ uint32 i = qty;
+
+ if (!qty) {
+ WL_ERR(("Invalid qty\n"));
+ return false;
+ }
+
+ while (i--) {
+ if (pList[i]) {
+ if (wf_chspec_ctlchspec((pList[i])) == wf_chspec_ctlchspec(sta_chanspec)) {
+ WL_INFORM_MEM(("Found sta chanspec in the list:0x%x\n",
+ sta_chanspec));
+ return true;
+ }
+ WL_INFORM_MEM(("skipped chanspec:0x%x\n", pList[i]));
+ }
+ }
+
+ return false;
+}
+
+static bool
+wl_acs_check_scc(struct bcm_cfg80211 *cfg, drv_acs_params_t *parameter,
+ chanspec_t sta_chanspec, int qty, uint32 *pList)
+{
+ bool scc = FALSE;
+
+ if (!(parameter->freq_bands & CHSPEC_TO_WLC_BAND(sta_chanspec))) {
+ return scc;
+ }
+
+ if (wl_find_matching_chanspec(sta_chanspec, qty, pList)) {
+ scc = TRUE;
+ }
+
+#ifdef DHD_ACS_CHECK_SCC_2G_ACTIVE_CH
+ /*
+ * For the corner case when STA is running in Ch12 or Ch13
+ * and Framework may give the Ch [1-11] to ACS algorithm.
+ * In this case, SoftAP will be failed to run.
+ * To allow SoftAP to run in that channel as SCC mode,
+ * get active channels and check it
+ */
+ if (scc == FALSE && CHSPEC_IS2G(sta_chanspec)) {
+ scc = wl_check_active_2g_chan(cfg, parameter, sta_chanspec);
+ }
+#endif /* DHD_ACS_CHECK_SCC_2G_ACTIVE_CH */
+
+ if (scc == TRUE) {
+ parameter->scc_chspec = sta_chanspec;
+ parameter->freq_bands = CHSPEC_TO_WLC_BAND(sta_chanspec);
+ WL_INFORM_MEM(("SCC case, ACS pick up STA chanspec:0x%x\n", sta_chanspec));
+ }
+ return scc;
+}
+
+int
+wl_handle_acs_concurrency_cases(struct bcm_cfg80211 *cfg, drv_acs_params_t *parameter,
+ int qty, uint32 *pList)
+{
+ chanspec_t chspec = 0;
+ wl_ap_oper_data_t ap_oper_data = {0};
+
+ /* If STA is connected, figure out the STA connected band and applly
+ * following rules:
+ * If STA is in DFS channel or there is an AP already in that band, check
+ * whether the AP can be started in the other band
+ * If STA band and incoming Band matches, attempt SCC
+ */
+
+ /* Check whether AP is already operational */
+ wl_get_ap_chanspecs(cfg, &ap_oper_data);
+
+ if (ap_oper_data.count >= MAX_AP_IFACES) {
+ WL_ERR(("ACS request in multi AP case!! count:%d\n",
+ ap_oper_data.count));
+ return -EINVAL;
+ }
+
+ if (ap_oper_data.count == 1) {
+ chanspec_t ch = ap_oper_data.iface[0].chspec;
+ u16 ap_band;
+
+ /* Single AP case. Bring up the AP in the other band */
+ ap_band = CHSPEC_TO_WLC_BAND(ch);
+ if ((ap_band == WLC_BAND_5G) || (ap_band == WLC_BAND_6G)) {
+ WL_INFORM_MEM(("AP operational in band:%d\n", ap_band));
+ if (!(parameter->freq_bands & WLC_BAND_2G)) {
+ WL_ERR(("2G band not present in ACS list. fail ACS\n"));
+ return -EINVAL;
+ } else {
+ /* Force set 2g and clear other bands for ACS */
+ parameter->freq_bands = WLC_BAND_2G;
+ }
+ } else if (ap_band == WLC_BAND_2G) {
+ WL_INFORM_MEM(("AP operational in 2G band\n"));
+ if (!(parameter->freq_bands & WLC_BAND_5G) &&
+ !(parameter->freq_bands & WLC_BAND_6G)) {
+ WL_ERR(("5G/6G freqs not available in the ACS list. FAIL ACS\n"));
+ return -EINVAL;
+ } else {
+ /* 6g/5g freqlist available. Clear 2g */
+ parameter->freq_bands &= ~WLC_BAND_2G;
+ }
+ }
+ WL_INFORM_MEM(("AP band:0x%x Trimmed ACS band:0x%x\n",
+ ap_band, parameter->freq_bands));
+ }
+
+ /* Check STA concurrency cases */
+ if (wl_cfgvif_get_iftype_count(cfg, WL_IF_TYPE_STA) >= 2) {
+ /* Dual sta operational. Invalid use case */
+ WL_ERR(("Dual sta operational. ACS request not expected.\n"));
+ return -EINVAL;
+ }
+
+ chspec = wl_cfg80211_get_sta_chanspec(cfg);
+
+ if (chspec) {
+ bool scc_case = false;
+ u32 sta_band = CHSPEC_TO_WLC_BAND(chspec);
+ if (sta_band == WLC_BAND_2G) {
+ if (parameter->freq_bands & (WLC_BAND_5G | WLC_BAND_6G)) {
+ /* Remove the 2g band from incoming ACS bands */
+ parameter->freq_bands &= ~WLC_BAND_2G;
+ } else if (wl_acs_check_scc(cfg, parameter, chspec, qty, pList)) {
+ scc_case = TRUE;
+ } else {
+ WL_ERR(("STA connected in 2G,"
+ " but no 2G channel available. Fail ACS\n"));
+ return -EINVAL;
+ }
+ } else if (sta_band == WLC_BAND_5G) {
+ if (is_chanspec_dfs(cfg, chspec) ||
+#ifdef WL_UNII4_CHAN
+ (CHSPEC_IS5G(chspec) &&
+ IS_UNII4_CHANNEL(wf_chspec_primary20_chan(chspec))) ||
+#endif /* WL_UNII4_CHAN */
+ FALSE) {
+ /*
+ * If STA is in DFS/UNII4 channel,
+ * check for 2G availability in ACS list
+ */
+ if (!(parameter->freq_bands & WLC_BAND_2G)) {
+ WL_ERR(("STA connected in 5G DFS."
+ " but no 2G channel available. Fail ACS\n"));
+ return -EINVAL;
+ }
+ /* Remove the 5g/6g band from incoming ACS bands */
+ parameter->freq_bands &= ~(WLC_BAND_5G | WLC_BAND_6G);
+ } else if (wl_acs_check_scc(cfg, parameter, chspec, qty, pList)) {
+ scc_case = TRUE;
+ } else if (parameter->freq_bands & WLC_BAND_2G) {
+ parameter->freq_bands = WLC_BAND_2G;
+ } else {
+ WL_ERR(("STA connected in 5G %x, but no channel available "
+ "for ACS %x\n", chspec, parameter->freq_bands));
+ return -EINVAL;
+ }
+ } else if (sta_band == WLC_BAND_6G) {
+ if (wl_acs_check_scc(cfg, parameter, chspec, qty, pList)) {
+ scc_case = TRUE;
+ } else if (parameter->freq_bands & WLC_BAND_2G) {
+ parameter->freq_bands = WLC_BAND_2G;
+ } else {
+ WL_ERR(("STA connected in 6G %x, but no channel available "
+ "for ACS %x\n", chspec, parameter->freq_bands));
+ return -EINVAL;
+ }
+ } else {
+ WL_ERR(("Invalid sta band. Fail ACS\n"));
+ return -EINVAL;
+ }
+
+ if (!scc_case) {
+ WL_INFORM_MEM(("sta_band:%d chanspec:0x%x."
+ " Attempt rsdb ACS for band/s:0x%x\n",
+ sta_band, chspec, parameter->freq_bands));
+ }
+ }
+ return BCME_OK;
+}
diff --git a/wl_cfgscan.h b/wl_cfgscan.h
index 353f48c..579aa17 100644
--- a/wl_cfgscan.h
+++ b/wl_cfgscan.h
@@ -1,7 +1,7 @@
/*
* Header for Linux cfg80211 scan
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -98,6 +98,17 @@
const wl_event_msg_t *e, void *data);
#endif /* GSCAN_SUPPORT */
+#ifdef WL_SCHED_SCAN
+extern s32 wl_cfgscan_pfn_scanresult_handler(struct bcm_cfg80211 *cfg, bcm_struct_cfgdev *cfgdev,
+ const wl_event_msg_t *e, void *data);
+extern s32 wl_cfgscan_pfn_handler(struct bcm_cfg80211 *cfg,
+ wl_pfn_scanresult_v3_1_t *pfn_scanresult);
+#endif /* WL_SCHED_SCAN */
+
+#if defined(GSCAN_SUPPORT) || defined(WL_SCHED_SCAN)
+extern s32 wl_cfgscan_notify_pfn_complete(struct bcm_cfg80211 *cfg, bcm_struct_cfgdev *cfgdev,
+ const wl_event_msg_t *e, void *data);
+#endif /* GSCAN_SUPPORT || WL_SCHED_SCAN */
#ifdef WES_SUPPORT
#ifdef CUSTOMER_SCAN_TIMEOUT_SETTING
#define CUSTOMER_WL_SCAN_TIMER_INTERVAL_MS 25000 /* Scan timeout */
@@ -147,7 +158,7 @@
extern s32 wl_cfgscan_cancel_remain_on_channel(struct wiphy *wiphy,
bcm_struct_cfgdev *cfgdev, u64 cookie);
extern chanspec_t wl_freq_to_chanspec(int freq);
-extern s32 wl_inform_single_bss(struct bcm_cfg80211 *cfg, wl_bss_info_t *bi, bool update_ssid);
+extern s32 wl_inform_single_bss(struct bcm_cfg80211 *cfg, wl_bss_info_v109_t *bi, bool update_ssid);
#ifdef WL_GET_RCC
extern int wl_android_get_roam_scan_chanlist(struct bcm_cfg80211 *cfg);
extern int wl_android_get_roam_scan_freqlist(struct bcm_cfg80211 *cfg);
@@ -203,12 +214,20 @@
extern void wl_get_ap_chanspecs(struct bcm_cfg80211 *cfg, wl_ap_oper_data_t *ap_data);
extern int wl_android_get_sta_channel(struct bcm_cfg80211 *cfg);
+extern int wl_handle_acs_concurrency_cases(struct bcm_cfg80211 *cfg,
+ drv_acs_params_t *parameter, int qty, uint32 *pList);
#ifdef WL_SCHED_SCAN
extern void wl_cfgscan_sched_scan_stop_work(struct work_struct *work);
#endif /* WL_SCHED_SCAN */
#ifdef WL_SOFTAP_ACS
extern bool is_chanspec_dfs(struct bcm_cfg80211 *cfg, chanspec_t chspec);
-extern int wl_handle_acs_concurrency_cases(struct bcm_cfg80211 *cfg,
- drv_acs_params_t *parameter, int qty, uint32 *pList);
#endif /* WL_SOFTAP_ACS */
+
+#ifdef ESCAN_CHANNEL_CACHE
+void reset_roam_cache(struct bcm_cfg80211 *cfg);
+void add_roam_cache(struct bcm_cfg80211 *cfg, wl_bss_info_v109_t *bi);
+int get_roam_channel_list(struct bcm_cfg80211 *cfg, chanspec_t target_chan, chanspec_t *channels,
+ int n_channels, const wlc_ssid_t *ssid, int ioctl_ver);
+void set_roam_band(int band);
+#endif /* ESCAN_CHANNEL_CACHE */
#endif /* _wl_cfgscan_h_ */
diff --git a/wl_cfgvendor.c b/wl_cfgvendor.c
index 4e6dcc0..7a81e4d 100755
--- a/wl_cfgvendor.c
+++ b/wl_cfgvendor.c
@@ -1,7 +1,7 @@
/*
* Linux cfg80211 Vendor Extension Code
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -95,6 +95,69 @@
#include <wl_cfg_cellavoid.h>
#endif /* WL_CELLULAR_CHAN_AVOID */
+#ifdef WL_CFGVENDOR_CUST_ADVLOG
+static void wl_cfgvendor_custom_advlog_scan_start(void *plog, uint32 armcycle);
+static void wl_cfgvendor_custom_advlog_scan_cmpl(void *plog, uint32 armcycle);
+static void wl_cfgvendor_custom_advlog_roam_cmpl(void *plog, uint32 armcycle);
+static void wl_cfgvendor_custom_advlog_btm_req(void *plog, uint32 armcycle);
+static void wl_cfgvendor_custom_advlog_btm_resp(void *plog, uint32 armcycle);
+static void wl_cfgvendor_custom_advlog_btm_wtc(void *plog, uint32 armcycle);
+static void wl_cfgvendor_custom_advlog_btm_query(void *plog, uint32 armcycle);
+
+typedef void (*print_advlog_func)(void *log, uint32 armcycle);
+typedef struct _pr_advlog_tbl {
+ uint8 id;
+ print_advlog_func advlog_func;
+} pr_advlog_tbl_t;
+
+typedef struct dhd_covt_roam_rsn {
+ uint roam_rsn;
+ uint cust_roam_rsn;
+} dhd_covt_roam_rsn_t;
+
+typedef enum {
+ WL_CUST_ROAM_REASON_UNKNOWN = 0,
+ WL_CUST_ROAM_REASON_LOW_RSSI,
+ WL_CUST_ROAM_REASON_LOW_RSSI_CU,
+ WL_CUST_ROAM_REASON_BCNS_LOST,
+ WL_CUST_ROAM_REASON_EMERG_ROAM,
+ WL_CUST_ROAM_REASON_BTM_REQ,
+ WL_CUST_ROAM_REASON_IDLE_ROAM,
+ WL_CUST_ROAM_REASON_WTC,
+ WL_CUST_ROAM_REASON_INACTIVITY,
+ WL_CUST_ROAM_REASON_SCAN_TIMEOUT,
+ WL_CUST_ROAM_REASON_BTCOEX,
+ WL_CUST_ROAM_REASON_MAX
+} cust_roam_reason_t;
+
+static dhd_covt_roam_rsn_t dhd_covt_roam_rsn_list[] =
+{
+ {WLC_E_REASON_INITIAL_ASSOC, WL_CUST_ROAM_REASON_UNKNOWN},
+ {WLC_E_REASON_LOW_RSSI, WL_CUST_ROAM_REASON_LOW_RSSI},
+ {WLC_E_REASON_DEAUTH, WL_CUST_ROAM_REASON_EMERG_ROAM},
+ {WLC_E_REASON_DISASSOC, WL_CUST_ROAM_REASON_EMERG_ROAM},
+ {WLC_E_REASON_BCNS_LOST, WL_CUST_ROAM_REASON_BCNS_LOST},
+ {WLC_E_REASON_BSSTRANS_REQ, WL_CUST_ROAM_REASON_BTM_REQ},
+ {WLC_E_REASON_LOW_RSSI_CU, WL_CUST_ROAM_REASON_LOW_RSSI_CU},
+ {WLC_E_REASON_SILENT_ROAM, WL_CUST_ROAM_REASON_IDLE_ROAM},
+ {WLC_E_REASON_INACTIVITY, WL_CUST_ROAM_REASON_INACTIVITY},
+ {WLC_E_REASON_ROAM_SCAN_TIMEOUT, WL_CUST_ROAM_REASON_SCAN_TIMEOUT},
+ {WLC_E_REASON_BTCX_ROAM, WL_CUST_ROAM_REASON_BTCOEX}
+};
+
+static const pr_advlog_tbl_t advlog_print_tbl[] =
+{
+ {ROAM_LOG_SCANSTART, wl_cfgvendor_custom_advlog_scan_start},
+ {ROAM_LOG_SCAN_CMPLT, wl_cfgvendor_custom_advlog_scan_cmpl},
+ {ROAM_LOG_ROAM_CMPLT, wl_cfgvendor_custom_advlog_roam_cmpl},
+ {ROAM_LOG_BTM_REP, wl_cfgvendor_custom_advlog_btm_resp},
+ {ROAM_LOG_WTC_BTM_REP, wl_cfgvendor_custom_advlog_btm_wtc},
+ {ROAM_LOG_BTM_QUERY, wl_cfgvendor_custom_advlog_btm_query},
+ {ROAM_LOG_BTM_REQ, wl_cfgvendor_custom_advlog_btm_req},
+ {PRSV_PERIODIC_ID_MAX, NULL}
+};
+#endif /* WL_CFGVENDOR_CUST_ADVLOG */
+
char*
wl_get_kernel_timestamp(void)
{
@@ -201,6 +264,55 @@
return wl_cfgvendor_send_async_event(wiphy,
bcmcfg_to_prmry_ndev(cfg), BRCM_VENDOR_EVENT_PRIV_STR, buf, len);
}
+
+#ifdef WL_CFGVENDOR_CUST_ADVLOG
+int
+wl_cfgvendor_send_supp_advlog(const char *fmt, ...)
+{
+ char buf[SUPP_LOG_LEN] = {0};
+ struct bcm_cfg80211 *cfg;
+ struct wiphy *wiphy;
+ va_list args;
+ int len;
+ int prefix_len;
+ int rem_len;
+
+ cfg = wl_cfg80211_get_bcmcfg();
+ if (!cfg || !cfg->wdev) {
+ WL_DBG(("supp evt invalid arg\n"));
+ return BCME_OK;
+ }
+
+ wiphy = cfg->wdev->wiphy;
+ prefix_len = snprintf(buf, SUPP_LOG_LEN, "[%s]",
+ wl_get_kernel_timestamp());
+ /* Remaining buffer len */
+ rem_len = SUPP_LOG_LEN - (prefix_len + 1);
+ /* Print the arg list on to the remaining part of the buffer */
+ va_start(args, fmt);
+ len = vsnprintf((buf + prefix_len), rem_len, fmt, args);
+ va_end(args);
+ if (len < 0) {
+ return -EINVAL;
+ }
+
+ if (len > rem_len) {
+ /* If return length is greater than buffer len,
+ * then its truncated buffer case.
+ */
+ len = rem_len;
+ }
+
+ /* Ensure the buffer is null terminated */
+ len += prefix_len;
+ buf[len] = '\0';
+ len++;
+
+ return wl_cfgvendor_send_async_event(wiphy,
+ bcmcfg_to_prmry_ndev(cfg), BRCM_VENDOR_EVENT_CONNECTIVITY_LOG,
+ buf, len);
+}
+#endif /* WL_CFGVENDOR_CUST_ADVLOG */
#endif /* WL_SUPP_EVENT */
/*
@@ -359,6 +471,7 @@
exit:
return err;
}
+
#ifdef CUSTOM_FORCE_NODFS_FLAG
static int
wl_cfgvendor_set_nodfs_flag(struct wiphy *wiphy,
@@ -1654,8 +1767,10 @@
struct bcm_cfg80211 *cfg = wiphy_priv(wiphy);
#ifdef WL_STA_ASSOC_RAND
struct ether_addr primary_mac;
- dhd_pub_t *dhd = (dhd_pub_t *)(cfg->pub);
#endif /* WL_STA_ASSOC_RAND */
+#if defined(WL_STA_ASSOC_RAND) || defined(DHD_FILE_DUMP_EVENT)
+ dhd_pub_t *dhd = (dhd_pub_t *)(cfg->pub);
+#endif /* WL_STA_ASSOC_RAND || DHD_FILE_DUMP_EVENT */
int ret = BCME_OK;
#if defined(WIFI_TURNON_USE_HALINIT)
struct net_device *ndev = wdev_to_wlc_ndev(wdev, cfg);
@@ -1810,6 +1925,12 @@
return;
}
rtt_cache_list = (struct list_head *)rtt_data;
+
+ if (!wiphy) {
+ WL_ERR(("wiphy is NULL\n"));
+ return;
+ }
+
kflags = in_atomic() ? GFP_ATOMIC : GFP_KERNEL;
if (list_empty(rtt_cache_list)) {
#if (defined(CONFIG_ARCH_MSM) && defined(SUPPORT_WDEV_CFG80211_VENDOR_EVENT_ALLOC)) || \
@@ -2268,6 +2389,7 @@
exit:
return err;
}
+
static int
get_responder_info(struct bcm_cfg80211 *cfg,
struct wifi_rtt_responder *responder_info)
@@ -2293,6 +2415,7 @@
}
return err;
}
+
static int
wl_cfgvendor_rtt_get_responder_info(struct wiphy *wiphy, struct wireless_dev *wdev,
const void *data, int len)
@@ -2597,6 +2720,7 @@
return err;
}
#endif /* GSCAN_SUPPORT */
+
#if defined(GSCAN_SUPPORT) || defined(ROAMEXP_SUPPORT)
static int
wl_cfgvendor_set_bssid_blacklist(struct wiphy *wiphy,
@@ -3231,6 +3355,46 @@
}
#endif /* WL_SAE || WL_CLIENT_SAE */
+static int
+wl_cfgvendor_set_td_policy(struct wiphy *wiphy,
+ struct wireless_dev *wdev, const void *data, int len)
+{
+ struct net_device *net = wdev->netdev;
+ int ret = BCME_OK;
+ int attr_type;
+ int rem = len;
+ const struct nlattr *iter;
+
+ BCM_REFERENCE(net);
+ nla_for_each_attr(iter, data, len, rem) {
+ attr_type = nla_type(iter);
+ WL_DBG(("attr type: (%u)\n", attr_type));
+
+ switch (attr_type) {
+ case BRCM_ATTR_TD_POLICY: {
+ u32 td_policy = nla_get_u32(iter);
+
+ WL_INFORM_MEM(("Setting TD policy %d\n", td_policy));
+ ret = wl_cfg80211_set_wsec_info(net, &td_policy,
+ sizeof(td_policy), WL_WSEC_INFO_BSS_TD_POLICY);
+ if (unlikely(ret)) {
+ WL_ERR(("set wsec_info for td_policy failed, error %d\n", ret));
+ /* Trigger disassoc, going ahead with connection is
+ * violation of TD policy
+ */
+ wl_cfg80211_disassoc(net, WLAN_REASON_UNSPECIFIED);
+ }
+ break;
+ }
+ /* Add new attributes here */
+ default:
+ WL_ERR(("%s: Unknown type, %d\n", __FUNCTION__, attr_type));
+ }
+ }
+
+ return ret;
+}
+
#ifdef BCM_PRIV_CMD_SUPPORT
/* strlen("ifname=") + IFNAMESIZE + strlen(" ") + '\0' */
#define ANDROID_PRIV_CMD_IF_PREFIX_LEN (7 + IFNAMSIZ + 2)
@@ -3756,6 +3920,9 @@
if (cmd_data->key.data) {
MFREE(cfg->osh, cmd_data->key.data, NAN_MAX_PMK_LEN);
}
+ if (cmd_data->scid.data) {
+ MFREE(cfg->osh, cmd_data->scid.data, cmd_data->scid.dlen);
+ }
if (cmd_data->sde_svc_info.data) {
MFREE(cfg->osh, cmd_data->sde_svc_info.data, cmd_data->sde_svc_info.dlen);
}
@@ -3779,6 +3946,9 @@
if (cmd_data->key.data) {
MFREE(cfg->osh, cmd_data->key.data, NAN_MAX_PMK_LEN);
}
+ if (cmd_data->scid.data) {
+ MFREE(cfg->osh, cmd_data->scid.data, cmd_data->scid.dlen);
+ }
MFREE(cfg->osh, cmd_data, sizeof(*cmd_data));
}
@@ -3826,6 +3996,65 @@
}
#endif /* WL_NAN_DISC_CACHE */
+static int
+wl_cfgvendor_nan_parse_scid_params(struct bcm_cfg80211 *cfg, nan_str_data_t *scid,
+ const struct nlattr *iter, int attr_type)
+{
+ int ret = BCME_OK;
+
+ switch (attr_type) {
+ case NAN_ATTRIBUTE_SCID_LEN:
+ if (nla_len(iter) != sizeof(uint32)) {
+ ret = -EINVAL;
+ goto exit;
+ }
+ if (scid->dlen) {
+ WL_ERR(("trying to overwrite:%d\n", attr_type));
+ ret = -EINVAL;
+ goto exit;
+ }
+ scid->dlen = nla_get_u32(iter);
+ if ((!scid->dlen) || scid->dlen >= NAN_MAX_SCID_BUF_LEN) {
+ ret = -EINVAL;
+ WL_ERR(("scid len %d invalid\n", scid->dlen));
+ goto exit;
+ }
+ WL_TRACE(("valid scid length = %u\n", scid->dlen));
+ break;
+ case NAN_ATTRIBUTE_SCID:
+ if (!scid->dlen || (nla_len(iter) != scid->dlen)) {
+ WL_ERR(("wrong scid len:%d,%d\n", scid->dlen, nla_len(iter)));
+ ret = -EINVAL;
+ goto exit;
+ }
+ if (scid->data) {
+ WL_ERR(("trying to overwrite:%d\n", attr_type));
+ ret = -EINVAL;
+ goto exit;
+ }
+
+ scid->data = MALLOCZ(cfg->osh, scid->dlen);
+ if (scid->data == NULL) {
+ WL_ERR(("failed to allocate scid, len=%d\n", scid->dlen));
+ ret = -ENOMEM;
+ goto exit;
+ }
+ ret = memcpy_s(scid->data, scid->dlen,
+ nla_data(iter), nla_len(iter));
+ if (ret != BCME_OK) {
+ WL_ERR(("Failed to copy scid data\n"));
+ return ret;
+ }
+ break;
+ default:
+ WL_ERR(("Unknown type, %d\n", attr_type));
+ ret = -EINVAL;
+ break;
+ }
+exit:
+ return ret;
+}
+
int8 chanbuf[CHANSPEC_STR_LEN];
static int
wl_cfgvendor_nan_parse_datapath_args(struct wiphy *wiphy,
@@ -4140,7 +4369,16 @@
goto exit;
}
break;
-
+ case NAN_ATTRIBUTE_SCID_LEN:
+ /* Fall through */
+ case NAN_ATTRIBUTE_SCID:
+ ret = wl_cfgvendor_nan_parse_scid_params(cfg, &cmd_data->scid,
+ iter, attr_type);
+ if (ret != BCME_OK) {
+ WL_ERR(("Failed to scid data\n"));
+ return ret;
+ }
+ break;
default:
WL_ERR(("Unknown type, %d\n", attr_type));
ret = -EINVAL;
@@ -4700,6 +4938,16 @@
return ret;
}
break;
+ case NAN_ATTRIBUTE_SCID_LEN:
+ /* Fall through */
+ case NAN_ATTRIBUTE_SCID:
+ ret = wl_cfgvendor_nan_parse_scid_params(cfg, &cmd_data->scid,
+ iter, attr_type);
+ if (ret != BCME_OK) {
+ WL_ERR(("Failed to scid data\n"));
+ return ret;
+ }
+ break;
case NAN_ATTRIBUTE_RSSI_THRESHOLD_FLAG:
if (nla_len(iter) != sizeof(uint8)) {
ret = -EINVAL;
@@ -5229,45 +5477,10 @@
WL_TRACE(("CSID = %u\n", cmd_data->csid));
break;
case NAN_ATTRIBUTE_SCID_LEN:
- if (nla_len(iter) != sizeof(uint32)) {
- ret = -EINVAL;
- goto exit;
- }
- if (cmd_data->scid.dlen) {
- WL_ERR(("trying to overwrite:%d\n", attr_type));
- ret = -EINVAL;
- goto exit;
- }
- cmd_data->scid.dlen = nla_get_u32(iter);
- if (cmd_data->scid.dlen > MAX_SCID_LEN) {
- ret = -EINVAL;
- WL_ERR_RLMT(("Not allowed beyond %d\n", MAX_SCID_LEN));
- goto exit;
- }
- WL_TRACE(("valid scid length = %u\n", cmd_data->scid.dlen));
- break;
+ /* Fall through */
case NAN_ATTRIBUTE_SCID:
- if (!cmd_data->scid.dlen || (nla_len(iter) != cmd_data->scid.dlen)) {
- WL_ERR(("wrong scid len:%d,%d\n", cmd_data->scid.dlen,
- nla_len(iter)));
- ret = -EINVAL;
- goto exit;
- }
- if (cmd_data->scid.data) {
- WL_ERR(("trying to overwrite:%d\n", attr_type));
- ret = -EINVAL;
- goto exit;
- }
-
- cmd_data->scid.data = MALLOCZ(cfg->osh, cmd_data->scid.dlen);
- if (cmd_data->scid.data == NULL) {
- WL_ERR(("failed to allocate scid, len=%d\n",
- cmd_data->scid.dlen));
- ret = -ENOMEM;
- goto exit;
- }
- ret = memcpy_s(cmd_data->scid.data, cmd_data->scid.dlen,
- nla_data(iter), nla_len(iter));
+ ret = wl_cfgvendor_nan_parse_scid_params(cfg, &cmd_data->scid,
+ iter, attr_type);
if (ret != BCME_OK) {
WL_ERR(("Failed to scid data\n"));
return ret;
@@ -5361,7 +5574,22 @@
ret = -EINVAL;
goto exit;
}
- cmd_data->instant_chan = nla_get_u32(iter);
+ chan = wf_mhz2channel((uint)nla_get_u32(iter), 0);
+ if (chan < 0) {
+ WL_ERR((" Instant mode Channel is not valid %d chan %d \n",
+ (uint)nla_get_u32(iter), chan));
+ ret = -EINVAL;
+ break;
+ }
+ /* 20MHz as BW */
+ cmd_data->instant_chan = wf_channel2chspec(chan, WL_CHANSPEC_BW_20);
+ if (cmd_data->instant_chan <= 0) {
+ WL_ERR((" Instant mode Channel is not valid \n"));
+ ret = -EINVAL;
+ break;
+ }
+ WL_DBG(("valid instant mode chanspec, chanspec = 0x%04x \n",
+ cmd_data->instant_chan));
break;
case NAN_ATTRIBUTE_ENABLE_MERGE:
if (nla_len(iter) != sizeof(uint8)) {
@@ -5401,6 +5629,13 @@
}
cmd_data->dw_early_termination = nla_get_u32(iter);
break;
+ case NAN_ATTRIBUTE_CHRE_REQUEST:
+ if (nla_len(iter) != sizeof(uint8)) {
+ ret = -EINVAL;
+ goto exit;
+ }
+ cmd_data->chre_req = nla_get_u8(iter);
+ break;
default:
WL_ERR(("%s: Unknown type, %d\n", __FUNCTION__, attr_type));
ret = -EINVAL;
@@ -5486,7 +5721,8 @@
}
static int
wl_cfgvendor_nan_dp_ind_event_data_filler(struct sk_buff *msg,
- nan_event_data_t *event_data) {
+ nan_event_data_t *event_data)
+{
int ret = BCME_OK;
ret = nla_put_u32(msg, NAN_ATTRIBUTE_PUBLISH_ID,
@@ -5526,6 +5762,23 @@
goto fail;
}
}
+#ifdef WL_NAN_INSTANT_MODE
+ /* PMKID(scid) info */
+ if (event_data->scid.dlen && event_data->scid.data) {
+ ret = nla_put_u32(msg, NAN_ATTRIBUTE_SCID_LEN, event_data->scid.dlen);
+ if (unlikely(ret)) {
+ WL_ERR(("Failed to put scid info len, ret=%d\n", ret));
+ goto fail;
+ }
+ ret = nla_put(msg, NAN_ATTRIBUTE_SCID,
+ event_data->scid.dlen, event_data->scid.data);
+ if (unlikely(ret)) {
+ WL_ERR(("Failed to put scid info, ret=%d\n", ret));
+ goto fail;
+ }
+ WL_TRACE(("scid info len = %d\n", event_data->scid.dlen));
+ }
+#endif /* WL_NAN_INSTANT_MODE */
fail:
return ret;
@@ -5775,6 +6028,13 @@
WL_ERR(("Failed to put remote NMI, ret=%d\n", ret));
goto fail;
}
+#ifdef WL_NAN_INSTANT_MODE
+ ret = nla_put_u8(msg, NAN_ATTRIBUTE_CIPHER_SUITE_TYPE, event_data->peer_cipher_suite);
+ if (unlikely(ret)) {
+ WL_ERR(("Failed to put CSID, ret=%d\n", ret));
+ goto fail;
+ }
+#endif /* WL_NAN_INSTANT_MODE */
if (event_data->publish_rssi) {
event_data->publish_rssi = -event_data->publish_rssi;
ret = nla_put_u8(msg, NAN_ATTRIBUTE_RSSI_PROXIMITY,
@@ -5822,6 +6082,24 @@
event_data->tx_match_filter.dlen));
}
+#ifdef WL_NAN_INSTANT_MODE
+ /* PMKID(scid) info */
+ if (event_data->scid.dlen && event_data->scid.data) {
+ ret = nla_put_u32(msg, NAN_ATTRIBUTE_SCID_LEN, event_data->scid.dlen);
+ if (unlikely(ret)) {
+ WL_ERR(("Failed to put scid info len, ret=%d\n", ret));
+ goto fail;
+ }
+ ret = nla_put(msg, NAN_ATTRIBUTE_SCID,
+ event_data->scid.dlen, event_data->scid.data);
+ if (unlikely(ret)) {
+ WL_ERR(("Failed to put scid info, ret=%d\n", ret));
+ goto fail;
+ }
+ WL_TRACE(("scid info len = %d\n", event_data->scid.dlen));
+ }
+#endif /* WL_NAN_INSTANT_MODE */
+
fail:
return ret;
}
@@ -6323,6 +6601,7 @@
struct bcm_cfg80211 *cfg = wiphy_priv(wiphy);
nan_hal_resp_t nan_req_resp;
uint32 nan_attr_mask = 0;
+ wl_nancfg_t *nancfg = cfg->nancfg;
wdev = bcmcfg_to_prmry_wdev(cfg);
cmd_data = (nan_config_cmd_data_t *)MALLOCZ(cfg->osh, sizeof(*cmd_data));
@@ -6339,11 +6618,6 @@
goto exit;
}
- if (cfg->nancfg->nan_enable) {
- WL_ERR(("nan is already enabled\n"));
- ret = BCME_OK;
- goto exit;
- }
bzero(&nan_req_resp, sizeof(nan_req_resp));
cmd_data->sid_beacon.sid_enable = NAN_SID_ENABLE_FLAG_INVALID; /* Setting to some default */
@@ -6360,6 +6634,32 @@
goto exit;
}
+ if (nancfg->nan_enable) {
+ if (cmd_data->chre_req) {
+ if (cfg->nancfg->enab_reason == ENABLE_FOR_CHRE) {
+ /* Already enabled for CHRE */
+ ret = BCME_OK;
+ goto exit;
+ } else {
+ /* enabled for APP .. return busy for CHRE req */
+ ret = BCME_BUSY;
+ goto exit;
+ }
+ } else {
+ if (cfg->nancfg->enab_reason == ENABLE_FOR_CHRE) {
+ /* TODO : Disable Nan and enable again for APP
+ * For now return busy
+ */
+ ret = BCME_BUSY;
+ goto exit;
+ } else {
+ /* already enabled for APP */
+ ret = BCME_OK;
+ goto exit;
+ }
+ }
+ }
+
ret = wl_cfgnan_start_handler(wdev->netdev, cfg, cmd_data, nan_attr_mask);
if (ret) {
WL_ERR(("failed to start nan error[%d]\n", ret));
@@ -6367,7 +6667,14 @@
}
/* Initializing Instance Id List */
bzero(cfg->nancfg->nan_inst_ctrl, NAN_ID_CTRL_SIZE * sizeof(nan_svc_inst_t));
+
exit:
+ if (ret == BCME_OK) {
+ nancfg->enab_reason = cmd_data->chre_req ?
+ ENABLE_FOR_CHRE : ENABLE_FOR_APP;
+ WL_INFORM_MEM(("Enabled successful for reason %d\n", nancfg->enab_reason));
+ }
+
ret = wl_cfgvendor_nan_cmd_reply(wiphy, NAN_WIFI_SUBCMD_ENABLE,
&nan_req_resp, ret, cmd_data ? cmd_data->status : BCME_OK);
if (cmd_data) {
@@ -6378,6 +6685,7 @@
MFREE(cfg->osh, cmd_data, sizeof(*cmd_data));
}
NAN_DBG_EXIT();
+
return ret;
}
@@ -6441,11 +6749,31 @@
bool ssn_exists = false;
uint32 delay_ms = 0;
wl_nancfg_t *nancfg = cfg->nancfg;
+ nan_config_cmd_data_t *cmd_data;
+ uint32 nan_attr_mask = 0;
NAN_DBG_ENTER();
mutex_lock(&cfg->if_sync);
wdev = bcmcfg_to_prmry_wdev(cfg);
+
+ cmd_data = (nan_config_cmd_data_t *)MALLOCZ(cfg->osh, sizeof(*cmd_data));
+ if (!cmd_data) {
+ WL_ERR(("%s: memory allocation failed\n", __func__));
+ ret = BCME_NOMEM;
+ goto exit;
+ }
+
+ ret = wl_cfgvendor_nan_parse_args(wiphy, data, len, cmd_data, &nan_attr_mask);
+ if (ret) {
+ WL_ERR(("failed to parse nan vendor args, ret %d\n", ret));
+ goto exit;
+ }
+ if (cmd_data->status == BCME_BADARG) {
+ WL_ERR(("nan vendor args is invalid\n"));
+ goto exit;
+ }
+
if (nancfg->nan_init_state == false) {
WL_INFORM_MEM(("nan is not initialized/nmi doesnt exists\n"));
goto exit;
@@ -6453,6 +6781,19 @@
if (nancfg->nan_enable == false) {
WL_INFORM_MEM(("nan is in disabled state\n"));
} else {
+ if (cmd_data->chre_req) {
+ if (nancfg->enab_reason != ENABLE_FOR_CHRE) {
+ /* Not enabled for CHRE.. ignore disable req */
+ WL_INFORM_MEM(("nan not enabled for CHRE..ignore disab\n"));
+ goto exit;
+ }
+ } else {
+ if (nancfg->enab_reason != ENABLE_FOR_APP) {
+ /* Not enabled for APP.. ignore disable req */
+ WL_INFORM_MEM(("nan not enabled for APP..ignore disab\n"));
+ goto exit;
+ }
+ }
nancfg->notify_user = true;
wl_cfgvendor_terminate_dp_rng_sessions(cfg, wdev, &ssn_exists);
if (ssn_exists == true) {
@@ -7054,6 +7395,50 @@
#define NUM_PNO_SCANS 8
#define NUM_CCA_SAMPLING_SECS 1
+static int wl_cfgvendor_send_stats_info(struct wiphy *wiphy,
+ const void *data, int len)
+{
+ int ret = 0;
+ struct sk_buff *skb;
+ struct bcm_cfg80211 *cfg = wiphy_priv(wiphy);
+ int mem_needed;
+
+ mem_needed = VENDOR_REPLY_OVERHEAD + len + ATTRIBUTE_U32_LEN;
+
+ /* Alloc the SKB for vendor_event */
+ skb = cfg80211_vendor_cmd_alloc_reply_skb(wiphy, mem_needed);
+ if (unlikely(!skb)) {
+ WL_ERR(("skb alloc failed"));
+ return -ENOMEM;
+ }
+
+ ret = nla_put_u32(skb, ANDR_LSTAT_ATTRIBUTE_NUM_RADIO, cfg->num_radios);
+ if (unlikely(ret)) {
+ WL_ERR(("Failed to put number of radios, ret=%d\n", ret));
+ goto fail;
+ }
+
+ ret = nla_put(skb, ANDR_LSTAT_ATTRIBUTE_STATS_INFO, len, data);
+ if (unlikely(ret)) {
+ WL_ERR(("Failed to put stats info , ret=%d\n", ret));
+ goto fail;
+ }
+
+ ret = cfg80211_vendor_cmd_reply(skb);
+ if (unlikely(ret)) {
+ WL_ERR(("Vendor Command reply failed ret:%d \n", ret));
+ }
+
+ return ret;
+fail:
+ /* Free skb memory */
+ if (skb) {
+ kfree_skb(skb);
+ }
+ return ret;
+
+}
+
static void fill_chanspec_to_channel_info(chanspec_t cur_chanspec,
wifi_channel_info *channel, int *cur_band)
{
@@ -7092,13 +7477,157 @@
}
}
-static const uint16 pwrstats_req_type[] = {
- WL_PWRSTATS_TYPE_SCAN,
- WL_PWRSTATS_TYPE_SLICE_INDEX
-};
-#define PWRSTATS_REQ_TYPE_NUM sizeof(pwrstats_req_type) / sizeof(uint16)
-#define LSTAT_SLICE_MAIN 0 /* SLICE ID for 5/6GHZ */
-#define LSTAT_SLICE_AUX 1 /* SLICE ID for 2GHZ */
+static s32
+wl_cfgvendor_get_radio_stats(struct bcm_cfg80211 *cfg, struct net_device *ndev,
+ wifi_channel_stat *chan_stats, int num_channels, char **output, uint *total_len)
+{
+ s32 err = 0;
+ uint radio_stats_size = 0, chan_stats_size = 0, avail_radio_stat_len = 0;
+ char *radio_stat_ptr = NULL, *out_radio_stat = NULL;
+ wifi_radio_stat_h_v2 radio_h_v2[WL_RADIOSTAT_SLICE_INDEX_MAX];
+ wifi_radio_stat_h radio_h;
+ wifi_radio_stat_v1_t *radio_v1;
+ wifi_radio_stat_v2_t radio_req_v2;
+ wifi_radio_stat_v2_t *radio_v2;
+ static char iovar_buf[WLC_IOCTL_MAXLEN];
+ int i = 0;
+
+ chan_stats_size = sizeof(wifi_channel_stat) * num_channels;
+ /* Radio stat field */
+ radio_stats_size = WL_RADIOSTAT_SLICE_INDEX_MAX*(offsetof(wifi_radio_stat, channels)) +
+ chan_stats_size;
+ radio_stat_ptr = (char*)MALLOCZ(cfg->osh, radio_stats_size);
+ if (radio_stat_ptr == NULL) {
+ WL_ERR(("radio_stat_ptr alloc failed\n"));
+ err = BCME_NOMEM;
+ goto exit;
+ }
+ bzero(radio_stat_ptr, radio_stats_size);
+ avail_radio_stat_len = radio_stats_size;
+
+ bzero(&radio_h, sizeof(radio_h));
+ bzero(&radio_h_v2, sizeof(radio_h_v2));
+
+ out_radio_stat = radio_stat_ptr;
+
+ for (i = 0; i < cfg->num_radios; i++) {
+ /* Try the VERSION_2 first */
+ radio_req_v2.version = WIFI_RADIO_STAT_VERSION_2;
+ radio_req_v2.length = sizeof(radio_req_v2);
+ radio_req_v2.radio = i;
+
+ err = wldev_iovar_getbuf(ndev, "radiostat", &radio_req_v2,
+ sizeof(radio_req_v2), iovar_buf, sizeof(iovar_buf), NULL);
+ if (err != BCME_OK && err != BCME_UNSUPPORTED && err != BCME_VERSION) {
+ WL_ERR(("error (%d) - size = %zu\n",
+ err, sizeof(wifi_radio_stat_v2_t)));
+ goto exit;
+ }
+
+ radio_v2 = (wifi_radio_stat_v2_t *)iovar_buf;
+ if ((err == BCME_OK) &&
+ (dtoh16(radio_v2->version) == WIFI_RADIO_STAT_VERSION_2)) {
+ if (i != radio_v2->radio) {
+ WL_ERR(("Fw version is unsupported\n"));
+ err = BCME_UNSUPPORTED;
+ goto exit;
+ }
+ radio_h_v2[i].radio = radio_v2->radio;
+ if (radio_v2->radio != WL_RADIOSTAT_SLICE_INDEX_SCAN) {
+ radio_h_v2[i].on_time = radio_v2->on_time;
+ } else {
+ radio_h_v2[i].on_time = 0;
+ }
+ radio_h_v2[i].tx_time = radio_v2->tx_time;
+ radio_h_v2[i].num_tx_levels = 0;
+ radio_h_v2[i].tx_time_per_levels = NULL;
+#ifdef LINKSTAT_EXT_SUPPORT
+ radio_h_v2[i].rx_time = radio_v2->myrx_time;
+#else
+ radio_h_v2[i].rx_time = radio_v2->rx_time;
+#endif /* LINKSTAT_EXT_SUPPORT */
+ if (radio_v2->radio != WL_RADIOSTAT_SLICE_INDEX_SCAN) {
+ radio_h_v2[i].on_time_scan =
+ (uint32)(radio_v2->on_time_scan / 1000);
+ } else {
+ radio_h_v2[i].on_time_scan = 0;
+ }
+ radio_h_v2[i].on_time_nbd = (uint32)(radio_v2->on_time_nbd / 1000);
+ radio_h_v2[i].on_time_gscan = (uint32)(radio_v2->on_time_gscan / 1000);
+ radio_h_v2[i].on_time_roam_scan = radio_v2->on_time_roam_scan;
+ radio_h_v2[i].on_time_pno_scan =
+ (uint32)(radio_v2->on_time_pno_scan / 1000);
+ radio_h_v2[i].on_time_hs20 = radio_v2->on_time_hs20;
+ if (i == WL_RADIOSTAT_SLICE_INDEX_MAIN) {
+ radio_h_v2[i].num_channels = 0;
+ } else if (i == WL_RADIOSTAT_SLICE_INDEX_AUX) {
+ radio_h_v2[i].num_channels = 0;
+ } else {
+ radio_h_v2[i].num_channels = num_channels;
+ }
+
+ err = memcpy_s(out_radio_stat, avail_radio_stat_len,
+ &radio_h_v2[i], offsetof(wifi_radio_stat, channels));
+ if (err) {
+ WL_ERR(("failed to copy radio_stat_h : %d\n", err));
+ goto exit;
+ }
+ out_radio_stat += offsetof(wifi_radio_stat, channels);
+ avail_radio_stat_len -= offsetof(wifi_radio_stat, channels);
+ } else {
+ /* Retry the VERSION_1 */
+ err = wldev_iovar_getbuf(ndev, "radiostat", NULL, 0,
+ iovar_buf, sizeof(iovar_buf), NULL);
+
+ if (err != BCME_OK && err != BCME_UNSUPPORTED) {
+ WL_ERR(("error (%d) - size = %zu\n",
+ err, sizeof(wifi_radio_stat_v1_t)));
+ goto exit;
+ }
+ radio_v1 = (wifi_radio_stat_v1_t *)iovar_buf;
+ radio_h.rx_time = radio_v1->rx_time;
+ if (radio_v1->radio != WL_RADIOSTAT_SLICE_INDEX_SCAN) {
+ radio_h.on_time = radio_v1->on_time;
+ } else {
+ radio_h.on_time = 0;
+ }
+ radio_h.tx_time = radio_v1->tx_time;
+ radio_h.on_time_nbd = radio_v1->on_time_nbd;
+ radio_h.on_time_gscan = radio_v1->on_time_gscan;
+ radio_h.on_time_hs20 = radio_v1->on_time_hs20;
+ err = memcpy_s(out_radio_stat, avail_radio_stat_len,
+ &radio_h, sizeof(wifi_radio_stat_h));
+ if (err) {
+ WL_ERR(("failed to copy VERSION_1 radio_stat_h : %d\n", err));
+ goto exit;
+ }
+ out_radio_stat += sizeof(wifi_radio_stat_h);
+ avail_radio_stat_len -= sizeof(wifi_radio_stat_h);
+ }
+ }
+ /* Update all channels */
+ err = memcpy_s(out_radio_stat, avail_radio_stat_len,
+ chan_stats, chan_stats_size);
+ if (err) {
+ WL_ERR(("failed to copy all channel_stat: %d\n", err));
+ goto exit;
+ }
+ out_radio_stat += chan_stats_size;
+ avail_radio_stat_len -= chan_stats_size;
+
+ err = memcpy_s(*output, WLC_IOCTL_MAXLEN, radio_stat_ptr, radio_stats_size);
+ if (err) {
+ WL_ERR(("Failed to copy wifi_radio_stat_h: %d\n", err));
+ goto exit;
+ }
+ *output += radio_stats_size;
+ *total_len += radio_stats_size;
+exit:
+ if (radio_stat_ptr) {
+ MFREE(cfg->osh, radio_stat_ptr, radio_stats_size);
+ }
+ return err;
+}
static int wl_cfgvendor_lstats_get_info(struct wiphy *wiphy,
struct wireless_dev *wdev, const void *data, int len)
@@ -7106,16 +7635,12 @@
static char iovar_buf[WLC_IOCTL_MAXLEN];
struct bcm_cfg80211 *cfg = wiphy_priv(wiphy);
struct net_device *inet_ndev = wdev_to_ndev(wdev);
- int err = 0, ret = 0, i;
+ int err = 0, i;
wifi_radio_stat_h radio_h;
wifi_channel_stat *chan_stats = NULL;
+ int num_channels = 0;
uint chan_stats_size = 0;
- wifi_radio_stat_v1_t *radio_v1;
- wifi_radio_stat_v2_t *radio_v2;
- wifi_radio_stat_v2_t radio_req_v2;
#ifdef LINKSTAT_EXT_SUPPORT
- wl_pwr_slice_index_t *p_slice_index = NULL;
- scan_stat_cache_cores_t *scan_stat_cores = &(cfg->scan_stat_cores);
wifi_channel_stat *all_chan_stats = NULL;
cca_congest_ext_channel_req_v2_t *per_chspec_stats = NULL;
uint per_chspec_stats_size = 0;
@@ -7141,19 +7666,12 @@
wl_if_stats_t *if_stats = NULL;
wl_if_infra_enh_stats_v2_t *if_infra_enh_stats = NULL;
dhd_pub_t *dhdp = (dhd_pub_t *)(cfg->pub);
- wl_pwrstats_query_t *p_query = NULL;
- wl_pwrstats_t *pwrstats = NULL;
- wl_pwr_scan_stats_t *p_scan_stats = NULL;
- uint32 tot_pno_dur = 0;
wifi_channel_stat cur_channel_stat;
cca_congest_channel_req_t *cca_result;
cca_congest_channel_req_t cca_req;
uint32 cca_busy_time = 0;
int cur_chansp, cur_band;
chanspec_t cur_chanspec;
- uint query_len;
- uint16 type, taglen;
- void *p_data = NULL;
COMPAT_STRUCT_IFACE(wifi_iface_stat, iface);
@@ -7163,6 +7681,7 @@
BCM_REFERENCE(if_stats);
BCM_REFERENCE(if_infra_enh_stats);
BCM_REFERENCE(dhdp);
+ BCM_REFERENCE(chan_stats_size);
/* Limit link stats query only on primary interface */
if (!IS_INET_LINK_NDEV(cfg, inet_ndev)) {
@@ -7188,179 +7707,12 @@
output = outdata;
bzero(&radio_h, sizeof(wifi_radio_stat_h));
- radio_h.num_channels = NUM_PEER;
-
- /* Try the VERSION_2 first */
- radio_req_v2.version = WIFI_RADIO_STAT_VERSION_2;
- radio_req_v2.length = sizeof(radio_req_v2);
- err = wldev_iovar_getbuf(inet_ndev, "radiostat", &radio_req_v2,
- sizeof(radio_req_v2), iovar_buf, sizeof(iovar_buf), NULL);
-
- if (err != BCME_OK && err != BCME_UNSUPPORTED && err != BCME_VERSION) {
- WL_ERR(("error (%d) - size = %zu\n",
- err, sizeof(wifi_radio_stat_v2_t)));
- goto exit;
- }
-
- radio_v2 = (wifi_radio_stat_v2_t *)iovar_buf;
- if ((err == BCME_OK) &&
- (dtoh16(radio_v2->version) == WIFI_RADIO_STAT_VERSION_2)) {
-#ifdef LINKSTAT_EXT_SUPPORT
- radio_h.rx_time = radio_v2->myrx_time;
-#else
- radio_h.rx_time = radio_v2->rx_time;
-#endif /* LINKSTAT_EXT_SUPPORT */
- radio_h.on_time = radio_v2->on_time;
- radio_h.tx_time = radio_v2->tx_time;
- radio_h.on_time_nbd = radio_v2->on_time_nbd;
- radio_h.on_time_gscan = radio_v2->on_time_gscan;
- radio_h.on_time_hs20 = radio_v2->on_time_hs20;
- } else {
- /* Retry the VERSION_1 */
- err = wldev_iovar_getbuf(inet_ndev, "radiostat", NULL, 0,
- iovar_buf, sizeof(iovar_buf), NULL);
-
- if (err != BCME_OK && err != BCME_UNSUPPORTED) {
- WL_ERR(("error (%d) - size = %zu\n",
- err, sizeof(wifi_radio_stat_v1_t)));
- goto exit;
- }
- radio_v1 = (wifi_radio_stat_v1_t *)iovar_buf;
- radio_h.rx_time = radio_v1->rx_time;
- radio_h.on_time = radio_v1->on_time;
- radio_h.tx_time = radio_v1->tx_time;
- radio_h.on_time_nbd = radio_v1->on_time_nbd;
- radio_h.on_time_gscan = radio_v1->on_time_gscan;
- radio_h.on_time_hs20 = radio_v1->on_time_hs20;
- }
-
- /* Alloc req buffer */
- query_len = OFFSETOF(wl_pwrstats_query_t, type) +
- PWRSTATS_REQ_TYPE_NUM * sizeof(uint16);
- p_query = (wl_pwrstats_query_t *)MALLOCZ(cfg->osh, query_len);
- if (p_query == NULL) {
- WL_ERR(("%s Fail to malloc buffer\n", __FUNCTION__));
- goto exit;
- }
-
- /* Build a list of types */
- p_query->length = PWRSTATS_REQ_TYPE_NUM;
- for (i = 0; i < PWRSTATS_REQ_TYPE_NUM; i++) {
- p_query->type[i] = pwrstats_req_type[i];
- }
-
- err = wldev_iovar_getbuf(inet_ndev, "pwrstats", p_query,
- query_len, iovar_buf, WLC_IOCTL_MAXLEN, NULL);
- if (err != BCME_OK && err != BCME_UNSUPPORTED) {
- WL_ERR(("error (%d) - size = %zu\n", err, sizeof(wl_pwrstats_t)));
- goto exit;
- }
-
- pwrstats = (wl_pwrstats_t *) iovar_buf;
-
- if (dtoh16(pwrstats->version) != WL_PWRSTATS_VERSION) {
- WL_ERR(("PWRSTATS Version mismatch\n"));
- err = BCME_ERROR;
- goto exit;
- }
-
- p_data = pwrstats->data;
- type = dtoh16(((uint16*)p_data)[0]);
- taglen = dtoh16(((uint16*)p_data)[1]);
-
- if (taglen < sizeof(wl_pwr_scan_stats_t)) {
- WL_ERR(("WL_PWRSTATS_TYPE_SCAN(%d) info short len : %d < %d\n",
- type, taglen, (int)sizeof(wl_pwr_scan_stats_t)));
- err = BCME_ERROR;
- goto exit;
- }
-
- p_scan_stats = (wl_pwr_scan_stats_t *)p_data;
-
- /* wl_pwr_scan_stats structure has the array of pno_scans.
- * scan_data_t pno_scans[8];
- * The number of array is 8 : For future PNO bucketing (BSSID, SSID, etc)
- * FW sets the number as harcoded.
- * If the hardcoded number (8) is changed,
- * the loop condition or NUM_PNO_SCANS has to be changed
- */
-
- for (i = 0; i < NUM_PNO_SCANS; i++) {
- tot_pno_dur += dtoh32(p_scan_stats->pno_scans[i].dur);
- }
-
- /* Android Framework defines the total scan time in ms.
- * But FW sends each scan time in us except for roam scan time.
- * So we need to scale the times in ms.
- */
-
- radio_h.on_time_scan = (uint32)((tot_pno_dur +
- dtoh32(p_scan_stats->user_scans.dur) +
- dtoh32(p_scan_stats->assoc_scans.dur) +
- dtoh32(p_scan_stats->other_scans.dur)) / 1000);
-
- radio_h.on_time_scan += dtoh32(p_scan_stats->roam_scans.dur);
- radio_h.on_time_roam_scan = dtoh32(p_scan_stats->roam_scans.dur);
- radio_h.on_time_pno_scan = (uint32)(tot_pno_dur / 1000);
-
- WL_TRACE(("pwr_scan_stats : %u %u %u %u %u %u\n",
- radio_h.on_time_scan,
- dtoh32(p_scan_stats->user_scans.dur),
- dtoh32(p_scan_stats->assoc_scans.dur),
- dtoh32(p_scan_stats->roam_scans.dur),
- tot_pno_dur,
- dtoh32(p_scan_stats->other_scans.dur)));
-
err = wldev_iovar_getint(inet_ndev, "chanspec", (int*)&cur_chansp);
if (err != BCME_OK) {
WL_ERR(("error (%d) \n", err));
goto exit;
}
-#ifdef LINKSTAT_EXT_SUPPORT
- p_data = pwrstats->data + taglen;
- type = dtoh16(((uint16*)p_data)[0]);
- taglen = dtoh16(((uint16*)p_data)[1]);
-
- if (taglen < sizeof(wl_pwr_slice_index_t)) {
- WL_ERR(("WL_PWRSTATS_TYPE_SLICE_INDEX(%d) info short len : %d < %d\n",
- type, taglen, (int)sizeof(wl_pwr_slice_index_t)));
- err = BCME_ERROR;
- goto exit;
- }
-
- p_slice_index = (wl_pwr_slice_index_t *)p_data;
-
- if (p_slice_index->slice_index == LSTAT_SLICE_AUX) {
- scan_stat_cores->on_time_scan_aux = radio_h.on_time_scan;
- scan_stat_cores->on_time_roam_scan_aux = radio_h.on_time_roam_scan;
- scan_stat_cores->on_time_pno_scan_aux = radio_h.on_time_pno_scan;
- } else if (p_slice_index->slice_index == LSTAT_SLICE_MAIN) {
- scan_stat_cores->on_time_scan_main = radio_h.on_time_scan;
- scan_stat_cores->on_time_roam_scan_main = radio_h.on_time_roam_scan;
- scan_stat_cores->on_time_pno_scan_main = radio_h.on_time_pno_scan;
- } else {
- WL_ERR(("Invalid slice : %x\n", p_slice_index->slice_index));
- err = BCME_ERROR;
- goto exit;
- }
-
- WL_INFORM_MEM(("scan_stats : %u %u %u %u %u %u\n",
- scan_stat_cores->on_time_scan_main,
- scan_stat_cores->on_time_roam_scan_main,
- scan_stat_cores->on_time_pno_scan_main,
- scan_stat_cores->on_time_scan_aux,
- scan_stat_cores->on_time_roam_scan_aux,
- scan_stat_cores->on_time_pno_scan_aux));
-
- radio_h.on_time_scan = scan_stat_cores->on_time_scan_main +
- scan_stat_cores->on_time_scan_aux;
- radio_h.on_time_roam_scan = scan_stat_cores->on_time_roam_scan_main +
- scan_stat_cores->on_time_roam_scan_aux;
- radio_h.on_time_pno_scan = scan_stat_cores->on_time_pno_scan_main +
- scan_stat_cores->on_time_pno_scan_aux;
-#endif /* LINKSTAT_EXT_SUPPORT */
-
cur_chanspec = wl_chspec_driver_to_host(cur_chansp);
if (!wf_chspec_valid(cur_chanspec)) {
@@ -7378,9 +7730,6 @@
cur_channel_stat.channel.center_freq0,
cur_channel_stat.channel.center_freq1));
- chan_stats_size = sizeof(wifi_channel_stat);
- chan_stats = &cur_channel_stat;
-
#ifdef LINKSTAT_EXT_SUPPORT
/* Option to get all channel statistics */
all_chan_req.num_of_entries = 0;
@@ -7396,26 +7745,25 @@
all_chan_results = (cca_congest_ext_channel_req_v3_t *) iovar_buf;
if ((err == BCME_OK) &&
(dtoh16(all_chan_results->ver) == WL_CCA_EXT_REQ_VER_V3)) {
- int i = 0, num_channels;
+ int i = 0;
num_channels = dtoh16(all_chan_results->num_of_entries);
- radio_h.num_channels = num_channels;
-
chan_stats_size = sizeof(wifi_channel_stat) * num_channels;
chan_stats = (wifi_channel_stat*)MALLOCZ(cfg->osh, chan_stats_size);
if (chan_stats == NULL) {
WL_ERR(("chan_stats alloc failed\n"));
+ err = BCME_NOMEM;
goto exit;
}
bzero(chan_stats, chan_stats_size);
all_chan_stats = chan_stats;
-
per_chspec_stats_size =
sizeof(cca_congest_ext_channel_req_v2_t) * num_channels;
per_chspec_stats = (cca_congest_ext_channel_req_v2_t *)
MALLOCZ(cfg->osh, per_chspec_stats_size);
if (per_chspec_stats == NULL) {
WL_ERR(("per_chspec_stats alloc failed\n"));
+ err = BCME_NOMEM;
goto exit;
}
(void) memcpy_s(per_chspec_stats, per_chspec_stats_size,
@@ -7445,6 +7793,9 @@
}
all_chan_stats = chan_stats;
#else
+ chan_stats_size = sizeof(wifi_channel_stat);
+ chan_stats = &cur_channel_stat;
+
cca_v3_req.num_of_entries = 1;
cca_v3_req.ver = WL_CCA_EXT_REQ_VER_V3;
cca_v3_req.per_chan_stats->chanspec =
@@ -7538,22 +7889,12 @@
cur_channel_stat.cca_busy_time = cca_busy_time;
}
- ret = memcpy_s(output, WLC_IOCTL_MAXLEN, &radio_h, sizeof(wifi_radio_stat_h));
- if (ret) {
- WL_ERR(("Failed to copy wifi_radio_stat_h: %d\n", ret));
+ err = wl_cfgvendor_get_radio_stats(cfg, inet_ndev, chan_stats,
+ num_channels, &output, &total_len);
+ if (unlikely(err)) {
+ WL_ERR(("Failed to get radio_stat (%d)\n", err));
goto exit;
}
- output += sizeof(wifi_radio_stat_h);
- total_len += sizeof(wifi_radio_stat_h);
-
- ret = memcpy_s(output, (WLC_IOCTL_MAXLEN - sizeof(wifi_radio_stat_h)),
- chan_stats, chan_stats_size);
- if (ret) {
- WL_ERR(("Failed to copy wifi_channel_stat: %d\n", ret));
- goto exit;
- }
- output += chan_stats_size;
- total_len += chan_stats_size;
COMPAT_BZERO_IFACE(wifi_iface_stat, iface);
#ifdef LINKSTAT_EXT_SUPPORT
@@ -7628,9 +7969,9 @@
if (!err) {
/* Populate from if_stats */
- if (dtoh16(if_stats->version) > WL_IF_STATS_T_VERSION) {
+ if (dtoh16(if_stats->version) > WL_IF_STATS_T_VERSION_1) {
WL_ERR(("incorrect version of wl_if_stats_t,"
- " expected=%u got=%u\n", WL_IF_STATS_T_VERSION,
+ " expected=%u got=%u\n", WL_IF_STATS_T_VERSION_1,
if_stats->version));
goto exit;
}
@@ -7722,15 +8063,16 @@
err = BCME_BADLEN;
goto exit;
}
- err = wl_cfgvendor_send_cmd_reply(wiphy, outdata, total_len);
-
- if (unlikely(err))
+ err = wl_cfgvendor_send_stats_info(wiphy, outdata, total_len);
+ if (unlikely(err)) {
WL_ERR(("Vendor Command reply failed ret:%d \n", err));
+ }
exit:
if (outdata) {
MFREE(cfg->osh, outdata, WLC_IOCTL_MAXLEN);
}
+#ifndef DISABLE_IF_COUNTERS
if (if_stats) {
MFREE(cfg->osh, if_stats, sizeof(wl_if_stats_t));
}
@@ -7738,18 +8080,21 @@
if (if_infra_enh_stats) {
MFREE(cfg->osh, if_infra_enh_stats, sizeof(wl_if_infra_enh_stats_v2_t));
}
+#endif /* !DISABLE_IF_COUNTERS */
#ifdef LINKSTAT_EXT_SUPPORT
- if (p_query) {
- MFREE(cfg->osh, p_query, len);
- }
- if (all_chan_stats) {
- MFREE(cfg->osh, all_chan_stats, chan_stats_size);
+ if (chan_stats) {
+ MFREE(cfg->osh, chan_stats, chan_stats_size);
}
if (per_chspec_stats) {
MFREE(cfg->osh, per_chspec_stats, per_chspec_stats_size);
}
#endif /* LINKSTAT_EXT_SUPPORT */
+
+#ifdef RPM_FAST_TRIGGER
+ WL_INFORM(("Trgger RPM Fast\n"));
+ dhd_trigger_rpm_fast(cfg);
+#endif /* RPM_FAST_TRIGGER */
return err;
}
#endif /* LINKSTAT_SUPPORT */
@@ -7813,6 +8158,7 @@
struct buf_data data_from_hal;
int pos = 0;
+ RETURN_EIO_IF_NOT_UP(cfg);
/* Alloc the SKB for vendor_event */
skb = cfg80211_vendor_cmd_alloc_reply_skb(wiphy, CFG80211_VENDOR_CMD_REPLY_SKB_SZ);
if (!skb) {
@@ -7820,7 +8166,6 @@
ret = BCME_NOMEM;
goto exit;
}
- WL_ERR(("%s\n", __FUNCTION__));
memset_s(&data_from_hal, sizeof(data_from_hal), 0, sizeof(data_from_hal));
buf = &data_from_hal;
@@ -7829,6 +8174,8 @@
ret = wl_cfgvendor_get_buf_data(iter, buf);
if (ret)
goto exit;
+
+ WL_DBG_MEM(("%s: type %d\n", __FUNCTION__, type));
switch (type) {
case DUMP_BUF_ATTR_MEMDUMP:
ret = dhd_os_get_socram_dump(bcmcfg_to_prmry_ndev(cfg), &mem_buf,
@@ -8206,14 +8553,14 @@
wl_cfgvendor_dbg_trigger_mem_dump(struct wiphy *wiphy,
struct wireless_dev *wdev, const void *data, int len)
{
- return WIFI_ERROR_NOT_SUPPORTED;
+ return -EOPNOTSUPP;
}
static int
wl_cfgvendor_dbg_get_mem_dump(struct wiphy *wiphy,
struct wireless_dev *wdev, const void *data, int len)
{
- return WIFI_ERROR_NOT_SUPPORTED;
+ return -EOPNOTSUPP;
}
#endif /* !DEBUGABILITY_DISABLE_MEMDUMP */
@@ -8343,6 +8690,7 @@
}
}
+ WL_MEM(("Received GET_RING_DATA ring:%s\n", ring_name));
ret = dhd_os_trigger_get_ring_data(dhd_pub, ring_name);
if (ret < 0) {
WL_ERR(("trigger_get_data failed ret:%d\n", ret));
@@ -8350,6 +8698,54 @@
return ret;
}
+
+#ifdef DHD_HAL_RING_DUMP
+static int wl_cfgvendor_dbg_get_buf_ring_map(struct wiphy *wiphy,
+ struct wireless_dev *wdev, const void *data, int len)
+{
+ int ret = BCME_OK;
+ struct sk_buff *skb = NULL;
+ int map_cnt = ARRAYSIZE(dhd_buf_ring_map);
+ int entry_size = sizeof(dhd_buf_ring_map_entry_t);
+ int i;
+
+ WL_MEM(("map_cnt:%d\n", map_cnt));
+ /* Alloc the SKB for vendor_event */
+ skb = cfg80211_vendor_cmd_alloc_reply_skb(wiphy,
+ nla_total_size(sizeof(dhd_buf_ring_map)) + nla_total_size(sizeof(map_cnt)));
+ if (!skb) {
+ WL_ERR(("skb allocation is failed\n"));
+ ret = BCME_NOMEM;
+ goto fail;
+ }
+
+ ret = nla_put_u32(skb, DEBUG_ATTRIBUTE_BUF_RING_NUM, map_cnt);
+ if (unlikely(ret)) {
+ goto fail;
+ }
+
+ for (i = 0; i < map_cnt; i++) {
+ ret = nla_put(skb, DEBUG_ATTRIBUTE_BUF_RING_MAP, entry_size,
+ &dhd_buf_ring_map[i]);
+ if (unlikely(ret)) {
+ goto fail;
+ }
+ }
+
+ ret = cfg80211_vendor_cmd_reply(skb);
+ if (ret) {
+ /* kfree_skb is called if it is failed */
+ WL_ERR(("Vendor Command reply failed ret:%d \n", ret));
+ }
+ return ret;
+
+fail:
+ if (skb) {
+ kfree_skb(skb);
+ }
+ return ret;
+}
+#endif /* DHD_HAL_RING_DUMP */
#endif /* DEBUGABILITY */
static int wl_cfgvendor_dbg_get_feature(struct wiphy *wiphy,
@@ -8419,6 +8815,7 @@
#endif /* DEBUGABILITY */
#ifdef DHD_LOG_DUMP
+#ifndef DHD_HAL_RING_DUMP
#ifdef DHD_SSSR_DUMP
#define DUMP_SSSR_DUMP_MAX_COUNT 8
static int wl_cfgvendor_nla_put_sssr_dump_data(struct sk_buff *skb,
@@ -8538,17 +8935,19 @@
return BCME_OK;
}
#endif /* DHD_SSSR_DUMP */
+#endif /* DHD_HAL_RING_DUMP */
static int wl_cfgvendor_nla_put_debug_dump_data(struct sk_buff *skb,
struct net_device *ndev)
{
int ret = BCME_OK;
uint32 len = 0;
- char dump_path[128];
#ifdef EWP_DACS
int i = 0, j = 0;
#endif
+#ifndef DHD_HAL_RING_DUMP
+ char dump_path[128];
ret = dhd_get_debug_dump_file_name(ndev, NULL, dump_path, sizeof(dump_path));
if (ret < 0) {
WL_ERR(("%s: Failed to get debug dump filename\n", __FUNCTION__));
@@ -8561,6 +8960,7 @@
}
WL_ERR(("debug_dump path = %s%s\n", dump_path, FILE_NAME_HAL_TAG));
wl_print_verinfo(wl_get_cfg(ndev));
+#endif /* DHD_HAL_RING_DUMP */
len = dhd_get_time_str_len();
if (len) {
@@ -8571,6 +8971,7 @@
}
}
+#ifndef DHD_HAL_RING_DUMP
len = dhd_get_dld_len(DLD_BUF_TYPE_GENERAL);
if (len) {
ret = nla_put_u32(skb, DUMP_LEN_ATTR_GENERAL_LOG, len);
@@ -8579,6 +8980,7 @@
goto exit;
}
}
+#endif /* DHD_HAL_RING_DUMP */
#ifdef EWP_ECNTRS_LOGGING
len = dhd_get_ecntrs_len(ndev, NULL);
if (len) {
@@ -8604,7 +9006,7 @@
++j;
}
#endif /* EWP_DACS */
-
+#ifndef DHD_HAL_RING_DUMP
len = dhd_get_dld_len(DLD_BUF_TYPE_SPECIAL);
if (len) {
ret = nla_put_u32(skb, DUMP_LEN_ATTR_SPECIAL_LOG, len);
@@ -8613,6 +9015,7 @@
goto exit;
}
}
+#endif /* DHD_HAL_RING_DUMP */
len = dhd_get_dhd_dump_len(ndev, NULL);
if (len) {
ret = nla_put_u32(skb, DUMP_LEN_ATTR_DHD_DUMP, len);
@@ -8643,7 +9046,7 @@
}
}
#endif
-
+#ifndef DHD_HAL_RING_DUMP
len = dhd_get_dld_len(DLD_BUF_TYPE_PRESERVE);
if (len) {
ret = nla_put_u32(skb, DUMP_LEN_ATTR_PRESERVE_LOG, len);
@@ -8652,7 +9055,7 @@
goto exit;
}
}
-
+#endif /* DHD_HAL_RING_DUMP */
len = dhd_get_cookie_log_len(ndev, NULL);
if (len) {
ret = nla_put_u32(skb, DUMP_LEN_ATTR_COOKIE, len);
@@ -8694,7 +9097,7 @@
#ifdef DHD_MAP_PKTID_LOGGING
len = dhd_get_pktid_map_logging_len(ndev, NULL, TRUE);
if (len) {
- ret = nla_put_u32(skb, DUMP_LEN_ATTR_PKTID_MAP_LOG, len);
+ ret = nla_put_u32(skb, DUMP_LEN_ATTR_PKTID_MAP_LOG, len);
if (unlikely(ret)) {
WL_ERR(("Failed to nla put pktid log length, ret=%d", ret));
goto exit;
@@ -8713,6 +9116,7 @@
exit:
return ret;
}
+
#if defined(DNGL_AXI_ERROR_LOGGING) && defined(REPORT_AXI_ERROR)
static void wl_cfgvendor_nla_put_axi_error_data(struct sk_buff *skb,
struct net_device *ndev)
@@ -8737,6 +9141,7 @@
}
}
#endif /* DNGL_AXI_ERROR_LOGGING && REPORT_AXI_ERROR */
+
#ifdef DHD_PKT_LOGGING
static int wl_cfgvendor_nla_put_pktlogdump_data(struct sk_buff *skb,
struct net_device *ndev, bool pktlogdbg)
@@ -8783,6 +9188,10 @@
}
#endif /* DHD_PKT_LOGGING */
+#ifndef DHD_HAL_RING_DUMP
+/* There is no appropriate ringbuffer to push etbdump data in google build.
+ * Disable it until negotiated with Google and the etb data is required.
+ */
#ifdef DHD_SDTC_ETB_DUMP
static int wl_cfgvendor_nla_put_sdtc_etb_dump_data(struct sk_buff *skb, struct net_device *ndev)
{
@@ -8820,18 +9229,21 @@
return BCME_OK;
}
#endif /* DHD_SDTC_ETB_DUMP */
+#endif /* DHD_HAL_RING_DUMP */
+
static int wl_cfgvendor_nla_put_memdump_data(struct sk_buff *skb,
struct net_device *ndev, const uint32 fw_len)
{
- char memdump_path[MEMDUMP_PATH_LEN];
int ret = BCME_OK;
-
+#ifndef DHD_HAL_RING_DUMP
+ char memdump_path[MEMDUMP_PATH_LEN];
dhd_get_memdump_filename(ndev, memdump_path, MEMDUMP_PATH_LEN, "mem_dump");
ret = nla_put_string(skb, DUMP_FILENAME_ATTR_MEM_DUMP, memdump_path);
if (unlikely(ret)) {
WL_ERR(("Failed to nla put mem dump path, ret=%d\n", ret));
goto exit;
}
+#endif /* DHD_HAL_RING_DUMP */
ret = nla_put_u32(skb, DUMP_LEN_ATTR_MEMDUMP, fw_len);
if (unlikely(ret)) {
WL_ERR(("Failed to nla put mem dump length, ret=%d\n", ret));
@@ -8854,8 +9266,11 @@
#endif /* DNGL_AXI_ERROR_LOGGING && REPORT_AXI_ERROR */
if (dhd_pub->memdump_enabled || (dhd_pub->memdump_type == DUMP_TYPE_BY_SYSDUMP)) {
if (((ret = wl_cfgvendor_nla_put_debug_dump_data(skb, ndev)) < 0) ||
- ((ret = wl_cfgvendor_nla_put_memdump_data(skb, ndev, fw_len)) < 0) ||
- ((ret = wl_cfgvendor_nla_put_sssr_dump_data(skb, ndev)) < 0)) {
+ ((ret = wl_cfgvendor_nla_put_memdump_data(skb, ndev, fw_len)) < 0)) {
+ goto done;
+ }
+#ifndef DHD_HAL_RING_DUMP
+ if ((ret = wl_cfgvendor_nla_put_sssr_dump_data(skb, ndev)) < 0) {
goto done;
}
if ((ret = wl_cfgvendor_nla_put_sdtc_etb_dump_data(skb, ndev)) < 0) {
@@ -8866,6 +9281,7 @@
goto done;
}
#endif /* DHD_PKT_LOGGING */
+#endif /* DHD_HAL_RING_DUMP */
}
done:
return ret;
@@ -9727,7 +10143,7 @@
err = -ENOMEM;
goto exit;
}
- tvpm_req->version = TVPM_REQ_CURRENT_VERSION;
+ tvpm_req->version = TVPM_REQ_VERSION_1;
tvpm_req->length = reqlen;
tvpm_req->req_type = WL_TVPM_REQ_CLTM_INDEX;
*(int32*)(tvpm_req->value) = duty_cycle;
@@ -10032,14 +10448,24 @@
{
int err = BCME_OK;
struct bcm_cfg80211 *cfg = NULL;
- struct net_device *dev = wdev_to_ndev(wdev);
+ struct net_device *dev = NULL;
if (wdev == NULL) {
WL_ERR(("Invalid wireless device, NULL\n"));
return -EINVAL;
}
- cfg = wl_get_cfg(wdev_to_ndev(wdev));
+ dev = wdev_to_ndev(wdev);
+ if (dev == NULL) {
+ WL_ERR(("Invalid net device, NULL\n"));
+ return -EINVAL;
+ }
+
+ cfg = wl_get_cfg(dev);
+ if (cfg == NULL) {
+ WL_ERR(("Invalid cfg, NULL\n"));
+ return -EINVAL;
+ }
if (dev != cfg->inet_ndev) {
WL_INFORM_MEM(("primary iface changed from (%s) to %s\n",
@@ -10600,7 +11026,7 @@
{
s32 err = BCME_OK;
const wl_twt_setup_cplt_t *setup_cplt = (wl_twt_setup_cplt_t *)event_data;
- const wl_twt_sdesc_t *sdesc = (const wl_twt_sdesc_t *)&setup_cplt[1];
+ const wl_twt_sdesc_v0_t *sdesc = (const wl_twt_sdesc_v0_t *)&setup_cplt[1];
WL_DBG(("TWT_SETUP: status %d, reason %d, configID %d, setup_cmd %d, flow_flags 0x%x,"
" flow_id %d, channel %d, negotiation_type %d, wake_time_h %u, wake_time_l %u,"
@@ -11152,10 +11578,172 @@
{
WL_INFORM_MEM(("trigger subsystem recovery\n"));
dhd_dev_set_accel_force_reg_on(wdev->netdev);
+
return BCME_OK;
}
#endif /* WLAN_ACCEL_BOOT */
+const struct nla_policy wifi_tx_power_limits_attr_policy[TX_POWER_ATTRIBUTE_MAX] = {
+ [TX_POWER_CAP_ENABLE_ATTRIBUTE] = { .type = NLA_U8 },
+};
+
+int
+wl_cfgvendor_set_tx_power_policy_handler(struct wiphy *wiphy,
+ struct wireless_dev *wdev, const void *data, int len)
+{
+ int ret = BCME_OK;
+ int attr_type;
+ int rem = len;
+ const struct nlattr *iter;
+ bool pwr_lmt_enab = false;
+
+ nla_for_each_attr(iter, data, len, rem) {
+ attr_type = nla_type(iter);
+
+ switch (attr_type) {
+ case TX_POWER_CAP_ENABLE_ATTRIBUTE: {
+ if (nla_len(iter) != sizeof(uint8)) {
+ WL_ERR(("Invalid value of tx_power cap\n"));
+ ret = -EINVAL;
+ break;
+ }
+ pwr_lmt_enab = nla_get_u8(iter);
+ break;
+ }
+ /* Add new attributes here */
+ default:
+ WL_ERR(("Unknown type %d\n", attr_type));
+ ret = -EINVAL;
+ goto exit;
+ }
+ }
+
+ WL_DBG_MEM(("wl phy_peak_curr_txpwrcap (%d)\n", pwr_lmt_enab));
+ ret = wldev_iovar_setint(wdev_to_ndev(wdev), "phy_peak_curr_txpwrcap", pwr_lmt_enab);
+ if (unlikely(ret)) {
+ WL_ERR(("txpwrcap set failed with error %d\n", ret));
+ goto exit;
+ }
+exit:
+ return ret;
+}
+
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(5, 3, 0))
+const struct nla_policy wifi_radio_combo_attr_policy[ANDR_WIFI_ATTRIBUTE_RADIO_COMBO_MAX] = {
+ [ANDR_WIFI_ATTRIBUTE_RADIO_COMBO_MATRIX] = { .type = NLA_BINARY },
+};
+#endif /* LINUX_VERSION >= 5.3 */
+
+wifi_radio_configuration radio6_2x2[] = {{WLAN_MAC_6_0_BAND, WIFI_ANTENNA_2X2}};
+wifi_radio_configuration radio5_2x2[] = {{WLAN_MAC_5_0_BAND, WIFI_ANTENNA_2X2}};
+wifi_radio_configuration radio2_2x2[] = {{WLAN_MAC_2_4_BAND, WIFI_ANTENNA_2X2}};
+wifi_radio_configuration radio25_2x2[] = {{WLAN_MAC_2_4_BAND, WIFI_ANTENNA_2X2},
+ {WLAN_MAC_5_0_BAND, WIFI_ANTENNA_2X2}};
+wifi_radio_configuration radio26_2x2[] = {{WLAN_MAC_2_4_BAND, WIFI_ANTENNA_2X2},
+ {WLAN_MAC_6_0_BAND, WIFI_ANTENNA_2X2}};
+
+static int
+wl_cfgvendor_get_radio_combo_matrix(struct wiphy *wiphy,
+ struct wireless_dev *wdev, const void *data, int len)
+{
+ struct net_device *ndev = wdev_to_ndev(wdev);
+ struct sk_buff *skb = NULL;
+ int err, mem_needed;
+ struct bcm_cfg80211 *cfg = wl_get_cfg(ndev);
+ dhd_pub_t *dhdp = (dhd_pub_t *)(cfg->pub);
+ u8 buf[WLC_IOCTL_SMLEN] = {0};
+ u32 total_len = 0, size = 0;
+ wifi_radio_combination *radio_combinations = NULL;
+ wifi_radio_combination_matrix *rc = NULL;
+
+ if (sizeof(buf) < MAX_RADIO_MATRIX_SIZE) {
+ WL_ERR(("Buff too short: %ld, exp max_radio matrix size: %ld\n",
+ sizeof(buf), MAX_RADIO_MATRIX_SIZE));
+ err = BCME_BUFTOOSHORT;
+ goto fail;
+ }
+
+ rc = (wifi_radio_combination_matrix *)buf;
+ (void)memset_s(&buf, sizeof(buf), 0x0, sizeof(buf));
+ radio_combinations = rc->radio_combinations;
+ total_len = sizeof(u32);
+
+ /* Fill up stand alone cases first and conditionally include rsdb & 6G */
+ radio_combinations->num_radio_combinations = 1;
+ (void)(memcpy_s(radio_combinations->radio_configurations,
+ sizeof(radio2_2x2), (void *)radio2_2x2, sizeof(radio2_2x2)));
+ total_len += size = sizeof(u32) + sizeof(radio2_2x2);
+ rc->num_combinations++;
+
+ radio_combinations = (wifi_radio_combination *)((u8 *)radio_combinations + size);
+ radio_combinations->num_radio_combinations = 1;
+ (void)(memcpy_s(radio_combinations->radio_configurations,
+ sizeof(radio5_2x2), (void *)radio5_2x2, sizeof(radio5_2x2)));
+ total_len += size = sizeof(u32) + sizeof(radio5_2x2);
+ rc->num_combinations++;
+
+#ifdef WL_6G_BAND
+ if (cfg->band_6g_supported) {
+ radio_combinations = (wifi_radio_combination *)((u8 *)radio_combinations + size);
+ radio_combinations->num_radio_combinations = 1;
+ (void)(memcpy_s(radio_combinations->radio_configurations,
+ sizeof(radio6_2x2), radio6_2x2, sizeof(radio6_2x2)));
+ total_len += size = sizeof(u32) + sizeof(radio6_2x2);
+ rc->num_combinations++;
+ }
+#endif /* WL_6G_BAND */
+
+ if (FW_SUPPORTED(dhdp, rsdb)) {
+ radio_combinations = (wifi_radio_combination *)((u8 *)radio_combinations + size);
+ radio_combinations->num_radio_combinations = 2;
+ (void)memcpy_s(radio_combinations->radio_configurations,
+ sizeof(radio25_2x2), radio25_2x2, sizeof(radio25_2x2));
+ total_len += size = sizeof(u32) + sizeof(radio25_2x2);
+ rc->num_combinations++;
+
+#ifdef WL_6G_BAND
+ if (cfg->band_6g_supported) {
+ radio_combinations =
+ (wifi_radio_combination *)((u8 *)radio_combinations + size);
+ radio_combinations->num_radio_combinations = 2;
+ (void)memcpy_s(radio_combinations->radio_configurations,
+ sizeof(radio26_2x2), radio26_2x2, sizeof(radio26_2x2));
+ total_len += size = sizeof(u32) + sizeof(radio26_2x2);
+ rc->num_combinations++;
+ }
+#endif /* WL_6G_BAND */
+ }
+
+ mem_needed = VENDOR_REPLY_OVERHEAD + total_len;
+ /* Alloc the SKB for vendor_event */
+ skb = cfg80211_vendor_cmd_alloc_reply_skb(wiphy, mem_needed);
+ if (unlikely(!skb)) {
+ WL_ERR(("skb alloc failed"));
+ err = -ENOMEM;
+ goto fail;
+ }
+
+ err = nla_put(skb, ANDR_WIFI_ATTRIBUTE_RADIO_COMBO_MATRIX, total_len, rc);
+ if (unlikely(err)) {
+ WL_ERR(("nla_put ANDR_WIFI_ATTRIBUTE_RADIO_COMBO_MATRIX failed\n"));
+ goto fail;
+ }
+
+ err = cfg80211_vendor_cmd_reply(skb);
+ if (unlikely(err)) {
+ WL_ERR(("Vendor Command reply failed err:%d \n", err));
+ }
+ return err;
+
+fail:
+ if (skb) {
+ /* Free skb memory */
+ kfree_skb(skb);
+ }
+
+ return err;
+}
+
#if (LINUX_VERSION_CODE >= KERNEL_VERSION(5, 3, 0))
const struct nla_policy andr_wifi_attr_policy[ANDR_WIFI_ATTRIBUTE_MAX] = {
[ANDR_WIFI_ATTRIBUTE_NUM_FEATURE_SET] = { .type = NLA_U32 },
@@ -11237,6 +11825,7 @@
((BRCM_WLAN_VENDOR_FEATURES_MAX / 8) + 1) },
[BRCM_ATTR_DRIVER_RAND_MAC] = { .type = NLA_BINARY, .len = ETHER_ADDR_LEN },
[BRCM_ATTR_SAE_PWE] = { .type = NLA_U32 },
+ [BRCM_ATTR_TD_POLICY] = { .type = NLA_U32 },
};
#ifdef RTT_SUPPORT
@@ -11321,7 +11910,7 @@
[NAN_ATTRIBUTE_RSSI_WINDOW_SIZE] = { .type = NLA_U8, .len = sizeof(uint8) },
[NAN_ATTRIBUTE_CIPHER_SUITE_TYPE] = { .type = NLA_U8, .len = sizeof(uint8) },
[NAN_ATTRIBUTE_SCID_LEN] = { .type = NLA_U32, .len = sizeof(uint32) },
- [NAN_ATTRIBUTE_SCID] = { .type = NLA_BINARY, .len = MAX_SCID_LEN },
+ [NAN_ATTRIBUTE_SCID] = { .type = NLA_BINARY, .len = NAN_MAX_SCID_BUF_LEN },
[NAN_ATTRIBUTE_2G_AWAKE_DW] = { .type = NLA_U32, .len = sizeof(uint32) },
[NAN_ATTRIBUTE_5G_AWAKE_DW] = { .type = NLA_U32, .len = sizeof(uint32) },
[NAN_ATTRIBUTE_DISC_IND_CFG] = { .type = NLA_U8, .len = sizeof(uint8) },
@@ -11390,15 +11979,13 @@
[NAN_ATTRIBUTE_PEER_DISC_MAC_ADDR] = { .type = NLA_BINARY, .len = ETHER_ADDR_LEN },
[NAN_ATTRIBUTE_PEER_NDI_MAC_ADDR] = { .type = NLA_BINARY, .len = ETHER_ADDR_LEN },
[NAN_ATTRIBUTE_IF_ADDR] = { .type = NLA_BINARY, .len = ETHER_ADDR_LEN },
- [NAN_ATTRIBUTE_ENTRY_CONTROL] = { .type = NLA_U8, .len = sizeof(uint8) },
- [NAN_ATTRIBUTE_AVAIL_BIT_MAP] = { .type = NLA_U32, .len = sizeof(uint32) },
- [NAN_ATTRIBUTE_CHANNEL] = { .type = NLA_U32, .len = sizeof(uint32) },
[NAN_ATTRIBUTE_NO_CONFIG_AVAIL] = { .type = NLA_U8, .len = sizeof(uint8) },
[NAN_ATTRIBUTE_CHANNEL_INFO] = { .type = NLA_BINARY, .len =
sizeof(nan_channel_info_t) * NAN_MAX_CHANNEL_INFO_SUPPORTED },
[NAN_ATTRIBUTE_NUM_CHANNELS] = { .type = NLA_U32, .len = sizeof(uint32) },
[NAN_ATTRIBUTE_INSTANT_MODE_ENABLE] = { .type = NLA_U32, .len = sizeof(uint32) },
[NAN_ATTRIBUTE_INSTANT_COMM_CHAN] = { .type = NLA_U32, .len = sizeof(uint32) },
+ [NAN_ATTRIBUTE_CHRE_REQUEST] = { .type = NLA_U8, .len = sizeof(uint8) },
};
#endif /* WL_NAN */
@@ -11631,6 +12218,18 @@
.maxattr = BRCM_ATTR_DRIVER_MAX
#endif /* LINUX_VERSION >= 5.3 */
},
+ {
+ {
+ .vendor_id = OUI_BRCM,
+ .subcmd = BRCM_VENDOR_SCMD_SET_TD_POLICY
+ },
+ .flags = WIPHY_VENDOR_CMD_NEED_WDEV | WIPHY_VENDOR_CMD_NEED_NETDEV,
+ .doit = wl_cfgvendor_set_td_policy,
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(5, 3, 0))
+ .policy = brcm_drv_attr_policy,
+ .maxattr = BRCM_ATTR_DRIVER_MAX
+#endif /* LINUX_VERSION >= 5.3 */
+ },
#ifdef GSCAN_SUPPORT
{
{
@@ -12031,6 +12630,20 @@
#endif /* LINUX_VERSION >= 5.3 */
},
+#ifdef DHD_HAL_RING_DUMP
+ {
+ {
+ .vendor_id = OUI_GOOGLE,
+ .subcmd = DEBUG_GET_BUF_RING_MAP
+ },
+ .flags = WIPHY_VENDOR_CMD_NEED_WDEV | WIPHY_VENDOR_CMD_NEED_NETDEV,
+ .doit = wl_cfgvendor_dbg_get_buf_ring_map,
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(5, 3, 0))
+ .policy = andr_dbg_policy,
+ .maxattr = DEBUG_ATTRIBUTE_MAX
+#endif /* LINUX_VERSION >= 5.3 */
+ },
+#endif /* DHD_HAL_RING_DUMP */
#endif /* DEBUGABILITY */
{
{
@@ -12763,6 +13376,30 @@
.doit = wl_cfgvendor_trigger_ssr
},
#endif /* WLAN_ACCEL_BOOT */
+ {
+ {
+ .vendor_id = OUI_GOOGLE,
+ .subcmd = WIFI_SUBCMD_GET_RADIO_COMBO_MATRIX
+ },
+ .flags = WIPHY_VENDOR_CMD_NEED_WDEV | WIPHY_VENDOR_CMD_NEED_NETDEV,
+ .doit = wl_cfgvendor_get_radio_combo_matrix,
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(5, 3, 0))
+ .policy = wifi_radio_combo_attr_policy,
+ .maxattr = ANDR_WIFI_ATTRIBUTE_RADIO_COMBO_MAX
+#endif /* LINUX_VERSION >= 5.3 */
+ },
+ {
+ {
+ .vendor_id = OUI_GOOGLE,
+ .subcmd = WIFI_SUBCMD_SET_TX_POWER_LIMITS
+ },
+ .flags = WIPHY_VENDOR_CMD_NEED_WDEV | WIPHY_VENDOR_CMD_NEED_NETDEV,
+ .doit = wl_cfgvendor_set_tx_power_policy_handler,
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(5, 3, 0))
+ .policy = wifi_tx_power_limits_attr_policy,
+ .maxattr = TX_POWER_ATTRIBUTE_MAX
+#endif /* LINUX_VERSION >= 5.3 */
+ },
};
@@ -12814,6 +13451,7 @@
{ OUI_GOOGLE, BRCM_VENDOR_EVENT_TPUT_DUMP},
{ OUI_GOOGLE, GOOGLE_NAN_EVENT_MATCH_EXPIRY},
{ OUI_BRCM, BRCM_VENDOR_EVENT_RCC_FREQ_INFO},
+ { OUI_BRCM, BRCM_VENDOR_EVENT_CONNECTIVITY_LOG},
};
#if (LINUX_VERSION_CODE >= KERNEL_VERSION(5, 3, 0))
@@ -13121,6 +13759,7 @@
return;
}
#endif /* WL_CFGVENDOR_SEND_HANG_EVENT */
+
#ifdef WL_CFGVENDOR_SEND_ALERT_EVENT
void
wl_cfgvendor_send_alert_event(struct net_device *dev, uint32 reason)
@@ -13158,3 +13797,218 @@
return;
}
#endif /* WL_CFGVENDOR_SEND_ALERT_EVENT */
+
+#ifdef WL_CFGVENDOR_CUST_ADVLOG
+void
+wl_cfgvendor_custom_advlog_roam_log(void *plog, uint32 armcycle)
+{
+ prsv_periodic_log_hdr_t *hdr = (prsv_periodic_log_hdr_t *)plog;
+ const pr_advlog_tbl_t *cur_advlog_elem = &advlog_print_tbl[0];
+
+ if (hdr->version < ROAM_LOG_VER_3) {
+ WL_ERR(("%s: Version mis-match(%d)\n", __FUNCTION__, hdr->version));
+ return;
+ }
+
+ while (cur_advlog_elem && cur_advlog_elem->advlog_func) {
+ if (hdr->id == cur_advlog_elem->id) {
+ cur_advlog_elem->advlog_func(plog, armcycle);
+ break;
+ }
+ cur_advlog_elem++;
+ }
+}
+
+static void
+wl_cfgvendor_custom_advlog_scan_start(void *plog, uint32 armcycle)
+{
+ roam_log_trig_v2_t *log = (roam_log_trig_v2_t *)plog;
+ uint cust_roam_rsn = WLC_E_REASON_INITIAL_ASSOC;
+ int i;
+ bool rssi_thresh = FALSE;
+
+ if (log->result != BCME_OK) {
+ /* Not required logging if ROAM scan is failed. */
+ return;
+ }
+
+ for (i = 0; i < WL_CUST_ROAM_REASON_MAX; i++) {
+ if (dhd_covt_roam_rsn_list[i].roam_rsn == log->reason) {
+ cust_roam_rsn = dhd_covt_roam_rsn_list[i].cust_roam_rsn;
+ break;
+ }
+ }
+
+ if ((log->reason == WLC_E_REASON_LOW_RSSI) ||
+ (log->reason == WLC_E_REASON_LOW_RSSI_CU) ||
+ (log->reason == WLC_E_REASON_INACTIVITY) ||
+ (log->reason == WLC_E_REASON_ROAM_SCAN_TIMEOUT)) {
+ rssi_thresh = TRUE;
+ }
+ SUPP_ADVLOG(("[ROAM] SCAN_START reason=%d rssi=%d cu=%d full_scan=%d "
+ "rssi_thresh=%d [%d]\n",
+ cust_roam_rsn, log->rssi, log->current_cu, log->full_scan,
+ (rssi_thresh ? log->low_rssi.rssi_threshold : (0)), armcycle));
+}
+
+static int
+wl_cfgvendor_custom_advlog_get_rcc(chanspec_t *chanspecs)
+{
+ struct bcm_cfg80211 *cfg;
+ struct net_device *ndev;
+ int rcc_chan_cnt = 0;
+ wlc_ssid_t *ssid = NULL;
+
+ cfg = wl_cfg80211_get_bcmcfg();
+ ndev = bcmcfg_to_prmry_ndev(cfg);
+
+ /* Get Current SSID */
+ ssid = (struct wlc_ssid *)wl_read_prof(cfg, ndev, WL_PROF_SSID);
+ if (!ssid) {
+ WL_ERR(("No SSID found in the saved profile\n"));
+ goto exit;
+ }
+
+ rcc_chan_cnt = get_roam_channel_list(cfg, 0, chanspecs, MAX_ROAM_CHANNEL,
+ ssid, ioctl_version);
+
+exit:
+ return rcc_chan_cnt;
+}
+
+#define CH_LIST_LEN (SUPP_LOG_LEN / 2)
+static void
+wl_cfgvendor_custom_advlog_scan_cmpl(void *plog, uint32 armcycle)
+{
+ int i;
+ roam_log_scan_cmplt_v2_t *log = (roam_log_scan_cmplt_v2_t *)plog;
+ int freq;
+#ifdef ESCAN_CHANNEL_CACHE
+ chanspec_t chanspecs[MAX_ROAM_CHANNEL] = {0};
+ uint ch_cnt = 0;
+ char ch_list[CH_LIST_LEN] = {'\0'};
+ uint buf_pos = 0;
+
+ ch_cnt = wl_cfgvendor_custom_advlog_get_rcc(chanspecs);
+
+ bzero(ch_list, CH_LIST_LEN);
+ for (i = 0; i < ch_cnt; i++) {
+ freq = wl_channel_to_frequency(wf_chspec_ctlchan(chanspecs[i]),
+ CHSPEC_BAND(chanspecs[i]));
+ if (CH_LIST_LEN < buf_pos) {
+ break;
+ }
+ buf_pos += snprintf(&ch_list[buf_pos], CH_LIST_LEN - buf_pos,
+ "%d ", freq);
+ }
+
+ SUPP_ADVLOG(("[ROAM] SCAN_DONE ap_count=%d freq[%d]=%s [%d]\n",
+ log->scan_count, ch_cnt, ch_list, armcycle));
+#else
+ SUPP_ADVLOG(("[ROAM] SCAN_DONE ap_count=%d freq[%d] [%d]\n",
+ log->scan_count, log->chan_num, armcycle));
+#endif /* ESCAN_CHANNEL_CACHE */
+
+ freq = wl_channel_to_frequency(wf_chspec_ctlchan(log->cur_info.chanspec),
+ CHSPEC_BAND(log->cur_info.chanspec));
+ /* do not print to the kernel, only for framework (MACDBG_FULL) */
+ SUPP_ADVLOG(("[ROAM] SCORE_CUR_AP bssid=" MACDBG_FULL " freq=%d rssi=%d cu=%d "
+ "score=%d.%02d\n",
+ MAC2STRDBG_FULL((uint8 *)&log->cur_info.addr),
+ freq, log->cur_info.rssi,
+ log->cur_info.cu_avail ?
+ (log->cur_info.cu * 100 / WL_MAX_CHANNEL_USAGE) : WL_CU_NOT_AVAIL,
+ log->cur_info.score / 100, log->cur_info.score % 100));
+
+ for (i = 0; i < log->scan_list_size; i++) {
+ freq = wl_channel_to_frequency(wf_chspec_ctlchan(log->scan_list[i].chanspec),
+ CHSPEC_BAND(log->scan_list[i].chanspec));
+ /* do not print to the kernel, only for framework (MACDBG_FULL) */
+ SUPP_ADVLOG(("[ROAM] SCORE_CANDI[%d], bssid=" MACDBG_FULL " freq=%d "
+ "rssi=%d cu=%d score=%d.%02d tp=%dkbps\n",
+ i, MAC2STRDBG_FULL((uint8 *)&log->scan_list[i].addr), freq,
+ log->scan_list[i].rssi,
+ log->scan_list[i].cu_avail ?
+ (log->scan_list[i].cu * 100 / WL_MAX_CHANNEL_USAGE) : WL_CU_NOT_AVAIL,
+ log->scan_list[i].score / 100, log->scan_list[i].score % 100,
+ log->scan_list[i].estm_tput != ROAM_LOG_INVALID_TPUT?
+ log->scan_list[i].estm_tput:0));
+ }
+}
+
+static void
+wl_cfgvendor_custom_advlog_roam_cmpl(void *plog, uint32 armcycle)
+{
+ roam_log_cmplt_v1_t *log = (roam_log_cmplt_v1_t *)plog;
+
+ if (log->status == WLC_E_STATUS_ABORT) {
+ /* Roaming Abort(Cancel) */
+ SUPP_ADVLOG(("[ROAM] CANCELLED [%d]\n", armcycle));
+ } else if (log->status == WLC_E_STATUS_NO_NETWORKS || log->status == WLC_E_STATUS_TIMEOUT) {
+ /* Roaming No Networks */
+ /* do not print to the kernel, only for framework (MACDBG_FULL) */
+ SUPP_ADVLOG(("[ROAM] RESULT NO_ROAM bssid=" MACDBG_FULL " [%d]\n",
+ MAC2STRDBG_FULL((uint8 *)&log->addr), armcycle));
+ } else {
+ /* do not print to the kernel, only for framework (MACDBG_FULL) */
+ SUPP_ADVLOG(("[ROAM] RESULT ROAM bssid=" MACDBG_FULL " [%d status=%d]\n",
+ MAC2STRDBG_FULL((uint8 *)&log->addr), armcycle, log->status));
+ }
+}
+
+static void
+wl_cfgvendor_custom_advlog_btm_req(void *plog, uint32 armcycle)
+{
+ roam_log_btm_req_v4_t *log = (roam_log_btm_req_v4_t *)plog;
+ int i;
+
+ SUPP_ADVLOG(("[BTM] REQ token=%d mode=%d disassoc=%d validity=%d "
+ "candidate_list_cnt=%d [%d]\n",
+ log->token, log->req_mode, log->disassoc_dur, log->validity_dur,
+ log->nbrlist_size, armcycle));
+ if (log->nbrlist_size) {
+ int max_idx = MIN(log->nbrlist_size, ROAM_NBR_RPT_LIST_SIZE);
+ for (i = 0; i < max_idx; i++) {
+ /* do not print to the kernel, only for framework (MACDBG_FULL) */
+ SUPP_ADVLOG(("[BTM] REQ_CANDI[%d] bssid=" MACDBG_FULL " preference=%d\n",
+ i, MAC2STRDBG_FULL((uint8 *)&log->nbr_list[i].bssid),
+ log->nbr_list[i].preference));
+ }
+ }
+}
+
+static void
+wl_cfgvendor_custom_advlog_btm_resp(void *plog, uint32 armcycle)
+{
+ roam_log_btm_resp_v4_t *log = (roam_log_btm_resp_v4_t *)plog;
+
+ /* do not print to the kernel, only for framework (MACDBG_FULL) */
+ SUPP_ADVLOG(("[BTM] RESP token=%d status=%d delay=%d target=" MACDBG_FULL " [%d]\n",
+ log->token, log->status, log->term_delay,
+ MAC2STRDBG_FULL((uint8 *)&log->target_addr), armcycle));
+}
+
+static void
+wl_cfgvendor_custom_advlog_btm_wtc(void *plog, uint32 armcycle)
+{
+ roam_log_wtc_btmrep_v3_t *log = (roam_log_wtc_btmrep_v3_t *)plog;
+
+ if (log->wtc_type == WTC_BTMREQ) {
+ SUPP_ADVLOG(("[BTM] WTC reason=%d sub_code=%d duration=%d [%d]\n",
+ log->wtcreq.rsn_code, log->wtcreq.subcode, log->wtcreq.duration,
+ armcycle));
+ } else if (log->wtc_type == WTC_BTMRESP) {
+ SUPP_ADVLOG(("[BTM] WTC reason_code=%d [%d]\n",
+ log->wtcresp.rsn_code, armcycle));
+ }
+}
+
+static void
+wl_cfgvendor_custom_advlog_btm_query(void *plog, uint32 armcycle)
+{
+ roam_log_btm_query_v3_t *log = (roam_log_btm_query_v3_t *)plog;
+
+ SUPP_ADVLOG(("[BTM] QUERY token=%d reason=%d [%d]\n",
+ log->token, log->reason, armcycle));
+}
+#endif /* WL_CFGVENDOR_CUST_ADVLOG */
diff --git a/wl_cfgvendor.h b/wl_cfgvendor.h
index fbb4590..e365ce8 100644
--- a/wl_cfgvendor.h
+++ b/wl_cfgvendor.h
@@ -1,7 +1,7 @@
/*
* Linux cfg80211 Vendor Extension Code
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -45,7 +45,8 @@
BRCM_ATTR_DRIVER_FEATURE_FLAGS = 2,
BRCM_ATTR_DRIVER_RAND_MAC = 3,
BRCM_ATTR_SAE_PWE = 4,
- BRCM_ATTR_DRIVER_MAX = 5
+ BRCM_ATTR_TD_POLICY = 5,
+ BRCM_ATTR_DRIVER_MAX = 6
};
enum brcm_wlan_vendor_features {
@@ -261,6 +262,7 @@
DEBUG_SET_HAL_STOP,
DEBUG_SET_HAL_PID,
DEBUG_SET_TPUT_DEBUG_DUMP_CMD,
+ DEBUG_GET_BUF_RING_MAP,
WIFI_OFFLOAD_SUBCMD_START_MKEEP_ALIVE = ANDROID_NL80211_SUBCMD_WIFI_OFFLOAD_RANGE_START,
WIFI_OFFLOAD_SUBCMD_STOP_MKEEP_ALIVE,
@@ -297,6 +299,8 @@
WIFI_SUBCMD_OTA_UPDATE,
WIFI_SUBCMD_USABLE_CHAN = ANDROID_NL80211_SUBCMD_USABLE_CHAN_RANGE_START,
WIFI_SUBCMD_TRIGGER_SSR = ANDROID_NL80211_SUBCMD_INIT_DEINIT_RANGE_START,
+ WIFI_SUBCMD_GET_RADIO_COMBO_MATRIX,
+ WIFI_SUBCMD_SET_TX_POWER_LIMITS,
/* Add more sub commands here */
VENDOR_SUBCMD_MAX
};
@@ -500,6 +504,8 @@
DEBUG_ATTRIBUTE_PKT_FATE_NUM = 17,
DEBUG_ATTRIBUTE_PKT_FATE_DATA = 18,
DEBUG_ATTRIBUTE_HANG_REASON = 19,
+ DEBUG_ATTRIBUTE_BUF_RING_NUM = 20,
+ DEBUG_ATTRIBUTE_BUF_RING_MAP = 21,
/* Add new attributes just above this */
DEBUG_ATTRIBUTE_MAX
};
@@ -591,6 +597,31 @@
DUMP_BUF_ATTR_MAX
} EWP_DUMP_CMD_ATTRIBUTE;
+#ifdef DHD_HAL_RING_DUMP
+typedef struct dhd_buf_ring_map_entry {
+ uint32 type;
+ uint32 ring_id;
+ char ring_name[DBGRING_NAME_MAX];
+} dhd_buf_ring_map_entry_t;
+
+static dhd_buf_ring_map_entry_t dhd_buf_ring_map[] = {
+ {DUMP_BUF_ATTR_TIMESTAMP, DEBUG_DUMP_RING1_ID, DEBUG_DUMP_RING1_NAME},
+ {DUMP_BUF_ATTR_ECNTRS, DEBUG_DUMP_RING2_ID, DEBUG_DUMP_RING2_NAME},
+ {DUMP_BUF_ATTR_STATUS_LOG, DEBUG_DUMP_RING1_ID, DEBUG_DUMP_RING1_NAME},
+ {DUMP_BUF_ATTR_RTT_LOG, DEBUG_DUMP_RING2_ID, DEBUG_DUMP_RING2_NAME},
+ {DUMP_BUF_ATTR_PKTID_MAP_LOG, DEBUG_DUMP_RING2_ID, DEBUG_DUMP_RING2_NAME},
+ {DUMP_BUF_ATTR_PKTID_UNMAP_LOG, DEBUG_DUMP_RING2_ID, DEBUG_DUMP_RING2_NAME},
+ {DUMP_BUF_ATTR_DHD_DUMP, DEBUG_DUMP_RING1_ID, DEBUG_DUMP_RING1_NAME},
+ {DUMP_BUF_ATTR_EXT_TRAP, DEBUG_DUMP_RING1_ID, DEBUG_DUMP_RING1_NAME},
+ {DUMP_BUF_ATTR_HEALTH_CHK, DEBUG_DUMP_RING1_ID, DEBUG_DUMP_RING1_NAME},
+ {DUMP_BUF_ATTR_COOKIE, DEBUG_DUMP_RING1_ID, DEBUG_DUMP_RING1_NAME},
+ {DUMP_BUF_ATTR_FLOWRING_DUMP, DEBUG_DUMP_RING1_ID, DEBUG_DUMP_RING1_NAME},
+#ifdef DHD_HAL_RING_DUMP_MEMDUMP
+ {DUMP_BUF_ATTR_MEMDUMP, MEM_DUMP_RING_ID, MEM_DUMP_RING_NAME},
+#endif /* DHD_HAL_RING_DUMP_MEMDUMP */
+};
+#endif /* DHD_HAL_RING_DUMP */
+
enum mkeep_alive_attributes {
MKEEP_ALIVE_ATTRIBUTE_INVALID = 0,
MKEEP_ALIVE_ATTRIBUTE_ID = 1,
@@ -701,6 +732,7 @@
BRCM_VENDOR_EVENT_TPUT_DUMP = 44,
GOOGLE_NAN_EVENT_MATCH_EXPIRY = 45,
BRCM_VENDOR_EVENT_RCC_FREQ_INFO = 46,
+ BRCM_VENDOR_EVENT_CONNECTIVITY_LOG = 47,
BRCM_VENDOR_EVENT_LAST
} wl_vendor_event_t;
@@ -1019,6 +1051,72 @@
} andr_twt_sub_event;
#endif /* WL_TWT_HAL_IF */
+typedef enum {
+ ANDR_LSTAT_ATTRIBUTE_INVALID = 0,
+ ANDR_LSTAT_ATTRIBUTE_NUM_RADIO = 1,
+ ANDR_LSTAT_ATTRIBUTE_STATS_INFO = 2,
+ ANDR_LSTAT_ATTRIBUTE_STATS_MAX = 3
+} LINK_STAT_ATTRIBUTE;
+
+typedef enum {
+ /* WLAN MAC Operates in 2.4 GHz Band */
+ WLAN_MAC_2_4_BAND = 1 << 0,
+ /* WLAN MAC Operates in 5 GHz Band */
+ WLAN_MAC_5_0_BAND = 1 << 1,
+ /* WLAN MAC Operates in 6 GHz Band */
+ WLAN_MAC_6_0_BAND = 1 << 2,
+ /* WLAN MAC Operates in 60 GHz Band */
+ WLAN_MAC_60_0_BAND = 1 << 3
+} wlan_mac_band;
+
+typedef enum {
+ TX_POWER_CAP_ATTRIBUTE_INVALID = 0,
+ TX_POWER_CAP_ENABLE_ATTRIBUTE = 1,
+ /* Add more attributes here */
+ TX_POWER_ATTRIBUTE_MAX
+} wifi_tx_power_limits;
+
+typedef enum {
+ ANDR_WIFI_ATTRIBUTE_RADIO_COMBO_INVALID = 0,
+ ANDR_WIFI_ATTRIBUTE_RADIO_COMBO_MATRIX = 1,
+ ANDR_WIFI_ATTRIBUTE_RADIO_COMBO_MAX
+} wifi_radio_combo_attributes;
+
+/* Antenna configuration */
+typedef enum {
+ WIFI_ANTENNA_INVALID = 0,
+ WIFI_ANTENNA_1X1 = 1,
+ WIFI_ANTENNA_2X2 = 2,
+ WIFI_ANTENNA_3X3 = 3,
+ WIFI_ANTENNA_4X4 = 4
+} wifi_antenna_configuration;
+
+/* Wifi Radio configuration */
+typedef struct {
+ /* Operating band */
+ wlan_mac_band band;
+ /* Antenna configuration */
+ wifi_antenna_configuration antenna_cfg;
+} wifi_radio_configuration;
+
+/* WiFi Radio Combination */
+typedef struct {
+ uint32 num_radio_combinations;
+ wifi_radio_configuration radio_configurations[];
+} wifi_radio_combination;
+
+/* WiFi Radio combinations matrix */
+typedef struct {
+ uint32 num_combinations;
+ /* Each row represents possible radio combinations */
+ wifi_radio_combination radio_combinations[];
+} wifi_radio_combination_matrix;
+
+#define MAX_RADIO_COMBO 5u
+#define MAX_RADIO_CONFIGS 2u
+#define MAX_RADIO_MATRIX_SIZE (MAX_RADIO_COMBO * (sizeof(wifi_radio_combination) +\
+ (MAX_RADIO_CONFIGS * sizeof(wifi_radio_configuration))))
+
/* Capture the BRCM_VENDOR_SUBCMD_PRIV_STRINGS* here */
#define BRCM_VENDOR_SCMD_CAPA "cap"
#define MEMDUMP_PATH_LEN 128
@@ -1053,6 +1151,15 @@
#define SUPP_EVT_LOG(evt_name, fmt, ...) \
wl_cfgvendor_notify_supp_event_str(evt_name, fmt, ##__VA_ARGS__);
#define SUPP_EVENT(args) SUPP_EVT_LOG args
+
+#ifdef WL_CFGVENDOR_CUST_ADVLOG
+extern int wl_cfgvendor_send_supp_advlog(const char *fmt, ...);
+#define PRINT_SUPP_ADVLOG(fmt, ...) \
+ wl_cfgvendor_send_supp_advlog(fmt, ##__VA_ARGS__);
+#define SUPP_ADVLOG(args) PRINT_SUPP_ADVLOG args;
+#else
+#define SUPP_ADVLOG(x)
+#endif /* WL_CFGVENDOR_CUST_ADVLOG */
#else
#define SUPP_LOG(x)
#define SUPP_EVENT(x)
@@ -1146,4 +1253,8 @@
#endif /* TPUT_DEBUG_DUMP */
extern int wl_cfgvendor_multista_set_primary_connection(struct wiphy *wiphy,
struct wireless_dev *wdev, const void *data, int len);
+
+#ifdef WL_CFGVENDOR_CUST_ADVLOG
+void wl_cfgvendor_custom_advlog_roam_log(void *plog, uint32 armcycle);
+#endif /* WL_CFGVENDOR_CUST_ADVLOG */
#endif /* _wl_cfgvendor_h_ */
diff --git a/wl_cfgvif.c b/wl_cfgvif.c
old mode 100755
new mode 100644
index 823488c..5169bf7
--- a/wl_cfgvif.c
+++ b/wl_cfgvif.c
@@ -1,7 +1,7 @@
/*
* Wifi Virtual Interface implementaion
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -115,7 +115,6 @@
#define DNGL_FUNC(func, parameters)
#else
#define DNGL_FUNC(func, parameters) func parameters
-#define COEX_DHCP
#endif /* defined(BCMDONGLEHOST) */
@@ -383,6 +382,7 @@
return ret;
}
#endif /* WL_IFACE_MGMT */
+
#ifdef WL_NANP2P
int
wl_cfg80211_set_iface_conc_disc(struct net_device *ndev,
@@ -418,6 +418,7 @@
return cfg->conc_disc;
}
#endif /* WL_NANP2P */
+
#ifdef WL_IFACE_MGMT
int
wl_cfg80211_set_iface_policy(struct net_device *ndev,
@@ -644,6 +645,7 @@
* as for AP and associated ifaces, both are same
*/
}
+ /* falls through */
case WL_IF_POLICY_DEFAULT: {
if (sec_wl_if_type == WL_IF_TYPE_AP) {
WL_INFORM_MEM(("AP is active, cant support new iface\n"));
@@ -656,11 +658,11 @@
* Fall through
*/
} else {
- /* clear associated group interfaces */
- WL_INFORM_MEM(("remove P2P group,"
- " to support new iface\n"));
- ret = wl_cfg80211_delete_iface(cfg,
- sec_wl_if_type);
+ /* clear associated group interfaces */
+ WL_INFORM_MEM(("remove P2P group,"
+ " to support new iface\n"));
+ ret = wl_cfg80211_delete_iface(cfg,
+ sec_wl_if_type);
}
} else if (sec_wl_if_type == WL_IF_TYPE_NAN) {
ret = wl_cfg80211_delete_iface(cfg, sec_wl_if_type);
@@ -1515,6 +1517,16 @@
bw = WL_CHANSPEC_BW_20;
}
+#if defined(LIMIT_AP_BW)
+ if (band == WL_CHANSPEC_BAND_6G) {
+ struct bcm_cfg80211 *cfg = wl_get_cfg(ndev);
+ if (cfg->ap_bw_chspec != INVCHANSPEC &&
+ (wf_bw_chspec_to_mhz(cfg->ap_bw_chspec) < wf_bw_chspec_to_mhz(bw))) {
+ bw = cfg->ap_bw_chspec;
+ }
+ }
+#endif /* LIMIT_AP_BW */
+
*bandwidth = bw;
return err;
@@ -1601,6 +1613,14 @@
dev->ifindex, chspec, channel_type,
CHSPEC_CHANNEL(chspec), chan->center_freq));
+#ifdef WL_DUAL_STA
+ /* In case of Dual STA if both STAs are connected, do not allow softAP bringup */
+ if (wl_cfgvif_get_iftype_count(cfg, WL_IF_TYPE_STA) >= 2) {
+ WL_ERR(("Dual STA case, softAP bringup not supported\n"));
+ return -ENOTSUPP;
+ }
+#endif /* WL_DUAL_STA */
+
if (IS_P2P_GO(dev->ieee80211_ptr) && (CHSPEC_IS6G(chspec))) {
WL_ERR(("P2P GO not allowed on 6G\n"));
return -ENOTSUPP;
@@ -1613,6 +1633,13 @@
}
#endif /* WL_SOFTAP_6G */
+#ifdef WL_UNII4_CHAN
+ if (CHSPEC_IS5G(chspec) &&
+ IS_UNII4_CHANNEL(wf_chspec_primary20_chan(chspec))) {
+ WL_ERR(("AP not allowed on UNII-4 chanspec 0x%x\n", chspec));
+ return -ENOTSUPP;
+ }
+#endif /* WL_UNII4_CHAN */
/* Check whether AP is already operational */
wl_get_ap_chanspecs(cfg, &ap_oper_data);
if (ap_oper_data.count >= MAX_AP_IFACES) {
@@ -1622,6 +1649,7 @@
}
if (ap_oper_data.count == 1) {
+ chanspec_t sta_chspec;
chanspec_t ch = ap_oper_data.iface[0].chspec;
u16 ap_band, incoming_band;
@@ -1635,6 +1663,22 @@
WL_ERR(("DUAL AP not allowed on same band\n"));
return -ENOTSUPP;
}
+ sta_chspec = wl_cfg80211_get_sta_chanspec(cfg);
+ if (sta_chspec && wf_chspec_valid(sta_chspec)) {
+ /* 5G cant be upgraded to 6G since dual band clients
+ * wont be able able to scan 6G
+ */
+ if (CHSPEC_IS6G(sta_chspec) && (incoming_band == WLC_BAND_5G)) {
+ WL_ERR(("DUAL AP not allowed for"
+ " 5G band as sta in 6G chspec 0x%x\n",
+ chspec));
+ return -ENOTSUPP;
+ }
+ if (incoming_band == CHSPEC_TO_WLC_BAND(sta_chspec)) {
+ /* use sta chanspec for SCC */
+ chspec = sta_chspec;
+ }
+ }
}
#ifdef NOT_YET
@@ -1657,13 +1701,13 @@
/* Some customer platform used limited number of channels
* for SoftAP interface on STA/SoftAP concurrent mode.
* - 2.4GHz Channel: CH1 - CH13
- * - 5GHz Channel: CH149 (it depends on the country code)
+ * - 5GHz Channel: CH 149, 153, 157, 161 (it depends on the country code)
* If the Android framework sent invaild channel configuration
* to DHD, driver should change the channel which is suitable for
* STA/SoftAP concurrent mode.
* - Set operating channel to CH1 (default 2.4GHz channel for
* restricted APSTA mode) if STA interface was associated to
- * 5GHz APs except for CH149.
+ * 5GHz APs except for CH149, 153, 157, 161.
* - Otherwise, set the channel to the same channel as existing AP.
*/
if (wl_get_mode_by_netdev(cfg, dev) == WL_MODE_AP &&
@@ -1675,11 +1719,13 @@
/* Do not try SCC in 5GHz if channel is not CH149 */
chspec = (
#ifdef WL_6G_BAND
- CHSPEC_IS6G(*sta_chanspec) ||
+ (CHSPEC_IS6G(*sta_chanspec) &&
+ (!CHSPEC_IS_6G_PSC(*sta_chanspec) ||
+ (wf_chspec_primary20_chspec(*sta_chanspec) !=
+ wf_chspec_primary20_chspec(chspec)))) ||
#endif /* WL_6G_BAND */
(CHSPEC_IS5G(*sta_chanspec) &&
- wf_chspec_primary20_chan(*sta_chanspec) !=
- DEFAULT_5G_SOFTAP_CHANNEL)) ?
+ !IS_5G_APCS_CHANNEL(wf_chspec_primary20_chan(*sta_chanspec)))) ?
DEFAULT_2G_SOFTAP_CHANSPEC: *sta_chanspec;
WL_ERR(("target chanspec will be changed to %x\n", chspec));
if (CHSPEC_IS2G(chspec)) {
@@ -1708,8 +1754,17 @@
if (CHSPEC_IS5G(chspec) && (bw == WL_CHANSPEC_BW_160)) {
bw = WL_CHANSPEC_BW_80;
}
+
+#ifdef WL_UNII4_CHAN
+ /* Handle 165/20 channel as special case to not upgrade the bw */
+ if (IS_5G_UNII4_165_CHANNEL(chspec)) {
+ bw = WL_CHANSPEC_BW_20;
+ }
+#endif /* WL_UNII4_CHAN */
+
#ifdef WL_CELLULAR_CHAN_AVOID
if (!CHSPEC_IS6G(chspec)) {
+ wl_cellavoid_sanity_check_chan_info_list(cfg->cellavoid_info);
wl_cellavoid_sync_lock(cfg);
cur_chspec = wl_cellavoid_find_widechspec_fromchspec(cfg->cellavoid_info, chspec);
if (cur_chspec == INVCHANSPEC) {
@@ -1766,13 +1821,17 @@
#ifdef DISABLE_WL_FRAMEBURST_SOFTAP
else {
/* Disable Frameburst only for stand-alone 2GHz SoftAP */
- if (wl_get_mode_by_netdev(cfg, dev) == WL_MODE_AP &&
- DHD_OPMODE_SUPPORTED(cfg->pub, DHD_FLAG_HOSTAP_MODE) &&
- (CHSPEC_IS2G(chspec)) &&
- !wl_is_sta_connected(cfg)) {
- WL_DBG(("Disabling frameburst on "
- "stand-alone 2GHz SoftAP\n"));
- wl_cfg80211_set_frameburst(cfg, FALSE);
+ if ((wl_get_mode_by_netdev(cfg, dev) == WL_MODE_AP) &&
+ DHD_OPMODE_SUPPORTED(cfg->pub, DHD_FLAG_HOSTAP_MODE)) {
+ if (CHSPEC_IS2G(chspec) && !wl_is_sta_connected(cfg)) {
+ WL_DBG(("Disabling frameburst on "
+ "stand-alone 2GHz SoftAP\n"));
+ wl_cfg80211_set_frameburst(cfg, FALSE);
+ } else if (!CHSPEC_IS2G(chspec) &&
+ cfg->frameburst_disabled) {
+ WL_INFORM(("Enable back frameburst\n"));
+ wl_cfg80211_set_frameburst(cfg, TRUE);
+ }
}
}
#endif /* DISABLE_WL_FRAMEBURST_SOFTAP */
@@ -1896,7 +1955,7 @@
err = BCME_NOMEM;
goto exit;
}
- iov_buf->version = WL_FILS_IOV_VERSION;
+ iov_buf->version = WL_FILS_IOV_VERSION_1_1;
iov_buf->id = WL_FILS_CMD_ADD_IND_IE;
iov_buf->len = sizeof(bcm_xtlv_t) + filsindie->len - 1;
pxtlv = (bcm_xtlv_t*)&iov_buf->data[0];
@@ -2345,38 +2404,8 @@
return 0;
}
-#if defined(SUPPORT_SOFTAP_WPAWPA2_MIXED)
-static u32 wl_get_cipher_type(uint8 type)
-{
- u32 ret = 0;
- switch (type) {
- case WPA_CIPHER_NONE:
- ret = 0;
- break;
- case WPA_CIPHER_WEP_40:
- case WPA_CIPHER_WEP_104:
- ret = WEP_ENABLED;
- break;
- case WPA_CIPHER_TKIP:
- ret = TKIP_ENABLED;
- break;
- case WPA_CIPHER_AES_CCM:
- ret = AES_ENABLED;
- break;
-
-#ifdef BCMWAPI_WPI
- case WAPI_CIPHER_SMS4:
- ret = SMS4_ENABLED;
- break;
-#endif
-
- default:
- WL_ERR(("No Security Info\n"));
- }
- return ret;
-}
-
-static u32 wl_get_suite_auth_key_mgmt_type(uint8 type, const wpa_suite_mcast_t *mcast)
+static u32
+wl_get_suite_auth_key_mgmt_type(uint8 type, const wpa_suite_mcast_t *mcast)
{
u32 ret = 0;
u32 is_wpa2 = 0;
@@ -2426,6 +2455,82 @@
return ret;
}
+s32
+wl_update_akm_from_assoc_ie(struct bcm_cfg80211 *cfg, struct net_device *ndev,
+ u8 *assoc_ies, u32 assoc_ie_len)
+{
+ const wpa_suite_mcast_t *mcast;
+ const wpa_suite_ucast_t *ucast;
+ const wpa_suite_auth_key_mgmt_t *mgmt;
+ struct parsed_ies parsed_assoc_ies;
+ const bcm_tlv_t *wpa2ie;
+ u16 suite_count;
+ struct wl_security *sec = wl_read_prof(cfg, ndev, WL_PROF_SEC);
+
+ WL_DBG(("Enter \n"));
+
+ /* Parse assoc IEs */
+ if (wl_cfg80211_parse_ies(assoc_ies, assoc_ie_len, &parsed_assoc_ies) < 0) {
+ WL_ERR(("Get Assoc IEs failed\n"));
+ return 0;
+ }
+
+ if (parsed_assoc_ies.wpa2_ie == NULL) {
+ WL_ERR(("wpa2_ie\n"));
+ return -EINVAL;
+ } else {
+ wpa2ie = parsed_assoc_ies.wpa2_ie;
+ }
+
+ /* Get the mcast cipher */
+ mcast = (const wpa_suite_mcast_t *)&wpa2ie->data[WPA2_VERSION_LEN];
+
+ /* Get the unicast cipher */
+ ucast = (const wpa_suite_ucast_t *)&mcast[1];
+ suite_count = ltoh16_ua(&ucast->count);
+
+ /* check and update the AKM and FW auth in DHD security profile */
+ mgmt = (const wpa_suite_auth_key_mgmt_t *)&ucast->list[suite_count];
+ sec->wpa_auth = ntoh32_ua(&mgmt->list[0]);
+ sec->fw_wpa_auth = wl_get_suite_auth_key_mgmt_type(mgmt->list[0].type, mcast);
+
+ WL_INFORM(("AKM updated from assoc ie in DHD Security profile = 0x%X 0x%X\n",
+ sec->wpa_auth, sec->fw_wpa_auth));
+
+ return 0;
+}
+
+#if defined(SUPPORT_SOFTAP_WPAWPA2_MIXED)
+static u32 wl_get_cipher_type(uint8 type)
+{
+ u32 ret = 0;
+ switch (type) {
+ case WPA_CIPHER_NONE:
+ ret = 0;
+ break;
+ case WPA_CIPHER_WEP_40:
+ case WPA_CIPHER_WEP_104:
+ ret = WEP_ENABLED;
+ break;
+ case WPA_CIPHER_TKIP:
+ ret = TKIP_ENABLED;
+ break;
+ case WPA_CIPHER_AES_CCM:
+ ret = AES_ENABLED;
+ break;
+
+#ifdef BCMWAPI_WPI
+ case WAPI_CIPHER_SMS4:
+ ret = SMS4_ENABLED;
+ break;
+#endif
+
+ default:
+ WL_ERR(("No Security Info\n"));
+ }
+ return ret;
+}
+
static s32
wl_validate_wpaie_wpa2ie(struct net_device *dev, const wpa_ie_fixed_t *wpaie,
const bcm_tlv_t *wpa2ie, s32 bssidx)
@@ -3186,6 +3291,15 @@
}
#endif /* MFP */
+ /* sync up host macaddr */
+ err = wldev_iovar_setbuf(dev, "cur_etheraddr",
+ dev->dev_addr, ETH_ALEN, cfg->ioctl_buf, WLC_IOCTL_SMLEN,
+ &cfg->ioctl_buf_sync);
+ if (err) {
+ WL_ERR(("sync macaddr for softap error\n"));
+ goto exit;
+ }
+
bzero(&join_params, sizeof(join_params));
/* join parameters starts with ssid */
join_params_size = sizeof(join_params.ssid);
@@ -3661,6 +3775,7 @@
WL_ERR(("set ap role failed!\n"));
return BCME_ERROR;
}
+
}
dev_role = NL80211_IFTYPE_AP;
#ifdef BCMDONGLEHOST
@@ -3851,6 +3966,8 @@
#ifdef BCMDONGLEHOST
dhd_pub_t *dhd = (dhd_pub_t *)(cfg->pub);
#endif /* BCMDONGLEHOST */
+ u8 null_mac[ETH_ALEN];
+
WL_DBG(("Enter \n"));
/* wl_cfg80211_start_ap() schedules cfg->ap_work
@@ -3859,7 +3976,6 @@
* immediately after wl_cfg80211_start_ap().
* In this case we should cancel the work.
*/
-
cancel_delayed_work_sync(&cfg->ap_work);
#if defined(BCMDONGLEHOST)
@@ -3875,6 +3991,17 @@
if (dev->ieee80211_ptr->iftype == NL80211_IFTYPE_AP) {
dev_role = NL80211_IFTYPE_AP;
WL_DBG(("stopping AP operation\n"));
+
+ /* Clear macaddress to prevent any macaddress conflict with interface
+ * like p2p discovery which can run as soon as softap is brought down
+ */
+ (void)memset_s(null_mac, sizeof(null_mac), 0, sizeof(null_mac));
+ err = wldev_iovar_setbuf(dev, "cur_etheraddr",
+ null_mac, ETH_ALEN, cfg->ioctl_buf, WLC_IOCTL_SMLEN,
+ &cfg->ioctl_buf_sync);
+ if (err) {
+ WL_ERR(("softap mac_addr set failed\n"));
+ }
} else if (dev->ieee80211_ptr->iftype == NL80211_IFTYPE_P2P_GO) {
dev_role = NL80211_IFTYPE_P2P_GO;
WL_DBG(("stopping P2P GO operation\n"));
@@ -3970,7 +4097,6 @@
}
#endif /* SUPPORT_AP_RADIO_PWRSAVE */
#ifdef WL_CELLULAR_CHAN_AVOID
- wl_cellavoid_clear_requested_freq_bands(dev, cfg->cellavoid_info);
wl_cellavoid_sync_lock(cfg);
wl_cellavoid_free_csa_info(cfg->cellavoid_info, dev);
wl_cellavoid_sync_unlock(cfg);
@@ -4007,6 +4133,7 @@
if (wl_cfgvif_get_iftype_count(cfg, WL_IF_TYPE_AP) == 0) {
dhd->op_mode &= ~DHD_FLAG_HOSTAP_MODE;
}
+
}
#endif /* BCMDONGLEHOST */
return err;
@@ -5600,7 +5727,7 @@
{
struct bcm_cfg80211 *cfg = wl_get_cfg(dev);
dhd_pub_t *dhdp;
- wl_rateset_args_t rs;
+ wl_rateset_args_v1_t rs;
int error = BCME_ERROR, i;
struct net_device *ndev = NULL;
@@ -5618,9 +5745,9 @@
return BCME_NOTAP;
}
- bzero(&rs, sizeof(wl_rateset_args_t));
+ bzero(&rs, sizeof(wl_rateset_args_v1_t));
error = wldev_iovar_getbuf(ndev, "rateset", NULL, 0,
- &rs, sizeof(wl_rateset_args_t), NULL);
+ &rs, sizeof(wl_rateset_args_v1_t), NULL);
if (error < 0) {
WL_ERR(("get rateset failed = %d\n", error));
return error;
@@ -5658,7 +5785,7 @@
{
struct bcm_cfg80211 *cfg = wl_get_cfg(dev);
dhd_pub_t *dhdp;
- wl_rateset_args_t rs;
+ wl_rateset_args_v1_t rs;
int error = BCME_ERROR;
int i, bytes_written = 0;
struct net_device *ndev = NULL;
@@ -5677,9 +5804,9 @@
return BCME_NOTAP;
}
- bzero(&rs, sizeof(wl_rateset_args_t));
+ bzero(&rs, sizeof(wl_rateset_args_v1_t));
error = wldev_iovar_getbuf(ndev, "rateset", NULL, 0,
- &rs, sizeof(wl_rateset_args_t), NULL);
+ &rs, sizeof(wl_rateset_args_v1_t), NULL);
if (error < 0) {
WL_ERR(("get rateset failed = %d\n", error));
return error;
@@ -6109,7 +6236,7 @@
if (chspec == cfg->ap_oper_channel) {
WL_ERR(("Channel %d is same as current operating channel,"
" so skip\n", CHSPEC_CHANNEL(chspec)));
- return BCME_OK;
+ return -EINVAL;
}
if (
@@ -6351,6 +6478,7 @@
fail:
return err;
}
+
int wl_get_softap_elna_bypass(struct net_device *dev, char *ifname, void *param)
{
struct bcm_cfg80211 *cfg = wl_get_cfg(dev);
@@ -6817,14 +6945,13 @@
wl_cfgvif_roam_config(struct bcm_cfg80211 *cfg, struct net_device *dev,
wl_roam_conf_t state)
{
-
- WL_DBG_MEM(("Enter. state:%d stas:%d\n", state, cfg->stas_associated));
-
if (!cfg || !dev) {
WL_ERR(("invalid args\n"));
return;
}
+ WL_DBG_MEM(("Enter. state:%d stas:%d\n", state, cfg->stas_associated));
+
if (!IS_STA_IFACE(dev->ieee80211_ptr)) {
WL_ERR(("non-sta iface. ignore.\n"));
return;
@@ -6838,8 +6965,9 @@
if (state == ROAM_CONF_ROAM_DISAB_REQ) {
cfg->disable_fw_roam = TRUE;
-
+#ifdef WL_DUAL_APSTA
wl_android_rcroam_turn_on(dev, FALSE);
+#endif /* WL_DUAL_APSTA */
/* roam off for incoming ndev interface */
wl_roam_off_config(dev, TRUE);
return;
@@ -6863,7 +6991,9 @@
/* ROAM enable */
wl_roam_off_config(dev, FALSE);
/* Single Interface. Enable back rcroam */
+#ifdef WL_DUAL_APSTA
wl_android_rcroam_turn_on(dev, TRUE);
+#endif /* WL_DUAL_APSTA */
return;
}
@@ -7002,3 +7132,180 @@
}
return count;
}
+
+#ifdef CUSTOM_SOFTAP_SET_ANT
+int
+wl_set_softap_antenna(struct net_device *dev, char *ifname, int set_chain)
+{
+ struct bcm_cfg80211 *cfg = wl_get_cfg(dev);
+ struct net_device *ifdev = NULL;
+ char iobuf[WLC_IOCTL_SMLEN];
+ int err = BCME_OK;
+ int iftype = 0;
+ s32 val = 1;
+
+ memset(iobuf, 0, WLC_IOCTL_SMLEN);
+
+ /* Check the interface type */
+ ifdev = wl_get_netdev_by_name(cfg, ifname);
+ if (ifdev == NULL) {
+ WL_ERR(("%s: Could not find net_device for ifname:%s\n",
+ __FUNCTION__, ifname));
+ err = BCME_BADARG;
+ goto fail;
+ }
+
+ iftype = ifdev->ieee80211_ptr->iftype;
+ if (iftype == NL80211_IFTYPE_AP) {
+ err = wldev_ioctl_set(dev, WLC_DOWN, &val, sizeof(s32));
+ if (err) {
+ WL_ERR(("WLC_DOWN error %d\n", err));
+ goto fail;
+ } else {
+ err = wldev_iovar_setint(ifdev, "txchain", set_chain);
+ if (unlikely(err)) {
+ WL_ERR(("%s: Failed to set txchain[%d], err=%d\n",
+ __FUNCTION__, set_chain, err));
+ }
+ err = wldev_iovar_setint(ifdev, "rxchain", set_chain);
+ if (unlikely(err)) {
+ WL_ERR(("%s: Failed to set rxchain[%d], err=%d\n",
+ __FUNCTION__, set_chain, err));
+ }
+ err = wldev_ioctl_set(dev, WLC_UP, &val, sizeof(s32));
+ if (err < 0) {
+ WL_ERR(("WLC_UP error %d\n", err));
+ }
+ }
+ } else {
+ WL_ERR(("%s: Chain set should control in SoftAP mode only\n",
+ __FUNCTION__));
+ err = BCME_BADARG;
+ }
+fail:
+ return err;
+}
+
+int
+wl_get_softap_antenna(struct net_device *dev, char *ifname, void *param)
+{
+ struct bcm_cfg80211 *cfg = wl_get_cfg(dev);
+ uint32 *cur_rxchain = (uint32*)param;
+ struct net_device *ifdev = NULL;
+ char iobuf[WLC_IOCTL_SMLEN];
+ int err = BCME_OK;
+ int iftype = 0;
+
+ memset(iobuf, 0, WLC_IOCTL_SMLEN);
+
+ /* Check the interface type */
+ ifdev = wl_get_netdev_by_name(cfg, ifname);
+ if (ifdev == NULL) {
+ WL_ERR(("%s: Could not find net_device for ifname:%s\n", __FUNCTION__, ifname));
+ err = BCME_BADARG;
+ goto fail;
+ }
+
+ iftype = ifdev->ieee80211_ptr->iftype;
+ if (iftype == NL80211_IFTYPE_AP) {
+ err = wldev_iovar_getint(ifdev, "rxchain", cur_rxchain);
+ if (unlikely(err)) {
+ WL_ERR(("%s: Failed to get rxchain, err=%d\n",
+ __FUNCTION__, err));
+ }
+ } else {
+ WL_ERR(("%s: rxchain should control in SoftAP mode only\n",
+ __FUNCTION__));
+ err = BCME_BADARG;
+ }
+fail:
+ return err;
+}
+#endif /* CUSTOM_SOFTAP_SET_ANT */
+
+#if defined(LIMIT_AP_BW)
+uint32
+wl_cfg80211_get_ap_bw_limit_bit(struct bcm_cfg80211 *cfg, uint32 band)
+{
+
+ if (band != WL_CHANSPEC_BAND_6G) {
+ WL_ERR(("AP BW LIMIT supportted for 6G band only requested = %d\n", band));
+ return 0;
+ }
+
+ return cfg->ap_bw_limit;
+}
+
+#ifdef WL_6G_320_SUPPORT
+#define BAND_PARAM(a) a, 0
+#else
+#define BAND_PARAM(a) a
+#endif /* WL_6G_320_SUPPORT */
+
+chanspec_t
+wl_cfg80211_get_ap_bw_limited_chspec(struct bcm_cfg80211 *cfg, uint32 band, chanspec_t candidate)
+{
+
+ chanspec_t updated_chspec;
+ if (band != WL_CHANSPEC_BAND_6G) {
+ WL_ERR(("AP BW LIMIT supported for 6G band only requested = %d\n", band));
+ return candidate;
+ }
+
+ if (!cfg->ap_bw_limit ||
+ (wf_bw_chspec_to_mhz(candidate) <= wf_bw_chspec_to_mhz(cfg->ap_bw_chspec))) {
+ /* LIMIT is not set or narrower bandwidth is required */
+ return candidate;
+ }
+ updated_chspec = wf_create_chspec_from_primary(
+ wf_chspec_primary20_chan(candidate),
+ cfg->ap_bw_chspec,
+ BAND_PARAM(WL_CHANSPEC_BAND_6G));
+
+ return updated_chspec;
+}
+
+/* configure BW limit for AP
+ * support 6G band only
+ */
+int
+wl_cfg80211_set_softap_bw(struct bcm_cfg80211 *cfg, uint32 band, uint32 limit)
+{
+ int i, found = FALSE, f_idx = 0;
+ uint32 support_bw[][2] = {
+ {WLC_BW_20MHZ_BIT, WL_CHANSPEC_BW_20},
+ {WLC_BW_40MHZ_BIT, WL_CHANSPEC_BW_40},
+ {WLC_BW_80MHZ_BIT, WL_CHANSPEC_BW_80},
+#if defined(CHSPEC_IS160)
+ {WLC_BW_160MHZ_BIT, WL_CHANSPEC_BW_160},
+#endif /* CHSPEC_IS160 */
+ };
+
+ if (band != WL_CHANSPEC_BAND_6G) {
+ WL_ERR(("AP BW LIMIT supportted for 6G band only requested = %d\n", band));
+ return FALSE;
+ }
+
+ for (i = 0; i < ARRAYSIZE(support_bw); i++) {
+ if (support_bw[i][0] == limit) {
+ found = TRUE;
+ f_idx = i;
+ break;
+ }
+ }
+
+ if (limit && !found) {
+ WL_ERR(("AP BW LIMIT not supported bandwidth :%d\n", limit));
+ return BCME_ERROR;
+ }
+
+ cfg->ap_bw_limit = limit;
+ if (found) {
+ cfg->ap_bw_chspec = support_bw[f_idx][1];
+ } else {
+ cfg->ap_bw_chspec = INVCHANSPEC;
+ }
+
+ return BCME_OK;
+}
+#endif /* LIMIT_AP_BW */
diff --git a/wl_cfgvif.h b/wl_cfgvif.h
index 917feaf..86ab7cc 100644
--- a/wl_cfgvif.h
+++ b/wl_cfgvif.h
@@ -1,7 +1,7 @@
/*
* Wifi Virtual Interface implementaion
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -134,6 +134,10 @@
int wl_set_softap_elna_bypass(struct net_device *dev, char *ifname, int enable);
int wl_get_softap_elna_bypass(struct net_device *dev, char *ifname, void *param);
#endif /* SUPPORT_SOFTAP_ELNA_BYPASS */
+#ifdef CUSTOM_SOFTAP_SET_ANT
+int wl_set_softap_antenna(struct net_device *dev, char *ifname, int set_chain);
+int wl_get_softap_antenna(struct net_device *dev, char *ifname, void *param);
+#endif /* CUSTOM_SOFTAP_SET_ANT */
#ifdef SUPPORT_AP_BWCTRL
extern int wl_set_ap_bw(struct net_device *dev, u32 bw, char *ifname);
extern int wl_get_ap_bw(struct net_device *dev, char* command, char *ifname, int total_len);
@@ -245,4 +249,13 @@
wl_update_configured_bw(uint32 bw);
#endif /* SUPPORT_AP_INIT_BWCONF */
extern uint32 wl_cfgvif_get_iftype_count(struct bcm_cfg80211 *cfg, wl_iftype_t iftype);
+extern s32 wl_update_akm_from_assoc_ie(struct bcm_cfg80211 *cfg, struct net_device *ndev,
+ u8 *assoc_ies, u32 assoc_ie_len);
+
+#if defined(LIMIT_AP_BW)
+uint32 wl_cfg80211_get_ap_bw_limit_bit(struct bcm_cfg80211 *cfg, uint32 band);
+chanspec_t wl_cfg80211_get_ap_bw_limited_chspec(struct bcm_cfg80211 *cfg,
+ uint32 band, chanspec_t candidate);
+int wl_cfg80211_set_softap_bw(struct bcm_cfg80211 *cfg, uint32 band, uint32 limit);
+#endif /* LIMIT_AP_BW */
#endif /* _wl_cfgvif_h_ */
diff --git a/wl_linux_mon.c b/wl_linux_mon.c
index 37b9a42..f202e52 100644
--- a/wl_linux_mon.c
+++ b/wl_linux_mon.c
@@ -1,7 +1,7 @@
/*
* Broadcom Dongle Host Driver (DHD), Linux monitor network interface
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
diff --git a/wl_roam.c b/wl_roam.c
index 81e19a1..a53697d 100644
--- a/wl_roam.c
+++ b/wl_roam.c
@@ -1,7 +1,7 @@
/*
* Linux roam cache
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -206,7 +206,7 @@
}
void
-add_roam_cache(struct bcm_cfg80211 *cfg, wl_bss_info_t *bi)
+add_roam_cache(struct bcm_cfg80211 *cfg, wl_bss_info_v109_t *bi)
{
if (!cfg->rcc_enabled) {
return;
@@ -353,29 +353,59 @@
return i;
}
+bool
+check_prune_roam_band(uint8 allowed_band, chanspec_t chanspec)
+{
+ int ret = FALSE;
+
+ if ((allowed_band == WLC_ROAM_ALLOW_BAND_AUTO) ||
+ (allowed_band == WLC_ROAM_ALLOW_BAND_MAX)) {
+ return ret;
+ }
+
+ /* Pruned BSS via ROAM Band mode */
+ if ((CHSPEC_IS2G(chanspec) && !(allowed_band & WLC_ROAM_ALLOW_BAND_2G))) {
+ ret = TRUE;
+ } else if (CHSPEC_IS5G(chanspec) && !(allowed_band & WLC_ROAM_ALLOW_BAND_5G)) {
+ ret = TRUE;
+#ifdef WL_6G_BAND
+ } else if (CHSPEC_IS6G(chanspec) && !(allowed_band & WLC_ROAM_ALLOW_BAND_6G)) {
+ ret = TRUE;
+#endif /* WL_6G_BAND */
+ }
+
+ return ret;
+}
+
int
set_roamscan_chanspec_list(struct net_device *dev, uint nchan, chanspec_t *chanspecs)
{
- int i;
+ int i, j;
int error;
wl_roam_channel_list_t channel_list;
- char iobuf[WLC_IOCTL_SMLEN];
struct bcm_cfg80211 *cfg = wl_get_cfg(dev);
- cfg->roamscan_mode = ROAMSCAN_MODE_WES;
+ char iobuf[WLC_IOCTL_SMLEN];
if (nchan > MAX_ROAM_CHANNEL) {
nchan = MAX_ROAM_CHANNEL;
}
- for (i = 0; i < nchan; i++) {
- roam_cache[i].chanspec = chanspecs[i];
- channel_list.channels[i] = chanspecs[i];
-
+ for (i = 0, j = 0; i < nchan; i++) {
+ if (!wf_chspec_valid(chanspecs[i])) {
+ WL_ERR(("%02d/%d: invalid chan: 0x%04x\n", i, nchan, chanspecs[i]));
+ continue;
+ }
+ if (check_prune_roam_band(cfg->roam_allowed_band, chanspecs[i])) {
+ WL_ERR(("%02d/%d: Pruned ROAM band(%d) 0x%04x\n", i, nchan,
+ cfg->roam_allowed_band, chanspecs[i]));
+ continue;
+ }
+ channel_list.channels[j] = roam_cache[j].chanspec = chanspecs[i];
WL_DBG(("%02d/%d: chan: 0x%04x\n", i, nchan, chanspecs[i]));
+ j++;
}
- n_roam_cache = nchan;
- channel_list.n = nchan;
+ channel_list.n = n_roam_cache = j;
/* need to set ROAMSCAN_MODE_NORMAL to update roamscan_channels,
* otherwise, it won't be updated
@@ -392,11 +422,6 @@
WL_ERR(("Failed to set roamscan channels, error = %d\n", error));
return error;
}
- error = wldev_iovar_setint(dev, "roamscan_mode", ROAMSCAN_MODE_WES);
- if (error) {
- WL_ERR(("Failed to set roamscan mode to %d, error = %d\n",
- ROAMSCAN_MODE_WES, error));
- }
return error;
}
@@ -432,7 +457,12 @@
WL_DBG(("Add Roam scan channel count %d\n", nchan));
for (i = 0; i < nchan; i++) {
- if (chanspecs[i] == 0) {
+ if (!wf_chspec_valid(chanspecs[i])) {
+ continue;
+ }
+ if (check_prune_roam_band(cfg->roam_allowed_band, chanspecs[i])) {
+ WL_ERR(("%02d/%d: Pruned ROAM band(%d) 0x%04x\n", i, nchan,
+ cfg->roam_allowed_band, chanspecs[i]));
continue;
}
add_roam_cache_list(ssid.SSID, ssid.SSID_len, chanspecs[i]);
diff --git a/wldev_common.c b/wldev_common.c
index 37f94fa..d5fa615 100644
--- a/wldev_common.c
+++ b/wldev_common.c
@@ -1,7 +1,7 @@
/*
* Common function shared by Linux WEXT, cfg80211 and p2p drivers
*
- * Copyright (C) 2021, Broadcom.
+ * Copyright (C) 2022, Broadcom.
*
* Unless you and Broadcom execute a separate written software license
* agreement governing use of this software, this software is licensed to you
@@ -22,6 +22,7 @@
*/
#include <osl.h>
+#include <linuxver.h>
#include <linux/kernel.h>
#include <linux/kthread.h>
#include <linux/netdevice.h>
@@ -102,14 +103,13 @@
strlcpy(ifr.ifr_name, dev->name, sizeof(ifr.ifr_name));
ifr.ifr_data = (caddr_t)&ioc;
- fs = get_fs();
- set_fs(get_ds());
+ GETFS_AND_SETFS_TO_KERNEL_DS(fs);
#if LINUX_VERSION_CODE < KERNEL_VERSION(2, 6, 31)
ret = dev->do_ioctl(dev, &ifr, SIOCDEVPRIVATE);
#else
ret = dev->netdev_ops->ndo_do_ioctl(dev, &ifr, SIOCDEVPRIVATE);
#endif /* LINUX_VERSION_CODE < KERNEL_VERSION(2, 6, 31) */
- set_fs(fs);
+ SETFS(fs);
ret = 0;
#endif /* defined(BCMDONGLEHOST) */
@@ -499,6 +499,7 @@
}
return error;
}
+
int wldev_get_datarate(struct net_device *dev, int *datarate)
{
int error = 0;
@@ -523,7 +524,7 @@
int chanspec = 0;
uint16 band = 0;
uint16 bandwidth = 0;
- wl_bss_info_t *bss = NULL;
+ wl_bss_info_v109_t *bss = NULL;
char* buf = NULL;
buf = kzalloc(WL_EXTRA_BUF_MAX, GFP_KERNEL);
@@ -540,7 +541,7 @@
buf = NULL;
return error;
}
- bss = (wl_bss_info_t*)(buf + 4);
+ bss = (wl_bss_info_v109_t*)(buf + 4);
chanspec = wl_chspec_driver_to_host(bss->chanspec);
band = chanspec & WL_CHANSPEC_BAND_MASK;
@@ -573,6 +574,7 @@
buf = NULL;
return error;
}
+
int wldev_set_country(
struct net_device *dev, char *country_code, bool notify, int revinfo)
{