@@ -46,7 +46,8 @@ LOG_MODULE_REGISTER(net_wifi_shell, LOG_LEVEL_INF);
4646 NET_EVENT_WIFI_AP_STA_CONNECTED |\
4747 NET_EVENT_WIFI_AP_STA_DISCONNECTED|\
4848 NET_EVENT_WIFI_SIGNAL_CHANGE |\
49- NET_EVENT_WIFI_NEIGHBOR_REP_COMP)
49+ NET_EVENT_WIFI_NEIGHBOR_REP_COMP |\
50+ NET_EVENT_WIFI_P2P_DEVICE_FOUND)
5051
5152#ifdef CONFIG_WIFI_MGMT_RAW_SCAN_RESULTS_ONLY
5253#define WIFI_SHELL_SCAN_EVENTS ( \
@@ -519,6 +520,26 @@ static void handle_wifi_neighbor_rep_complete(struct net_mgmt_event_callback *cb
519520}
520521#endif
521522
523+ #ifdef CONFIG_WIFI_NM_WPA_SUPPLICANT_P2P
524+ static void handle_wifi_p2p_device_found (struct net_mgmt_event_callback * cb )
525+ {
526+ const struct wifi_p2p_device_info * peer_info =
527+ (const struct wifi_p2p_device_info * )cb -> info ;
528+ const struct shell * sh = context .sh ;
529+
530+ if (!peer_info || peer_info -> device_name [0 ] == '\0' ) {
531+ return ;
532+ }
533+
534+ PR ("Device Name: %-20s MAC Address: %02x:%02x:%02x:%02x:%02x:%02x "
535+ "Config Methods: 0x%x\n" ,
536+ peer_info -> device_name ,
537+ peer_info -> mac [0 ], peer_info -> mac [1 ], peer_info -> mac [2 ],
538+ peer_info -> mac [3 ], peer_info -> mac [4 ], peer_info -> mac [5 ],
539+ peer_info -> config_methods );
540+ }
541+ #endif /* CONFIG_WIFI_NM_WPA_SUPPLICANT_P2P */
542+
522543static void wifi_mgmt_event_handler (struct net_mgmt_event_callback * cb ,
523544 uint64_t mgmt_event , struct net_if * iface )
524545{
@@ -552,6 +573,11 @@ static void wifi_mgmt_event_handler(struct net_mgmt_event_callback *cb,
552573 handle_wifi_neighbor_rep_complete (cb , iface );
553574 break ;
554575#endif
576+ #ifdef CONFIG_WIFI_NM_WPA_SUPPLICANT_P2P
577+ case NET_EVENT_WIFI_P2P_DEVICE_FOUND :
578+ handle_wifi_p2p_device_found (cb );
579+ break ;
580+ #endif /* CONFIG_WIFI_NM_WPA_SUPPLICANT_P2P */
555581 default :
556582 break ;
557583 }
@@ -3528,6 +3554,180 @@ static int cmd_wifi_dpp_reconfig(const struct shell *sh, size_t argc, char *argv
35283554}
35293555
35303556#endif /* CONFIG_WIFI_NM_WPA_SUPPLICANT_DPP */
3557+
3558+ #ifdef CONFIG_WIFI_NM_WPA_SUPPLICANT_P2P
3559+ static void print_peer_info (const struct shell * sh , int index ,
3560+ const struct wifi_p2p_device_info * peer )
3561+ {
3562+ uint8_t mac_string_buf [sizeof ("xx:xx:xx:xx:xx:xx" )];
3563+ const char * device_name ;
3564+ const char * device_type ;
3565+ const char * config_methods ;
3566+
3567+ device_name = (peer -> device_name [0 ] != '\0' ) ?
3568+ peer -> device_name : "<Unknown>" ;
3569+ device_type = (peer -> pri_dev_type_str [0 ] != '\0' ) ?
3570+ peer -> pri_dev_type_str : "-" ;
3571+ config_methods = (peer -> config_methods_str [0 ] != '\0' ) ?
3572+ peer -> config_methods_str : "-" ;
3573+
3574+ PR ("%-4d | %-32s | %-17s | %-4d | %-20s | %s\n" ,
3575+ index ,
3576+ device_name ,
3577+ net_sprint_ll_addr_buf (peer -> mac , WIFI_MAC_ADDR_LEN ,
3578+ mac_string_buf ,
3579+ sizeof (mac_string_buf )),
3580+ peer -> rssi ,
3581+ device_type ,
3582+ config_methods );
3583+ }
3584+
3585+ static int cmd_wifi_p2p_peer (const struct shell * sh , size_t argc , char * argv [])
3586+ {
3587+ struct net_if * iface = get_iface (IFACE_TYPE_STA , argc , argv );
3588+ struct wifi_p2p_params params = {0 };
3589+ uint8_t mac_addr [WIFI_MAC_ADDR_LEN ];
3590+ static struct wifi_p2p_device_info peers [WIFI_P2P_MAX_PEERS ];
3591+ int ret ;
3592+ int max_peers = (argc < 2 ) ? WIFI_P2P_MAX_PEERS : 1 ;
3593+
3594+ context .sh = sh ;
3595+
3596+ memset (peers , 0 , sizeof (peers ));
3597+
3598+ params .peers = peers ;
3599+ params .oper = WIFI_P2P_PEER ;
3600+ params .peer_count = max_peers ;
3601+
3602+ if (argc >= 2 ) {
3603+ if (sscanf (argv [1 ], "%hhx:%hhx:%hhx:%hhx:%hhx:%hhx" ,
3604+ & mac_addr [0 ], & mac_addr [1 ], & mac_addr [2 ],
3605+ & mac_addr [3 ], & mac_addr [4 ], & mac_addr [5 ]) != WIFI_MAC_ADDR_LEN ) {
3606+ PR_ERROR ("Invalid MAC address format. Use: XX:XX:XX:XX:XX:XX\n" );
3607+ return - EINVAL ;
3608+ }
3609+ memcpy (params .peer_addr , mac_addr , WIFI_MAC_ADDR_LEN );
3610+ params .peer_count = 1 ;
3611+ } else {
3612+ /* Use broadcast MAC to query all peers */
3613+ memset (params .peer_addr , 0xFF , WIFI_MAC_ADDR_LEN );
3614+ }
3615+
3616+ ret = net_mgmt (NET_REQUEST_WIFI_P2P_OPER , iface , & params , sizeof (params ));
3617+ if (ret ) {
3618+ PR_WARNING ("P2P peer info request failed\n" );
3619+ return - ENOEXEC ;
3620+ }
3621+
3622+ if (params .peer_count > 0 ) {
3623+ PR ("\n%-4s | %-32s | %-17s | %-4s | %-20s | %s\n" ,
3624+ "Num" , "Device Name" , "MAC Address" , "RSSI" , "Device Type" , "Config Methods" );
3625+ for (int i = 0 ; i < params .peer_count ; i ++ ) {
3626+ print_peer_info (sh , i + 1 , & peers [i ]);
3627+ }
3628+ } else {
3629+ if (argc >= 2 ) {
3630+ shell_print (sh , "No information available for peer %s" , argv [1 ]);
3631+ } else {
3632+ shell_print (sh , "No P2P peers found" );
3633+ }
3634+ }
3635+
3636+ return 0 ;
3637+ }
3638+
3639+
3640+ static int cmd_wifi_p2p_find (const struct shell * sh , size_t argc , char * argv [])
3641+ {
3642+ struct net_if * iface = get_iface (IFACE_TYPE_STA , argc , argv );
3643+ struct wifi_p2p_params params = {0 };
3644+
3645+ context .sh = sh ;
3646+
3647+ params .oper = WIFI_P2P_FIND ;
3648+ params .discovery_type = WIFI_P2P_FIND_START_WITH_FULL ;
3649+ params .timeout = 10 ; /* Default 10 second timeout */
3650+
3651+ if (argc > 1 ) {
3652+ int opt ;
3653+ int opt_index = 0 ;
3654+ struct sys_getopt_state * state ;
3655+ static const struct sys_getopt_option long_options [] = {
3656+ {"timeout" , sys_getopt_required_argument , 0 , 't' },
3657+ {"type" , sys_getopt_required_argument , 0 , 'T' },
3658+ {"iface" , sys_getopt_required_argument , 0 , 'i' },
3659+ {"help" , sys_getopt_no_argument , 0 , 'h' },
3660+ {0 , 0 , 0 , 0 }
3661+ };
3662+ long val ;
3663+
3664+ while ((opt = sys_getopt_long (argc , argv , "t:T:i:h" ,
3665+ long_options , & opt_index )) != -1 ) {
3666+ state = sys_getopt_state_get ();
3667+ switch (opt ) {
3668+ case 't' :
3669+ if (!parse_number (sh , & val , state -> optarg , "timeout" , 0 , 65535 )) {
3670+ return - EINVAL ;
3671+ }
3672+ params .timeout = (uint16_t )val ;
3673+ break ;
3674+ case 'T' :
3675+ if (!parse_number (sh , & val , state -> optarg , "type" , 0 , 2 )) {
3676+ return - EINVAL ;
3677+ }
3678+ switch (val ) {
3679+ case 0 :
3680+ params .discovery_type = WIFI_P2P_FIND_ONLY_SOCIAL ;
3681+ break ;
3682+ case 1 :
3683+ params .discovery_type = WIFI_P2P_FIND_PROGRESSIVE ;
3684+ break ;
3685+ case 2 :
3686+ params .discovery_type = WIFI_P2P_FIND_START_WITH_FULL ;
3687+ break ;
3688+ default :
3689+ return - EINVAL ;
3690+ }
3691+ break ;
3692+ case 'i' :
3693+ /* Unused, but parsing to avoid unknown option error */
3694+ break ;
3695+ case 'h' :
3696+ shell_help (sh );
3697+ return - ENOEXEC ;
3698+ default :
3699+ PR_ERROR ("Invalid option %c\n" , state -> optopt );
3700+ return - EINVAL ;
3701+ }
3702+ }
3703+ }
3704+
3705+ if (net_mgmt (NET_REQUEST_WIFI_P2P_OPER , iface , & params , sizeof (params ))) {
3706+ PR_WARNING ("P2P find request failed\n" );
3707+ return - ENOEXEC ;
3708+ }
3709+ PR ("P2P find started\n" );
3710+ return 0 ;
3711+ }
3712+
3713+ static int cmd_wifi_p2p_stop_find (const struct shell * sh , size_t argc , char * argv [])
3714+ {
3715+ struct net_if * iface = get_iface (IFACE_TYPE_STA , argc , argv );
3716+ struct wifi_p2p_params params = {0 };
3717+
3718+ context .sh = sh ;
3719+
3720+ params .oper = WIFI_P2P_STOP_FIND ;
3721+
3722+ if (net_mgmt (NET_REQUEST_WIFI_P2P_OPER , iface , & params , sizeof (params ))) {
3723+ PR_WARNING ("P2P stop find request failed\n" );
3724+ return - ENOEXEC ;
3725+ }
3726+ PR ("P2P find stopped\n" );
3727+ return 0 ;
3728+ }
3729+ #endif /* CONFIG_WIFI_NM_WPA_SUPPLICANT_P2P */
3730+
35313731static int cmd_wifi_pmksa_flush (const struct shell * sh , size_t argc , char * argv [])
35323732{
35333733 struct net_if * iface = get_iface (IFACE_TYPE_STA , argc , argv );
@@ -4232,6 +4432,38 @@ SHELL_SUBCMD_ADD((wifi), bgscan, NULL,
42324432 2 , 6 );
42334433#endif /* CONFIG_WIFI_NM_WPA_SUPPLICANT_BGSCAN */
42344434
4435+ #ifdef CONFIG_WIFI_NM_WPA_SUPPLICANT_P2P
4436+ SHELL_STATIC_SUBCMD_SET_CREATE (
4437+ wifi_cmd_p2p ,
4438+ SHELL_CMD_ARG (find , NULL ,
4439+ "Start P2P device discovery\n"
4440+ "[-t, --timeout=<timeout in seconds>]: Discovery timeout\n"
4441+ "[-T, --type=<0|1|2>]: Discovery type\n"
4442+ " 0: Social channels only (1, 6, 11)\n"
4443+ " 1: Progressive scan (all channels)\n"
4444+ " 2: Full scan first, then social (default)\n"
4445+ "[-i, --iface=<interface index>]: Interface index\n"
4446+ "[-h, --help]: Show help\n" ,
4447+ cmd_wifi_p2p_find , 1 , 6 ),
4448+ SHELL_CMD_ARG (stop_find , NULL ,
4449+ "Stop P2P device discovery\n"
4450+ "[-i, --iface=<interface index>]: Interface index\n" ,
4451+ cmd_wifi_p2p_stop_find , 1 , 2 ),
4452+ SHELL_CMD_ARG (peer , NULL ,
4453+ "Show information about P2P peers\n"
4454+ "Usage: peer [<MAC address>]\n"
4455+ "<MAC address>: Show detailed info for specific peer (format: XX:XX:XX:XX:XX:XX)\n"
4456+ "[-i, --iface=<interface index>]: Interface index\n" ,
4457+ cmd_wifi_p2p_peer , 1 , 3 ),
4458+ SHELL_SUBCMD_SET_END
4459+ );
4460+
4461+ SHELL_SUBCMD_ADD ((wifi ), p2p , & wifi_cmd_p2p ,
4462+ "Wi-Fi Direct (P2P) commands." ,
4463+ NULL ,
4464+ 0 , 0 );
4465+ #endif /* CONFIG_WIFI_NM_WPA_SUPPLICANT_P2P */
4466+
42354467SHELL_SUBCMD_ADD ((wifi ), config , NULL ,
42364468 "Configure STA parameters.\n"
42374469 "-o, --okc=<0/1>: Opportunistic Key Caching. 0: disable, 1: enable\n"
0 commit comments