12
12
#include <nwp.h>
13
13
#include "siwx91x_wifi.h"
14
14
#include "siwx91x_wifi_ap.h"
15
+ #include "siwx91x_wifi_ps.h"
15
16
#include "siwx91x_wifi_scan.h"
16
17
#include "siwx91x_wifi_socket.h"
17
18
@@ -30,12 +31,6 @@ LOG_MODULE_REGISTER(siwx91x_wifi);
30
31
31
32
NET_BUF_POOL_FIXED_DEFINE (siwx91x_tx_pool , 1 , _NET_ETH_MAX_FRAME_SIZE , 0 , NULL );
32
33
33
- enum {
34
- REQUEST_TWT = 0 ,
35
- SUGGEST_TWT = 1 ,
36
- DEMAND_TWT = 2 ,
37
- };
38
-
39
34
enum {
40
35
STATE_IDLE = 0x00 ,
41
36
/* Failover Roam */
@@ -191,203 +186,6 @@ static enum wifi_mfp_options siwx91x_set_sta_mfp_option(sl_wifi_security_t secur
191
186
return WIFI_MFP_UNKNOWN ;
192
187
}
193
188
194
- static int siwx91x_get_connected_ap_beacon_interval_ms (void )
195
- {
196
- sl_wifi_operational_statistics_t sl_stat ;
197
- sl_wifi_interface_t interface ;
198
- int status ;
199
-
200
- interface = sl_wifi_get_default_interface ();
201
- if (FIELD_GET (SIWX91X_INTERFACE_MASK , interface ) != SL_WIFI_CLIENT_INTERFACE ) {
202
- return 0 ;
203
- }
204
-
205
- status = sl_wifi_get_operational_statistics (SL_WIFI_CLIENT_INTERFACE , & sl_stat );
206
- if (status ) {
207
- return 0 ;
208
- }
209
-
210
- return sys_get_le16 (sl_stat .beacon_interval ) * 1024 / 1000 ;
211
- }
212
-
213
- static int siwx91x_apply_power_save (struct siwx91x_dev * sidev )
214
- {
215
- sl_wifi_performance_profile_t sl_ps_profile ;
216
- sl_wifi_interface_t interface ;
217
- int beacon_interval ;
218
- int status ;
219
-
220
- interface = sl_wifi_get_default_interface ();
221
- if (FIELD_GET (SIWX91X_INTERFACE_MASK , interface ) != SL_WIFI_CLIENT_INTERFACE ) {
222
- LOG_ERR ("Wi-Fi not in station mode" );
223
- return - EINVAL ;
224
- }
225
-
226
- if (sidev -> state == WIFI_STATE_INTERFACE_DISABLED ) {
227
- LOG_ERR ("Command given in invalid state" );
228
- return - EINVAL ;
229
- }
230
-
231
- sl_wifi_get_performance_profile (& sl_ps_profile );
232
-
233
- if (sidev -> ps_params .enabled == WIFI_PS_DISABLED ) {
234
- sl_ps_profile .profile = HIGH_PERFORMANCE ;
235
- goto out ;
236
- }
237
- if (sidev -> ps_params .exit_strategy == WIFI_PS_EXIT_EVERY_TIM ) {
238
- sl_ps_profile .profile = ASSOCIATED_POWER_SAVE_LOW_LATENCY ;
239
- } else if (sidev -> ps_params .exit_strategy == WIFI_PS_EXIT_CUSTOM_ALGO ) {
240
- sl_ps_profile .profile = ASSOCIATED_POWER_SAVE ;
241
- } else {
242
- /* Already sanitized by siwx91x_set_power_save() */
243
- return - EINVAL ;
244
- }
245
-
246
- sl_ps_profile .monitor_interval = sidev -> ps_params .timeout_ms ;
247
-
248
- beacon_interval = siwx91x_get_connected_ap_beacon_interval_ms ();
249
- /* 1000ms is arbitrary sane value */
250
- sl_ps_profile .listen_interval = MIN (beacon_interval * sidev -> ps_params .listen_interval ,
251
- 1000 );
252
-
253
- if (sidev -> ps_params .wakeup_mode == WIFI_PS_WAKEUP_MODE_LISTEN_INTERVAL &&
254
- !sidev -> ps_params .listen_interval ) {
255
- LOG_INF ("Disabling listen interval based wakeup until connection establishes" );
256
- }
257
- if (sidev -> ps_params .wakeup_mode == WIFI_PS_WAKEUP_MODE_DTIM ||
258
- !sidev -> ps_params .listen_interval ) {
259
- sl_ps_profile .dtim_aligned_type = 1 ;
260
- } else if (sidev -> ps_params .wakeup_mode == WIFI_PS_WAKEUP_MODE_LISTEN_INTERVAL ) {
261
- sl_ps_profile .dtim_aligned_type = 0 ;
262
- } else {
263
- /* Already sanitized by siwx91x_set_power_save() */
264
- return - EINVAL ;
265
- }
266
-
267
- out :
268
- status = sl_wifi_set_performance_profile (& sl_ps_profile );
269
- return status ? - EIO : 0 ;
270
- }
271
-
272
- static int siwx91x_set_power_save (const struct device * dev , struct wifi_ps_params * params )
273
- {
274
- struct siwx91x_dev * sidev = dev -> data ;
275
- int status ;
276
-
277
- __ASSERT (params , "params cannot be NULL" );
278
-
279
- switch (params -> type ) {
280
- case WIFI_PS_PARAM_STATE :
281
- sidev -> ps_params .enabled = params -> enabled ;
282
- break ;
283
- case WIFI_PS_PARAM_MODE :
284
- if (params -> mode != WIFI_PS_MODE_LEGACY ) {
285
- params -> fail_reason = WIFI_PS_PARAM_FAIL_OPERATION_NOT_SUPPORTED ;
286
- return - ENOTSUP ;
287
- }
288
- break ;
289
- case WIFI_PS_PARAM_LISTEN_INTERVAL :
290
- sidev -> ps_params .listen_interval = params -> listen_interval ;
291
- break ;
292
- case WIFI_PS_PARAM_WAKEUP_MODE :
293
- if (params -> wakeup_mode != WIFI_PS_WAKEUP_MODE_LISTEN_INTERVAL &&
294
- params -> wakeup_mode != WIFI_PS_WAKEUP_MODE_DTIM ) {
295
- params -> fail_reason = WIFI_PS_PARAM_FAIL_OPERATION_NOT_SUPPORTED ;
296
- return - ENOTSUP ;
297
- }
298
- sidev -> ps_params .wakeup_mode = params -> wakeup_mode ;
299
- break ;
300
- case WIFI_PS_PARAM_TIMEOUT :
301
- /* 1000ms is arbitrary sane value */
302
- if (params -> timeout_ms < SLI_DEFAULT_MONITOR_INTERVAL ||
303
- params -> timeout_ms > 1000 ) {
304
- params -> fail_reason = WIFI_PS_PARAM_FAIL_CMD_EXEC_FAIL ;
305
- return - EINVAL ;
306
- }
307
- sidev -> ps_params .timeout_ms = params -> timeout_ms ;
308
- break ;
309
- case WIFI_PS_PARAM_EXIT_STRATEGY :
310
- if (params -> exit_strategy != WIFI_PS_EXIT_EVERY_TIM &&
311
- params -> exit_strategy != WIFI_PS_EXIT_CUSTOM_ALGO ) {
312
- params -> fail_reason = WIFI_PS_PARAM_FAIL_OPERATION_NOT_SUPPORTED ;
313
- return - ENOTSUP ;
314
- }
315
- sidev -> ps_params .exit_strategy = params -> exit_strategy ;
316
- break ;
317
- default :
318
- params -> fail_reason = WIFI_PS_PARAM_FAIL_CMD_EXEC_FAIL ;
319
- return - EINVAL ;
320
- }
321
- status = siwx91x_apply_power_save (sidev );
322
- if (status ) {
323
- params -> fail_reason = WIFI_PS_PARAM_FAIL_CMD_EXEC_FAIL ;
324
- return status ;
325
- }
326
- return 0 ;
327
- }
328
-
329
- static int siwx91x_get_power_save_config (const struct device * dev , struct wifi_ps_config * config )
330
- {
331
- sl_wifi_performance_profile_t sl_ps_profile ;
332
- struct siwx91x_dev * sidev = dev -> data ;
333
- sl_wifi_interface_t interface ;
334
- uint16_t beacon_interval ;
335
- sl_status_t status ;
336
-
337
- __ASSERT (config , "config cannot be NULL" );
338
-
339
- interface = sl_wifi_get_default_interface ();
340
- if (FIELD_GET (SIWX91X_INTERFACE_MASK , interface ) != SL_WIFI_CLIENT_INTERFACE ) {
341
- LOG_ERR ("Wi-Fi not in station mode" );
342
- return - EINVAL ;
343
- }
344
-
345
- if (sidev -> state == WIFI_STATE_INTERFACE_DISABLED ) {
346
- LOG_ERR ("Command given in invalid state" );
347
- return - EINVAL ;
348
- }
349
-
350
- status = sl_wifi_get_performance_profile (& sl_ps_profile );
351
- if (status != SL_STATUS_OK ) {
352
- LOG_ERR ("Failed to get power save profile: 0x%x" , status );
353
- return - EIO ;
354
- }
355
-
356
- switch (sl_ps_profile .profile ) {
357
- case HIGH_PERFORMANCE :
358
- config -> ps_params .enabled = WIFI_PS_DISABLED ;
359
- break ;
360
- case ASSOCIATED_POWER_SAVE_LOW_LATENCY :
361
- config -> ps_params .enabled = WIFI_PS_ENABLED ;
362
- config -> ps_params .exit_strategy = WIFI_PS_EXIT_EVERY_TIM ;
363
- break ;
364
- case ASSOCIATED_POWER_SAVE :
365
- config -> ps_params .enabled = WIFI_PS_ENABLED ;
366
- config -> ps_params .exit_strategy = WIFI_PS_EXIT_CUSTOM_ALGO ;
367
- break ;
368
- default :
369
- break ;
370
- }
371
-
372
- if (sl_ps_profile .dtim_aligned_type ) {
373
- config -> ps_params .wakeup_mode = WIFI_PS_WAKEUP_MODE_DTIM ;
374
- } else {
375
- config -> ps_params .wakeup_mode = WIFI_PS_WAKEUP_MODE_LISTEN_INTERVAL ;
376
-
377
- beacon_interval = siwx91x_get_connected_ap_beacon_interval_ms ();
378
- if (beacon_interval > 0 ) {
379
- config -> ps_params .listen_interval =
380
- sl_ps_profile .listen_interval / beacon_interval ;
381
- }
382
- }
383
-
384
- /* Device supports only legacy power-save mode */
385
- config -> ps_params .mode = WIFI_PS_MODE_LEGACY ;
386
- config -> ps_params .timeout_ms = sl_ps_profile .monitor_interval ;
387
-
388
- return 0 ;
389
- }
390
-
391
189
static unsigned int siwx91x_on_join (sl_wifi_event_t event ,
392
190
char * result , uint32_t result_size , void * arg )
393
191
{
@@ -929,138 +727,6 @@ static int siwx91x_dev_init(const struct device *dev)
929
727
return 0 ;
930
728
}
931
729
932
- static int siwx91x_convert_z_sl_twt_req_type (enum wifi_twt_setup_cmd z_req_cmd )
933
- {
934
- switch (z_req_cmd ) {
935
- case WIFI_TWT_SETUP_CMD_REQUEST :
936
- return REQUEST_TWT ;
937
- case WIFI_TWT_SETUP_CMD_SUGGEST :
938
- return SUGGEST_TWT ;
939
- case WIFI_TWT_SETUP_CMD_DEMAND :
940
- return DEMAND_TWT ;
941
- default :
942
- return - EINVAL ;
943
- }
944
- }
945
-
946
- static int siwx91x_set_twt_setup (struct wifi_twt_params * params )
947
- {
948
- sl_status_t status ;
949
- int twt_req_type = siwx91x_convert_z_sl_twt_req_type (params -> setup_cmd );
950
-
951
- sl_wifi_twt_request_t twt_req = {
952
- .twt_retry_interval = 5 ,
953
- .wake_duration_unit = 0 ,
954
- .wake_int_mantissa = params -> setup .twt_mantissa ,
955
- .un_announced_twt = !params -> setup .announce ,
956
- .wake_duration = params -> setup .twt_wake_interval ,
957
- .triggered_twt = params -> setup .trigger ,
958
- .wake_int_exp = params -> setup .twt_exponent ,
959
- .implicit_twt = 1 ,
960
- .twt_flow_id = params -> flow_id ,
961
- .twt_enable = 1 ,
962
- .req_type = twt_req_type ,
963
- };
964
-
965
- if (twt_req_type < 0 ) {
966
- params -> fail_reason = WIFI_TWT_FAIL_CMD_EXEC_FAIL ;
967
- return - EINVAL ;
968
- }
969
-
970
- if (!params -> setup .twt_info_disable ) {
971
- params -> fail_reason = WIFI_TWT_FAIL_OPERATION_NOT_SUPPORTED ;
972
- return - ENOTSUP ;
973
- }
974
-
975
- if (params -> setup .responder ) {
976
- params -> fail_reason = WIFI_TWT_FAIL_OPERATION_NOT_SUPPORTED ;
977
- return - ENOTSUP ;
978
- }
979
-
980
- /* implicit -> won't do renegotiation
981
- * explicit -> must do renegotiation for each session
982
- */
983
- if (!params -> setup .implicit ) {
984
- /* explicit twt is not supported */
985
- params -> fail_reason = WIFI_TWT_FAIL_OPERATION_NOT_SUPPORTED ;
986
- return - ENOTSUP ;
987
- }
988
-
989
- if (params -> setup .twt_wake_interval > 255 * 256 ) {
990
- twt_req .wake_duration_unit = 1 ;
991
- twt_req .wake_duration = params -> setup .twt_wake_interval / 1024 ;
992
- } else {
993
- twt_req .wake_duration_unit = 0 ;
994
- twt_req .wake_duration = params -> setup .twt_wake_interval / 256 ;
995
- }
996
-
997
- status = sl_wifi_enable_target_wake_time (& twt_req );
998
- if (status != SL_STATUS_OK ) {
999
- params -> fail_reason = WIFI_TWT_FAIL_CMD_EXEC_FAIL ;
1000
- params -> resp_status = WIFI_TWT_RESP_NOT_RECEIVED ;
1001
- return - EINVAL ;
1002
- }
1003
-
1004
- return 0 ;
1005
- }
1006
-
1007
- static int siwx91x_set_twt_teardown (struct wifi_twt_params * params )
1008
- {
1009
- sl_status_t status ;
1010
- sl_wifi_twt_request_t twt_req = { };
1011
-
1012
- twt_req .twt_enable = 0 ;
1013
-
1014
- if (params -> teardown .teardown_all ) {
1015
- twt_req .twt_flow_id = 0xFF ;
1016
- } else {
1017
- twt_req .twt_flow_id = params -> flow_id ;
1018
- }
1019
-
1020
- status = sl_wifi_disable_target_wake_time (& twt_req );
1021
- if (status != SL_STATUS_OK ) {
1022
- params -> fail_reason = WIFI_TWT_FAIL_CMD_EXEC_FAIL ;
1023
- params -> teardown_status = WIFI_TWT_TEARDOWN_FAILED ;
1024
- return - EINVAL ;
1025
- }
1026
-
1027
- params -> teardown_status = WIFI_TWT_TEARDOWN_SUCCESS ;
1028
-
1029
- return 0 ;
1030
- }
1031
-
1032
- static int siwx91x_set_twt (const struct device * dev , struct wifi_twt_params * params )
1033
- {
1034
- sl_wifi_interface_t interface = sl_wifi_get_default_interface ();
1035
- struct siwx91x_dev * sidev = dev -> data ;
1036
-
1037
- __ASSERT (params , "params cannot be a NULL" );
1038
-
1039
- if (FIELD_GET (SIWX91X_INTERFACE_MASK , interface ) != SL_WIFI_CLIENT_INTERFACE ) {
1040
- params -> fail_reason = WIFI_TWT_FAIL_OPERATION_NOT_SUPPORTED ;
1041
- return - ENOTSUP ;
1042
- }
1043
-
1044
- if (sidev -> state != WIFI_STATE_DISCONNECTED && sidev -> state != WIFI_STATE_INACTIVE &&
1045
- sidev -> state != WIFI_STATE_COMPLETED ) {
1046
- LOG_ERR ("Command given in invalid state" );
1047
- return - EBUSY ;
1048
- }
1049
-
1050
- if (params -> negotiation_type != WIFI_TWT_INDIVIDUAL ) {
1051
- params -> fail_reason = WIFI_TWT_FAIL_OPERATION_NOT_SUPPORTED ;
1052
- return - ENOTSUP ;
1053
- }
1054
-
1055
- if (params -> operation == WIFI_TWT_SETUP ) {
1056
- return siwx91x_set_twt_setup (params );
1057
- } else if (params -> operation == WIFI_TWT_TEARDOWN ) {
1058
- return siwx91x_set_twt_teardown (params );
1059
- }
1060
- params -> fail_reason = WIFI_TWT_FAIL_OPERATION_NOT_SUPPORTED ;
1061
- return - ENOTSUP ;
1062
- }
1063
-
1064
730
static const struct wifi_mgmt_ops siwx91x_mgmt = {
1065
731
.scan = siwx91x_scan ,
1066
732
.connect = siwx91x_connect ,
@@ -1072,12 +738,12 @@ static const struct wifi_mgmt_ops siwx91x_mgmt = {
1072
738
.iface_status = siwx91x_status ,
1073
739
.mode = siwx91x_mode ,
1074
740
.set_twt = siwx91x_set_twt ,
741
+ .set_power_save = siwx91x_set_power_save ,
742
+ .get_power_save_config = siwx91x_get_power_save_config ,
1075
743
#if defined(CONFIG_NET_STATISTICS_WIFI )
1076
744
.get_stats = siwx91x_stats ,
1077
745
#endif
1078
746
.get_version = siwx91x_get_version ,
1079
- .set_power_save = siwx91x_set_power_save ,
1080
- .get_power_save_config = siwx91x_get_power_save_config ,
1081
747
};
1082
748
1083
749
static const struct net_wifi_mgmt_offload siwx91x_api = {
0 commit comments