diff --git a/core/src/wlan_tdls_main.c b/core/src/wlan_tdls_main.c index 000bc78ee1..a423dcd08a 100644 --- a/core/src/wlan_tdls_main.c +++ b/core/src/wlan_tdls_main.c @@ -293,6 +293,9 @@ QDF_STATUS tdls_process_cmd(struct scheduler_msg *msg) case TDLS_NOTIFY_RESET_ADAPTERS: tdls_notify_reset_adapter(msg->bodyptr); break; + case TDLS_CMD_GET_ALL_PEERS: + tdls_get_all_peers_from_list(msg->bodyptr); + break; default: break; } @@ -1001,6 +1004,97 @@ static void tdls_process_reset_adapter(struct wlan_objmgr_vdev *vdev) tdls_timers_stop(tdls_vdev); } +static int __tdls_get_all_peers_from_list( + struct tdls_get_all_peers *get_tdls_peers) +{ + int i; + int len, init_len; + qdf_list_t *head; + qdf_list_node_t *p_node; + struct tdls_peer *curr_peer; + char *buf; + int buf_len; + struct tdls_vdev_priv_obj *tdls_vdev; + QDF_STATUS status; + + tdls_notice("Enter "); + + buf = get_tdls_peers->buf; + buf_len = get_tdls_peers->buf_len; + + if (!tdls_is_vdev_connected(get_tdls_peers->vdev)) { + len = qdf_scnprintf(buf, buf_len, + "\nSTA is not associated\n"); + return len; + } + + tdls_vdev = wlan_vdev_get_tdls_vdev_obj(get_tdls_peers->vdev); + + if (!tdls_vdev) { + len = qdf_scnprintf(buf, buf_len, "TDLS not enabled\n"); + return len; + } + + init_len = buf_len; + len = qdf_scnprintf(buf, buf_len, + "\n%-18s%-3s%-4s%-3s%-5s\n", + "MAC", "Id", "cap", "up", "RSSI"); + buf += len; + buf_len -= len; + len = qdf_scnprintf(buf, buf_len, + "---------------------------------\n"); + buf += len; + buf_len -= len; + + for (i = 0; i < WLAN_TDLS_PEER_LIST_SIZE; i++) { + head = &tdls_vdev->peer_list[i]; + status = qdf_list_peek_front(head, &p_node); + while (QDF_IS_STATUS_SUCCESS(status)) { + curr_peer = qdf_container_of(p_node, + struct tdls_peer, node); + if (buf_len < 32 + 1) + break; + len = qdf_scnprintf(buf, buf_len, + QDF_MAC_ADDRESS_STR "%3d%4s%3s%5d\n", + QDF_MAC_ADDR_ARRAY(curr_peer->peer_mac.bytes), + curr_peer->sta_id, + (curr_peer->tdls_support == + TDLS_CAP_SUPPORTED) ? "Y" : "N", + TDLS_IS_LINK_CONNECTED(curr_peer) ? "Y" : + "N", curr_peer->rssi); + buf += len; + buf_len -= len; + status = qdf_list_peek_next(head, p_node, &p_node); + } + } + + tdls_notice("Exit "); + return init_len - buf_len; +} + +void tdls_get_all_peers_from_list( + struct tdls_get_all_peers *get_tdls_peers) +{ + int32_t len; + struct tdls_soc_priv_obj *tdls_soc_obj; + struct tdls_osif_indication indication; + + if (!get_tdls_peers->vdev) + qdf_mem_free(get_tdls_peers); + + len = __tdls_get_all_peers_from_list(get_tdls_peers); + + indication.status = len; + indication.vdev = get_tdls_peers->vdev; + + tdls_soc_obj = wlan_vdev_get_tdls_soc_obj(get_tdls_peers->vdev); + if (tdls_soc_obj && tdls_soc_obj->tdls_event_cb) + tdls_soc_obj->tdls_event_cb(tdls_soc_obj->tdls_evt_cb_data, + TDLS_EVENT_USER_CMD, &indication); + + qdf_mem_free(get_tdls_peers); +} + void tdls_notify_reset_adapter(struct wlan_objmgr_vdev *vdev) { if (!vdev) { diff --git a/core/src/wlan_tdls_main.h b/core/src/wlan_tdls_main.h index 95178af8cc..0dee99c63f 100644 --- a/core/src/wlan_tdls_main.h +++ b/core/src/wlan_tdls_main.h @@ -574,6 +574,16 @@ QDF_STATUS tdls_notify_sta_connect(struct tdls_sta_notify_params *notify); */ QDF_STATUS tdls_notify_sta_disconnect(struct tdls_sta_notify_params *notify); + +/** + * tdls_get_all_peers_from_list() - get all the tdls peers from the list + * @get_tdls_peers: get_tdls_peers object + * + * Return: None + */ +void tdls_get_all_peers_from_list( + struct tdls_get_all_peers *get_tdls_peers); + /** * tdls_notify_reset_adapter() - notify reset adapter * @vdev: vdev object manager diff --git a/dispatcher/inc/wlan_tdls_public_structs.h b/dispatcher/inc/wlan_tdls_public_structs.h index 936623c0eb..ae0a4077b2 100644 --- a/dispatcher/inc/wlan_tdls_public_structs.h +++ b/dispatcher/inc/wlan_tdls_public_structs.h @@ -62,6 +62,9 @@ /** Maximum time(ms) to wait for tdls mgmt to complete **/ #define WAIT_TIME_FOR_TDLS_MGMT 11000 +/** Maximum time(ms) to wait for tdls mgmt to complete **/ +#define WAIT_TIME_FOR_TDLS_USER_CMD 11000 + /** Maximum waittime for TDLS teardown links **/ #define WAIT_TIME_FOR_TDLS_TEARDOWN_LINKS 10000 @@ -181,6 +184,7 @@ enum tdls_feature_mode { * @TDLS_CMD_SESSION_DECREMENT: notify session decrement * @TDLS_CMD_TEARDOWN_LINKS: notify teardown * @TDLS_NOTIFY_RESET_ADAPTERS: notify adapater reset + * @TDLS_CMD_GET_ALL_PEERS: get all the tdls peers from the list */ enum tdls_command_type { TDLS_CMD_TX_ACTION = 1, @@ -201,6 +205,7 @@ enum tdls_command_type { TDLS_CMD_SESSION_DECREMENT, TDLS_CMD_TEARDOWN_LINKS, TDLS_NOTIFY_RESET_ADAPTERS, + TDLS_CMD_GET_ALL_PEERS, }; /** @@ -213,6 +218,8 @@ enum tdls_command_type { * @TDLS_EVENT_DISCOVERY_REQ: dicovery request * @TDLS_EVENT_TEARDOWN_REQ: teardown request * @TDLS_EVENT_SETUP_REQ: setup request + * @TDLS_EVENT_TEARDOWN_LINKS_DONE: teardown completion event + * @TDLS_EVENT_USER_CMD: tdls user command */ enum tdls_event_type { TDLS_EVENT_VDEV_STATE_CHANGE = 0, @@ -224,6 +231,7 @@ enum tdls_event_type { TDLS_EVENT_TEARDOWN_REQ, TDLS_EVENT_SETUP_REQ, TDLS_EVENT_TEARDOWN_LINKS_DONE, + TDLS_EVENT_USER_CMD, }; /** @@ -968,6 +976,18 @@ struct tdls_validate_action_req { int max_sta_failed; }; +/** + * struct tdls_get_all_peers - get all peers from the list + * @vdev: vdev object + * @buf: output string buffer to hold the peer info + * @buf_len: the size of output string buffer + */ +struct tdls_get_all_peers { + struct wlan_objmgr_vdev *vdev; + char *buf; + int buf_len; +}; + /** * struct tdls_send_action_frame_request - tdls send mgmt request * @vdev: vdev object diff --git a/dispatcher/inc/wlan_tdls_ucfg_api.h b/dispatcher/inc/wlan_tdls_ucfg_api.h index 0a06658fe8..f23bf52aeb 100644 --- a/dispatcher/inc/wlan_tdls_ucfg_api.h +++ b/dispatcher/inc/wlan_tdls_ucfg_api.h @@ -119,6 +119,17 @@ QDF_STATUS ucfg_tdls_update_peer(struct wlan_objmgr_vdev *vdev, QDF_STATUS ucfg_tdls_oper(struct wlan_objmgr_vdev *vdev, const uint8_t *macaddr, enum tdls_command_type cmd); +/** + * ucfg_tdls_get_all_peers() - get all tdls peers from the list + * @vdev: vdev object + * @buf: output buffer + * @buflen: length of written data + * + * Return: QDF_STATUS + */ +QDF_STATUS ucfg_tdls_get_all_peers(struct wlan_objmgr_vdev *vdev, + char *buf, int buflen); + /** * ucfg_tdls_send_mgmt_frame() - send TDLS mgmt frame * @mgmt_req: pointer to TDLS action frame request struct diff --git a/dispatcher/src/wlan_tdls_ucfg_api.c b/dispatcher/src/wlan_tdls_ucfg_api.c index 930ea1bf93..36c6318156 100644 --- a/dispatcher/src/wlan_tdls_ucfg_api.c +++ b/dispatcher/src/wlan_tdls_ucfg_api.c @@ -485,6 +485,35 @@ error: return status; } +QDF_STATUS ucfg_tdls_get_all_peers(struct wlan_objmgr_vdev *vdev, + char *buf, int buflen) +{ + struct scheduler_msg msg = {0, }; + struct tdls_get_all_peers *tdls_peers; + QDF_STATUS status; + + tdls_peers = qdf_mem_malloc(sizeof(*tdls_peers)); + + if (!tdls_peers) { + tdls_err("mem allocate fail"); + return QDF_STATUS_E_NOMEM; + } + + tdls_peers->vdev = vdev; + tdls_peers->buf_len = buflen; + tdls_peers->buf = buf; + + msg.bodyptr = tdls_peers; + msg.callback = tdls_process_cmd; + msg.type = TDLS_CMD_GET_ALL_PEERS; + status = scheduler_post_msg(QDF_MODULE_ID_OS_IF, &msg); + + if (status != QDF_STATUS_SUCCESS) + qdf_mem_free(tdls_peers); + + return QDF_STATUS_SUCCESS; +} + QDF_STATUS ucfg_tdls_send_mgmt_frame( struct tdls_action_frame_request *req) {