ath10k: Add support to provide higher range mem chunks in wmi init command
authorSurabhi Vishnoi <svishnoi@codeaurora.org>
Mon, 25 Feb 2019 12:48:46 +0000 (18:18 +0530)
committerKalle Valo <kvalo@codeaurora.org>
Mon, 23 Sep 2019 07:53:30 +0000 (10:53 +0300)
With the current implementation of wmi init command,
there is no provision for the host driver to provide mem
chunks addresses with more than 32-bit, to the firmware.
WCN3990 is a 35-bit target and can accept mem chunks addresses
which are above 32-bit.

If firmware supports address range more than 32 bit, it
advertises the support by setting the WMI_SERVICE_EXTEND_ADDRESS
service. Based on this service fill the upper bits of paddr while
providing the mem chunks in the wmi init command.

Tested HW: WCN3990
Tested FW: WLAN.HL.3.1-00784-QCAHLSWMTPLZ-1

Signed-off-by: Surabhi Vishnoi <svishnoi@codeaurora.org>
Signed-off-by: Kalle Valo <kvalo@codeaurora.org>
drivers/net/wireless/ath/ath10k/wmi-tlv.c
drivers/net/wireless/ath/ath10k/wmi-tlv.h
drivers/net/wireless/ath/ath10k/wmi.h

index 0ca8f9cb4f68f61417e8be626375c880fe43030e..363fd0bd1e2d7fa097ac9026c6eebfb4e84c7a22 100644 (file)
@@ -1649,8 +1649,9 @@ ath10k_wmi_tlv_op_gen_pdev_set_param(struct ath10k *ar, u32 param_id,
 static void
 ath10k_wmi_tlv_put_host_mem_chunks(struct ath10k *ar, void *host_mem_chunks)
 {
-       struct host_memory_chunk *chunk;
+       struct host_memory_chunk_tlv *chunk;
        struct wmi_tlv *tlv;
+       dma_addr_t paddr;
        int i;
        __le16 tlv_len, tlv_tag;
 
@@ -1666,6 +1667,12 @@ ath10k_wmi_tlv_put_host_mem_chunks(struct ath10k *ar, void *host_mem_chunks)
                chunk->size = __cpu_to_le32(ar->wmi.mem_chunks[i].len);
                chunk->req_id = __cpu_to_le32(ar->wmi.mem_chunks[i].req_id);
 
+               if (test_bit(WMI_SERVICE_SUPPORT_EXTEND_ADDRESS,
+                            ar->wmi.svc_map)) {
+                       paddr = ar->wmi.mem_chunks[i].paddr;
+                       chunk->ptr_high = __cpu_to_le32(upper_32_bits(paddr));
+               }
+
                ath10k_dbg(ar, ATH10K_DBG_WMI,
                           "wmi-tlv chunk %d len %d, addr 0x%llx, id 0x%x\n",
                           i,
@@ -1689,7 +1696,7 @@ static struct sk_buff *ath10k_wmi_tlv_op_gen_init(struct ath10k *ar)
        void *ptr;
 
        chunks_len = ar->wmi.num_mem_chunks *
-                    (sizeof(struct host_memory_chunk) + sizeof(*tlv));
+                    (sizeof(struct host_memory_chunk_tlv) + sizeof(*tlv));
        len = (sizeof(*tlv) + sizeof(*cmd)) +
              (sizeof(*tlv) + sizeof(*cfg)) +
              (sizeof(*tlv) + chunks_len);
index 0b7cb011cb19c8dc72fca86d9461499066caaaf6..5a85f2eedfe02ae7879c6cce164dcbcb2a9c19ae 100644 (file)
@@ -1427,6 +1427,11 @@ enum wmi_tlv_service {
        WMI_TLV_SERVICE_WLAN_HPCS_PULSE = 172,
        WMI_TLV_SERVICE_PER_VDEV_CHAINMASK_CONFIG_SUPPORT = 173,
        WMI_TLV_SERVICE_TX_DATA_MGMT_ACK_RSSI = 174,
+       WMI_TLV_SERVICE_NAN_DISABLE_SUPPORT = 175,
+       WMI_TLV_SERVICE_HTT_H2T_NO_HTC_HDR_LEN_IN_MSG_LEN = 176,
+       WMI_TLV_SERVICE_COEX_SUPPORT_UNEQUAL_ISOLATION = 177,
+       WMI_TLV_SERVICE_HW_DB2DBM_CONVERSION_SUPPORT = 178,
+       WMI_TLV_SERVICE_SUPPORT_EXTEND_ADDRESS = 179,
 
        WMI_TLV_MAX_EXT_SERVICE = 256,
 };
@@ -1606,6 +1611,9 @@ wmi_tlv_svc_map_ext(const __le32 *in, unsigned long *out, size_t len)
               WMI_TLV_MAX_SERVICE);
        SVCMAP(WMI_TLV_SERVICE_TX_DATA_MGMT_ACK_RSSI,
               WMI_SERVICE_TX_DATA_ACK_RSSI, WMI_TLV_MAX_SERVICE);
+       SVCMAP(WMI_TLV_SERVICE_SUPPORT_EXTEND_ADDRESS,
+              WMI_SERVICE_SUPPORT_EXTEND_ADDRESS,
+              WMI_TLV_MAX_SERVICE);
 }
 
 #undef SVCMAP
@@ -1761,6 +1769,21 @@ struct wmi_tlv_resource_config {
        __le32 host_capab;
 } __packed;
 
+/* structure describing host memory chunk. */
+struct host_memory_chunk_tlv {
+       /* id of the request that is passed up in service ready */
+       __le32 req_id;
+
+       /* the physical address the memory chunk */
+       __le32 ptr;
+
+       /* size of the chunk */
+       __le32 size;
+
+       /* the upper 32 bit address valid only for more than 32 bit target */
+       __le32 ptr_high;
+} __packed;
+
 struct wmi_tlv_init_cmd {
        struct wmi_tlv_abi_version abi;
        __le32 num_host_mem_chunks;
index fc95c0c460ac371aefce100ef5aa6251398c5fc1..bdeebc5b84b44d8497b45d57445f580e070bae2a 100644 (file)
@@ -202,6 +202,7 @@ enum wmi_service {
        WMI_SERVICE_REPORT_AIRTIME,
        WMI_SERVICE_SYNC_DELETE_CMDS,
        WMI_SERVICE_TX_PWR_PER_PEER,
+       WMI_SERVICE_SUPPORT_EXTEND_ADDRESS,
 
        /* Remember to add the new value to wmi_service_name()! */
 
@@ -496,6 +497,7 @@ static inline char *wmi_service_name(enum wmi_service service_id)
        SVCSTR(WMI_SERVICE_REPORT_AIRTIME);
        SVCSTR(WMI_SERVICE_SYNC_DELETE_CMDS);
        SVCSTR(WMI_SERVICE_TX_PWR_PER_PEER);
+       SVCSTR(WMI_SERVICE_SUPPORT_EXTEND_ADDRESS);
 
        case WMI_SERVICE_MAX:
                return NULL;