1*5113495bSYour Name /*
2*5113495bSYour Name * Copyright (c) 2011,2017-2021 The Linux Foundation. All rights reserved.
3*5113495bSYour Name * Copyright (c) 2022-2023 Qualcomm Innovation Center, Inc. All rights reserved.
4*5113495bSYour Name *
5*5113495bSYour Name *
6*5113495bSYour Name * Permission to use, copy, modify, and/or distribute this software for
7*5113495bSYour Name * any purpose with or without fee is hereby granted, provided that the
8*5113495bSYour Name * above copyright notice and this permission notice appear in all
9*5113495bSYour Name * copies.
10*5113495bSYour Name *
11*5113495bSYour Name * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL
12*5113495bSYour Name * WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED
13*5113495bSYour Name * WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE
14*5113495bSYour Name * AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL
15*5113495bSYour Name * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
16*5113495bSYour Name * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
17*5113495bSYour Name * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
18*5113495bSYour Name * PERFORMANCE OF THIS SOFTWARE.
19*5113495bSYour Name */
20*5113495bSYour Name
21*5113495bSYour Name #include <qdf_types.h>
22*5113495bSYour Name #include "wlan_dfs_ioctl.h"
23*5113495bSYour Name #include <spectral_ioctl.h>
24*5113495bSYour Name
25*5113495bSYour Name #ifndef __KERNEL__
26*5113495bSYour Name #include <math.h>
27*5113495bSYour Name #endif /* __KERNEL__ */
28*5113495bSYour Name
29*5113495bSYour Name #ifndef _WLAN_SPECTRAL_PUBLIC_STRUCTS_H_
30*5113495bSYour Name #define _WLAN_SPECTRAL_PUBLIC_STRUCTS_H_
31*5113495bSYour Name
32*5113495bSYour Name #ifndef AH_MAX_CHAINS
33*5113495bSYour Name #define AH_MAX_CHAINS 3
34*5113495bSYour Name #endif
35*5113495bSYour Name
36*5113495bSYour Name #define MAX_NUM_CHANNELS 255
37*5113495bSYour Name #define SPECTRAL_PHYERR_PARAM_NOVAL 65535
38*5113495bSYour Name
39*5113495bSYour Name #ifdef SPECTRAL_USE_EMU_DEFAULTS
40*5113495bSYour Name /* Use defaults from emulation */
41*5113495bSYour Name #define SPECTRAL_SCAN_ACTIVE_DEFAULT (0x0)
42*5113495bSYour Name #define SPECTRAL_SCAN_ENABLE_DEFAULT (0x0)
43*5113495bSYour Name #define SPECTRAL_SCAN_COUNT_DEFAULT (0x0)
44*5113495bSYour Name #define SPECTRAL_SCAN_PERIOD_DEFAULT (250)
45*5113495bSYour Name #define SPECTRAL_SCAN_PRIORITY_DEFAULT (0x1)
46*5113495bSYour Name #define SPECTRAL_SCAN_FFT_SIZE_DEFAULT (0x7)
47*5113495bSYour Name #define SPECTRAL_SCAN_GC_ENA_DEFAULT (0x1)
48*5113495bSYour Name #define SPECTRAL_SCAN_RESTART_ENA_DEFAULT (0x0)
49*5113495bSYour Name #define SPECTRAL_SCAN_NOISE_FLOOR_REF_DEFAULT (0xa0)
50*5113495bSYour Name #define SPECTRAL_SCAN_INIT_DELAY_DEFAULT (0x50)
51*5113495bSYour Name #define SPECTRAL_SCAN_NB_TONE_THR_DEFAULT (0xc)
52*5113495bSYour Name #define SPECTRAL_SCAN_STR_BIN_THR_DEFAULT (0x7)
53*5113495bSYour Name #define SPECTRAL_SCAN_WB_RPT_MODE_DEFAULT (0x0)
54*5113495bSYour Name #define SPECTRAL_SCAN_RSSI_RPT_MODE_DEFAULT (0x1)
55*5113495bSYour Name #define SPECTRAL_SCAN_RSSI_THR_DEFAULT (0xf)
56*5113495bSYour Name #define SPECTRAL_SCAN_PWR_FORMAT_DEFAULT (0x1)
57*5113495bSYour Name #define SPECTRAL_SCAN_RPT_MODE_DEFAULT (0x2)
58*5113495bSYour Name #define SPECTRAL_SCAN_BIN_SCALE_DEFAULT (0x1)
59*5113495bSYour Name #define SPECTRAL_SCAN_DBM_ADJ_DEFAULT (0x0)
60*5113495bSYour Name #define SPECTRAL_SCAN_CHN_MASK_DEFAULT (0x1)
61*5113495bSYour Name #else
62*5113495bSYour Name /*
63*5113495bSYour Name * Static default values for spectral state and configuration.
64*5113495bSYour Name * These definitions should be treated as temporary. Ideally,
65*5113495bSYour Name * we should get the defaults from firmware - this will be discussed.
66*5113495bSYour Name *
67*5113495bSYour Name * Use defaults from Spectral Hardware Micro-Architecture
68*5113495bSYour Name * document (v1.0)
69*5113495bSYour Name */
70*5113495bSYour Name #define SPECTRAL_SCAN_ACTIVE_DEFAULT (0)
71*5113495bSYour Name #define SPECTRAL_SCAN_ENABLE_DEFAULT (0)
72*5113495bSYour Name #define SPECTRAL_SCAN_COUNT_DEFAULT (0)
73*5113495bSYour Name #define SPECTRAL_SCAN_PERIOD_GEN_I_DEFAULT (35)
74*5113495bSYour Name #define SPECTRAL_SCAN_PERIOD_GEN_II_DEFAULT (35)
75*5113495bSYour Name #define SPECTRAL_SCAN_PERIOD_GEN_III_DEFAULT (224)
76*5113495bSYour Name #define SPECTRAL_SCAN_PRIORITY_DEFAULT (1)
77*5113495bSYour Name #define SPECTRAL_SCAN_FFT_SIZE_DEFAULT (7)
78*5113495bSYour Name #define SPECTRAL_SCAN_GC_ENA_DEFAULT (1)
79*5113495bSYour Name #define SPECTRAL_SCAN_RESTART_ENA_DEFAULT (0)
80*5113495bSYour Name #define SPECTRAL_SCAN_NOISE_FLOOR_REF_DEFAULT (-96)
81*5113495bSYour Name #define SPECTRAL_SCAN_INIT_DELAY_DEFAULT (80)
82*5113495bSYour Name #define SPECTRAL_SCAN_NB_TONE_THR_DEFAULT (12)
83*5113495bSYour Name #define SPECTRAL_SCAN_STR_BIN_THR_DEFAULT (8)
84*5113495bSYour Name #define SPECTRAL_SCAN_WB_RPT_MODE_DEFAULT (0)
85*5113495bSYour Name #define SPECTRAL_SCAN_RSSI_RPT_MODE_DEFAULT (0)
86*5113495bSYour Name #define SPECTRAL_SCAN_RSSI_THR_DEFAULT (0xf0)
87*5113495bSYour Name #define SPECTRAL_SCAN_PWR_FORMAT_DEFAULT (0)
88*5113495bSYour Name #define SPECTRAL_SCAN_RPT_MODE_DEFAULT (2)
89*5113495bSYour Name #define SPECTRAL_SCAN_BIN_SCALE_DEFAULT (1)
90*5113495bSYour Name #define SPECTRAL_SCAN_DBM_ADJ_DEFAULT (1)
91*5113495bSYour Name #define SPECTRAL_SCAN_CHN_MASK_DEFAULT (1)
92*5113495bSYour Name #define SPECTRAL_SCAN_FREQUENCY_DEFAULT (0)
93*5113495bSYour Name #define SPECTRAL_FFT_RECAPTURE_DEFAULT (0)
94*5113495bSYour Name #endif /* SPECTRAL_USE_EMU_DEFAULTS */
95*5113495bSYour Name
96*5113495bSYour Name /* The below two definitions apply only to pre-11ac chipsets */
97*5113495bSYour Name #define SPECTRAL_SCAN_SHORT_REPORT_DEFAULT (1)
98*5113495bSYour Name #define SPECTRAL_SCAN_FFT_PERIOD_DEFAULT (1)
99*5113495bSYour Name
100*5113495bSYour Name /*
101*5113495bSYour Name * Definitions to help in scaling of gen3 linear format Spectral bins to values
102*5113495bSYour Name * similar to those from gen2 chipsets.
103*5113495bSYour Name */
104*5113495bSYour Name
105*5113495bSYour Name /*
106*5113495bSYour Name * Max gain for QCA9984. Since this chipset is a prime representative of gen2
107*5113495bSYour Name * chipsets, it is chosen for this value.
108*5113495bSYour Name */
109*5113495bSYour Name #define SPECTRAL_QCA9984_MAX_GAIN (78)
110*5113495bSYour Name
111*5113495bSYour Name /* Temporary section for hard-coded values. These need to come from FW. */
112*5113495bSYour Name
113*5113495bSYour Name /* Max gain for IPQ8074 */
114*5113495bSYour Name #define SPECTRAL_IPQ8074_DEFAULT_MAX_GAIN_HARDCODE (62)
115*5113495bSYour Name
116*5113495bSYour Name /*
117*5113495bSYour Name * Section for values needing tuning per customer platform. These too may need
118*5113495bSYour Name * to come from FW. To be considered as hard-coded for now.
119*5113495bSYour Name */
120*5113495bSYour Name
121*5113495bSYour Name /*
122*5113495bSYour Name * If customers have a different gain line up than QCA reference designs for
123*5113495bSYour Name * IPQ8074 and/or QCA9984, they may have to tune the low level threshold and
124*5113495bSYour Name * the RSSI threshold.
125*5113495bSYour Name */
126*5113495bSYour Name #define SPECTRAL_SCALING_LOW_LEVEL_OFFSET (7)
127*5113495bSYour Name #define SPECTRAL_SCALING_RSSI_THRESH (5)
128*5113495bSYour Name
129*5113495bSYour Name /*
130*5113495bSYour Name * If customers set the AGC backoff differently, they may have to tune the high
131*5113495bSYour Name * level threshold.
132*5113495bSYour Name */
133*5113495bSYour Name #define SPECTRAL_SCALING_HIGH_LEVEL_OFFSET (5)
134*5113495bSYour Name
135*5113495bSYour Name /* End of section for values needing fine tuning. */
136*5113495bSYour Name /* End of temporary section for hard-coded values */
137*5113495bSYour Name
138*5113495bSYour Name /**
139*5113495bSYour Name * enum spectral_msg_buf_type - Spectral message buffer type
140*5113495bSYour Name * @SPECTRAL_MSG_BUF_NEW: Allocate new buffer
141*5113495bSYour Name * @SPECTRAL_MSG_BUF_SAVED: Reuse last buffer, used for secondary segment report
142*5113495bSYour Name * in case of 160 MHz.
143*5113495bSYour Name * @SPECTRAL_MSG_BUF_TYPE_MAX: Max enumeration
144*5113495bSYour Name */
145*5113495bSYour Name enum spectral_msg_buf_type {
146*5113495bSYour Name SPECTRAL_MSG_BUF_NEW,
147*5113495bSYour Name SPECTRAL_MSG_BUF_SAVED,
148*5113495bSYour Name SPECTRAL_MSG_BUF_TYPE_MAX,
149*5113495bSYour Name };
150*5113495bSYour Name
151*5113495bSYour Name /**
152*5113495bSYour Name * enum spectral_msg_type - Spectral SAMP message type
153*5113495bSYour Name * @SPECTRAL_MSG_NORMAL_MODE: Normal mode Spectral SAMP message
154*5113495bSYour Name * @SPECTRAL_MSG_AGILE_MODE: Agile mode Spectral SAMP message
155*5113495bSYour Name * @SPECTRAL_MSG_INTERFERENCE_NOTIFICATION: Interference notification to
156*5113495bSYour Name * external auto channel selection
157*5113495bSYour Name * entity
158*5113495bSYour Name * @SPECTRAL_MSG_TYPE_MAX: Spectral SAMP message type max
159*5113495bSYour Name */
160*5113495bSYour Name enum spectral_msg_type {
161*5113495bSYour Name SPECTRAL_MSG_NORMAL_MODE,
162*5113495bSYour Name SPECTRAL_MSG_AGILE_MODE,
163*5113495bSYour Name SPECTRAL_MSG_INTERFERENCE_NOTIFICATION,
164*5113495bSYour Name SPECTRAL_MSG_TYPE_MAX,
165*5113495bSYour Name };
166*5113495bSYour Name
167*5113495bSYour Name /**
168*5113495bSYour Name * enum spectral_debug - Spectral debug level
169*5113495bSYour Name * @DEBUG_SPECTRAL: Minimal SPECTRAL debug
170*5113495bSYour Name * @DEBUG_SPECTRAL1: Normal SPECTRAL debug
171*5113495bSYour Name * @DEBUG_SPECTRAL2: Maximal SPECTRAL debug
172*5113495bSYour Name * @DEBUG_SPECTRAL3: Matched filterID display
173*5113495bSYour Name * @DEBUG_SPECTRAL4: One time dump of FFT report
174*5113495bSYour Name */
175*5113495bSYour Name enum spectral_debug {
176*5113495bSYour Name DEBUG_SPECTRAL = 0x00000100,
177*5113495bSYour Name DEBUG_SPECTRAL1 = 0x00000200,
178*5113495bSYour Name DEBUG_SPECTRAL2 = 0x00000400,
179*5113495bSYour Name DEBUG_SPECTRAL3 = 0x00000800,
180*5113495bSYour Name DEBUG_SPECTRAL4 = 0x00001000,
181*5113495bSYour Name };
182*5113495bSYour Name
183*5113495bSYour Name /**
184*5113495bSYour Name * enum spectral_capability_type - Spectral capability type
185*5113495bSYour Name * @SPECTRAL_CAP_PHYDIAG: Phydiag capability
186*5113495bSYour Name * @SPECTRAL_CAP_RADAR: Radar detection capability
187*5113495bSYour Name * @SPECTRAL_CAP_SPECTRAL_SCAN: Spectral capability
188*5113495bSYour Name * @SPECTRAL_CAP_ADVNCD_SPECTRAL_SCAN: Advanced spectral capability
189*5113495bSYour Name */
190*5113495bSYour Name enum spectral_capability_type {
191*5113495bSYour Name SPECTRAL_CAP_PHYDIAG,
192*5113495bSYour Name SPECTRAL_CAP_RADAR,
193*5113495bSYour Name SPECTRAL_CAP_SPECTRAL_SCAN,
194*5113495bSYour Name SPECTRAL_CAP_ADVNCD_SPECTRAL_SCAN,
195*5113495bSYour Name };
196*5113495bSYour Name
197*5113495bSYour Name /**
198*5113495bSYour Name * enum spectral_cp_error_code - Spectral control path response code
199*5113495bSYour Name * @SPECTRAL_SCAN_ERR_INVALID: Invalid error identifier
200*5113495bSYour Name * @SPECTRAL_SCAN_ERR_PARAM_UNSUPPORTED: parameter unsupported
201*5113495bSYour Name * @SPECTRAL_SCAN_ERR_MODE_UNSUPPORTED: mode unsupported
202*5113495bSYour Name * @SPECTRAL_SCAN_ERR_PARAM_INVALID_VALUE: invalid parameter value
203*5113495bSYour Name * @SPECTRAL_SCAN_ERR_PARAM_NOT_INITIALIZED: parameter uninitialized
204*5113495bSYour Name */
205*5113495bSYour Name enum spectral_cp_error_code {
206*5113495bSYour Name SPECTRAL_SCAN_ERR_INVALID,
207*5113495bSYour Name SPECTRAL_SCAN_ERR_PARAM_UNSUPPORTED,
208*5113495bSYour Name SPECTRAL_SCAN_ERR_MODE_UNSUPPORTED,
209*5113495bSYour Name SPECTRAL_SCAN_ERR_PARAM_INVALID_VALUE,
210*5113495bSYour Name SPECTRAL_SCAN_ERR_PARAM_NOT_INITIALIZED,
211*5113495bSYour Name };
212*5113495bSYour Name
213*5113495bSYour Name /**
214*5113495bSYour Name * enum spectral_dma_debug - Spectral DMA debug
215*5113495bSYour Name * @SPECTRAL_DMA_RING_DEBUG: Spectral DMA ring debug
216*5113495bSYour Name * @SPECTRAL_DMA_BUFFER_DEBUG: Spectral DMA buffer debug
217*5113495bSYour Name */
218*5113495bSYour Name enum spectral_dma_debug {
219*5113495bSYour Name SPECTRAL_DMA_RING_DEBUG,
220*5113495bSYour Name SPECTRAL_DMA_BUFFER_DEBUG,
221*5113495bSYour Name };
222*5113495bSYour Name
223*5113495bSYour Name struct wiphy;
224*5113495bSYour Name struct wlan_objmgr_pdev;
225*5113495bSYour Name struct wlan_objmgr_vdev;
226*5113495bSYour Name /**
227*5113495bSYour Name * struct spectral_cfg80211_vendor_cmd_handlers - Spectral vendor command
228*5113495bSYour Name * handlers
229*5113495bSYour Name * @wlan_cfg80211_spectral_scan_start: start scan handler
230*5113495bSYour Name * @wlan_cfg80211_spectral_scan_stop: stop scan handler
231*5113495bSYour Name * @wlan_cfg80211_spectral_scan_get_config: get config handler
232*5113495bSYour Name * @wlan_cfg80211_spectral_scan_get_diag_stats: get diag stats handler
233*5113495bSYour Name * @wlan_cfg80211_spectral_scan_get_cap: get capability handler
234*5113495bSYour Name * @wlan_cfg80211_spectral_scan_get_status: get status handler
235*5113495bSYour Name */
236*5113495bSYour Name struct spectral_cfg80211_vendor_cmd_handlers {
237*5113495bSYour Name int (*wlan_cfg80211_spectral_scan_start)(struct wiphy *wiphy,
238*5113495bSYour Name struct wlan_objmgr_pdev *pdev,
239*5113495bSYour Name struct wlan_objmgr_vdev *vdev,
240*5113495bSYour Name const void *data,
241*5113495bSYour Name int data_len);
242*5113495bSYour Name int (*wlan_cfg80211_spectral_scan_stop)(struct wiphy *wiphy,
243*5113495bSYour Name struct wlan_objmgr_pdev *pdev,
244*5113495bSYour Name struct wlan_objmgr_vdev *vdev,
245*5113495bSYour Name const void *data,
246*5113495bSYour Name int data_len);
247*5113495bSYour Name int (*wlan_cfg80211_spectral_scan_get_config)(
248*5113495bSYour Name struct wiphy *wiphy,
249*5113495bSYour Name struct wlan_objmgr_pdev *pdev,
250*5113495bSYour Name struct wlan_objmgr_vdev *vdev,
251*5113495bSYour Name const void *data,
252*5113495bSYour Name int data_len);
253*5113495bSYour Name int (*wlan_cfg80211_spectral_scan_get_diag_stats)(
254*5113495bSYour Name struct wiphy *wiphy,
255*5113495bSYour Name struct wlan_objmgr_pdev *pdev,
256*5113495bSYour Name struct wlan_objmgr_vdev *vdev,
257*5113495bSYour Name const void *data,
258*5113495bSYour Name int data_len);
259*5113495bSYour Name int (*wlan_cfg80211_spectral_scan_get_cap)(
260*5113495bSYour Name struct wiphy *wiphy,
261*5113495bSYour Name struct wlan_objmgr_pdev *pdev,
262*5113495bSYour Name struct wlan_objmgr_vdev *vdev,
263*5113495bSYour Name const void *data,
264*5113495bSYour Name int data_len);
265*5113495bSYour Name int (*wlan_cfg80211_spectral_scan_get_status)(
266*5113495bSYour Name struct wiphy *wiphy,
267*5113495bSYour Name struct wlan_objmgr_pdev *pdev,
268*5113495bSYour Name struct wlan_objmgr_vdev *vdev,
269*5113495bSYour Name const void *data,
270*5113495bSYour Name int data_len);
271*5113495bSYour Name };
272*5113495bSYour Name
273*5113495bSYour Name /**
274*5113495bSYour Name * struct spectral_cp_param - Spectral control path data structure which
275*5113495bSYour Name * contains parameter and its value
276*5113495bSYour Name * @id: Parameter ID
277*5113495bSYour Name * @value: Single parameter value
278*5113495bSYour Name * @freq: Spectral scan frequency
279*5113495bSYour Name */
280*5113495bSYour Name struct spectral_cp_param {
281*5113495bSYour Name uint32_t id;
282*5113495bSYour Name union {
283*5113495bSYour Name uint32_t value;
284*5113495bSYour Name struct spectral_config_frequency freq;
285*5113495bSYour Name };
286*5113495bSYour Name };
287*5113495bSYour Name
288*5113495bSYour Name /**
289*5113495bSYour Name * struct spectral_chan_stats - channel status info
290*5113495bSYour Name * @cycle_count: Cycle count
291*5113495bSYour Name * @channel_load: Channel load
292*5113495bSYour Name * @per: Period
293*5113495bSYour Name * @noisefloor: Noise floor
294*5113495bSYour Name * @comp_usablity: Computed usability
295*5113495bSYour Name * @maxregpower: Maximum allowed regulatory power
296*5113495bSYour Name * @comp_usablity_sec80: Computed usability of secondary 80 Mhz
297*5113495bSYour Name * @maxregpower_sec80: Max regulatory power of secondary 80 Mhz
298*5113495bSYour Name */
299*5113495bSYour Name struct spectral_chan_stats {
300*5113495bSYour Name int cycle_count;
301*5113495bSYour Name int channel_load;
302*5113495bSYour Name int per;
303*5113495bSYour Name int noisefloor;
304*5113495bSYour Name uint16_t comp_usablity;
305*5113495bSYour Name int8_t maxregpower;
306*5113495bSYour Name uint16_t comp_usablity_sec80;
307*5113495bSYour Name int8_t maxregpower_sec80;
308*5113495bSYour Name };
309*5113495bSYour Name
310*5113495bSYour Name /**
311*5113495bSYour Name * struct spectral_diag_stats - spectral diag stats
312*5113495bSYour Name * @spectral_mismatch: Spectral TLV signature mismatches
313*5113495bSYour Name * @spectral_sec80_sfft_insufflen: Insufficient length when parsing for
314*5113495bSYour Name * Secondary 80 Search FFT report
315*5113495bSYour Name * @spectral_no_sec80_sfft: Secondary 80 Search FFT report
316*5113495bSYour Name * TLV not found
317*5113495bSYour Name * @spectral_vhtseg1id_mismatch: VHT Operation Segment 1 ID
318*5113495bSYour Name * mismatches in Search FFT report
319*5113495bSYour Name * @spectral_vhtseg2id_mismatch: VHT Operation Segment 2 ID
320*5113495bSYour Name * mismatches in Search FFT report
321*5113495bSYour Name * @spectral_invalid_detector_id: Invalid detector id
322*5113495bSYour Name */
323*5113495bSYour Name struct spectral_diag_stats {
324*5113495bSYour Name uint64_t spectral_mismatch;
325*5113495bSYour Name uint64_t spectral_sec80_sfft_insufflen;
326*5113495bSYour Name uint64_t spectral_no_sec80_sfft;
327*5113495bSYour Name uint64_t spectral_vhtseg1id_mismatch;
328*5113495bSYour Name uint64_t spectral_vhtseg2id_mismatch;
329*5113495bSYour Name uint64_t spectral_invalid_detector_id;
330*5113495bSYour Name };
331*5113495bSYour Name
332*5113495bSYour Name /**
333*5113495bSYour Name * struct spectral_scan_state - State of spectral scan
334*5113495bSYour Name * @is_active: Is spectral scan active
335*5113495bSYour Name * @is_enabled: Is spectral scan enabled
336*5113495bSYour Name */
337*5113495bSYour Name struct spectral_scan_state {
338*5113495bSYour Name uint8_t is_active;
339*5113495bSYour Name uint8_t is_enabled;
340*5113495bSYour Name };
341*5113495bSYour Name
342*5113495bSYour Name /* Forward declarations */
343*5113495bSYour Name struct wlan_objmgr_pdev;
344*5113495bSYour Name
345*5113495bSYour Name /**
346*5113495bSYour Name * struct spectral_nl_cb - Spectral Netlink callbacks
347*5113495bSYour Name * @get_sbuff: Get the socket buffer to send the data to the application
348*5113495bSYour Name * @send_nl_bcast: Send data to the application using netlink broadcast
349*5113495bSYour Name * @send_nl_unicast: Send data to the application using netlink unicast
350*5113495bSYour Name * @free_sbuff: Free the socket buffer for a particular message type
351*5113495bSYour Name * @convert_to_nl_ch_width:
352*5113495bSYour Name * @convert_to_phy_ch_width:
353*5113495bSYour Name */
354*5113495bSYour Name struct spectral_nl_cb {
355*5113495bSYour Name void *(*get_sbuff)(struct wlan_objmgr_pdev *pdev,
356*5113495bSYour Name enum spectral_msg_type smsg_type,
357*5113495bSYour Name enum spectral_msg_buf_type buf_type);
358*5113495bSYour Name int (*send_nl_bcast)(struct wlan_objmgr_pdev *pdev,
359*5113495bSYour Name enum spectral_msg_type smsg_type);
360*5113495bSYour Name int (*send_nl_unicast)(struct wlan_objmgr_pdev *pdev,
361*5113495bSYour Name enum spectral_msg_type smsg_type);
362*5113495bSYour Name void (*free_sbuff)(struct wlan_objmgr_pdev *pdev,
363*5113495bSYour Name enum spectral_msg_type smsg_type);
364*5113495bSYour Name int (*convert_to_nl_ch_width)(uint8_t phy_chwidth);
365*5113495bSYour Name uint8_t (*convert_to_phy_ch_width)(uint8_t nl_chwidth);
366*5113495bSYour Name };
367*5113495bSYour Name
368*5113495bSYour Name /**
369*5113495bSYour Name * struct spectral_scan_config_request - Config request
370*5113495bSYour Name * @sscan_config: Spectral parameters
371*5113495bSYour Name * @sscan_err_code: Spectral scan error code
372*5113495bSYour Name */
373*5113495bSYour Name struct spectral_scan_config_request {
374*5113495bSYour Name struct spectral_config sscan_config;
375*5113495bSYour Name enum spectral_cp_error_code sscan_err_code;
376*5113495bSYour Name };
377*5113495bSYour Name
378*5113495bSYour Name /**
379*5113495bSYour Name * struct spectral_scan_action_request - Action request
380*5113495bSYour Name * @sscan_err_code: Spectral scan error code
381*5113495bSYour Name */
382*5113495bSYour Name struct spectral_scan_action_request {
383*5113495bSYour Name enum spectral_cp_error_code sscan_err_code;
384*5113495bSYour Name };
385*5113495bSYour Name
386*5113495bSYour Name /**
387*5113495bSYour Name * struct spectral_scan_get_caps_request - Get caps request
388*5113495bSYour Name * @sscan_caps: Spectral capabilities
389*5113495bSYour Name * @sscan_err_code: Spectral scan error code
390*5113495bSYour Name */
391*5113495bSYour Name struct spectral_scan_get_caps_request {
392*5113495bSYour Name struct spectral_caps sscan_caps;
393*5113495bSYour Name enum spectral_cp_error_code sscan_err_code;
394*5113495bSYour Name };
395*5113495bSYour Name
396*5113495bSYour Name /**
397*5113495bSYour Name * struct spectral_scan_get_diag_request - Get diag request
398*5113495bSYour Name * @sscan_diag: Spectral diag stats
399*5113495bSYour Name * @sscan_err_code: Spectral scan error code
400*5113495bSYour Name */
401*5113495bSYour Name struct spectral_scan_get_diag_request {
402*5113495bSYour Name struct spectral_diag_stats sscan_diag;
403*5113495bSYour Name enum spectral_cp_error_code sscan_err_code;
404*5113495bSYour Name };
405*5113495bSYour Name
406*5113495bSYour Name /**
407*5113495bSYour Name * struct spectral_scan_get_chan_width_request - Get channel width request
408*5113495bSYour Name * @chan_width: Channel width
409*5113495bSYour Name * @sscan_err_code: Spectral scan error code
410*5113495bSYour Name */
411*5113495bSYour Name struct spectral_scan_get_chan_width_request {
412*5113495bSYour Name uint32_t chan_width;
413*5113495bSYour Name enum spectral_cp_error_code sscan_err_code;
414*5113495bSYour Name };
415*5113495bSYour Name
416*5113495bSYour Name /**
417*5113495bSYour Name * struct spectral_scan_get_status_request - Get status request
418*5113495bSYour Name * @is_active: is Spectral scan active
419*5113495bSYour Name * @is_enabled: is Spectral scan enabled
420*5113495bSYour Name * @sscan_err_code: Spectral scan error code
421*5113495bSYour Name */
422*5113495bSYour Name struct spectral_scan_get_status_request {
423*5113495bSYour Name bool is_active;
424*5113495bSYour Name bool is_enabled;
425*5113495bSYour Name enum spectral_cp_error_code sscan_err_code;
426*5113495bSYour Name };
427*5113495bSYour Name
428*5113495bSYour Name /**
429*5113495bSYour Name * struct spectral_scan_debug_request - Get/set debug level request
430*5113495bSYour Name * @spectral_dbg_level: Spectral debug level
431*5113495bSYour Name * @sscan_err_code: Spectral scan error code
432*5113495bSYour Name */
433*5113495bSYour Name struct spectral_scan_debug_request {
434*5113495bSYour Name uint32_t spectral_dbg_level;
435*5113495bSYour Name enum spectral_cp_error_code sscan_err_code;
436*5113495bSYour Name };
437*5113495bSYour Name
438*5113495bSYour Name /**
439*5113495bSYour Name * struct spectral_scan_dma_debug_request - DMA debug request
440*5113495bSYour Name * @dma_debug_enable: Enable/disable @dma_debug_type
441*5113495bSYour Name * @dma_debug_type: Type of Spectral DMA debug i.e., ring or buffer debug
442*5113495bSYour Name * @sscan_err_code: Spectral scan error code
443*5113495bSYour Name */
444*5113495bSYour Name struct spectral_scan_dma_debug_request {
445*5113495bSYour Name bool dma_debug_enable;
446*5113495bSYour Name enum spectral_dma_debug dma_debug_type;
447*5113495bSYour Name enum spectral_cp_error_code sscan_err_code;
448*5113495bSYour Name };
449*5113495bSYour Name
450*5113495bSYour Name /**
451*5113495bSYour Name * struct spectral_cp_request - Spectral control path request
452*5113495bSYour Name * Creating request and extracting response has to
453*5113495bSYour Name * be atomic.
454*5113495bSYour Name * @ss_mode: Spectral scan mode
455*5113495bSYour Name * @req_id: Request identifier
456*5113495bSYour Name * @vdev_id: VDEV id
457*5113495bSYour Name * @config_req: Spectral scan config request
458*5113495bSYour Name * @action_req: Spectral scan action request
459*5113495bSYour Name * @caps_req: Spectral scan get caps request
460*5113495bSYour Name * @diag_req: Spectral scan get diag request
461*5113495bSYour Name * @chan_width_req:Spectral scan get chan width request
462*5113495bSYour Name * @status_req: Spectral scan get status request
463*5113495bSYour Name * @debug_req: Spectral scan debug request
464*5113495bSYour Name * @dma_debug_req: Spectral DMA debug request
465*5113495bSYour Name */
466*5113495bSYour Name struct spectral_cp_request {
467*5113495bSYour Name enum spectral_scan_mode ss_mode;
468*5113495bSYour Name uint8_t req_id;
469*5113495bSYour Name uint8_t vdev_id;
470*5113495bSYour Name union {
471*5113495bSYour Name struct spectral_scan_config_request config_req;
472*5113495bSYour Name struct spectral_scan_action_request action_req;
473*5113495bSYour Name struct spectral_scan_get_caps_request caps_req;
474*5113495bSYour Name struct spectral_scan_get_diag_request diag_req;
475*5113495bSYour Name struct spectral_scan_get_chan_width_request chan_width_req;
476*5113495bSYour Name struct spectral_scan_get_status_request status_req;
477*5113495bSYour Name struct spectral_scan_debug_request debug_req;
478*5113495bSYour Name struct spectral_scan_dma_debug_request dma_debug_req;
479*5113495bSYour Name };
480*5113495bSYour Name };
481*5113495bSYour Name
482*5113495bSYour Name /**
483*5113495bSYour Name * struct spectral_data_stats - Spectral data stats
484*5113495bSYour Name * @spectral_rx_events: Number of Spectral rx events
485*5113495bSYour Name * @consume_spectral_calls: Number of consume_spectral_report() invocations
486*5113495bSYour Name * @fill_samp_msg_calls: Number of fill_samp_msg() invocations
487*5113495bSYour Name * @msgs_ready_for_user: Number of SAMP messages that are ready to be sent to
488*5113495bSYour Name * user-space
489*5113495bSYour Name * @msgs_queued_to_user: Number of SAMP messages queued to the user-space
490*5113495bSYour Name */
491*5113495bSYour Name struct spectral_data_stats {
492*5113495bSYour Name uint32_t spectral_rx_events;
493*5113495bSYour Name uint32_t consume_spectral_calls;
494*5113495bSYour Name uint32_t fill_samp_msg_calls;
495*5113495bSYour Name uint32_t msgs_ready_for_user;
496*5113495bSYour Name uint32_t msgs_queued_to_user;
497*5113495bSYour Name };
498*5113495bSYour Name
499*5113495bSYour Name #ifndef __KERNEL__
500*5113495bSYour Name
501*5113495bSYour Name static inline int16_t
spectral_pwfactor_max(int16_t pwfactor1,int16_t pwfactor2)502*5113495bSYour Name spectral_pwfactor_max(int16_t pwfactor1,
503*5113495bSYour Name int16_t pwfactor2)
504*5113495bSYour Name {
505*5113495bSYour Name return ((pwfactor1 > pwfactor2) ? pwfactor1 : pwfactor2);
506*5113495bSYour Name }
507*5113495bSYour Name
508*5113495bSYour Name /**
509*5113495bSYour Name * get_spectral_scale_rssi_corr() - Compute RSSI correction factor for scaling
510*5113495bSYour Name * @agc_total_gain_db: AGC total gain in dB steps
511*5113495bSYour Name * @gen3_defmaxgain: Default max gain value of the gen III chipset
512*5113495bSYour Name * @gen2_maxgain: Max gain value used by the reference gen II chipset
513*5113495bSYour Name * @lowlevel_offset: Low level offset for scaling
514*5113495bSYour Name * @inband_pwr: In band power in dB steps
515*5113495bSYour Name * @rssi_thr: RSSI threshold for scaling
516*5113495bSYour Name *
517*5113495bSYour Name * Helper function to compute RSSI correction factor for Gen III linear format
518*5113495bSYour Name * Spectral scaling. It is the responsibility of the caller to ensure that
519*5113495bSYour Name * correct values are passed.
520*5113495bSYour Name *
521*5113495bSYour Name * Return: RSSI correction factor
522*5113495bSYour Name */
523*5113495bSYour Name static inline int16_t
get_spectral_scale_rssi_corr(u_int8_t agc_total_gain_db,u_int8_t gen3_defmaxgain,u_int8_t gen2_maxgain,int16_t lowlevel_offset,int16_t inband_pwr,int16_t rssi_thr)524*5113495bSYour Name get_spectral_scale_rssi_corr(u_int8_t agc_total_gain_db,
525*5113495bSYour Name u_int8_t gen3_defmaxgain, u_int8_t gen2_maxgain,
526*5113495bSYour Name int16_t lowlevel_offset, int16_t inband_pwr,
527*5113495bSYour Name int16_t rssi_thr)
528*5113495bSYour Name {
529*5113495bSYour Name return ((agc_total_gain_db < gen3_defmaxgain) ?
530*5113495bSYour Name (gen2_maxgain - gen3_defmaxgain + lowlevel_offset) :
531*5113495bSYour Name spectral_pwfactor_max((inband_pwr - rssi_thr), 0));
532*5113495bSYour Name }
533*5113495bSYour Name
534*5113495bSYour Name /**
535*5113495bSYour Name * spectral_scale_linear_to_gen2() - Scale linear bin value to gen II equivalent
536*5113495bSYour Name * @gen3_binmag: Captured FFT bin value from the Spectral Search FFT report
537*5113495bSYour Name * generated by the Gen III chipset
538*5113495bSYour Name * @gen2_maxgain: Max gain value used by the reference gen II chipset
539*5113495bSYour Name * @gen3_defmaxgain: Default max gain value of the gen III chipset
540*5113495bSYour Name * @lowlevel_offset: Low level offset for scaling
541*5113495bSYour Name * @inband_pwr: In band power in dB steps
542*5113495bSYour Name * @rssi_thr: RSSI threshold for scaling
543*5113495bSYour Name * @agc_total_gain_db: AGC total gain in dB steps
544*5113495bSYour Name * @highlevel_offset: High level offset for scaling
545*5113495bSYour Name * @gen2_bin_scale: Bin scale value used on reference gen II chipset
546*5113495bSYour Name * @gen3_bin_scale: Bin scale value used on gen III chipset
547*5113495bSYour Name *
548*5113495bSYour Name * Helper function to scale a given gen III linear format bin value into an
549*5113495bSYour Name * approximately equivalent gen II value. The scaled value can possibly be
550*5113495bSYour Name * higher than 8 bits. If the caller is incapable of handling values larger
551*5113495bSYour Name * than 8 bits, the caller can saturate the value at 255. This function does not
552*5113495bSYour Name * carry out this saturation for the sake of flexibility so that callers
553*5113495bSYour Name * interested in the larger values can avail of this. Also note it is the
554*5113495bSYour Name * responsibility of the caller to ensure that correct values are passed.
555*5113495bSYour Name *
556*5113495bSYour Name * Return: Scaled bin value
557*5113495bSYour Name */
558*5113495bSYour Name static inline u_int32_t
spectral_scale_linear_to_gen2(u_int8_t gen3_binmag,u_int8_t gen2_maxgain,u_int8_t gen3_defmaxgain,int16_t lowlevel_offset,int16_t inband_pwr,int16_t rssi_thr,u_int8_t agc_total_gain_db,int16_t highlevel_offset,u_int8_t gen2_bin_scale,u_int8_t gen3_bin_scale)559*5113495bSYour Name spectral_scale_linear_to_gen2(u_int8_t gen3_binmag,
560*5113495bSYour Name u_int8_t gen2_maxgain, u_int8_t gen3_defmaxgain,
561*5113495bSYour Name int16_t lowlevel_offset, int16_t inband_pwr,
562*5113495bSYour Name int16_t rssi_thr, u_int8_t agc_total_gain_db,
563*5113495bSYour Name int16_t highlevel_offset, u_int8_t gen2_bin_scale,
564*5113495bSYour Name u_int8_t gen3_bin_scale)
565*5113495bSYour Name {
566*5113495bSYour Name return (gen3_binmag *
567*5113495bSYour Name sqrt(pow(10, (((double)spectral_pwfactor_max(gen2_maxgain -
568*5113495bSYour Name gen3_defmaxgain + lowlevel_offset -
569*5113495bSYour Name get_spectral_scale_rssi_corr(agc_total_gain_db,
570*5113495bSYour Name gen3_defmaxgain,
571*5113495bSYour Name gen2_maxgain,
572*5113495bSYour Name lowlevel_offset,
573*5113495bSYour Name inband_pwr,
574*5113495bSYour Name rssi_thr),
575*5113495bSYour Name (agc_total_gain_db < gen3_defmaxgain) *
576*5113495bSYour Name highlevel_offset)) / 10))) *
577*5113495bSYour Name pow(2, (gen3_bin_scale - gen2_bin_scale)));
578*5113495bSYour Name }
579*5113495bSYour Name
580*5113495bSYour Name #endif /* __KERNEL__ */
581*5113495bSYour Name
582*5113495bSYour Name #endif /* _WLAN_SPECTRAL_PUBLIC_STRUCTS_H_ */
583