wlan-ap-Telecominfraproject/feeds/ipq95xx/mac80211/patches/qca/670-02-ath12k-Add-mlo-wmi-setup-apis.patch
John Crispin 144c5d00f4 ipq95xx/mac80211: update to ATH12.3-CS
Signed-off-by: John Crispin <john@phrozen.org>
2024-02-28 18:56:21 +01:00

374 lines
10 KiB
Diff

From 31ba379043c3bde8f69d1e898dcd0d54b669e3c5 Mon Sep 17 00:00:00 2001
From: Bhagavathi Perumal S <quic_bperumal@quicinc.com>
Date: Tue, 14 Sep 2021 13:06:02 +0530
Subject: [PATCH 2/4] ath12k: Add mlo wmi setup apis
Added WMI helper function for the MLO setup/teardown command and event.
Add appropriate WMI tag, command id and event id to parse the event and
send request.
Signed-off-by: Bhagavathi Perumal S <quic_bperumal@quicinc.com>
Signed-off-by: Karthikeyan Periyasamy <quic_periyasa@quicinc.com>
---
drivers/net/wireless/ath/ath12k/core.c | 8 --
drivers/net/wireless/ath/ath12k/core.h | 3 +-
drivers/net/wireless/ath/ath12k/wmi.c | 170 ++++++++++++++++++++++++-
drivers/net/wireless/ath/ath12k/wmi.h | 66 +++++++++-
4 files changed, 229 insertions(+), 18 deletions(-)
--- a/drivers/net/wireless/ath/ath12k/core.h
+++ b/drivers/net/wireless/ath/ath12k/core.h
@@ -853,7 +853,8 @@ struct mlo_timestamp {
struct ath12k_pdev {
struct ath12k *ar;
- u32 pdev_id;
+ u16 pdev_id;
+ u16 hw_link_id;
struct ath12k_pdev_cap cap;
u8 mac_addr[ETH_ALEN];
struct mlo_timestamp timestamp;
--- a/drivers/net/wireless/ath/ath12k/wmi.c
+++ b/drivers/net/wireless/ath/ath12k/wmi.c
@@ -485,6 +485,8 @@ ath12k_pull_mac_phy_cap_svc_ready_ext(st
mac_phy_caps = wmi_mac_phy_caps + phy_idx;
pdev->pdev_id = mac_phy_caps->pdev_id;
+ pdev->hw_link_id = mac_phy_caps->hw_link_id;
+
pdev_cap->supported_bands |= mac_phy_caps->supported_bands;
pdev_cap->ampdu_density = mac_phy_caps->ampdu_density;
@@ -9026,6 +9028,66 @@ exit:
kfree(tb);
}
+static void ath12k_wmi_event_mlo_setup_complete(struct ath12k_base *ab,
+ struct sk_buff *skb)
+{
+ const void **tb;
+ const struct wmi_mlo_setup_complete_event_fixed_param *ev;
+ int ret;
+
+ tb = ath12k_wmi_tlv_parse_alloc(ab, skb->data, skb->len, GFP_ATOMIC);
+ if (IS_ERR(tb)) {
+ ret = PTR_ERR(tb);
+ ath12k_warn(ab,
+ "failed to parse mlo setup complete event tlv %d\n",
+ ret);
+ return;
+ }
+
+ ev = tb[WMI_TAG_MLO_SETUP_COMPLETE_EVENT];
+ if (!ev) {
+ ath12k_warn(ab, "failed to fetch mlo setup complete event\n");
+ kfree(tb);
+ return;
+ }
+
+ if (ev->status)
+ ath12k_warn(ab, "mlo setup, pdev id %u, err %u\n",
+ ev->pdev_id, ev->status);
+
+ kfree(tb);
+}
+
+static void ath12k_wmi_event_teardown_complete(struct ath12k_base *ab,
+ struct sk_buff *skb)
+{
+ const void **tb;
+ const struct wmi_mlo_teardown_complete_fixed_param *ev;
+ int ret;
+
+ tb = ath12k_wmi_tlv_parse_alloc(ab, skb->data, skb->len, GFP_ATOMIC);
+ if (IS_ERR(tb)) {
+ ret = PTR_ERR(tb);
+ ath12k_warn(ab,
+ "failed to parse teardown complete event tlv %d\n",
+ ret);
+ return;
+ }
+
+ ev = tb[WMI_TAG_MLO_TEARDOWN_COMPLETE];
+ if (!ev) {
+ ath12k_warn(ab, "failed to fetch teardown complete event\n");
+ kfree(tb);
+ return;
+ }
+
+ if (ev->status)
+ ath12k_warn(ab, "mlo teardown, pdev id %u, err %u\n",
+ ev->pdev_id, ev->status);
+
+ kfree(tb);
+}
+
static void ath12k_wmi_tlv_op_rx(struct ath12k_base *ab, struct sk_buff *skb)
{
struct wmi_cmd_hdr *cmd_hdr;
@@ -9160,6 +9222,12 @@ static void ath12k_wmi_tlv_op_rx(struct
case WMI_STATS_CTRL_PATH_EVENTID:
ath12k_process_tpc_stats(ab, skb);
break;
+ case WMI_MLO_SETUP_COMPLETE_EVENTID:
+ ath12k_wmi_event_mlo_setup_complete(ab, skb);
+ break;
+ case WMI_MLO_TEARDOWN_COMPLETE_EVENTID:
+ ath12k_wmi_event_teardown_complete(ab, skb);
+ break;
/* TODO: Add remaining events */
default:
ath12k_dbg(ab, ATH12K_DBG_WMI, "Unknown eventid: 0x%x\n", id);
@@ -9516,3 +9584,100 @@ int ath12k_wmi_pdev_ap_ps_cmd_send(struc
return ret;
}
+
+int ath12k_wmi_mlo_setup(struct ath12k *ar,
+ struct wmi_mlo_setup_params *mlo_params)
+{
+ struct ath12k_pdev_wmi *wmi = ar->wmi;
+ struct wmi_mlo_setup_cmd_fixed_param *cmd;
+ struct sk_buff *skb;
+ struct wmi_tlv *tlv;
+ u32 *plinks;
+ u32 num_links;
+ int i, ret, len;
+
+ num_links = mlo_params->num_partner_links;
+
+ len = sizeof(*cmd) + TLV_HDR_SIZE + (num_links * sizeof(u32));
+ skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, len);
+ if (!skb)
+ return -ENOMEM;
+
+ cmd = (struct wmi_mlo_setup_cmd_fixed_param *)skb->data;
+ cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_MLO_SETUP_CMD) |
+ FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE);
+ cmd->mld_group_id = mlo_params->group_id;
+ cmd->pdev_id = ar->pdev->pdev_id;
+
+ tlv = (struct wmi_tlv *)(skb->data + sizeof(*cmd));
+ tlv->header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_ARRAY_UINT32) |
+ FIELD_PREP(WMI_TLV_LEN, num_links);
+
+ plinks = (u32 *)tlv->value;
+ for (i = 0; i < num_links; i++)
+ plinks[i] = mlo_params->partner_link_id[i];
+
+ ret = ath12k_wmi_cmd_send(wmi, skb, WMI_MLO_SETUP_CMDID);
+ if (ret) {
+ ath12k_warn(ar->ab,
+ "failed to submit WMI_MLO_SETUP_CMDID cmd\n");
+ dev_kfree_skb(skb);
+ }
+
+ return ret;
+}
+
+int ath12k_wmi_mlo_ready(struct ath12k *ar)
+{
+ struct ath12k_pdev_wmi *wmi = ar->wmi;
+ struct wmi_mlo_ready_cmd_fixed_param *cmd;
+ struct sk_buff *skb;
+ int ret, len;
+
+ len = sizeof(*cmd);
+ skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, len);
+ if (!skb)
+ return -ENOMEM;
+
+ cmd = (struct wmi_mlo_ready_cmd_fixed_param *)skb->data;
+ cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_MLO_READY_CMD) |
+ FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE);
+ cmd->pdev_id = ar->pdev->pdev_id;
+
+ ret = ath12k_wmi_cmd_send(wmi, skb, WMI_MLO_READY_CMDID);
+ if (ret) {
+ ath12k_warn(ar->ab,
+ "failed to submit WMI_MLO_READY_CMDID cmd\n");
+ dev_kfree_skb(skb);
+ }
+
+ return ret;
+}
+
+int ath12k_wmi_mlo_teardown(struct ath12k *ar)
+{
+ struct ath12k_pdev_wmi *wmi = ar->wmi;
+ struct wmi_mlo_teardown_fixed_param *cmd;
+ struct sk_buff *skb;
+ int ret, len;
+
+ len = sizeof(*cmd);
+ skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, len);
+ if (!skb)
+ return -ENOMEM;
+
+ cmd = (struct wmi_mlo_teardown_fixed_param *)skb->data;
+ cmd->tlv_header = FIELD_PREP(WMI_TLV_TAG, WMI_TAG_MLO_TEARDOWN_CMD) |
+ FIELD_PREP(WMI_TLV_LEN, sizeof(*cmd) - TLV_HDR_SIZE);
+ cmd->pdev_id = ar->pdev->pdev_id;
+ cmd->reason_code = WMI_MLO_TEARDOWN_SSR_REASON;
+
+ ret = ath12k_wmi_cmd_send(wmi, skb, WMI_MLO_TEARDOWN_CMDID);
+ if (ret) {
+ ath12k_warn(ar->ab,
+ "failed to submit WMI MLO teardown cmd\n");
+ dev_kfree_skb(skb);
+ }
+
+ return ret;
+}
--- a/drivers/net/wireless/ath/ath12k/wmi.h
+++ b/drivers/net/wireless/ath/ath12k/wmi.h
@@ -202,6 +202,7 @@ enum wmi_cmd_group {
WMI_GRP_TWT = 0x3e,
WMI_GRP_MOTION_DET = 0x3f,
WMI_GRP_SPATIAL_REUSE = 0x40,
+ WMI_GRP_MLO = 0x48,
};
#define WMI_CMD_GRP(grp_id) (((grp_id) << 12) | 0x1)
@@ -626,6 +627,11 @@ enum wmi_tlv_cmd_id {
WMI_PDEV_OBSS_PD_SPATIAL_REUSE_CMDID =
WMI_TLV_CMD(WMI_GRP_SPATIAL_REUSE),
WMI_PDEV_OBSS_PD_SPATIAL_REUSE_SET_DEF_OBSS_THRESH_CMDID,
+ WMI_MLO_LINK_SET_ACTIVE_CMDID = WMI_TLV_CMD(WMI_GRP_MLO),
+ WMI_MLO_SETUP_CMDID,
+ WMI_MLO_READY_CMDID,
+ WMI_MLO_TEARDOWN_CMDID,
+ WMI_MLO_PEER_TID_TO_LINK_MAP_CMDID,
};
enum wmi_tlv_event_id {
@@ -849,6 +855,9 @@ enum wmi_tlv_event_id {
WMI_TWT_DEL_DIALOG_EVENTID,
WMI_TWT_PAUSE_DIALOG_EVENTID,
WMI_TWT_RESUME_DIALOG_EVENTID,
+ WMI_MLO_LINK_SET_ACTIVE_RESP_EVENTID = WMI_EVT_GRP_START_ID(WMI_GRP_MLO),
+ WMI_MLO_SETUP_COMPLETE_EVENTID,
+ WMI_MLO_TEARDOWN_COMPLETE_EVENTID,
};
enum wmi_tlv_pdev_param {
@@ -1923,6 +1932,14 @@ enum wmi_tlv_tag {
WMI_TAG_VDEV_CH_POWER_INFO,
WMI_TAG_EHT_RATE_SET = 0x3C4,
WMI_TAG_DCS_AWGN_INT_TYPE = 0x3C5,
+ WMI_TAG_MLO_TX_SEND_PARAMS,
+ WMI_TAG_MLO_PARTNER_LINK_PARAMS,
+ WMI_TAG_MLO_PARTNER_LINK_PARAMS_PEER_ASSOC,
+ WMI_TAG_MLO_SETUP_CMD,
+ WMI_TAG_MLO_SETUP_COMPLETE_EVENT,
+ WMI_TAG_MLO_READY_CMD,
+ WMI_TAG_MLO_TEARDOWN_CMD,
+ WMI_TAG_MLO_TEARDOWN_COMPLETE,
WMI_TAG_PDEV_PKTLOG_DECODE_INFO = 0x414,
WMI_TAG_TPC_STATS_GET_CMD = 0x38B,
WMI_TAG_TPC_STATS_EVENT_FIXED_PARAM,
@@ -2278,6 +2295,7 @@ struct ath12k_ppe_threshold {
u32 ru_bit_mask;
u32 ppet16_ppet8_ru3_ru0[PSOC_HOST_MAX_NUM_SS];
};
+
struct ath12k_service_ext_param {
u32 default_conc_scan_config_bits;
u32 default_fw_config_bits;
@@ -2699,6 +2717,25 @@ enum wmi_eht_mcs_support {
WMI_EHT_MCS_NOT_SUPPORTED = 3,
};
+#define EML_INFO_EMLSR_SUPPORT BIT(0)
+#define EML_INFO_EMLSR_PADDING_DELAY GENMASK(3, 1)
+#define EML_INFO_EMLSR_TRANSITION_DELAY GENMASK(6, 4)
+#define EML_INFO_EMLMR_SUPPORT BIT(7)
+#define EML_INFO_EMLMR_PADDING_DELAY GENMASK(10, 8)
+#define EML_INFO_TRANSITION_TIMEOUT GENMASK(14, 11)
+
+enum wmi_mld_cap_tid_to_link_map {
+ WMI_MLD_MAP_TID_TO_LINK_NONE,
+ WMI_MLD_MAP_EACH_TID_TO_SAME_OR_DIFF_LINK_SET,
+ WMI_MLD_MAP_ALL_TID_TO_SAME_LINK_SET,
+};
+
+#define MLD_INFO_MAX_SIMULTANEOUS_LINK GENMASK(3, 0)
+#define MLD_INFO_SRS_SUPPORT BIT(4)
+#define MLD_INFO_TID_TO_LINK_MAP_SUPPORT GENMASK(6, 5)
+#define MLD_INFO_FREQ_SEPARATION_STR GENMASK(11, 7)
+#define MLD_INFO_AAR_SUPPORT BIT(12)
+
struct wmi_mac_phy_caps_ext {
u32 hw_mode_id;
union {
@@ -2720,6 +2757,8 @@ struct wmi_mac_phy_caps_ext {
u32 eht_cap_info_internal;
u32 eht_supp_mcs_ext_2G[WMI_MAX_EHT_SUPP_MCS_2G_SIZE];
u32 eht_supp_mcs_ext_5G[WMI_MAX_EHT_SUPP_MCS_5G_SIZE];
+ u32 eml_info;
+ u32 mld_info;
} __packed;
/* 2 word representation of MAC addr */
@@ -5975,6 +6014,7 @@ struct wmi_dbglog_config_cmd_fixed_param
#define MAX_RADIOS 3
+#define WMI_MLO_CMD_TIMEOUT_HZ (5 * HZ)
#define WMI_SERVICE_READY_TIMEOUT_HZ (5 * HZ)
#define WMI_SEND_TIMEOUT_HZ (3 * HZ)
@@ -6162,6 +6202,43 @@ struct wmi_wow_ev_arg {
u32 data_len;
};
+struct wmi_mlo_setup_cmd_fixed_param {
+ u32 tlv_header;
+ u32 mld_group_id;
+ u32 pdev_id;
+} __packed;
+
+struct wmi_mlo_setup_params {
+ u32 group_id;
+ u8 num_partner_links;
+ u8 *partner_link_id;
+};
+
+struct wmi_mlo_ready_cmd_fixed_param {
+ u32 tlv_header;
+ u32 pdev_id;
+} __packed;
+
+enum wmi_mlo_tear_down_reason_code_type {
+ WMI_MLO_TEARDOWN_SSR_REASON,
+};
+
+struct wmi_mlo_teardown_fixed_param {
+ u32 tlv_header;
+ u32 pdev_id;
+ u32 reason_code;
+} __packed;
+
+struct wmi_mlo_setup_complete_event_fixed_param {
+ u32 pdev_id;
+ u32 status;
+} __packed;
+
+struct wmi_mlo_teardown_complete_fixed_param {
+ u32 pdev_id;
+ u32 status;
+} __packed;
+
#define ATH12K_FW_STATS_BUF_SIZE (1024 * 1024)
void ath12k_wmi_init_qcn9274(struct ath12k_base *ab,
@@ -6326,4 +6403,8 @@ int ath12k_wmi_send_vdev_set_tpc_power(s
int ath12k_wmi_pdev_m3_dump_enable(struct ath12k *ar, u32 enable);
int ath12k_wmi_pdev_get_tpc_table_cmdid(struct ath12k *ar);
void ath12k_wmi_free_tpc_stats_mem(struct ath12k *ar);
+int ath12k_wmi_mlo_setup(struct ath12k *ar,
+ struct wmi_mlo_setup_params *mlo_params);
+int ath12k_wmi_mlo_ready(struct ath12k *ar);
+int ath12k_wmi_mlo_teardown(struct ath12k *ar);
#endif