From patchwork Wed Oct 16 06:35:03 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Kang Yang X-Patchwork-Id: 836138 Received: from mx0a-0031df01.pphosted.com (mx0a-0031df01.pphosted.com [205.220.168.131]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id A5C2318C32E for ; Wed, 16 Oct 2024 06:36:56 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=205.220.168.131 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1729060618; cv=none; b=LMbAWpb+I2xw2AAtHp8h7k155YBg8l/i51XjMeTcrwzEcw5RYBC2beohKhSp/RS29asYQVZbnV0QppyVguLSG2KufcfX3IlNQf/mZGVW8OgF+Ah6br0PUzh91tpmAfIBmVAQOl2MhlaZsGyEwGT3imDeN1W8QpjZuH7FW3qBxtU= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1729060618; c=relaxed/simple; bh=CiNhcYVyxwmlN57hrsbJb6tfqtY9uF4hI94cmXWUNCw=; h=From:To:CC:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version:Content-Type; b=szBp2xh1NCUPLKEot0aWANsNVRzPia6SeOG8n3Q6OebumhQ8FKHJYnTehV+sNvnPad/0mavnCckyQcZy9g2GAx0AGPAbTFCa3ZmoxjcACtvreA4XCCn6LLnfvag5T39L282lcoPtbgQICOKA6InCkaWt54WTTJch/YbbwnkPsH0= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=quicinc.com; spf=pass smtp.mailfrom=quicinc.com; dkim=pass (2048-bit key) header.d=quicinc.com header.i=@quicinc.com header.b=Ge5R/SBf; arc=none smtp.client-ip=205.220.168.131 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=quicinc.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=quicinc.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=quicinc.com header.i=@quicinc.com header.b="Ge5R/SBf" Received: from pps.filterd (m0279862.ppops.net [127.0.0.1]) by mx0a-0031df01.pphosted.com (8.18.1.2/8.18.1.2) with ESMTP id 49G3pg40019227; Wed, 16 Oct 2024 06:36:54 GMT DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=quicinc.com; h= cc:content-transfer-encoding:content-type:date:from:in-reply-to :message-id:mime-version:references:subject:to; s=qcppdkim1; bh= +3Fm1e4oIUsaj6mAZylxDP6aBaTfJFMzhZB6qGFVJQs=; b=Ge5R/SBfWQomzzod BOk/qNLADeDsyHxsZ2VMQ310Bynno5oftX4drEMpTTzrCtxox6HhCsFxPLR39+pw f/9ew4qN21WmYZuiLF1X3RyEBUByiH7EAgO1Kanafg6A+pi278YB5t2XGuqYeF4W At51UObGelOWGLSWGj+ihbytIGh13L20kyY0bMAp+5gof1kJ2x3JGv6Uiz+GXgxA Y+S0eVOlxF/kAuB45yDW8hL/t00n3Oftd+njnRnHTItVpz1HZxPivh9H/05esRTj dav3xg4NbIiwFbGNwJQyZjGyIDZC9S68Mzgrze816CI9L0gVSKYk3mElfsixZhiZ JTgAuQ== Received: from nalasppmta02.qualcomm.com (Global_NAT1.qualcomm.com [129.46.96.20]) by mx0a-0031df01.pphosted.com (PPS) with ESMTPS id 42a5xygb07-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT); Wed, 16 Oct 2024 06:36:54 +0000 (GMT) Received: from nalasex01b.na.qualcomm.com (nalasex01b.na.qualcomm.com [10.47.209.197]) by NALASPPMTA02.qualcomm.com (8.18.1.2/8.18.1.2) with ESMTPS id 49G6afDB004576 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT); Wed, 16 Oct 2024 06:36:41 GMT Received: from kangyang.ap.qualcomm.com (10.80.80.8) by nalasex01b.na.qualcomm.com (10.47.209.197) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.1544.9; Tue, 15 Oct 2024 23:36:39 -0700 From: Kang Yang To: CC: , Subject: [PATCH v5 1/4] wifi: ath12k: add configure country code for WCN7850 Date: Wed, 16 Oct 2024 14:35:03 +0800 Message-ID: <20241016063506.1037-2-quic_kangyang@quicinc.com> X-Mailer: git-send-email 2.34.1.windows.1 In-Reply-To: <20241016063506.1037-1-quic_kangyang@quicinc.com> References: <20241016063506.1037-1-quic_kangyang@quicinc.com> Precedence: bulk X-Mailing-List: linux-wireless@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 X-ClientProxiedBy: nasanex01b.na.qualcomm.com (10.46.141.250) To nalasex01b.na.qualcomm.com (10.47.209.197) X-QCInternal: smtphost X-Proofpoint-Virus-Version: vendor=nai engine=6200 definitions=5800 signatures=585085 X-Proofpoint-GUID: GoqnWoCe17NgGz4A7GSRKiv6QH-kUL4R X-Proofpoint-ORIG-GUID: GoqnWoCe17NgGz4A7GSRKiv6QH-kUL4R X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.293,Aquarius:18.0.1039,Hydra:6.0.680,FMLib:17.12.60.29 definitions=2024-09-06_09,2024-09-06_01,2024-09-02_01 X-Proofpoint-Spam-Details: rule=outbound_notspam policy=outbound score=0 impostorscore=0 mlxlogscore=999 lowpriorityscore=0 mlxscore=0 bulkscore=0 malwarescore=0 suspectscore=0 priorityscore=1501 phishscore=0 clxscore=1015 adultscore=0 spamscore=0 classifier=spam adjust=0 reason=mlx scancount=1 engine=8.19.0-2409260000 definitions=main-2410160042 From: Wen Gong Add handler to send WMI_SET_CURRENT_COUNTRY_CMDID to firmware, which is used for WCN7850 to update country code. Tested-on: WCN7850 hw2.0 PCI WLAN.HMT.1.0.c5-00481-QCAHMTSWPL_V1.0_V2.0_SILICONZ-3 Signed-off-by: Wen Gong Signed-off-by: Kang Yang --- drivers/net/wireless/ath/ath12k/wmi.c | 36 +++++++++++++++++++++++++++ drivers/net/wireless/ath/ath12k/wmi.h | 13 ++++++++++ 2 files changed, 49 insertions(+) diff --git a/drivers/net/wireless/ath/ath12k/wmi.c b/drivers/net/wireless/ath/ath12k/wmi.c index 190439ad7f23..f7b6e0a45f7c 100644 --- a/drivers/net/wireless/ath/ath12k/wmi.c +++ b/drivers/net/wireless/ath/ath12k/wmi.c @@ -3084,6 +3084,42 @@ int ath12k_wmi_send_init_country_cmd(struct ath12k *ar, return ret; } +int ath12k_wmi_send_set_current_country_cmd(struct ath12k *ar, + struct wmi_set_current_country_arg *arg) +{ + struct ath12k_wmi_pdev *wmi = ar->wmi; + struct wmi_set_current_country_cmd *cmd; + struct sk_buff *skb; + int ret; + + skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); + if (!skb) + return -ENOMEM; + + cmd = (struct wmi_set_current_country_cmd *)skb->data; + cmd->tlv_header = + ath12k_wmi_tlv_cmd_hdr(WMI_TAG_SET_CURRENT_COUNTRY_CMD, + sizeof(*cmd)); + + cmd->pdev_id = cpu_to_le32(ar->pdev->pdev_id); + memcpy(&cmd->new_alpha2, &arg->alpha2, sizeof(arg->alpha2)); + ret = ath12k_wmi_cmd_send(wmi, skb, WMI_SET_CURRENT_COUNTRY_CMDID); + + ath12k_dbg(ar->ab, ATH12K_DBG_WMI, + "set current country pdev id %d alpha2 %c%c\n", + ar->pdev->pdev_id, + arg->alpha2[0], + arg->alpha2[1]); + + if (ret) { + ath12k_warn(ar->ab, + "failed to send WMI_SET_CURRENT_COUNTRY_CMDID: %d\n", ret); + dev_kfree_skb(skb); + } + + return ret; +} + int ath12k_wmi_send_twt_enable_cmd(struct ath12k *ar, u32 pdev_id) { diff --git a/drivers/net/wireless/ath/ath12k/wmi.h b/drivers/net/wireless/ath/ath12k/wmi.h index 6a913f9b8315..1797f5c88fb5 100644 --- a/drivers/net/wireless/ath/ath12k/wmi.h +++ b/drivers/net/wireless/ath/ath12k/wmi.h @@ -3945,6 +3945,16 @@ struct ath12k_wmi_eht_rate_set_params { #define MAX_6G_REG_RULES 5 #define REG_US_5G_NUM_REG_RULES 4 +struct wmi_set_current_country_arg { + u8 alpha2[REG_ALPHA2_LEN]; +}; + +struct wmi_set_current_country_cmd { + __le32 tlv_header; + __le32 pdev_id; + __le32 new_alpha2; +} __packed; + enum wmi_start_event_param { WMI_VDEV_START_RESP_EVENT = 0, WMI_VDEV_RESTART_RESP_EVENT, @@ -5547,6 +5557,9 @@ int ath12k_wmi_send_bcn_offload_control_cmd(struct ath12k *ar, u32 vdev_id, u32 bcn_ctrl_op); int ath12k_wmi_send_init_country_cmd(struct ath12k *ar, struct ath12k_wmi_init_country_arg *arg); +int +ath12k_wmi_send_set_current_country_cmd(struct ath12k *ar, + struct wmi_set_current_country_arg *arg); int ath12k_wmi_peer_rx_reorder_queue_setup(struct ath12k *ar, int vdev_id, const u8 *addr, dma_addr_t paddr, u8 tid, From patchwork Wed Oct 16 06:35:04 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Kang Yang X-Patchwork-Id: 836670 Received: from mx0b-0031df01.pphosted.com (mx0b-0031df01.pphosted.com [205.220.180.131]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 27A6018C32E for ; Wed, 16 Oct 2024 06:37:18 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=205.220.180.131 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1729060641; cv=none; b=XWGc89fa7m2m53fEw4JDWUtU41tnrR+GXRoBnuahFK45tYLPnDi0Y8b+DsXRg1bAoUjR88LviIIqDr6sbdHmEiGWhkjw/sV8Zncb0EoTozMMoCsfCBe9O/xalUtm1mEtdMGa1nsyeQWiB7kPSyq1rC3YCNCjdMBR3snWoonO7FI= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1729060641; c=relaxed/simple; bh=/RXouaJti5J0YVkfH7clUrj0SPsvKOeXn0SySKw9gHE=; h=From:To:CC:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version:Content-Type; b=ktk7+l8Y5irGykRAP/KFJJJ2KRWCW8e+wkbRXTzbV/q/AieS/ZAy6EUJW+w58UmVGhQr/lvNgPYrD7lQpgKudsDo8gmc+kvBgiB0K5gva6b16qUF9S7KhcSTqikrZksWK2oGCPaKeJNMTRhEKkMqs5euBmkR+Mvx8gsbA8FRRPE= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=quicinc.com; spf=pass smtp.mailfrom=quicinc.com; dkim=pass (2048-bit key) header.d=quicinc.com header.i=@quicinc.com header.b=QkqBmlqC; arc=none smtp.client-ip=205.220.180.131 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=quicinc.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=quicinc.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=quicinc.com header.i=@quicinc.com header.b="QkqBmlqC" Received: from pps.filterd (m0279871.ppops.net [127.0.0.1]) by mx0a-0031df01.pphosted.com (8.18.1.2/8.18.1.2) with ESMTP id 49G5MGsf028548; Wed, 16 Oct 2024 06:36:44 GMT DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=quicinc.com; h= cc:content-transfer-encoding:content-type:date:from:in-reply-to :message-id:mime-version:references:subject:to; s=qcppdkim1; bh= 0ZqSb++H2BowURLzZycLmbGvlq01SiKl3lcAdI/+ZAw=; b=QkqBmlqCQxYQb3nk K998rTm0nIyp4hTqnA721dDy3LjGLwxQwUXeBrUuM+qyVThXmUOwt7XXn7LyN8Sd dUlxctJpWcU+T48KP6i2qo4AhAyPJzMsjNOytiAoxBwT7fB9spZs+lU//2wA1YDy DfZ3JKQjWcPhtonZRdoy3EitLltHc7Hoa5PaDiV2W7QBO4DRfNnlt1pK/BNP5/FQ 5lXZU2XtbiT10vpajW0UhZPS3+crfPjvhAx95TtwrTqzobLP+dAS9+NEYizV0CN9 hPFdAwbHsGukLsdBx0LnASOcqmFPqIkAB4H4aZwCXETetweH8ogjVG4UhA0xQ0Rj VlZ9HQ== Received: from nalasppmta03.qualcomm.com (Global_NAT1.qualcomm.com [129.46.96.20]) by mx0a-0031df01.pphosted.com (PPS) with ESMTPS id 42a79h85qd-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT); Wed, 16 Oct 2024 06:36:44 +0000 (GMT) Received: from nalasex01b.na.qualcomm.com (nalasex01b.na.qualcomm.com [10.47.209.197]) by NALASPPMTA03.qualcomm.com (8.18.1.2/8.18.1.2) with ESMTPS id 49G6ahgh026545 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT); Wed, 16 Oct 2024 06:36:43 GMT Received: from kangyang.ap.qualcomm.com (10.80.80.8) by nalasex01b.na.qualcomm.com (10.47.209.197) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.1544.9; Tue, 15 Oct 2024 23:36:41 -0700 From: Kang Yang To: CC: , Subject: [PATCH v5 2/4] wifi: ath12k: add 11d scan offload support Date: Wed, 16 Oct 2024 14:35:04 +0800 Message-ID: <20241016063506.1037-3-quic_kangyang@quicinc.com> X-Mailer: git-send-email 2.34.1.windows.1 In-Reply-To: <20241016063506.1037-1-quic_kangyang@quicinc.com> References: <20241016063506.1037-1-quic_kangyang@quicinc.com> Precedence: bulk X-Mailing-List: linux-wireless@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 X-ClientProxiedBy: nasanex01b.na.qualcomm.com (10.46.141.250) To nalasex01b.na.qualcomm.com (10.47.209.197) X-QCInternal: smtphost X-Proofpoint-Virus-Version: vendor=nai engine=6200 definitions=5800 signatures=585085 X-Proofpoint-GUID: WTOvQgJoze3wAjODOOz-KnWcD4qqcW2h X-Proofpoint-ORIG-GUID: WTOvQgJoze3wAjODOOz-KnWcD4qqcW2h X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.293,Aquarius:18.0.1039,Hydra:6.0.680,FMLib:17.12.60.29 definitions=2024-09-06_09,2024-09-06_01,2024-09-02_01 X-Proofpoint-Spam-Details: rule=outbound_notspam policy=outbound score=0 phishscore=0 lowpriorityscore=0 mlxlogscore=999 suspectscore=0 bulkscore=0 priorityscore=1501 impostorscore=0 adultscore=0 mlxscore=0 spamscore=0 malwarescore=0 clxscore=1015 classifier=spam adjust=0 reason=mlx scancount=1 engine=8.19.0-2409260000 definitions=main-2410160041 From: Wen Gong Add process of event WMI_11D_NEW_COUNTRY_EVENTID. Add handler for WMI_11D_SCAN_START_CMDID, WMI_11D_SCAN_STOP_CMDID. Use WMI_11D_SCAN_START_CMDID to trigger 11d scan then firmware will report 11d scan result by WMI_11D_NEW_COUNTRY_EVENTID. Host will update the new country code back to firmware. The priority of 11d scan is WMI_SCAN_PRIORITY_MEDIUM in firmware, the priority of hw scan is WMI_SCAN_PRIORITY_LOW. Then hw scan will be canceled when 11d scan is running. To avoid this, need to change the priority of first hw scan to WMI_SCAN_PRIORITY_MEDIUM. Add wait_for_completion_timeout() for scan.complete in ath12k_reg_update_chan_list(). Plus another existing wait in ath12k_scan_stop(), there are two places to wait the scan.complete. They run in different threads so it is possible that both of the enter into wait status. Therefore use complete_all() instead of complete() for scan.complete. complete_all() can work well when it is only one thread wait for scan.complete. Tested-on: WCN7850 hw2.0 PCI WLAN.HMT.1.0.c5-00481-QCAHMTSWPL_V1.0_V2.0_SILICONZ-3 Signed-off-by: Wen Gong Signed-off-by: Kang Yang --- drivers/net/wireless/ath/ath12k/core.c | 33 ++++- drivers/net/wireless/ath/ath12k/core.h | 16 +++ drivers/net/wireless/ath/ath12k/mac.c | 159 ++++++++++++++++++++++++- drivers/net/wireless/ath/ath12k/mac.h | 7 ++ drivers/net/wireless/ath/ath12k/reg.c | 40 ++++++- drivers/net/wireless/ath/ath12k/reg.h | 4 +- drivers/net/wireless/ath/ath12k/wmi.c | 122 ++++++++++++++++++- drivers/net/wireless/ath/ath12k/wmi.h | 25 ++++ 8 files changed, 396 insertions(+), 10 deletions(-) diff --git a/drivers/net/wireless/ath/ath12k/core.c b/drivers/net/wireless/ath/ath12k/core.c index 9cd485ed42ab..867ff086f0b8 100644 --- a/drivers/net/wireless/ath/ath12k/core.c +++ b/drivers/net/wireless/ath/ath12k/core.c @@ -1014,6 +1014,7 @@ void ath12k_core_halt(struct ath12k *ar) cancel_delayed_work_sync(&ar->scan.timeout); cancel_work_sync(&ar->regd_update_work); cancel_work_sync(&ab->rfkill_work); + cancel_work_sync(&ab->update_11d_work); rcu_assign_pointer(ab->pdevs_active[ar->pdev_idx], NULL); synchronize_rcu(); @@ -1021,6 +1022,33 @@ void ath12k_core_halt(struct ath12k *ar) idr_init(&ar->txmgmt_idr); } +static void ath12k_update_11d(struct work_struct *work) +{ + struct ath12k_base *ab = container_of(work, struct ath12k_base, update_11d_work); + struct ath12k *ar; + struct ath12k_pdev *pdev; + struct wmi_set_current_country_arg arg = {}; + int ret, i; + + spin_lock_bh(&ab->base_lock); + memcpy(&arg.alpha2, &ab->new_alpha2, 2); + spin_unlock_bh(&ab->base_lock); + + ath12k_dbg(ab, ATH12K_DBG_WMI, "update 11d new cc %c%c\n", + arg.alpha2[0], arg.alpha2[1]); + + for (i = 0; i < ab->num_radios; i++) { + pdev = &ab->pdevs[i]; + ar = pdev->ar; + + ret = ath12k_wmi_send_set_current_country_cmd(ar, &arg); + if (ret) + ath12k_warn(ar->ab, + "pdev id %d failed set current country code: %d\n", + i, ret); + } +} + static void ath12k_core_pre_reconfigure_recovery(struct ath12k_base *ab) { struct ath12k *ar; @@ -1045,8 +1073,10 @@ static void ath12k_core_pre_reconfigure_recovery(struct ath12k_base *ab) ar = &ah->radio[j]; ath12k_mac_drain_tx(ar); + ar->state_11d = ATH12K_11D_IDLE; + complete(&ar->completed_11d_scan); complete(&ar->scan.started); - complete(&ar->scan.completed); + complete_all(&ar->scan.completed); complete(&ar->scan.on_channel); complete(&ar->peer_assoc_done); complete(&ar->peer_delete_done); @@ -1311,6 +1341,7 @@ struct ath12k_base *ath12k_core_alloc(struct device *dev, size_t priv_size, INIT_WORK(&ab->restart_work, ath12k_core_restart); INIT_WORK(&ab->reset_work, ath12k_core_reset); INIT_WORK(&ab->rfkill_work, ath12k_rfkill_work); + INIT_WORK(&ab->update_11d_work, ath12k_update_11d); timer_setup(&ab->rx_replenish_retry, ath12k_ce_rx_replenish_retry, 0); init_completion(&ab->htc_suspend); diff --git a/drivers/net/wireless/ath/ath12k/core.h b/drivers/net/wireless/ath/ath12k/core.h index ebfc1e370acc..43e680c36add 100644 --- a/drivers/net/wireless/ath/ath12k/core.h +++ b/drivers/net/wireless/ath/ath12k/core.h @@ -199,6 +199,12 @@ enum ath12k_scan_state { ATH12K_SCAN_ABORTING, }; +enum ath12k_11d_state { + ATH12K_11D_IDLE, + ATH12K_11D_PREPARING, + ATH12K_11D_RUNNING, +}; + enum ath12k_dev_flags { ATH12K_CAC_RUNNING, ATH12K_FLAG_CRASH_FLUSH, @@ -319,6 +325,8 @@ struct ath12k_vif_iter { #define ATH12K_RX_RATE_TABLE_11AX_NUM 576 #define ATH12K_RX_RATE_TABLE_NUM 320 +#define ATH12K_SCAN_TIMEOUT_HZ (20 * HZ) + struct ath12k_rx_peer_rate_stats { u64 ht_mcs_count[HAL_RX_MAX_MCS_HT + 1]; u64 vht_mcs_count[HAL_RX_MAX_MCS_VHT + 1]; @@ -651,6 +659,12 @@ struct ath12k { u32 freq_low; u32 freq_high; + /* Protected by wiphy::mtx lock. */ + u32 vdev_id_11d_scan; + struct completion completed_11d_scan; + enum ath12k_11d_state state_11d; + bool regdom_set_by_user; + bool nlo_enabled; }; @@ -883,6 +897,8 @@ struct ath12k_base { /* continuous recovery fail count */ atomic_t fail_cont_count; unsigned long reset_fail_timeout; + struct work_struct update_11d_work; + u8 new_alpha2[2]; struct { /* protected by data_lock */ u32 fw_crash_counter; diff --git a/drivers/net/wireless/ath/ath12k/mac.c b/drivers/net/wireless/ath/ath12k/mac.c index d4b438e4b7bf..a9ee881fec59 100644 --- a/drivers/net/wireless/ath/ath12k/mac.c +++ b/drivers/net/wireless/ath/ath12k/mac.c @@ -2947,6 +2947,11 @@ static void ath12k_bss_assoc(struct ath12k *ar, if (ret) ath12k_warn(ar->ab, "failed to set vdev %i OBSS PD parameters: %d\n", arvif->vdev_id, ret); + + if (test_bit(WMI_TLV_SERVICE_11D_OFFLOAD, ar->ab->wmi_ab.svc_map) && + arvif->vdev_type == WMI_VDEV_TYPE_STA && + arvif->vdev_subtype == WMI_VDEV_SUBTYPE_NONE) + ath12k_mac_11d_scan_stop_all(ar->ab); } static void ath12k_bss_disassoc(struct ath12k *ar, @@ -3520,7 +3525,7 @@ void __ath12k_mac_scan_finish(struct ath12k *ar) ar->scan_channel = NULL; ar->scan.roc_freq = 0; cancel_delayed_work(&ar->scan.timeout); - complete(&ar->scan.completed); + complete_all(&ar->scan.completed); break; } } @@ -3782,7 +3787,12 @@ static int ath12k_mac_op_hw_scan(struct ieee80211_hw *hw, ret = ath12k_start_scan(ar, arg); if (ret) { - ath12k_warn(ar->ab, "failed to start hw scan: %d\n", ret); + if (ret == -EBUSY) + ath12k_dbg(ar->ab, ATH12K_DBG_MAC, + "scan engine is busy 11d state %d\n", ar->state_11d); + else + ath12k_warn(ar->ab, "failed to start hw scan: %d\n", ret); + spin_lock_bh(&ar->data_lock); ar->scan.state = ATH12K_SCAN_IDLE; spin_unlock_bh(&ar->data_lock); @@ -3800,6 +3810,11 @@ static int ath12k_mac_op_hw_scan(struct ieee80211_hw *hw, kfree(arg); } + if (ar->state_11d == ATH12K_11D_PREPARING && + arvif->vdev_type == WMI_VDEV_TYPE_STA && + arvif->vdev_subtype == WMI_VDEV_SUBTYPE_NONE) + ath12k_mac_11d_scan_start(ar, arvif->vdev_id); + return ret; } @@ -5972,7 +5987,7 @@ static int ath12k_mac_start(struct ath12k *ar) /* TODO: Do we need to enable ANI? */ - ath12k_reg_update_chan_list(ar); + ath12k_reg_update_chan_list(ar, false); ar->num_started_vdevs = 0; ar->num_created_vdevs = 0; @@ -6148,6 +6163,9 @@ static void ath12k_mac_stop(struct ath12k *ar) cancel_delayed_work_sync(&ar->scan.timeout); cancel_work_sync(&ar->regd_update_work); cancel_work_sync(&ar->ab->rfkill_work); + cancel_work_sync(&ar->ab->update_11d_work); + ar->state_11d = ATH12K_11D_IDLE; + complete(&ar->completed_11d_scan); spin_lock_bh(&ar->data_lock); list_for_each_entry_safe(ppdu_stats, tmp, &ar->ppdu_stats_info, list) { @@ -6394,6 +6412,117 @@ static void ath12k_mac_op_update_vif_offload(struct ieee80211_hw *hw, ath12k_mac_update_vif_offload(arvif); } +static bool ath12k_mac_vif_ap_active_any(struct ath12k_base *ab) +{ + struct ath12k *ar; + struct ath12k_pdev *pdev; + struct ath12k_vif *arvif; + int i; + + for (i = 0; i < ab->num_radios; i++) { + pdev = &ab->pdevs[i]; + ar = pdev->ar; + list_for_each_entry(arvif, &ar->arvifs, list) { + if (arvif->is_up && arvif->vdev_type == WMI_VDEV_TYPE_AP) + return true; + } + } + return false; +} + +void ath12k_mac_11d_scan_start(struct ath12k *ar, u32 vdev_id) +{ + struct wmi_11d_scan_start_arg arg; + int ret; + + lockdep_assert_wiphy(ath12k_ar_to_hw(ar)->wiphy); + + if (ar->regdom_set_by_user) + goto fin; + + if (ar->vdev_id_11d_scan != ATH12K_11D_INVALID_VDEV_ID) + goto fin; + + if (!test_bit(WMI_TLV_SERVICE_11D_OFFLOAD, ar->ab->wmi_ab.svc_map)) + goto fin; + + if (ath12k_mac_vif_ap_active_any(ar->ab)) + goto fin; + + arg.vdev_id = vdev_id; + arg.start_interval_msec = 0; + arg.scan_period_msec = ATH12K_SCAN_11D_INTERVAL; + + ath12k_dbg(ar->ab, ATH12K_DBG_MAC, + "mac start 11d scan for vdev %d\n", vdev_id); + + ret = ath12k_wmi_send_11d_scan_start_cmd(ar, &arg); + if (ret) { + ath12k_warn(ar->ab, "failed to start 11d scan vdev %d ret: %d\n", + vdev_id, ret); + } else { + ar->vdev_id_11d_scan = vdev_id; + if (ar->state_11d == ATH12K_11D_PREPARING) + ar->state_11d = ATH12K_11D_RUNNING; + } + +fin: + if (ar->state_11d == ATH12K_11D_PREPARING) { + ar->state_11d = ATH12K_11D_IDLE; + complete(&ar->completed_11d_scan); + } +} + +void ath12k_mac_11d_scan_stop(struct ath12k *ar) +{ + int ret; + u32 vdev_id; + + lockdep_assert_wiphy(ath12k_ar_to_hw(ar)->wiphy); + + if (!test_bit(WMI_TLV_SERVICE_11D_OFFLOAD, ar->ab->wmi_ab.svc_map)) + return; + + ath12k_dbg(ar->ab, ATH12K_DBG_MAC, "mac stop 11d for vdev %d\n", + ar->vdev_id_11d_scan); + + if (ar->state_11d == ATH12K_11D_PREPARING) { + ar->state_11d = ATH12K_11D_IDLE; + complete(&ar->completed_11d_scan); + } + + if (ar->vdev_id_11d_scan != ATH12K_11D_INVALID_VDEV_ID) { + vdev_id = ar->vdev_id_11d_scan; + + ret = ath12k_wmi_send_11d_scan_stop_cmd(ar, vdev_id); + if (ret) { + ath12k_warn(ar->ab, + "failed to stopt 11d scan vdev %d ret: %d\n", + vdev_id, ret); + } else { + ar->vdev_id_11d_scan = ATH12K_11D_INVALID_VDEV_ID; + ar->state_11d = ATH12K_11D_IDLE; + complete(&ar->completed_11d_scan); + } + } +} + +void ath12k_mac_11d_scan_stop_all(struct ath12k_base *ab) +{ + struct ath12k *ar; + struct ath12k_pdev *pdev; + int i; + + ath12k_dbg(ab, ATH12K_DBG_MAC, "mac stop soc 11d scan\n"); + + for (i = 0; i < ab->num_radios; i++) { + pdev = &ab->pdevs[i]; + ar = pdev->ar; + + ath12k_mac_11d_scan_stop(ar); + } +} + static int ath12k_mac_vdev_create(struct ath12k *ar, struct ieee80211_vif *vif) { struct ath12k_hw *ah = ar->ah; @@ -6508,6 +6637,7 @@ static int ath12k_mac_vdev_create(struct ath12k *ar, struct ieee80211_vif *vif) arvif->vdev_id, ret); goto err_peer_del; } + ath12k_mac_11d_scan_stop_all(ar->ab); break; case WMI_VDEV_TYPE_STA: param_id = WMI_STA_PS_PARAM_RX_WAKE_POLICY; @@ -6546,6 +6676,13 @@ static int ath12k_mac_vdev_create(struct ath12k *ar, struct ieee80211_vif *vif) arvif->vdev_id, ret); goto err_peer_del; } + + if (test_bit(WMI_TLV_SERVICE_11D_OFFLOAD, ab->wmi_ab.svc_map) && + arvif->vdev_type == WMI_VDEV_TYPE_STA && + arvif->vdev_subtype == WMI_VDEV_SUBTYPE_NONE) { + reinit_completion(&ar->completed_11d_scan); + ar->state_11d = ATH12K_11D_PREPARING; + } break; default: break; @@ -6884,6 +7021,11 @@ static void ath12k_mac_op_remove_interface(struct ieee80211_hw *hw, ath12k_dbg(ab, ATH12K_DBG_MAC, "mac remove interface (vdev %d)\n", arvif->vdev_id); + if (test_bit(WMI_TLV_SERVICE_11D_OFFLOAD, ab->wmi_ab.svc_map) && + arvif->vdev_type == WMI_VDEV_TYPE_STA && + arvif->vdev_subtype == WMI_VDEV_SUBTYPE_NONE) + ath12k_mac_11d_scan_stop(ar); + if (arvif->vdev_type == WMI_VDEV_TYPE_AP) { ret = ath12k_peer_delete(ar, arvif->vdev_id, vif->addr); if (ret) @@ -7703,6 +7845,14 @@ ath12k_mac_op_unassign_vif_chanctx(struct ieee80211_hw *hw, if (arvif->vdev_type != WMI_VDEV_TYPE_MONITOR && ar->num_started_vdevs == 1 && ar->monitor_vdev_created) ath12k_mac_monitor_stop(ar); + + if (test_bit(WMI_TLV_SERVICE_11D_OFFLOAD, ab->wmi_ab.svc_map) && + arvif->vdev_type == WMI_VDEV_TYPE_STA && + arvif->vdev_subtype == WMI_VDEV_SUBTYPE_NONE && + ar->state_11d != ATH12K_11D_PREPARING) { + reinit_completion(&ar->completed_11d_scan); + ar->state_11d = ATH12K_11D_PREPARING; + } } static int @@ -9262,6 +9412,9 @@ static void ath12k_mac_setup(struct ath12k *ar) INIT_WORK(&ar->wmi_mgmt_tx_work, ath12k_mgmt_over_wmi_tx_work); skb_queue_head_init(&ar->wmi_mgmt_tx_queue); + + ar->vdev_id_11d_scan = ATH12K_11D_INVALID_VDEV_ID; + init_completion(&ar->completed_11d_scan); } int ath12k_mac_register(struct ath12k_base *ab) diff --git a/drivers/net/wireless/ath/ath12k/mac.h b/drivers/net/wireless/ath/ath12k/mac.h index 5efbb6822628..28cc113b7d00 100644 --- a/drivers/net/wireless/ath/ath12k/mac.h +++ b/drivers/net/wireless/ath/ath12k/mac.h @@ -51,6 +51,13 @@ enum ath12k_supported_bw { extern const struct htt_rx_ring_tlv_filter ath12k_mac_mon_status_filter_default; +#define ATH12K_SCAN_11D_INTERVAL 600000 +#define ATH12K_11D_INVALID_VDEV_ID 0xFFFF + +void ath12k_mac_11d_scan_start(struct ath12k *ar, u32 vdev_id); +void ath12k_mac_11d_scan_stop(struct ath12k *ar); +void ath12k_mac_11d_scan_stop_all(struct ath12k_base *ab); + void ath12k_mac_destroy(struct ath12k_base *ab); void ath12k_mac_unregister(struct ath12k_base *ab); int ath12k_mac_register(struct ath12k_base *ab); diff --git a/drivers/net/wireless/ath/ath12k/reg.c b/drivers/net/wireless/ath/ath12k/reg.c index 439d61f284d8..aecfd55aef59 100644 --- a/drivers/net/wireless/ath/ath12k/reg.c +++ b/drivers/net/wireless/ath/ath12k/reg.c @@ -94,10 +94,16 @@ ath12k_reg_notifier(struct wiphy *wiphy, struct regulatory_request *request) if (ret) ath12k_warn(ar->ab, "INIT Country code set to fw failed : %d\n", ret); + + wiphy_lock(wiphy); + ath12k_mac_11d_scan_stop(ar); + wiphy_unlock(wiphy); + + ar->regdom_set_by_user = true; } } -int ath12k_reg_update_chan_list(struct ath12k *ar) +int ath12k_reg_update_chan_list(struct ath12k *ar, bool wait) { struct ieee80211_supported_band **bands; struct ath12k_wmi_scan_chan_list_arg *arg; @@ -106,7 +112,35 @@ int ath12k_reg_update_chan_list(struct ath12k *ar) struct ath12k_wmi_channel_arg *ch; enum nl80211_band band; int num_channels = 0; - int i, ret; + int i, ret, left; + + if (wait && ar->state_11d != ATH12K_11D_IDLE) { + left = wait_for_completion_timeout(&ar->completed_11d_scan, + ATH12K_SCAN_TIMEOUT_HZ); + if (!left) { + ath12k_dbg(ar->ab, ATH12K_DBG_REG, + "failed to receive 11d scan complete: timed out\n"); + ar->state_11d = ATH12K_11D_IDLE; + } + ath12k_dbg(ar->ab, ATH12K_DBG_REG, + "reg 11d scan wait left time %d\n", left); + } + + if (wait && + (ar->scan.state == ATH12K_SCAN_STARTING || + ar->scan.state == ATH12K_SCAN_RUNNING)) { + left = wait_for_completion_timeout(&ar->scan.completed, + ATH12K_SCAN_TIMEOUT_HZ); + if (!left) + ath12k_dbg(ar->ab, ATH12K_DBG_REG, + "failed to receive hw scan complete: timed out\n"); + + ath12k_dbg(ar->ab, ATH12K_DBG_REG, + "reg hw scan wait left time %d\n", left); + } + + if (ar->ah->state == ATH12K_HW_STATE_RESTARTING) + return 0; bands = hw->wiphy->bands; for (band = 0; band < NUM_NL80211_BANDS; band++) { @@ -295,7 +329,7 @@ int ath12k_regd_update(struct ath12k *ar, bool init) */ for_each_ar(ah, ar, i) { ab = ar->ab; - ret = ath12k_reg_update_chan_list(ar); + ret = ath12k_reg_update_chan_list(ar, true); if (ret) goto err; } diff --git a/drivers/net/wireless/ath/ath12k/reg.h b/drivers/net/wireless/ath/ath12k/reg.h index 29c7ec3260da..e4ceae46e556 100644 --- a/drivers/net/wireless/ath/ath12k/reg.h +++ b/drivers/net/wireless/ath/ath12k/reg.h @@ -1,7 +1,7 @@ /* SPDX-License-Identifier: BSD-3-Clause-Clear */ /* * Copyright (c) 2019-2021 The Linux Foundation. All rights reserved. - * Copyright (c) 2021-2023 Qualcomm Innovation Center, Inc. All rights reserved. + * Copyright (c) 2021-2024 Qualcomm Innovation Center, Inc. All rights reserved. */ #ifndef ATH12K_REG_H @@ -96,6 +96,6 @@ struct ieee80211_regdomain *ath12k_reg_build_regd(struct ath12k_base *ab, struct ath12k_reg_info *reg_info, bool intersect); int ath12k_regd_update(struct ath12k *ar, bool init); -int ath12k_reg_update_chan_list(struct ath12k *ar); +int ath12k_reg_update_chan_list(struct ath12k *ar, bool wait); #endif diff --git a/drivers/net/wireless/ath/ath12k/wmi.c b/drivers/net/wireless/ath/ath12k/wmi.c index f7b6e0a45f7c..f60c0eeb221f 100644 --- a/drivers/net/wireless/ath/ath12k/wmi.c +++ b/drivers/net/wireless/ath/ath12k/wmi.c @@ -171,6 +171,8 @@ static const struct ath12k_wmi_tlv_policy ath12k_wmi_tlv_policies[] = { .min_len = sizeof(struct ath12k_wmi_p2p_noa_info) }, [WMI_TAG_P2P_NOA_EVENT] = { .min_len = sizeof(struct wmi_p2p_noa_event) }, + [WMI_TAG_11D_NEW_COUNTRY_EVENT] = { + .min_len = sizeof(struct wmi_11d_new_cc_event) }, }; static __le32 ath12k_wmi_tlv_hdr(u32 cmd, u32 len) @@ -2364,7 +2366,10 @@ int ath12k_wmi_send_scan_start_cmd(struct ath12k *ar, cmd->scan_id = cpu_to_le32(arg->scan_id); cmd->scan_req_id = cpu_to_le32(arg->scan_req_id); cmd->vdev_id = cpu_to_le32(arg->vdev_id); - cmd->scan_priority = cpu_to_le32(arg->scan_priority); + if (ar->state_11d == ATH12K_11D_PREPARING) + arg->scan_priority = WMI_SCAN_PRIORITY_MEDIUM; + else + arg->scan_priority = WMI_SCAN_PRIORITY_LOW; cmd->notify_scan_events = cpu_to_le32(arg->notify_scan_events); ath12k_wmi_copy_scan_event_cntrl_flags(cmd, arg); @@ -3120,6 +3125,74 @@ int ath12k_wmi_send_set_current_country_cmd(struct ath12k *ar, return ret; } +int ath12k_wmi_send_11d_scan_start_cmd(struct ath12k *ar, + struct wmi_11d_scan_start_arg *arg) +{ + struct ath12k_wmi_pdev *wmi = ar->wmi; + struct wmi_11d_scan_start_cmd *cmd; + struct sk_buff *skb; + int ret; + + skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); + if (!skb) + return -ENOMEM; + + cmd = (struct wmi_11d_scan_start_cmd *)skb->data; + cmd->tlv_header = + ath12k_wmi_tlv_cmd_hdr(WMI_TAG_11D_SCAN_START_CMD, + sizeof(*cmd)); + + cmd->vdev_id = cpu_to_le32(arg->vdev_id); + cmd->scan_period_msec = cpu_to_le32(arg->scan_period_msec); + cmd->start_interval_msec = cpu_to_le32(arg->start_interval_msec); + ret = ath12k_wmi_cmd_send(wmi, skb, WMI_11D_SCAN_START_CMDID); + + ath12k_dbg(ar->ab, ATH12K_DBG_WMI, + "send 11d scan start vdev id %d period %d ms internal %d ms\n", + arg->vdev_id, arg->scan_period_msec, + arg->start_interval_msec); + + if (ret) { + ath12k_warn(ar->ab, + "failed to send WMI_11D_SCAN_START_CMDID: %d\n", ret); + dev_kfree_skb(skb); + } + + return ret; +} + +int ath12k_wmi_send_11d_scan_stop_cmd(struct ath12k *ar, u32 vdev_id) +{ + struct ath12k_wmi_pdev *wmi = ar->wmi; + struct wmi_11d_scan_stop_cmd *cmd; + struct sk_buff *skb; + int ret; + + skb = ath12k_wmi_alloc_skb(wmi->wmi_ab, sizeof(*cmd)); + if (!skb) + return -ENOMEM; + + cmd = (struct wmi_11d_scan_stop_cmd *)skb->data; + cmd->tlv_header = + ath12k_wmi_tlv_cmd_hdr(WMI_TAG_11D_SCAN_STOP_CMD, + sizeof(*cmd)); + + cmd->vdev_id = cpu_to_le32(vdev_id); + ret = ath12k_wmi_cmd_send(wmi, skb, WMI_11D_SCAN_STOP_CMDID); + + ath12k_dbg(ar->ab, ATH12K_DBG_WMI, + "send 11d scan stop vdev id %d\n", + cmd->vdev_id); + + if (ret) { + ath12k_warn(ar->ab, + "failed to send WMI_11D_SCAN_STOP_CMDID: %d\n", ret); + dev_kfree_skb(skb); + } + + return ret; +} + int ath12k_wmi_send_twt_enable_cmd(struct ath12k *ar, u32 pdev_id) { @@ -5705,6 +5778,50 @@ static void ath12k_wmi_op_ep_tx_credits(struct ath12k_base *ab) wake_up(&ab->wmi_ab.tx_credits_wq); } +static int ath12k_reg_11d_new_cc_event(struct ath12k_base *ab, struct sk_buff *skb) +{ + const struct wmi_11d_new_cc_event *ev; + struct ath12k *ar; + struct ath12k_pdev *pdev; + const void **tb; + int ret, i; + + tb = ath12k_wmi_tlv_parse_alloc(ab, skb, GFP_ATOMIC); + if (IS_ERR(tb)) { + ret = PTR_ERR(tb); + ath12k_warn(ab, "failed to parse tlv: %d\n", ret); + return ret; + } + + ev = tb[WMI_TAG_11D_NEW_COUNTRY_EVENT]; + if (!ev) { + kfree(tb); + ath12k_warn(ab, "failed to fetch 11d new cc ev"); + return -EPROTO; + } + + spin_lock_bh(&ab->base_lock); + memcpy(&ab->new_alpha2, &ev->new_alpha2, REG_ALPHA2_LEN); + spin_unlock_bh(&ab->base_lock); + + ath12k_dbg(ab, ATH12K_DBG_WMI, "wmi 11d new cc %c%c\n", + ab->new_alpha2[0], + ab->new_alpha2[1]); + + kfree(tb); + + for (i = 0; i < ab->num_radios; i++) { + pdev = &ab->pdevs[i]; + ar = pdev->ar; + ar->state_11d = ATH12K_11D_IDLE; + complete(&ar->completed_11d_scan); + } + + queue_work(ab->workqueue, &ab->update_11d_work); + + return 0; +} + static void ath12k_wmi_htc_tx_complete(struct ath12k_base *ab, struct sk_buff *skb) { @@ -7306,6 +7423,9 @@ static void ath12k_wmi_op_rx(struct ath12k_base *ab, struct sk_buff *skb) case WMI_GTK_OFFLOAD_STATUS_EVENTID: ath12k_wmi_gtk_offload_status_event(ab, skb); break; + case WMI_11D_NEW_COUNTRY_EVENTID: + ath12k_reg_11d_new_cc_event(ab, skb); + break; /* TODO: Add remaining events */ default: ath12k_dbg(ab, ATH12K_DBG_WMI, "Unknown eventid: 0x%x\n", id); diff --git a/drivers/net/wireless/ath/ath12k/wmi.h b/drivers/net/wireless/ath/ath12k/wmi.h index 1797f5c88fb5..dad40b21d974 100644 --- a/drivers/net/wireless/ath/ath12k/wmi.h +++ b/drivers/net/wireless/ath/ath12k/wmi.h @@ -3860,6 +3860,28 @@ struct wmi_init_country_cmd { } cc_info; } __packed; +struct wmi_11d_scan_start_arg { + u32 vdev_id; + u32 scan_period_msec; + u32 start_interval_msec; +}; + +struct wmi_11d_scan_start_cmd { + __le32 tlv_header; + __le32 vdev_id; + __le32 scan_period_msec; + __le32 start_interval_msec; +} __packed; + +struct wmi_11d_scan_stop_cmd { + __le32 tlv_header; + __le32 vdev_id; +} __packed; + +struct wmi_11d_new_cc_event { + __le32 new_alpha2; +} __packed; + struct wmi_delba_send_cmd { __le32 tlv_header; __le32 vdev_id; @@ -5565,6 +5587,9 @@ int ath12k_wmi_peer_rx_reorder_queue_setup(struct ath12k *ar, dma_addr_t paddr, u8 tid, u8 ba_window_size_valid, u32 ba_window_size); +int ath12k_wmi_send_11d_scan_start_cmd(struct ath12k *ar, + struct wmi_11d_scan_start_arg *arg); +int ath12k_wmi_send_11d_scan_stop_cmd(struct ath12k *ar, u32 vdev_id); int ath12k_wmi_rx_reord_queue_remove(struct ath12k *ar, struct ath12k_wmi_rx_reorder_queue_remove_arg *arg); From patchwork Wed Oct 16 06:35:05 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Kang Yang X-Patchwork-Id: 836671 Received: from mx0a-0031df01.pphosted.com (mx0a-0031df01.pphosted.com [205.220.168.131]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id D533818CC01 for ; Wed, 16 Oct 2024 06:36:56 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=205.220.168.131 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1729060618; cv=none; b=utkVFJdk7+YcY2uocIrQG0pGoR5dblz0qZpTrHzKD/TcZOyY+3LLvo4RAwcuYaH3FBV2UIYw3esw5b/yzdxQG93LVM5e7LO5t55Nwt/S8siRGls5fI+fhxsrNPHVomWDxd1O4B+99CUHB4DvtqtTEoVWqm2fFuzbresFT+uQt80= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1729060618; c=relaxed/simple; bh=R6ENEZnmpM3LU8FQmSGr7+CG5fwLKKS6l9tlHBrtxjE=; h=From:To:CC:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version:Content-Type; b=V8jreOR7xedoVB6Fwu+I7g4Gx4ZZvdaZhhnQ4iMvbOBrCreeiUbmrGje+b6oaW8VL8DkebHQ2PNI0ZV5QzFz95E//8zHhr+IfpRqzcoQ0P8LhobYnxPVcr5uJ/xIRqKbGN/e6UcrJKPre62Ht6zsoi2636Xq+NF9/7RcQcLVTtM= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=quicinc.com; spf=pass smtp.mailfrom=quicinc.com; dkim=pass (2048-bit key) header.d=quicinc.com header.i=@quicinc.com header.b=bQqeOm8w; arc=none smtp.client-ip=205.220.168.131 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=quicinc.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=quicinc.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=quicinc.com header.i=@quicinc.com header.b="bQqeOm8w" Received: from pps.filterd (m0279864.ppops.net [127.0.0.1]) by mx0a-0031df01.pphosted.com (8.18.1.2/8.18.1.2) with ESMTP id 49G2S2C8010648; Wed, 16 Oct 2024 06:36:54 GMT DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=quicinc.com; h= cc:content-transfer-encoding:content-type:date:from:in-reply-to :message-id:mime-version:references:subject:to; s=qcppdkim1; bh= DAo1dRf31vjWa7qa/+NFudIUJFN1aRgAerodvf2VzK4=; b=bQqeOm8wgDFXjZpd ykYqC+AN0WCftBBtKb9A6WPm8205vXa860WiSPmVp8RfVjIRo6f9a4lhM6gcYUY1 DpToLnizuTvy/g9/ZaN+IdXNMIrslhnv+MNXudf0NKWSW2KGxH3J/B86aiTpj0xM EicIWn22Fbad2hwBwzHs5y9xNC3oicFZIOktTArdyBavtDsxfsdgB4psO/Avv8+g krWtPekj/JxdLrzjbOYzSSlOIq1rJ840M/J78dRzX6FGHfKNpJG/3uMDHDDkZ5v/ j5SZ73Ttw33xRdJuFgGdeqNKHAHBev8jQpHFNCUAZ2qDS6OSpJTgvKkHrYWhudfI 7p+1Bw== Received: from nalasppmta01.qualcomm.com (Global_NAT1.qualcomm.com [129.46.96.20]) by mx0a-0031df01.pphosted.com (PPS) with ESMTPS id 429uapa7my-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT); Wed, 16 Oct 2024 06:36:54 +0000 (GMT) Received: from nalasex01b.na.qualcomm.com (nalasex01b.na.qualcomm.com [10.47.209.197]) by NALASPPMTA01.qualcomm.com (8.18.1.2/8.18.1.2) with ESMTPS id 49G6aiov017265 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT); Wed, 16 Oct 2024 06:36:44 GMT Received: from kangyang.ap.qualcomm.com (10.80.80.8) by nalasex01b.na.qualcomm.com (10.47.209.197) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.1544.9; Tue, 15 Oct 2024 23:36:43 -0700 From: Kang Yang To: CC: , Subject: [PATCH v5 3/4] wifi: ath12k: use correct WMI command to set country code for WCN7850 Date: Wed, 16 Oct 2024 14:35:05 +0800 Message-ID: <20241016063506.1037-4-quic_kangyang@quicinc.com> X-Mailer: git-send-email 2.34.1.windows.1 In-Reply-To: <20241016063506.1037-1-quic_kangyang@quicinc.com> References: <20241016063506.1037-1-quic_kangyang@quicinc.com> Precedence: bulk X-Mailing-List: linux-wireless@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 X-ClientProxiedBy: nasanex01b.na.qualcomm.com (10.46.141.250) To nalasex01b.na.qualcomm.com (10.47.209.197) X-QCInternal: smtphost X-Proofpoint-Virus-Version: vendor=nai engine=6200 definitions=5800 signatures=585085 X-Proofpoint-ORIG-GUID: hj8cFHol_dyiT2IT7L9SDeGL-11P9UWE X-Proofpoint-GUID: hj8cFHol_dyiT2IT7L9SDeGL-11P9UWE X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.293,Aquarius:18.0.1039,Hydra:6.0.680,FMLib:17.12.60.29 definitions=2024-09-06_09,2024-09-06_01,2024-09-02_01 X-Proofpoint-Spam-Details: rule=outbound_notspam policy=outbound score=0 impostorscore=0 mlxscore=0 spamscore=0 bulkscore=0 clxscore=1015 malwarescore=0 mlxlogscore=956 phishscore=0 priorityscore=1501 suspectscore=0 adultscore=0 lowpriorityscore=0 classifier=spam adjust=0 reason=mlx scancount=1 engine=8.19.0-2409260000 definitions=main-2410160042 From: Wen Gong When userspace try to set country code by NL80211_REGDOM_SET_BY_USER hint(like iw reg set XX), it will pass new country code to ath12k. Then ath12k will set this new country code to firmware by WMI_SET_INIT_COUNTRY_CMDID. But for WCN7850, this WMI command won't take effect. For AP based chips(QCN92xx), WMI_SET_INIT_COUNTRY_CMDID is the correct command. However, for STATION based chips(WCN7850), it need to use WMI_SET_CURRENT_COUNTRY_CMDID. Add flag current_cc_support in hardware parameters. It is used to distinguish AP/STA platform. After that, the firmware will work normal and the regulatory feature works well for WCN7850. Tested-on: WCN7850 hw2.0 PCI WLAN.HMT.1.0.c5-00481-QCAHMTSWPL_V1.0_V2.0_SILICONZ-3 Signed-off-by: Wen Gong Signed-off-by: Kang Yang --- drivers/net/wireless/ath/ath12k/hw.c | 6 ++++++ drivers/net/wireless/ath/ath12k/hw.h | 1 + drivers/net/wireless/ath/ath12k/reg.c | 29 ++++++++++++++++----------- 3 files changed, 24 insertions(+), 12 deletions(-) diff --git a/drivers/net/wireless/ath/ath12k/hw.c b/drivers/net/wireless/ath/ath12k/hw.c index ec1bda95e555..8762a57e8ee5 100644 --- a/drivers/net/wireless/ath/ath12k/hw.c +++ b/drivers/net/wireless/ath/ath12k/hw.c @@ -928,6 +928,8 @@ static const struct ath12k_hw_params ath12k_hw_params[] = { .iova_mask = 0, .supports_aspm = false, + + .current_cc_support = false, }, { .name = "wcn7850 hw2.0", @@ -1008,6 +1010,8 @@ static const struct ath12k_hw_params ath12k_hw_params[] = { .iova_mask = ATH12K_PCIE_MAX_PAYLOAD_SIZE - 1, .supports_aspm = true, + + .current_cc_support = true, }, { .name = "qcn9274 hw2.0", @@ -1084,6 +1088,8 @@ static const struct ath12k_hw_params ath12k_hw_params[] = { .iova_mask = 0, .supports_aspm = false, + + .current_cc_support = false, }, }; diff --git a/drivers/net/wireless/ath/ath12k/hw.h b/drivers/net/wireless/ath/ath12k/hw.h index 8d52182e28ae..8067b103e266 100644 --- a/drivers/net/wireless/ath/ath12k/hw.h +++ b/drivers/net/wireless/ath/ath12k/hw.h @@ -190,6 +190,7 @@ struct ath12k_hw_params { bool reoq_lut_support:1; bool supports_shadow_regs:1; bool supports_aspm:1; + bool current_cc_support:1; u32 num_tcl_banks; u32 max_tx_ring; diff --git a/drivers/net/wireless/ath/ath12k/reg.c b/drivers/net/wireless/ath/ath12k/reg.c index aecfd55aef59..c7b0d66f4874 100644 --- a/drivers/net/wireless/ath/ath12k/reg.c +++ b/drivers/net/wireless/ath/ath12k/reg.c @@ -48,6 +48,7 @@ ath12k_reg_notifier(struct wiphy *wiphy, struct regulatory_request *request) { struct ieee80211_hw *hw = wiphy_to_ieee80211_hw(wiphy); struct ath12k_wmi_init_country_arg arg; + struct wmi_set_current_country_arg current_arg = {}; struct ath12k_hw *ah = ath12k_hw_to_ah(hw); struct ath12k *ar = ath12k_ah_to_ar(ah, 0); int ret, i; @@ -77,23 +78,27 @@ ath12k_reg_notifier(struct wiphy *wiphy, struct regulatory_request *request) return; } - /* Set the country code to the firmware and wait for - * the WMI_REG_CHAN_LIST_CC EVENT for updating the - * reg info - */ - arg.flags = ALPHA_IS_SET; - memcpy(&arg.cc_info.alpha2, request->alpha2, 2); - arg.cc_info.alpha2[2] = 0; - /* Allow fresh updates to wiphy regd */ ah->regd_updated = false; /* Send the reg change request to all the radios */ for_each_ar(ah, ar, i) { - ret = ath12k_wmi_send_init_country_cmd(ar, &arg); - if (ret) - ath12k_warn(ar->ab, - "INIT Country code set to fw failed : %d\n", ret); + if (ar->ab->hw_params->current_cc_support) { + memcpy(¤t_arg.alpha2, request->alpha2, 2); + ret = ath12k_wmi_send_set_current_country_cmd(ar, ¤t_arg); + if (ret) + ath12k_warn(ar->ab, + "failed set current country code: %d\n", ret); + } else { + arg.flags = ALPHA_IS_SET; + memcpy(&arg.cc_info.alpha2, request->alpha2, 2); + arg.cc_info.alpha2[2] = 0; + + ret = ath12k_wmi_send_init_country_cmd(ar, &arg); + if (ret) + ath12k_warn(ar->ab, + "failed set INIT Country code: %d\n", ret); + } wiphy_lock(wiphy); ath12k_mac_11d_scan_stop(ar); From patchwork Wed Oct 16 06:35:06 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Kang Yang X-Patchwork-Id: 836137 Received: from mx0b-0031df01.pphosted.com (mx0b-0031df01.pphosted.com [205.220.180.131]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 40AB918CC01 for ; Wed, 16 Oct 2024 06:37:03 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=205.220.180.131 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1729060624; cv=none; b=VdSCLi7bRkSyeWeautB1R9IWKQu8KbaGlxUInOe1KVvVhwpJcAS3TD/D7RuMMIBldXTFdSNqKIEbJ071Ag5SzUqZcVGhfWjNqYijuvM5/RCA29jQMuWPh1JIdJ5tQxY0krlnCaIkDJk6qnh4zF7YEsoRip6W4rGT5alwB+PW9WE= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1729060624; c=relaxed/simple; bh=a0pStZ2oIfxRrQr9hCPWIrCRTlHXKoWvdUkAz4+r53c=; h=From:To:CC:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version:Content-Type; b=VvJqf1aMbZhb8gfVdyC1wLrThXdFFYzhxSl+euyGkFUlLbRloP/c9m8kCGrJ/RX2asTV73CRKaP+OuxZHohpYsogBNvV5IN+j/7vXPs816bmxn4t4Svxwkhw2J59zfBcccVdgUwiGQeorByS7MX+AaQjIJAgHSxhBmdrTVhkHcM= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=quicinc.com; spf=pass smtp.mailfrom=quicinc.com; dkim=pass (2048-bit key) header.d=quicinc.com header.i=@quicinc.com header.b=OX62bEAP; arc=none smtp.client-ip=205.220.180.131 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=quicinc.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=quicinc.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=quicinc.com header.i=@quicinc.com header.b="OX62bEAP" Received: from pps.filterd (m0279872.ppops.net [127.0.0.1]) by mx0a-0031df01.pphosted.com (8.18.1.2/8.18.1.2) with ESMTP id 49G2aNhV022404; Wed, 16 Oct 2024 06:37:00 GMT DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=quicinc.com; h= cc:content-transfer-encoding:content-type:date:from:in-reply-to :message-id:mime-version:references:subject:to; s=qcppdkim1; bh= UHq4HQqBEzq9NiVeIN2yJCaso+EgV4q+3UQStMukBeg=; b=OX62bEAPAd5Napfm nUwwMquWiwi7N7vM7j17w7dspVB48jObczbkzxVK0loMUmgJosYof0rfF+Ron3PH YrhqWQZhx+GUs3GYZbQnN1vGa9DH6JU+xWmp0XtVcW9O+Xfn3iFbxao3qRt5WkNL WNo2J+4rHbeS3e8Z65QOxssOhtxwFIEW10R0gYy9vRGuOqdhRfso+9DfMWXQfF8p Kuo/xqX5/oCXAFhrOlQrKrCC6Lfs4uJjwCmzBPyU0Y18dHIrGXFNiV0XQP9Jc06r mRprQG54R+XLitecZC3QL5/hcclUqtil9BDjpFWSaI6k/qhcV7oBq29CnUu9S4xv 9C81kw== Received: from nalasppmta02.qualcomm.com (Global_NAT1.qualcomm.com [129.46.96.20]) by mx0a-0031df01.pphosted.com (PPS) with ESMTPS id 429jrfbsb6-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT); Wed, 16 Oct 2024 06:36:59 +0000 (GMT) Received: from nalasex01b.na.qualcomm.com (nalasex01b.na.qualcomm.com [10.47.209.197]) by NALASPPMTA02.qualcomm.com (8.18.1.2/8.18.1.2) with ESMTPS id 49G6aktd005033 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=NOT); Wed, 16 Oct 2024 06:36:46 GMT Received: from kangyang.ap.qualcomm.com (10.80.80.8) by nalasex01b.na.qualcomm.com (10.47.209.197) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.2.1544.9; Tue, 15 Oct 2024 23:36:44 -0700 From: Kang Yang To: CC: , Subject: [PATCH v5 4/4] wifi: ath12k: store and send country code to firmware after recovery Date: Wed, 16 Oct 2024 14:35:06 +0800 Message-ID: <20241016063506.1037-5-quic_kangyang@quicinc.com> X-Mailer: git-send-email 2.34.1.windows.1 In-Reply-To: <20241016063506.1037-1-quic_kangyang@quicinc.com> References: <20241016063506.1037-1-quic_kangyang@quicinc.com> Precedence: bulk X-Mailing-List: linux-wireless@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 X-ClientProxiedBy: nasanex01b.na.qualcomm.com (10.46.141.250) To nalasex01b.na.qualcomm.com (10.47.209.197) X-QCInternal: smtphost X-Proofpoint-Virus-Version: vendor=nai engine=6200 definitions=5800 signatures=585085 X-Proofpoint-GUID: VPGOfTrK_5ylbEaOvQ3joWrbfmRN1p-H X-Proofpoint-ORIG-GUID: VPGOfTrK_5ylbEaOvQ3joWrbfmRN1p-H X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.293,Aquarius:18.0.1039,Hydra:6.0.680,FMLib:17.12.60.29 definitions=2024-09-06_09,2024-09-06_01,2024-09-02_01 X-Proofpoint-Spam-Details: rule=outbound_notspam policy=outbound score=0 bulkscore=0 mlxscore=0 spamscore=0 malwarescore=0 suspectscore=0 phishscore=0 impostorscore=0 clxscore=1015 mlxlogscore=999 priorityscore=1501 adultscore=0 lowpriorityscore=0 classifier=spam adjust=0 reason=mlx scancount=1 engine=8.19.0-2409260000 definitions=main-2410160042 From: Wen Gong Currently ath12k does not send the country code to firmware after device recovery. As a result the country code will be the default one which is reported from firmware. Country code is important, so ath12k also need to restore it to the value which was used before recovery. This is only needed for platforms which support the current_cc_support hardware parameter. Tested-on: WCN7850 hw2.0 PCI WLAN.HMT.1.0.c5-00481-QCAHMTSWPL_V1.0_V2.0_SILICONZ-3 Signed-off-by: Wen Gong Signed-off-by: Kang Yang --- drivers/net/wireless/ath/ath12k/core.c | 1 + drivers/net/wireless/ath/ath12k/core.h | 1 + drivers/net/wireless/ath/ath12k/mac.c | 8 ++++++++ drivers/net/wireless/ath/ath12k/reg.c | 1 + 4 files changed, 11 insertions(+) diff --git a/drivers/net/wireless/ath/ath12k/core.c b/drivers/net/wireless/ath/ath12k/core.c index 867ff086f0b8..2b8eb6ddc8de 100644 --- a/drivers/net/wireless/ath/ath12k/core.c +++ b/drivers/net/wireless/ath/ath12k/core.c @@ -1041,6 +1041,7 @@ static void ath12k_update_11d(struct work_struct *work) pdev = &ab->pdevs[i]; ar = pdev->ar; + memcpy(&ar->alpha2, &arg.alpha2, 2); ret = ath12k_wmi_send_set_current_country_cmd(ar, &arg); if (ret) ath12k_warn(ar->ab, diff --git a/drivers/net/wireless/ath/ath12k/core.h b/drivers/net/wireless/ath/ath12k/core.h index 43e680c36add..12c4d9b57f4c 100644 --- a/drivers/net/wireless/ath/ath12k/core.h +++ b/drivers/net/wireless/ath/ath12k/core.h @@ -663,6 +663,7 @@ struct ath12k { u32 vdev_id_11d_scan; struct completion completed_11d_scan; enum ath12k_11d_state state_11d; + u8 alpha2[REG_ALPHA2_LEN]; bool regdom_set_by_user; bool nlo_enabled; diff --git a/drivers/net/wireless/ath/ath12k/mac.c b/drivers/net/wireless/ath/ath12k/mac.c index a9ee881fec59..d200822a9454 100644 --- a/drivers/net/wireless/ath/ath12k/mac.c +++ b/drivers/net/wireless/ath/ath12k/mac.c @@ -8377,6 +8377,14 @@ ath12k_mac_op_reconfig_complete(struct ieee80211_hw *hw, ath12k_warn(ar->ab, "pdev %d successfully recovered\n", ar->pdev->pdev_id); + if (ar->ab->hw_params->current_cc_support && + ar->alpha2[0] != 0 && ar->alpha2[1] != 0) { + struct wmi_set_current_country_arg arg = {}; + + memcpy(&arg.alpha2, ar->alpha2, 2); + ath12k_wmi_send_set_current_country_cmd(ar, &arg); + } + if (ab->is_reset) { recovery_count = atomic_inc_return(&ab->recovery_count); diff --git a/drivers/net/wireless/ath/ath12k/reg.c b/drivers/net/wireless/ath/ath12k/reg.c index c7b0d66f4874..c3ebb0247e6f 100644 --- a/drivers/net/wireless/ath/ath12k/reg.c +++ b/drivers/net/wireless/ath/ath12k/reg.c @@ -85,6 +85,7 @@ ath12k_reg_notifier(struct wiphy *wiphy, struct regulatory_request *request) for_each_ar(ah, ar, i) { if (ar->ab->hw_params->current_cc_support) { memcpy(¤t_arg.alpha2, request->alpha2, 2); + memcpy(&ar->alpha2, ¤t_arg.alpha2, 2); ret = ath12k_wmi_send_set_current_country_cmd(ar, ¤t_arg); if (ret) ath12k_warn(ar->ab,