1 /*
2  * Copyright (c) 2017 Intel Corporation.
3  *
4  * SPDX-License-Identifier: Apache-2.0
5  */
6 
7 /**
8  * @file
9  * @brief WiFi L2 stack public header
10  */
11 
12 #ifndef ZEPHYR_INCLUDE_NET_WIFI_MGMT_H_
13 #define ZEPHYR_INCLUDE_NET_WIFI_MGMT_H_
14 
15 #include <zephyr/net/net_mgmt.h>
16 #include <zephyr/net/wifi.h>
17 #include <zephyr/net/ethernet.h>
18 #include <zephyr/net/offloaded_netdev.h>
19 
20 #ifdef __cplusplus
21 extern "C" {
22 #endif
23 
24 /* Management part definitions */
25 
26 #define _NET_WIFI_LAYER	NET_MGMT_LAYER_L2
27 #define _NET_WIFI_CODE	0x156
28 #define _NET_WIFI_BASE	(NET_MGMT_IFACE_BIT |			\
29 			 NET_MGMT_LAYER(_NET_WIFI_LAYER) |	\
30 			 NET_MGMT_LAYER_CODE(_NET_WIFI_CODE))
31 #define _NET_WIFI_EVENT	(_NET_WIFI_BASE | NET_MGMT_EVENT_BIT)
32 
33 enum net_request_wifi_cmd {
34 	NET_REQUEST_WIFI_CMD_SCAN = 1,
35 	NET_REQUEST_WIFI_CMD_CONNECT,
36 	NET_REQUEST_WIFI_CMD_DISCONNECT,
37 	NET_REQUEST_WIFI_CMD_AP_ENABLE,
38 	NET_REQUEST_WIFI_CMD_AP_DISABLE,
39 	NET_REQUEST_WIFI_CMD_IFACE_STATUS,
40 	NET_REQUEST_WIFI_CMD_PS,
41 	NET_REQUEST_WIFI_CMD_PS_MODE,
42 	NET_REQUEST_WIFI_CMD_TWT,
43 	NET_REQUEST_WIFI_CMD_PS_CONFIG,
44 	NET_REQUEST_WIFI_CMD_REG_DOMAIN,
45 	NET_REQUEST_WIFI_CMD_PS_TIMEOUT,
46 	NET_REQUEST_WIFI_CMD_MAX
47 };
48 
49 #define NET_REQUEST_WIFI_SCAN					\
50 	(_NET_WIFI_BASE | NET_REQUEST_WIFI_CMD_SCAN)
51 
52 NET_MGMT_DEFINE_REQUEST_HANDLER(NET_REQUEST_WIFI_SCAN);
53 
54 #define NET_REQUEST_WIFI_CONNECT				\
55 	(_NET_WIFI_BASE | NET_REQUEST_WIFI_CMD_CONNECT)
56 
57 NET_MGMT_DEFINE_REQUEST_HANDLER(NET_REQUEST_WIFI_CONNECT);
58 
59 #define NET_REQUEST_WIFI_DISCONNECT				\
60 	(_NET_WIFI_BASE | NET_REQUEST_WIFI_CMD_DISCONNECT)
61 
62 NET_MGMT_DEFINE_REQUEST_HANDLER(NET_REQUEST_WIFI_DISCONNECT);
63 
64 #define NET_REQUEST_WIFI_AP_ENABLE				\
65 	(_NET_WIFI_BASE | NET_REQUEST_WIFI_CMD_AP_ENABLE)
66 
67 NET_MGMT_DEFINE_REQUEST_HANDLER(NET_REQUEST_WIFI_AP_ENABLE);
68 
69 #define NET_REQUEST_WIFI_AP_DISABLE				\
70 	(_NET_WIFI_BASE | NET_REQUEST_WIFI_CMD_AP_DISABLE)
71 
72 NET_MGMT_DEFINE_REQUEST_HANDLER(NET_REQUEST_WIFI_AP_DISABLE);
73 
74 #define NET_REQUEST_WIFI_IFACE_STATUS				\
75 	(_NET_WIFI_BASE | NET_REQUEST_WIFI_CMD_IFACE_STATUS)
76 
77 NET_MGMT_DEFINE_REQUEST_HANDLER(NET_REQUEST_WIFI_IFACE_STATUS);
78 
79 #define NET_REQUEST_WIFI_PS				\
80 	(_NET_WIFI_BASE | NET_REQUEST_WIFI_CMD_PS)
81 
82 NET_MGMT_DEFINE_REQUEST_HANDLER(NET_REQUEST_WIFI_PS);
83 
84 #define NET_REQUEST_WIFI_PS_MODE			\
85 	(_NET_WIFI_BASE | NET_REQUEST_WIFI_CMD_PS_MODE)
86 
87 NET_MGMT_DEFINE_REQUEST_HANDLER(NET_REQUEST_WIFI_PS_MODE);
88 
89 #define NET_REQUEST_WIFI_TWT			\
90 	(_NET_WIFI_BASE | NET_REQUEST_WIFI_CMD_TWT)
91 
92 NET_MGMT_DEFINE_REQUEST_HANDLER(NET_REQUEST_WIFI_TWT);
93 
94 #define NET_REQUEST_WIFI_PS_CONFIG				\
95 	(_NET_WIFI_BASE | NET_REQUEST_WIFI_CMD_PS_CONFIG)
96 
97 NET_MGMT_DEFINE_REQUEST_HANDLER(NET_REQUEST_WIFI_PS_CONFIG);
98 #define NET_REQUEST_WIFI_REG_DOMAIN				\
99 	(_NET_WIFI_BASE | NET_REQUEST_WIFI_CMD_REG_DOMAIN)
100 
101 NET_MGMT_DEFINE_REQUEST_HANDLER(NET_REQUEST_WIFI_REG_DOMAIN);
102 
103 #define NET_REQUEST_WIFI_PS_TIMEOUT			\
104 	(_NET_WIFI_BASE | NET_REQUEST_WIFI_CMD_PS_TIMEOUT)
105 
106 NET_MGMT_DEFINE_REQUEST_HANDLER(NET_REQUEST_WIFI_PS_TIMEOUT);
107 
108 enum net_event_wifi_cmd {
109 	NET_EVENT_WIFI_CMD_SCAN_RESULT = 1,
110 	NET_EVENT_WIFI_CMD_SCAN_DONE,
111 	NET_EVENT_WIFI_CMD_CONNECT_RESULT,
112 	NET_EVENT_WIFI_CMD_DISCONNECT_RESULT,
113 	NET_EVENT_WIFI_CMD_IFACE_STATUS,
114 	NET_EVENT_WIFI_CMD_TWT,
115 	NET_EVENT_WIFI_CMD_TWT_SLEEP_STATE,
116 	NET_EVENT_WIFI_CMD_RAW_SCAN_RESULT,
117 	NET_EVENT_WIFI_CMD_DISCONNECT_COMPLETE,
118 };
119 
120 #define NET_EVENT_WIFI_SCAN_RESULT				\
121 	(_NET_WIFI_EVENT | NET_EVENT_WIFI_CMD_SCAN_RESULT)
122 
123 #define NET_EVENT_WIFI_SCAN_DONE				\
124 	(_NET_WIFI_EVENT | NET_EVENT_WIFI_CMD_SCAN_DONE)
125 
126 #define NET_EVENT_WIFI_CONNECT_RESULT				\
127 	(_NET_WIFI_EVENT | NET_EVENT_WIFI_CMD_CONNECT_RESULT)
128 
129 #define NET_EVENT_WIFI_DISCONNECT_RESULT			\
130 	(_NET_WIFI_EVENT | NET_EVENT_WIFI_CMD_DISCONNECT_RESULT)
131 
132 #define NET_EVENT_WIFI_IFACE_STATUS						\
133 	(_NET_WIFI_EVENT | NET_EVENT_WIFI_CMD_IFACE_STATUS)
134 
135 #define NET_EVENT_WIFI_TWT					\
136 	(_NET_WIFI_EVENT | NET_EVENT_WIFI_CMD_TWT)
137 
138 #define NET_EVENT_WIFI_TWT_SLEEP_STATE				\
139 	(_NET_WIFI_EVENT | NET_EVENT_WIFI_CMD_TWT_SLEEP_STATE)
140 
141 #define NET_EVENT_WIFI_RAW_SCAN_RESULT                          \
142 	(_NET_WIFI_EVENT | NET_EVENT_WIFI_CMD_RAW_SCAN_RESULT)
143 
144 #define NET_EVENT_WIFI_DISCONNECT_COMPLETE			\
145 	(_NET_WIFI_EVENT | NET_EVENT_WIFI_CMD_DISCONNECT_COMPLETE)
146 /* Each result is provided to the net_mgmt_event_callback
147  * via its info attribute (see net_mgmt.h)
148  */
149 struct wifi_scan_result {
150 	uint8_t ssid[WIFI_SSID_MAX_LEN];
151 	uint8_t ssid_length;
152 
153 	uint8_t band;
154 	uint8_t channel;
155 	enum wifi_security_type security;
156 	enum wifi_mfp_options mfp;
157 	int8_t rssi;
158 
159 	uint8_t mac[WIFI_MAC_ADDR_LEN];
160 	uint8_t mac_length;
161 };
162 
163 struct wifi_connect_req_params {
164 	const uint8_t *ssid;
165 	uint8_t ssid_length; /* Max 32 */
166 
167 	uint8_t *psk;
168 	uint8_t psk_length; /* Min 8 - Max 64 */
169 
170 	uint8_t *sae_password; /* Optional with fallback to psk */
171 	uint8_t sae_password_length; /* No length restrictions */
172 
173 	uint8_t band;
174 	uint8_t channel;
175 	enum wifi_security_type security;
176 	enum wifi_mfp_options mfp;
177 	int timeout; /* SYS_FOREVER_MS for no timeout */
178 };
179 
180 struct wifi_status {
181 	int status;
182 };
183 
184 struct wifi_iface_status {
185 	int state; /* enum wifi_iface_state */
186 	unsigned int ssid_len;
187 	char ssid[WIFI_SSID_MAX_LEN];
188 	char bssid[WIFI_MAC_ADDR_LEN];
189 	enum wifi_frequency_bands band;
190 	unsigned int channel;
191 	enum wifi_iface_mode iface_mode;
192 	enum wifi_link_mode link_mode;
193 	enum wifi_security_type security;
194 	enum wifi_mfp_options mfp;
195 	int rssi;
196 	unsigned char dtim_period;
197 	unsigned short beacon_interval;
198 	bool twt_capable;
199 };
200 
201 struct wifi_ps_params {
202 	enum wifi_ps enabled;
203 	unsigned short listen_interval;
204 	enum wifi_ps_wakeup_mode wakeup_mode;
205 	enum wifi_ps_mode mode;
206 	int timeout_ms;
207 	enum ps_param_type type;
208 	enum wifi_config_ps_param_fail_reason fail_reason;
209 };
210 
211 struct wifi_twt_params {
212 	enum wifi_twt_operation operation;
213 	enum wifi_twt_negotiation_type negotiation_type;
214 	enum wifi_twt_setup_cmd setup_cmd;
215 	enum wifi_twt_setup_resp_status resp_status;
216 	/* Map requests to responses */
217 	uint8_t dialog_token;
218 	/* Map setup with teardown */
219 	uint8_t flow_id;
220 	union {
221 		struct {
222 			/* Interval = Wake up time + Sleeping time */
223 			uint64_t twt_interval;
224 			bool responder;
225 			bool trigger;
226 			bool implicit;
227 			bool announce;
228 			/* Wake up time */
229 			uint32_t twt_wake_interval;
230 		} setup;
231 		struct {
232 			/* Only for Teardown */
233 			bool teardown_all;
234 		} teardown;
235 	};
236 	enum wifi_twt_fail_reason fail_reason;
237 };
238 
239 /* Flow ID is only 3 bits */
240 #define WIFI_MAX_TWT_FLOWS 8
241 #define WIFI_MAX_TWT_INTERVAL_US (LONG_MAX - 1)
242 /* 256 (u8) * 1TU */
243 #define WIFI_MAX_TWT_WAKE_INTERVAL_US 262144
244 struct wifi_twt_flow_info {
245 	/* Interval = Wake up time + Sleeping time */
246 	uint64_t  twt_interval;
247 	/* Map requests to responses */
248 	uint8_t dialog_token;
249 	/* Map setup with teardown */
250 	uint8_t flow_id;
251 	enum wifi_twt_negotiation_type negotiation_type;
252 	bool responder;
253 	bool trigger;
254 	bool implicit;
255 	bool announce;
256 	/* Wake up time */
257 	uint32_t twt_wake_interval;
258 };
259 
260 struct wifi_ps_config {
261 	char num_twt_flows;
262 	struct wifi_twt_flow_info twt_flows[WIFI_MAX_TWT_FLOWS];
263 	struct wifi_ps_params ps_params;
264 };
265 
266 /* Generic get/set operation for any command*/
267 enum wifi_mgmt_op {
268 	WIFI_MGMT_GET = 0,
269 	WIFI_MGMT_SET = 1,
270 };
271 
272 struct wifi_reg_domain {
273 	enum wifi_mgmt_op oper;
274 	/* Ignore all other regulatory hints */
275 	bool force;
276 	uint8_t country_code[WIFI_COUNTRY_CODE_LEN];
277 };
278 
279 enum wifi_twt_sleep_state {
280 	WIFI_TWT_STATE_SLEEP = 0,
281 	WIFI_TWT_STATE_AWAKE = 1,
282 };
283 
284 #ifdef CONFIG_WIFI_MGMT_RAW_SCAN_RESULTS
285 struct wifi_raw_scan_result {
286 	int8_t rssi;
287 	int frame_length;
288 	unsigned short frequency;
289 	uint8_t data[CONFIG_WIFI_MGMT_RAW_SCAN_RESULT_LENGTH];
290 };
291 #endif /* CONFIG_WIFI_MGMT_RAW_SCAN_RESULTS */
292 #include <zephyr/net/net_if.h>
293 
294 typedef void (*scan_result_cb_t)(struct net_if *iface, int status,
295 				 struct wifi_scan_result *entry);
296 
297 #ifdef CONFIG_WIFI_MGMT_RAW_SCAN_RESULTS
298 typedef void (*raw_scan_result_cb_t)(struct net_if *iface, int status,
299 				     struct wifi_raw_scan_result *entry);
300 #endif /* CONFIG_WIFI_MGMT_RAW_SCAN_RESULTS */
301 struct net_wifi_mgmt_offload {
302 	/**
303 	 * Mandatory to get in first position.
304 	 * A network device should indeed provide a pointer on such
305 	 * net_if_api structure. So we make current structure pointer
306 	 * that can be casted to a net_if_api structure pointer.
307 	 */
308 #ifdef CONFIG_WIFI_USE_NATIVE_NETWORKING
309 	struct ethernet_api wifi_iface;
310 #else
311 	struct offloaded_if_api wifi_iface;
312 #endif
313 
314 	/* cb parameter is the cb that should be called for each
315 	 * result by the driver. The wifi mgmt part will take care of
316 	 * raising the necessary event etc...
317 	 */
318 	int (*scan)(const struct device *dev, scan_result_cb_t cb);
319 	int (*connect)(const struct device *dev,
320 		       struct wifi_connect_req_params *params);
321 	int (*disconnect)(const struct device *dev);
322 	int (*ap_enable)(const struct device *dev,
323 			 struct wifi_connect_req_params *params);
324 	int (*ap_disable)(const struct device *dev);
325 	int (*iface_status)(const struct device *dev, struct wifi_iface_status *status);
326 #ifdef CONFIG_NET_STATISTICS_WIFI
327 	int (*get_stats)(const struct device *dev, struct net_stats_wifi *stats);
328 #endif /* CONFIG_NET_STATISTICS_WIFI */
329 	int (*set_power_save)(const struct device *dev, struct wifi_ps_params *params);
330 	int (*set_twt)(const struct device *dev, struct wifi_twt_params *params);
331 	int (*get_power_save_config)(const struct device *dev, struct wifi_ps_config *config);
332 	int (*reg_domain)(const struct device *dev, struct wifi_reg_domain *reg_domain);
333 };
334 
335 /* Make sure that the network interface API is properly setup inside
336  * Wifi mgmt offload API struct (it is the first one).
337  */
338 BUILD_ASSERT(offsetof(struct net_wifi_mgmt_offload, wifi_iface) == 0);
339 
340 void wifi_mgmt_raise_connect_result_event(struct net_if *iface, int status);
341 void wifi_mgmt_raise_disconnect_result_event(struct net_if *iface, int status);
342 void wifi_mgmt_raise_iface_status_event(struct net_if *iface,
343 		struct wifi_iface_status *iface_status);
344 void wifi_mgmt_raise_twt_event(struct net_if *iface,
345 		struct wifi_twt_params *twt_params);
346 void wifi_mgmt_raise_twt_sleep_state(struct net_if *iface, int twt_sleep_state);
347 #ifdef CONFIG_WIFI_MGMT_RAW_SCAN_RESULTS
348 void wifi_mgmt_raise_raw_scan_result_event(struct net_if *iface,
349 		struct wifi_raw_scan_result *raw_scan_info);
350 #endif /* CONFIG_WIFI_MGMT_RAW_SCAN_RESULTS */
351 void wifi_mgmt_raise_disconnect_complete_event(struct net_if *iface, int status);
352 #ifdef __cplusplus
353 }
354 #endif
355 
356 #endif /* ZEPHYR_INCLUDE_NET_WIFI_MGMT_H_ */
357