CONFIG_LTO_CLANG=y
CONFIG_CFI_CLANG=y
#CONFIG_CFI_PERMISSIVE=y
+#CONFIG_SARSENSOR_SX9325=y
+CONFIG_SARSENSOR_SX9331=y
+CONFIG_NFC=y
+CONFIG_SEC_NFC=y
+CONFIG_SEC_NFC_PRODUCT_N5=y
+CONFIG_SEC_NFC_IF_I2C=y
+CONFIG_SEC_NFC_LDO_EN=y
+CONFIG_SEC_NFC_CLK_REQ=y
+CONFIG_SENSORS_CLASS=y
+CONFIG_INPUT_EGISTEC_320=y
+CONFIG_AW8695_HAPTIC=y
+CONFIG_MOT_UTAG=y
+CONFIG_HWMON=y
+CONFIG_SENSORS_NTC_THERMISTOR=y
+CONFIG_BACKLIGHT_SGM37603=y
+CONFIG_BACKLIGHT_LM36923=y
+CONFIG_SCSC_WLAN_ENABLE_MAC_RANDOMISATION=y
typedef bool (*hid_usage_cmp_t)(struct hid_usage *usage,
unsigned int cur_idx, unsigned int val);
+extern bool lcd_is_on;
+
static struct hid_usage *hidinput_find_key(struct hid_device *hid,
hid_usage_cmp_t match,
unsigned int value,
if (!buf)
return;
+ if (!lcd_is_on) {
+ kfree(buf);
+ return;
+ }
+
hid_output_report(report, buf);
/* synchronous output report */
ret = hid_hw_output_report(hid, buf, len);
#include <linux/spinlock.h>
#include <linux/uhid.h>
#include <linux/wait.h>
+#include <linux/fb.h>
#define UHID_NAME "uhid"
#define UHID_BUFSIZE 32
};
static struct miscdevice uhid_misc;
+bool lcd_is_on = true;
static void uhid_device_add_worker(struct work_struct *work)
{
.minor = UHID_MINOR,
.name = UHID_NAME,
};
-module_misc_device(uhid_misc);
+static int fb_state_change(struct notifier_block *nb,
+ unsigned long val, void *data)
+{
+ struct fb_event *evdata = data;
+ unsigned int blank;
+
+ dbg_hid("fb_state_change");
+ if (val != FB_EVENT_BLANK)
+ return 0;
+
+ blank = *(int *)evdata->data;
+
+ switch (blank) {
+ case FB_BLANK_POWERDOWN:
+ lcd_is_on = false;
+ break;
+ case FB_BLANK_UNBLANK:
+ lcd_is_on = true;
+ break;
+ default:
+ break;
+ }
+
+ return NOTIFY_OK;
+}
+static struct notifier_block fb_block = {
+ .notifier_call = fb_state_change,
+};
+
+static int __init uhid_init(void)
+{
+ fb_register_client(&fb_block);
+ return misc_register(&uhid_misc);
+}
+
+static void __exit uhid_exit(void)
+{
+ fb_unregister_client(&fb_block);
+ misc_deregister(&uhid_misc);
+}
+
+module_init(uhid_init);
+module_exit(uhid_exit);
MODULE_LICENSE("GPL");
MODULE_AUTHOR("David Herrmann <dh.herrmann@gmail.com>");
MODULE_DESCRIPTION("User-space I/O driver support for HID subsystem");
ccflags-$(CONFIG_SLSI_KIC_API_ENABLED) += -DCONFIG_SLSI_KIC_API_ENABLED
-ccflags-$(CONFIG_SCSC_DEBUG) += -DCONFIG_SCSC_PRINTK
+ccflags-$(CONFIG_SCSC_LOGRING) += -DCONFIG_SCSC_PRINTK
---help---
Uses generic netlink messages to communicate events to userspace daemon which takes necessary actions e.g. taking moredump
+config SCSC_QOS
+ bool "Samsung SCSC kernel PM QoS support"
+ default y
+ depends on SCSC_CORE
+ ---help---
+ SCSC_QOS provides support to configure kernel PM QoS to register configuration as per performance expectations
+
config SCSC_PLATFORM
tristate "Samsung SCSC MIF Platform driver implementation"
depends on SCSC_CORE
depends on SCSC_CORE
config SCSC_CLK20MHZ_TEST
- tristate "Samsung SCSC USB 20MHz Clock Test"
+ bool "Samsung SCSC USB 20MHz Clock Test"
depends on SCSC_CLK20MHZ
config SCSC_FM
depends on SCSC_CORE
config SCSC_FM_TEST
- tristate "Samsung SCSC MX250 Test for enabling LDOs used for FM"
+ bool "Samsung SCSC MX250 Test for enabling LDOs used for FM"
depends on SCSC_FM
config SCSC_MMAP
config SCSC_DEBUG_COMPATIBILITY
bool "Samsung SCSC Logging mode"
- depends on SCSC_DEBUG
default y
+config SCSC_LOGRING
+ tristate "Samsung SCSC Kernel Logging"
+ default y
+ ---help---
+ SCSC Drivers logging mechanism
+
config SCSC_STATIC_RING
tristate "Samsung SCSC Logging use static ring"
- depends on SCSC_DEBUG
- default n
+ depends on SCSC_LOGRING
+ default y
config SCSC_STATIC_RING_SIZE
int "Size of the static ring"
-#############################################################################
-#
-# Copyright (c) 2014 - 2016 Samsung Electronics Co., Ltd. All rights reserved
-#
-#############################################################################
+########################################################################
+# Copyright (c) 2018 Samsung Electronics Co., Ltd. All rights reserved #
+########################################################################
# Needed since this subdir is symlinked in the main Kernel tree
# without this our samsung subdir is NOT cleaned.
clean-files := *.o *.ko
-ifneq ($(CONFIG_SCSC_CORE),n)
-
-ccflags-y += -Iinclude/scsc
ccflags-y += $(CONFIG_SAMSUNG_MAXWELL_EXTRA)
-obj-$(CONFIG_SCSC_DEBUG) += scsc_logring.o
-scsc_logring-y += scsc_logring_main.o scsc_logring_ring.o scsc_logring_debugfs.o
-
-obj-$(CONFIG_SCSC_LOG_COLLECTION) += scsc_log_collection.o
-scsc_log_collection-y += scsc_log_collector.o scsc_log_collector_proc.o scsc_log_collector_mmap.o
-##
-## The following cumbersome ifeq/else is the only way to make
-## this CONFIG_SCSC_PRINTK propagate correctly in any scenario (y,m,n)
-## Otherwise using ONLY the else branch when CONFIG_SCSC_DEBUG evaluates
-## to m ==>> ccflags-m does NOT work correctly in every build scenario:
-## - kernel debug modules : builtin with scsc_logring support
-## - kernel nodebug modules : builtins without scsc_logring support
-## - kernel debug|nodebug nomodules : no builtin / no scsclogring
-##
+# No such thing as ccflags-m, so ifeq(..., m)/else
+# to correctly handle all options (y,m,n)
ifeq ($(CONFIG_SCSC_DEBUG), m)
ccflags-y += -DCONFIG_SCSC_PRINTK
else
-ccflags-$(CONFIG_SCSC_DEBUG) += -DCONFIG_SCSC_PRINTK
+ccflags-$(CONFIG_SCSC_LOGRING) += -DCONFIG_SCSC_PRINTK
endif
-ifneq ($(CONFIG_SCSC_DEBUG),n)
-ccflags-$(CONFIG_SCSC_STATIC_RING) += -DCONFIG_SCSC_STATIC_RING_SIZE=$(CONFIG_SCSC_STATIC_RING_SIZE)
+ifneq ($(CONFIG_SCSC_STATIC_RING), n)
+ccflags-y += -DCONFIG_SCSC_STATIC_RING_SIZE=$(CONFIG_SCSC_STATIC_RING_SIZE)
endif
-obj-$(CONFIG_SCSC_WIFILOGGER) += scsc_wifilogger.o
-scsc_wifilogger-y += scsc_wifilogger_api.o \
- scsc_wifilogger_internal.o \
- scsc_wifilogger_core.o \
- scsc_wifilogger_module.o \
- scsc_wifilogger_ring_connectivity.o \
- scsc_wifilogger_ring_wakelock.o \
- scsc_wifilogger_ring_pktfate.o
+# Debug
+obj-$(CONFIG_SCSC_LOGRING) += scsc_logring.o
+scsc_logring-$(CONFIG_SCSC_LOGRING) += \
+ scsc_logring_main.o \
+ scsc_logring_ring.o \
+ scsc_logring_debugfs.o
+
+# Log collection
+obj-$(CONFIG_SCSC_LOG_COLLECTION) += scsc_log_collection.o
+scsc_log_collection-$(CONFIG_SCSC_LOG_COLLECTION) += \
+ scsc_log_collector.o \
+ scsc_log_collector_proc.o \
+ scsc_log_collector_mmap.o \
+
+# WiFi logger
+obj-$(CONFIG_SCSC_WIFILOGGER) += scsc_wifilogger.o
+scsc_wifilogger-$(CONFIG_SCSC_WIFILOGGER) += \
+ scsc_wifilogger_api.o \
+ scsc_wifilogger_internal.o \
+ scsc_wifilogger_core.o \
+ scsc_wifilogger_module.o \
+ scsc_wifilogger_ring_connectivity.o \
+ scsc_wifilogger_ring_wakelock.o \
+ scsc_wifilogger_ring_pktfate.o
scsc_wifilogger-$(CONFIG_SCSC_WIFILOGGER_DEBUGFS) += scsc_wifilogger_debugfs.o
+
scsc_wifilogger-$(CONFIG_SCSC_WIFILOGGER_TEST) += scsc_wifilogger_ring_test.o
-#pcie_module for static functions and registration of client modules (only core)
-#pcie_mif for instance
+# PCI-E MIF
obj-$(CONFIG_SCSC_PCIE) += scsc_pcie_mif.o
-scsc_pcie_mif-y += pcie_mif_module.o pcie_mif.o pcie_proc.o pcie_mbox.o pcie_mbox_intgen.o
-
+scsc_pcie_mif-$(CONFIG_SCSC_PCIE) += \
+ pcie_mif_module.o \
+ pcie_mif.o \
+ pcie_proc.o \
+ pcie_mbox.o \
+ pcie_mbox_intgen.o
+
+# Platform MIF
obj-$(CONFIG_SCSC_PLATFORM) += scsc_platform_mif.o
-scsc_platform_mif-y += platform_mif_module.o platform_mif.o
+scsc_platform_mif-$(CONFIG_SCSC_PLATFORM) += \
+ platform_mif_module.o \
+ platform_mif.o
-#core_module for static functions and registration client module (all the service driver modules -wlan, bt,...-)
-#core for instance
+# Maxwell manager
obj-$(CONFIG_SCSC_CORE_CM) += scsc_mx.o
-scsc_mx-y += \
+scsc_mx-$(CONFIG_SCSC_CORE_CM) += \
mxlog_transport.o \
fw_panic_record.o \
panicmon.o \
mifstream.o \
mxmgmt_transport.o \
gdb_transport.o \
- mifqos.o \
mx140_file.o
+# Maxwell logger
scsc_mx-$(CONFIG_SCSC_MXLOGGER) += mxlogger.o
+# SMAPPER
scsc_mx-$(CONFIG_SCSC_SMAPPER) += mifsmapper.o
+# WLBT daemon
scsc_mx-$(CONFIG_SCSC_WLBTD) += scsc_wlbtd.o
-ifneq ($(CONFIG_SCSC_CM_MX_CLIENT_TEST),n)
+# QOS
+scsc_mx-$(CONFIG_SCSC_QOS) += mifqos.o
+
+# Null service (test)
obj-$(CONFIG_SCSC_CM_MX_CLIENT_TEST) += mx_client_test.o
-mx_client_test-y += client_test.o
-endif
+mx_client_test-$(CONFIG_SCSC_CM_MX_CLIENT_TEST) += client_test.o
-ifneq ($(CONFIG_SCSC_MMAP),n)
+# Memory map
obj-$(CONFIG_SCSC_MMAP) += scsc_mmap.o
-scsc_mmap-y += mx_mmap.o
-endif
+scsc_mmap-$(CONFIG_SCSC_MMAP) += mx_mmap.o
-ifneq ($(CONFIG_SCSC_CLK20MHZ),n)
+# 20 MHz clock test
obj-$(CONFIG_SCSC_CLK20MHZ) += scsc_mx140_clk.o
-scsc_mx140_clk-y += mx140_clk.o
+scsc_mx140_clk-$(CONFIG_SCSC_CLK20MHZ) += mx140_clk.o
ifeq ($(CONFIG_SCSC_CLK20MHZ_TEST),y)
-scsc_mx140_clk-y += mx140_clk_test.o
-endif
+scsc_mx140_clk-$(CONFIG_SCSC_CLK20MHZ) += mx140_clk_test.o
endif
-ifneq ($(CONFIG_SCSC_FM),n)
+# FM LDO test
obj-$(CONFIG_SCSC_FM) += scsc_mx250_fm.o
-scsc_mx250_fm-y += mx250_fm.o
+scsc_mx250_fm-$(CONFIG_SCSC_FM) += mx250_fm.o
ifeq ($(CONFIG_SCSC_FM_TEST),y)
-scsc_mx250_fm-y += mx250_fm_test.o
-endif
+scsc_mx250_fm-$(CONFIG_SCSC_FM) += mx250_fm_test.o
endif
+# Debug sampler
obj-$(CONFIG_SCSC_DBG_SAMPLER) += scsc_dbg_sampler.o
-scsc_dbg_sampler-y += mx_dbg_sampler.o
-
-endif
+scsc_dbg_sampler-$(CONFIG_SCSC_DBG_SAMPLER) += mx_dbg_sampler.o
# The below section is only for DTE purpose. It is controlled by the flag SCSC_DTE_BUILD which is set only by the
# DTE top level Makefile. Hence, no risk.
#include <scsc/scsc_logring.h>
#include "scsc_mif_abs.h"
+#include "scsc/api/bt_audio.h"
#include "miframman.h"
+
/* Caller should provide locking */
void miframman_init(struct miframman *ram, void *start_dram, size_t size_pool)
{
ram->free_mem = ram->num_blocks * MIFRAMMAN_BLOCK_SIZE;
}
+void miframabox_init(struct mifabox *mifabox, void *start_aboxram)
+{
+ /* No locking as not a shared resource */
+ mifabox->aboxram = (struct scsc_bt_audio_abox *)start_aboxram;
+}
+
void *__miframman_alloc(struct miframman *ram, size_t nbytes)
{
unsigned int index = 0;
ram->size_pool = 0;
ram->free_mem = 0;
}
+
+void miframabox_deinit(struct mifabox *mifabox)
+{
+ /* not dynamic - so just mark as NULL */
+ /* Maybe this function should be empty? */
+ mifabox->aboxram = NULL;
+}
+
#define __MIFRAMMAN_H
#include <linux/mutex.h>
+#include "scsc/api/bt_audio.h"
/* TODO: Needs to define the max mem */
struct miframman;
+struct mifabox;
+
void miframman_init(struct miframman *ram, void *start_dram, size_t size_pool);
+void miframabox_init(struct mifabox *mifabox, void *start_aboxram);
void *miframman_alloc(struct miframman *ram, size_t nbytes, size_t align);
void miframman_free(struct miframman *ram, void *mem);
void miframman_deinit(struct miframman *ram);
+void miframabox_deinit(struct mifabox *mifabox);
#define MIFRAMMAN_MAXMEM (16 * 1024 * 1024)
#define MIFRAMMAN_BLOCK_SIZE (64)
u32 free_mem;
struct mutex lock;
};
+
+struct mifabox {
+ struct scsc_bt_audio_abox *aboxram;
+};
#endif
#include <linux/version.h>
#include <linux/firmware.h>
#include <linux/fs.h>
+#if KERNEL_VERSION(4, 15, 0) <= LINUX_VERSION_CODE
+#include <linux/uaccess.h>
+#else
#include <asm/uaccess.h>
+#endif
#include <linux/slab.h>
#include <linux/vmalloc.h>
#endif
/* Look for this file in <dir>/etc/wifi */
-#define MX140_FW_DETECT "mx"
+#ifdef CONFIG_ANDROID
+#define MX140_FW_DETECT "mx"
+#else
+/* Linux host vfs_stat() doesn't find mx* with "mx" */
+#define MX140_FW_DETECT "mx140.bin"
+#endif
/* Paths for vendor utilities, used when CONFIG_SCSC_CORE_FW_LOCATION_AUTO=n */
#define MX140_EXE_DIR_VENDOR "/vendor/bin" /* Oreo */
MODULE_PARM_DESC(firmware_hw_ver, "mx140 hw version detect, manual=disable");
/* FW base dir readable by usermode script */
+#ifdef CONFIG_SCSC_CORE_FW_LOCATION_AUTO
+static char *fw_base_dir;
+#else
static char *fw_base_dir = CONFIG_SCSC_CORE_FW_LOCATION;
+#endif
module_param_named(base_dir, fw_base_dir, charp, S_IRUGO | S_IWUSR);
MODULE_PARM_DESC(base_dir, "WLBT FW base directory");
r = open_start_service();
if (r) {
SCSC_TAG_ERR(FM, "Error starting service: open_start_service(fm_service) failed %d\n", r);
- return r;
+
+ if (!fm_client->ldo_on) {
+ /* Do not return here. For the case where WLBT FW is crashed, and FM off request is
+ * rejected, it's safest to continue to let scsc_service_on_halt_ldos_off() reset
+ * the global flag to indicate that FM is no longer needed when WLBT next boots.
+ * Otherwise LDO could be stuck always-on.
+ */
+ } else
+ return r;
}
if (fm_client->ldo_on)
#include <linux/cdev.h>
#include <linux/device.h>
#include <linux/fs.h>
-#include <asm/uaccess.h>
+#include <linux/uaccess.h>
#include <scsc/scsc_logring.h>
#include <scsc/scsc_mx.h>
* mismatches.
*/
#define MXCONF_VERSION_MAJOR 0
-#define MXCONF_VERSION_MINOR 1
+#define MXCONF_VERSION_MINOR 3 /* For FM status */
/* Types */
struct mxtransconf mx_trans_conf_gdb_m4;
/**
- * Mxlog Event Buffer Configuration.
- */
+ * Mxlog Event Buffer Configuration.
+ */
struct mxlogconf mxlogconf;
+ /* FROM MINOR_2 */
+
+ /**
+ * SOC HW revision override from host
+ */
+ uint32_t soc_revision;
+
+ /* FROM MINOR_3 */
+
+ /**
+ * Setup flags
+ */
+#define MXCONF_FLAGS_FM_ON (BIT(0)) /* FM already on */
+ uint32_t flags;
+
} __MXPACKED;
#endif /* MXCONF_H__ */
{
unsigned char *buf = (unsigned char *)message;
- SCSC_TAG_LVL(MX_FW, level, "%d: %s\n", (int)length, buf);
+ SCSC_TAG_LVL(MX_FW, level, SCSC_PREFIX"%d: %s\n", (int)length, buf);
}
/**
/* Add FW provided tstamp on front and proper \n at
* the end when needed
*/
- snprintf(spare, MAX_SPARE_FMT + TSTAMP_LEN - 2, "%08X %s%c",
+ snprintf(spare, MAX_SPARE_FMT + TSTAMP_LEN - 2, SCSC_PREFIX"%08X %s%c",
elogmsg->timestamp, fmt,
(fmt[fmt_sz] != '\n') ? '\n' : '\0');
fmt = spare;
static int __mxlogger_generate_sync_record(struct mxlogger *mxlogger, enum mxlogger_sync_event event)
{
- struct mxlogger_sync_record sync_r = {};
+ struct mxlogger_sync_record *sync_r_mem;
struct timeval t;
struct log_msg_packet msg = {};
+ unsigned long int jd;
void *mem;
+ ktime_t t1, t2;
msg.msg = MM_MXLOGGER_SYNC_RECORD;
msg.arg = MM_MXLOGGER_SYNC_INDEX;
memcpy(&msg.payload, &mxlogger->sync_buffer_index, sizeof(mxlogger->sync_buffer_index));
- do_gettimeofday(&t);
-
- sync_r.tv_sec = (u64)t.tv_sec;
- sync_r.tv_usec = (u64)t.tv_usec;
- sync_r.kernel_time = ktime_to_ns(ktime_get());
- sync_r.sync_event = event;
-
/* Get the pointer from the index of the sync array */
mem = mxlogger->mem_sync_buf + mxlogger->sync_buffer_index * sizeof(struct mxlogger_sync_record);
- memcpy(mem, &sync_r, sizeof(struct mxlogger_sync_record));
-
- mxlogger->sync_buffer_index++;
- mxlogger->sync_buffer_index &= SYNC_MASK;
-
+ sync_r_mem = (struct mxlogger_sync_record *)mem;
+ /* Write values in record as FW migth be doing sanity checks */
+ sync_r_mem->tv_sec = 1;
+ sync_r_mem->tv_usec = 1;
+ sync_r_mem->kernel_time = 1;
+ sync_r_mem->sync_event = event;
+ sync_r_mem->fw_time = 0;
+ sync_r_mem->fw_wrap = 0;
+
+
+ SCSC_TAG_INFO(MXMAN, "Get FW time\n");
+ preempt_disable();
+ /* set the tight loop timeout - we do not require precission but something to not
+ * loop forever
+ */
+ jd = jiffies + msecs_to_jiffies(20);
/* Send the msg as fast as possible */
mxmgmt_transport_send(scsc_mx_get_mxmgmt_transport(mxlogger->mx),
MMTRANS_CHAN_ID_MAXWELL_LOGGING,
&msg, sizeof(msg));
+ t1 = ktime_get();
+ /* Tight loop to read memory */
+ while (time_before(jiffies, jd) && sync_r_mem->fw_time == 0 && sync_r_mem->fw_wrap == 0)
+ ;
+ t2 = ktime_get();
+ do_gettimeofday(&t);
+ preempt_enable();
+
+ /* Do the processing */
+ if (sync_r_mem->fw_wrap == 0 && sync_r_mem->fw_time == 0) {
+ /* FW didn't update the record (FW panic?). Do not create a SYNC record */
+ SCSC_TAG_INFO(MXMAN, "FW failure updating the FW time\n");
+ SCSC_TAG_INFO(MXMAN, "Sync delta %lld\n", ktime_to_ns(ktime_sub(t2, t1)));
+ return 0;
+ }
+
+ sync_r_mem->tv_sec = (u64)t.tv_sec;
+ sync_r_mem->tv_usec = (u64)t.tv_usec;
+ sync_r_mem->kernel_time = ktime_to_ns(t2);
+ sync_r_mem->sync_event = event;
+
+ SCSC_TAG_INFO(MXMAN, "Sample, %lld, %u, %lld.%06lld\n",
+ ktime_to_ns(sync_r_mem->kernel_time), sync_r_mem->fw_time, sync_r_mem->tv_sec, sync_r_mem->tv_usec);
+ SCSC_TAG_INFO(MXMAN, "Sync delta %lld\n", ktime_to_ns(ktime_sub(t2, t1)));
+
+ mxlogger->sync_buffer_index++;
+ mxlogger->sync_buffer_index &= SYNC_MASK;
return 0;
}
MEM_LAYOUT_CHECK();
+ mxlogger->configured = false;
+
if (mem_sz <= (sizeof(struct mxlogger_config_area) + MXLOGGER_TOTAL_FIX_BUF)) {
SCSC_TAG_ERR(MXMAN, "Insufficient memory allocation\n");
return -EIO;
struct mxlogger_node *mn, *next;
bool match = false;
+ SCSC_TAG_INFO(MXMAN, "\n");
+
+ if (!mxlogger || !mxlogger->configured) {
+ SCSC_TAG_WARNING(MXMAN, "MXLOGGER is not valid or not configured.\n");
+ return;
+ }
/* Run deregistration before adquiring the mxlogger lock to avoid
* deadlock with log_collector.
*/
if (match == false)
SCSC_TAG_ERR(MXMAN, "FATAL, no match for given scsc_mif_abs\n");
+ SCSC_TAG_INFO(MXMAN, "End\n");
mutex_unlock(&mxlogger->lock);
}
#ifdef CONFIG_SCSC_SMAPPER
#include "mifsmapper.h"
#endif
+#ifdef CONFIG_SCSC_QOS
#include "mifqos.h"
+#endif
#include <scsc/kic/slsi_kic_lib.h>
#include <scsc/scsc_release.h>
-#include "scsc_mx.h"
+#include <scsc/scsc_mx.h>
#include <linux/fs.h>
#ifdef CONFIG_SCSC_LOG_COLLECTION
#include <scsc/scsc_log_collector.h>
static struct work_struct wlbtd_work;
#endif
+#include <asm/page.h>
+#include <scsc/api/bt_audio.h>
+
#define STRING_BUFFER_MAX_LENGTH 512
#define NUMBER_OF_STRING_ARGS 5
#define MX_DRAM_SIZE (4 * 1024 * 1024)
bool reset_failed;
static u64 reset_failed_time;
+/* Status of FM driver request, which persists beyond the lifecyle
+ * of the scsx_mx driver.
+ */
+#ifdef CONFIG_SCSC_FM
+static u32 is_fm_on;
+#endif
+
static int firmware_runtime_flags;
/**
* This mxman reference is initialized/nullified via mxman_init/deinit
mxconf->magic = MXCONF_MAGIC;
mxconf->version.major = MXCONF_VERSION_MAJOR;
mxconf->version.minor = MXCONF_VERSION_MINOR;
+
+ /* Pass pre-existing FM status to FW */
+#if (MXCONF_VERSION_MINOR >= 3)
+ mxconf->flags = 0;
+#ifdef CONFIG_SCSC_FM
+ mxconf->flags |= is_fm_on ? MXCONF_FLAGS_FM_ON : 0;
+#endif
+ SCSC_TAG_INFO(MXMAN, "mxconf flags 0x%08x\n", mxconf->flags);
+#endif
/* serialise mxmgmt transport */
mxmgmt_transport_config_serialise(scsc_mx_get_mxmgmt_transport(mx), &mxconf->mx_trans_conf);
/* serialise Cortex-R4 gdb transport */
start_mifram_heap = (char *)start_dram + fwhdr->fw_runtime_length;
length_mifram_heap = MX_DRAM_SIZE_SECTION_1 - fwhdr->fw_runtime_length;
+
start_mifram_heap2 = (char *)start_dram + MX_DRAM_SIZE_SECTION_2;
- length_mifram_heap2 = MX_DRAM_SIZE_SECTION_2;
+
+ /* ABox reserved at end so adjust length - round to multiple of PAGE_SIZE */
+ length_mifram_heap2 = MX_DRAM_SIZE_SECTION_2 -
+ ((sizeof(struct scsc_bt_audio_abox) + PAGE_SIZE - 1) & ~(PAGE_SIZE - 1));
miframman_init(scsc_mx_get_ramman(mxman->mx), start_mifram_heap, length_mifram_heap);
miframman_init(scsc_mx_get_ramman2(mxman->mx), start_mifram_heap2, length_mifram_heap2);
+ miframabox_init(scsc_mx_get_aboxram(mxman->mx), start_mifram_heap2 + length_mifram_heap2);
mifmboxman_init(scsc_mx_get_mboxman(mxman->mx));
mifintrbit_init(scsc_mx_get_intrbit(mxman->mx), mif);
mifintrbit_deinit(scsc_mx_get_intrbit(mxman->mx));
miframman_deinit(scsc_mx_get_ramman(mxman->mx));
miframman_deinit(scsc_mx_get_ramman2(mxman->mx));
+ miframabox_deinit(scsc_mx_get_aboxram(mxman->mx));
mifmboxman_deinit(scsc_mx_get_mboxman(mxman->mx));
#ifdef CONFIG_SCSC_SMAPPER
mifsmapper_deinit(scsc_mx_get_smapper(mxman->mx));
#endif
+#ifdef CONFIG_SCSC_QOS
mifqos_deinit(scsc_mx_get_qos(mxman->mx));
+#endif
/* Release the MIF memory resources */
mif->unmap(mif, mxman->start_dram);
return r;
mbox_init(mxman, fwhdr->firmware_entry_point);
init_completion(&mxman->mm_msg_start_ind_completion);
init_completion(&mxman->mm_msg_halt_rsp_completion);
- mxmgmt_transport_register_channel_handler(scsc_mx_get_mxmgmt_transport(mxman->mx), MMTRANS_CHAN_ID_MAXWELL_MANAGEMENT,
- &mxman_message_handler, mxman);
+ mxmgmt_transport_register_channel_handler(scsc_mx_get_mxmgmt_transport(mxman->mx),
+ MMTRANS_CHAN_ID_MAXWELL_MANAGEMENT,
+ &mxman_message_handler, mxman);
mxlog_init(scsc_mx_get_mxlog(mxman->mx), mxman->mx, mxman->fw_build_id);
#ifdef CONFIG_SCSC_MXLOGGER
/* Initialize SMAPPER */
mifsmapper_init(scsc_mx_get_smapper(mxman->mx), mif);
#endif
+#ifdef CONFIG_SCSC_QOS
mifqos_init(scsc_mx_get_qos(mxman->mx), mif);
+#endif
#ifdef CONFIG_SCSC_CHV_SUPPORT
if (chv_run) {
print_panic_code(mxman->scsc_panic_code);
SCSC_TAG_INFO(MXMAN, "Reason: '%s'\n", mxman->failure_reason[0] ? mxman->failure_reason : "<null>");
+ SCSC_TAG_INFO(MXMAN, "Auto-recovery: %s\n", disable_recovery_handling ? "off" : "on");
if (disable_recovery_handling) {
/* Labour the point that a reboot is needed when autorecovery is disabled */
struct srvman *srvman;
struct scsc_mx *mx = mxman->mx;
struct scsc_mif_abs *mif = scsc_mx_get_mif_abs(mxman->mx);
+ int used = 0, r = 0;
+#ifdef CONFIG_ANDROID
wake_lock(&mxman->recovery_wake_lock);
+#endif
slsi_kic_system_event(slsi_kic_system_event_category_error,
slsi_kic_system_events_subsystem_crashed, GFP_KERNEL);
if (mxman->mxman_state != MXMAN_STATE_STARTED && mxman->mxman_state != MXMAN_STATE_STARTING) {
SCSC_TAG_WARNING(MXMAN, "Not in started state: mxman->mxman_state=%d\n", mxman->mxman_state);
+#ifdef CONFIG_ANDROID
wake_unlock(&mxman->recovery_wake_lock);
+#endif
mutex_unlock(&mxman->mxman_mutex);
return;
}
WARN_ON(mxman->mxman_state != MXMAN_STATE_FAILED
&& mxman->mxman_state != MXMAN_STATE_FREEZED);
SCSC_TAG_ERR(MXMAN, "Bad state=%d\n", mxman->mxman_state);
+#ifdef CONFIG_ANDROID
wake_unlock(&mxman->recovery_wake_lock);
+#endif
mutex_unlock(&mxman->mxman_mutex);
return;
}
SCSC_RELEASE_ITERATION,
SCSC_RELEASE_CANDIDATE,
SCSC_RELEASE_POINT);
+ SCSC_TAG_INFO(MXMAN, "Auto-recovery: %s\n", mxman_recovery_disabled() ? "off" : "on");
#ifdef CONFIG_SCSC_WLBTD
scsc_wlbtd_get_and_print_build_type();
#endif
MAX_UHELP_TMO_MS);
/* Waits for the usermode_helper subsytem to be re-enabled. */
if (usermodehelper_read_lock_wait(msecs_to_jiffies(MAX_UHELP_TMO_MS))) {
- int used, r;
-
/**
* Release immediately the rwsem on usermode_helper
* enabled since we anyway already hold a wakelock here
if (mif->mif_cleanup && mxman_recovery_disabled())
mif->mif_cleanup(mif);
}
+ SCSC_TAG_INFO(MXMAN, "Auto-recovery: %s\n", mxman_recovery_disabled() ? "off" : "on");
if (!mxman_recovery_disabled())
srvman_clear_error(srvman);
if (mxman_recovery_disabled())
complete(&mxman->recovery_completion);
+#ifdef CONFIG_ANDROID
wake_unlock(&mxman->recovery_wake_lock);
+#endif
}
static void failure_wq_init(struct mxman *mxman)
SCSC_TAG_INFO(MXMAN, "Reason: '%s'\n", mxman->failure_reason[0] ? mxman->failure_reason : "<null>");
print_panic_code(mxman->scsc_panic_code);
}
+ SCSC_TAG_INFO(MXMAN, "Auto-recovery: %s\n", mxman_recovery_disabled() ? "off" : "on");
srvman = scsc_mx_get_srvman(mxman->mx);
if (srvman && srvman->error) {
mutex_unlock(&mxman->mxman_mutex);
mifintrbit_deinit(scsc_mx_get_intrbit(mxman->mx));
miframman_deinit(scsc_mx_get_ramman(mxman->mx));
miframman_deinit(scsc_mx_get_ramman2(mxman->mx));
+ miframabox_deinit(scsc_mx_get_aboxram(mxman->mx));
mifmboxman_deinit(scsc_mx_get_mboxman(mxman->mx));
#ifdef CONFIG_SCSC_SMAPPER
mifsmapper_deinit(scsc_mx_get_smapper(mxman->mx));
#endif
+#ifdef CONFIG_SCSC_QOS
mifqos_deinit(scsc_mx_get_qos(mxman->mx));
+#endif
/* Release the MIF memory resources */
mif->unmap(mif, mxman->start_dram);
}
mutex_unlock(&mxman->mxman_mutex);
return;
}
+#ifdef CONFIG_SCSC_MXLOGGER
+ /**
+ * Deinit mxlogger on last service stop...BUT before asking for HALT
+ */
+ mxlogger_deinit(mxman->mx, scsc_mx_get_mxlogger(mxman->mx));
+#endif
mxman_stop(mxman);
mxman->mxman_state = MXMAN_STATE_STOPPED;
#endif
mutex_init(&mxman->mxman_mutex);
init_completion(&mxman->recovery_completion);
+#ifdef CONFIG_ANDROID
wake_lock_init(&mxman->recovery_wake_lock, WAKE_LOCK_SUSPEND, "mxman_recovery");
+#endif
/* set the initial state */
mxman->mxman_state = MXMAN_STATE_STOPPED;
#ifdef CONFIG_SCSC_WLBTD
wlbtd_wq_deinit(mxman);
#endif
+#ifdef CONFIG_ANDROID
wake_lock_destroy(&mxman->recovery_wake_lock);
+#endif
mutex_destroy(&mxman->mxman_mutex);
}
void mxman_on_halt_ldos_on(struct mxman *mxman)
{
mxman->on_halt_ldos_on = 1;
+
+ /* FM status to pass into FW at next FW init,
+ * by which time driver context is lost.
+ * This is required, because now WLBT gates
+ * LDOs with TCXO instead of leaving them
+ * always on, to save power in deep sleep.
+ * FM, however, needs them always on. So
+ * we need to know when to leave the LDOs
+ * alone at WLBT boot.
+ */
+ is_fm_on = 1;
}
void mxman_on_halt_ldos_off(struct mxman *mxman)
{
+ /* Newer FW no longer need set shared LDOs
+ * always-off at WLBT halt, as TCXO gating
+ * has the same effect. But pass the "off"
+ * request for backwards compatibility
+ * with old FW.
+ */
mxman->on_halt_ldos_on = 0;
+ is_fm_on = 0;
}
#endif
}
# endif /* CONFIG_SCSC_WLBTD */
return r;
-
-
#else
return 0;
#endif
void mxman_get_fw_version(char *version, size_t ver_sz)
{
/* unavailable only if chip not probed ! */
- snprintf(version, ver_sz - 1, "%s", saved_fw_build_id);
+ snprintf(version, ver_sz, "%s", saved_fw_build_id);
}
EXPORT_SYMBOL(mxman_get_fw_version);
{
/* IMPORTANT - Do not change the formatting as User space tooling is parsing the string
* to read SAP fapi versions. */
- snprintf(version, ver_sz - 1, "drv_ver: %u.%u.%u.%u",
+ snprintf(version, ver_sz, "drv_ver: %u.%u.%u.%u",
SCSC_RELEASE_PRODUCT, SCSC_RELEASE_ITERATION, SCSC_RELEASE_CANDIDATE, SCSC_RELEASE_POINT);
#ifdef CONFIG_SCSC_WLBTD
scsc_wlbtd_get_and_print_build_type();
#include "fwhdr.h"
#include "mxmgmt_transport.h"
#include "mxproc.h"
-#include "scsc_mx.h"
+#include <scsc/scsc_mx.h>
+#ifdef CONFIG_ANDROID
#include <linux/wakelock.h>
+#endif
struct mxman;
bool check_crc;
char fw_build_id[FW_BUILD_ID_SZ]; /* Defined in SC-505846-SW */
struct completion recovery_completion;
+#ifdef CONFIG_ANDROID
struct wake_lock recovery_wake_lock;
+#endif
u32 rf_hw_ver;
u16 scsc_panic_code;
u64 last_panic_time;
}
}
+#ifdef CONFIG_SCSC_QOS
+static int pcie_mif_pm_qos_add_request(struct scsc_mif_abs *interface, struct scsc_mifqos_request *qos_req, enum scsc_qos_config config)
+{
+ return 0;
+}
+
+static int pcie_mif_pm_qos_update_request(struct scsc_mif_abs *interface, struct scsc_mifqos_request *qos_req, enum scsc_qos_config config)
+{
+ return 0;
+}
+
+static int pcie_mif_pm_qos_remove_request(struct scsc_mif_abs *interface, struct scsc_mifqos_request *qos_req)
+{
+ return 0;
+}
+#endif
+
irqreturn_t pcie_mif_isr(int irq, void *data)
{
struct pcie_mif *pcie = (struct pcie_mif *)data;
pcie_if->get_mif_device = pcie_mif_get_mif_device;
pcie_if->irq_clear = pcie_mif_irq_clear;
pcie_if->mif_dump_registers = pcie_mif_dump_register;
+#ifdef CONFIG_SCSC_QOS
+ pcie_if->mif_pm_qos_add_request = pcie_mif_pm_qos_add_request;
+ pcie_if->mif_pm_qos_update_request = pcie_mif_pm_qos_update_request;
+ pcie_if->mif_pm_qos_remove_request = pcie_mif_pm_qos_remove_request;
+#endif
/* Suspend/resume not supported in PCIe MIF */
pcie_if->suspend_reg_handler = NULL;
#include <linux/dma-mapping.h>
#include "mif_reg_smapper.h"
#endif
+#ifdef CONFIG_SCSC_QOS
#include <linux/pm_qos.h>
+#endif
#if !defined(CONFIG_SOC_EXYNOS7872) && !defined(CONFIG_SOC_EXYNOS7570) \
&& !defined(CONFIG_SOC_EXYNOS7885) && !defined(CONFIG_SOC_EXYNOS9610)
module_param(enable_platform_mif_arm_reset, bool, S_IRUGO | S_IWUSR);
MODULE_PARM_DESC(enable_platform_mif_arm_reset, "Enables WIFIBT ARM cores reset");
+#ifdef CONFIG_SCSC_QOS
struct qos_table {
unsigned int freq_mif;
unsigned int freq_int;
unsigned int freq_cl0;
unsigned int freq_cl1;
};
+#endif
struct platform_mif {
struct scsc_mif_abs interface;
void (*reset_request_handler)(int irq, void *data);
void *irq_reset_request_dev;
+#ifdef CONFIG_SCSC_QOS
/* QoS table */
struct qos_table *qos;
bool qos_enabled;
-
+#endif
/* Suspend/resume handlers */
int (*suspend_handler)(struct scsc_mif_abs *abs, void *data);
void (*resume_handler)(struct scsc_mif_abs *abs, void *data);
return 0;
}
#endif
-
+#ifdef CONFIG_SCSC_QOS
static int platform_mif_parse_qos(struct platform_mif *platform, struct device_node *np)
{
int len, i;
return 0;
}
+#endif
static void platform_mif_irq_default_handler(int irq, void *data)
{
platform_if->mif_smapper_configure = platform_mif_smapper_configure;
platform_if->mif_smapper_get_bank_base_address = platform_mif_smapper_get_bank_base_address;
#endif
+#ifdef CONFIG_SCSC_QOS
platform_if->mif_pm_qos_add_request = platform_mif_pm_qos_add_request;
platform_if->mif_pm_qos_update_request = platform_mif_pm_qos_update_request;
platform_if->mif_pm_qos_remove_request = platform_mif_pm_qos_remove_request;
-
+#endif
/* Update state */
platform->pdev = pdev;
platform->dev = &pdev->dev;
platform_mif_parse_smapper(platform, platform->dev->of_node, smapper_banks);
#endif
+#ifdef CONFIG_SCSC_QOS
platform_mif_parse_qos(platform, platform->dev->of_node);
+#endif
#ifdef CONFIG_SCSC_CLK20MHZ
/* Assign USBPLL ownership to WLBT f/w */
__platform_mif_usbpll_claim(platform, true);
#include <linux/list_sort.h>
#include <linux/limits.h>
#include <linux/workqueue.h>
-#include <linux/completion.h>
#include <scsc/scsc_log_collector.h>
#include "scsc_log_collector_proc.h"
static int scsc_log_collector_collect(enum scsc_log_reason reason, u16 reason_code);
+static atomic_t in_collection;
+
/* Collect logs in an intermediate buffer to be collected at later time (mmap or wq) */
static bool collect_to_ram = true;
module_param(collect_to_ram, bool, S_IRUGO | S_IWUSR);
struct work_struct collect_work;
enum scsc_log_reason collect_reason;
u16 reason_code;
- struct completion complete;
struct mutex collection_serial;
} log_status;
pr_info("SCSC running scheduled Log Collection - collect reason:%d reason code:%d\n",
ls->collect_reason, ls->reason_code);
scsc_log_collector_collect(ls->collect_reason, ls->reason_code);
- complete(&log_status.complete);
+ atomic_set(&in_collection, 0);
}
/* Module init */
log_status.buf = NULL;
}
- init_completion(&log_status.complete);
mutex_init(&log_status.collection_serial);
scsc_log_collect_proc_create();
scsc_log_collect_proc_remove();
if (log_status.collection_workq) {
- cancel_work_sync(&log_status.collect_work);
+ flush_workqueue(log_status.collection_workq);
destroy_workqueue(log_status.collection_workq);
log_status.collection_workq = NULL;
}
lc->collect_client->collect_end(lc->collect_client);
}
- pr_info("Log collection end. Took: %lld\n", ktime_to_ns(ktime_sub(ktime_get(), start)));
+ pr_info("Calling sable collection\n");
#ifdef CONFIG_SCSC_WLBTD
if (sbl_is_valid)
call_wlbtd_sable(scsc_loc_reason_str[reason], reason_code);
#endif
+ pr_info("Log collection end. Took: %lld\n", ktime_to_ns(ktime_sub(ktime_get(), start)));
+
mutex_unlock(&log_mutex);
return ret;
void scsc_log_collector_schedule_collection(enum scsc_log_reason reason, u16 reason_code)
{
- int err;
if (log_status.collection_workq) {
mutex_lock(&log_status.collection_serial);
pr_info("Log collection Schedule");
+
+ /* Serialize with previous work if the reason is a FW panic */
+ if (reason == SCSC_LOG_FW_PANIC)
+ flush_work(&log_status.collect_work);
+ else if (atomic_read(&in_collection)) {
+ pr_info("Log collection %s reason_code 0x%x rejected. Collection already scheduled\n",
+ scsc_loc_reason_str[reason], reason_code);
+ mutex_unlock(&log_status.collection_serial);
+ return;
+ }
log_status.collect_reason = reason;
log_status.reason_code = reason_code;
- if (!queue_work(log_status.collection_workq, &log_status.collect_work))
- pr_info("Log collection %s reason_code 0x%x rejected. Collection already scheduled\n",
+ if (!queue_work(log_status.collection_workq, &log_status.collect_work)) {
+ pr_info("Log collection %s reason_code 0x%x queue_work error\n",
scsc_loc_reason_str[reason], reason_code);
- err = wait_for_completion_timeout(&log_status.complete, 5*HZ);
- if (!err)
- pr_err("Log collection Timeout");
- pr_info("Log collection End");
+ mutex_unlock(&log_status.collection_serial);
+ return;
+ }
+ atomic_set(&in_collection, 1);
+ pr_info("Log collection Scheduled");
mutex_unlock(&log_status.collection_serial);
} else {
#endif
/* Global module parameters */
+static int cached_enable;
static int enable = DEFAULT_ENABLE_LOGRING;
static bool initialized;
#ifndef CONFIG_SCSC_STATIC_RING_SIZE
if (IS_PRINTK_REDIRECT_ALLOWED(force, level, tag)) {
if (level < SCSC_MIN_DBG || level >= ARRAY_SIZE(map2kern))
level = ARRAY_SIZE(map2kern) - 1;
- print_hex_dump(map2kern[level], "SCSC_HEX->|",
+ print_hex_dump(map2kern[level], SCSC_PREFIX"SCSC_HEX->|",
DUMP_PREFIX_NONE, 16, 1, start, len, false);
}
}
}
EXPORT_SYMBOL(scsc_printk_bin);
+/*
+ * This is a very basic mechanism to have implement the dynamic switch
+ * for one user (currently WLAN). If multiple users are
+ * required to use the dynamic logring switch, a new registration
+ * mechanism based on requests and use_count should be implemented to avoid one service
+ * re-enabling logring when some other has requested not to do so.
+ */
+int scsc_logring_enable(bool logging_enable)
+{
+ scsc_printk_tag(FORCE_PRK, NO_TAG, "scsc_logring %s\n", logging_enable ? "enable" : "disable");
+ /* User has requested to disable logring */
+ if (!logging_enable && enable) {
+ cached_enable = true;
+ enable = 0;
+ scsc_printk_tag(FORCE_PRK, NO_TAG, "Logring disabled\n");
+ } else if (logging_enable && cached_enable) {
+ cached_enable = false;
+ enable = 1;
+ scsc_printk_tag(FORCE_PRK, NO_TAG, "Logring re-enabled\n");
+ } else {
+ scsc_printk_tag(FORCE_PRK, NO_TAG, "Ignored\n");
+ }
+ return 0;
+}
+EXPORT_SYMBOL(scsc_logring_enable);
+
MODULE_DESCRIPTION("SCSC Event Logger");
MODULE_AUTHOR("SLSI");
rec_len = tag_writer_string(rb->spare, tag, lev, prepend_header,
msg_head, args);
/* Line too long anyway drop */
- if (rec_len == BASE_SPARE_SZ) {
+ if (rec_len >= BASE_SPARE_SZ - SCSC_RINGREC_SZ) {
raw_spin_unlock_irqrestore(&rb->lock, flags);
return 0;
}
#ifndef __SCSC_MIF_ABS_H
#define __SCSC_MIF_ABS_H
+#ifdef CONFIG_SCSC_QOS
#include <linux/pm_qos.h>
+#endif
#include <linux/types.h>
#include <scsc/scsc_mifram.h>
#include <scsc/scsc_mx.h>
};
#endif
+#ifdef CONFIG_SCSC_QOS
struct scsc_mifqos_request {
struct pm_qos_request pm_qos_req_mif;
struct pm_qos_request pm_qos_req_int;
struct pm_qos_request pm_qos_req_cl0;
struct pm_qos_request pm_qos_req_cl1;
};
+#endif
/**
* Abstraction of the Maxwell "Memory Interface" aka MIF.
*
void (*mif_smapper_configure)(struct scsc_mif_abs *interface, u32 granularity);
u32 (*mif_smapper_get_bank_base_address)(struct scsc_mif_abs *interface, u8 bank);
#endif
+#ifdef CONFIG_SCSC_QOS
int (*mif_pm_qos_add_request)(struct scsc_mif_abs *interface, struct scsc_mifqos_request *qos_req, enum scsc_qos_config config);
int (*mif_pm_qos_update_request)(struct scsc_mif_abs *interface, struct scsc_mifqos_request *qos_req, enum scsc_qos_config config);
int (*mif_pm_qos_remove_request)(struct scsc_mif_abs *interface, struct scsc_mifqos_request *qos_req);
+#endif
};
struct device;
#include "mifintrbit.h"
#include "miframman.h"
#include "mifmboxman.h"
+#ifdef CONFIG_SCSC_SMAPPER
#include "mifsmapper.h"
+#endif
+#ifdef CONFIG_SCSC_QOS
#include "mifqos.h"
+#endif
#include "mifproc.h"
#include "mxman.h"
#include "mxproc.h"
#include "panicmon.h"
#include "mxlog_transport.h"
#include "suspendmon.h"
+
+#include "scsc/api/bt_audio.h"
#ifdef CONFIG_SCSC_WLBTD
#include "scsc_wlbtd.h"
#endif
struct miframman ram;
struct miframman ram2;
struct mifmboxman mbox;
+ struct mifabox mifabox;
#ifdef CONFIG_SCSC_SMAPPER
struct mifsmapper smapper;
#endif
+#ifdef CONFIG_SCSC_QOS
struct mifqos qos;
+#endif
struct mifproc proc;
struct mxman mxman;
struct srvman srvman;
return &mx->ram2;
}
+struct mifabox *scsc_mx_get_aboxram(struct scsc_mx *mx)
+{
+ return &mx->mifabox;
+}
+
struct mifmboxman *scsc_mx_get_mboxman(struct scsc_mx *mx)
{
return &mx->mbox;
}
#endif
+#ifdef CONFIG_SCSC_QOS
struct mifqos *scsc_mx_get_qos(struct scsc_mx *mx)
{
return &mx->qos;
}
+#endif
struct device *scsc_mx_get_device(struct scsc_mx *mx)
{
struct mifmuxman *scsc_mx_get_muxman(struct scsc_mx *mx);
struct miframman *scsc_mx_get_ramman(struct scsc_mx *mx);
struct miframman *scsc_mx_get_ramman2(struct scsc_mx *mx);
+struct mifabox *scsc_mx_get_aboxram(struct scsc_mx *mx);
struct mifmboxman *scsc_mx_get_mboxman(struct scsc_mx *mx);
#ifdef CONFIG_SCSC_SMAPPER
struct mifsmapper *scsc_mx_get_smapper(struct scsc_mx *mx);
#endif
+#ifdef CONFIG_SCSC_QOS
struct mifqos *scsc_mx_get_qos(struct scsc_mx *mx);
+#endif
struct device *scsc_mx_get_device(struct scsc_mx *mx);
struct mxman *scsc_mx_get_mxman(struct scsc_mx *mx);
struct srvman *scsc_mx_get_srvman(struct scsc_mx *mx);
SCSC_RELEASE_ITERATION,
SCSC_RELEASE_CANDIDATE,
SCSC_RELEASE_POINT);
-#ifdef CONFIG_SCSC_WLBTD
- scsc_wlbtd_get_and_print_build_type();
-#endif
scsc_mif_abs_register(&mx_module_mif_if);
return 0;
#include <linux/module.h>
#include <linux/version.h>
#include <linux/firmware.h>
+#ifdef CONFIG_ANDROID
#include <linux/wakelock.h>
+#endif
#include <scsc/scsc_mx.h>
#include <scsc/scsc_logring.h>
#ifdef CONFIG_SCSC_SMAPPER
#include "mifsmapper.h"
#endif
+#ifdef CONFIG_SCSC_QOS
#include "mifqos.h"
+#endif
#include "mxlogger.h"
#include "srvman.h"
#include "servman_messages.h"
#define reinit_completion(completion) INIT_COMPLETION(*(completion))
#endif
-
-
struct scsc_service {
struct list_head list;
struct scsc_mx *mx;
mutex_init(&srvman->service_list_mutex);
mutex_init(&srvman->api_access_mutex);
+#ifdef CONFIG_ANDROID
wake_lock_init(&srvman->sm_wake_lock, WAKE_LOCK_SUSPEND, "srvman_wakelock");
+#endif
}
void srvman_deinit(struct srvman *srvman)
mutex_destroy(&srvman->api_access_mutex);
mutex_destroy(&srvman->service_list_mutex);
+#ifdef CONFIG_ANDROID
wake_lock_destroy(&srvman->sm_wake_lock);
+#endif
}
void srvman_set_error(struct srvman *srvman)
/* Send to FW in MM stream */
mxmgmt_transport_send(mxmgmt_transport, MMTRANS_CHAN_ID_SERVICE_MANAGEMENT, &message, sizeof(message));
r = wait_for_sm_msg_start_cfm(service);
- if (r)
+ if (r) {
SCSC_TAG_ERR(MXMAN, "wait_for_sm_msg_start_cfm() failed: r=%d\n", r);
+
+ /* Report the error in order to get a moredump. Avoid auto-recovering this type of failure */
+ if (mxman_recovery_disabled())
+ scsc_mx_service_service_failed(service, "SM_MSG_START_CFM timeout");
+ }
return r;
}
return 0;
#endif
mutex_lock(&srvman->api_access_mutex);
+#ifdef CONFIG_ANDROID
wake_lock(&srvman->sm_wake_lock);
+#endif
if (srvman->error) {
tval = ns_to_timeval(mxman->last_panic_time);
SCSC_TAG_ERR(MXMAN, "error: refused due to previous f/w failure scsc_panic_code=0x%x happened at [%6lu.%06ld]\n",
/* Print the last panic record to help track ancient failures */
mxman_show_last_panic(mxman);
+#ifdef CONFIG_ANDROID
wake_unlock(&srvman->sm_wake_lock);
+#endif
mutex_unlock(&srvman->api_access_mutex);
return -EILSEQ;
}
r = send_sm_msg_start_blocking(service, ref);
if (r) {
SCSC_TAG_ERR(MXMAN, "send_sm_msg_start_blocking() failed: r=%d\n", r);
+#ifdef CONFIG_ANDROID
wake_unlock(&srvman->sm_wake_lock);
+#endif
mutex_unlock(&srvman->api_access_mutex);
return r;
}
+#ifdef CONFIG_ANDROID
wake_unlock(&srvman->sm_wake_lock);
+#endif
mutex_unlock(&srvman->api_access_mutex);
return 0;
}
return 0;
#endif
mutex_lock(&srvman->api_access_mutex);
+#ifdef CONFIG_ANDROID
wake_lock(&srvman->sm_wake_lock);
+#endif
if (srvman->error) {
tval = ns_to_timeval(mxman->last_panic_time);
SCSC_TAG_ERR(MXMAN, "error: refused due to previous f/w failure scsc_panic_code=0x%x happened at [%6lu.%06ld]\n",
/* Print the last panic record to help track ancient failures */
mxman_show_last_panic(mxman);
+#ifdef CONFIG_ANDROID
wake_unlock(&srvman->sm_wake_lock);
+#endif
mutex_unlock(&srvman->api_access_mutex);
/* Return a special status to allow caller recovery logic to know
r = send_sm_msg_stop_blocking(service);
if (r) {
SCSC_TAG_ERR(MXMAN, "send_sm_msg_stop_blocking() failed: r=%d\n", r);
+#ifdef CONFIG_ANDROID
wake_unlock(&srvman->sm_wake_lock);
+#endif
mutex_unlock(&srvman->api_access_mutex);
return -EIO; /* operation failed */
}
+#ifdef CONFIG_ANDROID
wake_unlock(&srvman->sm_wake_lock);
+#endif
mutex_unlock(&srvman->api_access_mutex);
return 0;
}
SCSC_TAG_INFO(MXMAN, "\n");
mutex_lock(&srvman->api_access_mutex);
+#ifdef CONFIG_ANDROID
wake_lock(&srvman->sm_wake_lock);
+#endif
if (srvman->error) {
tval = ns_to_timeval(mxman->last_panic_time);
mxman_show_last_panic(mxman);
mutex_unlock(&srvman->api_access_mutex);
+#ifdef CONFIG_ANDROID
wake_unlock(&srvman->sm_wake_lock);
+#endif
/* Return a special status when recovery is disabled, to allow
* calling recovery logic to be aware that recovery is disabled,
kfree(service);
mxman_close(mxman);
+#ifdef CONFIG_ANDROID
wake_unlock(&srvman->sm_wake_lock);
+#endif
mutex_unlock(&srvman->api_access_mutex);
return 0;
}
SCSC_TAG_INFO(MXMAN, "\n");
mutex_lock(&srvman->api_access_mutex);
+#ifdef CONFIG_ANDROID
wake_lock(&srvman->sm_wake_lock);
+#endif
if (srvman->error) {
tval = ns_to_timeval(mxman->last_panic_time);
SCSC_TAG_ERR(MXMAN, "error: refused due to previous f/w failure scsc_panic_code=0x%x happened at [%6lu.%06ld]\n",
mxman->scsc_panic_code, tval.tv_sec, tval.tv_usec);
/* Print the last panic record to help track ancient failures */
mxman_show_last_panic(mxman);
+#ifdef CONFIG_ANDROID
wake_unlock(&srvman->sm_wake_lock);
+#endif
mutex_unlock(&srvman->api_access_mutex);
*status = -EILSEQ;
return NULL;
msecs_to_jiffies(SCSC_MX_SERVICE_RECOVERY_TIMEOUT));
if (r == 0) {
SCSC_TAG_ERR(MXMAN, "Recovery timeout\n");
+#ifdef CONFIG_ANDROID
wake_unlock(&srvman->sm_wake_lock);
+#endif
*status = -EIO;
return NULL;
}
ret = mxman_open(mxman);
if (ret) {
kfree(service);
+#ifdef CONFIG_ANDROID
wake_unlock(&srvman->sm_wake_lock);
+#endif
mutex_unlock(&srvman->api_access_mutex);
*status = ret;
return NULL;
} else
*status = -ENOMEM;
+#ifdef CONFIG_ANDROID
wake_unlock(&srvman->sm_wake_lock);
+#endif
mutex_unlock(&srvman->api_access_mutex);
return service;
EXPORT_SYMBOL(scsc_service_on_halt_ldos_off);
#endif
+struct scsc_bt_audio_abox *scsc_mx_service_get_bt_audio_abox(struct scsc_service *service)
+{
+ struct scsc_mx *mx = service->mx;
+ struct mifabox *ptr;
+
+ ptr = scsc_mx_get_aboxram(mx);
+
+ return ptr->aboxram;
+}
+
+struct mifabox *scsc_mx_service_get_aboxram(struct scsc_service *service)
+{
+ struct scsc_mx *mx = service->mx;
+ struct mifabox *ptr;
+
+ ptr = scsc_mx_get_aboxram(mx);
+
+ return ptr;
+}
+
/**
* Allocate a contiguous block of SDRAM accessible to Client Driver
*
}
EXPORT_SYMBOL(scsc_service_get_device);
+struct device *scsc_service_get_device_by_mx(struct scsc_mx *mx)
+{
+ return scsc_mx_get_device(mx);
+}
+EXPORT_SYMBOL(scsc_service_get_device_by_mx);
+
/* Force a FW panic for test purposes only */
int scsc_service_force_panic(struct scsc_service *service)
{
EXPORT_SYMBOL(scsc_service_mifsmapper_get_bank_base_address);
#endif
+#ifdef CONFIG_SCSC_QOS
int scsc_service_pm_qos_add_request(struct scsc_service *service, enum scsc_qos_config config)
{
struct scsc_mx *mx = service->mx;
return 0;
}
EXPORT_SYMBOL(scsc_service_pm_qos_remove_request);
-
+#endif
#ifdef CONFIG_SCSC_MXLOGGER
/* If there is no service/mxman associated, register the observer as global (will affect all the mx instanes)*/
/* Users of these functions should ensure that the registers/unregister functions are balanced (i.e. if observer is registed as global,
#define MAX_TIMEOUT 30000 /* in milisecounds */
/* completion to indicate when moredump is done */
-static DECLARE_COMPLETION(script_done);
+static DECLARE_COMPLETION(event_done);
static DEFINE_MUTEX(build_type_lock);
static char *build_type;
+static DEFINE_MUTEX(sable_lock);
/**
* This callback runs whenever the socket receives messages.
SCSC_TAG_ERR(WLBTD, "returned error : %u\n", status);
}
- complete(&script_done);
+ complete(&event_done);
+
return 0;
}
SCSC_TAG_ERR(WLBTD, "returned error : %u\n", status);
}
- complete(&script_done);
+ complete(&event_done);
+
return 0;
}
/* The netlink family */
static struct genl_family scsc_nlfamily = {
.id = 0, /* Don't bother with a hardcoded ID */
- .name = "scsc_nl_family", /* Have users key off the name instead */
+ .name = "scsc_mdp_family", /* Have users key off the name instead */
.hdrsize = 0, /* No private header */
.version = 1,
.maxattr = __ATTR_MAX,
unsigned long completion_jiffies = 0;
unsigned long max_timeout_jiffies = msecs_to_jiffies(MAX_TIMEOUT);
+ mutex_lock(&sable_lock);
SCSC_TAG_INFO(WLBTD, "start:trigger - %s\n", trigger);
skb = nlmsg_new(NLMSG_GOODSIZE, GFP_KERNEL);
SCSC_TAG_INFO(WLBTD, "waiting for completion\n");
/* wait for script to finish */
- completion_jiffies = wait_for_completion_timeout(&script_done,
+ completion_jiffies = wait_for_completion_timeout(&event_done,
max_timeout_jiffies);
if (completion_jiffies) {
-
completion_jiffies = max_timeout_jiffies - completion_jiffies;
SCSC_TAG_INFO(WLBTD, "sable generated in %dms\n",
(int)jiffies_to_msecs(completion_jiffies) ? : 1);
SCSC_TAG_ERR(WLBTD, "wait for completion timed out !\n");
/* reinit so completion can be re-used */
- reinit_completion(&script_done);
+ reinit_completion(&event_done);
SCSC_TAG_INFO(WLBTD, " end:trigger - %s\n", trigger);
+ mutex_unlock(&sable_lock);
return rc;
SCSC_TAG_INFO(WLBTD, "waiting for completion\n");
/* wait for script to finish */
- completion_jiffies = wait_for_completion_timeout(&script_done,
+ completion_jiffies = wait_for_completion_timeout(&event_done,
max_timeout_jiffies);
- if (completion_jiffies != max_timeout_jiffies) {
+ if (completion_jiffies) {
completion_jiffies = max_timeout_jiffies - completion_jiffies;
SCSC_TAG_INFO(WLBTD, "done in %dms\n",
- (int)jiffies_to_msecs(completion_jiffies));
+ (int)jiffies_to_msecs(completion_jiffies) ? : 1);
} else
SCSC_TAG_ERR(WLBTD, "wait for completion timed out !\n");
/* reinit so completion can be re-used */
- reinit_completion(&script_done);
+ reinit_completion(&event_done);
SCSC_TAG_DEBUG(WLBTD, "end\n");
return -1;
}
- init_completion(&script_done);
+ init_completion(&event_done);
return r;
}
};
static const struct genl_multicast_group scsc_mcgrp[] = {
- { .name = "scsc_mc_grp", },
+ { .name = "scsc_mdp_grp", },
};
int scsc_wlbtd_init(void);
#ifndef _SRVMAN_H
#define _SRVMAN_H
+#ifdef CONFIG_ANDROID
#include <linux/wakelock.h>
+#endif
struct srvman;
struct mutex service_list_mutex;
struct mutex api_access_mutex;
bool error;
+#ifdef CONFIG_ANDROID
struct wake_lock sm_wake_lock;
+#endif
};
ccflags-y += $(CONFIG_SAMSUNG_MAXWELL_EXTRA)
## See sibling scsc/ Makefile for an explanation of the reasons of
## the following ifeq/else
-ifeq ($(CONFIG_SCSC_DEBUG), m)
+ifeq ($(CONFIG_SCSC_LOGRING), m)
ccflags-y += -DCONFIG_SCSC_PRINTK
else
-ccflags-$(CONFIG_SCSC_DEBUG) += -DCONFIG_SCSC_PRINTK
+ccflags-$(CONFIG_SCSC_LOGRING) += -DCONFIG_SCSC_PRINTK
endif
ifeq ($(CONFIG_SCSC_BT_BLUEZ), m)
#define SCSC_MODDESC "SCSC MX BT Driver"
#define SCSC_MODAUTH "Samsung Electronics Co., Ltd"
#define SCSC_MODVERSION "-devel"
-#define SCSC_BT_LOGGER "/system/bin/bt_dump.sh"
#define SLSI_BT_SERVICE_CLOSE_RETRY 60
#define SLSI_BT_SERVICE_STOP_RECOVERY_TIMEOUT 20000
static bool firmware_control_reset = true;
static u32 firmware_mxlog_filter;
static bool disable_service;
-static bool call_usermode_helper;
-static char *envp[] = { "HOME=/", "PATH=/system/bin:/sbin:", NULL };
-static char *argv[] = { SCSC_BT_LOGGER, NULL };
/* Audio */
static struct device *audio_device;
+static struct device *previous_audio_device;
static bool audio_device_probed;
+static bool audio_device_been_probed;
static struct scsc_bt_audio bt_audio;
module_param(bluetooth_address, ullong, S_IRUGO | S_IWUSR);
MODULE_PARM_DESC(disable_service,
"Disables service startup");
-module_param(call_usermode_helper, bool, S_IRUGO | S_IWUSR);
-MODULE_PARM_DESC(call_usermode_helper, "Allows the call to the usermode helper");
-
/*
* Service event callbacks called from mx-core when things go wrong
*/
bt_recovery_in_progress = 1;
atomic_inc(&bt_service.error_count);
+
+ /* Zero the shared memory on error. The A-Box does not stop using this
+ * memory immediately as designed. To prevent noise during recovery we zero the
+ * shared memory before freeing it
+ */
+ mutex_lock(&bt_audio_mutex);
+
+ if (bt_service.abox_ref != 0 && bt_audio.abox_virtual) {
+ memset(bt_audio.abox_virtual->abox_to_bt_streaming_if_data, 0, SCSC_BT_AUDIO_ABOX_DATA_SIZE);
+ memset(bt_audio.abox_virtual->bt_to_abox_streaming_if_data, 0, SCSC_BT_AUDIO_ABOX_DATA_SIZE);
+ }
+
+ mutex_unlock(&bt_audio_mutex);
}
static void bt_failure_reset(struct scsc_service_client *client, u16 scsc_panic_code)
};
#endif
-static void scsc_bt_invoke_usermode_helper(void)
-{
- int ret = 0;
-
- ret = call_usermodehelper(SCSC_BT_LOGGER, argv, envp, UMH_WAIT_EXEC);
- if (ret != 0)
- SCSC_TAG_ERR(BT_COMMON, "Bluetooth logger failed with error: %i\n", ret);
- else
- SCSC_TAG_INFO(BT_COMMON, "Bluetooth logger invoked successfully\n");
-}
-
static void slsi_sm_bt_service_cleanup_interrupts(void)
{
u16 int_src = bt_service.bsmhcp_protocol->header.info_bg_to_ap_int_src;
scsc_mx_service_service_failed(bt_service.service, "BT service stop failed");
SCSC_TAG_DEBUG(BT_COMMON,
"force service fail complete\n");
- return -EIO;
}
+ return -EIO;
}
return 0;
{
size_t size;
- if (audio_device == NULL || bt_audio.dev_iommu_unmap == NULL)
+ if (previous_audio_device == NULL || bt_audio.dev_iommu_unmap == NULL)
return;
size = PAGE_ALIGN(sizeof(*bt_audio.abox_physical));
- bt_audio.dev_iommu_unmap(audio_device, size);
+ bt_audio.dev_iommu_unmap(previous_audio_device, size);
+ previous_audio_device = NULL;
}
#ifdef CONFIG_SCSC_LOG_COLLECTION
mutex_lock(&bt_audio_mutex);
if (audio_device) {
- if (audio_device_probed)
- slsi_bt_audio_remove();
-
bt_audio.dev = NULL;
bt_audio.abox_virtual = NULL;
bt_audio.abox_physical = NULL;
* only if the physical start address of the 4MB region is aligned
* to 4kB (which maybe will be always the case).
*/
- err = scsc_mx_service_mifram_alloc(bt_service.service,
- sizeof(struct scsc_bt_audio_abox),
- &bt_service.abox_ref,
- SCSC_BT_AUDIO_PAGE_SIZE);
+
+ /* unmap previously mapped memory if necessary */
+ if (audio_device_been_probed) {
+ slsi_bt_audio_remove();
+ /* audio_device_been_probed is always true once set */
+ }
+
+ err = scsc_mx_service_mif_ptr_to_addr(bt_service.service,
+ scsc_mx_service_get_bt_audio_abox(bt_service.service),
+ &bt_service.abox_ref);
if (err) {
- SCSC_TAG_WARNING(BT_COMMON, "mifram alloc failed\n");
+ SCSC_TAG_WARNING(BT_COMMON, "scsc_mx_service_mif_ptr_to_addr failed\n");
err = -EINVAL;
goto exit;
}
+ /* irrespective of the technical definition of probe - wrt to memory allocation it has been */
+ audio_device_been_probed = true;
+ /* ...and this is the audio_device it was associated with */
+ previous_audio_device = audio_device;
bt_audio.abox_virtual = (struct scsc_bt_audio_abox *)
scsc_mx_service_mif_addr_to_ptr(
ret = slsi_sm_bt_service_start();
if (0 == ret)
bt_service.h4_users = true;
- else if (call_usermode_helper) {
- scsc_bt_invoke_usermode_helper();
- call_usermode_helper = false;
- }
} else {
- if (call_usermode_helper) {
- scsc_bt_invoke_usermode_helper();
- call_usermode_helper = false;
- }
ret = -EBUSY;
}
ret = slsi_sm_ant_service_start();
if (ret == 0)
ant_service.ant_users = true;
- else if (call_usermode_helper) {
- scsc_bt_invoke_usermode_helper();
- call_usermode_helper = false;
- }
} else {
- if (call_usermode_helper) {
- scsc_bt_invoke_usermode_helper();
- call_usermode_helper = false;
- }
ret = -EBUSY;
}
mutex_lock(&bt_audio_mutex);
if (audio_device != NULL && dev == audio_device) {
- if (audio_device_probed)
- slsi_bt_audio_remove();
-
bt_audio.dev = NULL;
bt_audio.abox_virtual = NULL;
bt_audio.abox_physical = NULL;
* - cte type : 1 octet
* - Slot durations : 1 octet
* - packet_status : 1 octet
+ * - event_counter : 2 octets
* - Sample count : 1 octet
*********************************
- * Total : 15 octets
+ * Total : 17 octets
*
* The maximum hci event size in bytes is:
- * (15 + (number of samples * 2 (both I and Q)))
+ * (17 + (number of samples * 2 (both I and Q)))
*
*/
-#define HCI_IQ_REPORT_MAX_LEN (15 + (2 * HCI_IQ_REPORTING_MAX_NUM_SAMPLES))
+#define HCI_IQ_REPORT_MAX_LEN (17 + (2 * HCI_IQ_REPORTING_MAX_NUM_SAMPLES))
#define HCI_LE_CONNECTIONLESS_IQ_REPORT_EVENT_SUB_CODE (0x15)
#define HCI_LE_CONNECTION_IQ_REPORT_EVENT_SUB_CODE (0x16)
h4_iq_report_evt[index++] = td->cte_type;
h4_iq_report_evt[index++] = td->slot_durations;
h4_iq_report_evt[index++] = td->packet_status;
+ h4_iq_report_evt[index++] = td->event_count & 0xFF;
+ h4_iq_report_evt[index++] = (td->event_count >> 8) & 0xFF;
h4_iq_report_evt[index++] = td->sample_count;
/* Total length of hci event */
bool gen_bg_int = false;
bool gen_fg_int = false;
+ if (len == 0)
+ return 0;
+
/* Only 1 reader is allowed */
if (1 != atomic_inc_return(&bt_service.h4_readers)) {
atomic_dec(&bt_service.h4_readers);
bt_service.bsmhcp_protocol->header.mailbox_acl_rx_read ||
bt_service.bsmhcp_protocol->header.mailbox_acl_free_write !=
bt_service.bsmhcp_protocol->header.mailbox_acl_free_read ||
+ bt_service.bsmhcp_protocol->header.mailbox_iq_report_write !=
+ bt_service.bsmhcp_protocol->header.mailbox_iq_report_read ||
(bt_service.read_operation != BT_READ_OP_NONE &&
bt_service.read_operation != BT_READ_OP_STOP) ||
((BT_READ_OP_STOP != bt_service.read_operation) &&
This option enables the Enhanced Logging
Feature.
+config SCSC_WLAN_ACM_API
+ bool "Provide TSF read API"
+ default n
+ ---help---
+ This option provides API to read TSF.
+
endif
config SCSC_WLAN_MAC_ADDRESS_FILENAME
---help---
This option tells if wifi sharing is supported or not.
+config SCSC_WLAN_ENABLE_MAC_RANDOMISATION
+ bool "Wifi Mac Randomization Support"
+ default n
+ ---help---
+ This option tells if mac randomization is supported or not.
+
config SCSC_WLAN_SINGLE_ANTENNA
depends on SCSC_WLAN_WIFI_SHARING
bool "Single Antenna Supported"
# PURPOSE:
# Build instructions for SCSC Wlan driver.
#
-# Copyright (c) 2016 Samsung Electronics Co., Ltd. All rights reserved
+# Copyright (c) 2018 Samsung Electronics Co., Ltd. All rights reserved
# ----------------------------------------------------------------------------
# Needed since this subdir is symlinked in the main Kernel tree
clean-files := *.o *.ko
obj-$(CONFIG_SCSC_WLAN) += scsc_wlan.o
-scsc_wlan-y += hip4.o
-scsc_wlan-y += mbulk.o
+scsc_wlan-$(CONFIG_SCSC_WLAN) += hip4.o
+scsc_wlan-$(CONFIG_SCSC_WLAN) += mbulk.o
# ----------------------------------------------------------------------------
# HIP4 sampler
# ----------------------------------------------------------------------------
ifeq ($(CONFIG_SCSC_WLAN_HIP4_PROFILING),y)
-scsc_wlan-y += hip4_sampler.o
+scsc_wlan-$(CONFIG_SCSC_WLAN) += hip4_sampler.o
endif
scsc_wlan-$(CONFIG_SCSC_SMAPPER) += hip4_smapper.o
# Upper driver
-scsc_wlan-y += dev.o
-scsc_wlan-y += cfg80211_ops.o
-scsc_wlan-y += netif.o
-scsc_wlan-y += rx.o
-scsc_wlan-y += tx.o
-scsc_wlan-y += ba.o
+scsc_wlan-$(CONFIG_SCSC_WLAN) += dev.o
+scsc_wlan-$(CONFIG_SCSC_WLAN) += cfg80211_ops.o
+scsc_wlan-$(CONFIG_SCSC_WLAN) += netif.o
+scsc_wlan-$(CONFIG_SCSC_WLAN) += rx.o
+scsc_wlan-$(CONFIG_SCSC_WLAN) += tx.o
+scsc_wlan-$(CONFIG_SCSC_WLAN) += ba.o
# SAPs
-scsc_wlan-y += sap_mlme.o
-scsc_wlan-y += sap_ma.o
-scsc_wlan-y += sap_dbg.o
-scsc_wlan-y += sap_test.o
+scsc_wlan-$(CONFIG_SCSC_WLAN) += sap_mlme.o
+scsc_wlan-$(CONFIG_SCSC_WLAN) += sap_ma.o
+scsc_wlan-$(CONFIG_SCSC_WLAN) += sap_dbg.o
+scsc_wlan-$(CONFIG_SCSC_WLAN) += sap_test.o
# ----------------------------------------------------------------------------
# Common Driver Files
# ----------------------------------------------------------------------------
-scsc_wlan-y += mib.o
-scsc_wlan-y += mib_text_convert.o
-scsc_wlan-y += debug.o
-scsc_wlan-y += debug_frame.o
-scsc_wlan-y += procfs.o
-scsc_wlan-y += mgt.o
-scsc_wlan-y += mlme.o
-scsc_wlan-y += udi.o
-scsc_wlan-y += log_clients.o
-scsc_wlan-y += src_sink.o
-scsc_wlan-y += fw_test.o
-scsc_wlan-y += cac.o
-scsc_wlan-y += scsc_wifi_fcq.o
-scsc_wlan-y += ioctl.o
-scsc_wlan-y += wakelock.o
-scsc_wlan-y += traffic_monitor.o
+scsc_wlan-$(CONFIG_SCSC_WLAN) += mib.o
+scsc_wlan-$(CONFIG_SCSC_WLAN) += mib_text_convert.o
+scsc_wlan-$(CONFIG_SCSC_WLAN) += debug.o
+scsc_wlan-$(CONFIG_SCSC_WLAN) += debug_frame.o
+scsc_wlan-$(CONFIG_SCSC_WLAN) += procfs.o
+scsc_wlan-$(CONFIG_SCSC_WLAN) += mgt.o
+scsc_wlan-$(CONFIG_SCSC_WLAN) += mlme.o
+scsc_wlan-$(CONFIG_SCSC_WLAN) += udi.o
+scsc_wlan-$(CONFIG_SCSC_WLAN) += log_clients.o
+scsc_wlan-$(CONFIG_SCSC_WLAN) += src_sink.o
+scsc_wlan-$(CONFIG_SCSC_WLAN) += fw_test.o
+scsc_wlan-$(CONFIG_SCSC_WLAN) += cac.o
+scsc_wlan-$(CONFIG_SCSC_WLAN) += scsc_wifi_fcq.o
+scsc_wlan-$(CONFIG_SCSC_WLAN) += ioctl.o
+scsc_wlan-$(CONFIG_SCSC_WLAN) += wakelock.o
+scsc_wlan-$(CONFIG_SCSC_WLAN) += traffic_monitor.o
+
+# ----------------------------------------------------------------------------
+# ACM
+# ----------------------------------------------------------------------------
+ifeq ($(CONFIG_SCSC_WLAN_ACM_API),y)
+scsc_wlan-$(CONFIG_SCSC_WLAN) += acm_api.o
+endif
# ----------------------------------------------------------------------------
# Building for Hardware
# ----------------------------------------------------------------------------
-scsc_wlan-y += hip.o
-scsc_wlan-y += cm_if.o
+scsc_wlan-$(CONFIG_SCSC_WLAN) += hip.o
+scsc_wlan-$(CONFIG_SCSC_WLAN) += cm_if.o
ifeq ($(CONFIG_SCSC_WLAN_KIC_OPS),y)
-scsc_wlan-y += kic.o
+scsc_wlan-$(CONFIG_SCSC_WLAN) += kic.o
endif
ccflags-$(CONFIG_SCSC_WLAN_KIC_OPS) += -DCONFIG_SCSC_WLAN_KIC_OPS
ifeq ($(CONFIG_SCSC_WLAN_GSCAN_ENABLE),y)
-scsc_wlan-y += nl80211_vendor.o
+scsc_wlan-$(CONFIG_SCSC_WLAN) += nl80211_vendor.o
ccflags-y += -DCONFIG_SCSC_WLAN_GSCAN_ENABLE
endif
ifeq ($(CONFIG_SCSC_WLAN_KEY_MGMT_OFFLOAD),y)
ccflags-y += -DCONFIG_SCSC_WLAN_KEY_MGMT_OFFLOAD
endif
+
# ---------------------------------------------------------------------------
# Include
# ---------------------------------------------------------------------------
-ccflags-y += -Idrivers/misc/samsung/scsc
-ccflags-y += -Iinclude/scsc
-ccflags-y += $(CONFIG_SAMSUNG_MAXWELL_EXTRA)
-ccflags-y += -I$(src)
+# TODO: This is only required because scsc_wifilogger is in the wrong driver directory
+ccflags-y += -Idrivers/misc/samsung/scsc
# ----------------------------------------------------------------------------
# Wlan configuration
ccflags-$(CONFIG_SCSC_WLAN_BLOCK_IPV6) += -DCONFIG_SCSC_WLAN_BLOCK_IPV6
ccflags-$(CONFIG_SCSC_WLAN_DISABLE_NAT_KA) += -DCONFIG_SCSC_WLAN_DISABLE_NAT_KA
+ccflags-y += $(CONFIG_SAMSUNG_MAXWELL_EXTRA)
ccflags-y += -DCONFIG_SCSC_WLAN_MAX_INTERFACES=$(CONFIG_SCSC_WLAN_MAX_INTERFACES)
# Android specific build options
## See drivers/misc/samsung/scsc/ Makefile for an explanation of the reasons
## of the following ifeq/else
-ifeq ($(CONFIG_SCSC_DEBUG), m)
+ifeq ($(CONFIG_SCSC_LOGRING), m)
ccflags-y += -DCONFIG_SCSC_PRINTK
else
-ccflags-$(CONFIG_SCSC_DEBUG) += -DCONFIG_SCSC_PRINTK
+ccflags-$(CONFIG_SCSC_LOGRING) += -DCONFIG_SCSC_PRINTK
endif
--- /dev/null
+/*****************************************************************************
+ *
+ * Copyright (c) 2012 - 2018 Samsung Electronics Co., Ltd. All rights reserved
+ *
+ ****************************************************************************/
+
+#include <linux/netdevice.h>
+#include "mlme.h"
+#include "mib.h"
+#include "debug.h"
+/* PSID Hdr(4) + VLDATA Hdr(1) + TSF(8) * + padding(1)*/
+#define TSF_RESP_SIZE (14)
+
+unsigned long long SDA_getTsf(const unsigned char if_id)
+{
+ struct net_device *dev = NULL;
+ struct netdev_vif *ndev_vif = NULL;
+ struct slsi_dev *sdev = NULL;
+ struct slsi_mib_data mibreq = { 0, NULL };
+ struct slsi_mib_data mibrsp = { 0, NULL };
+ /* Alloc buffer in stack to avoid possible scheduling when malloc.*/
+ u8 res_payload[TSF_RESP_SIZE] = { 0 };
+ int r = 0;
+ int rx_length = 0;
+ unsigned long long ret = 0;
+
+ read_lock(&dev_base_lock);
+ dev = first_net_device(&init_net);
+ while (dev) {
+ if (if_id == 0 && !dev->name && memcmp(dev->name, "wlan0", 5) == 0)
+ break;
+ else if (if_id == 1 && !dev->name && memcmp(dev->name, "p2p0", 4) == 0)
+ break;
+ dev = next_net_device(dev);
+ }
+ read_unlock(&dev_base_lock);
+
+ if (!dev) {
+ SLSI_ERR(sdev, "dev is null\n");
+ return 0;
+ }
+ ndev_vif = netdev_priv(dev);
+ if (!ndev_vif) {
+ SLSI_ERR(sdev, "ndev_vif is null\n");
+ return 0;
+ }
+ sdev = ndev_vif->sdev;
+ if (!sdev) {
+ SLSI_ERR(sdev, "sdev is null\n");
+ return 0;
+ }
+
+ SLSI_DBG3(sdev, SLSI_MLME, "\n");
+ slsi_mib_encode_get(&mibreq, SLSI_PSID_UNIFI_CURRENT_TSF_TIME, 0);
+ mibrsp.dataLength = sizeof(res_payload);
+ mibrsp.data = res_payload;
+
+ r = slsi_mlme_get(sdev, dev, mibreq.data, mibreq.dataLength, mibrsp.data, mibrsp.dataLength, &rx_length);
+
+ kfree(mibreq.data);
+
+ if (r == 0) {
+ mibrsp.dataLength = rx_length;
+ if (rx_length == 0) {
+ SLSI_ERR(sdev, "Mib decode error\n");
+ return 0;
+ }
+ slsi_mib_decodeInt64(&mibrsp.data[4], &ret);
+ } else {
+ SLSI_ERR(sdev, "Mib read failed (error: %d)\n", r);
+ return 0;
+ }
+ return ret;
+}
struct sk_buff *skb;
while ((skb = slsi_skb_dequeue(&ndev_vif->ba_complete)) != NULL) {
-#ifdef CONFIG_SCSC_WLAN_RX_NAPI
- slsi_rx_data_napi(ndev_vif->sdev, dev, skb, true);
-#else
- slsi_rx_data(ndev_vif->sdev, dev, skb, true);
-#endif
+ slsi_rx_data_deliver_skb(ndev_vif->sdev, dev, skb);
}
}
struct netdev_vif *ndev_vif = netdev_priv(dev);
atomic_set(&ndev_vif->ba_flush, 1);
+#ifndef CONFIG_SCSC_WLAN_RX_NAPI
slsi_skb_schedule_work(&ndev_vif->rx_data);
+#endif
}
static void ba_add_frame_to_ba_complete(struct net_device *dev, struct slsi_ba_frame_desc *frame_desc)
return i;
}
+#if KERNEL_VERSION(4, 15, 0) <= LINUX_VERSION_CODE
+static void slsi_ba_aging_timeout_handler(struct timer_list *t)
+#else
static void slsi_ba_aging_timeout_handler(unsigned long data)
+#endif
{
+#if KERNEL_VERSION(4, 15, 0) <= LINUX_VERSION_CODE
+ struct slsi_ba_session_rx *ba_session_rx = from_timer(ba_session_rx, t, ba_age_timer);
+#else
struct slsi_ba_session_rx *ba_session_rx = (struct slsi_ba_session_rx *)data;
+#endif
u8 i, j;
u8 gap = 1;
u16 temp_sn;
}
slsi_spinlock_unlock(&ba_session_rx->ba_lock);
/* Process the data now marked as completed */
+#ifdef CONFIG_SCSC_WLAN_RX_NAPI
+ slsi_ba_process_complete(dev);
+#else
slsi_ba_signal_process_complete(dev);
+#endif
} else {
slsi_spinlock_unlock(&ba_session_rx->ba_lock);
}
ba_session_rx->trigger_ba_after_ssn = false;
ba_session_rx->tid = tid;
ba_session_rx->timer_on = false;
+#if KERNEL_VERSION(4, 15, 0) <= LINUX_VERSION_CODE
+ timer_setup(&ba_session_rx->ba_age_timer, slsi_ba_aging_timeout_handler, 0);
+#else
ba_session_rx->ba_age_timer.function = slsi_ba_aging_timeout_handler;
ba_session_rx->ba_age_timer.data = (unsigned long)ba_session_rx;
init_timer(&ba_session_rx->ba_age_timer);
+#endif
ba_session_rx->active = true;
SLSI_NET_DBG1(dev, SLSI_RX_BA, "Started a new BA session tid=%d buffer_size=%d start_sn=%d\n",
ba_scroll_window(dev, ba_session_rx, sequence_number);
slsi_spinlock_unlock(&ba_session_rx->ba_lock);
-
slsi_ba_signal_process_complete(dev);
}
#include "unifiio.h"
#include "mib.h"
+#ifdef CONFIG_ANDROID
#include "scsc_wifilogger_rings.h"
+#endif
#define SLSI_MAX_CHAN_2G_BAND 14
#if (LINUX_VERSION_CODE <= KERNEL_VERSION(4, 11, 0))
SLSI_UNUSED_PARAMETER(flags);
#endif
- SLSI_NET_DBG1(dev, SLSI_CFG80211, "Intf name:%d, type:%d, macaddr:%pM\n", name, type, params->macaddr);
+ SLSI_NET_DBG1(dev, SLSI_CFG80211, "Intf name:%s, type:%d, macaddr:%pM\n", name, type, params->macaddr);
dev = slsi_new_interface_create(wiphy, name, type, params);
if (!dev)
goto exit_with_error;
if (WARN_ON(!dev))
return -EINVAL;
- SLSI_NET_DBG1(dev, SLSI_CFG80211, "Dev name:%d\n", dev->name);
+ SLSI_NET_DBG1(dev, SLSI_CFG80211, "Dev name:%s\n", dev->name);
slsi_stop_net_dev(sdev, dev);
slsi_netif_remove_rtlnl_locked(sdev, dev);
struct ieee80211_channel *channels[64];
int i, chan_count = 0;
struct cfg80211_scan_info info = {.aborted = false};
+#ifdef CONFIG_SCSC_WLAN_ENABLE_MAC_RANDOMISATION
+ u8 mac_addr_mask[ETH_ALEN] = {0xFF};
+#endif
if (WARN_ON(!request->wdev))
return -EINVAL;
ndev_vif->scan[SLSI_SCAN_HW_ID].is_blocking_scan = false;
slsi_purge_scan_results(ndev_vif, SLSI_SCAN_HW_ID);
+
+#ifdef CONFIG_SCSC_WLAN_ENABLE_MAC_RANDOMISATION
+ if (request->flags & NL80211_SCAN_FLAG_RANDOM_ADDR) {
+ memcpy(sdev->scan_mac_addr, request->mac_addr, ETH_ALEN);
+ r = slsi_set_mac_randomisation_mask(sdev, request->mac_addr_mask);
+ if (!r)
+ sdev->scan_addr_set = 1;
+ } else if (sdev->scan_addr_set == 1) {
+ memset(mac_addr_mask, 0xFF, ETH_ALEN);
+ for (i = 3; i < ETH_ALEN; i++)
+ mac_addr_mask[i] = 0x00;
+ slsi_set_mac_randomisation_mask(sdev, mac_addr_mask);
+ } else {
+ if (sdev->scan_addr_set) {
+ memset(mac_addr_mask, 0xFF, ETH_ALEN);
+ slsi_set_mac_randomisation_mask(sdev, mac_addr_mask);
+ if (!r)
+ sdev->scan_addr_set = 0;
+ }
+ }
+#endif
r = slsi_mlme_add_scan(sdev,
dev,
scan_type,
struct netdev_vif *ndev_vif = netdev_priv(dev);
SLSI_MUTEX_LOCK(ndev_vif->scan_mutex);
+
SLSI_NET_DBG1(dev, SLSI_CFG80211, "Abort on-going scan, vif_index:%d,"
- "ndev_vif->scan[SLSI_SCAN_HW_ID].scan_req:%d\n", ndev_vif->ifnum,
+ "ndev_vif->scan[SLSI_SCAN_HW_ID].scan_req:%p\n", ndev_vif->ifnum,
ndev_vif->scan[SLSI_SCAN_HW_ID].scan_req);
+
if (ndev_vif->scan[SLSI_SCAN_HW_ID].scan_req) {
(void)slsi_mlme_del_scan(sdev, dev, ndev_vif->ifnum << 8 | SLSI_SCAN_HW_ID, false);
slsi_scan_complete(sdev, dev, SLSI_SCAN_HW_ID, false);
struct ieee80211_channel *channel;
const u8 *connected_ssid = NULL;
u8 peer_address[ETH_ALEN] = { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 };
+ u16 center_freq = 0;
if (slsi_is_test_mode_enabled()) {
SLSI_NET_INFO(dev, "Skip sending signal, WlanLite FW does not support MLME_CONNECT.request\n");
if (ndev_vif->sta.sta_bss)
SLSI_ETHER_COPY(peer_address, ndev_vif->sta.sta_bss->bssid);
- SLSI_NET_DBG2(dev, SLSI_CFG80211,
- "%.*s CentFreq=%d vifStatus=%d CurrBssid:%pM NewBssid:%pM QOSinfo:%d\n",
- (int)sme->ssid_len, sme->ssid, sme->channel->center_freq, ndev_vif->sta.vif_status,
+
+ center_freq = sme->channel ? sme->channel->center_freq : 0;
+
+ SLSI_NET_INFO(dev, "%.*s CentFreq=%d vifStatus=%d CurrBssid:%pM NewBssid:%pM QOSinfo:%d\n",
+ (int)sme->ssid_len, sme->ssid, center_freq, ndev_vif->sta.vif_status,
peer_address, sme->bssid, sdev->device_config.qos_info);
+#ifdef CONFIG_SCSC_WIFILOGGER
SCSC_WLOG_PKTFATE_NEW_ASSOC();
- SCSC_WLOG_DRIVER_EVENT(WLOG_NORMAL, WIFI_EVENT_ASSOCIATION_REQUESTED, 3,
- WIFI_TAG_BSSID, ETH_ALEN, sme->bssid,
- WIFI_TAG_SSID, sme->ssid_len, sme->ssid,
- WIFI_TAG_CHANNEL, sizeof(u16), &sme->channel->center_freq);
- // ?? WIFI_TAG_VENDOR_SPECIFIC, sizeof(RSSE), RSSE);
+ if (sme->bssid) {
+ SCSC_WLOG_DRIVER_EVENT(WLOG_NORMAL, WIFI_EVENT_ASSOCIATION_REQUESTED, 3,
+ WIFI_TAG_BSSID, ETH_ALEN, sme->bssid,
+ WIFI_TAG_SSID, sme->ssid_len, sme->ssid,
+ WIFI_TAG_CHANNEL, sizeof(u16), ¢er_freq);
+ // ?? WIFI_TAG_VENDOR_SPECIFIC, sizeof(RSSE), RSSE);
+ }
+#endif
if (SLSI_IS_HS2_UNSYNC_VIF(ndev_vif)) {
- slsi_hs2_vif_deactivate(sdev, dev, true);
+ slsi_wlan_unsync_vif_deactivate(sdev, dev, true);
} else if (SLSI_IS_VIF_INDEX_P2P(ndev_vif)) {
SLSI_NET_ERR(dev, "Connect requested on incorrect vif\n");
goto exit_with_error;
peer = ndev_vif->peer_sta_record[SLSI_STA_PEER_QUEUESET];
+#ifdef CONFIG_SCSC_WIFILOGGER
SCSC_WLOG_DRIVER_EVENT(WLOG_NORMAL, WIFI_EVENT_DISASSOCIATION_REQUESTED, 2,
WIFI_TAG_BSSID, ETH_ALEN, peer->address,
WIFI_TAG_REASON_CODE, sizeof(u16), &reason_code);
+#endif
switch (ndev_vif->vif_type) {
case FAPI_VIFTYPE_STATION:
SLSI_MUTEX_LOCK(ndev_vif->vif_mutex);
- if (slsi_mlme_set_channel(sdev, dev, chandef->chan, 0, 0, 0) != 0) {
+ if (slsi_test_sap_configure_monitor_mode(sdev, dev, chandef) != 0) {
SLSI_ERR(sdev, "set Monitor channel failed\n");
SLSI_MUTEX_UNLOCK(ndev_vif->vif_mutex);
return -EINVAL;
SLSI_MUTEX_LOCK(ndev_vif->vif_mutex);
SLSI_NET_DBG2(dev, SLSI_CFG80211, "channel freq = %d, duration = %d, vif_type = %d, vif_index = %d,"
- "sdev->p2p_state = %d\n", chan->center_freq, duration, ndev_vif->vif_type, ndev_vif->ifnum,
+ "sdev->p2p_state = %s\n", chan->center_freq, duration, ndev_vif->vif_type, ndev_vif->ifnum,
slsi_p2p_state_text(sdev->p2p_state));
-
if (!SLSI_IS_VIF_INDEX_P2P(ndev_vif)) {
SLSI_NET_ERR(dev, "Invalid vif type\n");
goto exit_with_error;
SLSI_MUTEX_LOCK(ndev_vif->vif_mutex);
- SLSI_NET_DBG2(dev, SLSI_CFG80211, "Cookie = 0x%llx, vif_type = %d, vif_index = %d, sdev->p2p_state = %d,"
+ SLSI_NET_DBG2(dev, SLSI_CFG80211, "Cookie = 0x%llx, vif_type = %d, vif_index = %d, sdev->p2p_state = %s,"
"ndev_vif->ap.p2p_gc_keys_set = %d, ndev_vif->unsync.roc_cookie = 0x%llx\n", cookie,
ndev_vif->vif_type, ndev_vif->ifnum, slsi_p2p_state_text(sdev->p2p_state),
ndev_vif->ap.p2p_gc_keys_set, ndev_vif->unsync.roc_cookie);
slsi_abort_hw_scan(sdev, wlan_dev);
SLSI_NET_DBG1(dev, SLSI_CFG80211, "AP frequency received: %d\n", settings->chandef.chan->center_freq);
-#ifdef CONFIG_SCSC_WLAN_WIFI_SHARING
mgmt = (struct ieee80211_mgmt *)settings->beacon.head;
beacon_ie_head_len = settings->beacon.head_len - ((u8 *)mgmt->u.beacon.variable - (u8 *)mgmt);
+#ifdef CONFIG_SCSC_WLAN_WIFI_SHARING
ndev_sta_vif = netdev_priv(wlan_dev);
if (SLSI_IS_INTERFACE_WIFI_SHARING_AP(ndev_vif)) {
SLSI_MUTEX_LOCK(ndev_sta_vif->vif_mutex);
r = -EINVAL;
goto exit_with_vif_mutex;
}
- if ((channel->flags) & (IEEE80211_CHAN_INDOOR_ONLY)) {
- chan_flags = (IEEE80211_CHAN_INDOOR_ONLY | IEEE80211_CHAN_RADAR | IEEE80211_CHAN_DISABLED |
+ if (ndev_vif->iftype != NL80211_IFTYPE_P2P_GO) {
+ if ((channel->flags) & (IEEE80211_CHAN_INDOOR_ONLY)) {
+ chan_flags = (IEEE80211_CHAN_INDOOR_ONLY | IEEE80211_CHAN_RADAR |
+ IEEE80211_CHAN_DISABLED |
#if LINUX_VERSION_CODE <= KERNEL_VERSION(3, 10, 13)
- IEEE80211_CHAN_PASSIVE_SCAN
+ IEEE80211_CHAN_PASSIVE_SCAN
#else
- IEEE80211_CHAN_NO_IR
-#endif
- );
-
- for (i = 0; i < wiphy->bands[NL80211_BAND_5GHZ]->n_channels; i++) {
- if (!(wiphy->bands[NL80211_BAND_5GHZ]->channels[i].flags & chan_flags)) {
- center_freq = wiphy->bands[NL80211_BAND_5GHZ]->channels[i].center_freq;
- settings->chandef.chan = ieee80211_get_channel(wiphy, center_freq);
- settings->chandef.center_freq1 = center_freq;
- SLSI_DBG1(sdev, SLSI_CFG80211, "ap valid frequency :%d, chan_flags:%x\n",
- center_freq, wiphy->bands[NL80211_BAND_5GHZ]->channels[i].flags);
- indoor_channel = 1;
- break;
+ IEEE80211_CHAN_NO_IR
+#endif
+ );
+
+ for (i = 0; i < wiphy->bands[NL80211_BAND_5GHZ]->n_channels; i++) {
+ if (!(wiphy->bands[NL80211_BAND_5GHZ]->channels[i].flags & chan_flags)) {
+ center_freq = wiphy->bands[NL80211_BAND_5GHZ]->channels[i].center_freq;
+ settings->chandef.chan = ieee80211_get_channel(wiphy, center_freq);
+ settings->chandef.center_freq1 = center_freq;
+ SLSI_DBG1(sdev, SLSI_CFG80211, "ap valid frequency:%d,chan_flags:%x\n",
+ center_freq,
+ wiphy->bands[NL80211_BAND_5GHZ]->channels[i].flags);
+ indoor_channel = 1;
+ break;
+ }
+ }
+ if (indoor_channel == 0) {
+ SLSI_ERR(sdev, "No valid channel found to start the AP");
+ r = -EINVAL;
+ goto exit_with_vif_mutex;
}
- }
- if (indoor_channel == 0) {
- SLSI_ERR(sdev, "No valid channel found to start the AP");
- r = -EINVAL;
- goto exit_with_vif_mutex;
}
}
}
#endif
#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 10, 9))
- if (slsi_check_channelization(sdev, ndev_vif->chandef) != 0) {
+#ifdef CONFIG_SCSC_WLAN_WIFI_SHARING
+ if (slsi_check_channelization(sdev, ndev_vif->chandef, wifi_sharing_channel_switched) != 0) {
+#else
+ if (slsi_check_channelization(sdev, ndev_vif->chandef, 0) != 0) {
+#endif
#else
if (slsi_check_channelization(sdev, ndev_vif->channel_type) != 0) {
#endif
}
#endif
-if ((indoor_channel == 1)
+ if ((indoor_channel == 1)
#ifdef CONFIG_SCSC_WLAN_WIFI_SHARING
-|| (wifi_sharing_channel_switched == 1)
+ || (wifi_sharing_channel_switched == 1)
#endif
-)
- slsi_modify_ies_on_channel_switch(dev, settings, ds_params_ie, ht_operation_ie, mgmt, beacon_ie_head_len);
-
+ ) {
+ slsi_modify_ies_on_channel_switch(dev, settings, ds_params_ie, ht_operation_ie, mgmt, beacon_ie_head_len);
+ }
ndev_vif->vif_type = FAPI_VIFTYPE_AP;
if (slsi_mlme_add_vif(sdev, dev, dev->dev_addr, device_address) != 0) {
SLSI_NET_DBG2(dev, SLSI_CFG80211, "iface_num = %d, cookie = 0x%llx, vif_index = %d, vif_type = %d,"
"sdev->p2p_state = %d, ndev_vif->mgmt_tx_data.cookie = 0x%llx, sdev->p2p_group_exp_frame = %d,"
- "sdev->hs2_state = %d\n", ndev_vif->ifnum, cookie, ndev_vif->vif_type, sdev->p2p_state,
- ndev_vif->mgmt_tx_data.cookie, sdev->p2p_group_exp_frame, sdev->hs2_state);
+ "sdev->wlan_unsync_vif_state = %d\n", ndev_vif->ifnum, cookie,
+ ndev_vif->vif_type, sdev->p2p_state, ndev_vif->mgmt_tx_data.cookie,
+ sdev->p2p_group_exp_frame, sdev->wlan_unsync_vif_state);
/* If device was in frame tx_rx state, clear mgmt tx data and change state */
if ((sdev->p2p_state == P2P_ACTION_FRAME_TX_RX) && (ndev_vif->mgmt_tx_data.cookie == cookie)) {
} else if ((SLSI_IS_P2P_GROUP_STATE(sdev)) && (sdev->p2p_group_exp_frame != SLSI_P2P_PA_INVALID)) {
/* acquire mutex lock if it is not group net dev */
slsi_clear_offchannel_data(sdev, (!SLSI_IS_VIF_INDEX_P2P_GROUP(ndev_vif)) ? true : false);
- } else if ((sdev->hs2_state == HS2_VIF_TX) && (ndev_vif->mgmt_tx_data.cookie == cookie)) {
- sdev->hs2_state = HS2_VIF_ACTIVE;
+ } else if ((sdev->wlan_unsync_vif_state == WLAN_UNSYNC_VIF_TX) && (ndev_vif->mgmt_tx_data.cookie == cookie)) {
+ sdev->wlan_unsync_vif_state = WLAN_UNSYNC_VIF_ACTIVE;
cancel_delayed_work(&ndev_vif->unsync.hs2_del_vif_work);
queue_delayed_work(sdev->device_wq, &ndev_vif->unsync.hs2_del_vif_work, msecs_to_jiffies(SLSI_HS2_UNSYNC_VIF_EXTRA_MSEC));
}
SLSI_UNUSED_PARAMETER(sdev);
}
-static int slsi_hs2_mgmt_tx(struct slsi_dev *sdev, struct net_device *dev,
+static int slsi_wlan_mgmt_tx(struct slsi_dev *sdev, struct net_device *dev,
struct ieee80211_channel *chan, unsigned int wait,
const u8 *buf, size_t len, bool dont_wait_for_ack, u64 *cookie)
{
int r = 0;
struct ieee80211_mgmt *mgmt = (struct ieee80211_mgmt *)buf;
- slsi_hs2_dump_public_action_subtype(mgmt, true);
+ slsi_wlan_dump_public_action_subtype(mgmt, true);
if (!ndev_vif->activated) {
- r = slsi_hs2_vif_activate(sdev, dev, chan, wait);
+ r = slsi_wlan_unsync_vif_activate(sdev, dev, chan, wait);
if (r)
return r;
if (r)
goto exit_with_vif;
- sdev->hs2_state = HS2_VIF_TX;
+ sdev->wlan_unsync_vif_state = WLAN_UNSYNC_VIF_TX;
queue_delayed_work(sdev->device_wq, &ndev_vif->unsync.hs2_del_vif_work, msecs_to_jiffies(wait));
} else {
/* vif is active*/
r = slsi_mlme_send_frame_mgmt(sdev, dev, buf, len, FAPI_DATAUNITDESCRIPTOR_IEEE802_11_FRAME, FAPI_MESSAGETYPE_IEEE80211_ACTION, host_tag, 0, wait * 1000, 0);
if (r)
goto exit_with_vif;
- sdev->hs2_state = HS2_VIF_TX;
+ sdev->wlan_unsync_vif_state = WLAN_UNSYNC_VIF_TX;
queue_delayed_work(sdev->device_wq, &ndev_vif->unsync.hs2_del_vif_work, msecs_to_jiffies(wait));
} else if (ndev_vif->chan->hw_value == chan->hw_value) {
SLSI_NET_DBG1(dev, SLSI_CFG80211, "STA VIF is active on same channel, send GAS (ANQP) request on channel freq %d\n", chan->center_freq);
return r;
exit_with_vif:
- slsi_hs2_vif_deactivate(sdev, dev, true);
+ slsi_wlan_unsync_vif_deactivate(sdev, dev, true);
return r;
}
}
if (SLSI_IS_VIF_INDEX_WLAN(ndev_vif)) {
- r = slsi_hs2_mgmt_tx(SDEV_FROM_WIPHY(wiphy), dev, chan, wait, buf, len, dont_wait_for_ack, cookie);
+ r = slsi_wlan_mgmt_tx(SDEV_FROM_WIPHY(wiphy), dev, chan, wait, buf, len, dont_wait_for_ack, cookie);
goto exit;
}
/* TDLS support */
wiphy->flags |= WIPHY_FLAG_SUPPORTS_TDLS;
+#endif
+ /* Mac Randomization */
+#ifdef CONFIG_SCSC_WLAN_ENABLE_MAC_RANDOMISATION
+ wiphy->features |= NL80211_FEATURE_SCAN_RANDOM_MAC_ADDR;
#endif
return sdev;
}
#include "hip4_sampler.h"
#endif
-#include "../scsc/scsc_mx_impl.h" /* TODO */
#include <scsc/scsc_mx.h>
#ifdef CONFIG_SCSC_LOG_COLLECTION
#include <scsc/scsc_log_collector.h>
mx_wlan_client.suspend = wlan_suspend;
mx_wlan_client.resume = wlan_resume;
- dev = scsc_mx_get_device(mx);
+ dev = scsc_service_get_device_by_mx(mx);
/* The mutex must be released at this point since the attach
* process may call various functions including
#include <linux/kernel.h>
#include "dev.h"
+#include <scsc/scsc_logring.h>
/* Logging modules
* =======================
*/
-#ifdef CONFIG_SCSC_DEBUG_COMPATIBILITY
-#include <scsc/scsc_logring.h>
-#else
+#ifndef CONFIG_SCSC_DEBUG_COMPATIBILITY
extern const int SLSI_INIT_DEINIT;
extern const int SLSI_NETDEV;
extern const int SLSI_CFG80211;
#define SLSI_EWI_NET_DEV(ndev) (likely(ndev) ? SLSI_EWI_DEV(((struct netdev_vif *)netdev_priv(ndev))->sdev) : NULL)
#define SLSI_EWI_NET_NAME(ndev) (likely(ndev) ? netdev_name(ndev) : NULL)
-#define SLSI_EWI(output, sdev, label, fmt, arg ...) output(SLSI_EWI_DEV(sdev), " : " label ": %s: " fmt, __func__, ## arg)
-#define SLSI_EWI_NET(output, ndev, label, fmt, arg ...) output(SLSI_EWI_NET_DEV(ndev), "%-5s: " label ": %s: " fmt, SLSI_EWI_NET_NAME(ndev), __func__, ## arg)
-#define SLSI_EWI_NODEV(output, label, fmt, arg ...) output(SLSI_EWI_NODEV_LABEL label ": %s: " fmt, __func__, ## arg)
+#define SLSI_EWI(output, sdev, label, fmt, arg ...) output(SLSI_EWI_DEV(sdev), SCSC_PREFIX label ": %s: " fmt, __func__, ## arg)
+#define SLSI_EWI_NET(output, ndev, label, fmt, arg ...) output(SLSI_EWI_NET_DEV(ndev), SCSC_PREFIX "%s: " label ": %s: " fmt, SLSI_EWI_NET_NAME(ndev), __func__, ## arg)
+#define SLSI_EWI_NODEV(output, label, fmt, arg ...) output(SLSI_EWI_NODEV_LABEL SCSC_PREFIX label ": %s: " fmt, __func__, ## arg)
#define SLSI_EWI_HEX(output, klevel, sdev, label, p, len, fmt, arg ...) \
do { \
SLSI_EWI(output, sdev, label, fmt, ## arg); \
- print_hex_dump(klevel, "", DUMP_PREFIX_OFFSET, 16, 1, p, len, 0); \
+ print_hex_dump(klevel, SCSC_PREFIX, DUMP_PREFIX_OFFSET, 16, 1, p, len, 0); \
} while (0)
#define SLSI_EWI_HEX_NET(output, klevel, dev, label, p, len, fmt, arg ...) \
do { \
SLSI_EWI_NET(output, dev, label, fmt, ## arg); \
- print_hex_dump(klevel, "", DUMP_PREFIX_OFFSET, 16, 1, p, len, 0); \
+ print_hex_dump(klevel, SCSC_PREFIX, DUMP_PREFIX_OFFSET, 16, 1, p, len, 0); \
} while (0)
#define SLSI_EWI_HEX_NODEV(output, klevel, label, p, len, fmt, arg ...) \
do { \
SLSI_EWI_NODEV(output, label, fmt, ## arg); \
- print_hex_dump(klevel, "", DUMP_PREFIX_OFFSET, 16, 1, p, len, 0); \
+ print_hex_dump(klevel, SCSC_PREFIX, DUMP_PREFIX_OFFSET, 16, 1, p, len, 0); \
} while (0)
#define SLSI_ERR(sdev, fmt, arg ...) SLSI_EWI(dev_err, sdev, "E", fmt, ## arg)
static int max_scan_result_count = 200;
module_param(max_scan_result_count, int, S_IRUGO | S_IWUSR);
MODULE_PARM_DESC(max_scan_result_count, "Max scan results to be reported");
+static bool rtt_disabled = 1;
+module_param(rtt_disabled, bool, S_IRUGO | S_IWUSR);
+MODULE_PARM_DESC(rtt_disabled, "Disable rtt: to disable rtt set 1");
static bool nan_disabled;
module_param(nan_disabled, bool, S_IRUGO | S_IWUSR);
return !gscan_disabled;
}
+bool slsi_dev_rtt_supported(void)
+{
+ return !rtt_disabled;
+}
+
bool slsi_dev_llslogs_supported(void)
{
return !llslogs_disabled;
SLSI_NET_INFO(dev, "IP: %pI4\n", &ifa->ifa_address);
SLSI_MUTEX_LOCK(ndev_vif->vif_mutex);
-#ifndef SLSI_TEST_DEV
+#if !defined SLSI_TEST_DEV && defined CONFIG_ANDROID
if (SLSI_IS_VIF_INDEX_WLAN(ndev_vif) && wake_lock_active(&sdev->wlan_wl_roam)) {
SLSI_NET_DBG2(dev, SLSI_NETDEV, "Releasing the roaming wakelock\n");
wake_unlock(&sdev->wlan_wl_roam);
sdev->mlme_blocked = false;
SLSI_MUTEX_INIT(sdev->netdev_add_remove_mutex);
+ SLSI_MUTEX_INIT(sdev->netdev_remove_mutex);
SLSI_MUTEX_INIT(sdev->start_stop_mutex);
SLSI_MUTEX_INIT(sdev->device_config_mutex);
#ifdef CONFIG_SCSC_WLAN_ENHANCED_LOGGING
slsi_wakelock_init(&sdev->wlan_wl, "wlan");
slsi_wakelock_init(&sdev->wlan_wl_mlme, "wlan_mlme");
slsi_wakelock_init(&sdev->wlan_wl_ma, "wlan_ma");
-#ifndef SLSI_TEST_DEV
+#if !defined SLSI_TEST_DEV && defined CONFIG_ANDROID
wake_lock_init(&sdev->wlan_wl_roam, WAKE_LOCK_SUSPEND, "wlan_roam");
#endif
sdev->recovery_next_state = 0;
slsi_wakelock_exit(&sdev->wlan_wl);
slsi_wakelock_exit(&sdev->wlan_wl_mlme);
slsi_wakelock_exit(&sdev->wlan_wl_ma);
-#ifndef SLSI_TEST_DEV
+#if !defined SLSI_TEST_DEV && defined CONFIG_ANDROID
wake_lock_destroy(&sdev->wlan_wl_roam);
#endif
slsi_cfg80211_free(sdev);
slsi_wakelock_exit(&sdev->wlan_wl);
slsi_wakelock_exit(&sdev->wlan_wl_mlme);
slsi_wakelock_exit(&sdev->wlan_wl_ma);
-#ifndef SLSI_TEST_DEV
+#if !defined SLSI_TEST_DEV && defined CONFIG_ANDROID
wake_lock_destroy(&sdev->wlan_wl_roam);
#endif
#define SLSI_80211_MODE_11A 3
#define SLSI_80211_MODE_11AC 4
+#define SLSI_FW_API_RATE_HT_SELECTOR_FIELD 0xc000
+#define SLSI_FW_API_RATE_NON_HT_SELECTED 0x4000
+#define SLSI_FW_API_RATE_HT_SELECTED 0x8000
+#define SLSI_FW_API_RATE_VHT_SELECTED 0xc000
+
+#define SLSI_FW_API_RATE_VHT_MCS_FIELD 0x000F
+#define SLSI_FW_API_RATE_HT_MCS_FIELD 0x003F
+#define SLSI_FW_API_RATE_INDEX_FIELD 0x1fff
+#define SLSI_FW_API_RATE_VHT_NSS_FIELD 0x0070
+#define SLSI_FW_API_RATE_HT_NSS_FIELD 0x0040
+
+#define SLSI_FW_API_RATE_BW_FIELD 0x0600
+#define SLSI_FW_API_RATE_BW_40MHZ 0x0200
+#define SLSI_FW_API_RATE_BW_20MHZ 0x0000
+
+#define SLSI_FW_API_RATE_SGI 0x0100
+#define SLSI_FW_API_RATE_GF 0x0080
+
+/* indices: 3= BW20->idx_0, BW40->idx_1, BW80->idx_2.
+ * 2= noSGI->idx_0, SGI->idx_1
+ * 10= mcs index
+ * rate units 100kbps
+ * This table for single stream Nss=1and does not include 160MHz BW and 80+80MHz BW.
+ */
+static const u16 slsi_rates_table[3][2][10] = {
+ { /* BW20 */
+ { /* no SGI */
+ 65, 130, 195, 260, 390, 520, 585, 650, 780, 0
+ },
+ { /* SGI */
+ 72, 144, 217, 289, 433, 578, 650, 722, 867, 0
+ }
+ },
+ { /* BW40 */
+ { /* no SGI */
+ 135, 270, 405, 540, 810, 1080, 1215, 1350, 1620, 1800
+ },
+ { /* SGI */
+ 150, 300, 450, 600, 900, 1200, 1350, 1500, 1800, 2000
+ }
+ },
+ { /* BW80 */
+ { /* no SGI */
+ 293, 585, 878, 1170, 1755, 2340, 2633, 2925, 3510, 3900
+ },
+ { /* SGI */
+ 325, 650, 975, 1300, 1950, 2600, 2925, 3250, 3900, 4333
+ }
+ }
+};
/* MSDU subframe Header */
struct msduhdr {
unsigned char h_dest[ETH_ALEN]; /* destination eth addr */
#define NUM_BA_SESSIONS_PER_PEER 8
#define MAX_CHANNEL_LIST 20
#define SLSI_MAX_RX_BA_SESSIONS (8)
-#define SLSI_STA_ACTION_FRAME_BITMAP (SLSI_ACTION_FRAME_PUBLIC | SLSI_ACTION_FRAME_WMM | SLSI_ACTION_FRAME_WNM | SLSI_ACTION_FRAME_QOS)
+#define SLSI_STA_ACTION_FRAME_BITMAP (SLSI_ACTION_FRAME_PUBLIC | SLSI_ACTION_FRAME_WMM | SLSI_ACTION_FRAME_WNM |\
+ SLSI_ACTION_FRAME_QOS | SLSI_ACTION_FRAME_PROTECTED_DUAL)
/* Default value for MIB SLSI_PSID_UNIFI_DISCONNECT_TIMEOUT + 1 sec*/
#define SLSI_DEFAULT_AP_DISCONNECT_IND_TIMEOUT 3000
#define SLSI_AMPDU_F_CREATED (0x0002)
#define SLSI_AMPDU_F_OPERATIONAL (0x0004)
-#ifdef CONFIG_SCSC_WLAN_RX_NAPI
-struct slsi_napi {
- struct napi_struct napi;
- struct sk_buff_head rx_data;
- struct slsi_spinlock lock;
- bool interrupt_enabled;
-};
-#endif
-
#define SLSI_SCAN_HW_ID 0
#define SLSI_SCAN_SCHED_ID 1
#define SLSI_SCAN_MAX 3
ktime_t last_sample_time;
u32 last_ack_seq;
u64 num_bytes;
-
- /* corresponding socket to get stats (e.g. congestion window) */
- struct sock *tcp_sk;
-
#ifdef CONFIG_SCSC_WLAN_HIP4_PROFILING
u8 stream_id;
u8 rx_window_scale;
struct mutex vif_mutex;
#endif
struct slsi_sig_send sig_wait;
+#ifndef CONFIG_SCSC_WLAN_RX_NAPI
struct slsi_skb_work rx_data;
- struct slsi_skb_work rx_mlme;
-#ifdef CONFIG_SCSC_WLAN_RX_NAPI
- struct slsi_napi napi;
#endif
+ struct slsi_skb_work rx_mlme;
u16 ifnum;
enum nl80211_iftype iftype;
enum nl80211_channel_type channel_type;
*/
};
-enum slsi_hs2_state {
- HS2_NO_VIF = 0, /* Initial state - Unsync vif is not present */
- HS2_VIF_ACTIVE, /* Unsync vif is activated but no HS procedure in progress */
- HS2_VIF_TX /* Unsync vif is activated and HS procedure in progress */
+enum slsi_wlan_state {
+ WLAN_UNSYNC_NO_VIF = 0, /* Initial state - Unsync vif is not present */
+ WLAN_UNSYNC_VIF_ACTIVE, /* Unsync vif is activated but no wlan procedure in progress */
+ WLAN_UNSYNC_VIF_TX /* Unsync vif is activated and wlan procedure in progress */
};
/* Wakelock timeouts */
}
}
+#define SLSI_WLAN_MAX_HCF_PLATFORM_LEN (128)
+
struct slsi_dev_mib_info {
char *mib_file_name;
unsigned int mib_hash;
/* Cached File MIB Configuration values from User Space */
u8 *mib_data;
u32 mib_len;
+ char platform[SLSI_WLAN_MAX_HCF_PLATFORM_LEN];
};
#define SLSI_WLAN_MAX_MIB_FILE 2 /* Number of WLAN HCFs to load */
#ifdef CONFIG_SCSC_WLAN_MUTEX_DEBUG
struct slsi_mutex netdev_add_remove_mutex;
+ struct slsi_mutex netdev_remove_mutex;
#else
/* a std mutex */
struct mutex netdev_add_remove_mutex;
+ /* a std mutex */
+ struct mutex netdev_remove_mutex;
#endif
int netdev_up_count;
struct net_device __rcu *netdev[CONFIG_SCSC_WLAN_MAX_INTERFACES + 1]; /* 0 is reserved */
struct slsi_wake_lock wlan_wl;
struct slsi_wake_lock wlan_wl_mlme;
struct slsi_wake_lock wlan_wl_ma;
-#ifndef SLSI_TEST_DEV
+#if !defined SLSI_TEST_DEV && defined CONFIG_ANDROID
struct wake_lock wlan_wl_roam;
#endif
struct slsi_sig_send sig_wait;
struct workqueue_struct *device_wq; /* Driver Workqueue */
enum slsi_p2p_states p2p_state; /* Store current P2P operation */
- enum slsi_hs2_state hs2_state; /* Store current HS2 operations */
+ enum slsi_wlan_state wlan_unsync_vif_state; /* Store current sate of unsync wlan vif */
int current_tspec_id;
int tspec_error_code;
struct list_head hotlist_results;
bool epno_active;
#endif
-#ifdef CONFIG_SCSC_WLAN_ENABLE_MAC_OUI
- u8 scan_oui[6];
- bool scan_oui_active;
+#ifdef CONFIG_SCSC_WLAN_ENABLE_MAC_RANDOMISATION
+ u8 scan_mac_addr[6];
+ bool scan_addr_set;
#endif
#ifdef CONFIG_SCSC_WLAN_HIP4_PROFILING
int minor_prof;
#endif
#endif
struct slsi_traffic_mon_clients traffic_mon_clients;
+ /*Store vif index corresponding to rtt id for FTM*/
+ u16 rtt_vif[8];
};
/* Compact representation of channels a ESS has been seen on
#ifdef CONFIG_SCSC_WLAN_RX_NAPI
int slsi_rx_data_napi(struct slsi_dev *sdev, struct net_device *dev, struct sk_buff *skb, bool from_ba);
#endif
-int slsi_rx_data(struct slsi_dev *sdev, struct net_device *dev, struct sk_buff *skb, bool from_ba);
+void slsi_rx_data_deliver_skb(struct slsi_dev *sdev, struct net_device *dev, struct sk_buff *skb);
void slsi_rx_dbg_sap_work(struct work_struct *work);
void slsi_rx_netdev_data_work(struct work_struct *work);
void slsi_rx_netdev_mlme_work(struct work_struct *work);
bool slsi_dev_llslogs_supported(void);
int slsi_dev_nan_supported(struct slsi_dev *sdev);
void slsi_regd_init(struct slsi_dev *sdev);
+bool slsi_dev_rtt_supported(void);
static inline u16 slsi_tx_host_tag(struct slsi_dev *sdev, enum slsi_traffic_q tq)
{
#define FAPI_RTTSTATUS_FAIL_INVALID_REQUEST 0x000d
#define FAPI_RTTSTATUS_FAIL_FTM_PARAMETER_OVERRIDE 0x000f
-#define FAPI_RTTTYPE_ONE_SIDED 0x0000
-#define FAPI_RTTTYPE_TWO_SIDED 0x0001
+#define FAPI_RTTTYPE_ONE_SIDED 0x0001
+#define FAPI_RTTTYPE_TWO_SIDED 0x0002
#define FAPI_RXSTARTFLAGS_NONE 0x0000
#define FAPI_RXSTARTFLAGS_SCAN_CHANNEL 0x0001
#include <linux/ktime.h>
#include <linux/kthread.h>
#include <scsc/scsc_logring.h>
+#ifdef CONFIG_SCSC_WLAN_RX_NAPI
+#include <linux/cpu.h>
+#include <linux/bitmap.h>
+#endif
#include "hip4.h"
#include "mbulk.h"
#include "dev.h"
#include "hip4_sampler.h"
+#ifdef CONFIG_ANDROID
#include "scsc_wifilogger_rings.h"
+#endif
#include "debug.h"
+#ifdef CONFIG_SCSC_LOGRING
+static bool hip4_dynamic_logging = true;
+module_param(hip4_dynamic_logging, bool, S_IRUGO | S_IWUSR);
+MODULE_PARM_DESC(hip4_dynamic_logging, "Dynamic logging, logring is disabled if tput > hip4_qos_med_tput_in_mbps. (default: Y)");
+#endif
+
+#ifdef CONFIG_SCSC_QOS
static bool hip4_qos_enable = true;
module_param(hip4_qos_enable, bool, S_IRUGO | S_IWUSR);
MODULE_PARM_DESC(hip4_qos_enable, "enable HIP4 PM QoS. (default: Y)");
static int hip4_qos_med_tput_in_mbps = 150;
module_param(hip4_qos_med_tput_in_mbps, int, S_IRUGO | S_IWUSR);
MODULE_PARM_DESC(hip4_qos_med_tput_in_mbps, "throughput (in Mbps) to apply Median PM QoS");
+#endif
#ifdef CONFIG_SCSC_SMAPPER
static bool hip4_smapper_enable = true;
static bool hip4_smapper_is_enabled;
#endif
+#ifdef CONFIG_SCSC_WLAN_RX_NAPI
+/* run NAPI poll on a specific CPU (preferably a big CPU if online) */
+static int napi_select_cpu = 4; /* CPU number */
+module_param(napi_select_cpu, int, 0644);
+MODULE_PARM_DESC(napi_select_cpu, "select a specific CPU to execute NAPI poll");
+#endif
+
+static int max_buffered_frames = 10000;
+module_param(max_buffered_frames, int, S_IRUGO | S_IWUSR);
+MODULE_PARM_DESC(max_buffered_frames, "Maximum number of frames to buffer in the driver");
+
+#ifdef CONFIG_SCSC_WLAN_RX_NAPI
+static ktime_t intr_received_fb;
+static ktime_t bh_init_fb;
+static ktime_t bh_end_fb;
+static ktime_t intr_received_ctrl;
+static ktime_t bh_init_ctrl;
+static ktime_t bh_end_ctrl;
+static ktime_t intr_received_data;
+static ktime_t bh_init_data;
+static ktime_t bh_end_data;
+#else
static ktime_t intr_received;
static ktime_t bh_init;
static ktime_t bh_end;
+#endif
static ktime_t wdt;
static ktime_t send;
static ktime_t closing;
seq_printf(m, "ktime start %lld (ns)\n", ktime_to_ns(hip->hip_priv->stats.start));
seq_printf(m, "ktime now %lld (ns)\n\n", ktime_to_ns(ktime_get()));
- seq_printf(m, "rx_intr_tohost 0x%x\n", hip->hip_priv->rx_intr_tohost);
- seq_printf(m, "rx_intr_fromhost 0x%x\n\n", hip->hip_priv->rx_intr_fromhost);
+ seq_printf(m, "rx_intr_tohost 0x%x\n", hip->hip_priv->intr_tohost);
+ seq_printf(m, "rx_intr_fromhost 0x%x\n\n", hip->hip_priv->intr_fromhost);
/* HIP statistics */
seq_printf(m, "HIP IRQs: %u\n", atomic_read(&hip->hip_priv->stats.irqs));
seq_printf(m, "Q%dR\t0x%x\t%d\n", i, hip4_read_index(hip, i, ridx), hip->hip_priv->stats.q_num_frames[i]);
}
seq_puts(m, "\n");
-
return 0;
}
unsigned int i = 0;
scsc_mifram_ref ref;
- SLSI_ERR_NODEV("rx_intr_tohost 0x%x\n", hip->hip_priv->rx_intr_tohost);
- SLSI_ERR_NODEV("rx_intr_fromhost 0x%x\n", hip->hip_priv->rx_intr_fromhost);
+#ifdef CONFIG_SCSC_WLAN_RX_NAPI
+ SLSI_ERR_NODEV("intr_tohost_fb 0x%x\n", hip->hip_priv->intr_tohost_mul[HIP4_MIF_Q_FH_RFB]);
+ SLSI_ERR_NODEV("intr_tohost_ctrl 0x%x\n", hip->hip_priv->intr_tohost_mul[HIP4_MIF_Q_TH_CTRL]);
+ SLSI_ERR_NODEV("intr_tohost_dat 0x%x\n", hip->hip_priv->intr_tohost_mul[HIP4_MIF_Q_TH_DAT]);
+#else
+ SLSI_ERR_NODEV("intr_tohost 0x%x\n", hip->hip_priv->intr_tohost);
+#endif
+ SLSI_ERR_NODEV("intr_fromhost 0x%x\n", hip->hip_priv->intr_fromhost);
/* Print scoreboard */
for (i = 0; i < 6; i++) {
if (scsc_mx_service_mif_ptr_to_addr(service, m, &ref))
return;
SLSI_ERR_NODEV("m: %p 0x%x\n", m, ref);
- print_hex_dump(KERN_ERR, "mbulk ", DUMP_PREFIX_NONE, 16, 1, m, sizeof(struct mbulk), 0);
+ print_hex_dump(KERN_ERR, SCSC_PREFIX "mbulk ", DUMP_PREFIX_NONE, 16, 1, m, sizeof(struct mbulk), 0);
}
if (skb)
- print_hex_dump(KERN_ERR, "skb ", DUMP_PREFIX_NONE, 16, 1, skb->data, skb->len > 0xff ? 0xff : skb->len, 0);
+ print_hex_dump(KERN_ERR, SCSC_PREFIX "skb ", DUMP_PREFIX_NONE, 16, 1, skb->data, skb->len > 0xff ? 0xff : skb->len, 0);
SLSI_ERR_NODEV("time: wdt %lld\n", ktime_to_ns(wdt));
SLSI_ERR_NODEV("time: send %lld\n", ktime_to_ns(send));
+#ifdef CONFIG_SCSC_WLAN_RX_NAPI
+ SLSI_ERR_NODEV("time: intr_fb %lld\n", ktime_to_ns(intr_received_fb));
+ SLSI_ERR_NODEV("time: bh_init_fb %lld\n", ktime_to_ns(bh_init_fb));
+ SLSI_ERR_NODEV("time: bh_end_fb %lld\n", ktime_to_ns(bh_end_fb));
+ SLSI_ERR_NODEV("time: intr_ctrl %lld\n", ktime_to_ns(intr_received_ctrl));
+ SLSI_ERR_NODEV("time: bh_init_ctrl %lld\n", ktime_to_ns(bh_init_ctrl));
+ SLSI_ERR_NODEV("time: bh_end_ctrl %lld\n", ktime_to_ns(bh_end_ctrl));
+ SLSI_ERR_NODEV("time: intr_data %lld\n", ktime_to_ns(intr_received_data));
+ SLSI_ERR_NODEV("time: bh_init_data %lld\n", ktime_to_ns(bh_init_data));
+ SLSI_ERR_NODEV("time: bh_end_data %lld\n", ktime_to_ns(bh_end_data));
+#else
SLSI_ERR_NODEV("time: intr %lld\n", ktime_to_ns(intr_received));
SLSI_ERR_NODEV("time: bh_init %lld\n", ktime_to_ns(bh_init));
SLSI_ERR_NODEV("time: bh_end %lld\n", ktime_to_ns(bh_end));
+#endif
SLSI_ERR_NODEV("time: closing %lld\n", ktime_to_ns(closing));
#ifdef CONFIG_SCSC_WLAN_DEBUG
/* Discard noise if it is a mbulk/skb issue */
p = mbulk_get_signal(m);
if (!p) {
SLSI_ERR_NODEV("No signal in Mbulk\n");
- print_hex_dump(KERN_ERR, "mbulk ", DUMP_PREFIX_NONE, 16, 1, m, sizeof(struct mbulk), 0);
+ print_hex_dump(KERN_ERR, SCSC_PREFIX "mbulk ", DUMP_PREFIX_NONE, 16, 1, m, sizeof(struct mbulk), 0);
slsi_kfree_skb(skb);
return NULL;
}
hip4_update_index(hip, conf, widx, idx_w);
send = ktime_get();
- scsc_service_mifintrbit_bit_set(service, hip_priv->rx_intr_fromhost, SCSC_MIFINTR_TARGET_R4);
+ scsc_service_mifintrbit_bit_set(service, hip_priv->intr_fromhost, SCSC_MIFINTR_TARGET_R4);
return 0;
}
+#if KERNEL_VERSION(4, 15, 0) <= LINUX_VERSION_CODE
+static void hip4_watchdog(struct timer_list *t)
+#else
static void hip4_watchdog(unsigned long data)
+#endif
{
+#if KERNEL_VERSION(4, 15, 0) <= LINUX_VERSION_CODE
+ struct hip4_priv *priv = from_timer(priv, t, watchdog);
+ struct slsi_hip4 *hip = priv->hip;
+#else
struct slsi_hip4 *hip = (struct slsi_hip4 *)data;
+#endif
struct slsi_dev *sdev = container_of(hip, struct slsi_dev, hip4_inst);
struct scsc_service *service;
ktime_t intr_ov;
wdt = ktime_get();
+#ifdef CONFIG_SCSC_WLAN_RX_NAPI
+ /* if intr_received > wdt skip as intr has been unblocked */
+ if (test_and_clear_bit(HIP4_MIF_Q_FH_RFB, hip->hip_priv->irq_bitmap))
+ intr_ov = ktime_add_ms(intr_received_fb, jiffies_to_msecs(HZ));
+ if (test_and_clear_bit(HIP4_MIF_Q_TH_CTRL, hip->hip_priv->irq_bitmap))
+ intr_ov = ktime_add_ms(intr_received_ctrl, jiffies_to_msecs(HZ));
+ if (test_and_clear_bit(HIP4_MIF_Q_TH_DAT, hip->hip_priv->irq_bitmap))
+ intr_ov = ktime_add_ms(intr_received_data, jiffies_to_msecs(HZ));
+#else
/* if intr_received > wdt skip as intr has been unblocked */
if (ktime_compare(intr_received, wdt) > 0) {
wdt = ktime_set(0, 0);
goto exit;
}
- /* Check that wdt is > 1 HZ intr */
intr_ov = ktime_add_ms(intr_received, jiffies_to_msecs(HZ));
+#endif
+
+ /* Check that wdt is > 1 HZ intr */
if (!(ktime_compare(intr_ov, wdt) < 0)) {
wdt = ktime_set(0, 0);
/* Retrigger WDT to check flags again in the future */
SLSI_INFO_NODEV("Hip4 watchdog triggered\n");
- if (scsc_service_mifintrbit_bit_mask_status_get(service) & (1 << hip->hip_priv->rx_intr_tohost)) {
+#ifdef CONFIG_SCSC_WLAN_RX_NAPI
+ for (u8 i = 0; i < MIF_HIP_CFG_Q_NUM; i++) {
+ if (scsc_service_mifintrbit_bit_mask_status_get(service) & (1 << hip->hip_priv->intr_tohost_mul[i])) {
+ /* Interrupt might be pending! */
+ SLSI_INFO_NODEV("%d: Interrupt Masked. Unmask to restart Interrupt processing\n", i);
+ scsc_service_mifintrbit_bit_unmask(service, hip->hip_priv->intr_tohost_mul[i]);
+ }
+ }
+#else
+ if (scsc_service_mifintrbit_bit_mask_status_get(service) & (1 << hip->hip_priv->intr_tohost)) {
/* Interrupt might be pending! */
SLSI_INFO_NODEV("Interrupt Masked. Unmask to restart Interrupt processing\n");
- scsc_service_mifintrbit_bit_unmask(service, hip->hip_priv->rx_intr_tohost);
+ scsc_service_mifintrbit_bit_unmask(service, hip->hip_priv->intr_tohost);
}
+#endif
exit:
spin_unlock_irqrestore(&hip->hip_priv->watchdog_lock, flags);
}
-/* Tasklet: high priority, low latency atomic tasks
- * cannot sleep (run atomically in soft IRQ context and are guaranteed to
- * never run on more than one CPU of a given processor, for a given tasklet)
- */
+#ifdef CONFIG_SCSC_WLAN_RX_NAPI
+static void hip4_irq_handler_stub(int irq, void *data)
+{
+ /* should not happen */
+ WARN_ON(1);
+}
+
+static void hip4_wq_fb(struct work_struct *data)
+{
+ struct hip4_priv *hip_priv = container_of(data, struct hip4_priv, intr_wq_fb);
+ struct slsi_hip4 *hip = hip_priv->hip;
+ struct hip4_hip_control *ctrl = hip->hip_control;
+ struct scsc_service *service;
+ struct slsi_dev *sdev = container_of(hip, struct slsi_dev, hip4_inst);
+ bool no_change = true;
+ u8 idx_r;
+ u8 idx_w;
+ scsc_mifram_ref ref;
+ void *mem;
+
+ if (!hip || !sdev || !sdev->service || !hip->hip_priv)
+ return;
+
+ spin_lock_bh(&hip_priv->rx_lock);
+ service = sdev->service;
+ SCSC_HIP4_SAMPLER_INT_BH(hip->hip_priv->minor, 2);
+ bh_init_fb = ktime_get();
+ clear_bit(HIP4_MIF_Q_FH_RFB, hip->hip_priv->irq_bitmap);
+
+ idx_r = hip4_read_index(hip, HIP4_MIF_Q_FH_RFB, ridx);
+ idx_w = hip4_read_index(hip, HIP4_MIF_Q_FH_RFB, widx);
+
+#ifdef CONFIG_SCSC_WLAN_HIP4_PROFILING
+ if (idx_r != idx_w) {
+ SCSC_HIP4_SAMPLER_Q(hip_priv->minor, HIP4_MIF_Q_FH_RFB, ridx, idx_r, 1);
+ SCSC_HIP4_SAMPLER_Q(hip_priv->minor, HIP4_MIF_Q_FH_RFB, widx, idx_w, 1);
+ }
+#endif
+ while (idx_r != idx_w) {
+ struct mbulk *m;
+ u16 colour;
+
+ no_change = false;
+ ref = ctrl->q[HIP4_MIF_Q_FH_RFB].array[idx_r];
+#ifdef CONFIG_SCSC_WLAN_HIP4_PROFILING
+ SCSC_HIP4_SAMPLER_QREF(hip_priv->minor, ref, HIP4_MIF_Q_FH_RFB);
+#endif
+ mem = scsc_mx_service_mif_addr_to_ptr(service, ref);
+ m = (struct mbulk *)mem;
+
+ if (!m) {
+ SLSI_ERR_NODEV("FB: Mbulk is NULL\n");
+ goto consume_fb_mbulk;
+ }
+ /* colour is defined as: */
+ /* u16 register bits:
+ * 0 - do not use
+ * [2:1] - vif
+ * [7:3] - peer_index
+ * [10:8] - ac queue
+ */
+ colour = ((m->clas & 0xc0) << 2) | (m->pid & 0xfe);
+ /* Account ONLY for data RFB */
+ if ((m->pid & 0x1) == MBULK_CLASS_FROM_HOST_DAT) {
+#ifdef CONFIG_SCSC_WLAN_HIP4_PROFILING
+ SCSC_HIP4_SAMPLER_VIF_PEER(hip->hip_priv->minor, 0, (colour & 0x6) >> 1, (colour & 0xf8) >> 3);
+ /* to profile round-trip */
+ {
+ u16 host_tag;
+ u8 *get_host_tag;
+ /* This is a nasty way of getting the host_tag without involving mbulk processing
+ * This hostag value should also be include in the cb descriptor which goes to
+ * mbulk descriptor (no room left at the moment)
+ */
+ get_host_tag = (u8 *)m;
+ host_tag = get_host_tag[37] << 8 | get_host_tag[36];
+ SCSC_HIP4_SAMPLER_PKT_TX_FB(hip->hip_priv->minor, host_tag);
+ }
+#endif
+ /* Ignore return value */
+ slsi_hip_tx_done(sdev, colour);
+ }
+ mbulk_free_virt_host(m);
+consume_fb_mbulk:
+ /* Increase index */
+ idx_r++;
+ idx_r &= (MAX_NUM - 1);
+ hip4_update_index(hip, HIP4_MIF_Q_FH_RFB, ridx, idx_r);
+ }
+
+ if (no_change)
+ atomic_inc(&hip->hip_priv->stats.spurious_irqs);
+
+ scsc_service_mifintrbit_bit_unmask(sdev->service, hip->hip_priv->intr_tohost_mul[HIP4_MIF_Q_FH_RFB]);
+ SCSC_HIP4_SAMPLER_INT_OUT_BH(hip->hip_priv->minor, 2);
+ bh_end_fb = ktime_get();
+ spin_unlock_bh(&hip_priv->rx_lock);
+}
+
+static void hip4_irq_handler_fb(int irq, void *data)
+{
+ struct slsi_hip4 *hip = (struct slsi_hip4 *)data;
+ struct slsi_dev *sdev = container_of(hip, struct slsi_dev, hip4_inst);
+
+ SCSC_HIP4_SAMPLER_INT(hip->hip_priv->minor, 2);
+ intr_received_fb = ktime_get();
+
+ if (!atomic_read(&hip->hip_priv->watchdog_timer_active)) {
+ atomic_set(&hip->hip_priv->watchdog_timer_active, 1);
+ mod_timer(&hip->hip_priv->watchdog, jiffies + HZ);
+ }
+ set_bit(HIP4_MIF_Q_FH_RFB, hip->hip_priv->irq_bitmap);
+
+ scsc_service_mifintrbit_bit_mask(sdev->service, irq);
+ schedule_work(&hip->hip_priv->intr_wq_fb);
+ /* Clear interrupt */
+ scsc_service_mifintrbit_bit_clear(sdev->service, irq);
+ SCSC_HIP4_SAMPLER_INT_OUT(hip->hip_priv->minor, 2);
+}
+
+static void hip4_wq_ctrl(struct work_struct *data)
+{
+ struct hip4_priv *hip_priv = container_of(data, struct hip4_priv, intr_wq_ctrl);
+ struct slsi_hip4 *hip = hip_priv->hip;
+ struct hip4_hip_control *ctrl = hip->hip_control;
+ struct scsc_service *service;
+ struct slsi_dev *sdev = container_of(hip, struct slsi_dev, hip4_inst);
+ u8 retry;
+ bool no_change = true;
+ u8 idx_r;
+ u8 idx_w;
+ scsc_mifram_ref ref;
+ void *mem;
+ struct mbulk *m;
+#if defined(CONFIG_SCSC_WLAN_DEBUG) || defined(CONFIG_SCSC_WLAN_HIP4_PROFILING)
+ int id;
+#endif
+
+ if (!hip || !sdev || !sdev->service || !hip->hip_priv)
+ return;
+
+ spin_lock_bh(&hip_priv->rx_lock);
+ service = sdev->service;
+ SCSC_HIP4_SAMPLER_INT_BH(hip->hip_priv->minor, 1);
+ bh_init_ctrl = ktime_get();
+ clear_bit(HIP4_MIF_Q_TH_CTRL, hip->hip_priv->irq_bitmap);
+
+ idx_r = hip4_read_index(hip, HIP4_MIF_Q_TH_CTRL, ridx);
+ idx_w = hip4_read_index(hip, HIP4_MIF_Q_TH_CTRL, widx);
+
+#ifdef CONFIG_SCSC_WLAN_HIP4_PROFILING
+ if (idx_r != idx_w) {
+ SCSC_HIP4_SAMPLER_Q(hip_priv->minor, HIP4_MIF_Q_TH_CTRL, ridx, idx_r, 1);
+ SCSC_HIP4_SAMPLER_Q(hip_priv->minor, HIP4_MIF_Q_TH_CTRL, widx, idx_w, 1);
+ }
+#endif
+ while (idx_r != idx_w) {
+ struct sk_buff *skb;
+ /* TODO: currently the max number to be freed is 2. In future
+ * implementations (i.e. AMPDU) this number may be bigger
+ * list of mbulks to be freedi
+ */
+ scsc_mifram_ref to_free[MBULK_MAX_CHAIN + 1] = { 0 };
+ u8 i = 0;
+
+ no_change = false;
+ /* Catch-up with idx_w */
+ ref = ctrl->q[HIP4_MIF_Q_TH_CTRL].array[idx_r];
+#ifdef CONFIG_SCSC_WLAN_HIP4_PROFILING
+ SCSC_HIP4_SAMPLER_QREF(hip_priv->minor, ref, HIP4_MIF_Q_TH_CTRL);
+#endif
+ mem = scsc_mx_service_mif_addr_to_ptr(service, ref);
+ m = (struct mbulk *)(mem);
+ /* Process Control Signal */
+
+ skb = hip4_mbulk_to_skb(service, m, to_free, false);
+ if (!skb) {
+ SLSI_ERR_NODEV("Ctrl: Error parsing skb\n");
+ hip4_dump_dbg(hip, m, skb, service);
+ goto consume_ctl_mbulk;
+ }
+
+#if defined(CONFIG_SCSC_WLAN_DEBUG) || defined(CONFIG_SCSC_WLAN_HIP4_PROFILING)
+ id = fapi_get_sigid(skb);
+#endif
+#ifdef CONFIG_SCSC_WLAN_HIP4_PROFILING
+ /* log control signal, not unidata not debug */
+ if (fapi_is_mlme(skb))
+ SCSC_HIP4_SAMPLER_SIGNAL_CTRLRX(hip_priv->minor, (id & 0xff00) >> 8, id & 0xff);
+#endif
+#ifdef CONFIG_SCSC_WLAN_DEBUG
+ hip4_history_record_add(TH, id);
+#endif
+ if (slsi_hip_rx(sdev, skb) < 0) {
+ SLSI_ERR_NODEV("Ctrl: Error detected slsi_hip_rx\n");
+ hip4_dump_dbg(hip, m, skb, service);
+ slsi_kfree_skb(skb);
+ }
+consume_ctl_mbulk:
+ /* Increase index */
+ idx_r++;
+ idx_r &= (MAX_NUM - 1);
+
+ /* Go through the list of references to free */
+ while ((ref = to_free[i++])) {
+ /* Set the number of retries */
+ retry = FB_NO_SPC_NUM_RET;
+ /* return to the firmware */
+ while (hip4_q_add_signal(hip, HIP4_MIF_Q_TH_RFB, ref, service) && retry > 0) {
+ SLSI_WARN_NODEV("Ctrl: Not enough space in FB, retry: %d/%d\n", retry, FB_NO_SPC_NUM_RET);
+ spin_unlock_bh(&hip_priv->rx_lock);
+ msleep(FB_NO_SPC_SLEEP_MS);
+ spin_lock_bh(&hip_priv->rx_lock);
+ retry--;
+ if (retry == 0)
+ SLSI_ERR_NODEV("Ctrl: FB has not been freed for %d ms\n", FB_NO_SPC_NUM_RET * FB_NO_SPC_SLEEP_MS);
+ SCSC_HIP4_SAMPLER_QFULL(hip_priv->minor, HIP4_MIF_Q_TH_RFB);
+ }
+ }
+ hip4_update_index(hip, HIP4_MIF_Q_TH_CTRL, ridx, idx_r);
+ }
+
+ if (no_change)
+ atomic_inc(&hip->hip_priv->stats.spurious_irqs);
+
+ scsc_service_mifintrbit_bit_unmask(sdev->service, hip->hip_priv->intr_tohost_mul[HIP4_MIF_Q_TH_CTRL]);
+ SCSC_HIP4_SAMPLER_INT_OUT_BH(hip->hip_priv->minor, 1);
+ bh_end_ctrl = ktime_get();
+ spin_unlock_bh(&hip_priv->rx_lock);
+}
+
+static void hip4_irq_handler_ctrl(int irq, void *data)
+{
+ struct slsi_hip4 *hip = (struct slsi_hip4 *)data;
+ struct slsi_dev *sdev = container_of(hip, struct slsi_dev, hip4_inst);
+
+ SCSC_HIP4_SAMPLER_INT(hip->hip_priv->minor, 1);
+ intr_received_ctrl = ktime_get();
+
+ if (!atomic_read(&hip->hip_priv->watchdog_timer_active)) {
+ atomic_set(&hip->hip_priv->watchdog_timer_active, 1);
+ mod_timer(&hip->hip_priv->watchdog, jiffies + HZ);
+ }
+ set_bit(HIP4_MIF_Q_TH_CTRL, hip->hip_priv->irq_bitmap);
+
+ scsc_service_mifintrbit_bit_mask(sdev->service, irq);
+
+ schedule_work(&hip->hip_priv->intr_wq_ctrl);
+ /* Clear interrupt */
+ scsc_service_mifintrbit_bit_clear(sdev->service, irq);
+ SCSC_HIP4_SAMPLER_INT_OUT(hip->hip_priv->minor, 1);
+}
+
+static int hip4_napi_poll(struct napi_struct *napi, int budget)
+{
+ struct hip4_priv *hip_priv = container_of(napi, struct hip4_priv, napi);
+ struct slsi_hip4 *hip = hip_priv->hip;
+ struct hip4_hip_control *ctrl = hip->hip_control;
+ struct scsc_service *service;
+ struct slsi_dev *sdev = container_of(hip, struct slsi_dev, hip4_inst);
+
+#ifdef CONFIG_SCSC_WLAN_DEBUG
+ int id;
+#endif
+ u8 idx_r;
+ u8 idx_w;
+ scsc_mifram_ref ref;
+ void *mem;
+ struct mbulk *m;
+ u8 retry;
+ int work_done = 0;
+
+ if (!hip || !sdev || !sdev->service || !hip->hip_priv)
+ return 0;
+
+ spin_lock_bh(&hip_priv->rx_lock);
+ SCSC_HIP4_SAMPLER_INT_BH(hip->hip_priv->minor, 0);
+ if (ktime_compare(bh_init_data, bh_end_data) < 0)
+ bh_init_data = ktime_get();
+ clear_bit(HIP4_MIF_Q_TH_DAT, hip->hip_priv->irq_bitmap);
+
+ idx_r = hip4_read_index(hip, HIP4_MIF_Q_TH_DAT, ridx);
+ idx_w = hip4_read_index(hip, HIP4_MIF_Q_TH_DAT, widx);
+
+ service = sdev->service;
+
+ SLSI_DBG4(sdev, SLSI_RX, "todo:%d\n", (idx_w - idx_r) & 0xff);
+ if (idx_r == idx_w) {
+ SLSI_DBG4(sdev, SLSI_RX, "nothing to do, NAPI Complete\n");
+ bh_end_data = ktime_get();
+ napi_complete(napi);
+ /* Nothing more to drain, unmask interrupt */
+ scsc_service_mifintrbit_bit_unmask(sdev->service, hip->hip_priv->intr_tohost_mul[HIP4_MIF_Q_TH_DAT]);
+ goto end;
+ }
+
+#ifdef CONFIG_SCSC_WLAN_HIP4_PROFILING
+ if (idx_r != idx_w) {
+ SCSC_HIP4_SAMPLER_Q(hip_priv->minor, HIP4_MIF_Q_TH_DAT, ridx, idx_r, 1);
+ SCSC_HIP4_SAMPLER_Q(hip_priv->minor, HIP4_MIF_Q_TH_DAT, widx, idx_w, 1);
+ }
+#endif
+
+ while (idx_r != idx_w) {
+ struct sk_buff *skb;
+ /* TODO: currently the max number to be freed is 2. In future
+ * implementations (i.e. AMPDU) this number may be bigger
+ */
+ /* list of mbulks to be freed */
+ scsc_mifram_ref to_free[MBULK_MAX_CHAIN + 1] = { 0 };
+ u8 i = 0;
+
+ /* Catch-up with idx_w */
+ ref = ctrl->q[HIP4_MIF_Q_TH_DAT].array[idx_r];
+#ifdef CONFIG_SCSC_WLAN_HIP4_PROFILING
+ SCSC_HIP4_SAMPLER_QREF(hip_priv->minor, ref, HIP4_MIF_Q_TH_DAT);
+#endif
+ mem = scsc_mx_service_mif_addr_to_ptr(service, ref);
+ m = (struct mbulk *)(mem);
+ skb = hip4_mbulk_to_skb(service, m, to_free, false);
+ if (!skb) {
+ SLSI_ERR_NODEV("Dat: Error parsing skb\n");
+ hip4_dump_dbg(hip, m, skb, service);
+ goto consume_dat_mbulk;
+ }
+#ifdef CONFIG_SCSC_WLAN_DEBUG
+ id = fapi_get_sigid(skb);
+ hip4_history_record_add(TH, id);
+#endif
+ if (slsi_hip_rx(sdev, skb) < 0) {
+ SLSI_ERR_NODEV("Dat: Error detected slsi_hip_rx\n");
+ hip4_dump_dbg(hip, m, skb, service);
+ slsi_kfree_skb(skb);
+ }
+consume_dat_mbulk:
+ /* Increase index */
+ idx_r++;
+ idx_r &= (MAX_NUM - 1);
+
+ while ((ref = to_free[i++])) {
+ /* Set the number of retries */
+ retry = 100;
+ while (hip4_q_add_signal(hip, HIP4_MIF_Q_TH_RFB, ref, service) && retry > 0) {
+ SLSI_WARN_NODEV("Dat: Not enough space in FB, retry: %d/%d\n", retry, FB_NO_SPC_NUM_RET);
+ udelay(FB_NO_SPC_SLEEP_MS);
+ retry--;
+
+ if (retry == 0)
+ SLSI_ERR_NODEV("Dat: FB has not been freed for %d us\n", FB_NO_SPC_NUM_RET * FB_NO_SPC_SLEEP_MS);
+#ifdef CONFIG_SCSC_WLAN_HIP4_PROFILING
+ SCSC_HIP4_SAMPLER_QFULL(hip_priv->minor, HIP4_MIF_Q_TH_RFB);
+#endif
+ }
+ }
+
+ work_done++;
+ if (budget == work_done) {
+ /* We have consumed all the bugdet */
+ break;
+ }
+ }
+
+ hip4_update_index(hip, HIP4_MIF_Q_TH_DAT, ridx, idx_r);
+
+ if (work_done < budget) {
+ SLSI_DBG4(sdev, SLSI_RX, "NAPI Complete\n");
+ bh_end_data = ktime_get();
+ napi_complete(napi);
+ /* Nothing more to drain, unmask interrupt */
+ scsc_service_mifintrbit_bit_unmask(sdev->service, hip->hip_priv->intr_tohost_mul[HIP4_MIF_Q_TH_DAT]);
+ }
+end:
+ SLSI_DBG4(sdev, SLSI_RX, "work done:%d\n", work_done);
+ SCSC_HIP4_SAMPLER_INT_OUT_BH(hip->hip_priv->minor, 0);
+ spin_unlock_bh(&hip_priv->rx_lock);
+ return work_done;
+}
+
+static void hip4_napi_schedule(void *data)
+{
+ struct slsi_hip4 *hip = (struct slsi_hip4 *)data;
+
+ napi_schedule(&hip->hip_priv->napi);
+}
+
+static void hip4_irq_data_tasklet(unsigned long data)
+{
+ /* TODO: NAPI - formalize the CPU selection code */
+ struct slsi_hip4 *hip = (struct slsi_hip4 *)data;
+ int err = -EINVAL;
+
+ if (cpu_online(napi_select_cpu))
+ err = smp_call_function_single(napi_select_cpu, hip4_napi_schedule, hip, 0);
+
+ if (err)
+ napi_schedule(&hip->hip_priv->napi);
+}
+
+static void hip4_irq_handler_dat(int irq, void *data)
+{
+ struct slsi_hip4 *hip = (struct slsi_hip4 *)data;
+ struct slsi_dev *sdev = container_of(hip, struct slsi_dev, hip4_inst);
+
+ if (!hip || !sdev || !sdev->service || !hip->hip_priv)
+ return;
+
+ SCSC_HIP4_SAMPLER_INT(hip->hip_priv->minor, 0);
+ intr_received_data = ktime_get();
+
+ if (!atomic_read(&hip->hip_priv->watchdog_timer_active)) {
+ atomic_set(&hip->hip_priv->watchdog_timer_active, 1);
+ mod_timer(&hip->hip_priv->watchdog, jiffies + HZ);
+ }
+ set_bit(HIP4_MIF_Q_TH_DAT, hip->hip_priv->irq_bitmap);
+
+ if (napi_select_cpu)
+ tasklet_schedule(&hip->hip_priv->intr_tasklet);
+ else
+ napi_schedule(&hip->hip_priv->napi);
+
+ /* Mask interrupt to avoid interrupt storm and let BH run */
+ scsc_service_mifintrbit_bit_mask(sdev->service, hip->hip_priv->intr_tohost_mul[HIP4_MIF_Q_TH_DAT]);
+ /* Clear interrupt */
+ scsc_service_mifintrbit_bit_clear(sdev->service, hip->hip_priv->intr_tohost_mul[HIP4_MIF_Q_TH_DAT]);
+ SCSC_HIP4_SAMPLER_INT_OUT(hip->hip_priv->minor, 0);
+}
+
+#else /* #ifdef CONFIG_SCSC_WLAN_RX_NAPI */
+
+static bool slsi_check_rx_flowcontrol(struct slsi_dev *sdev)
+{
+ struct netdev_vif *ndev_vif;
+ int qlen = 0;
+
+ ndev_vif = netdev_priv(sdev->netdev[SLSI_NET_INDEX_WLAN]);
+ if (ndev_vif)
+ qlen = skb_queue_len(&ndev_vif->rx_data.queue);
+
+ SLSI_MUTEX_LOCK(sdev->netdev_remove_mutex);
+#if defined(SLSI_NET_INDEX_P2PX_SWLAN)
+ if (sdev->netdev[SLSI_NET_INDEX_P2PX_SWLAN]) {
+ ndev_vif = netdev_priv(sdev->netdev[SLSI_NET_INDEX_P2PX_SWLAN]);
+ if (ndev_vif)
+ qlen += skb_queue_len(&ndev_vif->rx_data.queue);
+ }
+#elif defined(SLSI_NET_INDEX_P2PX)
+ if (sdev->netdev[SLSI_NET_INDEX_P2PX]) {
+ ndev_vif = netdev_priv(sdev->netdev[SLSI_NET_INDEX_P2PX]);
+ if (ndev_vif)
+ qlen += skb_queue_len(&ndev_vif->rx_data.queue);
+ }
+#endif
+ SLSI_MUTEX_UNLOCK(sdev->netdev_remove_mutex);
+
+ if (qlen > max_buffered_frames) {
+ SLSI_DBG1_NODEV(SLSI_HIP, "max qlen reached: %d\n", qlen);
+ return true;
+ }
+ SLSI_DBG3_NODEV(SLSI_HIP, "qlen %d\n", qlen);
+
+ return false;
+}
/* Worqueue: Lower priority, run in process context. Can run simultaneously on
* different CPUs
*/
-#ifdef TASKLET
-static void hip4_tasklet(unsigned long data)
-#else
static void hip4_wq(struct work_struct *data)
-#endif
{
-#ifdef TASKLET
- struct slsi_hip4 *hip = (struct slsi_hip4 *)data;
- struct hip4_priv *hip_priv = hip->hip_priv;
- struct hip4_hip_control *ctrl = hip->hip_control;
-#else
struct hip4_priv *hip_priv = container_of(data, struct hip4_priv, intr_wq);
struct slsi_hip4 *hip = hip_priv->hip;
struct hip4_hip_control *ctrl = hip->hip_control;
-#endif
scsc_mifram_ref ref;
void *mem;
struct mbulk *m;
bool no_change = true;
u8 retry;
u32 packets_total;
+ bool rx_flowcontrol = false;
#if defined(CONFIG_SCSC_WLAN_HIP4_PROFILING) || defined(CONFIG_SCSC_WLAN_DEBUG)
int id;
return;
}
+ if (slsi_check_rx_flowcontrol(sdev))
+ rx_flowcontrol = true;
+
service = sdev->service;
-#ifndef TASKLET
spin_lock_bh(&hip_priv->rx_lock);
-#endif
atomic_set(&hip->hip_priv->in_rx, 1);
bh_init = ktime_get();
histogram_5++;
else
histogram_6++;
+
if (jitter > max_jitter)
max_jitter = jitter;
}
SCSC_HIP4_SAMPLER_INT_OUT_BH(hip_priv->minor, 1);
+ if (rx_flowcontrol)
+ goto skip_data_q;
+
atomic_set(&hip->hip_priv->in_rx, 3);
idx_r = hip4_read_index(hip, HIP4_MIF_Q_TH_DAT, ridx);
if (no_change)
atomic_inc(&hip->hip_priv->stats.spurious_irqs);
+skip_data_q:
if (!atomic_read(&hip->hip_priv->closing)) {
/* Reset status variable. DO THIS BEFORE UNMASKING!!!*/
atomic_set(&hip->hip_priv->watchdog_timer_active, 0);
- scsc_service_mifintrbit_bit_unmask(service, hip->hip_priv->rx_intr_tohost);
+ scsc_service_mifintrbit_bit_unmask(service, hip->hip_priv->intr_tohost);
}
+#ifdef CONFIG_ANDROID
if (wake_lock_active(&hip->hip_priv->hip4_wake_lock)) {
wake_unlock(&hip->hip_priv->hip4_wake_lock);
SCSC_WLOG_WAKELOCK(WLOG_LAZY, WL_RELEASED, "hip4_wake_lock", WL_REASON_RX);
}
+#endif
bh_end = ktime_get();
atomic_set(&hip->hip_priv->in_rx, 0);
-
-#ifndef TASKLET
spin_unlock_bh(&hip_priv->rx_lock);
-#endif
}
/* IRQ handler for hip4. The function runs in Interrupt context, so all the
intr_received = ktime_get();
+#ifdef CONFIG_ANDROID
if (!wake_lock_active(&hip->hip_priv->hip4_wake_lock)) {
wake_lock(&hip->hip_priv->hip4_wake_lock);
SCSC_WLOG_WAKELOCK(WLOG_LAZY, WL_TAKEN, "hip4_wake_lock", WL_REASON_RX);
}
+#endif
/* if wd timer is active system might be in trouble as it should be
* cleared in the BH. Ignore updating the timer
SLSI_ERR_NODEV("INT triggered while WDT is active\n");
SLSI_ERR_NODEV("bh_init %lld\n", ktime_to_ns(bh_init));
SLSI_ERR_NODEV("bh_end %lld\n", ktime_to_ns(bh_end));
-#ifndef TASKLET
SLSI_ERR_NODEV("hip4_wq work_busy %d\n", work_busy(&hip->hip_priv->intr_wq));
-#endif
SLSI_ERR_NODEV("hip4_priv->in_rx %d\n", atomic_read(&hip->hip_priv->in_rx));
}
/* If system is not in suspend, mask interrupt to avoid interrupt storm and let BH run */
if (!atomic_read(&hip->hip_priv->in_suspend)) {
- scsc_service_mifintrbit_bit_mask(sdev->service, hip->hip_priv->rx_intr_tohost);
+ scsc_service_mifintrbit_bit_mask(sdev->service, hip->hip_priv->intr_tohost);
hip->hip_priv->storm_count = 0;
} else if (++hip->hip_priv->storm_count >= MAX_STORM) {
/* A MAX_STORM number of interrupts has been received
* interrupt storm.
*/
hip->hip_priv->storm_count = 0;
- scsc_service_mifintrbit_bit_mask(sdev->service, hip->hip_priv->rx_intr_tohost);
+ scsc_service_mifintrbit_bit_mask(sdev->service, hip->hip_priv->intr_tohost);
}
atomic_inc(&hip->hip_priv->stats.irqs);
-#ifdef TASKLET
- tasklet_schedule(&hip->hip_priv->intr_tq);
-#else
schedule_work(&hip->hip_priv->intr_wq);
-#endif
end:
/* Clear interrupt */
- scsc_service_mifintrbit_bit_clear(sdev->service, hip->hip_priv->rx_intr_tohost);
+ scsc_service_mifintrbit_bit_clear(sdev->service, hip->hip_priv->intr_tohost);
SCSC_HIP4_SAMPLER_INT_OUT(hip->hip_priv->minor, 0);
SCSC_HIP4_SAMPLER_INT_OUT(hip->hip_priv->minor, 1);
SCSC_HIP4_SAMPLER_INT_OUT(hip->hip_priv->minor, 2);
}
+#endif /* #ifdef CONFIG_SCSC_WLAN_RX_NAPI */
+#ifdef CONFIG_SCSC_QOS
static void hip4_pm_qos_work(struct work_struct *data)
{
struct hip4_priv *hip_priv = container_of(data, struct hip4_priv, pm_qos_work);
spin_lock_bh(&hip->hip_priv->pm_qos_lock);
SLSI_DBG1(sdev, SLSI_HIP, "event (state:%u, tput_tx:%u bps, tput_rx:%u bps)\n", state, tput_tx, tput_rx);
- if (state == TRAFFIC_MON_CLIENT_STATE_HIGH)
+ if (state == TRAFFIC_MON_CLIENT_STATE_HIGH) {
hip->hip_priv->pm_qos_state = SCSC_QOS_MAX;
- else if (state == TRAFFIC_MON_CLIENT_STATE_MID)
+#ifdef CONFIG_SCSC_LOGRING
+ if (hip4_dynamic_logging)
+ scsc_logring_enable(false);
+#endif
+ } else if (state == TRAFFIC_MON_CLIENT_STATE_MID) {
hip->hip_priv->pm_qos_state = SCSC_QOS_MED;
- else
+#ifdef CONFIG_SCSC_LOGRING
+ if (hip4_dynamic_logging)
+ scsc_logring_enable(false);
+#endif
+ } else {
hip->hip_priv->pm_qos_state = SCSC_QOS_DISABLED;
+#ifdef CONFIG_SCSC_LOGRING
+ scsc_logring_enable(true);
+#endif
+ }
spin_unlock_bh(&hip->hip_priv->pm_qos_lock);
schedule_work(&hip->hip_priv->pm_qos_work);
}
+#endif
int hip4_init(struct slsi_hip4 *hip)
{
memset(&hip->hip_priv->stats, 0, sizeof(hip->hip_priv->stats));
hip->hip_priv->stats.start = ktime_get();
hip->hip_priv->stats.procfs_dir = proc_mkdir("driver/hip4", NULL);
- if (NULL != hip->hip_priv->stats.procfs_dir) {
+ if (!hip->hip_priv->stats.procfs_dir) {
proc_create_data("info", S_IRUSR | S_IRGRP,
hip->hip_priv->stats.procfs_dir, &hip4_procfs_stats_fops, hip);
proc_create_data("history", S_IRUSR | S_IRGRP,
/* Set driver is not ready to receive interrupts */
atomic_set(&hip->hip_priv->rx_ready, 0);
+#ifdef CONFIG_SCSC_WLAN_RX_NAPI
+ /* TOHOST Handler allocator */
+ /* Q0 FH CTRL */
+ hip->hip_priv->intr_tohost_mul[HIP4_MIF_Q_FH_CTRL] =
+ scsc_service_mifintrbit_register_tohost(service, hip4_irq_handler_stub, hip);
+ /* Mask the interrupt to prevent intr been kicked during start */
+ scsc_service_mifintrbit_bit_mask(service, hip->hip_priv->intr_tohost_mul[HIP4_MIF_Q_FH_CTRL]);
+ /* Q1 FH DAT - Use the same stub interrupt handler */
+ hip->hip_priv->intr_tohost_mul[HIP4_MIF_Q_FH_DAT] = hip->hip_priv->intr_tohost_mul[HIP4_MIF_Q_FH_CTRL];
+ /* Q2 FH FB */
+ hip->hip_priv->intr_tohost_mul[HIP4_MIF_Q_FH_RFB] =
+ scsc_service_mifintrbit_register_tohost(service, hip4_irq_handler_fb, hip);
+ scsc_service_mifintrbit_bit_mask(service, hip->hip_priv->intr_tohost_mul[HIP4_MIF_Q_FH_RFB]);
+ /* Q3 TH CTRL */
+ hip->hip_priv->intr_tohost_mul[HIP4_MIF_Q_TH_CTRL] =
+ scsc_service_mifintrbit_register_tohost(service, hip4_irq_handler_ctrl, hip);
+ scsc_service_mifintrbit_bit_mask(service, hip->hip_priv->intr_tohost_mul[HIP4_MIF_Q_TH_CTRL]);
+ /* Q4 TH DAT */
+ hip->hip_priv->intr_tohost_mul[HIP4_MIF_Q_TH_DAT] =
+ scsc_service_mifintrbit_register_tohost(service, hip4_irq_handler_dat, hip);
+ scsc_service_mifintrbit_bit_mask(service, hip->hip_priv->intr_tohost_mul[HIP4_MIF_Q_TH_DAT]);
+ /* Q5 TH RFB - Use the same stub interrupt handler */
+ hip->hip_priv->intr_tohost_mul[HIP4_MIF_Q_TH_RFB] = hip->hip_priv->intr_tohost_mul[HIP4_MIF_Q_FH_CTRL];
+#else
/* TOHOST Handler allocator */
- hip->hip_priv->rx_intr_tohost =
+ hip->hip_priv->intr_tohost =
scsc_service_mifintrbit_register_tohost(service, hip4_irq_handler, hip);
/* Mask the interrupt to prevent intr been kicked during start */
- scsc_service_mifintrbit_bit_mask(service, hip->hip_priv->rx_intr_tohost);
+ scsc_service_mifintrbit_bit_mask(service, hip->hip_priv->intr_tohost);
+#endif
/* FROMHOST Handler allocator */
- hip->hip_priv->rx_intr_fromhost =
+ hip->hip_priv->intr_fromhost =
scsc_service_mifintrbit_alloc_fromhost(service, SCSC_MIFINTR_TARGET_R4);
/* Get hip_control pointer on shared memory */
hip_control->config_v4.fw_buf_loc = hip->hip_ref + HIP4_WLAN_RX_OFFSET;
hip_control->config_v4.fw_buf_sz = HIP4_WLAN_RX_SIZE;
hip_control->config_v4.log_config_loc = 0;
- hip_control->config_v4.mif_fh_int_n = hip->hip_priv->rx_intr_fromhost;
- for (i = 0; i < MIF_HIP_CFG_Q_NUM; i++)
- hip_control->config_v4.mif_th_int_n[i] = hip->hip_priv->rx_intr_tohost;
+
+ hip_control->config_v4.mif_fh_int_n = hip->hip_priv->intr_fromhost;
+ for (i = 0; i < MIF_HIP_CFG_Q_NUM; i++) {
+#ifdef CONFIG_SCSC_WLAN_RX_NAPI
+ hip_control->config_v4.mif_th_int_n[i] = hip->hip_priv->intr_tohost_mul[i];
+#else
+ hip_control->config_v4.mif_th_int_n[i] = hip->hip_priv->intr_tohost;
+#endif
+ }
+
hip_control->config_v4.scbrd_loc = (u32)ref_scoreboard;
hip_control->config_v4.q_num = 6;
hip_control->config_v4.q_len = 256;
hip_control->config_v3.fw_buf_loc = hip->hip_ref + HIP4_WLAN_RX_OFFSET;
hip_control->config_v3.fw_buf_sz = HIP4_WLAN_RX_SIZE;
hip_control->config_v3.log_config_loc = 0;
- hip_control->config_v3.mif_fh_int_n = hip->hip_priv->rx_intr_fromhost;
- hip_control->config_v3.mif_th_int_n = hip->hip_priv->rx_intr_tohost;
+ hip_control->config_v3.mif_fh_int_n = hip->hip_priv->intr_fromhost;
+ hip_control->config_v3.mif_th_int_n = hip->hip_priv->intr_tohost;
hip_control->config_v3.q_num = 6;
hip_control->config_v3.q_len = 256;
hip_control->config_v3.q_idx_sz = 1;
hip->hip_control = hip_control;
hip->hip_priv->scbrd_base = &hip_control->scoreboard;
-#ifndef TASKLET
+
spin_lock_init(&hip->hip_priv->rx_lock);
-#endif
atomic_set(&hip->hip_priv->in_rx, 0);
spin_lock_init(&hip->hip_priv->tx_lock);
atomic_set(&hip->hip_priv->in_tx, 0);
-#ifdef TASKLET
- /* Init tasklet */
- tasklet_init(&hip->hip_priv->intr_tq, hip4_tasklet, (unsigned long)hip);
+
+ /* Init work structs */
+#ifdef CONFIG_SCSC_WLAN_RX_NAPI
+ tasklet_init(&hip->hip_priv->intr_tasklet, hip4_irq_data_tasklet, (unsigned long)hip);
+ INIT_WORK(&hip->hip_priv->intr_wq_ctrl, hip4_wq_ctrl);
+ INIT_WORK(&hip->hip_priv->intr_wq_fb, hip4_wq_fb);
#else
- /* Init wq */
INIT_WORK(&hip->hip_priv->intr_wq, hip4_wq);
#endif
+
rwlock_init(&hip->hip_priv->rw_scoreboard);
/* Setup watchdog timer */
atomic_set(&hip->hip_priv->watchdog_timer_active, 0);
spin_lock_init(&hip->hip_priv->watchdog_lock);
+#if KERNEL_VERSION(4, 15, 0) <= LINUX_VERSION_CODE
+ timer_setup(&hip->hip_priv->watchdog, hip4_watchdog, 0);
+#else
setup_timer(&hip->hip_priv->watchdog, hip4_watchdog, (unsigned long)hip);
+#endif
atomic_set(&hip->hip_priv->gmod, HIP4_DAT_SLOTS);
atomic_set(&hip->hip_priv->gactive, 1);
spin_lock_init(&hip->hip_priv->gbot_lock);
hip->hip_priv->saturated = 0;
+#ifdef CONFIG_ANDROID
wake_lock_init(&hip->hip_priv->hip4_wake_lock, WAKE_LOCK_SUSPEND, "hip4_wake_lock");
+#endif
#ifdef CONFIG_SCSC_SMAPPER
/* Init SMAPPER */
if (hip4_smapper_enable) {
- hip4_smapper_init(sdev, hip);
- hip4_smapper_is_enabled = true;
+ if (hip4_smapper_init(sdev, hip)) {
+ SLSI_ERR_NODEV("Error on hip4_smapper init\n");
+ hip4_smapper_is_enabled = false;
+ } else {
+ hip4_smapper_is_enabled = true;
+ }
}
#endif
-
+#ifdef CONFIG_SCSC_QOS
/* setup for PM QoS */
spin_lock_init(&hip->hip_priv->pm_qos_lock);
SLSI_WARN(sdev, "failed to add PM QoS request\n");
}
}
+#endif
return 0;
}
spin_lock_bh(&hip->hip_priv->tx_lock);
atomic_set(&hip->hip_priv->in_tx, 1);
+#ifdef CONFIG_ANDROID
if (!wake_lock_active(&hip->hip_priv->hip4_wake_lock)) {
wake_lock(&hip->hip_priv->hip4_wake_lock);
SCSC_WLOG_WAKELOCK(WLOG_LAZY, WL_TAKEN, "hip4_wake_lock", WL_REASON_TX);
}
+#endif
service = sdev->service;
return 0;
error:
+#ifdef CONFIG_ANDROID
if (wake_lock_active(&hip->hip_priv->hip4_wake_lock)) {
wake_unlock(&hip->hip_priv->hip4_wake_lock);
SCSC_WLOG_WAKELOCK(WLOG_LAZY, WL_RELEASED, "hip4_wake_lock", WL_REASON_TX);
}
+#endif
atomic_set(&hip->hip_priv->in_tx, 0);
spin_unlock_bh(&hip->hip_priv->tx_lock);
return ret;
struct slsi_dev *sdev = container_of(hip, struct slsi_dev, hip4_inst);
struct scsc_service *service;
u32 conf_hip4_ver = 0;
+#ifdef CONFIG_SCSC_WLAN_RX_NAPI
+ struct net_device *dev;
+#endif
if (!sdev || !sdev->service)
return -EIO;
return -EIO;
}
- /* If version 4 is used */
if (conf_hip4_ver == 4) {
hip->hip_priv->unidat_req_headroom =
scsc_wifi_get_hip_config_u8(&hip->hip_control, unidat_req_headroom, 4);
hip->hip_priv->unidat_req_tailroom =
scsc_wifi_get_hip_config_u8(&hip->hip_control, unidat_req_tailroom, 4);
hip->hip_priv->version = 4;
+
+#ifdef CONFIG_SCSC_WLAN_RX_NAPI
+ rcu_read_lock();
+ /* one NAPI instance is ok for multiple netdev devices */
+ dev = slsi_get_netdev_rcu(sdev, SLSI_NET_INDEX_WLAN);
+ if (!dev) {
+ SLSI_ERR(sdev, "netdev No longer exists\n");
+ rcu_read_unlock();
+ return -EINVAL;
+ }
+ netif_napi_add(dev, &hip->hip_priv->napi, hip4_napi_poll, NAPI_POLL_WEIGHT);
+ napi_enable(&hip->hip_priv->napi);
+ rcu_read_unlock();
+#endif
} else {
/* version 3 */
hip->hip_priv->unidat_req_headroom =
/* Driver is ready to process IRQ */
atomic_set(&hip->hip_priv->rx_ready, 1);
- scsc_service_mifintrbit_bit_unmask(service, hip->hip_priv->rx_intr_tohost);
+#ifdef CONFIG_SCSC_WLAN_RX_NAPI
+ scsc_service_mifintrbit_bit_unmask(service, hip->hip_priv->intr_tohost_mul[HIP4_MIF_Q_FH_RFB]);
+ scsc_service_mifintrbit_bit_unmask(service, hip->hip_priv->intr_tohost_mul[HIP4_MIF_Q_TH_CTRL]);
+ scsc_service_mifintrbit_bit_unmask(service, hip->hip_priv->intr_tohost_mul[HIP4_MIF_Q_TH_DAT]);
+#else
+ scsc_service_mifintrbit_bit_unmask(service, hip->hip_priv->intr_tohost);
+#endif
return 0;
}
/* On suspend hip4 needs to ensure that TH interrupts *are* unmasked */
void hip4_suspend(struct slsi_hip4 *hip)
{
- struct slsi_dev *sdev = container_of(hip, struct slsi_dev, hip4_inst);
+ struct slsi_dev *sdev;
struct scsc_service *service;
+ if (!hip || !hip->hip_priv)
+ return;
+
+ sdev = container_of(hip, struct slsi_dev, hip4_inst);
if (!sdev || !sdev->service)
return;
SCSC_HIP4_SAMPLER_SUSPEND(hip->hip_priv->minor);
atomic_set(&hip->hip_priv->in_suspend, 1);
- scsc_service_mifintrbit_bit_unmask(service, hip->hip_priv->rx_intr_tohost);
+
+#ifdef CONFIG_SCSC_WLAN_RX_NAPI
+ for (u8 i = 0; i < MIF_HIP_CFG_Q_NUM; i++)
+ scsc_service_mifintrbit_bit_unmask(service, hip->hip_priv->intr_tohost_mul[i]);
+#else
+ scsc_service_mifintrbit_bit_unmask(service, hip->hip_priv->intr_tohost);
+#endif
}
/* TH interrupts can be masked/unmasked */
void hip4_resume(struct slsi_hip4 *hip)
{
- struct slsi_dev *sdev = container_of(hip, struct slsi_dev, hip4_inst);
+ struct slsi_dev *sdev;
+
+ if (!hip || !hip->hip_priv)
+ return;
+ sdev = container_of(hip, struct slsi_dev, hip4_inst);
if (!sdev)
return;
void hip4_freeze(struct slsi_hip4 *hip)
{
- struct slsi_dev *sdev = container_of(hip, struct slsi_dev, hip4_inst);
+ struct slsi_dev *sdev;
struct scsc_service *service;
+ if (!hip || !hip->hip_priv)
+ return;
+
+ sdev = container_of(hip, struct slsi_dev, hip4_inst);
if (!sdev || !sdev->service)
return;
atomic_set(&hip->hip_priv->closing, 1);
hip4_dump_dbg(hip, NULL, NULL, service);
+#ifdef CONFIG_SCSC_WLAN_RX_NAPI
+ for (u8 i = 0; i < MIF_HIP_CFG_Q_NUM; i++)
+ scsc_service_mifintrbit_bit_mask(service, hip->hip_priv->intr_tohost_mul[i]);
- scsc_service_mifintrbit_bit_mask(service, hip->hip_priv->rx_intr_tohost);
-
-#ifdef TASKLET
- tasklet_kill(&hip->hip_priv->intr_tq);
+ tasklet_kill(&hip->hip_priv->intr_tasklet);
+ cancel_work_sync(&hip->hip_priv->intr_wq_ctrl);
+ cancel_work_sync(&hip->hip_priv->intr_wq_fb);
#else
+ scsc_service_mifintrbit_bit_mask(service, hip->hip_priv->intr_tohost);
cancel_work_sync(&hip->hip_priv->intr_wq);
#endif
atomic_set(&hip->hip_priv->rx_ready, 0);
atomic_set(&hip->hip_priv->watchdog_timer_active, 0);
+
/* Deactive the wd timer prior its expiration */
del_timer_sync(&hip->hip_priv->watchdog);
}
service = sdev->service;
+#ifdef CONFIG_SCSC_QOS
+#ifdef CONFIG_SCSC_LOGRING
+ /* Reenable logring in case was disabled */
+ scsc_logring_enable(true);
+#endif
/* de-register with traffic monitor */
slsi_traffic_mon_client_unregister(sdev, hip);
scsc_service_pm_qos_remove_request(service);
+#endif
#ifdef CONFIG_SCSC_SMAPPER
/* Init SMAPPER */
hip4_smapper_deinit(sdev, hip);
}
#endif
+#ifdef CONFIG_ANDROID
wake_lock_destroy(&hip->hip_priv->hip4_wake_lock);
+#endif
closing = ktime_get();
atomic_set(&hip->hip_priv->closing, 1);
- scsc_service_mifintrbit_bit_mask(service, hip->hip_priv->rx_intr_tohost);
+#ifdef CONFIG_SCSC_WLAN_RX_NAPI
+ for (u8 i = 0; i < MIF_HIP_CFG_Q_NUM; i++)
+ scsc_service_mifintrbit_bit_mask(service, hip->hip_priv->intr_tohost_mul[i]);
-#ifdef TASKLET
- tasklet_kill(&hip->hip_priv->intr_tq);
+ netif_napi_del(&hip->hip_priv->napi);
+ tasklet_kill(&hip->hip_priv->intr_tasklet);
+ cancel_work_sync(&hip->hip_priv->intr_wq_ctrl);
+ cancel_work_sync(&hip->hip_priv->intr_wq_fb);
+
+ for (i = 0; i < MIF_HIP_CFG_Q_NUM; i++)
+ scsc_service_mifintrbit_unregister_tohost(service, hip->hip_priv->intr_tohost_mul[i]);
#else
+ scsc_service_mifintrbit_bit_mask(service, hip->hip_priv->intr_tohost);
cancel_work_sync(&hip->hip_priv->intr_wq);
+ scsc_service_mifintrbit_unregister_tohost(service, hip->hip_priv->intr_tohost);
#endif
- scsc_service_mifintrbit_unregister_tohost(service, hip->hip_priv->rx_intr_tohost);
- scsc_service_mifintrbit_free_fromhost(service, hip->hip_priv->rx_intr_fromhost, SCSC_MIFINTR_TARGET_R4);
+
+ scsc_service_mifintrbit_free_fromhost(service, hip->hip_priv->intr_fromhost, SCSC_MIFINTR_TARGET_R4);
/* If we get to that point with rx_lock/tx_lock claimed, trigger BUG() */
WARN_ON(atomic_read(&hip->hip_priv->in_tx));
#include <linux/skbuff.h>
#include <scsc/scsc_mifram.h>
#include <scsc/scsc_mx.h>
+#ifdef CONFIG_SCSC_WLAN_RX_NAPI
+#include <linux/netdevice.h>
+#endif
#ifndef SLSI_TEST_DEV
+#ifdef CONFIG_ANDROID
#include <linux/wakelock.h>
#endif
+#endif
#include "mbulk.h"
#ifdef CONFIG_SCSC_SMAPPER
#include "hip4_smapper.h"
u32 log_config_loc; /* Logging Configuration Location in MIF_ADDR */
u32 log_config_sz; /* Logging Configuration Size in MIF_ADDR */
- u8 mif_fh_int_n; /* MIF from-host interrupt bit position for all HIP queue */
+ u8 mif_fh_int_n; /* MIF from-host interrupt bit position for all HIP queue */
u8 reserved1[3];
- u8 mif_th_int_n[6]; /* MIF to-host interrupt bit positions for each HIP queue */
+ u8 mif_th_int_n[6]; /* MIF to-host interrupt bit positions for each HIP queue */
u8 reserved2[2];
u32 scbrd_loc; /* Scoreboard locatin in MIF_ADDR */
u8 smapper_pow_sz[16]; /* Power of size of entry i.e. 12 = 4096B */
u32 smapper_bank_addr[16]; /* Bank start addr */
#endif
-
u8 reserved4[16];
} __packed;
struct slsi_hip4;
-/* #define TASKLET 1 */
/* This struct is private to the HIP implementation */
struct hip4_priv {
-#ifdef TASKLET
- struct tasklet_struct intr_tq;
+#ifdef CONFIG_SCSC_WLAN_RX_NAPI
+ struct tasklet_struct intr_tasklet;
+ struct work_struct intr_wq_ctrl;
+ struct work_struct intr_wq_fb;
+ struct napi_struct napi;
#else
struct work_struct intr_wq;
#endif
- /* Interrupts cache */
+
+ /* Interrupts cache < v4 */
/* TOHOST */
- u32 rx_intr_tohost;
+ u32 intr_tohost;
+
+ /* Interrupts cache v4 */
+ u32 intr_tohost_mul[MIF_HIP_CFG_Q_NUM];
/* FROMHOST */
- u32 rx_intr_fromhost;
+ u32 intr_fromhost;
/* For workqueue */
struct slsi_hip4 *hip;
/* Pool for ctl frames*/
u8 host_pool_id_ctl;
-#ifndef TASKLET
/* rx cycle lock */
spinlock_t rx_lock;
-#endif
/* tx cycle lock */
spinlock_t tx_lock;
spinlock_t watchdog_lock;
/* wd timer control */
atomic_t watchdog_timer_active;
+#ifdef CONFIG_SCSC_WLAN_RX_NAPI
+ DECLARE_BITMAP(irq_bitmap, MIF_HIP_CFG_Q_NUM);
+#endif
-#ifndef SLSI_TEST_DEV
+#if !defined SLSI_TEST_DEV && defined CONFIG_ANDROID
/* Wakelock for modem_ctl */
struct wake_lock hip4_wake_lock;
#endif
struct hip4_smapper_bank smapper_banks[HIP4_SMAPPER_TOTAL_BANKS];
struct hip4_smapper_control smapper_control;
#endif
-
+#ifdef CONFIG_SCSC_QOS
/* PM QoS control */
struct work_struct pm_qos_work;
/* PM QoS control spinlock */
spinlock_t pm_qos_lock;
u8 pm_qos_state;
-
+#endif
/* Collection artificats */
void *mib_collect;
u16 mib_sz;
#define scsc_wifi_get_hip_config_version_4_u8(buff_ptr, member) le16_to_cpu((((struct hip4_hip_config_version_4 *)(buff_ptr))->member))
#define scsc_wifi_get_hip_config_version_4_u16(buff_ptr, member) le16_to_cpu((((struct hip4_hip_config_version_4 *)(buff_ptr))->member))
#define scsc_wifi_get_hip_config_version_4_u32(buff_ptr, member) le32_to_cpu((((struct hip4_hip_config_version_4 *)(buff_ptr))->member))
-#define scsc_wifi_get_hip_config_version_3_u8(buff_ptr, member) le16_to_cpu((((struct hip4_hip_config_version_4 *)(buff_ptr))->member))
-#define scsc_wifi_get_hip_config_version_3_u16(buff_ptr, member) le16_to_cpu((((struct hip4_hip_config_version_4 *)(buff_ptr))->member))
-#define scsc_wifi_get_hip_config_version_3_u32(buff_ptr, member) le32_to_cpu((((struct hip4_hip_config_version_4 *)(buff_ptr))->member))
+#define scsc_wifi_get_hip_config_version_3_u8(buff_ptr, member) le16_to_cpu((((struct hip4_hip_config_version_3 *)(buff_ptr))->member))
+#define scsc_wifi_get_hip_config_version_3_u16(buff_ptr, member) le16_to_cpu((((struct hip4_hip_config_version_3 *)(buff_ptr))->member))
+#define scsc_wifi_get_hip_config_version_3_u32(buff_ptr, member) le32_to_cpu((((struct hip4_hip_config_version_3 *)(buff_ptr))->member))
#define scsc_wifi_get_hip_config_u8(buff_ptr, member, ver) le16_to_cpu((((struct hip4_hip_config_version_##ver *)(buff_ptr->config_v##ver))->member))
#define scsc_wifi_get_hip_config_u16(buff_ptr, member, ver) le16_to_cpu((((struct hip4_hip_config_version_##ver *)(buff_ptr->config_v##ver))->member))
#define scsc_wifi_get_hip_config_u32(buff_ptr, member, ver) le32_to_cpu((((struct hip4_hip_config_version_##ver *)(buff_ptr->config_v##ver))->member))
struct hip4_sampler_dev *hip4_dev;
unsigned long flags;
- if (!hip4_sampler_enable)
+ if (!hip4_sampler_enable || !hip4_sampler.init)
return;
if (atomic_read(&in_read))
if ((tcp_ack->dport == tcp_hdr->source) && (tcp_ack->sport == tcp_hdr->dest)) {
if (from_ba && tcp_hdr->syn && tcp_hdr->ack) {
unsigned char *options;
- u32 optlen, len = 0;
+ u32 optlen = 0, len = 0;
- optlen = (tcp_hdr->doff - 5) * 4;
- if (optlen > 60) {
- SLSI_WARN(sdev, "Error optlen : %u\n", optlen);
- optlen = 60;
- }
+ if (tcp_hdr->doff > 5)
+ optlen = (tcp_hdr->doff - 5) * 4;
options = (u8 *)tcp_hdr + TCP_ACK_SUPPRESSION_OPTIONS_OFFSET;
while (optlen > 0) {
switch (options[0]) {
case TCP_ACK_SUPPRESSION_OPTION_EOL:
+ len = 1;
break;
case TCP_ACK_SUPPRESSION_OPTION_NOP:
len = 1;
len = options[1];
break;
}
- /* if length field in TCP options is 0, then options are bogus; return here */
- if (len == 0)
+ /* if length field in TCP options is 0, or greater than
+ * total options length, then options are incorrect
+ */
+ if ((len == 0) || (len >= optlen))
break;
if (optlen >= len)
hip4_collect_client.prv = mx;
scsc_log_collector_register_client(&hip4_collect_client);
#endif
+ spin_lock_init(&g_spinlock);
hip4_sampler.init = true;
SLSI_INFO_NODEV("%s: Ready to start sampling....\n", DRV_NAME);
if (dma_set_mask_and_coherent(sdev->dev, DMA_BIT_MASK(64)) != 0)
return -EIO;
+ if (!scsc_mx_service_alloc_mboxes(sdev->service, 1, &control->mbox_scb)) {
+ SLSI_DBG4_NODEV(SLSI_SMAPPER, "Unable to allocate mbox\n");
+ return -ENODEV;
+ }
+
/* Claim the RX buffers */
hip4_smapper_alloc_bank(sdev, hip->hip_priv, RX_0, SMAPPER_GRANULARITY, HIP4_SMAPPER_BANK_LARGE);
hip4_smapper_alloc_bank(sdev, hip->hip_priv, RX_1, SMAPPER_GRANULARITY, HIP4_SMAPPER_BANK_LARGE);
hip4_smapper_allocate_skb_buffers(sdev, &hip->hip_priv->smapper_banks[RX_2]);
hip4_smapper_allocate_skb_buffers(sdev, &hip->hip_priv->smapper_banks[RX_3]);
- /* Allocate Maxwell resources - TODO: remove the emul */
+ /* Allocate Maxwell resources */
control->th_req =
scsc_service_mifintrbit_register_tohost(sdev->service, hip4_smapper_refill_isr, hip);
control->fh_ind =
scsc_service_mifintrbit_alloc_fromhost(sdev->service, SCSC_MIFINTR_TARGET_R4);
- scsc_mx_service_alloc_mboxes(sdev->service, 1, &control->mbox_scb);
control->mbox_ptr =
scsc_mx_service_get_mbox_ptr(sdev->service, control->mbox_scb);
control = &(hip->hip_priv->smapper_control);
spin_lock_irqsave(&control->smapper_lock, flags);
- scsc_service_mifintrbit_unregister_tohost(sdev->service, control->th_req);
- scsc_service_mifintrbit_free_fromhost(sdev->service, control->fh_ind, SCSC_MIFINTR_TARGET_R4);
-
for (i = RX_0; i < END_RX_BANKS; i++) {
bank = &hip->hip_priv->smapper_banks[i];
bank->in_use = false;
scsc_service_mifsmapper_free_bank(sdev->service, bank->bank);
}
spin_unlock_irqrestore(&control->smapper_lock, flags);
+
+ scsc_service_mifintrbit_unregister_tohost(sdev->service, control->th_req);
+ scsc_service_mifintrbit_free_fromhost(sdev->service, control->fh_ind, SCSC_MIFINTR_TARGET_R4);
+ scsc_service_free_mboxes(sdev->service, 1, control->mbox_scb);
+
}
}
- SLSI_DBG3(sdev, SLSI_INIT_DEINIT, "Number of channels for autchannel selection= %d", count_channels);
+ SLSI_DBG3(sdev, SLSI_INIT_DEINIT, "Number of channels for autochannel selection= %d", count_channels);
SLSI_MUTEX_LOCK(sdev->device_config_mutex);
sdev->device_config.ap_auto_chan = 0;
sdev->device_config.ap_auto_chan = ieee80211_frequency_to_channel(sta_frequency);
else
sdev->device_config.ap_auto_chan = 1;
- SLSI_DBG1(sdev, SLSI_INIT_DEINIT, "Auto channel written = %d", sdev->device_config.ap_auto_chan);
+ SLSI_INFO(sdev, "Channel selected = %d", sdev->device_config.ap_auto_chan);
SLSI_MUTEX_UNLOCK(sdev->device_config_mutex);
return 0;
}
else
enable = 0;
- status = slsi_mib_encode_bool(&mib_data, SLSI_PSID_UNIFI_MAC_ADDRESS_RANDOMISATION, enable, 0);
+ status = slsi_mib_encode_bool(&mib_data, SLSI_PSID_UNIFI_MAC_ADDRESS_RANDOMISATION_ACTIVATED, enable, 0);
if (status != SLSI_MIB_STATUS_SUCCESS) {
SLSI_ERR(sdev, "FAKE MAC FAIL: no mem for MIB\n");
return -ENOMEM;
priv_cmd.total_len - skip);
} else if (strncasecmp(command, CMD_GETROAMSCANCHANNELS, strlen(CMD_GETROAMSCANCHANNELS)) == 0) {
ret = slsi_roam_scan_channels_read(dev, command, priv_cmd.total_len);
+ } else if (strncasecmp(command, CMD_SETROAMOFFLOAD, strlen(CMD_SETROAMOFFLOAD)) == 0) {
+ ret = slsi_roam_mode_write(dev, command + strlen(CMD_SETROAMOFFLOAD) + 1,
+ priv_cmd.total_len - (strlen(CMD_SETROAMOFFLOAD) + 1));
+ } else if (strncasecmp(command, CMD_SETROAMOFFLAPLIST, strlen(CMD_SETROAMOFFLAPLIST)) == 0) {
+ ret = slsi_roam_offload_ap_list(dev, command + strlen(CMD_SETROAMOFFLAPLIST) + 1,
+ priv_cmd.total_len - (strlen(CMD_SETROAMOFFLAPLIST) + 1));
#endif
} else if (strncasecmp(command, CMD_SET_PMK, strlen(CMD_SET_PMK)) == 0) {
ret = slsi_set_pmk(dev, command, priv_cmd.total_len);
} else if (strncasecmp(command, CMD_TDLSCHANNELSWITCH, strlen(CMD_TDLSCHANNELSWITCH)) == 0) {
ret = slsi_tdls_channel_switch(dev, command + strlen(CMD_TDLSCHANNELSWITCH) + 1,
priv_cmd.total_len - (strlen(CMD_TDLSCHANNELSWITCH) + 1));
- } else if (strncasecmp(command, CMD_SETROAMOFFLOAD, strlen(CMD_SETROAMOFFLOAD)) == 0) {
- ret = slsi_roam_mode_write(dev, command + strlen(CMD_SETROAMOFFLOAD) + 1,
- priv_cmd.total_len - (strlen(CMD_SETROAMOFFLOAD) + 1));
- } else if (strncasecmp(command, CMD_SETROAMOFFLAPLIST, strlen(CMD_SETROAMOFFLAPLIST)) == 0) {
- ret = slsi_roam_offload_ap_list(dev, command + strlen(CMD_SETROAMOFFLAPLIST) + 1,
- priv_cmd.total_len - (strlen(CMD_SETROAMOFFLAPLIST) + 1));
} else if (strncasecmp(command, CMD_SET_TX_POWER_CALLING, strlen(CMD_SET_TX_POWER_CALLING)) == 0) {
ret = slsi_set_tx_power_calling(dev, command + strlen(CMD_SET_TX_POWER_CALLING) + 1,
priv_cmd.total_len - (strlen(CMD_SET_TX_POWER_CALLING) + 1));
#define SLSI_MIB_MAX_CLIENT (10)
#define SLSI_REG_PARAM_START_INDEX (1)
-/* temp until it gets integrated into mib.h by Autogen */
-#define SLSI_PSID_UNIFI_REG_DOM_VERSION 8019
-
static char *mib_file_t = "wlan_t.hcf";
module_param(mib_file_t, charp, S_IRUGO | S_IWUSR);
MODULE_PARM_DESC(mib_file_t, "mib data filename");
-static char *mib_file2_t = "wlan_sw_t.hcf";
+static char *mib_file2_t = "wlan_t_sw.hcf";
module_param(mib_file2_t, charp, S_IRUGO | S_IWUSR);
MODULE_PARM_DESC(mib_file2_t, "mib data filename");
return;
}
mac_efs:
+#ifdef CONFIG_SCSC_WLAN_MAC_ADDRESS_FILENAME
r = mx140_request_file(sdev->maxwell_core, CONFIG_SCSC_WLAN_MAC_ADDRESS_FILENAME, &e);
if (r != 0)
goto mac_default;
SLSI_INFO(sdev, "MAC address loaded from %s: %02X:%02X:%02X:%02X:%02X:%02X\n", CONFIG_SCSC_WLAN_MAC_ADDRESS_FILENAME, u[0], u[1], u[2], u[3], u[4], u[5]);
mx140_release_file(sdev->maxwell_core, e);
return;
+#endif
mac_default:
/* This is safe to call, even if the struct firmware handle is NULL */
static void write_wifi_version_info_file(struct slsi_dev *sdev)
{
struct file *fp = NULL;
+#if defined(ANDROID_VERSION) && (ANDROID_VERSION >= 90000)
char *filepath = "/data/vendor/conn/.wifiver.info";
+#else
+ char *filepath = "/data/misc/conn/.wifiver.info";
+#endif
char buf[256];
char build_id_fw[128];
char build_id_drv[64];
* as it can have fatal consequences.
* The framework parser for the version may depend on this
* exact formatting.
+ *
+ * Also beware that ANDROID_VERSION will not be defined in AOSP.
*/
+#if defined(ANDROID_VERSION) && (ANDROID_VERSION >= 90000)
+ /* P-OS */
snprintf(buf, sizeof(buf),
- "drv_ver: %s\n"
+ "%s\n" /* drv_ver: already appended by mxman_get_driver_version() */
"f/w_ver: %s\n"
- "hcf_ver_hw: %u\n"
- "hcf_ver_sw: %u\n"
+ "hcf_ver_hw: %s\n"
+ "hcf_ver_sw: %s\n"
"regDom_ver: %d.%d\n",
build_id_drv,
build_id_fw,
- sdev->mib[0].mib_hash,
- sdev->mib[1].mib_hash,
+ sdev->mib[0].platform,
+ sdev->mib[1].platform,
+ ((sdev->reg_dom_version >> 8) & 0xFF), (sdev->reg_dom_version & 0xFF));
+#else
+ /* O-OS, or unknown */
+ snprintf(buf, sizeof(buf),
+ "%s (f/w_ver: %s)\nregDom_ver: %d.%d\n",
+ build_id_drv,
+ build_id_fw,
((sdev->reg_dom_version >> 8) & 0xFF), (sdev->reg_dom_version & 0xFF));
+#endif
+/* If ANDROID_VERSION is not known, avoid writing the file, as it could go to the wrong
+ * location.
+ */
+#ifdef ANDROID_VERSION
+#ifdef CONFIG_SCSC_WLBTD
+ wlbtd_write_file(filepath, buf);
+#else
kernel_write(fp, buf, strlen(buf), 0);
if (fp)
filp_close(fp, NULL);
-
+#endif
SLSI_INFO(sdev, "Succeed to write firmware/host information to .wifiver.info\n");
+#else
+ SLSI_UNUSED_PARAMETER(filepath);
+#endif
}
#ifdef CONFIG_SCSC_WLAN_DEBUG
/* Only the first file is mandatory */
if (i == 0 && err) {
- SLSI_ERR(sdev, "slsi_mib_open_file failed: err=%d\n", err);
+ SLSI_ERR(sdev, "mib: Mandatory wlan hcf missing. WLAN will not start (err=%d)\n", err);
slsi_sm_wlan_service_close(sdev);
goto err_done;
}
} else {
offset = snprintf(buf + offset, sizeof(buf), "#softap.info\n");
offset += snprintf(buf + offset, sizeof(buf), "DualBandConcurrency=%s\n", sdev->dualband_concurrency ? "yes" : "no");
+#ifdef CONFIG_SCSC_WLAN_WIFI_SHARING
+ offset += snprintf(buf + offset, sizeof(buf), "DualInterface=%s\n", "yes");
+#else
+ offset += snprintf(buf + offset, sizeof(buf), "DualInterface=%s\n", "no");
+#endif
offset += snprintf(buf + offset, sizeof(buf), "5G=%s\n", sdev->band_5g_supported ? "yes" : "no");
offset += snprintf(buf + offset, sizeof(buf), "maxClient=%d\n", !sdev->softap_max_client ? SLSI_MIB_MAX_CLIENT : sdev->softap_max_client);
slsi_update_supported_channels_regd_flags(sdev);
SLSI_DBG2(sdev, SLSI_INIT_DEINIT, "---Driver started successfully---\n");
sdev->device_state = SLSI_DEVICE_STATE_STARTED;
+ memset(sdev->rtt_vif, -1, sizeof(sdev->rtt_vif));
SLSI_MUTEX_UNLOCK(sdev->start_stop_mutex);
slsi_kic_system_event(slsi_kic_system_event_category_initialisation,
if (hw_available) {
struct slsi_peer *peer;
int j = 0;
- int r = 0;
while (j < SLSI_PEER_INDEX_MAX) {
peer = ndev_vif->peer_sta_record[j];
slsi_ps_port_control(sdev, dev, peer, SLSI_STA_CONN_STATE_DISCONNECTED);
++j;
}
- r = slsi_mlme_disconnect(sdev, dev, NULL, WLAN_REASON_DEAUTH_LEAVING, true);
- if (r != 0)
- SLSI_NET_ERR(dev, "Disconnection returned with CFM failure\n");
slsi_mlme_del_vif(sdev, dev);
}
SLSI_DBG2(sdev, SLSI_INIT_DEINIT, "Calling slsi_vif_deactivated\n");
SLSI_P2P_STATE_CHANGE(sdev, P2P_IDLE_NO_VIF);
} else if (ndev_vif->vif_type == FAPI_VIFTYPE_UNSYNCHRONISED) {
if (SLSI_IS_VIF_INDEX_WLAN(ndev_vif)) {
- slsi_hs2_vif_deactivate(sdev, dev, hw_available);
+ slsi_wlan_unsync_vif_deactivate(sdev, dev, hw_available);
} else {
SLSI_DBG2(sdev, SLSI_INIT_DEINIT, "P2P active - Deactivate\n");
slsi_p2p_vif_deactivate(sdev, dev, hw_available);
return mib_slice;
}
+/* Extract the platform name string from the HCF file */
+static int slsi_mib_get_platform(struct slsi_dev_mib_info *mib_info)
+{
+ size_t plat_name_len;
+ int pos = 0;
+
+ /* The mib_data passed to this function should already
+ * have had its HCF header skipped.
+ *
+ * This is shoehorned into specific PSIDs to allow backward
+ * compatibility, so we must look into the HCF payload
+ * instead of the header :(
+ *
+ * The updated configcmd util guarantees that these keys
+ * will appear first:
+ *
+ * PSIDs:
+ * 0xfffe - 16 bit version ID, value 1.
+ * 0xffff - If version ID=1, holds platform name string.
+ */
+
+ mib_info->platform[0] = '\0';
+
+ /* Sanity - payload long enough for info? */
+ if (mib_info->mib_len < 12) {
+ SLSI_INFO_NODEV("HCF file too short\n");
+ return -EINVAL; /* file too short */
+ }
+
+ if (mib_info->mib_data[pos++] != 0xFE || /* Version ID FFFE */
+ mib_info->mib_data[pos++] != 0xFF) {
+ SLSI_INFO_NODEV("No HCF version ID\n");
+ return -EINVAL; /* No version ID */
+ }
+ if (mib_info->mib_data[pos++] != 0x01 || /* Len 1, LE */
+ mib_info->mib_data[pos++] != 0x00) {
+ SLSI_INFO_NODEV("Bad length\n");
+ return -EINVAL; /* Unknown length */
+ }
+ if (mib_info->mib_data[pos++] != 0x01 || /* Header ID 1, LE */
+ mib_info->mib_data[pos++] != 0x00) {
+ SLSI_INFO_NODEV("Bad version ID\n");
+ return -EINVAL; /* Unknown version ID */
+ }
+ if (mib_info->mib_data[pos++] != 0xFF || /* Platform Name FFFF */
+ mib_info->mib_data[pos++] != 0xFF) {
+ SLSI_INFO_NODEV("No HCF platform name\n");
+ return -EINVAL; /* No platform name */
+ }
+
+ /* Length of platform name */
+ plat_name_len = mib_info->mib_data[pos++];
+ plat_name_len |= (mib_info->mib_data[pos++] << 16);
+
+ /* Sanity check */
+ if (plat_name_len + pos > mib_info->mib_len || plat_name_len < 2) {
+ SLSI_ERR_NODEV("Bad HCF FFFF key length %zu\n",
+ plat_name_len);
+ return -EINVAL; /* Implausible length */
+ }
+
+ /* Skip vldata header SC-506179-SP. This conveys the
+ * length of the platform string and is 2 or 3 octets long
+ * depending on the length of the string.
+ */
+ {
+#define SLSI_VLDATA_STRING 0xA0
+#define SLSI_VLDATA_LEN 0x17
+
+ u8 vlen_hdr = mib_info->mib_data[pos++];
+ u8 vlen_len = vlen_hdr & SLSI_VLDATA_LEN; /* size of length field */
+
+ /* Skip vlen header octet */
+ plat_name_len--;
+
+ SLSI_DBG1_NODEV(SLSI_INIT_DEINIT, "vlhdr 0x%x, len %u\n", vlen_hdr, vlen_len);
+
+ /* Is it an octet string type? */
+ if (!(vlen_hdr & SLSI_VLDATA_STRING)) {
+ SLSI_ERR_NODEV("No string vlen header 0x%x\n", vlen_hdr);
+ return -EINVAL;
+ }
+
+ /* Handle 1 or 2 octet length field only */
+ if (vlen_len > 2) {
+ SLSI_ERR_NODEV("Too long octet string header %u\n", vlen_len);
+ return -EINVAL;
+ }
+
+ /* Skip over the string length field.
+ * Note we just use datalength anyway.
+ */
+ pos += vlen_len;
+ plat_name_len -= vlen_len;
+ }
+
+ /* Limit the platform name to space in driver and read */
+ {
+ size_t trunc_len = plat_name_len;
+
+ if (trunc_len > sizeof(mib_info->platform))
+ trunc_len = sizeof(mib_info->platform) - 1;
+
+ /* Extract platform name */
+ memcpy(mib_info->platform, &mib_info->mib_data[pos], trunc_len);
+ mib_info->platform[trunc_len] = '\0';
+
+ /* Print non-truncated string in log now */
+ SLSI_INFO_NODEV("MIB platform: %.*s\n", (int)plat_name_len, &mib_info->mib_data[pos]);
+
+ SLSI_DBG1_NODEV(SLSI_INIT_DEINIT, "plat_name_len: %zu + %u\n",
+ plat_name_len, (plat_name_len & 1));
+ }
+
+ /* Pad string to 16-bit boundary */
+ plat_name_len += (plat_name_len & 1);
+ pos += plat_name_len;
+
+ /* Advance over the keys we read, FW doesn't need them */
+ mib_info->mib_data += pos;
+ mib_info->mib_len -= pos;
+
+ SLSI_DBG1_NODEV(SLSI_INIT_DEINIT, "Skip %d octets HCF payload\n", pos);
+
+ return 0;
+}
+
#define MGT_HASH_SIZE_BYTES 2 /* Hash will be contained in a uint32 */
#define MGT_HASH_OFFSET 4
static int slsi_mib_open_file(struct slsi_dev *sdev, struct slsi_dev_mib_info *mib_info, const struct firmware **fw)
r = mx140_file_request_conf(sdev->maxwell_core, &e, "wlan", mib_file_name);
if (r || (!e)) {
- SLSI_DBG2(sdev, SLSI_INIT_DEINIT, "Skip MIB download as file [%s] is NOT found and is optional\n", mib_file_name);
+ SLSI_DBG2(sdev, SLSI_INIT_DEINIT, "Skip MIB download as file %s is NOT found\n", mib_file_name);
*fw = e;
- return 0;
+ return r;
}
mib_info->mib_data = (u8 *)e->data;
/* All good - skip header and continue */
mib_info->mib_data += 8;
mib_info->mib_len -= 8;
+
+ /* Extract platform name if available */
+ slsi_mib_get_platform(mib_info);
} else {
/* Bad header */
SLSI_ERR(sdev, "configuration file '%s' has bad header\n", mib_info->mib_file_name);
{ SLSI_PSID_UNIFI_HARDWARE_PLATFORM, {0, 0} },
{ SLSI_PSID_UNIFI_REG_DOM_VERSION, {0, 0} },
{ SLSI_PSID_UNIFI_NAN_ENABLED, {0, 0} },
- { SLSI_PSID_UNIFI_FORCED_SCHEDULE_DURATION, {0, 0} },
+ { SLSI_PSID_UNIFI_DEFAULT_DWELL_TIME, {0, 0} },
#ifdef CONFIG_SCSC_WLAN_WIFI_SHARING
{ SLSI_PSID_UNIFI_WI_FI_SHARING5_GHZ_CHANNEL, {0, 0} },
#endif
}
#endif
+int slsi_mib_get_rtt_cap(struct slsi_dev *sdev, struct net_device *dev, struct slsi_rtt_capabilities *cap)
+{
+ struct slsi_mib_data supported_rtt_capab = { 0, NULL };
+ struct slsi_mib_data mibrsp = { 0, NULL };
+ struct slsi_mib_value *values = NULL;
+
+ struct slsi_mib_get_entry get_values[] = { { SLSI_PSID_UNIFI_RTT_CAPABILITIES, { 0, 0 } } };
+
+ mibrsp.dataLength = 64;
+ mibrsp.data = kmalloc(mibrsp.dataLength, GFP_KERNEL);
+ if (!mibrsp.data) {
+ SLSI_ERR(sdev, "Cannot kmalloc %d bytes\n", mibrsp.dataLength);
+ kfree(mibrsp.data);
+ return -ENOMEM;
+ }
+
+ values = slsi_read_mibs(sdev, dev, get_values, 1, &mibrsp);
+ if (!values) {
+ kfree(mibrsp.data);
+ return -EINVAL;
+ }
+
+ if (values[0].type != SLSI_MIB_TYPE_OCTET) {
+ SLSI_ERR(sdev, "Invalid type (%d) for SLSI_PSID_UNIFI_RTT_CAPABILITIES", values[0].type);
+ kfree(mibrsp.data);
+ kfree(values);
+ return -EINVAL;
+ }
+ supported_rtt_capab = values[0].u.octetValue;
+ cap->rtt_one_sided_supported = supported_rtt_capab.data[0];
+ cap->rtt_ftm_supported = supported_rtt_capab.data[1];
+ cap->lci_support = supported_rtt_capab.data[2];
+ cap->lcr_support = supported_rtt_capab.data[3];
+ cap->responder_supported = supported_rtt_capab.data[4];
+ cap->preamble_support = supported_rtt_capab.data[5];
+ cap->bw_support = supported_rtt_capab.data[6];
+ cap->mc_version = supported_rtt_capab.data[7];
+
+ kfree(values);
+ kfree(mibrsp.data);
+ return 0;
+}
+
struct slsi_peer *slsi_peer_add(struct slsi_dev *sdev, struct net_device *dev, u8 *peer_address, u16 aid)
{
struct netdev_vif *ndev_vif = netdev_priv(dev);
/* MUST be done first to ensure that other code doesn't treat the VIF as still active */
ndev_vif->activated = false;
+#ifndef CONFIG_SCSC_WLAN_RX_NAPI
slsi_skb_queue_purge(&ndev_vif->rx_data.queue);
-
- slsi_skb_queue_purge(&ndev_vif->rx_data.queue);
-
+#endif
for (i = 0; i < (SLSI_ADHOC_PEER_CONNECTIONS_MAX); i++) {
struct slsi_peer *peer = ndev_vif->peer_sta_record[i];
static int slsi_get_sta_mode(struct net_device *dev, const u8 *last_peer_mac)
{
struct netdev_vif *ndev_vif = netdev_priv(dev);
- struct slsi_dev *sdev;
+ struct slsi_dev *sdev = ndev_vif->sdev;
struct slsi_peer *last_peer;
const u8 *peer_ie;
return r;
}
- SLSI_NET_DBG1(dev, SLSI_CFG80211, "number of Channels %d\n", n_channels);
-
ndev_vif = netdev_priv(dev);
SLSI_MUTEX_LOCK(ndev_vif->scan_mutex);
SLSI_MUTEX_LOCK(sdev->device_config_mutex);
sdev->device_config.ap_auto_chan = channels[selected_index]->hw_value & 0xFF;
SLSI_MUTEX_UNLOCK(sdev->device_config_mutex);
+
+ SLSI_INFO(sdev, "Channel selected = %d", sdev->device_config.ap_auto_chan);
}
slsi_skb_queue_purge(&unique_scan_results);
ndev_vif->scan[SLSI_SCAN_HW_ID].is_blocking_scan = false;
}
}
-void slsi_hs2_dump_public_action_subtype(struct ieee80211_mgmt *mgmt, bool tx)
+void slsi_wlan_dump_public_action_subtype(struct ieee80211_mgmt *mgmt, bool tx)
{
u8 action_code = ((u8 *)&mgmt->u.action.u)[0];
+ u8 action_category = mgmt->u.action.category;
- switch (action_code) {
- case SLSI_PA_GAS_INITIAL_REQ:
- SLSI_DBG1_NODEV(SLSI_CFG80211, "%s: GAS Initial Request\n", tx ? "TX" : "RX");
- break;
- case SLSI_PA_GAS_INITIAL_RSP:
- SLSI_DBG1_NODEV(SLSI_CFG80211, "%s: GAS Initial Response\n", tx ? "TX" : "RX");
- break;
- case SLSI_PA_GAS_COMEBACK_REQ:
- SLSI_DBG1_NODEV(SLSI_CFG80211, "%s: GAS Comeback Request\n", tx ? "TX" : "RX");
- break;
- case SLSI_PA_GAS_COMEBACK_RSP:
- SLSI_DBG1_NODEV(SLSI_CFG80211, "%s: GAS Comeback Response\n", tx ? "TX" : "RX");
- break;
- default:
- SLSI_DBG1_NODEV(SLSI_CFG80211, "Unknown GAS Frame : %d\n", action_code);
+ switch (action_category) {
+ case WLAN_CATEGORY_RADIO_MEASUREMENT:
+ switch (action_code) {
+ case SLSI_RM_NEIGH_REP_REQ:
+ SLSI_DBG1_NODEV(SLSI_CFG80211, "%s: RM Neigh Report Request\n", tx ? "TX" : "RX");
+ break;
+ case SLSI_RM_NEIGH_REP_RSP:
+ SLSI_DBG1_NODEV(SLSI_CFG80211, "%s: RM Neigh Report Response\n", tx ? "TX" : "RX");
+ break;
+ default:
+ SLSI_DBG1_NODEV(SLSI_CFG80211, "Unknown Radio Measurement Frame : %d\n", action_code);
+ }
+ case WLAN_CATEGORY_PUBLIC:
+ switch (action_code) {
+ case SLSI_PA_GAS_INITIAL_REQ:
+ SLSI_DBG1_NODEV(SLSI_CFG80211, "%s: GAS Initial Request\n", tx ? "TX" : "RX");
+ break;
+ case SLSI_PA_GAS_INITIAL_RSP:
+ SLSI_DBG1_NODEV(SLSI_CFG80211, "%s: GAS Initial Response\n", tx ? "TX" : "RX");
+ break;
+ case SLSI_PA_GAS_COMEBACK_REQ:
+ SLSI_DBG1_NODEV(SLSI_CFG80211, "%s: GAS Comeback Request\n", tx ? "TX" : "RX");
+ break;
+ case SLSI_PA_GAS_COMEBACK_RSP:
+ SLSI_DBG1_NODEV(SLSI_CFG80211, "%s: GAS Comeback Response\n", tx ? "TX" : "RX");
+ break;
+ default:
+ SLSI_DBG1_NODEV(SLSI_CFG80211, "Unknown GAS Frame : %d\n", action_code);
+ }
}
}
u8 *ds_params_ie, u8 *ht_operation_ie, struct ieee80211_mgmt *mgmt,
u16 beacon_ie_head_len)
{
- ds_params_ie = (u8 *)cfg80211_find_ie(WLAN_EID_DS_PARAMS, mgmt->u.beacon.variable, beacon_ie_head_len);
slsi_modify_ies(dev, WLAN_EID_DS_PARAMS, mgmt->u.beacon.variable,
beacon_ie_head_len, 2, ieee80211_frequency_to_channel(settings->chandef.chan->center_freq));
- ht_operation_ie = (u8 *)cfg80211_find_ie(WLAN_EID_HT_OPERATION, settings->beacon.tail,
- settings->beacon.tail_len);
slsi_modify_ies(dev, WLAN_EID_HT_OPERATION, (u8 *)settings->beacon.tail,
settings->beacon.tail_len, 2,
ieee80211_frequency_to_channel(settings->chandef.chan->center_freq));
return 0;
}
#endif
+#ifdef CONFIG_SCSC_WLAN_ENABLE_MAC_RANDOMISATION
+int slsi_set_mac_randomisation_mask(struct slsi_dev *sdev, u8 *mac_address_mask)
+{
+ int r = 0;
+ struct slsi_mib_data mib_data = { 0, NULL };
+ SLSI_DBG1(sdev, SLSI_CFG80211, "Mask is :%pM\n", mac_address_mask);
+ r = slsi_mib_encode_octet(&mib_data, SLSI_PSID_UNIFI_MAC_ADDRESS_RANDOMISATION_MASK, ETH_ALEN,
+ mac_address_mask, 0);
+ if (r != SLSI_MIB_STATUS_SUCCESS) {
+ SLSI_ERR(sdev, "Err setting unifiMacAddrRandomistaionMask MIB. error = %d\n", r);
+ if (sdev->scan_addr_set) {
+ struct slsi_mib_data mib_data_randomization_activated = { 0, NULL };
+
+ r = slsi_mib_encode_bool(&mib_data_randomization_activated,
+ SLSI_PSID_UNIFI_MAC_ADDRESS_RANDOMISATION_ACTIVATED, 1, 0);
+ if (r != SLSI_MIB_STATUS_SUCCESS) {
+ SLSI_ERR(sdev, "UNIFI_MAC_ADDRESS_RANDOMISATION_ACTIVATED: no mem for MIB\n");
+ return -ENOMEM;
+ }
+
+ r = slsi_mlme_set(sdev, NULL, mib_data_randomization_activated.data,
+ mib_data_randomization_activated.dataLength);
+
+ kfree(mib_data_randomization_activated.data);
+
+ if (r)
+ SLSI_ERR(sdev, "Err setting unifiMacAddrRandomistaionActivated MIB. error = %d\n", r);
+ return r;
+ }
+ return -ENOMEM;
+ }
+ if (mib_data.dataLength == 0) {
+ SLSI_WARN(sdev, "Mib Data length is Zero\n");
+ return -EINVAL;
+ }
+ r = slsi_mlme_set(sdev, NULL, mib_data.data, mib_data.dataLength);
+ if (r)
+ SLSI_ERR(sdev, "Err setting Randomized mac mask= %d\n", r);
+ kfree(mib_data.data);
+ return r;
+}
+#endif
/* Set the new country code and read the regulatory parameters of updated country. */
int slsi_set_country_update_regd(struct slsi_dev *sdev, const char *alpha2_code, int size)
{
SLSI_MUTEX_LOCK(ndev_vif->vif_mutex);
SLSI_NET_DBG1(ndev_vif->wdev.netdev, SLSI_CFG80211, "Delete HS vif duration expired - Deactivate unsync vif\n");
- slsi_hs2_vif_deactivate(ndev_vif->sdev, ndev_vif->wdev.netdev, true);
+ slsi_wlan_unsync_vif_deactivate(ndev_vif->sdev, ndev_vif->wdev.netdev, true);
SLSI_MUTEX_UNLOCK(ndev_vif->vif_mutex);
}
-int slsi_hs2_vif_activate(struct slsi_dev *sdev, struct net_device *dev, struct ieee80211_channel *chan, u16 wait)
+int slsi_wlan_unsync_vif_activate(struct slsi_dev *sdev, struct net_device *dev,
+ struct ieee80211_channel *chan, u16 wait)
{
struct netdev_vif *ndev_vif = netdev_priv(dev);
int r = 0;
u8 device_address[ETH_ALEN] = { 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF };
+ u32 action_frame_bmap;
- SLSI_DBG1(sdev, SLSI_INIT_DEINIT, "Activate HS unsync vif\n");
+ SLSI_DBG1(sdev, SLSI_INIT_DEINIT, "Activate wlan unsync vif\n");
WARN_ON(!SLSI_MUTEX_IS_LOCKED(ndev_vif->vif_mutex));
ndev_vif->vif_type = FAPI_VIFTYPE_UNSYNCHRONISED;
- /* Avoid suspend when HS2 unsync VIF is active */
+ /* Avoid suspend when wlan unsync VIF is active */
slsi_wakelock(&sdev->wlan_wl);
/* Interface address and device address are same for unsync vif */
if (slsi_mlme_add_vif(sdev, dev, dev->dev_addr, device_address) != 0) {
- SLSI_NET_ERR(dev, "add vif failed for HS unsync vif\n");
+ SLSI_NET_ERR(dev, "add vif failed for wlan unsync vif\n");
goto exit_with_error;
}
if (slsi_vif_activated(sdev, dev) != 0) {
- SLSI_NET_ERR(dev, "vif activate failed for HS unsync vif\n");
+ SLSI_NET_ERR(dev, "vif activate failed for wlan unsync vif\n");
slsi_mlme_del_vif(sdev, dev);
goto exit_with_error;
}
- sdev->hs2_state = HS2_VIF_ACTIVE;
+ sdev->wlan_unsync_vif_state = WLAN_UNSYNC_VIF_ACTIVE;
INIT_DELAYED_WORK(&ndev_vif->unsync.hs2_del_vif_work, slsi_hs2_unsync_vif_delete_work);
+ action_frame_bmap = SLSI_ACTION_FRAME_PUBLIC | SLSI_ACTION_FRAME_RADIO_MEASUREMENT;
- if (slsi_mlme_register_action_frame(sdev, dev, SLSI_ACTION_FRAME_PUBLIC, SLSI_ACTION_FRAME_PUBLIC) != 0) {
- SLSI_NET_ERR(dev, "Action frame registration failed for HS unsync vif\n");
+ r = slsi_mlme_register_action_frame(sdev, dev, action_frame_bmap, action_frame_bmap);
+ if (r != 0) {
+ SLSI_NET_ERR(dev, "slsi_mlme_register_action_frame failed: resultcode = %d, action_frame_bmap:%d\n",
+ r, action_frame_bmap);
goto exit_with_vif;
}
if (slsi_mlme_set_channel(sdev, dev, chan, SLSI_FW_CHANNEL_DURATION_UNSPECIFIED, 0, 0) != 0) {
- SLSI_NET_ERR(dev, "Set channel failed for HS unsync vif\n");
+ SLSI_NET_ERR(dev, "Set channel failed for wlan unsync vif\n");
goto exit_with_vif;
}
ndev_vif->chan = chan;
return r;
exit_with_vif:
- slsi_hs2_vif_deactivate(sdev, dev, true);
+ slsi_wlan_unsync_vif_deactivate(sdev, dev, true);
exit_with_error:
slsi_wakeunlock(&sdev->wlan_wl);
return -EINVAL;
}
/* Delete unsync vif - DON'T update the vif type */
-void slsi_hs2_vif_deactivate(struct slsi_dev *sdev, struct net_device *dev, bool hw_available)
+void slsi_wlan_unsync_vif_deactivate(struct slsi_dev *sdev, struct net_device *dev, bool hw_available)
{
struct netdev_vif *ndev_vif = netdev_priv(dev);
- SLSI_NET_DBG1(dev, SLSI_INIT_DEINIT, "De-activate HS unsync vif\n");
+ SLSI_NET_DBG1(dev, SLSI_INIT_DEINIT, "De-activate wlan unsync vif\n");
WARN_ON(!SLSI_MUTEX_IS_LOCKED(ndev_vif->vif_mutex));
- if (sdev->hs2_state == HS2_NO_VIF) {
- SLSI_NET_DBG1(dev, SLSI_INIT_DEINIT, "HS unsync vif already deactivated\n");
+ if (sdev->wlan_unsync_vif_state == WLAN_UNSYNC_NO_VIF) {
+ SLSI_NET_DBG1(dev, SLSI_INIT_DEINIT, "wlan unsync vif already deactivated\n");
return;
}
slsi_wakeunlock(&sdev->wlan_wl);
- sdev->hs2_state = HS2_NO_VIF;
+ sdev->wlan_unsync_vif_state = WLAN_UNSYNC_NO_VIF;
ndev_vif->activated = false;
ndev_vif->chan = NULL;
struct wiphy *wiphy = sdev->wiphy;
struct ieee80211_channel *chan;
+ /* If all channels are supported by chip no need disable any channel
+ * So return
+ */
if (sdev->enabled_channel_count == 39)
return;
-
- for (i = 0; i < ARRAY_SIZE(sdev->supported_2g_channels); i++) {
- if (sdev->supported_2g_channels[i] == 0) {
- chan = &wiphy->bands[0]->channels[i];
- chan->flags |= IEEE80211_CHAN_DISABLED;
+ if (wiphy->bands[0]) {
+ for (i = 0; i < ARRAY_SIZE(sdev->supported_2g_channels); i++) {
+ if (sdev->supported_2g_channels[i] == 0) {
+ chan = &wiphy->bands[0]->channels[i];
+ chan->flags |= IEEE80211_CHAN_DISABLED;
+ }
}
}
- if (sdev->band_5g_supported) {
+ if (sdev->band_5g_supported && wiphy->bands[1]) {
for (i = 0; i < ARRAY_SIZE(sdev->supported_5g_channels); i++) {
if (sdev->supported_5g_channels[i] == 0) {
chan = &wiphy->bands[1]->channels[i];
#define SLSI_PA_GAS_COMEBACK_REQ (12)
#define SLSI_PA_GAS_COMEBACK_RSP (13)
+/*Radio Measurement action frames types */
+#define SLSI_RM_NEIGH_REP_REQ (4)
+#define SLSI_RM_NEIGH_REP_RSP (5)
+
/* For service discovery action frames dummy subtype is used by setting the 7th bit */
#define SLSI_PA_GAS_DUMMY_SUBTYPE_MASK 0x80
#define SLSI_PA_GAS_INITIAL_REQ_SUBTYPE (SLSI_PA_GAS_INITIAL_REQ | SLSI_PA_GAS_DUMMY_SUBTYPE_MASK)
int slsi_read_default_country(struct slsi_dev *sdev, u8 *alpha2, u16 index);
int slsi_read_disconnect_ind_timeout(struct slsi_dev *sdev, u16 psid);
int slsi_read_regulatory_rules(struct slsi_dev *sdev, struct slsi_802_11d_reg_domain *domain_info, const char *alpha2);
+#ifdef CONFIG_SCSC_WLAN_ENABLE_MAC_RANDOMISATION
+int slsi_set_mac_randomisation_mask(struct slsi_dev *sdev, u8 *mac_address_mask);
+#endif
int slsi_set_country_update_regd(struct slsi_dev *sdev, const char *alpha2_code, int size);
void slsi_clear_offchannel_data(struct slsi_dev *sdev, bool acquire_lock);
-int slsi_hs2_vif_activate(struct slsi_dev *sdev, struct net_device *dev, struct ieee80211_channel *chan, u16 duration);
-void slsi_hs2_vif_deactivate(struct slsi_dev *sdev, struct net_device *devbool, bool hw_available);
+int slsi_wlan_unsync_vif_activate(struct slsi_dev *sdev, struct net_device *dev,
+ struct ieee80211_channel *chan, u16 duration);
+void slsi_wlan_unsync_vif_deactivate(struct slsi_dev *sdev, struct net_device *devbool, bool hw_available);
int slsi_is_wes_action_frame(const struct ieee80211_mgmt *mgmt);
void slsi_scan_ind_timeout_handle(struct work_struct *work);
void slsi_vif_cleanup(struct slsi_dev *sdev, struct net_device *dev, bool hw_available);
#ifdef CONFIG_SCSC_WLAN_HANG_TEST
int slsi_test_send_hanged_vendor_event(struct net_device *dev);
#endif
-void slsi_hs2_dump_public_action_subtype(struct ieee80211_mgmt *mgmt, bool tx);
+void slsi_wlan_dump_public_action_subtype(struct ieee80211_mgmt *mgmt, bool tx);
void slsi_reset_channel_flags(struct slsi_dev *sdev);
#endif /*__SLSI_MGT_H__*/
/******************************************************************************
*
- * Copyright (c) 2012 - 2017 Samsung Electronics Co., Ltd and its Licensors.
+ * Copyright (c) 2012 - 2018 Samsung Electronics Co., Ltd and its Licensors.
* All rights reserved.
*
*****************************************************************************/
return 1 + length;
}
+size_t slsi_mib_decodeUint64(u8 *buffer, u64 *value)
+{
+ size_t i;
+ u64 v = 0;
+ size_t length = buffer[0] & SLSI_MIB_LENGTH_MASK;
+
+ if (!(buffer[0] & SLSI_MIB_MORE_MASK)) {
+ *value = buffer[0] & 0x7F;
+ return 1;
+ }
+
+ for (i = 0; i < length; i++) {
+ v = (v << 8);
+ v |= buffer[1 + i];
+ }
+
+ *value = v;
+
+ return 1 + length;
+}
+
size_t slsi_mib_decodeInt32(u8 *buffer, s32 *value)
{
size_t i;
return 1 + length;
}
+size_t slsi_mib_decodeInt64(u8 *buffer, s64 *value)
+{
+ size_t i;
+ u64 v = 0xFFFFFFFFFFFFFFFFULL;
+ size_t length = buffer[0] & SLSI_MIB_LENGTH_MASK;
+
+ if (!(buffer[0] & SLSI_MIB_SIGN_MASK))
+ /* just use the Unsigned Decoder */
+ return slsi_mib_decodeUint64(buffer, (u64 *)value);
+
+ if (!(buffer[0] & SLSI_MIB_MORE_MASK)) {
+ *value = (s64)(0xFFFFFFFFFFFFFF80ULL | buffer[0]);
+ return 1;
+ }
+
+ for (i = 0; i < length; i++) {
+ v = (v << 8);
+ v |= buffer[1 + i];
+ }
+
+ *value = (s64)v;
+
+ return 1 + length;
+}
+
/* Just references the oid in the existing buffer. No new memory is allcated */
size_t slsi_mib_decode_octet_str(u8 *buffer, struct slsi_mib_data *octet_value)
{
size_t slsi_mib_decodeUint32(u8 *buffer, u32 *value);
size_t slsi_mib_decodeInt32(u8 *buffer, s32 *value);
+size_t slsi_mib_decodeUint64(u8 *buffer, u64 *value);
+size_t slsi_mib_decodeInt64(u8 *buffer, s64 *value);
size_t slsi_mib_decode_octet_str(u8 *buffer, struct slsi_mib_data *octetValue);
/*******************************************************************************
* MAX : 65535
* DEFAULT : 1
* DESCRIPTION :
- * The minimum time that needs to pass after the most recent TPU SP, before
- * a RAME_TPU_SP indication can be sent to MLME
+ * The minimum time after the last TPU SP, before a RAME_TPU_SP indication
+ * can be issued.
*******************************************************************************/
#define SLSI_PSID_DOT11_TDLS_PEER_UAPSD_INDICATION_WINDOW 0x0035
* NAME : Dot11RtsThreshold
* PSID : 121 (0x0079)
* PER INTERFACE?: NO
- * TYPE : SlsiUint16
+ * TYPE : SlsiUint32
* UNITS : octet
* MIN : 0
* MAX : 65536
- * DEFAULT : 9000
+ * DEFAULT : 65536
* DESCRIPTION :
* Size of an MPDU, below which an RTS/CTS handshake shall not be performed,
* except as RTS/CTS is used as a cross modulation protection mechanism as
* PSID : 2000 (0x07D0)
* PER INTERFACE?: NO
* TYPE : SlsiUint16
- * UNITS : milliseconds
* MIN : 0
* MAX : 65535
- * DEFAULT : 3000
+ * DEFAULT :
* DESCRIPTION :
- * Firmware waits for unifiMLMEConnectionTimeOut of no successful Tx/Rx
- * (including beacon) to/from AP before it disconnects from AP.For STA case
- * - Setting it to less than 3 seconds may result in frequent disconnection
- * with the AP
+ * Depricated
*******************************************************************************/
#define SLSI_PSID_UNIFI_MLME_CONNECTION_TIMEOUT 0x07D0
* PSID : 2007 (0x07D7)
* PER INTERFACE?: NO
* TYPE : SlsiUint16
- * UNITS : TU
* MIN : 0
* MAX : 65535
- * DEFAULT : 70
+ * DEFAULT :
* DESCRIPTION :
- * Time between transmissions of broadcast probe requests on a given channel
- * when performing an active scan.
+ * Deprecated.
*******************************************************************************/
#define SLSI_PSID_UNIFI_MLME_SCAN_PROBE_INTERVAL 0x07D7
* MAX : 65535
* DEFAULT :
* DESCRIPTION :
- * Depricate
+ * Depricated
*******************************************************************************/
#define SLSI_PSID_UNIFI_MLME_SCAN_MAXIMUM_AGE 0x07DE
* TYPE : SlsiUint16
* MIN : 0
* MAX : 65535
- * DEFAULT : 40
+ * DEFAULT : 100
* DESCRIPTION :
* Max number of scan results (for all scans) which will be stored before
* the oldest result is discarded, irrespective of its age. The value 0
*******************************************************************************/
#define SLSI_PSID_UNIFI_MLME_AUTONOMOUS_SCAN_NOISY 0x07E0
+/*******************************************************************************
+ * NAME : UnifiChannelBusyThreshold
+ * PSID : 2018 (0x07E2)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * MIN : 1
+ * MAX : 100
+ * DEFAULT : 30
+ * DESCRIPTION :
+ * The threshold in percentage of CCA busy time when a channel would be
+ * considered busy
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_CHANNEL_BUSY_THRESHOLD 0x07E2
+
/*******************************************************************************
* NAME : UnifiFirmwareBuildId
* PSID : 2021 (0x07E5)
* TYPE : SlsiUint8
* MIN : 21
* MAX : 21
- * DEFAULT : { 0X6F, 0X01, 0X17, 0XFF, 0X00, 0X00, 0X00, 0X01, 0X00, 0X00, 0X00, 0X00, 0X00, 0X00, 0X00, 0X00, 0X00, 0X00, 0X00, 0X00, 0X00 }
+ * DEFAULT : { 0XEF, 0X0A, 0X17, 0XFF, 0XFF, 0X00, 0X00, 0X01, 0X00, 0X00, 0X00, 0X00, 0X00, 0X00, 0X00, 0X00, 0X00, 0X00, 0X00, 0X00, 0X00 }
* DESCRIPTION :
* HT capabilities of the chip. See SC-503520-SP for further details. NOTE:
* Greenfield has been disabled due to interoperability issues wuth SGI.
* MAX : 1
* DEFAULT : FALSE
* DESCRIPTION :
- * Enables 40Mz wide channels in the 2.4G band
+ * Enables 40Mz wide channels in the 2.4G band for STA. Our AP does not
+ * support this.
*******************************************************************************/
#define SLSI_PSID_UNIFI24_G40_MHZ_CHANNELS 0x07F3
* TYPE : SlsiUint8
* MIN : 5
* MAX : 5
- * DEFAULT : { 0X71, 0X00, 0X00, 0X00, 0X00 }
+ * DEFAULT : { 0X71, 0X00, 0X00, 0X00, 0X04 }
* DESCRIPTION :
* RM Enabled capabilities of the chip. See SC-503520-SP for further
* details.
*******************************************************************************/
#define SLSI_PSID_UNIFI_HT_ACTIVATED 0x07FE
+/*******************************************************************************
+ * NAME : UnifiEnableTwoSimultaneousActiveScansSameBand
+ * PSID : 2047 (0x07FF)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiBool
+ * MIN : 0
+ * MAX : 1
+ * DEFAULT : FALSE
+ * DESCRIPTION :
+ * Enable two active scans to be simultaneously scheduled on two distinct
+ * channels on the same.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_ENABLE_TWO_SIMULTANEOUS_ACTIVE_SCANS_SAME_BAND 0x07FF
+
/*******************************************************************************
* NAME : UnifiRoamingEnabled
* PSID : 2049 (0x0801)
*******************************************************************************/
#define SLSI_PSID_UNIFI_AP_OLBC_INTERVAL 0x081D
+/*******************************************************************************
+ * NAME : UnifiOffchannelScheduleTimeout
+ * PSID : 2079 (0x081F)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT : 1000
+ * DESCRIPTION :
+ * Maximum timeout in ms the Offchannel FSM will wait until the complete
+ * dwell time is scheduled
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_OFFCHANNEL_SCHEDULE_TIMEOUT 0x081F
+
/*******************************************************************************
* NAME : UnifiFrameResponseTimeout
* PSID : 2080 (0x0820)
*******************************************************************************/
#define SLSI_PSID_UNIFI_MLME_SCAN_STOP_IF_LESS_THAN_XFRAMES 0x0828
+/*******************************************************************************
+ * NAME : UnifiApAssociationTimeout
+ * PSID : 2089 (0x0829)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT : 2000
+ * DESCRIPTION :
+ * SoftAP: Permitted time for a station to complete associatation with FW
+ * acting as AP in milliseconds.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_AP_ASSOCIATION_TIMEOUT 0x0829
+
/*******************************************************************************
* NAME : UnifiPeerBandwidth
* PSID : 2094 (0x082E)
*******************************************************************************/
#define SLSI_PSID_UNIFI_MLME_CLI_INACTIVITY_TIMEOUT 0x0833
+/*******************************************************************************
+ * NAME : UnifiMlmeStationInitialKickTimeout
+ * PSID : 2100 (0x0834)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * UNITS : millisecond
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT : 50
+ * DESCRIPTION :
+ * Timeout for sending the AP a NULL frame to kick off the EAPOL exchange.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_MLME_STATION_INITIAL_KICK_TIMEOUT 0x0834
+
/*******************************************************************************
* NAME : UnifiUartConfigure
* PSID : 2110 (0x083E)
*******************************************************************************/
#define SLSI_PSID_UNIFI_ENABLE_DORM 0x085E
-/*******************************************************************************
- * NAME : UnifiDisableDormWhenBtOn
- * PSID : 2143 (0x085F)
- * PER INTERFACE?: NO
- * TYPE : SlsiBool
- * MIN : 0
- * MAX : 1
- * DEFAULT : FALSE
- * DESCRIPTION :
- * Dorm/deep sleep would be dynamically disabled when BT is turned ON if the
- * value is TRUE, even though unifiEnableDorm is TRUE. For more details,
- * take a look at SSB-17864.
- *******************************************************************************/
-#define SLSI_PSID_UNIFI_DISABLE_DORM_WHEN_BT_ON 0x085F
-
/*******************************************************************************
* NAME : UnifiExternalClockDetect
* PSID : 2146 (0x0862)
* PSID : 2154 (0x086A)
* PER INTERFACE?: NO
* TYPE : SlsiUint8
- * MIN : 20
- * MAX : 20
+ * MIN : 18
+ * MAX : 18
* DEFAULT :
* DESCRIPTION :
* Scan parameters. Each row of the table contains 2 entries for a scan:
* first entry when there is 0 registered VIFs, second - when there is 1 or
* more registered VIFs. Entry has the following structure: octet 0 - Scan
- * priority (uint8_t) octet 1 - Enable Early Channel Exit (uint8_t as bool)
- * octet 2 ~ 3 - Probe Interval in Time Units (uint16_t) octet 4 ~ 5 - Max
- * Active Channel Time in Time Units (uint16_t) octet 6 ~ 7 - Max Passive
- * Channel Time in Time Units (uint16_t) octet 8 ~ 9 - Scan Policy
- * (uint16_t) Size of each entry is 10 octets, row size is 20 octets. A Time
- * Units value specifies a time interval as a multiple of TU (1024 us).
+ * priority (uint8) octet 1 - Enable Early Channel Exit (uint8 as bool)
+ * octet 2 ~ 3 - Probe Interval in Time Units (uint16) octet 4 ~ 5 - Max
+ * Active Channel Time in Time Units (uint16) octet 6 ~ 7 - Max Passive
+ * Channel Time in Time Units (uint16) octet 8 - Scan Policy (uint8) Size of
+ * each entry is 9 octets, row size is 18 octets. A Time Units value
+ * specifies a time interval as a multiple of TU (1024 us).
*******************************************************************************/
#define SLSI_PSID_UNIFI_SCAN_PARAMETERS 0x086A
*******************************************************************************/
#define SLSI_PSID_UNIFI_CURRENT_TSF_TIME 0x08AA
+/*******************************************************************************
+ * NAME : UnifiBaRxEnableTid
+ * PSID : 2219 (0x08AB)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint32
+ * MIN : 0
+ * MAX : 4294967295
+ * DEFAULT : 0X1555
+ * DESCRIPTION :
+ * Configure Block Ack RX on a per-TID basis. Bit mask is two bits per TID
+ * (B1 = Not Used, B0 = enable).
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_BA_RX_ENABLE_TID 0x08AB
+
/*******************************************************************************
* NAME : UnifiBaTxEnableTid
* PSID : 2221 (0x08AD)
* PER INTERFACE?: NO
* TYPE : SlsiUint16
* MIN : 1
- * MAX : 5
- * DEFAULT : 1
+ * MAX : 4
+ * DEFAULT : 2
* DESCRIPTION :
* Defines the maximum number of A-MSDU sub-frames per A-MSDU. A value of 1
* indicates A-MSDU aggregation has been disabled
* DEFAULT : 0X3FFF01
* DESCRIPTION :
* Block Ack Configuration. It is composed of A-MSDU supported, TX MPDU per
- * A-MPDU, RX Buffer size, TX Buffer size and Block Ack Timeout. see
- * init_mlme_ba() for more detail
+ * A-MPDU, RX Buffer size, TX Buffer size and Block Ack Timeout.
*******************************************************************************/
#define SLSI_PSID_UNIFI_BA_CONFIG 0x08B1
+/*******************************************************************************
+ * NAME : UnifiBaTxMaxNumber
+ * PSID : 2226 (0x08B2)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT : 0X10
+ * DESCRIPTION :
+ * Block Ack Configuration. Maximum number of BAs. Limited by HW.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_BA_TX_MAX_NUMBER 0x08B2
+
/*******************************************************************************
* NAME : UnifiBeaconReceived
* PSID : 2228 (0x08B4)
* DESCRIPTION :
* is used to access throughput related counters that can help diagnose
* throughput problems. The index of the MIB will access different counters,
- * as described in SC-506328-DD.
+ * as described in SC-506328-DD. Setting any index for a VIF to any value,
+ * clears all DPLP debug stats for the MAC instance used by the VIF. This is
+ * useful mainly for debugging LAA or small scale throughput issues that
+ * require short term collection of the statistics.
*******************************************************************************/
#define SLSI_PSID_UNIFI_THROUGHPUT_DEBUG 0x08CE
* MAX : 147
* DEFAULT :
* DESCRIPTION :
- * Write a static DPD LUT to the FW
+ * Write a static DPD LUT to the FW, read DPD LUT from hardware
*******************************************************************************/
#define SLSI_PSID_UNIFI_LOAD_DPD_LUT 0x08CF
* PSID : 2257 (0x08D1)
* PER INTERFACE?: NO
* TYPE : SlsiUint8
- * MIN : 13
- * MAX : 13
+ * MIN : 14
+ * MAX : 14
* DEFAULT :
* DESCRIPTION :
* DPD pre-distort gains. Takes a range of frequencies, where f_min <=
*******************************************************************************/
#define SLSI_PSID_UNIFI_MAC_BEACON_TIMEOUT 0x08DE
+/*******************************************************************************
+ * NAME : UnifiStaUsesOneAntennaWhenIdle
+ * PSID : 2274 (0x08E2)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiBool
+ * MIN : 0
+ * MAX : 1
+ * DEFAULT : TRUE
+ * DESCRIPTION :
+ * Allow the platform to downgrade antenna usage for STA VIFs to 1 if the
+ * VIF is idle. Only valid for multi-radio platforms.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_STA_USES_ONE_ANTENNA_WHEN_IDLE 0x08E2
+
+/*******************************************************************************
+ * NAME : UnifiStaUsesMultiAntennasDuringConnect
+ * PSID : 2275 (0x08E3)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiBool
+ * MIN : 0
+ * MAX : 1
+ * DEFAULT : TRUE
+ * DESCRIPTION :
+ * Allow the platform to use multiple antennas for STA VIFs during the
+ * connect phase. Only valid for multi-radio platforms.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_STA_USES_MULTI_ANTENNAS_DURING_CONNECT 0x08E3
+
+/*******************************************************************************
+ * NAME : UnifiApUsesOneAntennaWhenPeersIdle
+ * PSID : 2276 (0x08E4)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiBool
+ * MIN : 0
+ * MAX : 1
+ * DEFAULT : TRUE
+ * DESCRIPTION :
+ * Allow the platform to downgrade antenna usage for AP VIFs when all
+ * connected peers are idle. Only valid for multi-radio platforms.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_AP_USES_ONE_ANTENNA_WHEN_PEERS_IDLE 0x08E4
+
+/*******************************************************************************
+ * NAME : UnifiUpdateAntennaCapabilitiesWhenScanning
+ * PSID : 2277 (0x08E5)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiBool
+ * MIN : 0
+ * MAX : 1
+ * DEFAULT : FALSE
+ * DESCRIPTION :
+ * Specify whether antenna scan activities will be allowed to cause an
+ * update of VIF capability. Only valid for multi-radio platforms. WARNING:
+ * Changing this value after system start-up will have no effect.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_UPDATE_ANTENNA_CAPABILITIES_WHEN_SCANNING 0x08E5
+
+/*******************************************************************************
+ * NAME : UnifiLoadDpdLutPerRadio
+ * PSID : 2280 (0x08E8)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint8
+ * MIN : 147
+ * MAX : 147
+ * DEFAULT :
+ * DESCRIPTION :
+ * Write a static DPD LUT to the FW, read DPD LUT from hardware (for devices
+ * that support multiple radios)
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_LOAD_DPD_LUT_PER_RADIO 0x08E8
+
+/*******************************************************************************
+ * NAME : UnifiOverrideDpdLutPerRadio
+ * PSID : 2281 (0x08E9)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint8
+ * MIN : 147
+ * MAX : 147
+ * DEFAULT :
+ * DESCRIPTION :
+ * Write a DPD LUT directly to the HW (for devices that support multiple
+ * radios)
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_OVERRIDE_DPD_LUT_PER_RADIO 0x08E9
+
+/*******************************************************************************
+ * NAME : UnifiRoamDeauthReason
+ * PSID : 2294 (0x08F6)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT : 3
+ * DESCRIPTION :
+ * A deauthentication reason for which the STA will trigger a roaming scan
+ * rather than disconnect directly.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_ROAM_DEAUTH_REASON 0x08F6
+
+/*******************************************************************************
+ * NAME : UnifiCuRoamfactor
+ * PSID : 2295 (0x08F7)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT :
+ * DESCRIPTION :
+ * Table allocating CUfactor to Channel Utilisation values range.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_CU_ROAMFACTOR 0x08F7
+
+/*******************************************************************************
+ * NAME : UnifiRoamCuHighLowPoints
+ * PSID : 2296 (0x08F8)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT :
+ * DESCRIPTION :
+ * Table allocating the high and low points for computing the linear
+ * CUfactor.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_ROAM_CU_HIGH_LOW_POINTS 0x08F8
+
/*******************************************************************************
* NAME : UnifiRoamRssiHighLowPoints
* PSID : 2297 (0x08F9)
*******************************************************************************/
#define SLSI_PSID_UNIFI_CU_ROAMWEIGHT 0x08FF
-/*******************************************************************************
- * NAME : UnifiCuRoamfactor
- * PSID : 2304 (0x0900)
- * PER INTERFACE?: NO
- * TYPE : SlsiUint16
- * MIN : 0
- * MAX : 65535
- * DEFAULT :
- * DESCRIPTION :
- * Table allocating CUfactor to Channel Utilization values range.
- *******************************************************************************/
-#define SLSI_PSID_UNIFI_CU_ROAMFACTOR 0x0900
-
/*******************************************************************************
* NAME : UnifiRssiRoamweight
* PSID : 2305 (0x0901)
*******************************************************************************/
#define SLSI_PSID_UNIFI_ROAM_BSS_LOAD_MONITORING_FREQUENCY 0x0905
+/*******************************************************************************
+ * NAME : UnifiRoamBlacklistSize
+ * PSID : 2310 (0x0906)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * UNITS : entries
+ * MIN : 0
+ * MAX : 100
+ * DEFAULT : 5
+ * DESCRIPTION :
+ * Do not remove! Read by the host! And then passed up to the framework.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_ROAM_BLACKLIST_SIZE 0x0906
+
/*******************************************************************************
* NAME : UnifiCuMeasurementInterval
* PSID : 2311 (0x0907)
#define SLSI_PSID_UNIFI_AP_MIMO_USED 0x0909
/*******************************************************************************
- * NAME : UnifiRoamOffloaded4wshkTimeout
+ * NAME : UnifiRoamEapolTimeout
* PSID : 2314 (0x090A)
* PER INTERFACE?: NO
* TYPE : SlsiUint16
* MAX : 100
* DEFAULT : 10
* DESCRIPTION :
- * Maximum time allowed before an attempt to do an offloaded 4 way handshake
- * is considered failed?
+ * Maximum time allowed for an offloaded Eapol (4 way handshake).
*******************************************************************************/
-#define SLSI_PSID_UNIFI_ROAM_OFFLOADED4WSHK_TIMEOUT 0x090A
+#define SLSI_PSID_UNIFI_ROAM_EAPOL_TIMEOUT 0x090A
/*******************************************************************************
* NAME : UnifiRoamingCount
* MAX : 1
* DEFAULT : FALSE
* DESCRIPTION :
- * Enable reporting of the fate of the TX packets sent by the host
+ * Enable reporting of the fate of the TX packets sent by the host.This mib
+ * value will be updated if "unifiRameUpdateMibs" mib is toggled
*******************************************************************************/
#define SLSI_PSID_UNIFI_MA_PACKET_FATE_ENABLED 0x0911
/*******************************************************************************
- * NAME : UnifiCsrOnlyEifsDuration
- * PSID : 2362 (0x093A)
+ * NAME : UnifiLaaNssSpeculationIntervalSlotTime
+ * PSID : 2330 (0x091A)
* PER INTERFACE?: NO
* TYPE : SlsiUint16
- * UNITS : microseconds
* MIN : 0
* MAX : 65535
- * DEFAULT : 12
+ * DEFAULT : 300
* DESCRIPTION :
- * Specifies time that is used for EIFS. A value of 0 causes the build in
- * value to be used.
+ * For Link Adaptation Algorithm. It defines the repeatable amount of time,
+ * in ms, that firmware will start to send speculation frames for spatial
+ * streams.
*******************************************************************************/
-#define SLSI_PSID_UNIFI_CSR_ONLY_EIFS_DURATION 0x093A
+#define SLSI_PSID_UNIFI_LAA_NSS_SPECULATION_INTERVAL_SLOT_TIME 0x091A
/*******************************************************************************
- * NAME : UnifiOverrideDefaultBetxopForHt
- * PSID : 2364 (0x093C)
+ * NAME : UnifiLaaNssSpeculationIntervalSlotMaxNum
+ * PSID : 2331 (0x091B)
* PER INTERFACE?: NO
* TYPE : SlsiUint16
* MIN : 0
* MAX : 65535
- * DEFAULT : 171
+ * DEFAULT : 5
* DESCRIPTION :
- * When set to non-zero value then this will override the BE TXOP for 11n
- * and higher modulations (in 32 usec units) to the value specified here.
+ * For Link Adaptation Algorithm. It defines the maximum number of
+ * speculation time slot for spatial stream.
*******************************************************************************/
-#define SLSI_PSID_UNIFI_OVERRIDE_DEFAULT_BETXOP_FOR_HT 0x093C
+#define SLSI_PSID_UNIFI_LAA_NSS_SPECULATION_INTERVAL_SLOT_MAX_NUM 0x091B
/*******************************************************************************
- * NAME : UnifiOverrideDefaultBetxop
- * PSID : 2365 (0x093D)
+ * NAME : UnifiLaaBwSpeculationIntervalSlotTime
+ * PSID : 2332 (0x091C)
* PER INTERFACE?: NO
* TYPE : SlsiUint16
* MIN : 0
* MAX : 65535
- * DEFAULT : 78
+ * DEFAULT : 300
* DESCRIPTION :
- * When set to non-zero value then this will override the BE TXOP for 11g
- * (in 32 usec units) to the value specified here.
+ * For Link Adaptation Algorithm. It defines the repeatable amount of time,
+ * in ms, that firmware will start to send speculation frames for bandwidth.
*******************************************************************************/
-#define SLSI_PSID_UNIFI_OVERRIDE_DEFAULT_BETXOP 0x093D
+#define SLSI_PSID_UNIFI_LAA_BW_SPECULATION_INTERVAL_SLOT_TIME 0x091C
/*******************************************************************************
- * NAME : UnifiRxabbTrimSettings
- * PSID : 2366 (0x093E)
+ * NAME : UnifiLaaBwSpeculationIntervalSlotMaxNum
+ * PSID : 2333 (0x091D)
* PER INTERFACE?: NO
- * TYPE : SlsiUint32
+ * TYPE : SlsiUint16
* MIN : 0
- * MAX : 4294967295
- * DEFAULT :
+ * MAX : 65535
+ * DEFAULT : 8
* DESCRIPTION :
- * Various settings to change RX ABB filter trim behavior.
+ * For Link Adaptation Algorithm. It defines the maximum number of
+ * speculation time slot for bandwidth.
*******************************************************************************/
-#define SLSI_PSID_UNIFI_RXABB_TRIM_SETTINGS 0x093E
+#define SLSI_PSID_UNIFI_LAA_BW_SPECULATION_INTERVAL_SLOT_MAX_NUM 0x091D
/*******************************************************************************
- * NAME : UnifiRadioTrimsEnable
- * PSID : 2367 (0x093F)
+ * NAME : UnifiLaaMcsSpeculationIntervalSlotTime
+ * PSID : 2334 (0x091E)
* PER INTERFACE?: NO
- * TYPE : SlsiUint32
+ * TYPE : SlsiUint16
* MIN : 0
- * MAX : 4294967295
- * DEFAULT : 0X0FF5
+ * MAX : 65535
+ * DEFAULT : 100
* DESCRIPTION :
- * A bitmap for enabling/disabling trims at runtime. Check unifiEnabledTrims
- * enum for description of the possible values.
+ * For Link Adaptation Algorithm. It defines the repeatable amount of time,
+ * in ms, that firmware will start to send speculation frames for MCS or
+ * rate index.
*******************************************************************************/
-#define SLSI_PSID_UNIFI_RADIO_TRIMS_ENABLE 0x093F
+#define SLSI_PSID_UNIFI_LAA_MCS_SPECULATION_INTERVAL_SLOT_TIME 0x091E
/*******************************************************************************
- * NAME : UnifiRadioCcaThresholds
- * PSID : 2368 (0x0940)
+ * NAME : UnifiLaaMcsSpeculationIntervalSlotMaxNum
+ * PSID : 2335 (0x091F)
* PER INTERFACE?: NO
- * TYPE : SlsiUint32
+ * TYPE : SlsiUint16
* MIN : 0
- * MAX : 4294967295
- * DEFAULT : 0X16301630
+ * MAX : 65535
+ * DEFAULT : 10
* DESCRIPTION :
- * The CCA thresholds so that the CCA-ED triggers at the regulatory value of
- * -62 dBm. The least significant 16bit word contains thresholds for
- * standard operation and the most significant 16bit word contains
- * thresholds for operation with any (external) FEM LNA disabled. For each
- * 16bit word, gain threshold in the lower octet and RSSI threshold in the
- * higher octet.
+ * For Link Adaptation Algorithm. It defines the maximum number of
+ * speculation time slot for MCS or rate index.
*******************************************************************************/
-#define SLSI_PSID_UNIFI_RADIO_CCA_THRESHOLDS 0x0940
+#define SLSI_PSID_UNIFI_LAA_MCS_SPECULATION_INTERVAL_SLOT_MAX_NUM 0x091F
/*******************************************************************************
- * NAME : UnifiHardwarePlatform
- * PSID : 2369 (0x0941)
+ * NAME : UnifiLaaGiSpeculationIntervalSlotTime
+ * PSID : 2336 (0x0920)
* PER INTERFACE?: NO
- * TYPE : unifiHardwarePlatform
+ * TYPE : SlsiUint16
* MIN : 0
- * MAX : 255
- * DEFAULT :
+ * MAX : 65535
+ * DEFAULT : 100
* DESCRIPTION :
- * Hardware platform. This is necessary so we can apply tweaks to specific
- * revisions, even though they might be running the same baseband and RF
- * chip combination. Check unifiHardwarePlatform enum for description of the
- * possible values.
+ * For Link Adaptation Algorithm. It defines the repeatable amount of time,
+ * in ms, that firmware will start to send speculation frames for guard
+ * interval.
*******************************************************************************/
-#define SLSI_PSID_UNIFI_HARDWARE_PLATFORM 0x0941
+#define SLSI_PSID_UNIFI_LAA_GI_SPECULATION_INTERVAL_SLOT_TIME 0x0920
/*******************************************************************************
- * NAME : UnifiForceChannelBw
- * PSID : 2370 (0x0942)
+ * NAME : UnifiLaaGiSpeculationIntervalSlotMaxNum
+ * PSID : 2337 (0x0921)
* PER INTERFACE?: NO
* TYPE : SlsiUint16
* MIN : 0
* MAX : 65535
- * DEFAULT :
+ * DEFAULT : 50
* DESCRIPTION :
- * Test/debug Mib to force channel bandwidth to specified value. This can
+ * For Link Adaptation Algorithm. It defines the maximum number of
+ * speculation time slot for guard interval.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_LAA_GI_SPECULATION_INTERVAL_SLOT_MAX_NUM 0x0921
+
+/*******************************************************************************
+ * NAME : UnifiCsrOnlyEifsDuration
+ * PSID : 2362 (0x093A)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * UNITS : microseconds
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT : 12
+ * DESCRIPTION :
+ * Specifies time that is used for EIFS. A value of 0 causes the build in
+ * value to be used.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_CSR_ONLY_EIFS_DURATION 0x093A
+
+/*******************************************************************************
+ * NAME : UnifiOverrideDefaultBetxopForHt
+ * PSID : 2364 (0x093C)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT : 171
+ * DESCRIPTION :
+ * When set to non-zero value then this will override the BE TXOP for 11n
+ * and higher modulations (in 32 usec units) to the value specified here.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_OVERRIDE_DEFAULT_BETXOP_FOR_HT 0x093C
+
+/*******************************************************************************
+ * NAME : UnifiOverrideDefaultBetxop
+ * PSID : 2365 (0x093D)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT : 78
+ * DESCRIPTION :
+ * When set to non-zero value then this will override the BE TXOP for 11g
+ * (in 32 usec units) to the value specified here.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_OVERRIDE_DEFAULT_BETXOP 0x093D
+
+/*******************************************************************************
+ * NAME : UnifiRxabbTrimSettings
+ * PSID : 2366 (0x093E)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint32
+ * MIN : 0
+ * MAX : 4294967295
+ * DEFAULT :
+ * DESCRIPTION :
+ * Various settings to change RX ABB filter trim behavior.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_RXABB_TRIM_SETTINGS 0x093E
+
+/*******************************************************************************
+ * NAME : UnifiRadioTrimsEnable
+ * PSID : 2367 (0x093F)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint32
+ * MIN : 0
+ * MAX : 4294967295
+ * DEFAULT : 0X0FF5
+ * DESCRIPTION :
+ * A bitmap for enabling/disabling trims at runtime. Check unifiEnabledTrims
+ * enum for description of the possible values.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_RADIO_TRIMS_ENABLE 0x093F
+
+/*******************************************************************************
+ * NAME : UnifiRadioCcaThresholds
+ * PSID : 2368 (0x0940)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint8
+ * MIN : 0
+ * MAX : 255
+ * DEFAULT :
+ * DESCRIPTION :
+ * The wideband CCA ED thresholds so that the CCA-ED triggers at the
+ * regulatory value of -62 dBm.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_RADIO_CCA_THRESHOLDS 0x0940
+
+/*******************************************************************************
+ * NAME : UnifiHardwarePlatform
+ * PSID : 2369 (0x0941)
+ * PER INTERFACE?: NO
+ * TYPE : unifiHardwarePlatform
+ * MIN : 0
+ * MAX : 255
+ * DEFAULT :
+ * DESCRIPTION :
+ * Hardware platform. This is necessary so we can apply tweaks to specific
+ * revisions, even though they might be running the same baseband and RF
+ * chip combination. Check unifiHardwarePlatform enum for description of the
+ * possible values.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_HARDWARE_PLATFORM 0x0941
+
+/*******************************************************************************
+ * NAME : UnifiForceChannelBw
+ * PSID : 2370 (0x0942)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT :
+ * DESCRIPTION :
+ * Test/debug Mib to force channel bandwidth to specified value. This can
* also be used to allow emulator/silicon back to back connection to
* communicate at bandwidth other than default (20 MHz) Setting it to 0 uses
* the default bandwidth as selected by firmware channel_bw_20_mhz = 20,
- * channel_bw_40_mhz = 40, channel_bw_80_mhz = 80
+ * channel_bw_40_mhz = 40, channel_bw_80_mhz = 80 This mib value will be
+ * updated if "unifiRameUpdateMibs" mib is toggled
*******************************************************************************/
#define SLSI_PSID_UNIFI_FORCE_CHANNEL_BW 0x0942
*******************************************************************************/
#define SLSI_PSID_UNIFI_DPD_TRAIN_PACKET_CONFIG 0x0945
+/*******************************************************************************
+ * NAME : UnifiTxPowerTrimCommonConfig
+ * PSID : 2374 (0x0946)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint8
+ * MIN : 3
+ * MAX : 255
+ * DEFAULT :
+ * DESCRIPTION :
+ * Common transmitter power trim settings
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_TX_POWER_TRIM_COMMON_CONFIG 0x0946
+
/*******************************************************************************
* NAME : UnifiCoexDebugOverrideBt
* PSID : 2425 (0x0979)
*******************************************************************************/
#define SLSI_PSID_UNIFI_COEX_DEBUG_OVERRIDE_BT 0x0979
+/*******************************************************************************
+ * NAME : UnifiLteMailbox
+ * PSID : 2430 (0x097E)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint8
+ * MIN : 36
+ * MAX : 40
+ * DEFAULT :
+ * DESCRIPTION :
+ * Set modem status to simulate lte status updates. See SC-505775-SP for API
+ * description. Defined as array of uint32 represented by the octet string
+ * FOR TEST PURPOSES ONLY
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_LTE_MAILBOX 0x097E
+
+/*******************************************************************************
+ * NAME : UnifiLteMwsSignal
+ * PSID : 2431 (0x097F)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT :
+ * DESCRIPTION :
+ * Set modem status to simulate lte status updates. See SC-505775-SP for API
+ * description. See unifiLteSignalsBitField for enum bitmap. FOR TEST
+ * PURPOSES ONLY
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_LTE_MWS_SIGNAL 0x097F
+
+/*******************************************************************************
+ * NAME : UnifiLteEnableChannelAvoidance
+ * PSID : 2432 (0x0980)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiBool
+ * MIN : 0
+ * MAX : 1
+ * DEFAULT : TRUE
+ * DESCRIPTION :
+ * Enables channel avoidance scheme for LTE Coex
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_LTE_ENABLE_CHANNEL_AVOIDANCE 0x0980
+
+/*******************************************************************************
+ * NAME : UnifiLteEnablePowerBackoff
+ * PSID : 2433 (0x0981)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiBool
+ * MIN : 0
+ * MAX : 1
+ * DEFAULT : TRUE
+ * DESCRIPTION :
+ * Enables power backoff scheme for LTE Coex
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_LTE_ENABLE_POWER_BACKOFF 0x0981
+
+/*******************************************************************************
+ * NAME : UnifiLteEnableTimeDomain
+ * PSID : 2434 (0x0982)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiBool
+ * MIN : 0
+ * MAX : 1
+ * DEFAULT : TRUE
+ * DESCRIPTION :
+ * Enables TDD scheme for LTE Coex
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_LTE_ENABLE_TIME_DOMAIN 0x0982
+
+/*******************************************************************************
+ * NAME : UnifiLteEnableLteCoex
+ * PSID : 2435 (0x0983)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiBool
+ * MIN : 0
+ * MAX : 1
+ * DEFAULT : TRUE
+ * DESCRIPTION :
+ * Enables LTE Coex support
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_LTE_ENABLE_LTE_COEX 0x0983
+
+/*******************************************************************************
+ * NAME : UnifiLteBand40PowerBackoffChannelMask
+ * PSID : 2436 (0x0984)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT : 3
+ * DESCRIPTION :
+ * Channel Mask defining channels on which to apply power backoff when LTE
+ * operating on Band40. Defined as a 16 bit bitmask, as only 2G4 channels
+ * are impacted by this feature.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_LTE_BAND40_POWER_BACKOFF_CHANNEL_MASK 0x0984
+
+/*******************************************************************************
+ * NAME : UnifiLteBand40PowerBackoffRsrpLow
+ * PSID : 2437 (0x0985)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiInt16
+ * UNITS : dBm
+ * MIN : -140
+ * MAX : -77
+ * DEFAULT : -100
+ * DESCRIPTION :
+ * WLAN Power Reduction shall be applied when RSRP of LTE operating on band
+ * 40 falls below this level
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_LTE_BAND40_POWER_BACKOFF_RSRP_LOW 0x0985
+
+/*******************************************************************************
+ * NAME : UnifiLteBand40PowerBackoffRsrpHigh
+ * PSID : 2438 (0x0986)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiInt16
+ * UNITS : dBm
+ * MIN : -140
+ * MAX : -77
+ * DEFAULT : -95
+ * DESCRIPTION :
+ * WLAN Power Reduction shall be restored when RSRP of LTE operating on band
+ * 40 climbs above this level
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_LTE_BAND40_POWER_BACKOFF_RSRP_HIGH 0x0986
+
+/*******************************************************************************
+ * NAME : UnifiLteBand40PowerBackoffRsrpAveragingAlpha
+ * PSID : 2439 (0x0987)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * UNITS : percentage
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT : 50
+ * DESCRIPTION :
+ * Weighting applied when calculaing the average RSRP when considering Power
+ * Back Off Specifies the percentage weighting (alpha) to give to the most
+ * recent value when calculating the moving average. ma_new = alpha *
+ * new_sample + (1-alpha) * ma_old.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_LTE_BAND40_POWER_BACKOFF_RSRP_AVERAGING_ALPHA 0x0987
+
+/*******************************************************************************
+ * NAME : UnifiLteSetChannel
+ * PSID : 2440 (0x0988)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT :
+ * DESCRIPTION :
+ * Enables LTE Coex support
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_LTE_SET_CHANNEL 0x0988
+
+/*******************************************************************************
+ * NAME : UnifiLteSetPowerBackoff
+ * PSID : 2441 (0x0989)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT :
+ * DESCRIPTION :
+ * MIB to force WLAN Power Backoff for LTE COEX testing purposes
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_LTE_SET_POWER_BACKOFF 0x0989
+
+/*******************************************************************************
+ * NAME : UnifiLteSetTddDebugMode
+ * PSID : 2442 (0x098A)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT :
+ * DESCRIPTION :
+ * MIB to enable LTE TDD COEX simulation for testing purposes
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_LTE_SET_TDD_DEBUG_MODE 0x098A
+
+/*******************************************************************************
+ * NAME : UnifiApScanAbsenceDuration
+ * PSID : 2480 (0x09B0)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * UNITS : beacon intervals
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT : 7
+ * DESCRIPTION :
+ * Duration of the Absence time to use when protecting AP VIFs from scan
+ * operations. A value of 0 disables the feature.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_AP_SCAN_ABSENCE_DURATION 0x09B0
+
+/*******************************************************************************
+ * NAME : UnifiApScanAbsencePeriod
+ * PSID : 2481 (0x09B1)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * UNITS : beacon intervals
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT : 14
+ * DESCRIPTION :
+ * Period of the Absence/Presence times cycles to use when protecting AP
+ * VIFs from scan operations.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_AP_SCAN_ABSENCE_PERIOD 0x09B1
+
/*******************************************************************************
* NAME : UnifiFastPowerSaveTimeout
* PSID : 2500 (0x09C4)
*******************************************************************************/
#define SLSI_PSID_UNIFI_STATION_ACTIVITY_IDLE_TIME 0x09D0
+/*******************************************************************************
+ * NAME : UnifiDmsEnabled
+ * PSID : 2513 (0x09D1)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiBool
+ * MIN : 0
+ * MAX : 1
+ * DEFAULT : TRUE
+ * DESCRIPTION :
+ * Enables Directed Multicast Service (DMS)
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_DMS_ENABLED 0x09D1
+
/*******************************************************************************
* NAME : UnifiPowerManagementDelayTimeout
* PSID : 2514 (0x09D2)
* UNITS : DTIM intervals
* MIN : 0
* MAX : 4294967295
- * DEFAULT : 0X000A89AA
+ * DEFAULT : 0X00054645
* DESCRIPTION :
* Listen interval of beacons when in single-vif power saving mode and
* receiving DTIMs is enabled. No DTIMs are skipped during MVIF operation. A
* MAX : 100
* DEFAULT : 10
* DESCRIPTION :
- * Beacon Listen Interval
+ * Association request listen interval parameter. Not used for any other
+ * purpose.
*******************************************************************************/
#define SLSI_PSID_UNIFI_LISTEN_INTERVAL 0x09D7
* TYPE : SlsiUint32
* MIN : 0
* MAX : 4294967295
- * DEFAULT : 0X01010103
+ * DEFAULT : 0X00010103
* DESCRIPTION :
* Control beacon skipping behaviour within firmware with bit flags. 1
* defines enabled, with 0 showing the case disabled. If beacon skipping is
* LCD on bit 3: station skipping with multivif bit 4: station skipping with
* BT active. bit 8: station skip dtim on host suspend bit 9: station skip
* dtim on host awake bit 10: station skip dtim on LCD on bit 11: station
- * skip dtim on multivif bit 12: station skip dtim with BT active bit 15:
- * p2p-gc skipping on host suspend bit 16: p2p-gc skipping on host awake bit
- * 17: p2p-gc skipping on LCD on bit 18: p2p-gc skipping with multivif bit
- * 19: p2p-gc skipping with BT active bit 24: p2p-gc skip dtim on host
+ * skip dtim on multivif bit 12: station skip dtim with BT active bit 16:
+ * p2p-gc skipping on host suspend bit 17: p2p-gc skipping on host awake bit
+ * 18: p2p-gc skipping on LCD on bit 19: p2p-gc skipping with multivif bit
+ * 20: p2p-gc skipping with BT active bit 24: p2p-gc skip dtim on host
* suspend bit 25: p2p-gc skip dtim on host awake bit 26: p2p-gc skip dtim
* on LCD on bit 27: p2p-gc skip dtim on multivif bit 28: p2p-gc skip dtim
* with BT active
* TYPE : SlsiBool
* MIN : 0
* MAX : 1
- * DEFAULT : TRUE
+ * DEFAULT : FALSE
* DESCRIPTION :
* Enables Idle Mode Lite, if softAP is active, and there has been no
* activity for a time. Idle mode lite should not be active if host has sent
- * a command to change key.
+ * a command to change key. This mib value will be runtime (post-wlan
+ * enable) applied only if "unifiRameUpdateMibs" mib is toggled
*******************************************************************************/
#define SLSI_PSID_UNIFI_IDLE_MODE_LITE_ENABLED 0x09DE
* TYPE : SlsiBool
* MIN : 0
* MAX : 1
- * DEFAULT : TRUE
+ * DEFAULT : FALSE
* DESCRIPTION :
- * Enables Idle Mode, if single vif station is active, and there has been no
- * activity for a time.
+ * Enables Idle Mode, if single vif station is active or there is no vif,
+ * and there has been no activity for a time. This mib value will be runtime
+ * (post-wlan enable) applied if only "unifiRameUpdateMibs" mib is toggled
*******************************************************************************/
#define SLSI_PSID_UNIFI_IDLE_MODE_ENABLED 0x09DF
* TYPE : SlsiUint16
* UNITS : TU
* MIN : 0
- * MAX : 65536
+ * MAX : 65535
* DEFAULT : 1000
* DESCRIPTION :
* Maximum number length of time, in Time Units (1TU = 1024us), that can be
* UNITS : ms
* MIN : 0
* MAX : 65535
- * DEFAULT : 500
+ * DEFAULT : 100
* DESCRIPTION :
* Lifetime of proberesponse frame in unit of ms.
*******************************************************************************/
#define SLSI_PSID_UNIFI_ACTIVE_TIME_AFTER_MORE_BIT 0x09E9
/*******************************************************************************
- * NAME : UnifiForcedScheduleDuration
+ * NAME : UnifiDefaultDwellTime
* PSID : 2538 (0x09EA)
* PER INTERFACE?: NO
* TYPE : SlsiUint16
* MAX : 65535
* DEFAULT : 50
* DESCRIPTION :
- * Defines the time to keep a VIF scheduled after an outgoing packet is
- * queued, if the "Immediate_Response_Expected" bit is set in the Tx_Control
- * associated with a frame transmission request. The firmware may choose to
- * override this value based on internal logic.
+ * Defines the dwell time for frames that need a response but have no dwell
+ * time associated
*******************************************************************************/
-#define SLSI_PSID_UNIFI_FORCED_SCHEDULE_DURATION 0x09EA
+#define SLSI_PSID_UNIFI_DEFAULT_DWELL_TIME 0x09EA
/*******************************************************************************
* NAME : UnifiVhtCapabilities
* TYPE : SlsiUint8
* MIN : 12
* MAX : 12
- * DEFAULT : { 0X30, 0X78, 0X90, 0X01, 0XFA, 0XFF, 0X00, 0X00, 0XFA, 0XFF, 0X00, 0X00 }
+ * DEFAULT : { 0XB1, 0X7A, 0X11, 0X03, 0XFA, 0XFF, 0X00, 0X00, 0XFA, 0XFF, 0X00, 0X00 }
* DESCRIPTION :
* VHT capabilities of the chip. see SC-503520-SP.
*******************************************************************************/
#define SLSI_PSID_UNIFI_DEBUG_KEEP_RADIO_ON 0x09F1
/*******************************************************************************
- * NAME : UnifiScanAbsenceDuration
+ * NAME : UnifiForceFixedDurationSchedule
+ * PSID : 2546 (0x09F2)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * UNITS : TU
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT : 100
+ * DESCRIPTION :
+ * For schedules with fixed duration e.g. scan, unsync VIF, the schedule
+ * will be forced after this time to avoid VIF starving
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_FORCE_FIXED_DURATION_SCHEDULE 0x09F2
+
+/*******************************************************************************
+ * NAME : UnifiRameUpdateMibs
+ * PSID : 2547 (0x09F3)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiBool
+ * MIN : 0
+ * MAX : 1
+ * DEFAULT : FALSE
+ * DESCRIPTION :
+ * When this mib is called/toggled MACRAME mibs will be read and compared
+ * with mib values in ramedata.mibs and updated if the value changes
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_RAME_UPDATE_MIBS 0x09F3
+
+/*******************************************************************************
+ * NAME : UnifiGoScanAbsenceDuration
* PSID : 2548 (0x09F4)
* PER INTERFACE?: NO
* TYPE : SlsiUint16
* Duration of the Absence time to use when protecting P2PGO VIFs from scan
* operations. A value of 0 disables the feature.
*******************************************************************************/
-#define SLSI_PSID_UNIFI_SCAN_ABSENCE_DURATION 0x09F4
+#define SLSI_PSID_UNIFI_GO_SCAN_ABSENCE_DURATION 0x09F4
/*******************************************************************************
- * NAME : UnifiScanAbsencePeriod
+ * NAME : UnifiGoScanAbsencePeriod
* PSID : 2549 (0x09F5)
* PER INTERFACE?: NO
* TYPE : SlsiUint16
* Period of the Absence/Presence times cycles to use when protecting P2PGO
* VIFs from scan operations.
*******************************************************************************/
-#define SLSI_PSID_UNIFI_SCAN_ABSENCE_PERIOD 0x09F5
+#define SLSI_PSID_UNIFI_GO_SCAN_ABSENCE_PERIOD 0x09F5
/*******************************************************************************
* NAME : UnifiMaxClient
* MAX : 1
* DEFAULT : TRUE
* DESCRIPTION :
- * Use TDLS in P2P mode.
+ * Enable TDLS in P2P.
*******************************************************************************/
#define SLSI_PSID_UNIFI_TDLS_IN_P2P_ACTIVATED 0x09FC
* MAX : 1
* DEFAULT : TRUE
* DESCRIPTION :
- * Use TDLS mode.
+ * Enable TDLS.
*******************************************************************************/
#define SLSI_PSID_UNIFI_TDLS_ACTIVATED 0x09FE
* MAX : 4294967295
* DEFAULT : 100
* DESCRIPTION :
- * Used for the argument "throughput_threshold_pktsecs" of
- * RAME-MLME-ENABLE-PEER-TRAFFIC-REPORTING.request signal defined in
- * SC-505422-DD.
+ * Used for "throughput_threshold_pktsecs" of
+ * RAME-MLME-ENABLE-PEER-TRAFFIC-REPORTING.request.
*******************************************************************************/
#define SLSI_PSID_UNIFI_TDLS_TP_THRESHOLD_PKT_SECS 0x09FF
* MAX : 32767
* DEFAULT : -75
* DESCRIPTION :
- * Used for the FW initiated TDLS Discovery/Setup procedure. If the RSSI of
- * a received TDLS Discovery Response frame is greater than this value,the
- * TDLS FSM shall initiate the TDLS Setup procedure.
+ * FW initiated TDLS Discovery/Setup procedure. If the RSSI of a received
+ * TDLS Discovery Response frame is greater than this value, initiate the
+ * TDLS Setup procedure.
*******************************************************************************/
#define SLSI_PSID_UNIFI_TDLS_RSSI_THRESHOLD 0x0A00
* MAX : 65535
* DEFAULT : 3
* DESCRIPTION :
- * Transmission of a TDLS Action frame or a TDLS Discovery Response Public
- * Action frame shall be retried unifiTdlsMaximumRetry times until the frame
- * is transmitted successfully.
+ * Deprecated.
*******************************************************************************/
#define SLSI_PSID_UNIFI_TDLS_MAXIMUM_RETRY 0x0A01
* MAX : 65535
* DEFAULT : 10
* DESCRIPTION :
- * The measurement period for recording the number of packets sent to a peer
+ * Measurement period for recording the number of packets sent to a peer
* over a TDLS link.
*******************************************************************************/
#define SLSI_PSID_UNIFI_TDLS_TP_MONITOR_SECS 0x0A02
* TYPE : SlsiUint8
* MIN : 16
* MAX : 16
- * DEFAULT : { 0XFF, 0X00, 0X00, 0X00, 0X00, 0X00, 0X00, 0X00, 0X00, 0X00, 0X00, 0X00, 0X00, 0X00, 0X00, 0X00, 0X00, 0X00 }
+ * DEFAULT :
* DESCRIPTION :
- * The default Basic HT MCS SET used on a TDLS Link. Used to build the HT
- * Operation element in TDLS Setup frames.
+ * Deprecated.
*******************************************************************************/
#define SLSI_PSID_UNIFI_TDLS_BASIC_HT_MCS_SET 0x0A03
* TYPE : SlsiUint8
* MIN : 2
* MAX : 2
- * DEFAULT : { 0XFE, 0XFF }
+ * DEFAULT :
* DESCRIPTION :
- * Used to build the VHT Operation element in the TDLS Setup Confirm frame
+ * Deprecated
*******************************************************************************/
#define SLSI_PSID_UNIFI_TDLS_BASIC_VHT_MCS_SET 0x0A04
* MAX : 4294967295
* DEFAULT : 10
* DESCRIPTION :
- * TDLS shall not transmit the TDLS Discovery Request frame within
- * dot11TDLSDiscoveryRequestWindow DTIM intervals after transmitting TDLS
- * Discovery Request frame.
+ * Time to gate Discovery Request frame (in DTIM intervals) after
+ * transmitting a Discovery Request frame.
*******************************************************************************/
#define SLSI_PSID_DOT11_TDLS_DISCOVERY_REQUEST_WINDOW 0x0A05
* MAX : 4294967295
* DEFAULT : 5
* DESCRIPTION :
- * If no TDLS Setup Response frame is received within
- * dot11TDLSResponseTimeout (seconds), or if a TDLS Setup Response frame is
- * received with a nonzero status code, the TDLS initiator STA shall
- * terminate the setup procedure and discard the TDLS Setup Response frame.
+ * If a valid Setup Response frame is not received within (seconds), the
+ * initiator STA shall terminate the setup procedure and discard any Setup
+ * Response frames.
*******************************************************************************/
#define SLSI_PSID_DOT11_TDLS_RESPONSE_TIMEOUT 0x0A06
* MAX : 1
* DEFAULT : FALSE
* DESCRIPTION :
- * When true, indicates that the STA implementation is capable of supporting
- * TDLS Channel Switching.
+ * Deprecated.
*******************************************************************************/
#define SLSI_PSID_DOT11_TDLS_CHANNEL_SWITCH_ACTIVATED 0x0A07
* MAX : 4294967295
* DEFAULT : 0X00000000
* DESCRIPTION :
- * Set TDLS design for test mode
+ * Deprecated
*******************************************************************************/
#define SLSI_PSID_UNIFI_TDLS_DESIGN_FOR_TEST_MODE 0x0A08
* MAX : 1
* DEFAULT : FALSE
* DESCRIPTION :
- * When true, TDLS wider bandwidth selection is prohibited.
+ * Wider bandwidth prohibited flag.
*******************************************************************************/
#define SLSI_PSID_UNIFI_TDLS_WIDER_BANDWIDTH_PROHIBITED 0x0A09
* MAX : 65535
* DEFAULT : 500
* DESCRIPTION :
- * Allowed time in milliseconds for a TDLS Teardown frame to be trasmitted
- * over the air
+ * Allowed time in milliseconds for a Teardown frame to be transmitted.
*******************************************************************************/
#define SLSI_PSID_UNIFI_TDLS_TEARDOWN_FRAME_TX_TIMEOUT 0x0A12
* TYPE : SlsiBool
* MIN : 0
* MAX : 1
- * DEFAULT : FALSE
+ * DEFAULT : TRUE
* DESCRIPTION :
* Enables WiFi Sharing feature
*******************************************************************************/
#define SLSI_PSID_UNIFI_WIFI_SHARING_ENABLED 0x0A14
-/*******************************************************************************
- * NAME : UnifiWiFiSharing5GHzAllowed
- * PSID : 2581 (0x0A15)
- * PER INTERFACE?: NO
- * TYPE : SlsiBool
- * MIN : 0
- * MAX : 1
- * DEFAULT : FALSE
- * DESCRIPTION :
- * Whether usage of 5GHz band is allowed for WiFi Sharing
- *******************************************************************************/
-#define SLSI_PSID_UNIFI_WI_FI_SHARING5_GHZ_ALLOWED 0x0A15
-
/*******************************************************************************
* NAME : UnifiWiFiSharing5GHzChannel
* PSID : 2582 (0x0A16)
* TYPE : SlsiUint8
* MIN : 8
* MAX : 8
- * DEFAULT : { 0X00, 0X00, 0X00, 0X00, 0X20, 0X00, 0X00, 0X00 }
+ * DEFAULT : { 0X00, 0XC0, 0XFF, 0XFF, 0X7F, 0X00, 0X00, 0X00 }
* DESCRIPTION :
- * 5GHz Primary Channels applicable. Defined in a uint64 represented by the
- * octet string. First byte of the octet string maps to LSB. Bits 0-13 are
- * always set to 0 (don't care). Mapping defined in
- * mlme_regulatory_freq_list[]; i.e. Bit 14 maps to channel 36.
+ * Applicable 5GHz Primary Channels mask. Defined in a uint64 represented by
+ * the octet string. First byte of the octet string maps to LSB. Bits 0-13
+ * representing 2.4G channels are always set to 0. Mapping defined in
+ * ChannelisationRules; i.e. Bit 14 maps to channel 36.
*******************************************************************************/
#define SLSI_PSID_UNIFI_WI_FI_SHARING5_GHZ_CHANNEL 0x0A16
* MAX : 65535
* DEFAULT : 0X00000000
* DESCRIPTION :
- * Virtual router advertisement packet is only used for the test purpose,
+ * Virtual router advertisement packet. is only used for the test purpose,
* specified in chapter '6.2 Forward Received RA frame to Host' in
* SC-506393-TE
*******************************************************************************/
* MAX : 1
* DEFAULT : TRUE
* DESCRIPTION :
- * Indicate that the STA implementation is capable of supporting TDLS peer
- * U-APSD.
+ * Enable TDLS peer U-APSD.
*******************************************************************************/
#define SLSI_PSID_DOT11_TDLS_PEER_UAPSD_BUFFER_STA_ACTIVATED 0x0A1B
+/*******************************************************************************
+ * NAME : UnifiProbeResponseLifetimeP2p
+ * PSID : 2600 (0x0A28)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * UNITS : ms
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT : 500
+ * DESCRIPTION :
+ * Lifetime of proberesponse frame in unit of ms for P2P.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_PROBE_RESPONSE_LIFETIME_P2P 0x0A28
+
+/*******************************************************************************
+ * NAME : UnifiStaChannelSwitchSlowApActivated
+ * PSID : 2601 (0x0A29)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiBool
+ * MIN : 0
+ * MAX : 1
+ * DEFAULT : FALSE
+ * DESCRIPTION :
+ * ChanelSwitch: Enable waiting for a slow AP.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_STA_CHANNEL_SWITCH_SLOW_AP_ACTIVATED 0x0A29
+
+/*******************************************************************************
+ * NAME : UnifiStaChannelSwitchSlowApMaxTime
+ * PSID : 2604 (0x0A2C)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint32
+ * MIN : 0
+ * MAX : 4294967295
+ * DEFAULT : 70
+ * DESCRIPTION :
+ * ChannelSwitch delay for Slow APs. In Seconds.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_STA_CHANNEL_SWITCH_SLOW_AP_MAX_TIME 0x0A2C
+
+/*******************************************************************************
+ * NAME : UnifiStaChannelSwitchSlowApPollInterval
+ * PSID : 2605 (0x0A2D)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT : 1
+ * DESCRIPTION :
+ * ChannelSwitch polling interval for Slow APs. In Seconds.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_STA_CHANNEL_SWITCH_SLOW_AP_POLL_INTERVAL 0x0A2D
+
+/*******************************************************************************
+ * NAME : UnifiStaChannelSwitchSlowApProcedureTimeoutIncrement
+ * PSID : 2606 (0x0A2E)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT : 10
+ * DESCRIPTION :
+ * ChannelSwitch procedure timeout increment for Slow APs. In Seconds.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_STA_CHANNEL_SWITCH_SLOW_AP_PROCEDURE_TIMEOUT_INCREMENT 0x0A2E
+
+/*******************************************************************************
+ * NAME : UnifiMlmeScanMaxAerials
+ * PSID : 2607 (0x0A2F)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * MIN : 1
+ * MAX : 65535
+ * DEFAULT : 1
+ * DESCRIPTION :
+ * Limits the number of Aerials that Scan can use.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_MLME_SCAN_MAX_AERIALS 0x0A2F
+
/*******************************************************************************
* NAME : UnifiCsrOnlyMibShield
* PSID : 4001 (0x0FA1)
* MAX : 65535
* DEFAULT : 15
* DESCRIPTION :
- * Forces the WAPI encryption hardware use the QoS mask specified.
+ * Forces the WAPI encryption hardware use the QoS mask specified.This mib
+ * value will be updated if "unifiRameUpdateMibs" mib is toggled
*******************************************************************************/
#define SLSI_PSID_UNIFI_WAPI_QOS_MASK 0x1022
-/*******************************************************************************
- * NAME : UnifiRaaMaxSpecTimerMultiplier
- * PSID : 4138 (0x102A)
- * PER INTERFACE?: NO
- * TYPE : SlsiUint16
- * MIN : 0
- * MAX : 65535
- * DEFAULT : 8
- * DESCRIPTION :
- * For Rate Adaptation Algorithm. It defines the max number to be multiplied
- * to the speculation timer, which usually is 100 ms.
- *******************************************************************************/
-#define SLSI_PSID_UNIFI_RAA_MAX_SPEC_TIMER_MULTIPLIER 0x102A
-
/*******************************************************************************
* NAME : UnifiWmmStallEnable
* PSID : 4139 (0x102B)
*******************************************************************************/
#define SLSI_PSID_UNIFI_WMM_STALL_ENABLE 0x102B
-/*******************************************************************************
- * NAME : UnifiRaaSpeculationInterval
- * PSID : 4140 (0x102C)
- * PER INTERFACE?: NO
- * TYPE : SlsiUint16
- * MIN : 0
- * MAX : 65535
- * DEFAULT : 100
- * DESCRIPTION :
- * For Rate Adaptation Algorithm. It defines the repeatable amount of time,
- * in ms, that firmware will start to send speculation frames.
- *******************************************************************************/
-#define SLSI_PSID_UNIFI_RAA_SPECULATION_INTERVAL 0x102C
-
-/*******************************************************************************
- * NAME : UnifiRaaSpeculationPeriod
- * PSID : 4141 (0x102D)
- * PER INTERFACE?: NO
- * TYPE : SlsiUint16
- * MIN : 0
- * MAX : 65535
- * DEFAULT : 10
- * DESCRIPTION :
- * For Rate Adaptation Algorithm. It defines the max amount of time, in ms,
- * that firmware will use for sending speculation frames
- *******************************************************************************/
-#define SLSI_PSID_UNIFI_RAA_SPECULATION_PERIOD 0x102D
-
-/*******************************************************************************
- * NAME : UnifiRaaNumbSpeculationFrames
- * PSID : 4142 (0x102E)
- * PER INTERFACE?: NO
- * TYPE : SlsiUint16
- * MIN : 0
- * MAX : 65535
- * DEFAULT : 10
- * DESCRIPTION :
- * For Rate Adaptation Algorithm. It defines the max amount of speculation
- * frames that firmware is allowed to send.
- *******************************************************************************/
-#define SLSI_PSID_UNIFI_RAA_NUMB_SPECULATION_FRAMES 0x102E
-
-/*******************************************************************************
- * NAME : UnifiRaaTxSuccessesCount
- * PSID : 4143 (0x102F)
- * PER INTERFACE?: NO
- * TYPE : SlsiUint16
- * MIN : 0
- * MAX : 65535
- * DEFAULT :
- * DESCRIPTION :
- * For Rate Adaptation Algorithm. It represents the number of transmitted
- * frames that were acked at a given rate.
- *******************************************************************************/
-#define SLSI_PSID_UNIFI_RAA_TX_SUCCESSES_COUNT 0x102F
-
-/*******************************************************************************
- * NAME : UnifiRaaTxFailuresCount
- * PSID : 4144 (0x1030)
- * PER INTERFACE?: NO
- * TYPE : SlsiUint16
- * MIN : 0
- * MAX : 65535
- * DEFAULT :
- * DESCRIPTION :
- * For Rate Adaptation Algorithm. It represents the number of transmitted
- * frames that were NOT acked at a given rate.
- *******************************************************************************/
-#define SLSI_PSID_UNIFI_RAA_TX_FAILURES_COUNT 0x1030
-
-/*******************************************************************************
- * NAME : UnifiRaaTxPer
- * PSID : 4145 (0x1031)
- * PER INTERFACE?: NO
- * TYPE : SlsiUint16
- * MIN : 0
- * MAX : 65535
- * DEFAULT :
- * DESCRIPTION :
- * For Rate Adaptation Algorithm. It represents the Packet Error Rate for a
- * given rate on the RAA rate stats.
- *******************************************************************************/
-#define SLSI_PSID_UNIFI_RAA_TX_PER 0x1031
-
-/*******************************************************************************
- * NAME : UnifiRaaResetStats
- * PSID : 4146 (0x1032)
- * PER INTERFACE?: NO
- * TYPE : SlsiUint16
- * MIN : 0
- * MAX : 65535
- * DEFAULT :
- * DESCRIPTION :
- * For Rate Adaptation Algorithm. It Resets the stats table used by the RAA.
- *******************************************************************************/
-#define SLSI_PSID_UNIFI_RAA_RESET_STATS 0x1032
-
-/*******************************************************************************
- * NAME : UnifiRaaTxMtPer
- * PSID : 4147 (0x1033)
- * PER INTERFACE?: NO
- * TYPE : SlsiUint16
- * MIN : 0
- * MAX : 65535
- * DEFAULT :
- * DESCRIPTION :
- * For Rate Adaptation Algorithm. It represents the Maximum Tolerable Packet
- * Error Rate for each rate.
- *******************************************************************************/
-#define SLSI_PSID_UNIFI_RAA_TX_MT_PER 0x1033
-
/*******************************************************************************
* NAME : UnifiRaaTxHostRate
* PSID : 4148 (0x1034)
* PSID : 4149 (0x1035)
* PER INTERFACE?: NO
* TYPE : SlsiUint8
- * MIN : 5
+ * MIN : 6
* MAX : 5
- * DEFAULT : {0X03, 0X02, 0X01, 0X00, 0X00}
+ * DEFAULT : {0X3, 0X2, 0X2, 0X2, 0X1, 0X0}
* DESCRIPTION :
* Configure the retry distribution for fallback for short frames octet 0 -
* Number of retries for starting rate. octet 1 - Number of retries for next
* rate. octet 2 - Number of retries for next rate. octet 3 - Number of
- * retries for next rate. octet 4 - Number of retries for last rate. If 0 is
- * written to an entry then the retries for that rate will be the short
- * retry limit minus the sum of the retries for each rate above that entry
- * (e.g. 15 - 5). Therefore, this should always be the value for octet 4.
- * Also, when the starting rate has short guard enabled, the number of
- * retries in octet 1 will be used and for the next rate in the fallback
- * table (same MCS value, but with sgi disabled) octet 0 number of retries
- * will be used.
+ * retries for next rate. octet 4 - Number of retries for next rate. octet 5
+ * - Number of retries for last rate. If 0 is written to an entry then the
+ * retries for that rate will be the short retry limit minus the sum of the
+ * retries for each rate above that entry (e.g. 15 - 5). Therefore, this
+ * should always be the value for octet 4. Also, when the starting rate has
+ * short guard enabled, the number of retries in octet 1 will be used and
+ * for the next rate in the fallback table (same MCS value, but with sgi
+ * disabled) octet 0 number of retries will be used.
*******************************************************************************/
#define SLSI_PSID_UNIFI_FALLBACK_SHORT_FRAME_RETRY_DISTRIBUTION 0x1035
+/*******************************************************************************
+ * NAME : UnifiRxthroughputlow
+ * PSID : 4150 (0x1036)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint32
+ * MIN : 0
+ * MAX : 4294967295
+ * DEFAULT : 100
+ * DESCRIPTION :
+ * Lower threshold for total number of frames received in the system which
+ * is considered as low load
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_RXTHROUGHPUTLOW 0x1036
+
+/*******************************************************************************
+ * NAME : UnifiRxthroughputhigh
+ * PSID : 4151 (0x1037)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint32
+ * MIN : 0
+ * MAX : 4294967295
+ * DEFAULT : 1000
+ * DESCRIPTION :
+ * Upper threshold for total number of frames received in the system which
+ * is considered as high load
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_RXTHROUGHPUTHIGH 0x1037
+
/*******************************************************************************
* NAME : UnifiSetFixedAmpduAggregationSize
* PSID : 4152 (0x1038)
*******************************************************************************/
#define SLSI_PSID_UNIFI_PS_POLL_THRESHOLD 0x1053
+/*******************************************************************************
+ * NAME : UnifiDebugSvcModeStackHighWaterMark
+ * PSID : 5010 (0x1392)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT :
+ * DESCRIPTION :
+ * Read the SVC mode stack high water mark in bytes
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_DEBUG_SVC_MODE_STACK_HIGH_WATER_MARK 0x1392
+
+/*******************************************************************************
+ * NAME : UnifiDebugPreferred2G4Radio
+ * PSID : 5020 (0x139C)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT :
+ * DESCRIPTION :
+ * Specify the preferred radio/MAC/BBBmodem to use for 2G4 operation. Only
+ * valid for multi-radio platforms. Only used for SISO connections. WARNING:
+ * Changing this value after system start-up will have no effect.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_DEBUG_PREFERRED2_G4_RADIO 0x139C
+
+/*******************************************************************************
+ * NAME : UnifiDebugPreferred5GRadio
+ * PSID : 5021 (0x139D)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT : 1
+ * DESCRIPTION :
+ * Specify the preferred radio/MAC/BBBmodem to use for 5G operation. Only
+ * valid for multi-radio platforms. Only used for SISO connections. WARNING:
+ * Changing this value after system start-up will have no effect.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_DEBUG_PREFERRED5_GRADIO 0x139D
+
+/*******************************************************************************
+ * NAME : UnifiPanicSubSystemControl
+ * PSID : 5026 (0x13A2)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT :
+ * DESCRIPTION :
+ * PANIC levels for WLAN SubSystems. Panic level is used to filter Panic
+ * sent to the host. 4 levels of Panic per subsystem are available
+ * (FAILURE_LEVEL_T): a. 0 FATAL - Always reported to host b. 1 ERROR c. 2
+ * WARNING d. 3 DEBUG NOTE: If Panic level of a subsystem is configured to
+ * FATAL, all the Panics within that subsystem configured to FATAL will be
+ * effective, panics with ERROR, WARNING and Debug level will be converted
+ * to faults. If Panic level of a subsystem is configured to WARNING, all
+ * the panics within that subsystem configured to FATAL, ERROR and WARNING
+ * will be issued to host, panics with Debug level will be converted to
+ * faults.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_PANIC_SUB_SYSTEM_CONTROL 0x13A2
+
/*******************************************************************************
* NAME : UnifiFaultEnable
* PSID : 5027 (0x13A3)
* MAX : 65535
* DEFAULT :
* DESCRIPTION :
- * Fault Module levels for all SubSystems. Fault level is used to filter
- * faults sent to the host. 4 levels of faults per subsystem are available:
- * a. 0 ERROR b. 1 WARNING c. 2 INFO_1 d. 3 INFO_2 Modifying Fault Levels at
- * run time: 1. Set the fault level for the desired subsystem in
- * unifiFaultConfigTable 2. Set unifiFaultEnable NOTE: If fault level of a
- * subsystem is configured to ERROR, all the faults within that subsystem
- * configured to ERROR will only be issued to host, faults with WARNING,
- * INFO_1 and INFO_2 level will be converted to debug message If fault level
- * of a subsystem is configured to WARNING, all the faults within that
- * subsystem configured to ERROR and WARNING will be issued to host, faults
- * with INFO_1 and INFO_2 level will be converted to debug message
+ * Fault levels for WLAN SubSystems. Fault level is used to filter faults
+ * sent to the host. 4 levels of faults per subsystem are available
+ * (FAILURE_LEVEL_T): a. 0 ERROR b. 1 WARNING c. 2 INFO_1 d. 3 INFO_2
+ * Modifying Fault Levels at run time: 1. Set the fault level for the
+ * subsystems in unifiFaultConfigTable 2. Set unifiFaultEnable NOTE: If
+ * fault level of a subsystem is configured to ERROR, all the faults within
+ * that subsystem configured to ERROR will only be issued to host, faults
+ * with WARNING, INFO_1 and INFO_2 level will be converted to debug message
+ * If fault level of a subsystem is configured to WARNING, all the faults
+ * within that subsystem configured to ERROR and WARNING will be issued to
+ * host, faults with INFO_1 and INFO_2 level will be converted to debug
+ * message
*******************************************************************************/
#define SLSI_PSID_UNIFI_FAULT_SUB_SYSTEM_CONTROL 0x13A4
* time required. Only used in emergency debugging. Additional control for
* FSM transition and FSM signals logging is provided. Debug module level
* and 2 boolean flags are encoded within a uint16: Function | Is sending
- * FSM signals | Is sending FSM transitions | Reseved | Module level (signed
- * int)
- * -_-_-_-_-_+-_-_-_-_-_-_-_-_-_-_-_-_-_+-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_+-_-_-_-_-_-+-_-_-_-_-_-_-_-_-_-_-_-_-_-_ Bits | 15 | 14 | 13 - 8 | 7 - 0 Note: 0x00FF disables any debug for a module 0xC004 enables all debug for a module
+ * FSM signals | Is sending FSM transitions | Is sending FSM Timers |
+ * Reserved | Module level (signed int)
+ * -_-_-_-_-_+-_-_-_-_-_-_-_-_-_-_-_-_-_+-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_+-_-_-_-_-_-_-_-_-_-_-_-_-_+-_-_-_-_-_-_+-_-_-_-_-_-_-_-_-_-_-_-_-_- Bits | 15 | 14 | 13 | 12 - 8 | 7 - 0 Note: 0x00FF disables any debug for a module 0xE004 enables all debug for a module
*******************************************************************************/
#define SLSI_PSID_UNIFI_DEBUG_MODULE_CONTROL 0x13A5
#define SLSI_PSID_UNIFI_TX_SG_I160_ENABLED 0x13B3
/*******************************************************************************
- * NAME : UnifiMacAddressRandomisation
+ * NAME : UnifiMacAddressRandomisationActivated
* PSID : 5044 (0x13B4)
* PER INTERFACE?: NO
* TYPE : SlsiBool
* DESCRIPTION :
* Mac Address Randomisation should be applied for Probe Requests.
*******************************************************************************/
-#define SLSI_PSID_UNIFI_MAC_ADDRESS_RANDOMISATION 0x13B4
+#define SLSI_PSID_UNIFI_MAC_ADDRESS_RANDOMISATION_ACTIVATED 0x13B4
+/* TDB: Auto generate to add this */
+#define SLSI_PSID_UNIFI_MAC_ADDRESS_RANDOMISATION_MASK 0x13B7
/*******************************************************************************
- * NAME : UnifiSuBeamformerEnabled
- * PSID : 5045 (0x13B5)
+ * NAME : UnifiRfTestModeEnabled
+ * PSID : 5054 (0x13BE)
* PER INTERFACE?: NO
* TYPE : SlsiBool
* MIN : 0
* MAX : 1
* DEFAULT : FALSE
* DESCRIPTION :
- * SU Beamformer will be used, for transmit only. If disabled, chip will not
- * use SU Beamformer even if peer supports it. To advertise SU Beamformee
- * capability, enable bit 12 of unifiVhtCapabilities.
+ * Set to true when running in RF Test mode. Setting this MIB key to true
+ * prevents setting mandatory HT MCS Rates.
*******************************************************************************/
-#define SLSI_PSID_UNIFI_SU_BEAMFORMER_ENABLED 0x13B5
-
-/*******************************************************************************
- * NAME : UnifiMuBeamformerEnabled
- * PSID : 5046 (0x13B6)
- * PER INTERFACE?: NO
- * TYPE : SlsiBool
- * MIN : 0
- * MAX : 1
- * DEFAULT : FALSE
- * DESCRIPTION :
- * MU Beamformer will be used, for transmit only. If disabled, chip will not
- * use MU Beamformer even if peer supports it. To advertise MU Beamformee
- * capability, enable bit 20 of unifiVhtCapabilities.
- *******************************************************************************/
-#define SLSI_PSID_UNIFI_MU_BEAMFORMER_ENABLED 0x13B6
+#define SLSI_PSID_UNIFI_RF_TEST_MODE_ENABLED 0x13BE
/*******************************************************************************
* NAME : UnifiTxPowerDetectorResponse
* MAX : 32767
* DEFAULT :
* DESCRIPTION :
- * Read the chip temperature as seen by WLAN radio firmware.
+ * Read the chip temperature as seen by WLAN radio firmware.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_CHIP_TEMPERATURE 0x13C6
+
+/*******************************************************************************
+ * NAME : UnifiBatteryVoltage
+ * PSID : 5063 (0x13C7)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * UNITS : millivolt
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT :
+ * DESCRIPTION :
+ * Battery voltage
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_BATTERY_VOLTAGE 0x13C7
+
+/*******************************************************************************
+ * NAME : UnifiTxOobConstraints
+ * PSID : 5064 (0x13C8)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint8
+ * MIN : 0
+ * MAX : 255
+ * DEFAULT :
+ * DESCRIPTION :
+ * OOB constraints table. | octects | description |
+ * |-_-_-_-_-+-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-| | 0 | DPD applicability bitmask: 0 = no DPD, 1 = dynamic DPD, 2 = static DPD, 3 = applies to both static and dynamic DPD | | 1-2 | Bitmask indicating which regulatory domains this rule applies to FCC=bit0, ETSI=bit1, JAPAN=bit2 | | 3-4 | Bitmask indicating which band edges this rule applies to RICE_BAND_EDGE_ISM_24G_LOWER = bit 0, RICE_BAND_EDGE_ISM_24G_UPPER = bit 1, RICE_BAND_EDGE_U_NII_1_LOWER = bit 2, RICE_BAND_EDGE_U_NII_1_UPPER = bit 3, RICE_BAND_EDGE_U_NII_2_LOWER = bit 4, RICE_BAND_EDGE_U_NII_2_UPPER = bit 5, RICE_BAND_EDGE_U_NII_2E_LOWER = bit 6, RICE_BAND_EDGE_U_NII_2E_UPPER = bit 7, RICE_BAND_EDGE_U_NII_3_LOWER = bit 8, RICE_BAND_EDGE_U_NII_3_UPPER = bit 9 | | 5 | Bitmask indicating which modulation types this rule applies to (LSB/b0=DSSS/CCK, b1= OFDM0 modulation group, b2= OFDM1 modulation group) | | 6 | Bitmask indicating which channel bandwidths this rule applies to (LSB/b0=20MHz, b1=40MHz, b2=80MHz) | | 7 | Minimum distance to nearest band edge in 500 kHz units for which this constraint becomes is applicable. | | 8 | Maximum power (EIRP) for this particular constraint - specified in units of quarter dBm. | | 9-32 | Spectral shaping configuration to be used for this particular constraint. The value is specific to the radio hardware and should only be altered under advice from the IC supplier. | | 33-56| Tx DPD Spectral shaping configuration to be used for this particular constraint. The value is specific to the radio hardware and should only be altered under advice from the IC supplier. | |
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_TX_OOB_CONSTRAINTS 0x13C8
+
+/*******************************************************************************
+ * NAME : UnifiTxPaGainDpdTemperatureCompensation
+ * PSID : 5066 (0x13CA)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint8
+ * MIN : 0
+ * MAX : 255
+ * DEFAULT :
+ * DESCRIPTION :
+ * Hardware specific transmitter PA gain for DPD temperature compensation
+ * settings. 2G settings before 5G. Increasing order within band.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_TX_PA_GAIN_DPD_TEMPERATURE_COMPENSATION 0x13CA
+
+/*******************************************************************************
+ * NAME : UnifiTxPaGainDpdFrequencyCompensation
+ * PSID : 5067 (0x13CB)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint8
+ * MIN : 0
+ * MAX : 255
+ * DEFAULT :
+ * DESCRIPTION :
+ * Hardware specific transmitter PA gain for DPD frequency compensation
+ * settings. 2G settings before 5G. Increasing order within band.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_TX_PA_GAIN_DPD_FREQUENCY_COMPENSATION 0x13CB
+
+/*******************************************************************************
+ * NAME : UnifiTxPowerTrimConfig
+ * PSID : 5072 (0x13D0)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint8
+ * MIN : 25
+ * MAX : 25
+ * DEFAULT :
+ * DESCRIPTION :
+ * Hardware specific transmitter power trim settings
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_TX_POWER_TRIM_CONFIG 0x13D0
+
+/*******************************************************************************
+ * NAME : UnifiForceShortSlotTime
+ * PSID : 5080 (0x13D8)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiBool
+ * MIN : 0
+ * MAX : 1
+ * DEFAULT : FALSE
+ * DESCRIPTION :
+ * If set to true, forces FW to use short slot times for all VIFs.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_FORCE_SHORT_SLOT_TIME 0x13D8
+
+/*******************************************************************************
+ * NAME : UnifiTxGainStepSettings
+ * PSID : 5081 (0x13D9)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint8
+ * MIN : 0
+ * MAX : 255
+ * DEFAULT :
+ * DESCRIPTION :
+ * Hardware specific transmitter gain step settings. 2G settings before 5G.
+ * Increasing order within band.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_TX_GAIN_STEP_SETTINGS 0x13D9
+
+/*******************************************************************************
+ * NAME : UnifiDebugDisableRadioNannyActions
+ * PSID : 5082 (0x13DA)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT :
+ * DESCRIPTION :
+ * Bitmap to disable the radio nanny actions. B0==radio 0, B1==radio 1
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_DEBUG_DISABLE_RADIO_NANNY_ACTIONS 0x13DA
+
+/*******************************************************************************
+ * NAME : UnifiRxCckModemSensitivity
+ * PSID : 5083 (0x13DB)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint8
+ * MIN : 6
+ * MAX : 6
+ * DEFAULT :
+ * DESCRIPTION :
+ * Specify values of CCK modem sensitivity for scan, normal and low
+ * sensitivity.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_RX_CCK_MODEM_SENSITIVITY 0x13DB
+
+/*******************************************************************************
+ * NAME : UnifiDpdPerBandwidth
+ * PSID : 5084 (0x13DC)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT : 63
+ * DESCRIPTION :
+ * Bitmask to enable Digital Pre-Distortion per bandwidth
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_DPD_PER_BANDWIDTH 0x13DC
+
+/*******************************************************************************
+ * NAME : UnifiBbVersion
+ * PSID : 5085 (0x13DD)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT :
+ * DESCRIPTION :
+ * Baseband chip version number determined by reading BBIC version
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_BB_VERSION 0x13DD
+
+/*******************************************************************************
+ * NAME : UnifiRfVersion
+ * PSID : 5086 (0x13DE)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT :
+ * DESCRIPTION :
+ * RF chip version number determined by reading RFIC version
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_RF_VERSION 0x13DE
+
+/*******************************************************************************
+ * NAME : UnifiReadHardwareCounter
+ * PSID : 5087 (0x13DF)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint32
+ * MIN : 0
+ * MAX : 4294967295
+ * DEFAULT :
+ * DESCRIPTION :
+ * Read a value from a hardware packet counter for a specific radio_id and
+ * return it. The firmware will convert the radio_id to the associated
+ * mac_instance.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_READ_HARDWARE_COUNTER 0x13DF
+
+/*******************************************************************************
+ * NAME : UnifiClearRadioTrimCache
+ * PSID : 5088 (0x13E0)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT :
+ * DESCRIPTION :
+ * Clears the radio trim cache. The parameter is ignored.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_CLEAR_RADIO_TRIM_CACHE 0x13E0
+
+/*******************************************************************************
+ * NAME : UnifiRadioTxSettingsRead
+ * PSID : 5089 (0x13E1)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint32
+ * MIN : 0
+ * MAX : 4294967295
+ * DEFAULT :
+ * DESCRIPTION :
+ * Read value from Tx settings.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_RADIO_TX_SETTINGS_READ 0x13E1
+
+/*******************************************************************************
+ * NAME : UnifiModemSgiOffset
+ * PSID : 5090 (0x13E2)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT :
+ * DESCRIPTION :
+ * Overwrite SGI sampling offset. Indexed by Band and Bandwidth. Defaults
+ * currently defined in fw.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_MODEM_SGI_OFFSET 0x13E2
+
+/*******************************************************************************
+ * NAME : UnifiRadioTxPowerOverride
+ * PSID : 5091 (0x13E3)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiInt16
+ * MIN : -128
+ * MAX : 127
+ * DEFAULT :
+ * DESCRIPTION :
+ * Option in radio code to override the power requested by the upper layer
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_RADIO_TX_POWER_OVERRIDE 0x13E3
+
+/*******************************************************************************
+ * NAME : UnifiRxRadioCsMode
+ * PSID : 5092 (0x13E4)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT :
+ * DESCRIPTION :
+ * OBSOLETE. Configures RX Radio CS detection for 80MHz bandwidth.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_RX_RADIO_CS_MODE 0x13E4
+
+/*******************************************************************************
+ * NAME : UnifiRxPriEnergyDetThreshold
+ * PSID : 5093 (0x13E5)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT :
+ * DESCRIPTION :
+ * OBSOLETE. Energy detection threshold for primary 20MHz channel.
*******************************************************************************/
-#define SLSI_PSID_UNIFI_CHIP_TEMPERATURE 0x13C6
+#define SLSI_PSID_UNIFI_RX_PRI_ENERGY_DET_THRESHOLD 0x13E5
/*******************************************************************************
- * NAME : UnifiBatteryVoltage
- * PSID : 5063 (0x13C7)
+ * NAME : UnifiRxSecEnergyDetThreshold
+ * PSID : 5094 (0x13E6)
* PER INTERFACE?: NO
* TYPE : SlsiUint16
- * UNITS : millivolt
* MIN : 0
* MAX : 65535
* DEFAULT :
* DESCRIPTION :
- * Battery voltage
+ * OBSOLETE. Energy detection threshold for secondary 20MHz channel.
*******************************************************************************/
-#define SLSI_PSID_UNIFI_BATTERY_VOLTAGE 0x13C7
+#define SLSI_PSID_UNIFI_RX_SEC_ENERGY_DET_THRESHOLD 0x13E6
/*******************************************************************************
- * NAME : UnifiTxOobConstraints
- * PSID : 5064 (0x13C8)
+ * NAME : UnifiAgcThresholds
+ * PSID : 5095 (0x13E7)
* PER INTERFACE?: NO
* TYPE : SlsiUint8
* MIN : 0
* MAX : 255
* DEFAULT :
* DESCRIPTION :
- * OOB constraints table. | octects | description |
- * |-_-_-_-_-+-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-| | 0 | DPD applicability bitmask: 0 = no DPD, 1 = dynamic DPD, 2 = static DPD, 3 = applies to both static and dynamic DPD | | 1-2 | Bitmask indicating which regulatory domains this rule applies to FCC=bit0, ETSI=bit1, JAPAN=bit2 | | 3-4 | Bitmask indicating which band edges this rule applies to RICE_BAND_EDGE_ISM_24G_LOWER = bit 0, RICE_BAND_EDGE_ISM_24G_UPPER = bit 1, RICE_BAND_EDGE_U_NII_1_LOWER = bit 2, RICE_BAND_EDGE_U_NII_1_UPPER = bit 3, RICE_BAND_EDGE_U_NII_2_LOWER = bit 4, RICE_BAND_EDGE_U_NII_2_UPPER = bit 5, RICE_BAND_EDGE_U_NII_2E_LOWER = bit 6, RICE_BAND_EDGE_U_NII_2E_UPPER = bit 7, RICE_BAND_EDGE_U_NII_3_LOWER = bit 8, RICE_BAND_EDGE_U_NII_3_UPPER = bit 9 | | 5 | Bitmask indicating which modulation types this rule applies to (LSB/b0=DSSS/CCK, b1= OFDM0 modulation group, b2= OFDM1 modulation group) | | 6 | Bitmask indicating which channel bandwidths this rule applies to (LSB/b0=20MHz, b1=40MHz, b2=80MHz) | | 7 | Minimum distance to nearest band edge in 500 kHz units for which this constraint becomes is applicable. | | 8 | Maximum power (EIRP) for this particular constraint - specified in units of quarter dBm. | | 9-32 | Spectral shaping configuration to be used for this particular constraint. The value is specific to the radio hardware and should only be altered under advice from the IC supplier. | |
+ * AGC Thresholds settings
*******************************************************************************/
-#define SLSI_PSID_UNIFI_TX_OOB_CONSTRAINTS 0x13C8
+#define SLSI_PSID_UNIFI_AGC_THRESHOLDS 0x13E7
/*******************************************************************************
- * NAME : UnifiTxPaGainDpdTemperatureCompensation
- * PSID : 5066 (0x13CA)
+ * NAME : UnifiRadioRxSettingsRead
+ * PSID : 5096 (0x13E8)
* PER INTERFACE?: NO
* TYPE : SlsiUint8
* MIN : 0
- * MAX : 255
+ * MAX : 65535
* DEFAULT :
* DESCRIPTION :
- * Hardware specific transmitter PA gain for DPD temperature compensation
- * settings. 2G settings before 5G. Increasing order within band.
+ * Read value from Rx settings.
*******************************************************************************/
-#define SLSI_PSID_UNIFI_TX_PA_GAIN_DPD_TEMPERATURE_COMPENSATION 0x13CA
+#define SLSI_PSID_UNIFI_RADIO_RX_SETTINGS_READ 0x13E8
/*******************************************************************************
- * NAME : UnifiTxPaGainDpdFrequencyCompensation
- * PSID : 5067 (0x13CB)
+ * NAME : UnifiStaticDpdGain
+ * PSID : 5097 (0x13E9)
* PER INTERFACE?: NO
* TYPE : SlsiUint8
- * MIN : 0
- * MAX : 255
+ * MIN : 11
+ * MAX : 27
* DEFAULT :
* DESCRIPTION :
- * Hardware specific transmitter PA gain for DPD frequency compensation
- * settings. 2G settings before 5G. Increasing order within band.
+ * Specify modulation specifc gains for static dpd optimisation.
*******************************************************************************/
-#define SLSI_PSID_UNIFI_TX_PA_GAIN_DPD_FREQUENCY_COMPENSATION 0x13CB
+#define SLSI_PSID_UNIFI_STATIC_DPD_GAIN 0x13E9
/*******************************************************************************
- * NAME : UnifiTxPowerTrimConfig
- * PSID : 5072 (0x13D0)
+ * NAME : UnifiIqBufferSize
+ * PSID : 5098 (0x13EA)
* PER INTERFACE?: NO
- * TYPE : SlsiUint8
- * MIN : 21
- * MAX : 21
+ * TYPE : SlsiUint32
+ * MIN : 0
+ * MAX : 4294967295
* DEFAULT :
* DESCRIPTION :
- * Configuration settings for the TX power trim. The format is [band,
- * pcal_ofdm0_to_cck_mso, pcal_ofdm0_to_cck_lso, pcal_ofdm0_to_ofdm1_mso,
- * pcal_ofdm0_to_ofdm1_lso, pcal_20_to_80_mso, pcal_20_to_80_lso,
- * pcal_20_to_40_mso, pcal_20_to_40_lso, psat_v2i_gain, psat_mix_gain,
- * psat_drv_gain, psat_pa_gain, psat_power_ref_mso, psat_power_ref_lso,
- * psat_drv_bias, psat_pa_bias, max_adjust_up_mso, max_adjust_up_lso,
- * max_adjust_down_mso, max_adjust_down_lso].
+ * Buffer Size for IQ capture to allow CATs to read it.
*******************************************************************************/
-#define SLSI_PSID_UNIFI_TX_POWER_TRIM_CONFIG 0x13D0
+#define SLSI_PSID_UNIFI_IQ_BUFFER_SIZE 0x13EA
/*******************************************************************************
- * NAME : UnifiForceShortSlotTime
- * PSID : 5080 (0x13D8)
+ * NAME : UnifiNarrowbandCcaThresholds
+ * PSID : 5099 (0x13EB)
* PER INTERFACE?: NO
- * TYPE : SlsiBool
+ * TYPE : SlsiUint8
* MIN : 0
- * MAX : 1
- * DEFAULT : FALSE
+ * MAX : 255
+ * DEFAULT :
* DESCRIPTION :
- * If set to true, forces FW to use short slot times for all VIFs.
+ * The narrowband CCA ED thresholds so that the CCA-ED triggers at the
+ * regulatory value of -62 dBm.
*******************************************************************************/
-#define SLSI_PSID_UNIFI_FORCE_SHORT_SLOT_TIME 0x13D8
+#define SLSI_PSID_UNIFI_NARROWBAND_CCA_THRESHOLDS 0x13EB
/*******************************************************************************
- * NAME : UnifiTxGainStepSettings
- * PSID : 5081 (0x13D9)
+ * NAME : UnifiRadioCcaDebug
+ * PSID : 5100 (0x13EC)
* PER INTERFACE?: NO
- * TYPE : SlsiUint8
+ * TYPE : SlsiUint32
* MIN : 0
- * MAX : 255
+ * MAX : 4294967295
* DEFAULT :
* DESCRIPTION :
- * Hardware specific transmitter gain step settings. 2G settings before 5G.
- * Increasing order within band.
+ * Read values from Radio CCA settings.
*******************************************************************************/
-#define SLSI_PSID_UNIFI_TX_GAIN_STEP_SETTINGS 0x13D9
+#define SLSI_PSID_UNIFI_RADIO_CCA_DEBUG 0x13EC
/*******************************************************************************
- * NAME : UnifiDebugDisableRadioNannyActions
- * PSID : 5082 (0x13DA)
+ * NAME : UnifiCcacsThresh
+ * PSID : 5101 (0x13ED)
* PER INTERFACE?: NO
* TYPE : SlsiUint16
* MIN : 0
* MAX : 65535
* DEFAULT :
* DESCRIPTION :
- * Bitmap to disable the radio nanny actions. B0==radio 0, B1==radio 1
+ * Configures CCA CS thresholds.
*******************************************************************************/
-#define SLSI_PSID_UNIFI_DEBUG_DISABLE_RADIO_NANNY_ACTIONS 0x13DA
+#define SLSI_PSID_UNIFI_CCACS_THRESH 0x13ED
/*******************************************************************************
- * NAME : UnifiRxCckModemSensitivity
- * PSID : 5083 (0x13DB)
+ * NAME : UnifiCcaMasterSwitch
+ * PSID : 5102 (0x13EE)
* PER INTERFACE?: NO
- * TYPE : SlsiUint8
- * MIN : 6
- * MAX : 6
+ * TYPE : SlsiUint16
+ * MIN : 0
+ * MAX : 65535
* DEFAULT :
* DESCRIPTION :
- * Specify values of CCK modem sensitivity for scan, normal and low
- * sensitivity.
+ * Enables CCA
*******************************************************************************/
-#define SLSI_PSID_UNIFI_RX_CCK_MODEM_SENSITIVITY 0x13DB
+#define SLSI_PSID_UNIFI_CCA_MASTER_SWITCH 0x13EE
/*******************************************************************************
- * NAME : UnifiDpdPerBandwidth
- * PSID : 5084 (0x13DC)
+ * NAME : UnifiRxSyncCcaCfg
+ * PSID : 5103 (0x13EF)
* PER INTERFACE?: NO
* TYPE : SlsiUint16
* MIN : 0
* MAX : 65535
- * DEFAULT : 63
+ * DEFAULT :
* DESCRIPTION :
- * Bitmask to enable Digital Pre-Distortion per bandwidth
+ * Configures CCA per 20 MHz sub-band.
*******************************************************************************/
-#define SLSI_PSID_UNIFI_DPD_PER_BANDWIDTH 0x13DC
+#define SLSI_PSID_UNIFI_RX_SYNC_CCA_CFG 0x13EF
/*******************************************************************************
- * NAME : UnifiBbVersion
- * PSID : 5085 (0x13DD)
+ * NAME : UnifiMacCcaBusyTime
+ * PSID : 5104 (0x13F0)
* PER INTERFACE?: NO
* TYPE : SlsiUint16
* MIN : 0
* MAX : 65535
* DEFAULT :
* DESCRIPTION :
- * Baseband chip version number determined by reading BBIC version
+ * Counts the time CCA indicates busy
*******************************************************************************/
-#define SLSI_PSID_UNIFI_BB_VERSION 0x13DD
+#define SLSI_PSID_UNIFI_MAC_CCA_BUSY_TIME 0x13F0
/*******************************************************************************
- * NAME : UnifiRfVersion
- * PSID : 5086 (0x13DE)
+ * NAME : UnifiMacSecChanClearTime
+ * PSID : 5105 (0x13F1)
* PER INTERFACE?: NO
* TYPE : SlsiUint16
* MIN : 0
* MAX : 65535
* DEFAULT :
* DESCRIPTION :
- * RF chip version number determined by reading RFIC version
+ * Configures PIFS
*******************************************************************************/
-#define SLSI_PSID_UNIFI_RF_VERSION 0x13DE
+#define SLSI_PSID_UNIFI_MAC_SEC_CHAN_CLEAR_TIME 0x13F1
/*******************************************************************************
- * NAME : UnifiReadHardwareCounter
- * PSID : 5087 (0x13DF)
+ * NAME : UnifiDpdDebug
+ * PSID : 5106 (0x13F2)
* PER INTERFACE?: NO
* TYPE : SlsiUint32
* MIN : 0
* MAX : 4294967295
* DEFAULT :
* DESCRIPTION :
- * Read a value from a hardware packet counter in a specific mac instance
- * and return it.
+ * Debug MIBs for DPD
*******************************************************************************/
-#define SLSI_PSID_UNIFI_READ_HARDWARE_COUNTER 0x13DF
+#define SLSI_PSID_UNIFI_DPD_DEBUG 0x13F2
/*******************************************************************************
- * NAME : UnifiClearRadioTrimCache
- * PSID : 5088 (0x13E0)
+ * NAME : UnifiNarrowbandCcaDebug
+ * PSID : 5107 (0x13F3)
* PER INTERFACE?: NO
- * TYPE : SlsiUint16
+ * TYPE : SlsiUint32
* MIN : 0
- * MAX : 65535
+ * MAX : 4294967295
* DEFAULT :
* DESCRIPTION :
- * Clears the radio trim cache. The parameter is ignored.
+ * Read values from Radio CCA settings.
*******************************************************************************/
-#define SLSI_PSID_UNIFI_CLEAR_RADIO_TRIM_CACHE 0x13E0
+#define SLSI_PSID_UNIFI_NARROWBAND_CCA_DEBUG 0x13F3
/*******************************************************************************
- * NAME : UnifiRadioTxSettingsRead
- * PSID : 5089 (0x13E1)
+ * NAME : UnifiRttCapabilities
+ * PSID : 5300 (0x14B4)
* PER INTERFACE?: NO
- * TYPE : SlsiUint32
- * MIN : 0
- * MAX : 4294967295
- * DEFAULT :
+ * TYPE : SlsiUint8
+ * MIN : 8
+ * MAX : 8
+ * DEFAULT : { 0X01, 0X01, 0X01, 0X01, 0X00, 0X07, 0X1C, 0X32 }
* DESCRIPTION :
- * Read value from Tx settings.
+ * RTT capabilities of the chip. see SC-506960-SW.
*******************************************************************************/
-#define SLSI_PSID_UNIFI_RADIO_TX_SETTINGS_READ 0x13E1
+#define SLSI_PSID_UNIFI_RTT_CAPABILITIES 0x14B4
/*******************************************************************************
- * NAME : UnifiModemSgiOffset
- * PSID : 5090 (0x13E2)
+ * NAME : UnifiMinDeltaFtm
+ * PSID : 5301 (0x14B5)
* PER INTERFACE?: NO
* TYPE : SlsiUint16
* MIN : 0
* MAX : 65535
- * DEFAULT :
+ * DEFAULT : 5
* DESCRIPTION :
- * Overwrite SGI sampling offset. Indexed by Band and Bandwidth. Defaults
- * currently defined in fw.
+ * Indicates the default minimum time between consecutive FTM frames in
+ * units of 100 us
*******************************************************************************/
-#define SLSI_PSID_UNIFI_MODEM_SGI_OFFSET 0x13E2
+#define SLSI_PSID_UNIFI_MIN_DELTA_FTM 0x14B5
/*******************************************************************************
- * NAME : UnifiRadioTxPowerOverride
- * PSID : 5091 (0x13E3)
+ * NAME : UnifiFtmPerBurst
+ * PSID : 5302 (0x14B6)
* PER INTERFACE?: NO
- * TYPE : SlsiInt16
- * MIN : -128
- * MAX : 127
- * DEFAULT :
+ * TYPE : SlsiUint16
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT : 4
* DESCRIPTION :
- * Option in radio code to override the power requested by the upper layer
+ * indicates how many successfully transmitted FTM frames are requested per
+ * burst instance
*******************************************************************************/
-#define SLSI_PSID_UNIFI_RADIO_TX_POWER_OVERRIDE 0x13E3
+#define SLSI_PSID_UNIFI_FTM_PER_BURST 0x14B6
/*******************************************************************************
- * NAME : UnifiRxRadioCsMode
- * PSID : 5092 (0x13E4)
+ * NAME : UnifiFtmBurstDuration
+ * PSID : 5303 (0x14B7)
* PER INTERFACE?: NO
* TYPE : SlsiUint16
* MIN : 0
* MAX : 65535
- * DEFAULT :
+ * DEFAULT : 6
* DESCRIPTION :
- * Configures RX Radio CS detection for 80MHz bandwidth.
+ * indicates the duration of a burst instance, values 0, 1, 12-14 are
+ * reserved, [2..11], the burst duration is defined as (250 x 2)^(N-2), and
+ * 15 means "no preference"
*******************************************************************************/
-#define SLSI_PSID_UNIFI_RX_RADIO_CS_MODE 0x13E4
+#define SLSI_PSID_UNIFI_FTM_BURST_DURATION 0x14B7
/*******************************************************************************
- * NAME : UnifiRxPriEnergyDetThreshold
- * PSID : 5093 (0x13E5)
+ * NAME : UnifiNumOfBurstsExponent
+ * PSID : 5304 (0x14B8)
* PER INTERFACE?: NO
* TYPE : SlsiUint16
* MIN : 0
* MAX : 65535
* DEFAULT :
* DESCRIPTION :
- * Energy detection threshold for primary 20MHz channel.
+ * the number of burst instances is 2^(Number of Bursts Exponent), value 15
+ * means "no preference"
*******************************************************************************/
-#define SLSI_PSID_UNIFI_RX_PRI_ENERGY_DET_THRESHOLD 0x13E5
+#define SLSI_PSID_UNIFI_NUM_OF_BURSTS_EXPONENT 0x14B8
/*******************************************************************************
- * NAME : UnifiRxSecEnergyDetThreshold
- * PSID : 5094 (0x13E6)
+ * NAME : UnifiAsapModeEnabled
+ * PSID : 5305 (0x14B9)
* PER INTERFACE?: NO
- * TYPE : SlsiUint16
+ * TYPE : SlsiBool
* MIN : 0
- * MAX : 65535
- * DEFAULT :
+ * MAX : 1
+ * DEFAULT : 1
* DESCRIPTION :
- * Energy detection threshold for secondary 20MHz channel.
+ * Enable support for ASAP mode in FTM
*******************************************************************************/
-#define SLSI_PSID_UNIFI_RX_SEC_ENERGY_DET_THRESHOLD 0x13E6
+#define SLSI_PSID_UNIFI_ASAP_MODE_ENABLED 0x14B9
/*******************************************************************************
- * NAME : UnifiAgcThresholds
- * PSID : 5095 (0x13E7)
+ * NAME : UnifiTpcMinPower2Gmimo
+ * PSID : 6011 (0x177B)
* PER INTERFACE?: NO
- * TYPE : SlsiUint8
- * MIN : 0
- * MAX : 255
- * DEFAULT :
+ * TYPE : SlsiInt16
+ * MIN : -32768
+ * MAX : 32767
+ * DEFAULT : 52
* DESCRIPTION :
- * AGC Thresholds settings
+ * Minimum power for 2.4GHz MIMO interface when RSSI is above
+ * unifiTPCMinPowerRSSIThreshold (quarter dbm). Should be greater than
+ * dot11PowerCapabilityMinImplemented.
*******************************************************************************/
-#define SLSI_PSID_UNIFI_AGC_THRESHOLDS 0x13E7
+#define SLSI_PSID_UNIFI_TPC_MIN_POWER2_GMIMO 0x177B
+
+/*******************************************************************************
+ * NAME : UnifiTpcMinPower5Gmimo
+ * PSID : 6012 (0x177C)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiInt16
+ * MIN : -32768
+ * MAX : 32767
+ * DEFAULT : 52
+ * DESCRIPTION :
+ * Minimum power for 5 GHz MIMO interface when RSSI is above
+ * unifiTPCMinPowerRSSIThreshold (quarter dbm). Should be greater than
+ * dot11PowerCapabilityMinImplemented.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_TPC_MIN_POWER5_GMIMO 0x177C
/*******************************************************************************
* NAME : UnifiLnaControlEnabled
* MAX : 32767
* DEFAULT : 52
* DESCRIPTION :
- * Minimum power for 2.4GHz interface when RSSI is above
+ * Minimum power for 2.4GHz SISO interface when RSSI is above
* unifiTPCMinPowerRSSIThreshold (quarter dbm). Should be greater than
* dot11PowerCapabilityMinImplemented.
*******************************************************************************/
* MAX : 32767
* DEFAULT : 40
* DESCRIPTION :
- * Minimum power for 5 GHz interface when RSSI is above
+ * Minimum power for 5 GHz SISO interface when RSSI is above
* unifiTPCMinPowerRSSIThreshold (quarter dbm). Should be greater than
* dot11PowerCapabilityMinImplemented.
*******************************************************************************/
* MAX : 32767
* DEFAULT :
* DESCRIPTION :
- * Max power values per Band (quarter dBm).
+ * Max power values per band per index(quarter dBm).
*******************************************************************************/
#define SLSI_PSID_UNIFI_SAR_BACKOFF 0x178A
+/*******************************************************************************
+ * NAME : UnifiTpcUseAfterConnectRsp
+ * PSID : 6027 (0x178B)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiBool
+ * MIN : 0
+ * MAX : 1
+ * DEFAULT : TRUE
+ * DESCRIPTION :
+ * Use TPC only after MlmeConnect_Rsp has been received from the Host i.e.
+ * not during initial connection exchanges (EAPOL/DHCP operation) as RSSI
+ * readings might be inaccurate.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_TPC_USE_AFTER_CONNECT_RSP 0x178B
+
/*******************************************************************************
* NAME : UnifiRadioLpRxRssiThresholdLower
* PSID : 6028 (0x178C)
#define SLSI_PSID_UNIFI_RADIO_LP_RX_RSSI_THRESHOLD_UPPER 0x178D
/*******************************************************************************
- * NAME : UnifiGripCap
- * PSID : 6031 (0x178F)
+ * NAME : UnifiTestTxPowerEnable
+ * PSID : 6032 (0x1790)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT : 0XFFFF
+ * DESCRIPTION :
+ * Bitfield to enable Control Plane Tx Power processing. MLME/Macrame use
+ * only.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_TEST_TX_POWER_ENABLE 0x1790
+
+/*******************************************************************************
+ * NAME : UnifiLteCoexMaxPowerRssiThreshold
+ * PSID : 6033 (0x1791)
* PER INTERFACE?: NO
* TYPE : SlsiInt16
* MIN : -32768
* MAX : 32767
- * DEFAULT :
+ * DEFAULT : -55
* DESCRIPTION :
- * Max power values per Band (quarter dBm).
+ * Below this (dBm) threshold, switch to max power allowed by regulatory. If
+ * it has been previously reduced due to unifiTPCMinPowerRSSIThreshold.
*******************************************************************************/
-#define SLSI_PSID_UNIFI_GRIP_CAP 0x178F
+#define SLSI_PSID_UNIFI_LTE_COEX_MAX_POWER_RSSI_THRESHOLD 0x1791
/*******************************************************************************
- * NAME : UnifiTestTxPowerEnable
- * PSID : 6032 (0x1790)
+ * NAME : UnifiLteCoexMinPowerRssiThreshold
+ * PSID : 6034 (0x1792)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiInt16
+ * MIN : -32768
+ * MAX : 32767
+ * DEFAULT : -45
+ * DESCRIPTION :
+ * Above this(dBm) threshold, switch to minimum hardware supported - capped
+ * by unifiTPCMinPower2G/unifiTPCMinPower5G. A Zero value reverts the power
+ * to a default state.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_LTE_COEX_MIN_POWER_RSSI_THRESHOLD 0x1792
+
+/*******************************************************************************
+ * NAME : UnifiLteCoexPowerReduction
+ * PSID : 6035 (0x1793)
* PER INTERFACE?: NO
* TYPE : SlsiUint16
* MIN : 0
- * MAX : 65535
- * DEFAULT : 0XFF
+ * MAX : 127
+ * DEFAULT : 24
* DESCRIPTION :
- * Bitfield to enable Control Plane Tx Power processing. MLME/Macrame use
- * only.
+ * When LTE Coex Power Reduction provisions are met, impose a power cap of
+ * the regulatory domain less the amount specified by this MIB (quarter dB)
*******************************************************************************/
-#define SLSI_PSID_UNIFI_TEST_TX_POWER_ENABLE 0x1790
+#define SLSI_PSID_UNIFI_LTE_COEX_POWER_REDUCTION 0x1793
/*******************************************************************************
* NAME : UnifiPmfAssociationComebackTimeDelta
* TYPE : SlsiUint32
* MIN : 0
* MAX : 4294967295
- * DEFAULT : 0X3
+ * DEFAULT : 0X03
* DESCRIPTION :
* Bit mask for turning on individual debug entities in the data_plane that
* if enabled effect throughput. See DPLP_DEBUG_ENTITIES_T in
*******************************************************************************/
#define SLSI_PSID_UNIFI_DPLANE_DEBUG 0x17B9
+/*******************************************************************************
+ * NAME : UnifiDebugForceSiso
+ * PSID : 6074 (0x17BA)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiBool
+ * MIN : 0
+ * MAX : 1
+ * DEFAULT : FALSE
+ * DESCRIPTION :
+ * Force the platform to only use one radio even if multiple radios are
+ * supported. WARNING: Changing this value after system start-up will have
+ * no effect.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_DEBUG_FORCE_SISO 0x17BA
+
/*******************************************************************************
* NAME : UnifiNanEnabled
* PSID : 6080 (0x17C0)
* DESCRIPTION :
* Enables low power radio RX for idle STA and AP VIFs respectively.
* Setting/clearing bit 0 enables/disabled LP RX for (all) STA/Cli VIFs.
- * Setting/clearing bit 1 enables/disabled LP RX for AP/GO VIFs.
+ * Setting/clearing bit 1 enables/disabled LP RX for AP/GO VIFs.This mib
+ * value will be updated if "unifiRameUpdateMibs" mib is toggled
*******************************************************************************/
#define SLSI_PSID_RESERVED_FOR_NAN 0x17CE
* MAX : 1
* DEFAULT : FALSE
* DESCRIPTION :
- * Identify whether the chip supports dualband concurrency or not.
+ * Identify whether the chip supports dualband concurrency or not (RSDB vs.
+ * VSDB). Set in the respective platform htf file.
*******************************************************************************/
#define SLSI_PSID_UNIFI_DUAL_BAND_CONCURRENCY 0x17EB
* MAX : 3
* DEFAULT : {0X30, 0X30, 0X20}
* DESCRIPTION :
- * Hosts only sets the default Code (index 1). Each VIF updates its Code for
- * the Host to read (index 2-4).
+ * Hosts sets the Default Code.
*******************************************************************************/
#define SLSI_PSID_UNIFI_DEFAULT_COUNTRY 0x1F4D
*******************************************************************************/
#define SLSI_PSID_UNIFI_OPERATING_CLASS_PARAMTERS 0x1F4F
+/*******************************************************************************
+ * NAME : UnifiVifCountry
+ * PSID : 8016 (0x1F50)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint8
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT :
+ * DESCRIPTION :
+ * Per VIf: Each VIF updates its Country Code for the Host to read
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_VIF_COUNTRY 0x1F50
+
/*******************************************************************************
* NAME : UnifiNoCellMaxPower
* PSID : 8017 (0x1F51)
* DESCRIPTION :
* Channels applicable. Defined in a uint64 represented by the octet string.
* First byte of the octet string maps to LSB. Bit 0 maps to channel 1.
- * Mapping defined in mlme_regulatory_freq_list[].
+ * Mapping defined in ChannelisationRules.
*******************************************************************************/
#define SLSI_PSID_UNIFI_NO_CELL_INCLUDED_CHANNELS 0x1F52
+/*******************************************************************************
+ * NAME : UnifiRegDomVersion
+ * PSID : 8019 (0x1F53)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiUint16
+ * MIN : 0
+ * MAX : 65535
+ * DEFAULT :
+ * DESCRIPTION :
+ * Regulatory domain version encoded into 2 bytes, major version as MSB and
+ * minor version as LSB
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_REG_DOM_VERSION 0x1F53
+
+/*******************************************************************************
+ * NAME : UnifiDefaultCountryWithoutCH12CH13
+ * PSID : 8020 (0x1F54)
+ * PER INTERFACE?: NO
+ * TYPE : SlsiBool
+ * MIN : 0
+ * MAX : 1
+ * DEFAULT : FALSE
+ * DESCRIPTION :
+ * Update the default country code to ensure CH12 and CH13 are not used.
+ *******************************************************************************/
+#define SLSI_PSID_UNIFI_DEFAULT_COUNTRY_WITHOUT_CH12_CH13 0x1F54
+
/*******************************************************************************
* NAME : UnifiReadReg
* PSID : 8051 (0x1F73)
#define SLSI_SCAN_CHANNEL_DESCRIPTOR_SIZE 3
#define SLSI_CHANN_INFO_HT_SCB 0x0100
-#define SLSI_FW_API_RATE_HT_SELECTOR_FIELD 0xc000
-#define SLSI_FW_API_RATE_NON_HT_SELECTED 0x4000
-#define SLSI_FW_API_RATE_HT_SELECTED 0x8000
-#define SLSI_FW_API_RATE_VHT_SELECTED 0xc000
-
-#define SLSI_FW_API_RATE_VHT_MCS_FIELD 0x000F
-#define SLSI_FW_API_RATE_HT_MCS_FIELD 0x003F
-#define SLSI_FW_API_RATE_INDEX_FIELD 0x1fff
-#define SLSI_FW_API_RATE_VHT_NSS_FIELD 0x0070
-#define SLSI_FW_API_RATE_HT_NSS_FIELD 0x0040
-
-#define SLSI_FW_API_RATE_BW_FIELD 0x0600
-#define SLSI_FW_API_RATE_BW_40MHZ 0x0200
-#define SLSI_FW_API_RATE_BW_20MHZ 0x0000
-
-#define SLSI_FW_API_RATE_SGI 0x0100
-#define SLSI_FW_API_RATE_GF 0x0080
-
#ifdef CONFIG_SCSC_WLAN_GSCAN_ENABLE
#define SLSI_FW_MAX_BSSID_PER_TRACKING_IE (20)
#define SLSI_FW_BSSID_DESCRIPTOR_BSS_SIZE (10)
module_param(missing_cfm_ind_panic, bool, S_IRUGO | S_IWUSR);
MODULE_PARM_DESC(missing_cfm_ind_panic, "Panic on missing confirm or indication from the chip");
-/* indices: 3= BW20->idx_0, BW40->idx_1, BW80->idx_2.
- * 2= noSGI->idx_0, SGI->idx_1
- * 10= mcs index
- * rate units 100kbps
- * This table for single stream Nss=1and does not include 160MHz BW and 80+80MHz BW.
- */
-static const u16 slsi_rates_table[3][2][10] = {
- { /* BW20 */
- { /* no SGI */
- 65, 130, 195, 260, 390, 520, 585, 650, 780, 0
- },
- { /* SGI */
- 72, 144, 217, 289, 433, 578, 650, 722, 867, 0
- }
- },
- { /* BW40 */
- { /* no SGI */
- 135, 270, 405, 540, 810, 1080, 1215, 1350, 1620, 1800
- },
- { /* SGI */
- 150, 300, 450, 600, 900, 1200, 1350, 1500, 1800, 2000
- }
- },
- { /* BW80 */
- { /* no SGI */
- 293, 585, 878, 1170, 1755, 2340, 2633, 2925, 3510, 3900
- },
- { /* SGI */
- 325, 650, 975, 1300, 1950, 2600, 2925, 3250, 3900, 4333
- }
- }
-};
-
struct slsi_mlme_rsse {
u8 group_cs_count;
const u8 *group_cs;
return NULL;
}
-#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 10, 9))
-u16 slsi_get_chann_info(struct slsi_dev *sdev, struct cfg80211_chan_def *chandef)
+u16 slsi_compute_chann_info(struct slsi_dev *sdev, u16 width, u16 center_freq0, u16 channel_freq)
{
u16 chann_info;
u16 prim_chan_pos = 0;
- SLSI_UNUSED_PARAMETER(sdev);
-
- switch (chandef->width) {
+ SLSI_DBG3(sdev, SLSI_MLME, "compute channel info\n");
+ switch (width) {
case NL80211_CHAN_WIDTH_20:
- case NL80211_CHAN_WIDTH_20_NOHT:
chann_info = 20;
break;
case NL80211_CHAN_WIDTH_40:
chann_info = 40;
/* Check HT Minus */
- if (chandef->chan && chandef->center_freq1 < chandef->chan->center_freq)
+ if (center_freq0 < channel_freq)
chann_info |= SLSI_CHANN_INFO_HT_SCB;
break;
case NL80211_CHAN_WIDTH_80:
/* F = { F1-30, ... F1+30 } => { 0x0000, ... 0x0300} */
- prim_chan_pos = ((30 + chandef->chan->center_freq - chandef->center_freq1) / 20);
+ prim_chan_pos = ((30 + channel_freq - center_freq0) / 20);
if (prim_chan_pos > 3) {
- SLSI_ERR(sdev, "Invalid center_freq1 in chandef : %u, primary channel = %u, primary chan pos calculated = %d\n", chandef->center_freq1, chandef->chan->center_freq, prim_chan_pos);
+ SLSI_ERR(sdev, "Invalid center_freq0 in chandef : %u, primary channel = %u,"
+ "primary chan pos calculated = %d\n", center_freq0, channel_freq, prim_chan_pos);
prim_chan_pos = 0;
}
prim_chan_pos = 0xFFFF & (prim_chan_pos << 8);
chann_info = 80 | prim_chan_pos;
break;
default:
- SLSI_WARN(sdev, "Invalid chandef.width(0x%x)\n", chandef->width);
+ SLSI_WARN(sdev, "Invalid chandef.width(0x%x)\n", width);
chann_info = 0;
break;
}
- SLSI_DBG3(sdev, SLSI_MLME, "channel_width:%u, chann_info:0x%x\n", chandef->width, chann_info);
+ SLSI_DBG3(sdev, SLSI_MLME, "channel_width:%u, chann_info:0x%x\n", width, chann_info);
return chann_info;
}
-int slsi_check_channelization(struct slsi_dev *sdev, struct cfg80211_chan_def *chandef)
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 10, 9))
+u16 slsi_get_chann_info(struct slsi_dev *sdev, struct cfg80211_chan_def *chandef)
+{
+ u16 chann_info = 0;
+
+ SLSI_UNUSED_PARAMETER(sdev);
+
+ if (chandef->width == NL80211_CHAN_WIDTH_20 || chandef->width == NL80211_CHAN_WIDTH_20_NOHT) {
+ chann_info = 20;
+ SLSI_DBG3(sdev, SLSI_MLME, "channel_width:%u, chann_info:0x%x\n", chandef->width, chann_info);
+ } else if (chandef->chan) {
+ chann_info = slsi_compute_chann_info(sdev, chandef->width, chandef->center_freq1,
+ chandef->chan->center_freq);
+ }
+ return chann_info;
+}
+
+int slsi_check_channelization(struct slsi_dev *sdev, struct cfg80211_chan_def *chandef,
+ int wifi_sharing_channel_switched)
{
u8 width;
struct ieee80211_reg_rule *rule = NULL;
struct ieee80211_channel *channel = NULL;
+ u32 ref_flags;
switch (chandef->width) {
case NL80211_CHAN_WIDTH_20:
if (!channel) {
SLSI_ERR(sdev, "Invalid channel %d used to start AP. Channel not found\n", chandef->chan->center_freq);
return -EINVAL;
- } else if (channel->flags & (IEEE80211_CHAN_DISABLED |
- IEEE80211_CHAN_RADAR
+ }
+
+ if (wifi_sharing_channel_switched == 1) {
+ ref_flags = IEEE80211_CHAN_DISABLED
#if LINUX_VERSION_CODE <= KERNEL_VERSION(3, 10, 13)
- | IEEE80211_CHAN_PASSIVE_SCAN
+ | IEEE80211_CHAN_PASSIVE_SCAN
#endif
- )) {
+ ;
+ } else {
+ ref_flags = IEEE80211_CHAN_DISABLED |
+ IEEE80211_CHAN_RADAR
+#if LINUX_VERSION_CODE <= KERNEL_VERSION(3, 10, 13)
+ | IEEE80211_CHAN_PASSIVE_SCAN
+#endif
+ ;
+ }
+
+ if (channel->flags & ref_flags) {
SLSI_ERR(sdev, "Invalid channel %d used to start AP\n", chandef->chan->center_freq);
return -EINVAL;
}
-
rule = slsi_get_reg_rule(MHZ_TO_KHZ(chandef->center_freq1), &sdev->device_config.domain_info);
if (!rule) {
SLSI_ERR(sdev, "Invalid channel %d used to start AP. No reg rule found for this channel\n", chandef->chan->center_freq);
freq_fw_unit = cpu_to_le16(freq_fw_unit);
memcpy(p, &freq_fw_unit, sizeof(freq_fw_unit));
- if (passive_scan)
+ if (passive_scan && (scan_type != FAPI_SCANTYPE_AP_AUTO_CHANNEL_SELECTION))
p[2] = FAPI_SCANPOLICY_PASSIVE;
else
p[2] = 0;
u8 *p = NULL;
u8 i;
struct cfg80211_ssid *pssid = ssids;
-#ifdef CONFIG_SCSC_WLAN_ENABLE_MAC_OUI
+#ifdef CONFIG_SCSC_WLAN_ENABLE_MAC_RANDOMISATION
struct netdev_vif *netdev_vif = netdev_priv(dev);
struct slsi_dev *sdev = netdev_vif->sdev;
#endif
fapi_set_u16(req, u.mlme_add_scan_req.report_mode_bitmap, report_mode);
-#ifdef CONFIG_SCSC_WLAN_ENABLE_MAC_OUI
- if (scan_type == FAPI_SCANTYPE_GSCAN && sdev->scan_oui_active)
- fapi_set_memcpy(req, u.mlme_add_scan_req.device_address, sdev->scan_oui);
+#ifdef CONFIG_SCSC_WLAN_ENABLE_MAC_RANDOMISATION
+ if (sdev->scan_addr_set)
+ fapi_set_memcpy(req, u.mlme_add_scan_req.device_address, sdev->scan_mac_addr);
else
#endif
fapi_set_memcpy(req, u.mlme_add_scan_req.device_address, dev->dev_addr);
return -EINVAL;
WARN_ON(!SLSI_MUTEX_IS_LOCKED(ndev_vif->scan_mutex));
- SLSI_NET_DBG3(dev, SLSI_MLME, "id:0x%x, n_channels:%d, n_ssids:%d\n", (ndev_vif->ifnum << 8 | SLSI_SCAN_HW_ID),
- n_channels, n_ssids);
+ SLSI_INFO(sdev, "scan started for id:0x%x, n_channels:%d, n_ssids:%d, scan_type:%d\n",
+ (ndev_vif->ifnum << 8 | SLSI_SCAN_HW_ID), n_channels, n_ssids, scan_type);
alloc_data_size += sizeof(scan_timing_ie) +
ies_len +
/* Calculate NSS --> bits 6 to 4*/
nss = ((SLSI_FW_API_RATE_VHT_NSS_FIELD & fw_rate) >> 4) + 1;
mcs_idx = SLSI_FW_API_RATE_VHT_MCS_FIELD & fw_rate;
-
/* Bandwidth (BW): 0x0= 20 MHz, 0x1= 40 MHz, 0x2= 80 MHz, 0x3= 160/ 80+80 MHz. 0x3 is not supported */
if ((chan_bw_idx <= 2) && (mcs_idx <= 9)) {
if (tx_rate)
static const struct slsi_mib_get_entry get_values[] = {
{ SLSI_PSID_UNIFI_TX_DATA_RATE, { 0, 0 } }, /* to get STATION_INFO_TX_BITRATE*/
{ SLSI_PSID_UNIFI_RSSI, { 0, 0 } }, /* to get STATION_INFO_SIGNAL_AVG*/
+ { SLSI_PSID_UNIFI_THROUGHPUT_DEBUG, { 2, 0 } },
+ { SLSI_PSID_UNIFI_THROUGHPUT_DEBUG, { 3, 0 } },
+ { SLSI_PSID_UNIFI_THROUGHPUT_DEBUG, { 4, 0 } },
+ { SLSI_PSID_UNIFI_THROUGHPUT_DEBUG, { 24, 0 } },
+ { SLSI_PSID_UNIFI_THROUGHPUT_DEBUG, { 29, 0 } },
};
+ int tx_counter = 0;
+ int rx_counter = 0;
WARN_ON(!SLSI_MUTEX_IS_LOCKED(ndev_vif->vif_mutex));
/* Fixed fields len (5) : 2 bytes(PSID) + 2 bytes (Len) + 1 byte (VLDATA header ) [10 for 2 PSIDs]
* Data : 3 bytes for SLSI_PSID_UNIFI_TX_DATA_RATE , 1 byte for SLSI_PSID_UNIFI_RSSI
+ * 10*5 bytes for 5 Throughput Mib's
*/
- mibrsp.dataLength = 14;
+ mibrsp.dataLength = 64;
mibrsp.data = kmalloc(mibrsp.dataLength, GFP_KERNEL);
if (!mibrsp.data) {
SLSI_DBG3(sdev, SLSI_MLME, "SLSI_PSID_UNIFI_RSSI = %d\n",
values[1].u.intValue);
}
+
+ if (values[2].type == SLSI_MIB_TYPE_UINT)
+ rx_counter += values[2].u.uintValue; /*bad_fcs_count*/
+ else
+ SLSI_ERR(sdev, "invalid type. iter:%d", 2);
+ if (values[3].type == SLSI_MIB_TYPE_UINT)
+ tx_counter += values[3].u.uintValue; /*missed_ba_count*/
+ else
+ SLSI_ERR(sdev, "invalid type. iter:%d", 3);
+ if (values[4].type == SLSI_MIB_TYPE_UINT)
+ tx_counter += values[4].u.uintValue; /*missed_ack_count*/
+ else
+ SLSI_ERR(sdev, "invalid type. iter:%d", 4);
+ if (values[5].type == SLSI_MIB_TYPE_UINT)
+ rx_counter += values[5].u.uintValue; /*mac_bad_sig_count*/
+ else
+ SLSI_ERR(sdev, "invalid type. iter:%d", 5);
+ if (values[6].type == SLSI_MIB_TYPE_UINT)
+ rx_counter += values[6].u.uintValue; /*rx_error_count*/
+ else
+ SLSI_ERR(sdev, "invalid type. iter:%d", 6);
+
+ peer->sinfo.tx_failed = tx_counter;
+ peer->sinfo.rx_dropped_misc = rx_counter;
} else {
SLSI_NET_DBG1(dev, SLSI_MLME, "mlme_get_req failed(result:%u)\n", r);
}
return r;
}
+int slsi_mlme_add_range_req(struct slsi_dev *sdev, u8 count,
+ struct slsi_rtt_config *nl_rtt_params, u16 rtt_id, u16 vif_idx)
+{
+ struct sk_buff *req;
+ struct sk_buff *rx;
+ int r = 0, i;
+ size_t alloc_data_size = 0;
+ u8 fapi_ie_generic[] = { 0xdd, 0x24, 0x00, 0x16, 0x32, 0x0a, 0x01 };
+ /* calculate data size */
+ alloc_data_size += count * (fapi_ie_generic[1] + 2);
+
+ req = fapi_alloc(mlme_add_range_req, MLME_ADD_RANGE_REQ, 0, alloc_data_size);
+ if (!req) {
+ SLSI_ERR(sdev, "failed to alloc %zd\n", alloc_data_size);
+ return -ENOMEM;
+ }
+ SLSI_DBG2(sdev, SLSI_MLME, "count-->%d allocated data size: %d\n", count, alloc_data_size);
+ /*fill the data */
+ fapi_set_u16(req, u.mlme_add_range_req.vif, vif_idx);
+ fapi_set_u16(req, u.mlme_add_range_req.rtt_id, rtt_id);
+ for (i = 0; i < count; i++) {
+ fapi_append_data(req, fapi_ie_generic, sizeof(fapi_ie_generic));
+ fapi_append_data(req, nl_rtt_params[i].source_addr, ETH_ALEN);
+ fapi_append_data(req, nl_rtt_params[i].peer_addr, ETH_ALEN);
+ fapi_append_data(req, (u8 *)&nl_rtt_params[i].type, 2);
+ fapi_append_data(req, (u8 *)&nl_rtt_params[i].channel_freq, 2);
+ fapi_append_data(req, (u8 *)&nl_rtt_params[i].channel_info, 2);
+ fapi_append_data(req, (u8 *)&nl_rtt_params[i].burst_period, 1);
+ fapi_append_data(req, (u8 *)&nl_rtt_params[i].num_burst, 1);
+ fapi_append_data(req, (u8 *)&nl_rtt_params[i].num_frames_per_burst, 1);
+ fapi_append_data(req, (u8 *)&nl_rtt_params[i].num_retries_per_ftmr, 1);
+ fapi_append_data(req, (u8 *)&nl_rtt_params[i].burst_duration, 1);
+ fapi_append_data(req, (u8 *)&nl_rtt_params[i].preamble, 2);
+ fapi_append_data(req, (u8 *)&nl_rtt_params[i].bw, 2);
+ fapi_append_data(req, (u8 *)&nl_rtt_params[i].LCI_request, 2);
+ fapi_append_data(req, (u8 *)&nl_rtt_params[i].LCR_request, 2);
+ }
+ rx = slsi_mlme_req_cfm(sdev, NULL, req, MLME_ADD_RANGE_CFM);
+ SLSI_DBG2(sdev, SLSI_MLME, "(After mlme req cfm for rtt config)\n");
+ if (!rx)
+ return -EIO;
+ if (fapi_get_u16(rx, u.mlme_add_range_cfm.result_code) != FAPI_RESULTCODE_SUCCESS) {
+ SLSI_ERR(sdev, "mlme_add_range_cfm(ERROR:%x)",
+ fapi_get_u16(rx, u.mlme_add_range_cfm.result_code));
+ r = -EINVAL;
+ }
+
+ slsi_kfree_skb(rx);
+ return r;
+}
+
+bool slsi_del_range_cfm_validate(struct slsi_dev *sdev, struct net_device *dev, struct sk_buff *cfm)
+{
+ int result = fapi_get_u16(cfm, u.mlme_del_range_cfm.result_code);
+ bool r = false;
+
+ SLSI_UNUSED_PARAMETER(sdev);
+
+ if (WARN_ON(!dev))
+ goto exit;
+
+ if (result == FAPI_RESULTCODE_SUCCESS)
+ r = true;
+ else
+ SLSI_NET_ERR(dev, "mlme_del_range_cfm(result:%u) ERROR\n", result);
+
+exit:
+ slsi_kfree_skb(cfm);
+ return r;
+}
+
+int slsi_mlme_del_range_req(struct slsi_dev *sdev, struct net_device *dev, u16 count,
+ u8 *addr, u16 rtt_id)
+{
+ struct sk_buff *req;
+ struct sk_buff *rx;
+ u16 *rtt_vif_idx = sdev->rtt_vif;
+ int r = 0, i;
+ size_t alloc_data_size = 0;
+
+ /* calculate data size-->2 bytes for vif */
+ alloc_data_size += count * sizeof(ETH_ALEN);
+ /* Alloc data size */
+ req = fapi_alloc(mlme_del_range_req, MLME_DEL_RANGE_REQ, 0, alloc_data_size);
+ if (!req) {
+ SLSI_ERR(sdev, "failed to alloc %zd\n", alloc_data_size);
+ return -ENOMEM;
+ }
+ /*fill the data */
+ fapi_set_u16(req, u.mlme_del_range_req.vif, rtt_vif_idx[rtt_id]);
+ fapi_set_u16(req, u.mlme_del_range_req.rtt_id, rtt_id);
+ fapi_set_u16(req, u.mlme_del_range_req.entries, count);
+ for (i = 0; i < count; i++)
+ fapi_append_data(req, &addr[i * ETH_ALEN], ETH_ALEN);
+
+ rx = slsi_mlme_req_cfm_ind(sdev, dev, req, MLME_DEL_RANGE_CFM, MLME_RANGE_IND, slsi_del_range_cfm_validate);
+ sdev->rtt_vif[rtt_id] = -1;
+ if (!rx) {
+ SLSI_NET_ERR(dev, "mlme_del_range_cfm() ERROR\n");
+ slsi_kfree_skb(rx);
+ return -EINVAL;
+ }
+ slsi_kfree_skb(rx);
+ return r;
+}
+
#define SLSI_FAPI_EPNO_NETWORK_MIN_SIZE (3)
int slsi_mlme_set_pno_list(struct slsi_dev *sdev, int count,
struct slsi_epno_param *epno_param, struct slsi_epno_hs2_param *epno_hs2_param)
slsi_kfree_skb(cfm);
return r;
}
+
+#ifdef CONFIG_SCSC_WLAN_DEBUG
+#define SLSI_TEST_CONFIG_MONITOR_MODE_DESCRIPTOR_SIZE (12)
+int slsi_test_sap_configure_monitor_mode(struct slsi_dev *sdev, struct net_device *dev, struct cfg80211_chan_def *chandef)
+{
+ struct netdev_vif *ndev_vif = netdev_priv(dev);
+ struct sk_buff *req;
+ struct sk_buff *cfm;
+ u8 *p = NULL;
+ size_t alloc_data_size = 0;
+ u16 center_freq1;
+ u16 center_freq2;
+ u16 chan_info;
+ int r = 0;
+
+ const u8 monitor_config_ie_header[] = {
+ 0xDD, /* Element ID: Vendor Specific */
+ 0x11, /* Length */
+ 0x00, 0x16, 0x32, /* OUI: Samsung Electronics Co. */
+ 0x10, /* OUI Type: Monitor mode parameters */
+ 0x01 /* OUI Subtype: configuration */
+ };
+
+ if (slsi_is_test_mode_enabled()) {
+ SLSI_NET_WARN(dev, "WlanLite: NOT supported\n");
+ return -EOPNOTSUPP;
+ }
+
+ WARN_ON(!SLSI_MUTEX_IS_LOCKED(ndev_vif->vif_mutex));
+
+ chan_info = slsi_get_chann_info(sdev, chandef);
+ SLSI_NET_DBG2(dev, SLSI_MLME, "test_configure_monitor_mode_req(center_freq1:%u, chan_info:%u, center_freq2:%u)\n",
+ chandef->center_freq1,
+ chan_info,
+ chandef->center_freq2);
+
+ center_freq1 = SLSI_FREQ_HOST_TO_FW(chandef->center_freq1);
+ center_freq1 = cpu_to_le16(center_freq1);
+ center_freq2 = SLSI_FREQ_HOST_TO_FW(chandef->center_freq2);
+ center_freq2 = cpu_to_le16(center_freq2);
+
+ alloc_data_size = sizeof(monitor_config_ie_header) + SLSI_TEST_CONFIG_MONITOR_MODE_DESCRIPTOR_SIZE;
+
+ req = fapi_alloc(test_configure_monitor_mode_req, TEST_CONFIGURE_MONITOR_MODE_REQ, ndev_vif->ifnum, alloc_data_size);
+ if (!req) {
+ SLSI_NET_ERR(dev, "failed to alloc Monitor mode request (len:%d)\n", alloc_data_size);
+ return -ENOMEM;
+ }
+
+ fapi_append_data(req, monitor_config_ie_header, sizeof(monitor_config_ie_header));
+ fapi_append_data(req, (const u8 *)¢er_freq1, 2);
+ fapi_append_data(req, (const u8 *)&chan_info, 2);
+ p = fapi_append_data(req, (const u8 *)¢er_freq2, 2);
+
+ /* MAC address filtering is not supported yet; so fill in zeros */
+ memset(p, 0, 6);
+
+ cfm = slsi_mlme_req_cfm(sdev, dev, req, TEST_CONFIGURE_MONITOR_MODE_CFM);
+ if (!cfm) {
+ SLSI_NET_ERR(dev, "failed to receive Confirm\n");
+ return -EIO;
+ }
+
+ if (fapi_get_u16(cfm, u.mlme_set_channel_cfm.result_code) != FAPI_RESULTCODE_SUCCESS) {
+ SLSI_NET_ERR(dev, "test_configure_monitor_mode_cfm(result:%u) ERROR\n", fapi_get_u16(cfm, u.test_configure_monitor_mode_cfm.result_code));
+ r = -EINVAL;
+ }
+
+ slsi_kfree_skb(cfm);
+ return r;
+}
+
+#endif
/****************************************************************************
*
- * Copyright (c) 2012 - 2017 Samsung Electronics Co., Ltd. All rights reserved
+ * Copyright (c) 2012 - 2018 Samsung Electronics Co., Ltd. All rights reserved
*
****************************************************************************/
#define SLSI_ACTION_FRAME_WMM (1 << 17)
#define SLSI_ACTION_FRAME_WNM (1 << 10)
#define SLSI_ACTION_FRAME_QOS (1 << 1)
+#define SLSI_ACTION_FRAME_PROTECTED_DUAL BIT(9)
+#define SLSI_ACTION_FRAME_RADIO_MEASUREMENT BIT(5)
/* Firmware transmit rates */
#define SLSI_TX_RATE_NON_HT_1MBPS 0x4001
#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 10, 9))
u16 slsi_get_chann_info(struct slsi_dev *sdev, struct cfg80211_chan_def *chandef);
-int slsi_check_channelization(struct slsi_dev *sdev, struct cfg80211_chan_def *chandef);
+int slsi_check_channelization(struct slsi_dev *sdev, struct cfg80211_chan_def *chandef,
+ int wifi_sharing_channel_switched);
#else
u16 slsi_get_chann_info(struct slsi_dev *sdev, enum nl80211_channel_type channel_type);
int slsi_check_channelization(struct slsi_dev *sdev, enum nl80211_channel_type channel_type);
int slsi_mlme_spare_signal_1(struct slsi_dev *sdev, struct net_device *dev);
+u16 slsi_compute_chann_info(struct slsi_dev *sdev, u16 width, u16 center_freq0, u16 channel_freq);
/**
* slsi_mlme_add_autonomous_scan() Returns:
* 0 : Scan installed
int slsi_mlme_set_p2p_noa(struct slsi_dev *sdev, struct net_device *dev, unsigned int noa_count,
unsigned int interval, unsigned int duration);
void slsi_fw_tx_rate_calc(u16 fw_rate, struct rate_info *tx_rate, unsigned long *data_rate_mbps);
+int slsi_test_sap_configure_monitor_mode(struct slsi_dev *sdev, struct net_device *dev, struct cfg80211_chan_def *chandef);
+
#endif /*__SLSI_MLME_H__*/
#include <linux/rtnetlink.h>
#include <net/sch_generic.h>
#include <linux/if_ether.h>
+#include <scsc/scsc_logring.h>
#include "debug.h"
#include "netif.h"
module_param(tcp_ack_suppression_rcv_window, uint, S_IRUGO | S_IWUSR);
MODULE_PARM_DESC(tcp_ack_suppression_rcv_window, "Receive window size (in unit of Kbytes) that triggers Ack suppression");
+#if KERNEL_VERSION(4, 15, 0) <= LINUX_VERSION_CODE
+static void slsi_netif_tcp_ack_suppression_timeout(struct timer_list *t);
+#else
static void slsi_netif_tcp_ack_suppression_timeout(unsigned long data);
+#endif
static int slsi_netif_tcp_ack_suppression_start(struct net_device *dev);
static int slsi_netif_tcp_ack_suppression_stop(struct net_device *dev);
static struct sk_buff *slsi_netif_tcp_ack_suppression_pkt(struct net_device *dev, struct sk_buff *skb);
if (!skb_mac_header_was_set(skb))
skb_reset_mac_header(skb);
+ if (is_zero_ether_addr(ehdr->h_dest) || is_zero_ether_addr(ehdr->h_source)) {
+ SLSI_NET_WARN(dev, "invalid Ethernet addresses (dest:%pM,src:%pM)\n", ehdr->h_dest, ehdr->h_source);
+ SCSC_BIN_TAG_INFO(BINARY, skb->data, skb->len > 128 ? 128 : skb->len);
+ return SLSI_NETIF_Q_DISCARD;
+ }
+
proto = be16_to_cpu(eth_hdr(skb)->h_proto);
switch (proto) {
#endif
#ifdef CONFIG_SCSC_WLAN_RX_NAPI_GRO
- SLSI_NET_DBG1(dev, SLSI_RX, "napi rx gro enabled\n");
+ SLSI_NET_DBG1(dev, SLSI_RX, "NAPI Rx GRO enabled\n");
features |= NETIF_F_GRO;
#else
- SLSI_NET_DBG1(dev, SLSI_RX, "napi rx gro enabled\n");
+ SLSI_NET_DBG1(dev, SLSI_RX, "NAPI Rx GRO disabled\n");
features &= ~NETIF_F_GRO;
#endif
return features;
}
-#ifdef CONFIG_SCSC_WLAN_RX_NAPI
-int slsi_net_rx_poll(struct napi_struct *napi, int budget)
-{
- struct netdev_vif *ndev_vif = netdev_priv(napi->dev);
- struct sk_buff *skb = slsi_skb_dequeue(&ndev_vif->napi.rx_data);
- int npackets = 0;
-
- while (skb) {
- npackets++;
- slsi_dbg_untrack_skb(skb);
-#ifdef CONFIG_SCSC_WLAN_RX_NAPI_GRO
- napi_gro_receive(napi, skb);
-#else
- netif_receive_skb(skb);
-#endif
- if (npackets == budget)
- break;
- skb = slsi_skb_dequeue(&ndev_vif->napi.rx_data);
- }
-
- if (npackets < budget) {
- ndev_vif->napi.interrupt_enabled = true;
- napi_complete(napi);
- }
-
- return npackets;
-}
-#endif
-
static void slsi_set_multicast_list(struct net_device *dev)
{
struct netdev_vif *ndev_vif = netdev_priv(dev);
#if (LINUX_VERSION_CODE >= KERNEL_VERSION(4, 11, 9))
dev->needs_free_netdev = true;
#else
- dev->destructor = free_netdev;
-#endif
+ dev->destructor = free_netdev;
+#endif
}
int slsi_netif_add_locked(struct slsi_dev *sdev, const char *name, int ifnum)
/* For HS2 interface */
if (SLSI_IS_VIF_INDEX_WLAN(ndev_vif))
- sdev->hs2_state = HS2_NO_VIF;
+ sdev->wlan_unsync_vif_state = WLAN_UNSYNC_NO_VIF;
/* For p2p0 interface */
else if (SLSI_IS_VIF_INDEX_P2P(ndev_vif)) {
INIT_DELAYED_WORK(&ndev_vif->scan_timeout_work, slsi_scan_ind_timeout_handle);
+#ifndef CONFIG_SCSC_WLAN_RX_NAPI
ret = slsi_skb_work_init(sdev, dev, &ndev_vif->rx_data, "slsi_wlan_rx_data", slsi_rx_netdev_data_work);
if (ret)
goto exit_with_error;
-
+#endif
ret = slsi_skb_work_init(sdev, dev, &ndev_vif->rx_mlme, "slsi_wlan_rx_mlme", slsi_rx_netdev_mlme_work);
if (ret) {
+#ifndef CONFIG_SCSC_WLAN_RX_NAPI
slsi_skb_work_deinit(&ndev_vif->rx_data);
+#endif
goto exit_with_error;
}
#endif
SLSI_DBG1(sdev, SLSI_NETDEV, "Add:%pM\n", dev->dev_addr);
rcu_assign_pointer(sdev->netdev[ifnum], dev);
-
-#ifdef CONFIG_SCSC_WLAN_RX_NAPI
- SLSI_NET_DBG1(dev, SLSI_RX, "napi rx enabled\n");
- skb_queue_head_init(&ndev_vif->napi.rx_data);
- slsi_spinlock_create(&ndev_vif->napi.lock);
- ndev_vif->napi.interrupt_enabled = true;
- /* TODO_HARDMAC: What weight should we use? 32 is just a Guess */
- netif_napi_add(dev, &ndev_vif->napi.napi, slsi_net_rx_poll, 32);
- napi_enable(&ndev_vif->napi.napi);
-#endif
ndev_vif->delete_probe_req_ies = false;
ndev_vif->probe_req_ies = NULL;
ndev_vif->probe_req_ie_len = 0;
return 0;
exit_with_error:
+ SLSI_MUTEX_LOCK(sdev->netdev_remove_mutex);
free_netdev(dev);
+ SLSI_MUTEX_UNLOCK(sdev->netdev_remove_mutex);
return ret;
}
if (SLSI_IS_VIF_INDEX_P2P(ndev_vif)) {
slsi_p2p_deinit(sdev, ndev_vif);
} else if (SLSI_IS_VIF_INDEX_WLAN(ndev_vif)) {
- sdev->hs2_state = HS2_NO_VIF;
+ sdev->wlan_unsync_vif_state = WLAN_UNSYNC_NO_VIF;
ndev_vif->vif_type = SLSI_VIFTYPE_UNSPECIFIED;
}
cancel_delayed_work(&ndev_vif->scan_timeout_work);
ndev_vif->scan[SLSI_SCAN_HW_ID].requeue_timeout_work = false;
+#ifndef CONFIG_SCSC_WLAN_RX_NAPI
slsi_skb_work_deinit(&ndev_vif->rx_data);
+#endif
slsi_skb_work_deinit(&ndev_vif->rx_mlme);
for (i = 0; i < SLSI_SCAN_MAX; i++)
slsi_purge_scan_results(ndev_vif, i);
slsi_kfree_skb(ndev_vif->sta.mlme_scan_ind_skb);
slsi_roam_channel_cache_prune(dev, 0);
-
-#ifdef CONFIG_SCSC_WLAN_RX_NAPI
- slsi_skb_queue_purge(&ndev_vif->napi.rx_data);
-#endif
kfree(ndev_vif->probe_req_ies);
if (atomic_read(&ndev_vif->is_registered)) {
atomic_set(&ndev_vif->is_registered, 0);
unregister_netdevice(dev);
} else {
+ SLSI_MUTEX_LOCK(sdev->netdev_remove_mutex);
free_netdev(dev);
+ SLSI_MUTEX_UNLOCK(sdev->netdev_remove_mutex);
}
}
tcp_ack->max = 0;
tcp_ack->age = 0;
skb_queue_head_init(&tcp_ack->list);
+#if KERNEL_VERSION(4, 15, 0) <= LINUX_VERSION_CODE
+ timer_setup(&tcp_ack->timer, slsi_netif_tcp_ack_suppression_timeout, 0);
+#else
tcp_ack->timer.function = slsi_netif_tcp_ack_suppression_timeout;
tcp_ack->timer.data = (unsigned long)tcp_ack;
init_timer(&tcp_ack->timer);
+#endif
tcp_ack->state = 1;
slsi_spinlock_create(&tcp_ack->lock);
}
return 0;
}
+#if KERNEL_VERSION(4, 15, 0) <= LINUX_VERSION_CODE
+static void slsi_netif_tcp_ack_suppression_timeout(struct timer_list *t)
+#else
static void slsi_netif_tcp_ack_suppression_timeout(unsigned long data)
+#endif
{
+#if KERNEL_VERSION(4, 15, 0) <= LINUX_VERSION_CODE
+ struct slsi_tcp_ack_s *tcp_ack = from_timer(tcp_ack, t, timer);
+#else
struct slsi_tcp_ack_s *tcp_ack = (struct slsi_tcp_ack_s *)data;
+#endif
struct sk_buff *skb;
struct netdev_vif *ndev_vif;
struct slsi_dev *sdev;
static int slsi_netif_tcp_ack_suppression_option(struct sk_buff *skb, u32 option)
{
unsigned char *options;
- u32 optlen, len;
+ u32 optlen = 0, len = 0;
+
+ if (tcp_hdr(skb)->doff > 5)
+ optlen = (tcp_hdr(skb)->doff - 5) * 4;
- optlen = tcp_optlen(skb);
options = ((u8 *)tcp_hdr(skb)) + TCP_ACK_SUPPRESSION_OPTIONS_OFFSET;
while (optlen > 0) {
len = options[1];
break;
}
- /* if length field in TCP options is 0, then options are bogus; return here */
- if (len == 0) {
+ /* if length field in TCP options is 0, or greater than
+ * total options length, then options are incorrect; return here
+ */
+ if ((len == 0) || (len > optlen)) {
SLSI_DBG_HEX_NODEV(SLSI_TX, skb->data, skb->len < 128 ? skb->len : 128, "SKB:\n");
return 0;
}
tcp_ack->saddr = 0;
tcp_ack->count = 0;
tcp_ack->ack_seq = 0;
- tcp_ack->tcp_sk = NULL;
del_timer(&tcp_ack->timer);
}
}
tcp_ack->num_bytes = 0;
tcp_ack->hysteresis = 0;
}
- tcp_ack->tcp_sk = skb->sk;
#ifdef CONFIG_SCSC_WLAN_HIP4_PROFILING
tcp_ack->stream_id = index;
#endif
#ifdef CONFIG_SCSC_WLAN_HIP4_PROFILING
tcp_ack->stream_id = 0;
#endif
- tcp_ack->tcp_sk = NULL;
SCSC_HIP4_SAMPLER_TCP_FIN(ndev_vif->sdev->minor_prof, index);
slsi_spinlock_unlock(&tcp_ack->lock);
return;
return skb;
}
if ((tcp_ack->dport == tcp_hdr(skb)->dest) &&
+ (tcp_ack->sport == tcp_hdr(skb)->source) &&
(tcp_ack->daddr == ip_hdr(skb)->daddr)) {
found = 1;
ndev_vif->tcp_ack_stats.tack_lastrecord++;
return skb;
}
if ((tcp_ack->dport == tcp_hdr(skb)->dest) &&
+ (tcp_ack->sport == tcp_hdr(skb)->source) &&
(tcp_ack->daddr == ip_hdr(skb)->daddr)) {
found = 1;
ndev_vif->tcp_ack_stats.tack_searchrecord++;
/* Has data, forward straight away. */
if (be16_to_cpu(ip_hdr(skb)->tot_len) > ((ip_hdr(skb)->ihl * 4) + (tcp_hdr(skb)->doff * 4))) {
SCSC_HIP4_SAMPLER_TCP_DATA(ndev_vif->sdev->minor_prof, tcp_ack->stream_id, be32_to_cpu(tcp_hdr(skb)->seq));
- SCSC_HIP4_SAMPLER_TCP_CWND(ndev_vif->sdev->minor_prof, tcp_ack->stream_id, tcp_ack->tcp_sk ? tcp_sk(tcp_ack->tcp_sk)->snd_cwnd : 0);
+ SCSC_HIP4_SAMPLER_TCP_CWND(ndev_vif->sdev->minor_prof, tcp_ack->stream_id, (skb->sk) ? tcp_sk(skb->sk)->snd_cwnd : 0);
SCSC_HIP4_SAMPLER_TCP_SEND_BUF(ndev_vif->sdev->minor_prof, tcp_ack->stream_id, sysctl_tcp_wmem[2]);
ndev_vif->tcp_ack_stats.tack_hasdata++;
forward_now = 1;
return "SLSI_NL80211_NAN_FOLLOWUP_EVENT";
case SLSI_NL80211_NAN_DISCOVERY_ENGINE_EVENT:
return "SLSI_NL80211_NAN_DISCOVERY_ENGINE_EVENT";
+ case SLSI_NL80211_RTT_RESULT_EVENT:
+ return "SLSI_NL80211_RTT_RESULT_EVENT";
+ case SLSI_NL80211_RTT_COMPLETE_EVENT:
+ return "SLSI_NL80211_RTT_COMPLETE_EVENT";
default:
return "UNKNOWN_EVENT";
}
int ret = 0;
struct slsi_dev *sdev = SDEV_FROM_WIPHY(wiphy);
- SLSI_DBG1_NODEV(SLSI_GSCAN, "SUBCMD_GET_CAPABILITIES\n");
+ SLSI_DBG1_NODEV(SLSI_GSCAN, "SUBCMD_GET_GSCAN_CAPABILITIES\n");
memset(&nl_cap, 0, sizeof(struct slsi_nl_gscan_capabilities));
}
skb_reset_mac_header(skb);
+ skb_set_network_header(skb, sizeof(struct ethhdr));
/* Ethernet Header */
ehdr = (struct ethhdr *)skb_put(skb, sizeof(struct ethhdr));
{
int ret = 0;
-#ifdef CONFIG_SCSC_WLAN_ENABLE_MAC_OUI
+#ifdef CONFIG_SCSC_WLAN_ENABLE_MAC_RANDOMISATION
struct slsi_dev *sdev = SDEV_FROM_WIPHY(wiphy);
struct net_device *dev = wdev->netdev;
struct netdev_vif *ndev_vif;
- struct slsi_mib_data mib_data = { 0, NULL };
int temp;
int type;
const struct nlattr *attr;
ndev_vif = netdev_priv(dev);
SLSI_MUTEX_LOCK(ndev_vif->scan_mutex);
- sdev->scan_oui_active = 0;
+ sdev->scan_addr_set = 0;
nla_for_each_attr(attr, data, len, temp) {
type = nla_type(attr);
}
}
- ret = slsi_mib_encode_bool(&mib_data, SLSI_PSID_UNIFI_MAC_ADDRESS_RANDOMISATION, 1, 0);
- if (ret != SLSI_MIB_STATUS_SUCCESS) {
- SLSI_ERR(sdev, "GSCAN set_out Fail: no mem for MIB\n");
- ret = -ENOMEM;
- goto exit;
- }
+ memcpy(sdev->scan_mac_addr, scan_oui, 6);
+ sdev->scan_addr_set = 1;
- ret = slsi_mlme_set(sdev, NULL, mib_data.data, mib_data.dataLength);
-
- kfree(mib_data.data);
-
- if (ret) {
- SLSI_ERR(sdev, "Err setting unifiMacAddrRandomistaion MIB. error = %d\n", ret);
- goto exit;
- }
-
- memcpy(sdev->scan_oui, scan_oui, 6);
- sdev->scan_oui_active = 1;
-
-exit:
SLSI_MUTEX_UNLOCK(ndev_vif->scan_mutex);
#endif
return ret;
SLSI_DBG3_NODEV(SLSI_GSCAN, "\n");
feature_set |= SLSI_WIFI_HAL_FEATURE_RSSI_MONITOR;
+ feature_set |= SLSI_WIFI_HAL_FEATURE_CONTROL_ROAMING;
#ifndef CONFIG_SCSC_WLAN_NAT_KEEPALIVE_DISABLE
feature_set |= SLSI_WIFI_HAL_FEATURE_MKEEP_ALIVE;
#endif
feature_set |= SLSI_WIFI_HAL_FEATURE_HAL_EPNO;
if (slsi_dev_nan_supported(SDEV_FROM_WIPHY(wiphy)))
feature_set |= SLSI_WIFI_HAL_FEATURE_NAN;
+ if (slsi_dev_rtt_supported()) {
+ feature_set |= SLSI_WIFI_HAL_FEATURE_D2D_RTT;
+ feature_set |= SLSI_WIFI_HAL_FEATURE_D2AP_RTT;
+ }
ret = slsi_vendor_cmd_reply(wiphy, &feature_set, sizeof(feature_set));
return ret;
}
+static int slsi_rtt_get_capabilities(struct wiphy *wiphy, struct wireless_dev *wdev, const void *data, int len)
+{
+ struct slsi_rtt_capabilities rtt_cap;
+ int ret = 0;
+ struct slsi_dev *sdev = SDEV_FROM_WIPHY(wiphy);
+ struct net_device *dev = wdev->netdev;
+
+ SLSI_DBG1_NODEV(SLSI_GSCAN, "SUBCMD_GET_RTT_CAPABILITIES\n");
+ if (!slsi_dev_rtt_supported()) {
+ SLSI_WARN(sdev, "RTT not supported.\n");
+ return -ENOTSUPP;
+ }
+ memset(&rtt_cap, 0, sizeof(struct slsi_rtt_capabilities));
+
+ ret = slsi_mib_get_rtt_cap(sdev, dev, &rtt_cap);
+ if (ret != 0) {
+ SLSI_ERR(sdev, "Failed to read mib\n");
+ return ret;
+ }
+ ret = slsi_vendor_cmd_reply(wiphy, &rtt_cap, sizeof(struct slsi_rtt_capabilities));
+ if (ret)
+ SLSI_ERR_NODEV("rtt_get_capabilities vendor cmd reply failed (err = %d)\n", ret);
+ return ret;
+}
+
+static int slsi_rtt_set_config(struct wiphy *wiphy, struct wireless_dev *wdev, const void *data, int len)
+{
+ int r, type, j = 0;
+ struct slsi_dev *sdev = SDEV_FROM_WIPHY(wiphy);
+ struct net_device *dev = slsi_nan_get_netdev(sdev);
+ struct netdev_vif *ndev_vif;
+ struct slsi_rtt_config *nl_rtt_params;
+ const struct nlattr *iter, *outer, *inner;
+ int tmp, tmp1, tmp2;
+ u16 rtt_id = 0;
+ u8 num_devices = 0;
+ u16 rtt_peer = SLSI_RTT_PEER_AP;
+ u16 vif_idx = 0;
+ u16 center_freq0 = 0, center_freq1 = 0, channel_freq = 0, width = 0;
+
+ SLSI_DBG1_NODEV(SLSI_GSCAN, "SUBCMD_RTT_RANGE_START\n");
+ if (!slsi_dev_rtt_supported()) {
+ SLSI_ERR(sdev, "RTT not supported.\n");
+ return WIFI_HAL_ERROR_NOT_SUPPORTED;
+ }
+ nla_for_each_attr(iter, data, len, tmp) {
+ type = nla_type(iter);
+ switch (type) {
+ case SLSI_RTT_ATTRIBUTE_TARGET_CNT:
+ num_devices = nla_get_u8(iter);
+ SLSI_DBG1_NODEV(SLSI_GSCAN, "Target cnt %d\n", num_devices);
+ break;
+ case SLSI_RTT_ATTRIBUTE_TARGET_ID:
+ rtt_id = nla_get_u16(iter);
+ SLSI_DBG1_NODEV(SLSI_GSCAN, "Target id %d\n", rtt_id);
+ break;
+ default:
+ SLSI_ERR_NODEV("Unexpected RTT attribute:type - %d\n", type);
+ break;
+ }
+ }
+ if (!num_devices) {
+ SLSI_ERR_NODEV("No device found for rtt configuration!\n");
+ return -EINVAL;
+ }
+ /* Allocate memory for the received config params */
+ nl_rtt_params = kcalloc(num_devices, sizeof(*nl_rtt_params), GFP_KERNEL);
+ if (!nl_rtt_params) {
+ SLSI_ERR_NODEV("Failed for allocate memory for config rtt_param\n");
+ return -ENOMEM;
+ }
+ nla_for_each_attr(iter, data, len, tmp) {
+ type = nla_type(iter);
+ switch (type) {
+ case SLSI_RTT_ATTRIBUTE_TARGET_INFO:
+ nla_for_each_nested(outer, iter, tmp1) {
+ nla_for_each_nested(inner, outer, tmp2) {
+ switch (nla_type(inner)) {
+ case SLSI_RTT_ATTRIBUTE_TARGET_MAC:
+ memcpy(nl_rtt_params[j].peer_addr, nla_data(inner), ETH_ALEN);
+ break;
+ case SLSI_RTT_ATTRIBUTE_TARGET_TYPE:
+ nl_rtt_params[j].type = nla_get_u16(inner);
+ break;
+ case SLSI_RTT_ATTRIBUTE_TARGET_PEER:
+ rtt_peer = nla_get_u16(inner);
+ break;
+ case SLSI_RTT_ATTRIBUTE_TARGET_CHAN_FREQ:
+ channel_freq = nla_get_u16(inner);
+ nl_rtt_params[j].channel_freq = channel_freq * 2;
+ break;
+ case SLSI_RTT_ATTRIBUTE_TARGET_CHAN_WIDTH:
+ width = nla_get_u16(inner);
+ break;
+ case SLSI_RTT_ATTRIBUTE_TARGET_CHAN_FREQ0:
+ center_freq0 = nla_get_u16(inner);
+ break;
+ case SLSI_RTT_ATTRIBUTE_TARGET_CHAN_FREQ1:
+ center_freq1 = nla_get_u16(inner);
+ break;
+ case SLSI_RTT_ATTRIBUTE_TARGET_PERIOD:
+ nl_rtt_params[j].burst_period = nla_get_u8(inner);
+ break;
+ case SLSI_RTT_ATTRIBUTE_TARGET_NUM_BURST:
+ nl_rtt_params[j].num_burst = nla_get_u8(inner);
+ break;
+ case SLSI_RTT_ATTRIBUTE_TARGET_NUM_FTM_BURST:
+ nl_rtt_params[j].num_frames_per_burst = nla_get_u8(inner);
+ break;
+ case SLSI_RTT_ATTRIBUTE_TARGET_NUM_RETRY_FTMR:
+ nl_rtt_params[j].num_retries_per_ftmr = nla_get_u8(inner);
+ break;
+ case SLSI_RTT_ATTRIBUTE_TARGET_BURST_DURATION:
+ nl_rtt_params[j].burst_duration = nla_get_u8(inner);
+ break;
+ case SLSI_RTT_ATTRIBUTE_TARGET_PREAMBLE:
+ nl_rtt_params[j].preamble = nla_get_u16(inner);
+ break;
+ case SLSI_RTT_ATTRIBUTE_TARGET_BW:
+ nl_rtt_params[j].bw = nla_get_u16(inner);
+ break;
+ case SLSI_RTT_ATTRIBUTE_TARGET_LCI:
+ nl_rtt_params[j].LCI_request = nla_get_u16(inner);
+ break;
+ case SLSI_RTT_ATTRIBUTE_TARGET_LCR:
+ nl_rtt_params[j].LCR_request = nla_get_u16(inner);
+ break;
+ default:
+ SLSI_ERR_NODEV("Unknown RTT INFO ATTRIBUTE type: %d\n", type);
+ break;
+ }
+ if (rtt_peer == SLSI_RTT_PEER_NAN) {
+#if CONFIG_SCSC_WLAN_MAX_INTERFACES >= 4
+ SLSI_ETHER_COPY(nl_rtt_params[j].source_addr,
+ sdev->netdev_addresses[SLSI_NET_INDEX_NAN]);
+#else
+ SLSI_ERR(sdev, "NAN not supported(mib:%d)\n", sdev->nan_enabled);
+#endif
+ } else {
+ SLSI_ETHER_COPY(nl_rtt_params[j].source_addr,
+ sdev->netdev_addresses[SLSI_NET_INDEX_WLAN]);
+ }
+ }
+ /* width+1:to match RTT width enum value with NL enums */
+ nl_rtt_params[j].channel_info = slsi_compute_chann_info(sdev, width + 1, center_freq0,
+ channel_freq);
+ j++;
+ }
+ break;
+ default:
+ SLSI_ERR_NODEV("No ATTRIBUTE_Target cnt - %d\n", type);
+ break;
+ }
+ }
+ if (rtt_peer == SLSI_RTT_PEER_AP) {
+ vif_idx = 0;
+ } else if (rtt_peer == SLSI_RTT_PEER_NAN) {
+ if (!slsi_dev_nan_supported(sdev)) {
+ SLSI_ERR(sdev, "NAN not supported(mib:%d)\n", sdev->nan_enabled);
+ kfree(nl_rtt_params);
+ return WIFI_HAL_ERROR_NOT_SUPPORTED;
+ }
+ ndev_vif = netdev_priv(dev);
+ if (ndev_vif->activated) {
+ vif_idx = ndev_vif->vif_type;
+ } else {
+ SLSI_ERR(sdev, "NAN vif not activated\n");
+ kfree(nl_rtt_params);
+ return -EINVAL;
+ }
+ }
+ r = slsi_mlme_add_range_req(sdev, num_devices, nl_rtt_params, rtt_id, vif_idx);
+ if (r) {
+ r = -EINVAL;
+ SLSI_ERR_NODEV("Failed to set rtt config\n");
+ } else {
+ sdev->rtt_vif[rtt_id] = vif_idx;
+ SLSI_DBG1_NODEV(SLSI_GSCAN, "Successfully set rtt config\n");
+ }
+ kfree(nl_rtt_params);
+ return r;
+}
+
+int slsi_tx_rate_calc(struct sk_buff *nl_skb, u16 fw_rate, int res, bool tx_rate)
+{
+ u8 preamble;
+ const u32 fw_rate_idx_to_80211_rate[] = { 0, 10, 20, 55, 60, 90, 110, 120, 180, 240, 360, 480, 540 };
+ u32 data_rate = 0;
+ u32 mcs = 0, nss = 0;
+ u32 chan_bw_idx = 0;
+ int gi_idx;
+
+ preamble = (fw_rate & SLSI_FW_API_RATE_HT_SELECTOR_FIELD) >> 14;
+ if ((fw_rate & SLSI_FW_API_RATE_HT_SELECTOR_FIELD) == SLSI_FW_API_RATE_NON_HT_SELECTED) {
+ u16 fw_rate_idx = fw_rate & SLSI_FW_API_RATE_INDEX_FIELD;
+
+ if (fw_rate > 0 && fw_rate_idx < ARRAY_SIZE(fw_rate_idx_to_80211_rate))
+ data_rate = fw_rate_idx_to_80211_rate[fw_rate_idx];
+ } else if ((fw_rate & SLSI_FW_API_RATE_HT_SELECTOR_FIELD) == SLSI_FW_API_RATE_HT_SELECTED) {
+ nss = (SLSI_FW_API_RATE_HT_NSS_FIELD & fw_rate) >> 6;
+ chan_bw_idx = (fw_rate & SLSI_FW_API_RATE_BW_FIELD) >> 9;
+ gi_idx = ((fw_rate & SLSI_FW_API_RATE_SGI) == SLSI_FW_API_RATE_SGI) ? 1 : 0;
+ mcs = SLSI_FW_API_RATE_HT_MCS_FIELD & fw_rate;
+ if ((chan_bw_idx < 2) && (mcs <= 7)) {
+ data_rate = (nss + 1) * slsi_rates_table[chan_bw_idx][gi_idx][mcs];
+ } else if (mcs == 32 && chan_bw_idx == 1) {
+ if (gi_idx == 1)
+ data_rate = (nss + 1) * 67;
+ else
+ data_rate = (nss + 1) * 60;
+ } else {
+ SLSI_WARN_NODEV("FW DATA RATE decode error fw_rate:%x, bw:%x, mcs_idx:%x, nss : %d\n",
+ fw_rate, chan_bw_idx, mcs, nss);
+ }
+ } else if ((fw_rate & SLSI_FW_API_RATE_HT_SELECTOR_FIELD) == SLSI_FW_API_RATE_VHT_SELECTED) {
+ /* report vht rate in legacy units and not as mcs index. reason: upper layers may still be not
+ * updated with vht msc table.
+ */
+ chan_bw_idx = (fw_rate & SLSI_FW_API_RATE_BW_FIELD) >> 9;
+ gi_idx = ((fw_rate & SLSI_FW_API_RATE_SGI) == SLSI_FW_API_RATE_SGI) ? 1 : 0;
+ /* Calculate NSS --> bits 6 to 4*/
+ nss = (SLSI_FW_API_RATE_VHT_NSS_FIELD & fw_rate) >> 4;
+ mcs = SLSI_FW_API_RATE_VHT_MCS_FIELD & fw_rate;
+ /* Bandwidth (BW): 0x0= 20 MHz, 0x1= 40 MHz, 0x2= 80 MHz, 0x3= 160/ 80+80 MHz. 0x3 is not supported */
+ if ((chan_bw_idx <= 2) && (mcs <= 9))
+ data_rate = (nss + 1) * slsi_rates_table[chan_bw_idx][gi_idx][mcs];
+ else
+ SLSI_WARN_NODEV("FW DATA RATE decode error fw_rate:%x, bw:%x, mcs_idx:%x,nss : %d\n",
+ fw_rate, chan_bw_idx, mcs, nss);
+ if (nss > 1)
+ nss += 1;
+ }
+
+ if (tx_rate) {
+ res |= nla_put_u32(nl_skb, SLSI_RTT_EVENT_ATTR_TX_PREAMBLE, preamble);
+ res |= nla_put_u32(nl_skb, SLSI_RTT_EVENT_ATTR_TX_NSS, nss);
+ res |= nla_put_u32(nl_skb, SLSI_RTT_EVENT_ATTR_TX_BW, chan_bw_idx);
+ res |= nla_put_u32(nl_skb, SLSI_RTT_EVENT_ATTR_TX_MCS, mcs);
+ res |= nla_put_u32(nl_skb, SLSI_RTT_EVENT_ATTR_TX_RATE, data_rate);
+ } else {
+ res |= nla_put_u32(nl_skb, SLSI_RTT_EVENT_ATTR_RX_PREAMBLE, preamble);
+ res |= nla_put_u32(nl_skb, SLSI_RTT_EVENT_ATTR_RX_NSS, nss);
+ res |= nla_put_u32(nl_skb, SLSI_RTT_EVENT_ATTR_RX_BW, chan_bw_idx);
+ res |= nla_put_u32(nl_skb, SLSI_RTT_EVENT_ATTR_RX_MCS, mcs);
+ res |= nla_put_u32(nl_skb, SLSI_RTT_EVENT_ATTR_RX_RATE, data_rate);
+ }
+ return res;
+}
+
+void slsi_rx_range_ind(struct slsi_dev *sdev, struct net_device *dev, struct sk_buff *skb)
+{
+ struct netdev_vif *ndev_vif = netdev_priv(dev);
+ u32 i, tm;
+ u16 rtt_entry_count = fapi_get_u16(skb, u.mlme_range_ind.entries);
+ u16 rtt_id = fapi_get_u16(skb, u.mlme_range_ind.rtt_id);
+ u32 tmac = fapi_get_u32(skb, u.mlme_range_ind.spare_3);
+ int data_len = fapi_get_datalen(skb);
+ u8 *ip_ptr, *start_ptr;
+ u16 tx_data, rx_data;
+ struct sk_buff *nl_skb;
+ int res = 0;
+ struct nlattr *nlattr_nested;
+ struct timespec ts;
+ u64 tkernel;
+ u8 rep_cnt = 0;
+
+ SLSI_MUTEX_LOCK(ndev_vif->vif_mutex);
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(4, 1, 0))
+ nl_skb = cfg80211_vendor_event_alloc(sdev->wiphy, NULL, NLMSG_DEFAULT_SIZE,
+ SLSI_NL80211_RTT_RESULT_EVENT, GFP_KERNEL);
+#else
+ nl_skb = cfg80211_vendor_event_alloc(sdev->wiphy, NLMSG_DEFAULT_SIZE, SLSI_NL80211_RTT_RESULT_EVENT,
+ GFP_KERNEL);
+#endif
+ SLSI_DBG1_NODEV(SLSI_GSCAN, "Event: %s(%d)\n",
+ slsi_print_event_name(SLSI_NL80211_RTT_RESULT_EVENT), SLSI_NL80211_RTT_RESULT_EVENT);
+
+ if (!nl_skb) {
+ SLSI_ERR(sdev, "NO MEM for nl_skb!!!\n");
+ goto exit;
+ }
+
+ ip_ptr = fapi_get_data(skb);
+ start_ptr = fapi_get_data(skb);
+ res |= nla_put_u16(nl_skb, SLSI_RTT_ATTRIBUTE_RESULT_CNT, rtt_entry_count);
+ res |= nla_put_u16(nl_skb, SLSI_RTT_ATTRIBUTE_TARGET_ID, rtt_id);
+ res |= nla_put_u8(nl_skb, SLSI_RTT_ATTRIBUTE_RESULTS_PER_TARGET, 1);
+ for (i = 0; i < rtt_entry_count; i++) {
+ nlattr_nested = nla_nest_start(nl_skb, SLSI_RTT_ATTRIBUTE_RESULT);
+ if (!nlattr_nested) {
+ SLSI_ERR(sdev, "Error in nla_nest_start\n");
+ /* Dont use slsi skb wrapper for this free */
+ kfree_skb(nl_skb);
+ goto exit;
+ }
+ ip_ptr += 7; /*skip first 7 bytes for fapi_ie_generic */
+ res |= nla_put(nl_skb, SLSI_RTT_EVENT_ATTR_ADDR, ETH_ALEN, ip_ptr);
+ ip_ptr += 6;
+ res |= nla_put_u8(nl_skb, SLSI_RTT_EVENT_ATTR_BURST_NUM, *ip_ptr++);
+ res |= nla_put_u8(nl_skb, SLSI_RTT_EVENT_ATTR_MEASUREMENT_NUM, *ip_ptr++);
+ res |= nla_put_u8(nl_skb, SLSI_RTT_EVENT_ATTR_SUCCESS_NUM, *ip_ptr++);
+ res |= nla_put_u8(nl_skb, SLSI_RTT_EVENT_ATTR_NUM_PER_BURST_PEER, *ip_ptr++);
+ res |= nla_put_u16(nl_skb, SLSI_RTT_EVENT_ATTR_STATUS, *ip_ptr);
+ ip_ptr += 2;
+ res |= nla_put_u8(nl_skb, SLSI_RTT_EVENT_ATTR_RETRY_AFTER_DURATION, *ip_ptr++);
+ res |= nla_put_u16(nl_skb, SLSI_RTT_EVENT_ATTR_TYPE, *ip_ptr);
+ ip_ptr += 2;
+ res |= nla_put_u16(nl_skb, SLSI_RTT_EVENT_ATTR_RSSI, *ip_ptr);
+ ip_ptr += 2;
+ res |= nla_put_u16(nl_skb, SLSI_RTT_EVENT_ATTR_RSSI_SPREAD, *ip_ptr);
+ ip_ptr += 2;
+ memcpy(&tx_data, ip_ptr, 2);
+ res = slsi_tx_rate_calc(nl_skb, tx_data, res, 1);
+ ip_ptr += 2;
+ memcpy(&rx_data, ip_ptr, 2);
+ res = slsi_tx_rate_calc(nl_skb, rx_data, res, 0);
+ ip_ptr += 2;
+ res |= nla_put_u32(nl_skb, SLSI_RTT_EVENT_ATTR_RTT, *ip_ptr);
+ ip_ptr += 4;
+ res |= nla_put_u16(nl_skb, SLSI_RTT_EVENT_ATTR_RTT_SD, *ip_ptr);
+ ip_ptr += 2;
+ res |= nla_put_u16(nl_skb, SLSI_RTT_EVENT_ATTR_RTT_SPREAD, *ip_ptr);
+ ip_ptr += 2;
+ get_monotonic_boottime(&ts);
+ tkernel = (u64)TIMESPEC_TO_US(ts);
+ tm = *ip_ptr;
+ res |= nla_put_u32(nl_skb, SLSI_RTT_EVENT_ATTR_TIMESTAMP_US, tkernel - (tmac - tm));
+ ip_ptr += 4;
+ res |= nla_put_u16(nl_skb, SLSI_RTT_EVENT_ATTR_BURST_DURATION_MSN, *ip_ptr);
+ ip_ptr += 2;
+ res |= nla_put_u8(nl_skb, SLSI_RTT_EVENT_ATTR_NEGOTIATED_BURST_NUM, *ip_ptr++);
+ for (rep_cnt = 0; rep_cnt < 2; rep_cnt++) {
+ if (ip_ptr - start_ptr < data_len && ip_ptr[0] == WLAN_EID_MEASURE_REPORT) {
+ if (ip_ptr[4] == 8) /*LCI Element*/
+ res |= nla_put(nl_skb, SLSI_RTT_EVENT_ATTR_LCI,
+ ip_ptr[1] + 2, ip_ptr);
+ else if (ip_ptr[4] == 11) /*LCR element */
+ res |= nla_put(nl_skb, SLSI_RTT_EVENT_ATTR_LCR,
+ ip_ptr[1] + 2, ip_ptr);
+ ip_ptr += ip_ptr[1] + 2;
+ }
+ }
+ nla_nest_end(nl_skb, nlattr_nested);
+ }
+ SLSI_DBG_HEX(sdev, SLSI_GSCAN, fapi_get_data(skb), fapi_get_datalen(skb), "range indication skb buffer:\n");
+ if (res) {
+ SLSI_ERR(sdev, "Error in nla_put*:%x\n", res);
+ kfree_skb(nl_skb);
+ goto exit;
+ }
+ cfg80211_vendor_event(nl_skb, GFP_KERNEL);
+exit:
+ slsi_kfree_skb(skb);
+ SLSI_MUTEX_UNLOCK(ndev_vif->vif_mutex);
+}
+
+void slsi_rx_range_done_ind(struct slsi_dev *sdev, struct net_device *dev, struct sk_buff *skb)
+{
+ struct netdev_vif *ndev_vif = netdev_priv(dev);
+ u16 rtt_id = fapi_get_u16(skb, u.mlme_range_ind.rtt_id);
+ SLSI_MUTEX_LOCK(ndev_vif->vif_mutex);
+ SLSI_DBG1_NODEV(SLSI_GSCAN, "Event: %s(%d)\n",
+ slsi_print_event_name(SLSI_NL80211_RTT_COMPLETE_EVENT), SLSI_NL80211_RTT_COMPLETE_EVENT);
+ slsi_vendor_event(sdev, SLSI_NL80211_RTT_COMPLETE_EVENT, &rtt_id, sizeof(rtt_id));
+ slsi_kfree_skb(skb);
+ SLSI_MUTEX_UNLOCK(ndev_vif->vif_mutex);
+}
+
+static int slsi_rtt_cancel_config(struct wiphy *wiphy, struct wireless_dev *wdev, const void *data, int len)
+{
+ int temp, ret, r = 1, j = 0, type;
+ struct slsi_dev *sdev = SDEV_FROM_WIPHY(wiphy);
+ struct net_device *dev = wdev->netdev;
+ u8 *addr;
+ const struct nlattr *iter;
+ u16 num_devices = 0, rtt_id = 0;
+
+ SLSI_DBG1_NODEV(SLSI_GSCAN, "RTT_SUBCMD_CANCEL_CONFIG\n");
+ if (!slsi_dev_rtt_supported()) {
+ SLSI_WARN(sdev, "RTT not supported.\n");
+ return -ENOTSUPP;
+ }
+ nla_for_each_attr(iter, data, len, temp) {
+ type = nla_type(iter);
+ switch (type) {
+ case SLSI_RTT_ATTRIBUTE_TARGET_CNT:
+ num_devices = nla_get_u16(iter);
+ SLSI_DBG1_NODEV(SLSI_GSCAN, "Target cnt %d\n", num_devices);
+ break;
+ case SLSI_RTT_ATTRIBUTE_TARGET_ID:
+ rtt_id = nla_get_u16(iter);
+ SLSI_DBG1_NODEV(SLSI_GSCAN, "Target id %d\n", rtt_id);
+ break;
+ default:
+ SLSI_ERR_NODEV("No ATTRIBUTE_Target cnt - %d\n", type);
+ break;
+ }
+ }
+ /* Allocate memory for the received mac addresses */
+ if (num_devices) {
+ addr = kzalloc(ETH_ALEN * num_devices, GFP_KERNEL);
+ if (!addr) {
+ SLSI_ERR_NODEV("Failed for allocate memory for mac addresses\n");
+ ret = -ENOMEM;
+ return ret;
+ }
+ nla_for_each_attr(iter, data, len, temp) {
+ type = nla_type(iter);
+ if (type == SLSI_RTT_ATTRIBUTE_TARGET_MAC) {
+ memcpy(&addr[j], nla_data(iter), ETH_ALEN);
+ j++;
+ } else {
+ SLSI_ERR_NODEV("No ATTRIBUTE_MAC - %d\n", type);
+ }
+ }
+
+ r = slsi_mlme_del_range_req(sdev, dev, num_devices, addr, rtt_id);
+ kfree(addr);
+ }
+ if (r)
+ SLSI_ERR_NODEV("Failed to cancel rtt config\n");
+ return r;
+}
+
static int slsi_nan_get_new_id(u32 id_map, int max_ids)
{
int i;
slsi_print_event_name(hal_event), hal_event);
#endif
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(4, 1, 0))
nl_skb = cfg80211_vendor_event_alloc(sdev->wiphy, NULL, NLMSG_DEFAULT_SIZE, hal_event, GFP_KERNEL);
+#else
+ nl_skb = cfg80211_vendor_event_alloc(sdev->wiphy, NLMSG_DEFAULT_SIZE, hal_event, GFP_KERNEL);
+#endif
if (!nl_skb) {
SLSI_ERR(sdev, "NO MEM for nl_skb!!!\n");
return;
u8 *fapi_data_p, *ptr;
u8 followup_ie_header[] = {0xdd, 0, 0, 0x16, 0x32, 0x0b, 0x05};
int fapi_data_len;
- struct slsi_hal_nan_followup_ind hal_evt;
+ struct slsi_hal_nan_followup_ind *hal_evt;
struct sk_buff *nl_skb;
int res;
struct nlattr *nlattr_start;
- hal_evt.publish_subscribe_id = fapi_get_u16(skb, u.mlme_nan_followup_ind.publish_subscribe_id);
- hal_evt.requestor_instance_id = fapi_get_u16(skb, u.mlme_nan_followup_ind.requestor_instance_id);
+ hal_evt = kmalloc(sizeof(*hal_evt), GFP_KERNEL);
+ if (!hal_evt) {
+ SLSI_ERR(sdev, "No memory for service_ind\n");
+ return;
+ }
+ hal_evt->publish_subscribe_id = fapi_get_u16(skb, u.mlme_nan_followup_ind.publish_subscribe_id);
+ hal_evt->requestor_instance_id = fapi_get_u16(skb, u.mlme_nan_followup_ind.requestor_instance_id);
fapi_data_p = fapi_get_data(skb);
fapi_data_len = fapi_get_datalen(skb);
if (!fapi_data_len) {
ptr += sizeof(followup_ie_header);
- ether_addr_copy(hal_evt.addr, ptr);
+ ether_addr_copy(hal_evt->addr, ptr);
ptr += ETH_ALEN;
ptr += 1; /* skip priority */
- hal_evt.dw_or_faw = *ptr;
+ hal_evt->dw_or_faw = *ptr;
ptr += 1;
while (fapi_data_p[1] + 2 > (ptr - fapi_data_p) + 4) {
tag_id = *(u16 *)ptr;
return;
}
if (tag_id == SLSI_FAPI_NAN_SERVICE_SPECIFIC_INFO) {
- hal_evt.service_specific_info_len = tag_len;
- memcpy(hal_evt.service_specific_info, ptr, tag_len);
+ hal_evt->service_specific_info_len = tag_len;
+ memcpy(hal_evt->service_specific_info, ptr, tag_len);
}
ptr += tag_len;
}
SLSI_DBG1_NODEV(SLSI_GSCAN, "Event: %s(%d)\n",
slsi_print_event_name(SLSI_NL80211_NAN_FOLLOWUP_EVENT), SLSI_NL80211_NAN_FOLLOWUP_EVENT);
#endif
-
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(4, 1, 0))
nl_skb = cfg80211_vendor_event_alloc(sdev->wiphy, NULL, NLMSG_DEFAULT_SIZE, SLSI_NL80211_NAN_FOLLOWUP_EVENT,
GFP_KERNEL);
+#else
+ nl_skb = cfg80211_vendor_event_alloc(sdev->wiphy, NLMSG_DEFAULT_SIZE, SLSI_NL80211_NAN_FOLLOWUP_EVENT,
+ GFP_KERNEL);
+#endif
+
if (!nl_skb) {
SLSI_ERR(sdev, "NO MEM for nl_skb!!!\n");
+ kfree(hal_evt);
return;
}
nlattr_start = nla_nest_start(nl_skb, NL80211_ATTR_VENDOR_DATA);
if (!nlattr_start) {
SLSI_ERR(sdev, "failed to put NL80211_ATTR_VENDOR_DATA\n");
+ kfree(hal_evt);
/* Dont use slsi skb wrapper for this free */
kfree_skb(nl_skb);
return;
}
res = nla_put_be16(nl_skb, NAN_EVT_ATTR_FOLLOWUP_PUBLISH_SUBSCRIBE_ID,
- cpu_to_le16(hal_evt.publish_subscribe_id));
+ cpu_to_le16(hal_evt->publish_subscribe_id));
res |= nla_put_be16(nl_skb, NAN_EVT_ATTR_FOLLOWUP_REQUESTOR_INSTANCE_ID,
- cpu_to_le16(hal_evt.requestor_instance_id));
- res |= nla_put(nl_skb, NAN_EVT_ATTR_FOLLOWUP_ADDR, ETH_ALEN, hal_evt.addr);
- res |= nla_put_u8(nl_skb, NAN_EVT_ATTR_FOLLOWUP_DW_OR_FAW, hal_evt.dw_or_faw);
- res |= nla_put_u16(nl_skb, NAN_EVT_ATTR_FOLLOWUP_SERVICE_SPECIFIC_INFO_LEN, hal_evt.service_specific_info_len);
- if (hal_evt.service_specific_info_len)
- res |= nla_put(nl_skb, NAN_EVT_ATTR_FOLLOWUP_SERVICE_SPECIFIC_INFO, hal_evt.service_specific_info_len,
- hal_evt.service_specific_info);
+ cpu_to_le16(hal_evt->requestor_instance_id));
+ res |= nla_put(nl_skb, NAN_EVT_ATTR_FOLLOWUP_ADDR, ETH_ALEN, hal_evt->addr);
+ res |= nla_put_u8(nl_skb, NAN_EVT_ATTR_FOLLOWUP_DW_OR_FAW, hal_evt->dw_or_faw);
+ res |= nla_put_u16(nl_skb, NAN_EVT_ATTR_FOLLOWUP_SERVICE_SPECIFIC_INFO_LEN, hal_evt->service_specific_info_len);
+ if (hal_evt->service_specific_info_len)
+ res |= nla_put(nl_skb, NAN_EVT_ATTR_FOLLOWUP_SERVICE_SPECIFIC_INFO, hal_evt->service_specific_info_len,
+ hal_evt->service_specific_info);
if (res) {
SLSI_ERR(sdev, "Error in nla_put*:%x\n", res);
+ kfree(hal_evt);
/* Dont use slsi skb wrapper for this free */
kfree_skb(nl_skb);
return;
nla_nest_end(nl_skb, nlattr_start);
cfg80211_vendor_event(nl_skb, GFP_KERNEL);
+ kfree(hal_evt);
}
void slsi_nan_service_ind(struct slsi_dev *sdev, struct net_device *dev, struct sk_buff *skb)
SLSI_DBG1_NODEV(SLSI_GSCAN, "Event: %s(%d)\n",
slsi_print_event_name(SLSI_NL80211_NAN_MATCH_EVENT), SLSI_NL80211_NAN_MATCH_EVENT);
#endif
-
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(4, 1, 0))
nl_skb = cfg80211_vendor_event_alloc(sdev->wiphy, NULL, NLMSG_DEFAULT_SIZE, SLSI_NL80211_NAN_MATCH_EVENT,
GFP_KERNEL);
+#else
+ nl_skb = cfg80211_vendor_event_alloc(sdev->wiphy, NLMSG_DEFAULT_SIZE, SLSI_NL80211_NAN_MATCH_EVENT, GFP_KERNEL);
+#endif
if (!nl_skb) {
SLSI_ERR(sdev, "NO MEM for nl_skb!!!\n");
kfree(hal_evt);
return ret;
}
+static int slsi_get_roaming_capabilities(struct wiphy *wiphy, struct wireless_dev *wdev, const void *data, int len)
+{
+ struct slsi_dev *sdev = SDEV_FROM_WIPHY(wiphy);
+ struct net_device *dev = wdev->netdev;
+ struct netdev_vif *ndev_vif;
+ int ret = 0;
+ struct slsi_mib_value *values = NULL;
+ struct slsi_mib_data mibrsp = { 0, NULL };
+ struct slsi_mib_get_entry get_values[] = {{ SLSI_PSID_UNIFI_ROAM_BLACKLIST_SIZE, { 0, 0 } } };
+ u32 max_blacklist_size = 0;
+ u32 max_whitelist_size = 0;
+ struct sk_buff *nl_skb;
+ struct nlattr *nlattr_start;
+
+ if (!dev) {
+ SLSI_ERR(sdev, "dev is NULL!!\n");
+ return -EINVAL;
+ }
+
+ ndev_vif = netdev_priv(dev);
+
+ SLSI_MUTEX_LOCK(ndev_vif->vif_mutex);
+
+ mibrsp.dataLength = 10;
+ mibrsp.data = kmalloc(mibrsp.dataLength, GFP_KERNEL);
+ if (!mibrsp.data) {
+ SLSI_ERR(sdev, "Cannot kmalloc %d bytes\n", mibrsp.dataLength);
+ ret = -ENOMEM;
+ goto exit;
+ }
+ values = slsi_read_mibs(sdev, NULL, get_values, ARRAY_SIZE(get_values), &mibrsp);
+ if (values && (values[0].type == SLSI_MIB_TYPE_UINT || values[0].type == SLSI_MIB_TYPE_INT))
+ max_blacklist_size = values[0].u.uintValue;
+ nl_skb = cfg80211_vendor_cmd_alloc_reply_skb(sdev->wiphy, NLMSG_DEFAULT_SIZE);
+ if (!nl_skb) {
+ SLSI_ERR(sdev, "NO MEM for nl_skb!!!\n");
+ ret = -ENOMEM;
+ goto exit_with_mib_resp;
+ }
+
+ nlattr_start = nla_nest_start(nl_skb, NL80211_ATTR_VENDOR_DATA);
+ if (!nlattr_start) {
+ SLSI_ERR(sdev, "failed to put NL80211_ATTR_VENDOR_DATA\n");
+ /* Dont use slsi skb wrapper for this free */
+ kfree_skb(nl_skb);
+ ret = -EINVAL;
+ goto exit_with_mib_resp;
+ }
+
+ ret = nla_put_u32(nl_skb, SLSI_NL_ATTR_MAX_BLACKLIST_SIZE, max_blacklist_size);
+ ret |= nla_put_u32(nl_skb, SLSI_NL_ATTR_MAX_WHITELIST_SIZE, max_whitelist_size);
+ if (ret) {
+ SLSI_ERR(sdev, "Error in nla_put*:%x\n", ret);
+ /* Dont use slsi skb wrapper for this free */
+ kfree_skb(nl_skb);
+ goto exit_with_mib_resp;
+ }
+
+ ret = cfg80211_vendor_cmd_reply(nl_skb);
+ if (ret)
+ SLSI_ERR(sdev, "cfg80211_vendor_cmd_reply failed :%d\n", ret);
+exit_with_mib_resp:
+ kfree(mibrsp.data);
+ kfree(values);
+exit:
+ SLSI_MUTEX_UNLOCK(ndev_vif->vif_mutex);
+ return ret;
+}
+
+static int slsi_set_roaming_state(struct wiphy *wiphy, struct wireless_dev *wdev, const void *data, int len)
+{
+ struct slsi_dev *sdev = SDEV_FROM_WIPHY(wiphy);
+ struct net_device *dev = wdev->netdev;
+ int temp = 0;
+ int type = 0;
+ const struct nlattr *attr;
+ int ret = 0;
+ int roam_state = 0;
+
+ if (!dev) {
+ SLSI_WARN_NODEV("net_dev is NULL\n");
+ return -EINVAL;
+ }
+
+ nla_for_each_attr(attr, data, len, temp) {
+ type = nla_type(attr);
+ switch (type) {
+ case SLSI_NL_ATTR_ROAM_STATE:
+ roam_state = nla_get_u8(attr);
+ break;
+ default:
+ SLSI_ERR_NODEV("Unknown attribute: %d\n", type);
+ ret = -EINVAL;
+ goto exit;
+ }
+ }
+
+ SLSI_DBG1_NODEV(SLSI_GSCAN, "SUBCMD_SET_ROAMING_STATE roam_state = %d\n", roam_state);
+ ret = slsi_set_mib_roam(sdev, NULL, SLSI_PSID_UNIFI_ROAMING_ENABLED, roam_state);
+ if (ret < 0)
+ SLSI_ERR_NODEV("Failed to set roaming state\n");
+
+exit:
+ return ret;
+}
+
#ifdef CONFIG_SCSC_WLAN_ENHANCED_LOGGING
static void slsi_on_ring_buffer_data(char *ring_name, char *buffer, int buffer_size,
struct scsc_wifi_ring_buffer_status *buffer_status, void *ctx)
timestamp = fapi_get_u64(skb, u.mlme_event_log_ind.timestamp);
SLSI_DBG3(sdev, SLSI_GSCAN,
"slsi_rx_event_log_indication, event id = %d, timestamp = %d\n", event_id, timestamp);
+#ifdef CONFIG_SCSC_WIFILOGGER
SCSC_WLOG_FW_EVENT(WLOG_NORMAL, event_id, timestamp, fapi_get_data(skb), fapi_get_datalen(skb));
+#endif
+ slsi_kfree_skb(skb);
SLSI_MUTEX_UNLOCK(sdev->logger_mutex);
}
{ OUI_GOOGLE, SLSI_NL80211_RSSI_REPORT_EVENT},
#ifdef CONFIG_SCSC_WLAN_ENHANCED_LOGGING
{ OUI_GOOGLE, SLSI_NL80211_LOGGER_RING_EVENT},
- { OUI_GOOGLE, SLSI_NL80211_LOGGER_FW_DUMP_EVENT}
+ { OUI_GOOGLE, SLSI_NL80211_LOGGER_FW_DUMP_EVENT},
#endif
+ { OUI_GOOGLE, SLSI_NL80211_NAN_RESPONSE_EVENT},
+ { OUI_GOOGLE, SLSI_NL80211_NAN_PUBLISH_TERMINATED_EVENT},
+ { OUI_GOOGLE, SLSI_NL80211_NAN_MATCH_EVENT},
+ { OUI_GOOGLE, SLSI_NL80211_NAN_MATCH_EXPIRED_EVENT},
+ { OUI_GOOGLE, SLSI_NL80211_NAN_SUBSCRIBE_TERMINATED_EVENT},
+ { OUI_GOOGLE, SLSI_NL80211_NAN_FOLLOWUP_EVENT},
+ { OUI_GOOGLE, SLSI_NL80211_NAN_DISCOVERY_ENGINE_EVENT},
+ { OUI_GOOGLE, SLSI_NL80211_NAN_DISABLED_EVENT},
+ { OUI_GOOGLE, SLSI_NL80211_RTT_RESULT_EVENT},
+ { OUI_GOOGLE, SLSI_NL80211_RTT_COMPLETE_EVENT}
};
static const struct wiphy_vendor_command slsi_vendor_cmd[] = {
},
.flags = WIPHY_VENDOR_CMD_NEED_WDEV | WIPHY_VENDOR_CMD_NEED_NETDEV,
.doit = slsi_nan_get_capabilities
+ },
+ {
+ {
+ .vendor_id = OUI_GOOGLE,
+ .subcmd = SLSI_NL80211_VENDOR_SUBCMD_GET_ROAMING_CAPABILITIES
+ },
+ .flags = WIPHY_VENDOR_CMD_NEED_WDEV | WIPHY_VENDOR_CMD_NEED_NETDEV,
+ .doit = slsi_get_roaming_capabilities
+ },
+ {
+ {
+ .vendor_id = OUI_GOOGLE,
+ .subcmd = SLSI_NL80211_VENDOR_SUBCMD_SET_ROAMING_STATE
+ },
+ .flags = WIPHY_VENDOR_CMD_NEED_WDEV | WIPHY_VENDOR_CMD_NEED_NETDEV,
+ .doit = slsi_set_roaming_state
+ },
+ {
+ {
+ .vendor_id = OUI_GOOGLE,
+ .subcmd = SLSI_NL80211_VENDOR_SUBCMD_RTT_GET_CAPABILITIES
+ },
+ .flags = WIPHY_VENDOR_CMD_NEED_WDEV | WIPHY_VENDOR_CMD_NEED_NETDEV,
+ .doit = slsi_rtt_get_capabilities
+ },
+ {
+ {
+ .vendor_id = OUI_GOOGLE,
+ .subcmd = SLSI_NL80211_VENDOR_SUBCMD_RTT_RANGE_START
+ },
+ .flags = WIPHY_VENDOR_CMD_NEED_WDEV | WIPHY_VENDOR_CMD_NEED_NETDEV,
+ .doit = slsi_rtt_set_config
+ },
+ {
+ {
+ .vendor_id = OUI_GOOGLE,
+ .subcmd = SLSI_NL80211_VENDOR_SUBCMD_RTT_RANGE_CANCEL
+ },
+ .flags = WIPHY_VENDOR_CMD_NEED_WDEV | WIPHY_VENDOR_CMD_NEED_NETDEV,
+ .doit = slsi_rtt_cancel_config
}
-
};
void slsi_nl80211_vendor_deinit(struct slsi_dev *sdev)
sdev->gscan_hash_table[i] = NULL;
INIT_LIST_HEAD(&sdev->hotlist_results);
-
}
#define SLSI_NL80211_GSCAN_EVENT_RANGE_START 0x01
#define SLSI_NL80211_LOGGING_SUBCMD_RANGE_START 0x1400
#define SLSI_NL80211_NAN_SUBCMD_RANGE_START 0x1500
+#define SLSI_NL80211_RTT_SUBCMD_RANGE_START 0x1100
#define SLSI_GSCAN_SCAN_ID_START 0x410
#define SLSI_GSCAN_SCAN_ID_END 0x500
#define SLSI_WIFI_HAL_FEATURE_HAL_EPNO 0x040000 /* WiFi PNO enhanced */
#define SLSI_WIFI_HAL_FEATURE_RSSI_MONITOR 0x080000 /* RSSI Monitor */
#define SLSI_WIFI_HAL_FEATURE_MKEEP_ALIVE 0x100000 /* WiFi mkeep_alive */
+#define SLSI_WIFI_HAL_FEATURE_CONTROL_ROAMING 0x800000 /* Enable/Disable firmware roaming macro */
enum slsi_wifi_attr {
SLSI_NL_ATTRIBUTE_ND_OFFLOAD_VALUE = 0,
SLSI_NL_ATTRIBUTE_PNO_RANDOM_MAC_OUI
};
+enum SLSI_ROAM_ATTRIBUTES {
+ SLSI_NL_ATTR_MAX_BLACKLIST_SIZE,
+ SLSI_NL_ATTR_MAX_WHITELIST_SIZE,
+ SLSI_NL_ATTR_ROAM_STATE
+};
+
enum SLSI_NAN_REPLY_ATTRIBUTES {
NAN_REPLY_ATTR_STATUS_TYPE,
NAN_REPLY_ATTR_VALUE,
SLSI_NL80211_VENDOR_SUBCMD_GET_FEATURE_SET,
SLSI_NL80211_VENDOR_SUBCMD_SET_COUNTRY_CODE,
SLSI_NL80211_VENDOR_SUBCMD_CONFIGURE_ND_OFFLOAD,
+ SLSI_NL80211_VENDOR_SUBCMD_GET_ROAMING_CAPABILITIES,
+ SLSI_NL80211_VENDOR_SUBCMD_SET_ROAMING_STATE,
SLSI_NL80211_VENDOR_SUBCMD_START_LOGGING = SLSI_NL80211_LOGGING_SUBCMD_RANGE_START,
SLSI_NL80211_VENDOR_SUBCMD_TRIGGER_FW_MEM_DUMP,
SLSI_NL80211_VENDOR_SUBCMD_GET_FW_MEM_DUMP,
SLSI_NL80211_VENDOR_SUBCMD_NAN_SUBSCRIBECANCEL,
SLSI_NL80211_VENDOR_SUBCMD_NAN_TXFOLLOWUP,
SLSI_NL80211_VENDOR_SUBCMD_NAN_CONFIG,
- SLSI_NL80211_VENDOR_SUBCMD_NAN_CAPABILITIES
+ SLSI_NL80211_VENDOR_SUBCMD_NAN_CAPABILITIES,
+ SLSI_NL80211_VENDOR_SUBCMD_RTT_GET_CAPABILITIES = SLSI_NL80211_RTT_SUBCMD_RANGE_START,
+ SLSI_NL80211_VENDOR_SUBCMD_RTT_RANGE_START,
+ SLSI_NL80211_VENDOR_SUBCMD_RTT_RANGE_CANCEL
};
enum slsi_supp_vendor_subcmds {
SLSI_NL80211_NAN_MATCH_EXPIRED_EVENT,
SLSI_NL80211_NAN_SUBSCRIBE_TERMINATED_EVENT,
SLSI_NL80211_NAN_FOLLOWUP_EVENT,
- SLSI_NL80211_NAN_DISCOVERY_ENGINE_EVENT
+ SLSI_NL80211_NAN_DISCOVERY_ENGINE_EVENT,
+ SLSI_NL80211_NAN_DISABLED_EVENT,
+ SLSI_NL80211_RTT_RESULT_EVENT,
+ SLSI_NL80211_RTT_COMPLETE_EVENT
};
enum slsi_lls_interface_mode {
SLSI_ENHANCED_LOGGING_ATTRIBUTE_WAKE_STATS_OTHER_RX_MULTICAST_CNT,
};
+enum slsi_rtt_event_attributes {
+ SLSI_RTT_EVENT_ATTR_ADDR = 0,
+ SLSI_RTT_EVENT_ATTR_BURST_NUM,
+ SLSI_RTT_EVENT_ATTR_MEASUREMENT_NUM,
+ SLSI_RTT_EVENT_ATTR_SUCCESS_NUM,
+ SLSI_RTT_EVENT_ATTR_NUM_PER_BURST_PEER,
+ SLSI_RTT_EVENT_ATTR_STATUS,
+ SLSI_RTT_EVENT_ATTR_RETRY_AFTER_DURATION,
+ SLSI_RTT_EVENT_ATTR_TYPE,
+ SLSI_RTT_EVENT_ATTR_RSSI,
+ SLSI_RTT_EVENT_ATTR_RSSI_SPREAD,
+ SLSI_RTT_EVENT_ATTR_TX_PREAMBLE,
+ SLSI_RTT_EVENT_ATTR_TX_NSS,
+ SLSI_RTT_EVENT_ATTR_TX_BW,
+ SLSI_RTT_EVENT_ATTR_TX_MCS,
+ SLSI_RTT_EVENT_ATTR_TX_RATE,
+ SLSI_RTT_EVENT_ATTR_RX_PREAMBLE,
+ SLSI_RTT_EVENT_ATTR_RX_NSS,
+ SLSI_RTT_EVENT_ATTR_RX_BW,
+ SLSI_RTT_EVENT_ATTR_RX_MCS,
+ SLSI_RTT_EVENT_ATTR_RX_RATE,
+ SLSI_RTT_EVENT_ATTR_RTT,
+ SLSI_RTT_EVENT_ATTR_RTT_SD,
+ SLSI_RTT_EVENT_ATTR_RTT_SPREAD,
+ SLSI_RTT_EVENT_ATTR_DISTANCE_MM,
+ SLSI_RTT_EVENT_ATTR_DISTANCE_SD_MM,
+ SLSI_RTT_EVENT_ATTR_DISTANCE_SPREAD_MM,
+ SLSI_RTT_EVENT_ATTR_TIMESTAMP_US,
+ SLSI_RTT_EVENT_ATTR_BURST_DURATION_MSN,
+ SLSI_RTT_EVENT_ATTR_NEGOTIATED_BURST_NUM,
+ SLSI_RTT_EVENT_ATTR_LCI,
+ SLSI_RTT_EVENT_ATTR_LCR,
+
+};
+
+/* RTT peer type */
+enum slsi_rtt_peer_type {
+ SLSI_RTT_PEER_AP = 0x1,
+ SLSI_RTT_PEER_STA,
+ SLSI_RTT_PEER_P2P_GO,
+ SLSI_RTT_PEER_P2P_CLIENT,
+ SLSI_RTT_PEER_NAN,
+};
+
+/* RTT Measurement Bandwidth */
+enum slsi_wifi_rtt_bw {
+ SLSI_WIFI_RTT_BW_5 = 0x01,
+ SLSI_WIFI_RTT_BW_10 = 0x02,
+ SLSI_WIFI_RTT_BW_20 = 0x04,
+ SLSI_WIFI_RTT_BW_40 = 0x08,
+ SLSI_WIFI_RTT_BW_80 = 0x10,
+ SLSI_WIFI_RTT_BW_160 = 0x20
+};
+
+/* RTT Measurement Preamble */
+enum slsi_wifi_rtt_preamble {
+ SLSI_WIFI_RTT_PREAMBLE_LEGACY = 0x1,
+ SLSI_WIFI_RTT_PREAMBLE_HT = 0x2,
+ SLSI_WIFI_RTT_PREAMBLE_VHT = 0x4
+};
+
+/* RTT Type */
+enum slsi_wifi_rtt_type {
+ SLSI_RTT_TYPE_1_SIDED = 0x1,
+ SLSI_RTT_TYPE_2_SIDED,
+};
+
+enum slsi_rtt_attribute {
+ SLSI_RTT_ATTRIBUTE_TARGET_CNT = 0,
+ SLSI_RTT_ATTRIBUTE_TARGET_INFO,
+ SLSI_RTT_ATTRIBUTE_TARGET_MAC,
+ SLSI_RTT_ATTRIBUTE_TARGET_TYPE,
+ SLSI_RTT_ATTRIBUTE_TARGET_PEER,
+ SLSI_RTT_ATTRIBUTE_TARGET_CHAN_WIDTH,
+ SLSI_RTT_ATTRIBUTE_TARGET_CHAN_FREQ,
+ SLSI_RTT_ATTRIBUTE_TARGET_CHAN_FREQ0,
+ SLSI_RTT_ATTRIBUTE_TARGET_CHAN_FREQ1,
+ SLSI_RTT_ATTRIBUTE_TARGET_PERIOD,
+ SLSI_RTT_ATTRIBUTE_TARGET_NUM_BURST,
+ SLSI_RTT_ATTRIBUTE_TARGET_NUM_FTM_BURST,
+ SLSI_RTT_ATTRIBUTE_TARGET_NUM_RETRY_FTM,
+ SLSI_RTT_ATTRIBUTE_TARGET_NUM_RETRY_FTMR,
+ SLSI_RTT_ATTRIBUTE_TARGET_LCI,
+ SLSI_RTT_ATTRIBUTE_TARGET_LCR,
+ SLSI_RTT_ATTRIBUTE_TARGET_BURST_DURATION,
+ SLSI_RTT_ATTRIBUTE_TARGET_PREAMBLE,
+ SLSI_RTT_ATTRIBUTE_TARGET_BW,
+ SLSI_RTT_ATTRIBUTE_RESULTS_COMPLETE = 30,
+ SLSI_RTT_ATTRIBUTE_RESULTS_PER_TARGET,
+ SLSI_RTT_ATTRIBUTE_RESULT_CNT,
+ SLSI_RTT_ATTRIBUTE_RESULT,
+ SLSI_RTT_ATTRIBUTE_TARGET_ID
+};
+
+/* Ranging status */
+enum slsi_wifi_rtt_status {
+ SLSI_RTT_STATUS_SUCCESS = 0,
+ SLSI_RTT_STATUS_FAILURE, /* general failure status */
+ SLSI_RTT_STATUS_FAIL_NO_RSP, /* target STA does not respond to request */
+ SLSI_RTT_STATUS_FAIL_REJECTED, /* request rejected. Applies to 2-sided RTT only*/
+ SLSI_RTT_STATUS_FAIL_NOT_SCHEDULED_YET,
+ SLSI_RTT_STATUS_FAIL_TM_TIMEOUT, /* timing measurement times out */
+ SLSI_RTT_STATUS_FAIL_AP_ON_DIFF_CHANNEL, /* Target on different channel, cannot range */
+ SLSI_RTT_STATUS_FAIL_NO_CAPABILITY, /* ranging not supported */
+ SLSI_RTT_STATUS_ABORTED, /* request aborted for unknown reason */
+ SLSI_RTT_STATUS_FAIL_INVALID_TS, /* Invalid T1-T4 timestamp */
+ SLSI_RTT_STATUS_FAIL_PROTOCOL, /* 11mc protocol failed */
+ SLSI_RTT_STATUS_FAIL_SCHEDULE, /* request could not be scheduled */
+ SLSI_RTT_STATUS_FAIL_BUSY_TRY_LATER, /* responder cannot collaborate at time of request */
+ SLSI_RTT_STATUS_INVALID_REQ, /* bad request args */
+ SLSI_RTT_STATUS_NO_WIFI, /* WiFi not enabled */
+ SLSI_RTT_STATUS_FAIL_FTM_PARAM_OVERRIDE /* Responder overrides param info, cannot range with new params */
+};
+
+/* Format of information elements found in the beacon */
+struct slsi_wifi_information_element {
+ u8 id; /* element identifier */
+ u8 len; /* number of bytes to follow */
+ u8 data[];
+};
+
struct slsi_nl_gscan_capabilities {
int max_scan_cache_size;
int max_scan_buckets;
u8 cluster_attribute[32];
};
+struct slsi_rtt_capabilities {
+ u8 rtt_one_sided_supported; /* if 1-sided rtt data collection is supported */
+ u8 rtt_ftm_supported; /* if ftm rtt data collection is supported */
+ u8 lci_support; /* if initiator supports LCI request. Applies to 2-sided RTT */
+ u8 lcr_support; /* if initiator supports LCR request. Applies to 2-sided RTT */
+ u8 preamble_support; /* bit mask indicates what preamble is supported by initiator */
+ u8 bw_support; /* bit mask indicates what BW is supported by initiator */
+ u8 responder_supported; /* if 11mc responder mode is supported */
+ u8 mc_version; /* draft 11mc spec version supported by chip. For instance,
+ *version 4.0 should be 40 and version 4.3 should be 43 etc.
+ */
+};
+
+/* RTT configuration */
+struct slsi_rtt_config {
+ u8 source_addr[ETH_ALEN];
+ u8 peer_addr[ETH_ALEN]; /* peer device mac address */
+ u16 type; /* 1-sided or 2-sided RTT */
+ u16 channel_freq; /* Required for STA-AP mode, optional for P2P, NBD etc. */
+ u16 channel_info;
+ u8 burst_period; /* Time interval between bursts (units: 100 ms). */
+ /* Applies to 1-sided and 2-sided RTT multi-burst requests.
+ *Range: 0-31, 0: no preference by initiator (2-sided RTT)
+ */
+ u8 num_burst; /* Total number of RTT bursts to be executed. It will be
+ *specified in the same way as the parameter "Number of
+ *Burst Exponent" found in the FTM frame format. It
+ *applies to both: 1-sided RTT and 2-sided RTT. Valid
+ *values are 0 to 15 as defined in 802.11mc std
+ *0 means single shot
+ *The implication of this parameter on the maximum
+ *number of RTT results is the following:
+ *for 1-sided RTT: max num of RTT results = (2^num_burst)*(num_frames_per_burst)
+ *for 2-sided RTT: max num of RTT results = (2^num_burst)*(num_frames_per_burst - 1)
+ */
+ u8 num_frames_per_burst; /* num of frames per burst.
+ *Minimum value = 1, Maximum value = 31
+ *For 2-sided this equals the number of FTM frames
+ *to be attempted in a single burst. This also
+ *equals the number of FTM frames that the
+ *initiator will request that the responder send
+ *in a single frame.
+ */
+ u8 num_retries_per_ftmr; /* Maximum number of retries that the initiator can
+ *retry an FTMR frame.
+ *Minimum value = 0, Maximum value = 3
+ */
+ u8 burst_duration; /* Applies to 1-sided and 2-sided RTT. Valid values will
+ *be 2-11 and 15 as specified by the 802.11mc std for
+ *the FTM parameter burst duration. In a multi-burst
+ *request, if responder overrides with larger value,
+ *the initiator will return failure. In a single-burst
+ *request if responder overrides with larger value,
+ *the initiator will sent TMR_STOP to terminate RTT
+ *at the end of the burst_duration it requested.
+ */
+ u16 preamble; /* RTT preamble to be used in the RTT frames */
+ u16 bw; /* RTT BW to be used in the RTT frames */
+ u16 LCI_request; /* 1: request LCI, 0: do not request LCI */
+ u16 LCR_request; /* 1: request LCR, 0: do not request LCR */
+};
+
void slsi_nl80211_vendor_init(struct slsi_dev *sdev);
void slsi_nl80211_vendor_deinit(struct slsi_dev *sdev);
u8 slsi_gscan_get_scan_policy(enum wifi_band band);
int slsi_vendor_event(struct slsi_dev *sdev, int event_id, const void *data, int len);
int slsi_mib_get_gscan_cap(struct slsi_dev *sdev, struct slsi_nl_gscan_capabilities *cap);
void slsi_rx_rssi_report_ind(struct slsi_dev *sdev, struct net_device *dev, struct sk_buff *skb);
+int slsi_mib_get_rtt_cap(struct slsi_dev *sdev, struct net_device *dev, struct slsi_rtt_capabilities *cap);
+int slsi_mlme_add_range_req(struct slsi_dev *sdev, u8 count, struct slsi_rtt_config *nl_rtt_params,
+ u16 rtt_id, u16 vif_idx);
+int slsi_mlme_del_range_req(struct slsi_dev *sdev, struct net_device *dev, u16 count, u8 *addr, u16 rtt_id);
+void slsi_rx_range_ind(struct slsi_dev *sdev, struct net_device *dev, struct sk_buff *skb);
+void slsi_rx_range_done_ind(struct slsi_dev *sdev, struct net_device *dev, struct sk_buff *skb);
+int slsi_tx_rate_calc(struct sk_buff *nl_skb, u16 fw_rate, int res, bool tx_rate);
void slsi_check_num_radios(struct slsi_dev *sdev);
#ifdef CONFIG_SCSC_WLAN_ENHANCED_LOGGING
void slsi_rx_event_log_indication(struct slsi_dev *sdev, struct net_device *dev, struct sk_buff *skb);
return SLSI_LLS_AC_MAX;
}
}
+
#endif
}
#endif
+static ssize_t slsi_procfs_throughput_stats_read(struct file *file, char __user *user_buf, size_t count, loff_t *ppos)
+{
+ char buf[5 * 25];
+ int pos = 0;
+ const size_t bufsz = sizeof(buf);
+ struct slsi_dev *sdev = (struct slsi_dev *)file->private_data;
+ struct net_device *dev;
+ struct slsi_mib_data mibrsp = { 0, NULL };
+ struct slsi_mib_value *values = NULL;
+ struct slsi_mib_get_entry get_values[] = {{ SLSI_PSID_UNIFI_THROUGHPUT_DEBUG, { 2, 0 } },
+ { SLSI_PSID_UNIFI_THROUGHPUT_DEBUG, { 3, 0 } },
+ { SLSI_PSID_UNIFI_THROUGHPUT_DEBUG, { 4, 0 } },
+ { SLSI_PSID_UNIFI_THROUGHPUT_DEBUG, { 24, 0 } },
+ { SLSI_PSID_UNIFI_THROUGHPUT_DEBUG, { 29, 0 } } };
+
+ SLSI_UNUSED_PARAMETER(file);
+
+ dev = slsi_get_netdev(sdev, 1);
+
+ mibrsp.dataLength = 15 * ARRAY_SIZE(get_values);
+ mibrsp.data = kmalloc(mibrsp.dataLength, GFP_KERNEL);
+ if (!mibrsp.data)
+ SLSI_ERR(sdev, "Cannot kmalloc %d bytes\n", mibrsp.dataLength);
+ values = slsi_read_mibs(sdev, dev, get_values, ARRAY_SIZE(get_values), &mibrsp);
+ if (!values) {
+ kfree(mibrsp.data);
+ return -EINVAL;
+ }
+ if (values[0].type != SLSI_MIB_TYPE_UINT)
+ SLSI_ERR(sdev, "invalid type. iter:%d", 0); /*bad_fcs_count*/
+ if (values[1].type != SLSI_MIB_TYPE_UINT)
+ SLSI_ERR(sdev, "invalid type. iter:%d", 1); /*missed_ba_count*/
+ if (values[2].type != SLSI_MIB_TYPE_UINT)
+ SLSI_ERR(sdev, "invalid type. iter:%d", 2); /*missed_ack_count*/
+ if (values[3].type != SLSI_MIB_TYPE_UINT)
+ SLSI_ERR(sdev, "invalid type. iter:%d", 3); /*mac_bad_sig_count*/
+ if (values[4].type != SLSI_MIB_TYPE_UINT)
+ SLSI_ERR(sdev, "invalid type. iter:%d", 4); /*rx_error_count*/
+
+ pos += scnprintf(buf, bufsz, "RX FCS: %d\n", values[0].u.uintValue);
+ pos += scnprintf(buf + pos, bufsz - pos, "RX bad SIG: %d\n", values[3].u.uintValue);
+ pos += scnprintf(buf + pos, bufsz - pos, "RX dot11 error: %d\n", values[4].u.uintValue);
+ pos += scnprintf(buf + pos, bufsz - pos, "TX MPDU no ACK: %d\n", values[2].u.uintValue);
+ pos += scnprintf(buf + pos, bufsz - pos, "TX A-MPDU no ACK: %d\n", values[1].u.uintValue);
+
+ kfree(values);
+ kfree(mibrsp.data);
+
+ return simple_read_from_buffer(user_buf, count, ppos, buf, pos);
+}
+
static ssize_t slsi_procfs_sta_bss_read(struct file *file, char __user *user_buf, size_t count, loff_t *ppos)
{
char buf[100];
seq_printf(m, "HW Version [MIB] : 0x%.4X (%u)\n", sdev->chip_info_mib.chip_version, sdev->chip_info_mib.chip_version);
seq_printf(m, "Platform Build [MIB] : 0x%.4X (%u)\n", sdev->plat_info_mib.plat_build, sdev->plat_info_mib.plat_build);
- for (i = 0; i < SLSI_WLAN_MAX_MIB_FILE; i++)
+ for (i = 0; i < SLSI_WLAN_MAX_MIB_FILE; i++) {
seq_printf(m, "Hash [MIB%2d] : 0x%.4X (%u)\n", i, sdev->mib[i].mib_hash, sdev->mib[i].mib_hash);
+ seq_printf(m, "Platform: [MIB%2d] : %s\n", i, sdev->mib[i].platform);
+ }
seq_printf(m, "Hash [local_MIB] : 0x%.4X (%u)\n", sdev->local_mib.mib_hash, sdev->local_mib.mib_hash);
+ seq_printf(m, "Platform: [local_MIB] : %s\n", sdev->local_mib.platform);
+
return 0;
}
#endif
SLSI_PROCFS_READ_FILE_OPS(sta_bss);
SLSI_PROCFS_READ_FILE_OPS(big_data);
+SLSI_PROCFS_READ_FILE_OPS(throughput_stats);
SLSI_PROCFS_SEQ_FILE_OPS(tcp_ack_suppression);
int slsi_create_proc_dir(struct slsi_dev *sdev)
#endif
SLSI_PROCFS_ADD_FILE(sdev, sta_bss, parent, S_IRUSR | S_IWUSR | S_IRGRP | S_IWGRP);
SLSI_PROCFS_ADD_FILE(sdev, big_data, parent, S_IRUSR | S_IWUSR | S_IRGRP | S_IWGRP);
+ SLSI_PROCFS_ADD_FILE(sdev, throughput_stats, parent, S_IRUSR | S_IWUSR | S_IRGRP | S_IWGRP);
SLSI_PROCFS_SEQ_ADD_FILE(sdev, tcp_ack_suppression, sdev->procfs_dir, S_IRUSR | S_IRGRP);
}
#endif
SLSI_PROCFS_REMOVE_FILE(sta_bss, sdev->procfs_dir);
SLSI_PROCFS_REMOVE_FILE(big_data, sdev->procfs_dir);
+ SLSI_PROCFS_REMOVE_FILE(throughput_stats, sdev->procfs_dir);
SLSI_PROCFS_REMOVE_FILE(tcp_ack_suppression, sdev->procfs_dir);
(void)snprintf(dir, sizeof(dir), "driver/unifi%d", sdev->procfs_instance);
#include "cac.h"
#include "nl80211_vendor.h"
+#ifdef CONFIG_ANDROID
#include "scsc_wifilogger_rings.h"
+#endif
+
#ifdef CONFIG_SCSC_LOG_COLLECTION
#include <scsc/scsc_log_collector.h>
#endif
}
scan = slsi_dequeue_cached_scan_result(&ndev_vif->scan[scan_id], result_count);
}
- SLSI_NET_DBG3(dev, SLSI_MLME, "interface:%d, scan_id:%d, scan_results_count:%d %s\n",
- ndev_vif->ifnum, scan_id, scan_results_count,
+ SLSI_INFO(sdev, "Scan count:%d APs\n", scan_results_count);
+ SLSI_NET_DBG3(dev, SLSI_MLME, "interface:%d, scan_id:%d,%s\n", ndev_vif->ifnum, scan_id,
more_than_max_count ? "Scan results overflow" : "");
slsi_roam_channel_cache_prune(dev, SLSI_ROAMING_CHANNEL_CACHE_TIMEOUT);
ndev_vif->ap.channel_freq = freq; /* updated for GETSTAINFO */
cfg80211_ch_switch_notify(dev, &chandef);
+ slsi_kfree_skb(skb);
}
void __slsi_rx_blockack_ind(struct slsi_dev *sdev, struct net_device *dev, struct sk_buff *skb)
ndev_vif->sta.roam_in_progress = false;
ndev_vif->chan = ndev_vif->sta.sta_bss->channel;
-#ifndef SLSI_TEST_DEV
+#if !defined SLSI_TEST_DEV && defined CONFIG_ANDROID
SLSI_NET_DBG1(dev, SLSI_MLME, "Taking a wakelock for DHCP to finish after roaming\n");
wake_lock_timeout(&sdev->wlan_wl_roam, msecs_to_jiffies(10 * 1000));
+#ifdef CONFIG_SCSC_WIFILOGGER
SCSC_WLOG_WAKELOCK(WLOG_NORMAL, WL_TAKEN, "wlan_wl_roam", WL_REASON_ROAM);
+#endif
#endif
if (!temporal_keys_required) {
SLSI_MUTEX_LOCK(ndev_vif->vif_mutex);
- SLSI_NET_DBG1(dev, SLSI_MLME, "mlme_tdls_event_discovered\n");
+ SLSI_INFO(sdev, "\n");
if (len != 0) {
#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 10, 9))
ndev_vif->sta.tdls_enabled = true;
- SLSI_NET_DBG1(dev, SLSI_MLME, "mlme_tdls_event_connected(vif:%d, peer_index:%d mac[%pM])\n",
+ SLSI_INFO(sdev, "(vif:%d, peer_index:%d mac[%pM])\n",
fapi_get_vif(skb), peer_index, fapi_get_buff(skb, u.mlme_tdls_peer_ind.peer_sta_address));
if (!ndev_vif->activated) {
if (WARN_ON(!dev))
goto exit;
- SLSI_NET_DBG1(dev, SLSI_MLME, "slsi_tdls_event_disconnected(vif:%d, MAC:%pM)\n", ndev_vif->ifnum, fapi_get_buff(skb, u.mlme_tdls_peer_ind.peer_sta_address));
+ SLSI_INFO(sdev, "(vif:%d, MAC:%pM)\n", ndev_vif->ifnum,
+ fapi_get_buff(skb, u.mlme_tdls_peer_ind.peer_sta_address));
if (!ndev_vif->activated) {
SLSI_NET_DBG1(dev, SLSI_MLME, "VIF not activated\n");
if (tx_status != FAPI_TRANSMISSIONSTATUS_SUCCESSFUL) {
ack = false;
if (SLSI_IS_VIF_INDEX_WLAN(ndev_vif)) {
- if (sdev->hs2_state == HS2_VIF_TX)
- sdev->hs2_state = HS2_VIF_ACTIVE; /*We wouldn't delete VIF*/
+ if (sdev->wlan_unsync_vif_state == WLAN_UNSYNC_VIF_TX)
+ sdev->wlan_unsync_vif_state = WLAN_UNSYNC_VIF_ACTIVE; /*We wouldn't delete VIF*/
} else {
if (sdev->p2p_group_exp_frame != SLSI_P2P_PA_INVALID)
slsi_clear_offchannel_data(sdev, false);
if (mgmt->u.action.category == WLAN_CATEGORY_WMM) {
cac_rx_wmm_action(sdev, dev, mgmt, mgmt_len);
} else {
- slsi_hs2_dump_public_action_subtype(mgmt, false);
- if (sdev->hs2_state == HS2_VIF_TX)
- sdev->hs2_state = HS2_VIF_ACTIVE;
+ slsi_wlan_dump_public_action_subtype(mgmt, false);
+ if (sdev->wlan_unsync_vif_state == WLAN_UNSYNC_VIF_TX)
+ sdev->wlan_unsync_vif_state = WLAN_UNSYNC_VIF_ACTIVE;
}
#ifdef CONFIG_SCSC_WLAN_WES_NCHO
}
skb_pull(skb, fapi_get_siglen(skb));
skb->dev = dev;
- skb->ip_summed = CHECKSUM_UNNECESSARY;
+ skb->ip_summed = CHECKSUM_NONE;
ndev_vif->stats.rx_packets++;
ndev_vif->stats.rx_bytes += skb->len;
slsi_kfree_skb(skb);
}
-#ifdef CONFIG_SCSC_WLAN_RX_NAPI
-static int slsi_rx_msdu_napi(struct net_device *dev, struct sk_buff *skb)
-{
- struct netdev_vif *ndev_vif = netdev_priv(dev);
-
- slsi_skb_queue_tail(&ndev_vif->napi.rx_data, skb);
- slsi_spinlock_lock(&ndev_vif->napi.lock);
- if (ndev_vif->napi.interrupt_enabled) {
- ndev_vif->napi.interrupt_enabled = false;
- napi_schedule(&ndev_vif->napi.napi);
- }
- slsi_spinlock_unlock(&ndev_vif->napi.lock);
-}
-#endif
-
static int slsi_rx_wait_ind_match(u16 recv_id, u16 wait_id)
{
if (recv_id == wait_id)
#include "hip4_sampler.h"
#include "traffic_monitor.h"
+#ifdef CONFIG_ANDROID
#include "scsc_wifilogger_rings.h"
+#endif
#define SUPPORTED_OLD_VERSION 0
return -EINVAL;
}
-static int slsi_rx_amsdu_deaggregate(struct net_device *dev, struct sk_buff *skb)
+static int slsi_rx_amsdu_deaggregate(struct net_device *dev, struct sk_buff *skb, struct sk_buff_head *msdu_list)
{
- struct netdev_vif *ndev_vif = netdev_priv(dev);
- struct slsi_dev *sdev = ndev_vif->sdev;
unsigned int msdu_len;
unsigned int subframe_len;
int padding;
struct sk_buff *subframe = NULL;
+ bool last_sub_frame = false;
const unsigned char mac_0[ETH_ALEN] = { 0 };
bool skip_frame = false;
struct ethhdr *mh;
SLSI_NET_DBG4(dev, SLSI_RX, "A-MSDU received (len:%d)\n", skb->len);
- while (skb != subframe) {
+ while (!last_sub_frame) {
msdu_len = (skb->data[ETH_ALEN * 2] << 8) | skb->data[(ETH_ALEN * 2) + 1];
/* check if the length of sub-frame is valid */
/* For the last subframe skb length and subframe length will be same */
if (skb->len == subframe_len) {
/* Use the original skb for the last subframe */
- subframe = skb;
+ subframe = slsi_skb_copy(skb, GFP_ATOMIC);
/* There is no padding for last subframe */
padding = 0;
+ last_sub_frame = true;
} else {
/* Clone the skb for the subframe */
- subframe = slsi_skb_clone(skb, GFP_ATOMIC);
+ subframe = slsi_skb_copy(skb, GFP_ATOMIC);
if (!subframe) {
slsi_kfree_skb(skb);
SLSI_NET_ERR(dev, "Failed to clone the SKB for A-MSDU subframe\n");
skb_set_mac_header(subframe, 0);
mh = eth_hdr(subframe);
if (SLSI_ETHER_EQUAL(mh->h_dest, mac_0)) {
- SLSI_NET_DBG3(dev, SLSI_RX, "msdu subframe filtered out: MAC destination address %pM\n",
- mh->h_dest);
+ SLSI_NET_DBG3(dev, SLSI_RX, "msdu subframe filtered out: MAC destination address %pM\n", mh->h_dest);
skip_frame = true;
}
/* If this is not the last subframe then move to the next subframe */
- if (skb != subframe)
+ if (!last_sub_frame)
skb_pull(skb, (subframe_len + padding));
/* If this frame has been filtered out, free the clone and continue */
slsi_kfree_skb(subframe);
continue;
}
-
- /* Prepare the skb */
- subframe->dev = dev;
- subframe->ip_summed = CHECKSUM_UNNECESSARY;
- ndev_vif->stats.rx_bytes += subframe->len;
- ndev_vif->stats.rx_packets++;
-
- SCSC_HIP4_SAMPLER_TCP_DECODE(ndev_vif->sdev, dev, skb->data, true);
- subframe->protocol = eth_type_trans(subframe, dev);
-#ifdef CONFIG_SCSC_WLAN_RX_NAPI
- slsi_rx_msdu_napi(dev, subframe);
-#else
- slsi_traffic_mon_event_rx(sdev, dev, subframe);
- slsi_dbg_untrack_skb(subframe);
- SLSI_DBG4(sdev, SLSI_RX, "pass %u bytes to local stack\n", subframe->len);
- netif_rx_ni(subframe);
-#endif
+ __skb_queue_tail(msdu_list, subframe);
}
-
+ slsi_kfree_skb(skb);
return 0;
}
return (fapi_get_u16(skb, u.ma_unitdata_ind.data_unit_descriptor) == FAPI_DATAUNITDESCRIPTOR_AMSDU);
}
-static int slsi_rx_data_process_skb(struct slsi_dev *sdev, struct net_device *dev, struct sk_buff **skb, bool from_ba)
+void slsi_rx_data_deliver_skb(struct slsi_dev *sdev, struct net_device *dev, struct sk_buff *skb)
{
struct netdev_vif *ndev_vif = netdev_priv(dev);
+ struct sk_buff_head msdu_list;
struct slsi_peer *peer = NULL;
- struct ethhdr *ehdr;
- u16 seq_num;
- bool skip_ba = from_ba;
- bool is_amsdu = slsi_rx_is_amsdu((*skb));
- u8 trafic_q = slsi_frame_priority_to_ac_queue(fapi_get_u16((*skb), u.ma_unitdata_ind.priority));
+ struct ethhdr *eth_hdr;
+ bool is_amsdu = slsi_rx_is_amsdu(skb);
+ u8 trafic_q = slsi_frame_priority_to_ac_queue(fapi_get_u16(skb, u.ma_unitdata_ind.priority));
+
+ __skb_queue_head_init(&msdu_list);
#ifdef CONFIG_SCSC_SMAPPER
/* Check if the payload is in the SMAPPER entry */
- if (fapi_get_u16((*skb), u.ma_unitdata_ind.bulk_data_descriptor) == FAPI_BULKDATADESCRIPTOR_SMAPPER) {
- ehdr = (struct ethhdr *)slsi_hip_get_skb_data_from_smapper(sdev, (*skb));
- if (!(ehdr)) {
+ if (fapi_get_u16(skb, u.ma_unitdata_ind.bulk_data_descriptor) == FAPI_BULKDATADESCRIPTOR_SMAPPER) {
+ /* Retrieve the associated smapper skb */
+ skb = slsi_hip_get_skb_from_smapper(sdev, skb);
+ if (!skb) {
SLSI_NET_DBG2(dev, SLSI_RX, "SKB from SMAPPER is NULL\n");
- return -EINVAL;
+ return;
}
} else {
- ehdr = (struct ethhdr *)fapi_get_data((*skb));
+ /* strip signal and any signal/bulk roundings/offsets */
+ skb_pull(skb, fapi_get_siglen(skb));
}
#else
- ehdr = (struct ethhdr *)fapi_get_data((*skb));
+ skb_pull(skb, fapi_get_siglen(skb));
#endif
- SLSI_NET_DBG_HEX(dev, SLSI_RX, (*skb)->data, (*skb)->len < 64 ? (*skb)->len : 64, "\n");
+ eth_hdr = (struct ethhdr *)skb->data;
+ peer = slsi_get_peer_from_mac(sdev, dev, eth_hdr->h_source);
+ if (!peer) {
+ SLSI_NET_WARN(dev, "Packet dropped (no peer records)\n");
+ slsi_kfree_skb(skb);
+ return;
+ }
- if (!((fapi_get_u16((*skb), u.ma_unitdata_ind.data_unit_descriptor) == FAPI_DATAUNITDESCRIPTOR_IEEE802_3_FRAME) ||
- (fapi_get_u16((*skb), u.ma_unitdata_ind.data_unit_descriptor) == FAPI_DATAUNITDESCRIPTOR_IEEE802_11_FRAME) ||
- (fapi_get_u16((*skb), u.ma_unitdata_ind.data_unit_descriptor) == FAPI_DATAUNITDESCRIPTOR_AMSDU))) {
- WARN_ON(1);
- slsi_kfree_skb((*skb));
- return -ENOTSUPP;
+ /* A-MSDU deaggregation */
+ if (is_amsdu) {
+ if (slsi_rx_amsdu_deaggregate(dev, skb, &msdu_list)) {
+ ndev_vif->stats.rx_dropped++;
+ if (peer)
+ peer->sinfo.rx_dropped_misc++;
+ return;
+ }
+ } else {
+ __skb_queue_tail(&msdu_list, skb);
+ }
+
+ while (!skb_queue_empty(&msdu_list)) {
+ struct sk_buff *rx_skb;
+
+ rx_skb = __skb_dequeue(&msdu_list);
+
+ /* In STA mode, the AP relays back our multicast traffic.
+ * Receiving these frames and passing it up confuses some
+ * protocols and applications, notably IPv6 Duplicate
+ * Address Detection.
+ *
+ * So these frames are dropped instead of passing it further.
+ * No need to update the drop statistics as these frames are
+ * locally generated and should not be accounted in reception.
+ */
+ if (ndev_vif->vif_type == FAPI_VIFTYPE_STATION) {
+ struct ethhdr *ehdr = (struct ethhdr *)(rx_skb->data);
+
+ if (is_multicast_ether_addr(ehdr->h_dest) &&
+ !compare_ether_addr(ehdr->h_source, dev->dev_addr)) {
+ SLSI_NET_DBG2(dev, SLSI_RX, "drop locally generated multicast frame relayed back by AP\n");
+ slsi_kfree_skb(rx_skb);
+ continue;
+ }
+ }
+
+ /* Intra BSS */
+ if (ndev_vif->vif_type == FAPI_VIFTYPE_AP && ndev_vif->peer_sta_records) {
+ struct slsi_peer *peer = NULL;
+ struct ethhdr *ehdr = (struct ethhdr *)(rx_skb->data);
+
+ if (is_multicast_ether_addr(ehdr->h_dest)) {
+ struct sk_buff *rebroadcast_skb = slsi_skb_copy(rx_skb, GFP_KERNEL);
+
+ if (!rebroadcast_skb) {
+ SLSI_WARN(sdev, "Intra BSS: failed to alloc new SKB for broadcast\n");
+ } else {
+ SLSI_DBG3(sdev, SLSI_RX, "Intra BSS: multicast %pM\n", ehdr->h_dest);
+ rebroadcast_skb->dev = dev;
+ rebroadcast_skb->protocol = cpu_to_be16(ETH_P_802_3);
+ slsi_dbg_untrack_skb(rebroadcast_skb);
+ skb_reset_network_header(rebroadcast_skb);
+ skb_reset_mac_header(rebroadcast_skb);
+ dev_queue_xmit(rebroadcast_skb);
+ }
+ } else {
+ peer = slsi_get_peer_from_mac(sdev, dev, ehdr->h_dest);
+ if (peer && peer->authorized) {
+ SLSI_DBG3(sdev, SLSI_RX, "Intra BSS: unicast %pM\n", ehdr->h_dest);
+ rx_skb->dev = dev;
+ rx_skb->protocol = cpu_to_be16(ETH_P_802_3);
+ slsi_dbg_untrack_skb(rx_skb);
+ skb_reset_network_header(rx_skb);
+ skb_reset_mac_header(rx_skb);
+ dev_queue_xmit(rx_skb);
+ continue;
+ }
+ }
+ }
+
+ if (peer) {
+ peer->sinfo.rx_packets++;
+ peer->sinfo.rx_bytes += rx_skb->len;
+ }
+ ndev_vif->stats.rx_packets++;
+ ndev_vif->stats.rx_bytes += rx_skb->len;
+ ndev_vif->rx_packets[trafic_q]++;
+
+ rx_skb->dev = dev;
+ rx_skb->ip_summed = CHECKSUM_NONE;
+ rx_skb->protocol = eth_type_trans(rx_skb, dev);
+
+ SCSC_HIP4_SAMPLER_TCP_DECODE(sdev, dev, rx_skb->data, true);
+ slsi_traffic_mon_event_rx(sdev, dev, rx_skb);
+ slsi_dbg_untrack_skb(rx_skb);
+
+ SLSI_DBG4(sdev, SLSI_RX, "pass %u bytes to local stack\n", rx_skb->len);
+#ifdef CONFIG_SCSC_WLAN_RX_NAPI_GRO
+ napi_gro_receive(&sdev->hip4_inst.hip_priv->napi, rx_skb);
+#elif defined(CONFIG_SCSC_WLAN_RX_NAPI)
+ netif_receive_skb(rx_skb);
+#else
+ netif_rx_ni(rx_skb);
+#endif
+ slsi_wakelock_timeout(&sdev->wlan_wl_ma, SLSI_RX_WAKELOCK_TIME);
}
+}
- seq_num = fapi_get_u16((*skb), u.ma_unitdata_ind.sequence_number);
- SLSI_NET_DBG4(dev, SLSI_RX, "ma_unitdata_ind(vif:%d, %pM, datatype:%d, priority:%d, s:%d)\n",
- fapi_get_vif((*skb)),
- ehdr->h_source,
- fapi_get_u16((*skb), u.ma_unitdata_ind.data_unit_descriptor),
- fapi_get_u16((*skb), u.ma_unitdata_ind.priority),
- (seq_num & SLSI_RX_SEQ_NUM_MASK));
+static void slsi_rx_data_ind(struct slsi_dev *sdev, struct net_device *dev, struct sk_buff *skb)
+{
+ struct netdev_vif *ndev_vif = netdev_priv(dev);
+ struct slsi_peer *peer = NULL;
+ struct ethhdr *eth_hdr;
+ u16 seq_num;
+
+ if (!((fapi_get_u16(skb, u.ma_unitdata_ind.data_unit_descriptor) == FAPI_DATAUNITDESCRIPTOR_IEEE802_3_FRAME) ||
+ (fapi_get_u16(skb, u.ma_unitdata_ind.data_unit_descriptor) == FAPI_DATAUNITDESCRIPTOR_IEEE802_11_FRAME) ||
+ (fapi_get_u16(skb, u.ma_unitdata_ind.data_unit_descriptor) == FAPI_DATAUNITDESCRIPTOR_AMSDU))) {
+ WARN_ON(1);
+ slsi_kfree_skb(skb);
+ return;
+ }
#ifdef CONFIG_SCSC_WLAN_DEBUG
/* pass the data up "As is" if the VIF type is Monitor */
if (ndev_vif->vif_type == FAPI_VIFTYPE_MONITOR) {
/* strip signal */
- skb_pull((*skb), fapi_get_siglen((*skb)));
+ skb_pull(skb, fapi_get_siglen(skb));
- skb_reset_mac_header((*skb));
- (*skb)->dev = dev;
- (*skb)->ip_summed = CHECKSUM_UNNECESSARY;
- (*skb)->pkt_type = PACKET_OTHERHOST;
- return 0;
+ skb_reset_mac_header(skb);
+ skb->dev = dev;
+ skb->ip_summed = CHECKSUM_UNNECESSARY;
+ skb->pkt_type = PACKET_OTHERHOST;
+ netif_rx_ni(skb);
}
#endif
- peer = slsi_get_peer_from_mac(sdev, dev, ehdr->h_source);
+
+#ifdef CONFIG_SCSC_SMAPPER
+ /* Check if the payload is in the SMAPPER entry */
+ if (fapi_get_u16(skb, u.ma_unitdata_ind.bulk_data_descriptor) == FAPI_BULKDATADESCRIPTOR_SMAPPER) {
+ eth_hdr = (struct ethhdr *)slsi_hip_get_skb_data_from_smapper(sdev, skb);
+ if (!(eth_hdr)) {
+ SLSI_NET_DBG2(dev, SLSI_RX, "SKB from SMAPPER is NULL\n");
+ slsi_kfree_skb(skb);
+ return;
+ }
+ } else {
+ eth_hdr = (struct ethhdr *)fapi_get_data(skb);
+ }
+#else
+ eth_hdr = (struct ethhdr *)fapi_get_data(skb);
+#endif
+ seq_num = fapi_get_u16(skb, u.ma_unitdata_ind.sequence_number);
+ SLSI_NET_DBG4(dev, SLSI_RX, "ma_unitdata_ind(vif:%d, dest:%pM, src:%pM, datatype:%d, priority:%d, s:%d)\n",
+ fapi_get_vif(skb),
+ eth_hdr->h_dest,
+ eth_hdr->h_source,
+ fapi_get_u16(skb, u.ma_unitdata_ind.data_unit_descriptor),
+ fapi_get_u16(skb, u.ma_unitdata_ind.priority),
+ (seq_num & SLSI_RX_SEQ_NUM_MASK));
+
+ peer = slsi_get_peer_from_mac(sdev, dev, eth_hdr->h_source);
if (!peer) {
SLSI_NET_WARN(dev, "Packet dropped (no peer records)\n");
/* Race in Data plane (Shows up in fw test mode) */
- slsi_kfree_skb((*skb));
- return -EINVAL;
+ slsi_kfree_skb(skb);
+ return;
}
/* discard data frames if received before key negotiations are completed */
- if ((ndev_vif->vif_type == FAPI_VIFTYPE_AP) && (peer->connected_state != SLSI_STA_CONN_STATE_CONNECTED)) {
+ if (ndev_vif->vif_type == FAPI_VIFTYPE_AP && peer->connected_state != SLSI_STA_CONN_STATE_CONNECTED) {
SLSI_NET_WARN(dev, "Packet dropped (peer connection not complete (state:%u))\n", peer->connected_state);
- slsi_kfree_skb((*skb));
- return -EINVAL;
+ slsi_kfree_skb(skb);
+ return;
}
/* When TDLS connection has just been closed a few last frame may still arrive from the closed connection.
* This frames must not be injected in to the block session with the AP as the sequence numbers are different
* that will confuse the BA process. Therefore we have to skip BA for those frames.
*/
- if ((ndev_vif->vif_type == FAPI_VIFTYPE_STATION) && (peer->aid < SLSI_TDLS_PEER_INDEX_MIN) && (seq_num & SLSI_RX_VIA_TDLS_LINK)) {
+ if (ndev_vif->vif_type == FAPI_VIFTYPE_STATION && peer->aid < SLSI_TDLS_PEER_INDEX_MIN && (seq_num & SLSI_RX_VIA_TDLS_LINK)) {
if (printk_ratelimit())
SLSI_NET_WARN(dev, "Packet received from TDLS but no TDLS exists (seq: %x) Skip BA\n", seq_num);
- skip_ba = true;
+
+ /* Skip BA reorder and pass the frames Up */
+ slsi_rx_data_deliver_skb(sdev, dev, skb);
+ return;
}
/* TDLS is enabled for the PEER but still packet is received through the AP. Process this packet with the AP PEER */
- if ((ndev_vif->vif_type == FAPI_VIFTYPE_STATION) && (peer->aid >= SLSI_TDLS_PEER_INDEX_MIN) && (!(seq_num & SLSI_RX_VIA_TDLS_LINK))) {
+ if (ndev_vif->vif_type == FAPI_VIFTYPE_STATION && peer->aid >= SLSI_TDLS_PEER_INDEX_MIN && (!(seq_num & SLSI_RX_VIA_TDLS_LINK))) {
SLSI_NET_DBG2(dev, SLSI_TDLS, "Packet received from TDLS peer through the AP(seq: %x)\n", seq_num);
peer = slsi_get_peer_from_qs(sdev, dev, SLSI_STA_PEER_QUEUESET);
if (!peer) {
SLSI_NET_WARN(dev, "Packet dropped (AP peer not found)\n");
- slsi_kfree_skb((*skb));
- return -EINVAL;
- }
- }
-
- if (!skip_ba && (slsi_ba_check(peer, fapi_get_u16((*skb), u.ma_unitdata_ind.priority))))
- if (!slsi_ba_process_frame(dev, peer, (*skb), (seq_num & SLSI_RX_SEQ_NUM_MASK),
- fapi_get_u16((*skb), u.ma_unitdata_ind.priority)))
- return 1;
-
-#ifdef CONFIG_SCSC_SMAPPER
- /* Check if the payload is in the SMAPPER entry */
- if (fapi_get_u16((*skb), u.ma_unitdata_ind.bulk_data_descriptor) == FAPI_BULKDATADESCRIPTOR_SMAPPER) {
- /* Retrieve the associated smapper skb */
- *skb = slsi_hip_get_skb_from_smapper(sdev, (*skb));
- if (!(*skb)) {
- SLSI_NET_DBG2(dev, SLSI_RX, "SKB from SMAPPER is NULL\n");
- return -EINVAL;
- }
- } else {
- /* strip signal and any signal/bulk roundings/offsets */
- skb_pull((*skb), fapi_get_siglen((*skb)));
- }
-#else
- skb_pull((*skb), fapi_get_siglen((*skb)));
-#endif
-
- /* A-MSDU deaggregation */
- if (is_amsdu) {
- /* This function will consume the skb */
- if (slsi_rx_amsdu_deaggregate(dev, (*skb))) {
- ndev_vif->stats.rx_dropped++;
- if (peer)
- peer->sinfo.rx_dropped_misc++;
- } else {
- if (peer) {
- peer->sinfo.rx_packets++;
- ndev_vif->rx_packets[trafic_q]++;
- }
- slsi_wakelock_timeout(&sdev->wlan_wl_ma, SLSI_RX_WAKELOCK_TIME);
- }
- return 1;
- }
-
- (*skb)->dev = dev;
- (*skb)->ip_summed = CHECKSUM_UNNECESSARY;
-
- /* In STA mode, the AP relays back our multicast traffic.
- * Receiving these frames and passing it up confuses some
- * protocols and applications, notably IPv6 Duplicate
- * Address Detection.
- *
- * So these frames are dropped instead of passing it further.
- * No need to update the drop statistics as these frames are
- * locally generated and should not be accounted in reception.
- */
- if (ndev_vif->vif_type == FAPI_VIFTYPE_STATION) {
- struct ethhdr *ehdr = (struct ethhdr *)((*skb)->data);
-
- if (is_multicast_ether_addr(ehdr->h_dest) &&
- !compare_ether_addr(ehdr->h_source, dev->dev_addr)) {
- SLSI_NET_DBG2(dev, SLSI_RX, "drop locally generated multicast frame relayed back by AP\n");
- slsi_kfree_skb((*skb));
- return -EINVAL;
- }
- }
-
- if (peer) {
- peer->sinfo.rx_packets++;
- peer->sinfo.rx_bytes += (*skb)->len;
- }
-
- ndev_vif->stats.rx_packets++;
- ndev_vif->stats.rx_bytes += (*skb)->len;
- ndev_vif->rx_packets[trafic_q]++;
-
- /* Intra BSS */
- if (ndev_vif->vif_type == FAPI_VIFTYPE_AP && ndev_vif->peer_sta_records) {
- struct ethhdr *ehdr = (struct ethhdr *)((*skb)->data);
-
- if (is_multicast_ether_addr(ehdr->h_dest)) {
- struct sk_buff *rebroadcast_skb = slsi_skb_copy((*skb), GFP_KERNEL);
-
- (*skb)->protocol = eth_type_trans((*skb), dev);
- if (!rebroadcast_skb) {
- SLSI_WARN(sdev, "Intra BSS: failed to alloc new SKB for broadcast\n");
- return 0;
- }
- SLSI_DBG3(sdev, SLSI_RX, "Intra BSS: multicast %pM\n", ehdr->h_dest);
- rebroadcast_skb->dev = dev;
- rebroadcast_skb->protocol = cpu_to_be16(ETH_P_802_3);
- slsi_dbg_untrack_skb(rebroadcast_skb);
- skb_reset_network_header(rebroadcast_skb);
- skb_reset_mac_header(rebroadcast_skb);
- dev_queue_xmit(rebroadcast_skb);
- return 0;
- }
-
- peer = slsi_get_peer_from_mac(sdev, dev, ehdr->h_dest);
- if (peer && peer->authorized) {
- SLSI_DBG3(sdev, SLSI_RX, "Intra BSS: unicast %pM\n", ehdr->h_dest);
- (*skb)->protocol = cpu_to_be16(ETH_P_802_3);
- slsi_dbg_untrack_skb((*skb));
- skb_reset_network_header((*skb));
- skb_reset_mac_header((*skb));
- dev_queue_xmit((*skb));
- return 1;
+ slsi_kfree_skb(skb);
+ return;
}
}
- SCSC_HIP4_SAMPLER_TCP_DECODE(sdev, dev, (*skb)->data, true);
- (*skb)->protocol = eth_type_trans((*skb), dev);
- return 0;
-}
-
-#ifdef CONFIG_SCSC_WLAN_RX_NAPI
-int slsi_rx_data_napi(struct slsi_dev *sdev, struct net_device *dev, struct sk_buff *skb, bool from_ba)
-{
- struct netdev_vif *ndev_vif = netdev_priv(dev);
- slsi_debug_frame(sdev, dev, skb, "RX");
+ /* If frame belongs to a negotiated BA, BA will consume the frame */
+ if (slsi_ba_check(peer, fapi_get_u16(skb, u.ma_unitdata_ind.priority)))
+ if (!slsi_ba_process_frame(dev, peer, skb, (seq_num & SLSI_RX_SEQ_NUM_MASK),
+ fapi_get_u16(skb, u.ma_unitdata_ind.priority)))
+ return;
- if (slsi_rx_data_process_skb(sdev, dev, skb, from_ba) == 0) {
- slsi_skb_queue_tail(&ndev_vif->napi.rx_data, skb);
- slsi_spinlock_lock(&ndev_vif->napi.lock);
- if (ndev_vif->napi.interrupt_enabled) {
- ndev_vif->napi.interrupt_enabled = false;
- napi_schedule(&ndev_vif->napi.napi);
- }
- slsi_spinlock_unlock(&ndev_vif->napi.lock);
- }
- return 0;
-}
-#endif
-
-int slsi_rx_data(struct slsi_dev *sdev, struct net_device *dev, struct sk_buff *skb, bool from_ba)
-{
- if (slsi_rx_data_process_skb(sdev, dev, &skb, from_ba) == 0) {
- slsi_traffic_mon_event_rx(sdev, dev, skb);
- slsi_dbg_untrack_skb(skb);
- SLSI_DBG4(sdev, SLSI_RX, "pass %u bytes to local stack\n", skb->len);
- netif_rx_ni(skb);
- slsi_wakelock_timeout(&sdev->wlan_wl_ma, SLSI_RX_WAKELOCK_TIME);
- }
- return 0;
+ /* Pass to next receive process */
+ slsi_rx_data_deliver_skb(sdev, dev, skb);
}
static int slsi_rx_data_cfm(struct slsi_dev *sdev, struct net_device *dev, struct sk_buff *skb)
return 0;
}
+#ifdef CONFIG_SCSC_WLAN_RX_NAPI
+static int slsi_rx_napi_process(struct slsi_dev *sdev, struct sk_buff *skb)
+{
+ struct net_device *dev;
+ struct netdev_vif *ndev_vif;
+ u16 vif;
+
+ vif = fapi_get_vif(skb);
+
+ rcu_read_lock();
+ dev = slsi_get_netdev_rcu(sdev, vif);
+ if (!dev) {
+ SLSI_ERR(sdev, "netdev(%d) No longer exists\n", vif);
+ rcu_read_unlock();
+ return -EINVAL;
+ }
+ rcu_read_unlock();
+
+ ndev_vif = netdev_priv(dev);
+
+ switch (fapi_get_u16(skb, id)) {
+ case MA_UNITDATA_IND:
+ slsi_rx_data_ind(sdev, dev, skb);
+
+ /* SKBs in a BA session are not passed yet */
+ if (atomic_read(&ndev_vif->ba_flush)) {
+ atomic_set(&ndev_vif->ba_flush, 0);
+ slsi_ba_process_complete(dev);
+ }
+ break;
+ case MA_UNITDATA_CFM:
+ (void)slsi_rx_data_cfm(sdev, dev, skb);
+ break;
+ default:
+ SLSI_DBG1(sdev, SLSI_RX, "Unexpected Data: 0x%.4x\n", fapi_get_sigid(skb));
+ slsi_kfree_skb(skb);
+ break;
+ }
+ return 0;
+}
+#else
void slsi_rx_netdev_data_work(struct work_struct *work)
{
struct slsi_skb_work *w = container_of(work, struct slsi_skb_work, work);
SLSI_MUTEX_UNLOCK(ndev_vif->vif_mutex);
break;
}
+
if (atomic_read(&ndev_vif->ba_flush)) {
atomic_set(&ndev_vif->ba_flush, 0);
slsi_ba_process_complete(dev);
break;
}
- slsi_debug_frame(sdev, dev, skb, "RX");
switch (fapi_get_u16(skb, id)) {
case MA_UNITDATA_IND:
#ifdef CONFIG_SCSC_SMAPPER
#else
SCSC_HIP4_SAMPLER_TCP_DECODE(sdev, dev, skb->data + fapi_get_siglen(skb), false);
#endif
- (void)slsi_rx_data(sdev, dev, skb, false);
+ slsi_rx_data_ind(sdev, dev, skb);
break;
case MA_UNITDATA_CFM:
(void)slsi_rx_data_cfm(sdev, dev, skb);
goto err;
}
ndev_vif = netdev_priv(dev);
- SCSC_WLOG_PKTFATE_LOG_RX_DATA_FRAME(fapi_get_u16(skb, u.ma_unitdata_ind.data_unit_descriptor),
- fapi_get_data(skb), fapi_get_datalen(skb));
-
-#ifdef CONFIG_SCSC_WLAN_RX_NAPI
- slsi_rx_data_napi(sdev, dev, skb, false);
-#else
slsi_skb_work_enqueue(&ndev_vif->rx_data, skb);
-#endif
rcu_read_unlock();
return 0;
err:
return -EINVAL;
}
+#endif
static int sap_ma_rx_handler(struct slsi_dev *sdev, struct sk_buff *skb)
{
}
#endif
case MA_UNITDATA_CFM:
+#ifdef CONFIG_SCSC_WLAN_RX_NAPI
+ return slsi_rx_napi_process(sdev, skb);
+#else
return slsi_rx_queue_data(sdev, skb);
+#endif
case MA_BLOCKACK_IND:
/* It is anomolous to handle the MA_BLOCKACK_IND in the
* mlme wq.
/****************************************************************************
*
- * Copyright (c) 2014 - 2017 Samsung Electronics Co., Ltd. All rights reserved
+ * Copyright (c) 2014 - 2018 Samsung Electronics Co., Ltd. All rights reserved
*
****************************************************************************/
#include <linux/types.h>
#include "sap_mlme.h"
#include "hip.h"
#include "mgt.h"
+
+#ifdef CONFIG_ANDROID
#include "scsc_wifilogger_rings.h"
+#endif
#define SUPPORTED_OLD_VERSION 0
case MLME_RSSI_REPORT_IND:
slsi_rx_rssi_report_ind(sdev, dev, skb);
break;
+ case MLME_RANGE_IND:
+ slsi_rx_range_ind(sdev, dev, skb);
+ break;
+ case MLME_RANGE_DONE_IND:
+ slsi_rx_range_done_ind(sdev, dev, skb);
+ break;
+
#endif
#ifdef CONFIG_SCSC_WLAN_ENHANCED_LOGGING
case MLME_EVENT_LOG_IND:
slsi_rx_event_log_indication(sdev, dev, skb);
+ break;
#endif
+#ifdef CONFIG_SCSC_WLAN_GSCAN_ENABLE
case MLME_NAN_EVENT_IND:
slsi_nan_event(sdev, dev, skb);
+ slsi_kfree_skb(skb);
break;
case MLME_NAN_FOLLOWUP_IND:
slsi_nan_followup_ind(sdev, dev, skb);
+ slsi_kfree_skb(skb);
break;
case MLME_NAN_SERVICE_IND:
slsi_nan_service_ind(sdev, dev, skb);
+ slsi_kfree_skb(skb);
break;
+#endif
default:
slsi_kfree_skb(skb);
SLSI_NET_ERR(dev, "Unhandled Ind: 0x%.4x\n", id);
return 0;
if (fapi_is_ind(skb)) {
+#ifdef CONFIG_SCSC_WIFILOGGER
SCSC_WLOG_PKTFATE_LOG_RX_CTRL_FRAME(fapi_get_data(skb), fapi_get_datalen(skb));
+#endif
switch (fapi_get_sigid(skb)) {
case MLME_SCAN_DONE_IND:
case MLME_NAN_FOLLOWUP_IND:
case MLME_NAN_SERVICE_IND:
return slsi_rx_enqueue_netdev_mlme(sdev, skb, vif);
+ case MLME_RANGE_IND:
+ case MLME_RANGE_DONE_IND:
+ if (vif == 0)
+ return slsi_rx_enqueue_netdev_mlme(sdev, skb, SLSI_NET_INDEX_WLAN);
+ else
+ return slsi_rx_enqueue_netdev_mlme(sdev, skb, vif);
#endif
#ifdef CONFIG_SCSC_WLAN_ENHANCED_LOGGING
case MLME_EVENT_LOG_IND:
static int sap_test_rx_handler(struct slsi_dev *sdev, struct sk_buff *skb)
{
+ if (slsi_rx_blocking_signals(sdev, skb) == 0)
+ return 0;
+
SLSI_INFO_NODEV("TEST SAP not implemented\n");
/* Silently consume the skb */
slsi_kfree_skb(skb);
/* Check first the global domain */
if (sdev->hip4_inst.hip_priv->saturated) {
+#ifdef CONFIG_SCSC_DEBUG
SLSI_DBG4_NODEV(SLSI_WIFI_FCQ, "xxxxxxxxxxxxxxxxxxxxxxx Global domain. No space. active: %d vif: %d peer: %d ac: %d gcod (%d) gmod (%d) betx:%d berx:%d vitx:%d virx:%d votx:%d vorx:%d\n",
atomic_read(&sdev->hip4_inst.hip_priv->gactive), vif, peer_index, priority, atomic_read(&sdev->hip4_inst.hip_priv->gcod), atomic_read(&sdev->hip4_inst.hip_priv->gmod),
td[DIREC_TX][DOMAIN_G][0], td[DIREC_RX][DOMAIN_G][0], td[DIREC_TX][DOMAIN_G][2], td[DIREC_RX][DOMAIN_G][2], td[DIREC_TX][DOMAIN_G][3], td[DIREC_RX][DOMAIN_G][3]);
fcq_stop_all_queues(sdev);
+#endif
spin_unlock(&sdev->hip4_inst.hip_priv->gbot_lock);
return -ENOSPC;
}
if (!atomic_read(&sdev->hip4_inst.hip_priv->gactive) && sdev->hip4_inst.hip_priv->guard-- == 0) {
+#ifdef CONFIG_SCSC_DEBUG
SLSI_DBG4_NODEV(SLSI_WIFI_FCQ, "xxxxxxxxxxxxxxxxxxxxxxx Global domain. Saturating Gmod. active: %d vif: %d peer: %d ac: %d gcod (%d) gmod (%d) betx:%d berx:%d vitx:%d virx:%d votx:%d vorx:%d\n",
atomic_read(&sdev->hip4_inst.hip_priv->gactive), vif, peer_index, priority, atomic_read(&sdev->hip4_inst.hip_priv->gcod), atomic_read(&sdev->hip4_inst.hip_priv->gmod),
td[DIREC_TX][DOMAIN_G][0], td[DIREC_RX][DOMAIN_G][0], td[DIREC_TX][DOMAIN_G][2], td[DIREC_RX][DOMAIN_G][2], td[DIREC_TX][DOMAIN_G][3], td[DIREC_RX][DOMAIN_G][3]);
+#endif
sdev->hip4_inst.hip_priv->saturated = true;
}
gcod = atomic_inc_return(&sdev->hip4_inst.hip_priv->gcod);
#ifdef CONFIG_SCSC_DEBUG
fcq_update_counters(DIREC_TX, DOMAIN_G, priority);
-#endif
SLSI_DBG4_NODEV(SLSI_WIFI_FCQ, "tx: active: %d vif: %d peer: %d ac: %d gcod (%d) gmod (%d) betx:%d berx:%d vitx:%d virx:%d votx:%d vorx:%d\n",
atomic_read(&sdev->hip4_inst.hip_priv->gactive), vif, peer_index, priority, gcod, gmod,
td[DIREC_TX][DOMAIN_G][0], td[DIREC_RX][DOMAIN_G][0], td[DIREC_TX][DOMAIN_G][2], td[DIREC_RX][DOMAIN_G][2], td[DIREC_TX][DOMAIN_G][3], td[DIREC_RX][DOMAIN_G][3]);
+#endif
if (gcod >= (atomic_read(&sdev->hip4_inst.hip_priv->gmod) - STOP_GUARD_GMOD)) {
fcq_stop_all_queues(sdev);
if (atomic_read(&sdev->hip4_inst.hip_priv->gactive)) {
if (qs->saturated) {
int i;
+#ifdef CONFIG_SCSC_DEBUG
SLSI_DBG4_NODEV(SLSI_WIFI_FCQ, "xxxxxxxxxxxxxxxxxxxxxxx Smod domain. No space. active %d vif: %d peer: %d ac: %d scod (%d) smod (%d) betx:%d berx:%d vitx:%d virx:%d votx:%d vorx:%d\n",
atomic_read(&qs->active), vif, peer_index, priority, atomic_read(&qs->scod), atomic_read(&qs->smod),
td[DIREC_TX][DOMAIN_S][0], td[DIREC_RX][DOMAIN_S][0], td[DIREC_TX][DOMAIN_S][2], td[DIREC_RX][DOMAIN_S][2], td[DIREC_TX][DOMAIN_S][3], td[DIREC_RX][DOMAIN_S][3]);
+#endif
/* Close subqueues again */
for (i = 0; i < SLSI_NETIF_Q_PER_PEER; i++)
}
/* Pass the frame until reaching the actual saturation */
if (!atomic_read(&qs->active) && (qs->guard-- == 0)) {
+#ifdef CONFIG_SCSC_DEBUG
SLSI_DBG4_NODEV(SLSI_WIFI_FCQ, "xxxxxxxxxxxxxxxxxxxxxxx Smod domain. Going into Saturation. active %d vif: %d peer: %d ac: %d scod (%d) smod (%d) betx:%d berx:%d vitx:%d virx:%d votx:%d vorx:%d\n",
atomic_read(&qs->active), vif, peer_index, priority, atomic_read(&qs->scod), atomic_read(&qs->smod),
td[DIREC_TX][DOMAIN_S][0], td[DIREC_RX][DOMAIN_S][0], td[DIREC_TX][DOMAIN_S][2], td[DIREC_RX][DOMAIN_S][2], td[DIREC_TX][DOMAIN_S][3], td[DIREC_RX][DOMAIN_S][3]);
+#endif
qs->saturated = true;
}
scod = atomic_inc_return(&qs->scod);
SCSC_HIP4_SAMPLER_BOT_TX(sdev->minor_prof, scod, atomic_read(&qs->smod), priority << 6 | (peer_index & 0xf) << 2 | vif);
#ifdef CONFIG_SCSC_DEBUG
fcq_update_counters(DIREC_TX, DOMAIN_S, priority);
-#endif
SLSI_DBG4_NODEV(SLSI_WIFI_FCQ, "tx: active: %d vif: %d peer: %d ac: %d scod (%d) smod (%d) betx:%d berx:%d vitx:%d virx:%d votx:%d vorx:%d\n",
atomic_read(&qs->active), vif, peer_index, priority, atomic_read(&qs->scod), atomic_read(&qs->smod),
td[DIREC_TX][DOMAIN_S][0], td[DIREC_RX][DOMAIN_S][0], td[DIREC_TX][DOMAIN_S][2], td[DIREC_RX][DOMAIN_S][2], td[DIREC_TX][DOMAIN_S][3], td[DIREC_RX][DOMAIN_S][3]);
+#endif
if (scod >= (atomic_read(&qs->smod) - STOP_GUARD_SMOD)) {
int i;
#ifdef EXPERIMENTAL_DYNAMIC_SMOD_ADAPTATION
SCSC_HIP4_SAMPLER_BOT_QMOD_TX(sdev->minor_prof, qcod, atomic_read(&queue->qmod), priority << 6 | (peer_index & 0xf) << 2 | vif);
#ifdef CONFIG_SCSC_DEBUG
fcq_update_counters(DIREC_TX, DOMAIN_Q, priority);
-#endif
SLSI_DBG4_NODEV(SLSI_WIFI_FCQ, "tx: active: %d vif: %d peer: %d ac: %d qcod (%d) qmod (%d) betx:%d berx:%d vitx:%d virx:%d votx:%d vorx:%d\n",
atomic_read(&queue->active), vif, peer_index, priority, atomic_read(&queue->qcod), atomic_read(&queue->qmod),
td[DIREC_TX][DOMAIN_Q][0], td[DIREC_RX][DOMAIN_Q][0], td[DIREC_TX][DOMAIN_Q][2], td[DIREC_RX][DOMAIN_Q][2], td[DIREC_TX][DOMAIN_Q][3], td[DIREC_RX][DOMAIN_Q][3]);
+#endif
if (atomic_read(&queue->active) && qcod >= (atomic_read(&queue->qmod) - STOP_GUARD_QMOD)) {
/* Before closing check whether we could get slots from non used queues */
#ifdef EXPERIMENTAL_DYNAMIC_SMOD_ADAPTATION
#ifdef CONFIG_SCSC_DEBUG
fcq_update_counters(DIREC_RX, DOMAIN_G, priority);
-#endif
SLSI_DBG4_NODEV(SLSI_WIFI_FCQ, "rx: active: %d vif: %d peer: %d ac: %d gcod (%d) gmod (%d) betx:%d berx:%d vitx:%d virx:%d votx:%d vorx:%d %s\n",
gactive, vif, peer_index, priority, gcod, gmod,
td[DIREC_TX][DOMAIN_G][0], td[DIREC_RX][DOMAIN_G][0], td[DIREC_TX][DOMAIN_G][2], td[DIREC_RX][DOMAIN_G][2], td[DIREC_TX][DOMAIN_G][3], td[DIREC_RX][DOMAIN_G][3], qs ? "" : "NO PEER");
+#endif
if (!is_gmod_active(sdev) && (gcod + SCSC_WIFI_FCQ_GMOD_RESUME_HYSTERESIS / total < gmod)) {
SLSI_DBG4_NODEV(SLSI_WIFI_FCQ, "Global Queues Started. gcod (%d) < gmod (%d)\n", gcod, gmod);
#ifdef CONFIG_SCSC_DEBUG
fcq_update_counters(DIREC_RX, DOMAIN_S, priority);
-#endif
SLSI_DBG4_NODEV(SLSI_WIFI_FCQ, "rx: active: %d vif: %d peer: %d ac: %d scod (%d) smod (%d) betx:%d berx:%d vitx:%d virx:%d votx:%d vorx:%d\n",
atomic_read(&qs->active), vif, peer_index, priority, atomic_read(&qs->scod), atomic_read(&qs->smod),
td[DIREC_TX][DOMAIN_S][0], td[DIREC_RX][DOMAIN_S][0], td[DIREC_TX][DOMAIN_S][2], td[DIREC_RX][DOMAIN_S][2], td[DIREC_TX][DOMAIN_S][3], td[DIREC_RX][DOMAIN_S][3]);
+#endif
/* Only support a maximum of 16 peers!!!!!!*/
SCSC_HIP4_SAMPLER_BOT_RX(sdev->minor_prof, scod, atomic_read(&qs->smod), priority << 6 | (peer_index & 0xf) << 2 | vif);
if (!is_smod_active(qs) && (scod + SCSC_WIFI_FCQ_SMOD_RESUME_HYSTERESIS / total < atomic_read(&qs->smod))) {
#ifdef CONFIG_SCSC_DEBUG
fcq_update_counters(DIREC_RX, DOMAIN_Q, priority);
-#endif
SLSI_DBG4_NODEV(SLSI_WIFI_FCQ, "rx: active: %d vif: %d peer: %d ac: %d qcod (%d) qmod (%d) betx:%d berx:%d vitx:%d virx:%d votx:%d vorx:%d\n",
atomic_read(&queue->active), vif, peer_index, priority, atomic_read(&queue->qcod), atomic_read(&queue->qmod),
td[DIREC_TX][DOMAIN_Q][0], td[DIREC_RX][DOMAIN_Q][0], td[DIREC_TX][DOMAIN_Q][2], td[DIREC_RX][DOMAIN_Q][2], td[DIREC_TX][DOMAIN_Q][3], td[DIREC_RX][DOMAIN_Q][3]);
+#endif
SCSC_HIP4_SAMPLER_BOT_QMOD_RX(sdev->minor_prof, qcod, atomic_read(&queue->qmod), priority << 6 | (peer_index & 0xf) << 2 | vif);
if (!is_qmod_active(&qs->ac_q[priority]) && ((qcod + SCSC_WIFI_FCQ_QMOD_RESUME_HYSTERESIS / total) < atomic_read(&queue->qmod))) {
SLSI_MUTEX_UNLOCK(ndev_vif->vif_mutex);
return -EFAULT;
}
+ peer->qos_enabled = true;
slsi_ps_port_control(sdev, dev, peer, SLSI_STA_CONN_STATE_CONNECTED);
netif_carrier_on(dev);
SLSI_MUTEX_UNLOCK(ndev_vif->vif_mutex);
$(CONFIG_SCSC_WLAN_MODULE)-y += ../cac.o
$(CONFIG_SCSC_WLAN_MODULE)-y += ../ioctl.o
$(CONFIG_SCSC_WLAN_MODULE)-y += ../wakelock.o
-
+$(CONFIG_SCSC_WLAN_MODULE)-y += ../traffic_monitor.o
# enable GSCAN
ifeq ($(CONFIG_SCSC_WLAN_GSCAN_ENABLE),y)
$(CONFIG_SCSC_WLAN_MODULE)-y += ../nl80211_vendor.o
}
}
+#if KERNEL_VERSION(4, 15, 0) <= LINUX_VERSION_CODE
+static void traffic_mon_timer(struct timer_list *t)
+#else
static void traffic_mon_timer(unsigned long data)
+#endif
{
+#if KERNEL_VERSION(4, 15, 0) <= LINUX_VERSION_CODE
+ struct slsi_traffic_mon_clients *clients = from_timer(clients, t, timer);
+ struct slsi_dev *sdev = container_of(clients, typeof(*sdev), traffic_mon_clients);
+#else
struct slsi_dev *sdev = (struct slsi_dev *)data;
+#endif
struct net_device *dev;
struct netdev_vif *ndev_vif;
bool stop_monitor;
SLSI_ERR_NODEV("invalid sdev\n");
return;
}
-
+#if KERNEL_VERSION(4, 15, 0) <= LINUX_VERSION_CODE
+ timer_setup(&sdev->traffic_mon_clients.timer, traffic_mon_timer, 0);
+#else
setup_timer(&sdev->traffic_mon_clients.timer, traffic_mon_timer, (unsigned long)sdev);
+#endif
INIT_LIST_HEAD(&sdev->traffic_mon_clients.client_list);
spin_lock_init(&sdev->traffic_mon_clients.lock);
}
module_param(msdu_enable, bool, S_IRUGO | S_IWUSR);
MODULE_PARM_DESC(msdu_enable, "MSDU frame format, Y: enable (default), N: disable");
+#ifdef CONFIG_ANDROID
#include "scsc_wifilogger_rings.h"
+#endif
/**
* Needed to get HIP4_DAT)SLOTS...should be part
cb->colour = (slsi_frame_priority_to_ac_queue(skb->priority) << 8) |
(fapi_get_u16(skb, u.ma_unitdata_req.peer_index) << 3) | ndev_vif->ifnum << 1;
+#ifdef CONFIG_SCSC_WIFILOGGER
/* Log only the linear skb chunk ... unidata anywya will be truncated to 100.*/
SCSC_WLOG_PKTFATE_LOG_TX_DATA_FRAME(fapi_get_u16(skb, u.ma_unitdata_req.host_tag),
skb->data, skb_headlen(skb));
+#endif
/* ACCESS POINT MODE */
if (ndev_vif->vif_type == FAPI_VIFTYPE_AP) {
hdr = (struct fapi_signal_header *)skb->data;
hdr->fw_reference = 0;
+#ifdef CONFIG_SCSC_WIFILOGGER
/* Log only the linear skb chunk */
SCSC_WLOG_PKTFATE_LOG_TX_CTRL_FRAME(fapi_get_u16(skb, u.mlme_frame_transmission_ind.host_tag),
skb->data, skb_headlen(skb));
+#endif
slsi_debug_frame(sdev, dev, skb, "TX");
res = scsc_wifi_transmit_frame(&sdev->hip4_inst, true, skb);
#include <linux/workqueue.h>
#include <linux/skbuff.h>
#include <net/cfg80211.h>
-#include <netif.h>
+#include "netif.h"
#include "wakelock.h"
#ifdef CONFIG_SCSC_SMAPPER
struct slsi_skb_cb {
uint8_t cte_type;
uint8_t slot_durations;
uint8_t sample_count;
- uint16_t reserved;
+ uint16_t event_count;
uint8_t data[BSMHCP_IQ_REPORT_BUFFER_SIZE];
};
#define SCSC_NDEV_2_DEV(ndev) \
((ndev) ? SCSC_SDEV_2_DEV(((struct netdev_vif *)netdev_priv(ndev))->sdev) : NULL)
-#define SCSC_TAG_FMT(tag, fmt) "[" # tag "]: %-5s: - %s: "fmt
-#define SCSC_TAG_DBG_FMT(tag, fmt) "[" # tag "]: %s: "fmt
-#define SCSC_DEV_FMT(fmt) "%-5s: - %s: "fmt
-#define SCSC_DBG_FMT(fmt) "%s: "fmt
+#define SCSC_PREFIX "wlbt: " /* prepended to log statements */
+
+#define SCSC_TAG_FMT(tag, fmt) SCSC_PREFIX"[" # tag "]: %-5s: - %s: "fmt
+#define SCSC_TAG_DBG_FMT(tag, fmt) SCSC_PREFIX"[" # tag "]: %s: "fmt
+#define SCSC_DEV_FMT(fmt) SCSC_PREFIX"%-5s: - %s: "fmt
+#define SCSC_DBG_FMT(fmt) SCSC_PREFIX"%s: "fmt
+
+int scsc_logring_enable(bool logging_enable);
#ifdef CONFIG_SCSC_PRINTK
(start), (len))
#define SCSC_EMERG_FF(args ...) scsc_printk_tag(FORCE_PRK, WLBT, \
- KERN_EMERG args)
+ KERN_EMERG SCSC_PREFIX args)
#define SCSC_ALERT_FF(args ...) scsc_printk_tag(FORCE_PRK, WLBT, \
- KERN_ALERT args)
+ KERN_ALERT SCSC_PREFIX args)
#define SCSC_CRIT_FF(args ...) scsc_printk_tag(FORCE_PRK, WLBT, \
- KERN_CRIT args)
+ KERN_CRIT SCSC_PREFIX args)
#define SCSC_ERR_FF(args ...) scsc_printk_tag(FORCE_PRK, WLBT, \
- KERN_ERR args)
+ KERN_ERR SCSC_PREFIX args)
#define SCSC_WARNING_FF(args ...) scsc_printk_tag(FORCE_PRK, WLBT, \
- KERN_WARNING args)
+ KERN_WARNING SCSC_PREFIX args)
#define SCSC_NOTICE_FF(args ...) scsc_printk_tag(FORCE_PRK, WLBT, \
- KERN_NOTICE args)
+ KERN_NOTICE SCSC_PREFIX args)
#define SCSC_INFO_FF(args ...) scsc_printk_tag(FORCE_PRK, WLBT, \
- KERN_INFO args)
+ KERN_INFO SCSC_PREFIX args)
#define SCSC_DEBUG_FF(args ...) scsc_printk_tag(FORCE_PRK, WLBT, \
- KERN_DEBUG args)
+ KERN_DEBUG SCSC_PREFIX args)
#define SCSC_TAG_EMERG_FF(tag, args ...) scsc_printk_tag(FORCE_PRK, (tag), \
- KERN_EMERG args)
+ KERN_EMERG SCSC_PREFIX args)
#define SCSC_TAG_ALERT_FF(tag, args ...) scsc_printk_tag(FORCE_PRK, (tag), \
- KERN_ALERT args)
+ KERN_ALERT SCSC_PREFIX args)
#define SCSC_TAG_CRIT_FF(tag, args ...) scsc_printk_tag(FORCE_PRK, (tag), \
- KERN_CRIT args)
+ KERN_CRIT SCSC_PREFIX args)
#define SCSC_TAG_ERR_FF(tag, args ...) scsc_printk_tag(FORCE_PRK, (tag), \
- KERN_ERR args)
+ KERN_ERR SCSC_PREFIX args)
#define SCSC_TAG_WARNING_FF(tag, args ...) scsc_printk_tag(FORCE_PRK, (tag), \
- KERN_WARNING args)
+ KERN_WARNING SCSC_PREFIX args)
#define SCSC_TAG_NOTICE_FF(tag, args ...) scsc_printk_tag(FORCE_PRK, (tag), \
- KERN_NOTICE args)
+ KERN_NOTICE SCSC_PREFIX args)
#define SCSC_TAG_INFO_FF(tag, args ...) scsc_printk_tag(FORCE_PRK, (tag), \
- KERN_INFO args)
+ KERN_INFO SCSC_PREFIX args)
#define SCSC_TAG_DEBUG_FF(tag, args ...) scsc_printk_tag(FORCE_PRK, (tag), \
- KERN_DEBUG args)
+ KERN_DEBUG SCSC_PREFIX args)
#define SCSC_BIN_EMERG_FF(start, len) scsc_printk_bin(FORCE_PRK, 0, \
(start), (len))
dev_printk_emit((lvl), (dev), fmt, ## args);\
} while (0)
-#define SCSC_PRINTK(fmt, args ...) printk(fmt, ## args)
-#define SCSC_PRINTK_TAG(tag, fmt, args ...) printk("[" # tag "] "fmt, ## args)
+#define SCSC_PRINTK(fmt, args ...) printk(SCSC_PREFIX fmt, ## args)
+#define SCSC_PRINTK_TAG(tag, fmt, args ...) printk(SCSC_PREFIX "[" # tag "] "fmt, ## args)
#define SCSC_PRINTK_BIN(start, len) print_hex_dump(KERN_INFO, \
- "[BINARY]->|", \
+ SCSC_PREFIX"[BINARY]->|", \
DUMP_PREFIX_ADDRESS, \
16, 4, start, \
len, true)
-#define SCSC_PRINTK_FF(fmt, args ...) printk(fmt, ## args)
-#define SCSC_PRINTK_TAG_FF(tag, fmt, args ...) printk("[" # tag "] "fmt, ## args)
+#define SCSC_PRINTK_FF(fmt, args ...) printk(SCSC_PREFIX fmt, ## args)
+#define SCSC_PRINTK_TAG_FF(tag, fmt, args ...) printk(SCSC_PREFIX"[" # tag "] "fmt, ## args)
#define SCSC_PRINTK_BIN_FF(start, len) print_hex_dump(KERN_INFO, \
- "[BINARY]->|", \
+ SCSC_PREFIX"[BINARY]->|", \
DUMP_PREFIX_ADDRESS, \
16, 4, start, \
len, true)
#define SCSC_BIN_EMERG(start, len) print_hex_dump(KERN_EMERG, \
- "[BINARY]->|", \
+ SCSC_PREFIX"[BINARY]->|", \
DUMP_PREFIX_ADDRESS, \
16, 4, start, \
len, true)
#define SCSC_BIN_ALERT(start, len) print_hex_dump(KERN_ALERT, \
- "[BINARY]->|", \
+ SCSC_PREFIX"[BINARY]->|", \
DUMP_PREFIX_ADDRESS, \
16, 4, start, \
len, true)
#define SCSC_BIN_CRIT(start, len) print_hex_dump(KERN_CRIT, \
- "[BINARY]->|", \
+ SCSC_PREFIX"[BINARY]->|", \
DUMP_PREFIX_ADDRESS, \
16, 4, start, \
len, true)
#define SCSC_BIN_ERR(start, len) print_hex_dump(KERN_ERR, \
- "[BINARY]->|", \
+ SCSC_PREFIX"[BINARY]->|", \
DUMP_PREFIX_ADDRESS, \
16, 4, start, \
len, true)
#define SCSC_BIN_WARNING(start, len) print_hex_dump(KERN_WARNING, \
- "[BINARY]->|", \
+ SCSC_PREFIX"[BINARY]->|", \
DUMP_PREFIX_ADDRESS, \
16, 4, start, \
len, true)
#define SCSC_BIN_NOTICE(start, len) print_hex_dump(KERN_NOTICE, \
- "[BINARY]->|", \
+ SCSC_PREFIX"[BINARY]->|", \
DUMP_PREFIX_ADDRESS, \
16, 4, start, \
len, true)
#define SCSC_BIN_INFO(start, len) print_hex_dump(KERN_INFO, \
- "[BINARY]->|", \
+ SCSC_PREFIX"[BINARY]->|", \
DUMP_PREFIX_ADDRESS, \
16, 4, start, \
len, true)
#define SCSC_BIN_TAG_EMERG(tag, start, len) print_hex_dump(KERN_EMERG, \
- "[" # tag "]->|", \
+ SCSC_PREFIX"[" # tag "]->|", \
DUMP_PREFIX_ADDRESS, \
16, 4, start, \
len, true)
#define SCSC_BIN_TAG_ALERT(tag, start, len) print_hex_dump(KERN_ALERT, \
- "[" # tag "]->|", \
+ SCSC_PREFIX"[" # tag "]->|", \
DUMP_PREFIX_ADDRESS, \
16, 4, start, \
len, true)
#define SCSC_BIN_TAG_CRIT(tag, start, len) print_hex_dump(KERN_CRIT, \
- "[" # tag "]->|", \
+ SCSC_PREFIX"[" # tag "]->|", \
DUMP_PREFIX_ADDRESS, \
16, 4, start, \
len, true)
#define SCSC_BIN_TAG_ERR(tag, start, len) print_hex_dump(KERN_ERR, \
- "[" # tag "]->|", \
+ SCSC_PREFIX"[" # tag "]->|", \
DUMP_PREFIX_ADDRESS, \
16, 4, start, \
len, true)
#define SCSC_BIN_TAG_WARNING(tag, start, len) print_hex_dump(KERN_WARNING, \
- "[" # tag "]->|", \
+ SCSC_PREFIX"[" # tag "]->|", \
DUMP_PREFIX_ADDRESS, \
16, 4, start, \
len, true)
#define SCSC_BIN_TAG_NOTICE(tag, start, len) print_hex_dump(KERN_NOTICE, \
- "[" # tag "]->|", \
+ SCSC_PREFIX"[" # tag "]->|", \
DUMP_PREFIX_ADDRESS, \
16, 4, start, \
len, true)
#define SCSC_BIN_TAG_INFO(tag, start, len) print_hex_dump(KERN_INFO, \
- "[" # tag "]->|", \
+ SCSC_PREFIX"[" # tag "]->|", \
DUMP_PREFIX_NONE, \
16, 1, start, \
len, false)
#define SCSC_BIN_TAG_DEBUG(tag, start, len) do {} while (0)
-#define SCSC_EMERG_FF(args ...) pr_emerg(args)
-#define SCSC_ALERT_FF(args ...) pr_alert(args)
-#define SCSC_CRIT_FF(args ...) pr_crit(args)
-#define SCSC_ERR_FF(args ...) pr_err(args)
-#define SCSC_WARNING_FF(args ...) pr_warn(args)
-#define SCSC_NOTICE_FF(args ...) pr_notice(args)
-#define SCSC_INFO_FF(args ...) pr_info(args)
+#define SCSC_EMERG_FF(args ...) pr_emerg(SCSC_PREFIX args)
+#define SCSC_ALERT_FF(args ...) pr_alert(SCSC_PREFIX args)
+#define SCSC_CRIT_FF(args ...) pr_crit(SCSC_PREFIX args)
+#define SCSC_ERR_FF(args ...) pr_err(SCSC_PREFIX args)
+#define SCSC_WARNING_FF(args ...) pr_warn(SCSC_PREFIX args)
+#define SCSC_NOTICE_FF(args ...) pr_notice(SCSC_PREFIX args)
+#define SCSC_INFO_FF(args ...) pr_info(SCSC_PREFIX args)
#define SCSC_DEBUG_FF(args ...) do {} while (0)
#define SCSC_TAG_DEBUG_FF(tag, fmt, args ...) do {} while (0)
#define SCSC_BIN_EMERG_FF(start, len) print_hex_dump(KERN_EMERG, \
- "[BINARY]->|", \
+ SCSC_PREFIX"[BINARY]->|", \
DUMP_PREFIX_ADDRESS, \
16, 4, start, \
len, true)
#define SCSC_BIN_ALERT_FF(start, len) print_hex_dump(KERN_ALERT, \
- "[BINARY]->|", \
+ SCSC_PREFIX"[BINARY]->|", \
DUMP_PREFIX_ADDRESS, \
16, 4, start, \
len, true)
#define SCSC_BIN_CRIT_FF(start, len) print_hex_dump(KERN_CRIT, \
- "[BINARY]->|", \
+ SCSC_PREFIX"[BINARY]->|", \
DUMP_PREFIX_ADDRESS, \
16, 4, start, \
len, true)
#define SCSC_BIN_ERR_FF(start, len) print_hex_dump(KERN_ERR, \
- "[BINARY]->|", \
+ SCSC_PREFIX"[BINARY]->|", \
DUMP_PREFIX_ADDRESS, \
16, 4, start, \
len, true)
#define SCSC_BIN_WARNING_FF(start, len) print_hex_dump(KERN_WARNING, \
- "[BINARY]->|", \
+ SCSC_PREFIX"[BINARY]->|", \
DUMP_PREFIX_ADDRESS, \
16, 4, start, \
len, true)
#define SCSC_BIN_NOTICE_FF(start, len) print_hex_dump(KERN_NOTICE, \
- "[BINARY]->|", \
+ SCSC_PREFIX"[BINARY]->|", \
DUMP_PREFIX_ADDRESS, \
16, 4, start, \
len, true)
#define SCSC_BIN_INFO_FF(start, len) print_hex_dump(KERN_INFO, \
- "[BINARY]->|", \
+ SCSC_PREFIX"[BINARY]->|", \
DUMP_PREFIX_ADDRESS, \
16, 4, start, \
len, true)
SCSC_SERVICE_ID_INVALID = 0xff,
};
+#ifdef CONFIG_SCSC_QOS
#define SCSC_SERVICE_TOTAL 9
+#endif
enum scsc_module_client_reason {
SCSC_MODULE_CLIENT_REASON_HW_PROBE = 0,
SCSC_MODULE_CLIENT_REASON_INVALID = 0xff,
};
+#ifdef CONFIG_SCSC_QOS
enum scsc_qos_config {
SCSC_QOS_DISABLED = 0,
SCSC_QOS_MIN = 1,
SCSC_QOS_MED = 2,
SCSC_QOS_MAX = 3,
};
-/* Core Driver Module registration */
+#endif
+/* Core Driver Module registration */
struct scsc_mx_module_client {
char *name;
void (*probe)(struct scsc_mx_module_client *module_client, struct scsc_mx *mx, enum scsc_module_client_reason reason);
/* Same as scsc_mx_service_mifram_alloc but allows to specify flags (MIFRAMMAN_MEM_POOL_XX).
* So, for example, to allocate memory from the logging pool use MIFRAMMAN_MEM_POOL_LOGGING. */
int scsc_mx_service_mifram_alloc_extended(struct scsc_service *service, size_t nbytes, scsc_mifram_ref *ref, u32 align, uint32_t flags);
+struct scsc_bt_audio_abox *scsc_mx_service_get_bt_audio_abox(struct scsc_service *service);
+struct mifabox *scsc_mx_service_get_aboxram(struct scsc_service *service);
/** Free a contiguous block of SDRAM */
void scsc_mx_service_mifram_free(struct scsc_service *service, scsc_mifram_ref ref);
void scsc_mx_service_mifram_free_extended(struct scsc_service *service, scsc_mifram_ref ref, uint32_t flags);
* but this may change in future.
*/
struct device *scsc_service_get_device(struct scsc_service *service);
+struct device *scsc_service_get_device_by_mx(struct scsc_mx *mx);
int scsc_service_force_panic(struct scsc_service *service);
u16 scsc_service_get_alignment(struct scsc_service *service);
#endif
+#ifdef CONFIG_SCSC_QOS
int scsc_service_pm_qos_add_request(struct scsc_service *service, enum scsc_qos_config config);
int scsc_service_pm_qos_update_request(struct scsc_service *service, enum scsc_qos_config config);
int scsc_service_pm_qos_remove_request(struct scsc_service *service);
+#endif
/* MXLOGGER API */
/* If there is no service/mxman associated, register the observer as global (will affect all the mx instanes)*/
#define SCSC_RELEASE_SOLUTION "mx250"
#define SCSC_RELEASE_PRODUCT 6
-#define SCSC_RELEASE_ITERATION 51
+#define SCSC_RELEASE_ITERATION 57
#define SCSC_RELEASE_CANDIDATE 0
#define SCSC_RELEASE_POINT 0