From patchwork Fri Oct 4 11:44:10 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: Marek Vasut X-Patchwork-Id: 13822195 X-Patchwork-Delegate: kvalo@adurom.com Received: from phobos.denx.de (phobos.denx.de [85.214.62.61]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 93C0E1D5AD8; Fri, 4 Oct 2024 11:46:30 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=85.214.62.61 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1728042392; cv=none; b=AW3W8UZt54EcgSFmNla0mIgjiYiH/3a/N33iLFZnR5wCgbw0Eo4kk7FT7QbwCXzpM7ZULF6qQIa8MchS0kf0OQiH3pIiCCkeLi6qax5k7i5J0is1c69v+a9WxNVS13EWqLrkw1BrXAO+0Xn1HGeu6VvO71+ZeX2Iy1gszbJbVyM= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1728042392; c=relaxed/simple; bh=2L7VjJ4OyUB7xsUyQLlFIb71AfZScuDHuP5qtOXaNZQ=; h=From:To:Cc:Subject:Date:Message-ID:MIME-Version:Content-Type; b=lcGRzUFdI8OVgqHnvWhvZNNMWJydwGI1jiMoHjkAFpliIQ9Xaz5B37orm1pk5lEQ1D0DWAFlGl8y25AUJoR+oXcFrsVhLBFF9Oqg8V+aYB8y5ZF94yzrDVWYdkmyRgcG6J5vIfDdPVNSpKo/G8tU8umwQhFY0aCg6lbbkzWKiDk= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=denx.de; spf=pass smtp.mailfrom=denx.de; dkim=pass (2048-bit key) header.d=denx.de header.i=@denx.de header.b=ynn/LqzF; arc=none smtp.client-ip=85.214.62.61 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=denx.de Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=denx.de Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=denx.de header.i=@denx.de header.b="ynn/LqzF" Received: from tr.lan (ip-86-49-120-218.bb.vodafone.cz [86.49.120.218]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits)) (No client certificate requested) (Authenticated sender: marex@denx.de) by phobos.denx.de (Postfix) with ESMTPSA id B0893889E9; Fri, 4 Oct 2024 13:46:21 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=denx.de; s=phobos-20191101; t=1728042382; bh=4NUQsyhLZSbmevh275HRv8N4MNRmtfX0PQ1NeQOt1Mg=; h=From:To:Cc:Subject:Date:From; b=ynn/LqzFXbwlA1YBYjPQy7RYxKnix1N+UWtsAKn4kQE+QuGl+3PgfJtYLhjZ55mYK jhm7TmjIwXvqnhyisM+pCKGE9aXAftDiCsv2g+9wE/l+UCVh1aJn1YJRCI37LHeXoL /Xm0vaRDeDHcyoJsHj0oS8aNWJg9uUrMfiDrT3/RTsc6oxbIW6+FZsbpdHwf3GT1/+ egeA1FFMWgdHky4dSDDujRaxZaiAZGZbCgF3yQzkGhSlRyU8uQMM1M+J/Lop7AQkm6 ypZ79WW4vdrNlH/ao/TkFM5P43SAJjrFDT3gkdKXynIz0hikIPnkXYsyLOOwlJrT9m lV/MJEGcGbQ5A== From: Marek Vasut To: linux-wireless@vger.kernel.org Cc: Marek Vasut , Krzysztof Kozlowski , "David S. Miller" , Adham Abozaeid , Ajay Singh , =?utf-8?q?Alexis_Lothor=C3=A9?= , Claudiu Beznea , Conor Dooley , Eric Dumazet , Jakub Kicinski , Kalle Valo , Krzysztof Kozlowski , Paolo Abeni , Rob Herring , devicetree@vger.kernel.org, netdev@vger.kernel.org Subject: [PATCH v8 1/7] dt-bindings: wireless: wilc1000: Document WILC3000 compatible string Date: Fri, 4 Oct 2024 13:44:10 +0200 Message-ID: <20241004114551.40236-1-marex@denx.de> X-Mailer: git-send-email 2.45.2 Precedence: bulk X-Mailing-List: linux-wireless@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 X-Virus-Scanned: clamav-milter 0.103.8 at phobos.denx.de X-Virus-Status: Clean Document compatible string for the WILC3000 chip. The chip is similar to WILC1000, except that the register layout is slightly different and it does not support WPA3/SAE. Reviewed-by: Krzysztof Kozlowski Signed-off-by: Marek Vasut --- Cc: "David S. Miller" Cc: Adham Abozaeid Cc: Ajay Singh Cc: Alexis Lothoré Cc: Claudiu Beznea Cc: Conor Dooley Cc: Eric Dumazet Cc: Jakub Kicinski Cc: Kalle Valo Cc: Krzysztof Kozlowski Cc: Paolo Abeni Cc: Rob Herring Cc: devicetree@vger.kernel.org Cc: linux-wireless@vger.kernel.org Cc: netdev@vger.kernel.org --- V2: - Use WILC1000 as fallback compatible string for WILC3000 V3: - Swap the wilc1000/wilc3000 compatible order V4: - Add RB from Krzysztof V5: No change V6: - Rebase on next-20240926 V7: - Rebase on next-20241003 / wireless-next/main 5a4d42c1688c with v2 wifi: wilc1000: Keep slot powered on during suspend/resume V8: No change --- .../bindings/net/wireless/microchip,wilc1000.yaml | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/Documentation/devicetree/bindings/net/wireless/microchip,wilc1000.yaml b/Documentation/devicetree/bindings/net/wireless/microchip,wilc1000.yaml index 2460ccc082371..5d40f22765bb6 100644 --- a/Documentation/devicetree/bindings/net/wireless/microchip,wilc1000.yaml +++ b/Documentation/devicetree/bindings/net/wireless/microchip,wilc1000.yaml @@ -16,7 +16,11 @@ description: properties: compatible: - const: microchip,wilc1000 + oneOf: + - items: + - const: microchip,wilc3000 + - const: microchip,wilc1000 + - const: microchip,wilc1000 reg: true From patchwork Fri Oct 4 11:44:11 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: Marek Vasut X-Patchwork-Id: 13822196 X-Patchwork-Delegate: kvalo@adurom.com Received: from phobos.denx.de (phobos.denx.de [85.214.62.61]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 93C58148316; Fri, 4 Oct 2024 11:46:30 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=85.214.62.61 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1728042392; cv=none; b=CWVleslfNWG+bufdDKYUbV4UhP3jD7iKlWxJiAIr51NIYVBIIEtNG3G8exu3fn8FpQAhOwBXmSix/NWmnR8vHp69/cLyyymgk1Me8LI3qY47gojfDsh5/JLPQv3H0cz+TAT9Dn8yNFwKpkI+w5nCOa6sf/lxKXRCdVrXt42auI0= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1728042392; c=relaxed/simple; bh=1wWDEWjjdfcKcfIfVvpZcvZnWhG9Wc1aXAWz2l+SiOE=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version:Content-Type; b=W0nNgLIyHxoXYKGQAg6bJAghdWSFXSo8qEORzJbrg57qI4hyNVKJJy6RjkVXdCOdvC85p7kiJEQt+OPtWy1Pq06M7KWd4Fk5j0t46koRaPu6T5pkXf/skJUPd5VjBxw73+kzxhta56EdzS1+teO6VzoRDL4PyljMAhFJ1epi6+o= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=denx.de; spf=pass smtp.mailfrom=denx.de; dkim=pass (2048-bit key) header.d=denx.de header.i=@denx.de header.b=GzoK5Pav; arc=none smtp.client-ip=85.214.62.61 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=denx.de Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=denx.de Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=denx.de header.i=@denx.de header.b="GzoK5Pav" Received: from tr.lan (ip-86-49-120-218.bb.vodafone.cz [86.49.120.218]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits)) (No client certificate requested) (Authenticated sender: marex@denx.de) by phobos.denx.de (Postfix) with ESMTPSA id D2DB288B63; Fri, 4 Oct 2024 13:46:22 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=denx.de; s=phobos-20191101; t=1728042383; bh=OHSzMRtoLkZ1l0NiEhgbVrH5DU6gAPhAKPRc0Y49MjA=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=GzoK5Pavd2LD/lb2b6s0Ps9OqLIpdSFVp5V7Oyohf+52dEZABLQeC4ISfWiRmFSK5 LOuieMkkG7ow+5wxVPesM5vhanwsxflk0luXrdDlkLBx8IuhAgTLhYBRh563k+jOFz q/Pe6cjEGIMruqe1WJ0LBJIA3EVD43a25HYViCcTYu4W0lcTFVhgIK671cZQDGbAX2 l0x4j4xvZDCE1Ug2uZKFJEYurDpflCPS6WAg1D80sJELNnQXgVLl5NsP3pRWol9qxl ZtLjHLeJE5UI4568k1cN1KlxZuS7yjhVQMaR2zL4vq1+UQ9U1ATFsf3sYka4rMbTeP qgyd55kyxtRlw== From: Marek Vasut To: linux-wireless@vger.kernel.org Cc: Marek Vasut , =?utf-8?q?Alexis_Lothor=C3=A9?= , "David S. Miller" , Adham Abozaeid , Ajay Singh , Claudiu Beznea , Conor Dooley , Eric Dumazet , Jakub Kicinski , Kalle Valo , Krzysztof Kozlowski , Paolo Abeni , Rob Herring , devicetree@vger.kernel.org, netdev@vger.kernel.org Subject: [PATCH v8 2/7] wifi: wilc1000: Clean up usage of wilc_get_chipid() Date: Fri, 4 Oct 2024 13:44:11 +0200 Message-ID: <20241004114551.40236-2-marex@denx.de> X-Mailer: git-send-email 2.45.2 In-Reply-To: <20241004114551.40236-1-marex@denx.de> References: <20241004114551.40236-1-marex@denx.de> Precedence: bulk X-Mailing-List: linux-wireless@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 X-Virus-Scanned: clamav-milter 0.103.8 at phobos.denx.de X-Virus-Status: Clean Reduce the use of wilc_get_chipid(), use cached chip ID wherever possible. Remove duplicated partial chip ID read implementations from the driver. Update wilc_get_chipid() to always read the chip ID out of the hardware and update the cached chip ID, and make it return a proper return value instead of a chipid. Call wilc_get_chipid() early to make the cached chip ID available to various sites using is_wilc1000() to access the cached chip ID. Reviewed-by: Alexis Lothoré Signed-off-by: Marek Vasut --- Cc: "David S. Miller" Cc: Adham Abozaeid Cc: Ajay Singh Cc: Alexis Lothoré Cc: Claudiu Beznea Cc: Conor Dooley Cc: Eric Dumazet Cc: Jakub Kicinski Cc: Kalle Valo Cc: Krzysztof Kozlowski Cc: Paolo Abeni Cc: Rob Herring Cc: devicetree@vger.kernel.org Cc: linux-wireless@vger.kernel.org Cc: netdev@vger.kernel.org --- V2: New patch V3: - Undo setup in wilc_wlan_init() if chip is neither wilc1000 or wilc3000 - Make wilc_get_chipid() return proper return value V4: - Drop wilc_get_chipid() from netdev.c - Add RB from Alexis V5: No change V6: - Get chipid early in probe - Drop RB - Rebase on next-20240926 V7: - Update commit message - Reinstate RB - Rebase on next-20241003 / wireless-next/main 5a4d42c1688c with v2 wifi: wilc1000: Keep slot powered on during suspend/resume V8: Add missing EXPORT_SYMBOL_GPL(wilc_get_chipid) --- .../net/wireless/microchip/wilc1000/netdev.c | 6 +- .../net/wireless/microchip/wilc1000/sdio.c | 17 +---- drivers/net/wireless/microchip/wilc1000/spi.c | 2 +- .../net/wireless/microchip/wilc1000/wlan.c | 75 +++++++++++-------- .../net/wireless/microchip/wilc1000/wlan.h | 2 +- 5 files changed, 53 insertions(+), 49 deletions(-) diff --git a/drivers/net/wireless/microchip/wilc1000/netdev.c b/drivers/net/wireless/microchip/wilc1000/netdev.c index 8bc127c5a538c..3e80d29a99ccf 100644 --- a/drivers/net/wireless/microchip/wilc1000/netdev.c +++ b/drivers/net/wireless/microchip/wilc1000/netdev.c @@ -195,13 +195,13 @@ static int wilc_wlan_get_firmware(struct net_device *dev) { struct wilc_vif *vif = netdev_priv(dev); struct wilc *wilc = vif->wilc; - int chip_id; const struct firmware *wilc_fw; int ret; - chip_id = wilc_get_chipid(wilc, false); + if (!is_wilc1000(wilc->chipid)) + return -EINVAL; - netdev_info(dev, "ChipID [%x] loading firmware [%s]\n", chip_id, + netdev_info(dev, "WILC1000 loading firmware [%s]\n", WILC1000_FW(WILC1000_API_VER)); ret = request_firmware(&wilc_fw, WILC1000_FW(WILC1000_API_VER), diff --git a/drivers/net/wireless/microchip/wilc1000/sdio.c b/drivers/net/wireless/microchip/wilc1000/sdio.c index d67662b6b2a1a..7bc6d788f33a7 100644 --- a/drivers/net/wireless/microchip/wilc1000/sdio.c +++ b/drivers/net/wireless/microchip/wilc1000/sdio.c @@ -182,6 +182,10 @@ static int wilc_sdio_probe(struct sdio_func *func, wilc_sdio_init(wilc, false); + ret = wilc_get_chipid(wilc); + if (ret) + goto dispose_irq; + ret = wilc_load_mac_from_nv(wilc); if (ret) { pr_err("Can not retrieve MAC address from chip\n"); @@ -667,7 +671,6 @@ static int wilc_sdio_init(struct wilc *wilc, bool resume) struct wilc_sdio *sdio_priv = wilc->bus_data; struct sdio_cmd52 cmd; int loop, ret; - u32 chipid; /** * function 0 csa enable @@ -756,18 +759,6 @@ static int wilc_sdio_init(struct wilc *wilc, bool resume) return ret; } - /** - * make sure can read back chip id correctly - **/ - if (!resume) { - ret = wilc_sdio_read_reg(wilc, WILC_CHIPID, &chipid); - if (ret) { - dev_err(&func->dev, "Fail cmd read chip id...\n"); - return ret; - } - dev_err(&func->dev, "chipid (%08x)\n", chipid); - } - sdio_priv->isinit = true; return 0; } diff --git a/drivers/net/wireless/microchip/wilc1000/spi.c b/drivers/net/wireless/microchip/wilc1000/spi.c index 05b577b1068ea..81cf82c9175ef 100644 --- a/drivers/net/wireless/microchip/wilc1000/spi.c +++ b/drivers/net/wireless/microchip/wilc1000/spi.c @@ -245,7 +245,7 @@ static int wilc_bus_probe(struct spi_device *spi) if (ret) goto power_down; - ret = wilc_validate_chipid(wilc); + ret = wilc_get_chipid(wilc); if (ret) goto power_down; diff --git a/drivers/net/wireless/microchip/wilc1000/wlan.c b/drivers/net/wireless/microchip/wilc1000/wlan.c index 533939e71534a..28212ff28c112 100644 --- a/drivers/net/wireless/microchip/wilc1000/wlan.c +++ b/drivers/net/wireless/microchip/wilc1000/wlan.c @@ -1402,9 +1402,38 @@ int wilc_send_config_pkt(struct wilc_vif *vif, u8 mode, struct wid *wids, return ret; } +int wilc_get_chipid(struct wilc *wilc) +{ + u32 chipid = 0; + u32 rfrevid = 0; + + if (wilc->chipid == 0) { + wilc->hif_func->hif_read_reg(wilc, WILC_CHIPID, &chipid); + wilc->hif_func->hif_read_reg(wilc, WILC_RF_REVISION_ID, + &rfrevid); + if (!is_wilc1000(chipid)) { + wilc->chipid = 0; + return -EINVAL; + } + if (chipid == WILC_1000_BASE_ID_2A) { /* 0x1002A0 */ + if (rfrevid != 0x1) + chipid = WILC_1000_BASE_ID_2A_REV1; + } else if (chipid == WILC_1000_BASE_ID_2B) { /* 0x1002B0 */ + if (rfrevid == 0x4) + chipid = WILC_1000_BASE_ID_2B_REV1; + else if (rfrevid != 0x3) + chipid = WILC_1000_BASE_ID_2B_REV2; + } + + wilc->chipid = chipid; + } + + return 0; +} +EXPORT_SYMBOL_GPL(wilc_get_chipid); + static int init_chip(struct net_device *dev) { - u32 chipid; u32 reg; int ret = 0; struct wilc_vif *vif = netdev_priv(dev); @@ -1412,9 +1441,11 @@ static int init_chip(struct net_device *dev) acquire_bus(wilc, WILC_BUS_ACQUIRE_AND_WAKEUP); - chipid = wilc_get_chipid(wilc, true); + ret = wilc_get_chipid(wilc); + if (ret) + goto release; - if ((chipid & 0xfff) != 0xa0) { + if ((wilc->chipid & 0xfff) != 0xa0) { ret = wilc->hif_func->hif_read_reg(wilc, WILC_CORTUS_RESET_MUX_SEL, ®); @@ -1445,34 +1476,6 @@ static int init_chip(struct net_device *dev) return ret; } -u32 wilc_get_chipid(struct wilc *wilc, bool update) -{ - u32 chipid = 0; - u32 rfrevid = 0; - - if (wilc->chipid == 0 || update) { - wilc->hif_func->hif_read_reg(wilc, WILC_CHIPID, &chipid); - wilc->hif_func->hif_read_reg(wilc, WILC_RF_REVISION_ID, - &rfrevid); - if (!is_wilc1000(chipid)) { - wilc->chipid = 0; - return wilc->chipid; - } - if (chipid == WILC_1000_BASE_ID_2A) { /* 0x1002A0 */ - if (rfrevid != 0x1) - chipid = WILC_1000_BASE_ID_2A_REV1; - } else if (chipid == WILC_1000_BASE_ID_2B) { /* 0x1002B0 */ - if (rfrevid == 0x4) - chipid = WILC_1000_BASE_ID_2B_REV1; - else if (rfrevid != 0x3) - chipid = WILC_1000_BASE_ID_2B_REV2; - } - - wilc->chipid = chipid; - } - return wilc->chipid; -} - int wilc_load_mac_from_nv(struct wilc *wl) { int ret = -EINVAL; @@ -1535,9 +1538,19 @@ int wilc_wlan_init(struct net_device *dev) if (!wilc->hif_func->hif_is_init(wilc)) { acquire_bus(wilc, WILC_BUS_ACQUIRE_ONLY); ret = wilc->hif_func->hif_init(wilc, false); + if (!ret) + ret = wilc_get_chipid(wilc); release_bus(wilc, WILC_BUS_RELEASE_ONLY); if (ret) goto fail; + + if (!is_wilc1000(wilc->chipid)) { + netdev_err(dev, "Unsupported chipid: %x\n", wilc->chipid); + ret = -EINVAL; + goto fail; + } + + netdev_dbg(dev, "chipid (%08x)\n", wilc->chipid); } if (!wilc->vmm_table) diff --git a/drivers/net/wireless/microchip/wilc1000/wlan.h b/drivers/net/wireless/microchip/wilc1000/wlan.h index dd2fb3c2f06a2..44dce53d24916 100644 --- a/drivers/net/wireless/microchip/wilc1000/wlan.h +++ b/drivers/net/wireless/microchip/wilc1000/wlan.h @@ -443,6 +443,6 @@ void chip_wakeup(struct wilc *wilc); int wilc_send_config_pkt(struct wilc_vif *vif, u8 mode, struct wid *wids, u32 count); int wilc_wlan_init(struct net_device *dev); -u32 wilc_get_chipid(struct wilc *wilc, bool update); +int wilc_get_chipid(struct wilc *wilc); int wilc_load_mac_from_nv(struct wilc *wilc); #endif From patchwork Fri Oct 4 11:44:12 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: Marek Vasut X-Patchwork-Id: 13822197 X-Patchwork-Delegate: kvalo@adurom.com Received: from phobos.denx.de (phobos.denx.de [85.214.62.61]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 9FB82155C9E; Fri, 4 Oct 2024 11:46:31 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=85.214.62.61 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1728042393; cv=none; b=gITD5IOFsdTxIinzJfiwDeXYwX39Nff9cNfs9NM0Ozc20IaGIdVxa7RHjPv1dxFJwWGfT4NT9e8XTsfb+xilCosuklkk5aBVJYMdxLwLouEae5jS6nvAdQpI3aWhWheynGau0AgQ94bVf0YaC7GxqkBFgU+o+NepGImWOFckxro= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1728042393; c=relaxed/simple; bh=/KdKDUeJp5MPDeLGL74TtCpqNvp04l3qOUBHLtuHOG0=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version:Content-Type; b=MMp4qBWVaL3/EQZwiq2gy4ZUjo0AUbH1HGeqDG6uH00Yj17oQcOrnbEo9K54qQH/c6LeOlCzRyzyO3WHp7y35C3ZKd+HOnJQ5mK4VL48HkXRXdnWf5m8Mh597WP3YnNWdfl1zro+OdOJpYKOE1wWfO7Ez+ifIaYX1w40cP9VaCA= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=denx.de; spf=pass smtp.mailfrom=denx.de; dkim=pass (2048-bit key) header.d=denx.de header.i=@denx.de header.b=Dz17FAjF; arc=none smtp.client-ip=85.214.62.61 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=denx.de Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=denx.de Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=denx.de header.i=@denx.de header.b="Dz17FAjF" Received: from tr.lan (ip-86-49-120-218.bb.vodafone.cz [86.49.120.218]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits)) (No client certificate requested) (Authenticated sender: marex@denx.de) by phobos.denx.de (Postfix) with ESMTPSA id 6D2AF88B86; Fri, 4 Oct 2024 13:46:23 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=denx.de; s=phobos-20191101; t=1728042383; bh=NPVz4cAeAJEothSjPLJIXwH/jAIMKJ7lI+zwjp3b4Mk=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=Dz17FAjF1oahAUVNulFCDriEPwehI9Qyhw+hcFF2EI4FLqi5B3rrCk/XwnnfUHsjb j2WhL+B3iJwMhEK2Vi/VMYG3KxDzLvl3zO2uDS8DD7noGCvpLWtD0Nflax6PMSRwQH xBZ6B83Yk2Wz9KwVsr5oxkoAIu5ExlmkEG3HipiaYxlqKKOdpB+OCQ+nWh1SdPuhQ4 PSnmN7Re22qeGd50kJyCtuVRXSPuy7VHmqRWjKwwQqgbcBov9vTQ+m9wSvL9fJslrO AVsDkw/uitbAF8sdjXZGjmco9MCcokvyJhRNghpVFBpy7bBqBcxokJtmfrNz+k54/F NwpyKWanSTWYg== From: Marek Vasut To: linux-wireless@vger.kernel.org Cc: Marek Vasut , =?utf-8?q?Alexis_Lothor=C3=A9?= , "David S. Miller" , Adham Abozaeid , Ajay Singh , Claudiu Beznea , Conor Dooley , Eric Dumazet , Jakub Kicinski , Kalle Valo , Krzysztof Kozlowski , Paolo Abeni , Rob Herring , devicetree@vger.kernel.org, netdev@vger.kernel.org Subject: [PATCH v8 3/7] wifi: wilc1000: Fold chip_allow_sleep()/chip_wakeup() into wlan.c Date: Fri, 4 Oct 2024 13:44:12 +0200 Message-ID: <20241004114551.40236-3-marex@denx.de> X-Mailer: git-send-email 2.45.2 In-Reply-To: <20241004114551.40236-1-marex@denx.de> References: <20241004114551.40236-1-marex@denx.de> Precedence: bulk X-Mailing-List: linux-wireless@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 X-Virus-Scanned: clamav-milter 0.103.8 at phobos.denx.de X-Virus-Status: Clean Neither chip_allow_sleep()/chip_wakeup() is used outside of wlan.c . Make both functions static and remove both the exported symbol and entries from wlan.h . Make chip_allow_sleep() return error code in preparation for the follow up patches. Move acquire_bus() and release_bus() to avoid forward declaration of chip_allow_sleep()/chip_wakeup(). Reviewed-by: Alexis Lothoré Signed-off-by: Marek Vasut --- Cc: "David S. Miller" Cc: Adham Abozaeid Cc: Ajay Singh Cc: Alexis Lothoré Cc: Claudiu Beznea Cc: Conor Dooley Cc: Eric Dumazet Cc: Jakub Kicinski Cc: Kalle Valo Cc: Krzysztof Kozlowski Cc: Paolo Abeni Cc: Rob Herring Cc: devicetree@vger.kernel.org Cc: linux-wireless@vger.kernel.org Cc: netdev@vger.kernel.org --- V2: New patch V3: No change V4: Add RB from Alexis V5: No change V6: - Rebase on next-20240926 V7: - Rebase on next-20241003 / wireless-next/main 5a4d42c1688c with v2 wifi: wilc1000: Keep slot powered on during suspend/resume V8: No change --- .../net/wireless/microchip/wilc1000/wlan.c | 47 +++++++++---------- .../net/wireless/microchip/wilc1000/wlan.h | 2 - 2 files changed, 23 insertions(+), 26 deletions(-) diff --git a/drivers/net/wireless/microchip/wilc1000/wlan.c b/drivers/net/wireless/microchip/wilc1000/wlan.c index 28212ff28c112..875f0bb8af673 100644 --- a/drivers/net/wireless/microchip/wilc1000/wlan.c +++ b/drivers/net/wireless/microchip/wilc1000/wlan.c @@ -12,20 +12,6 @@ #define WAKE_UP_TRIAL_RETRY 10000 -static inline void acquire_bus(struct wilc *wilc, enum bus_acquire acquire) -{ - mutex_lock(&wilc->hif_cs); - if (acquire == WILC_BUS_ACQUIRE_AND_WAKEUP && wilc->power_save_mode) - chip_wakeup(wilc); -} - -static inline void release_bus(struct wilc *wilc, enum bus_release release) -{ - if (release == WILC_BUS_RELEASE_ALLOW_SLEEP && wilc->power_save_mode) - chip_allow_sleep(wilc); - mutex_unlock(&wilc->hif_cs); -} - static void wilc_wlan_txq_remove(struct wilc *wilc, u8 q_num, struct txq_entry_t *tqe) { @@ -555,7 +541,7 @@ static struct rxq_entry_t *wilc_wlan_rxq_remove(struct wilc *wilc) return rqe; } -void chip_allow_sleep(struct wilc *wilc) +static int chip_allow_sleep(struct wilc *wilc) { u32 reg = 0; const struct wilc_hif_func *hif_func = wilc->hif_func; @@ -584,7 +570,7 @@ void chip_allow_sleep(struct wilc *wilc) while (--trials) { ret = hif_func->hif_read_reg(wilc, to_host_from_fw_reg, ®); if (ret) - return; + return ret; if ((reg & to_host_from_fw_bit) == 0) break; } @@ -594,28 +580,28 @@ void chip_allow_sleep(struct wilc *wilc) /* Clear bit 1 */ ret = hif_func->hif_read_reg(wilc, wakeup_reg, ®); if (ret) - return; + return ret; if (reg & wakeup_bit) { reg &= ~wakeup_bit; ret = hif_func->hif_write_reg(wilc, wakeup_reg, reg); if (ret) - return; + return ret; } ret = hif_func->hif_read_reg(wilc, from_host_to_fw_reg, ®); if (ret) - return; + return ret; if (reg & from_host_to_fw_bit) { reg &= ~from_host_to_fw_bit; ret = hif_func->hif_write_reg(wilc, from_host_to_fw_reg, reg); if (ret) - return; - + return ret; } + + return 0; } -EXPORT_SYMBOL_GPL(chip_allow_sleep); -void chip_wakeup(struct wilc *wilc) +static void chip_wakeup(struct wilc *wilc) { u32 ret = 0; u32 clk_status_val = 0, trials = 0; @@ -674,7 +660,20 @@ void chip_wakeup(struct wilc *wilc) if (wilc->io_type == WILC_HIF_SPI) wilc->hif_func->hif_reset(wilc); } -EXPORT_SYMBOL_GPL(chip_wakeup); + +static inline void acquire_bus(struct wilc *wilc, enum bus_acquire acquire) +{ + mutex_lock(&wilc->hif_cs); + if (acquire == WILC_BUS_ACQUIRE_AND_WAKEUP && wilc->power_save_mode) + chip_wakeup(wilc); +} + +static inline void release_bus(struct wilc *wilc, enum bus_release release) +{ + if (release == WILC_BUS_RELEASE_ALLOW_SLEEP && wilc->power_save_mode) + chip_allow_sleep(wilc); + mutex_unlock(&wilc->hif_cs); +} void host_wakeup_notify(struct wilc *wilc) { diff --git a/drivers/net/wireless/microchip/wilc1000/wlan.h b/drivers/net/wireless/microchip/wilc1000/wlan.h index 44dce53d24916..90ba76cf14dd1 100644 --- a/drivers/net/wireless/microchip/wilc1000/wlan.h +++ b/drivers/net/wireless/microchip/wilc1000/wlan.h @@ -438,8 +438,6 @@ void wilc_wfi_p2p_rx(struct wilc_vif *vif, u8 *buff, u32 size); bool wilc_wfi_mgmt_frame_rx(struct wilc_vif *vif, u8 *buff, u32 size); void host_wakeup_notify(struct wilc *wilc); void host_sleep_notify(struct wilc *wilc); -void chip_allow_sleep(struct wilc *wilc); -void chip_wakeup(struct wilc *wilc); int wilc_send_config_pkt(struct wilc_vif *vif, u8 mode, struct wid *wids, u32 count); int wilc_wlan_init(struct net_device *dev); From patchwork Fri Oct 4 11:44:13 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: Marek Vasut X-Patchwork-Id: 13822198 X-Patchwork-Delegate: kvalo@adurom.com Received: from phobos.denx.de (phobos.denx.de [85.214.62.61]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id 9FB39155C95; Fri, 4 Oct 2024 11:46:31 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=85.214.62.61 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1728042393; cv=none; b=N3+4yO+mMSvHel5laHO6iODGKJLXZllbYEAIGR8YSXHVgaKGBgZzsWeulL7LmjirofPzRi+Ui7KhgpZeH4N4YzvRgrhoN2kPDglQPLWC44Ru5rVKO/w4PW0izA8+8rthFqz516XuX24XaZ9B+hgIdniE+bQXKMs/Z8i5Q4acq/k= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1728042393; c=relaxed/simple; bh=Jh8WZeCm8nJkt7ZjOEFxVtabP0bMvsYlozzEmXp8QsU=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version:Content-Type; b=aFGf3o7xAoUdE7a9dtHvolgHCQCY0S31b7DHZ6lisn/V/HU7RCJtSonViXXvgaY9K12lKWz/1969fM9H8JgG+R9W7pcbCphbfrC0B8lFIFXwVu4sRuyRIJ7DE7QWhZbcxU0I3CxDZi7ZzW8ri+8U3y2ZajBnxCkCkYdkALoccTI= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=denx.de; spf=pass smtp.mailfrom=denx.de; dkim=pass (2048-bit key) header.d=denx.de header.i=@denx.de header.b=rFhv7qUd; arc=none smtp.client-ip=85.214.62.61 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=denx.de Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=denx.de Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=denx.de header.i=@denx.de header.b="rFhv7qUd" Received: from tr.lan (ip-86-49-120-218.bb.vodafone.cz [86.49.120.218]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits)) (No client certificate requested) (Authenticated sender: marex@denx.de) by phobos.denx.de (Postfix) with ESMTPSA id 0AF1F88B89; Fri, 4 Oct 2024 13:46:24 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=denx.de; s=phobos-20191101; t=1728042384; bh=/8HXQqsE7V7o/I1N4vKkRIUpFo3wLY7Dqhg4y63ZDyA=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=rFhv7qUdag2ijiKaBVg7sHBSdhLjGnle4unplV58Lr1TvF/8vk4wtaxmrPrHdYE2u 6AcQUNO4gHQB2Zbms67+3eoEKIv/6Fyxdec4R29MEpkSh3LU3YDxhTlV2nl0+c0fWb wfdQE1fKXAAC6R7VikxM3/0SL3A1aWksOay9Vw3/n4xwpI2CcpOrn48Tf5+xLNWb3j KDyqZHPEcgIWYpx9k04brfALiz7AbQfS+WQuGzqJ0jYm9Yh6MbhDqetbwqTI5Y+yy6 TkDG0yTNAwyYDjnrdt7aFQjDnA+b7Cqh/hravSrdmVNS512b91uvrjGoSV50ZOT/0m DSq/H3J5Rg+Uw== From: Marek Vasut To: linux-wireless@vger.kernel.org Cc: Marek Vasut , =?utf-8?q?Alexis_Lothor=C3=A9?= , "David S. Miller" , Adham Abozaeid , Ajay Singh , Claudiu Beznea , Conor Dooley , Eric Dumazet , Jakub Kicinski , Kalle Valo , Krzysztof Kozlowski , Paolo Abeni , Rob Herring , devicetree@vger.kernel.org, netdev@vger.kernel.org Subject: [PATCH v8 4/7] wifi: wilc1000: Fill in missing error handling Date: Fri, 4 Oct 2024 13:44:13 +0200 Message-ID: <20241004114551.40236-4-marex@denx.de> X-Mailer: git-send-email 2.45.2 In-Reply-To: <20241004114551.40236-1-marex@denx.de> References: <20241004114551.40236-1-marex@denx.de> Precedence: bulk X-Mailing-List: linux-wireless@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 X-Virus-Scanned: clamav-milter 0.103.8 at phobos.denx.de X-Virus-Status: Clean Add error handling to chip_wakeup() and propagate the errors throughout the entire driver. Add error handling to acquire_bus()/release_bus() and host_sleep_notify()/host_wakeup_notify() functions as a result as well. Fill the error handling to all call sites. Reviewed-by: Alexis Lothoré Signed-off-by: Marek Vasut --- Cc: "David S. Miller" Cc: Adham Abozaeid Cc: Ajay Singh Cc: Alexis Lothoré Cc: Claudiu Beznea Cc: Conor Dooley Cc: Eric Dumazet Cc: Jakub Kicinski Cc: Kalle Valo Cc: Krzysztof Kozlowski Cc: Paolo Abeni Cc: Rob Herring Cc: devicetree@vger.kernel.org Cc: linux-wireless@vger.kernel.org Cc: netdev@vger.kernel.org --- V3: New patch V4: No change V4: Add RB from Alexis V5: No change V6: - Rebase on next-20240926 V7: - Rebase on next-20241003 / wireless-next/main 5a4d42c1688c with v2 wifi: wilc1000: Keep slot powered on during suspend/resume V8: No change --- .../net/wireless/microchip/wilc1000/sdio.c | 11 +- .../net/wireless/microchip/wilc1000/wlan.c | 154 +++++++++++++----- .../net/wireless/microchip/wilc1000/wlan.h | 4 +- 3 files changed, 118 insertions(+), 51 deletions(-) diff --git a/drivers/net/wireless/microchip/wilc1000/sdio.c b/drivers/net/wireless/microchip/wilc1000/sdio.c index 7bc6d788f33a7..9173f6f3beabf 100644 --- a/drivers/net/wireless/microchip/wilc1000/sdio.c +++ b/drivers/net/wireless/microchip/wilc1000/sdio.c @@ -960,6 +960,7 @@ static int wilc_sdio_suspend(struct device *dev) { struct sdio_func *func = dev_to_sdio_func(dev); struct wilc *wilc = sdio_get_drvdata(func); + int ret; dev_info(dev, "sdio suspend\n"); @@ -969,7 +970,11 @@ static int wilc_sdio_suspend(struct device *dev) if (!IS_ERR(wilc->rtc_clk)) clk_disable_unprepare(wilc->rtc_clk); - host_sleep_notify(wilc); + ret = host_sleep_notify(wilc); + if (ret) { + clk_prepare_enable(wilc->rtc_clk); + return ret; + } wilc_sdio_disable_interrupt(wilc); @@ -992,9 +997,7 @@ static int wilc_sdio_resume(struct device *dev) wilc_sdio_init(wilc, true); wilc_sdio_enable_interrupt(wilc); - host_wakeup_notify(wilc); - - return 0; + return host_wakeup_notify(wilc); } static const struct of_device_id wilc_of_match[] = { diff --git a/drivers/net/wireless/microchip/wilc1000/wlan.c b/drivers/net/wireless/microchip/wilc1000/wlan.c index 875f0bb8af673..521caa498035e 100644 --- a/drivers/net/wireless/microchip/wilc1000/wlan.c +++ b/drivers/net/wireless/microchip/wilc1000/wlan.c @@ -601,7 +601,7 @@ static int chip_allow_sleep(struct wilc *wilc) return 0; } -static void chip_wakeup(struct wilc *wilc) +static int chip_wakeup(struct wilc *wilc) { u32 ret = 0; u32 clk_status_val = 0, trials = 0; @@ -630,20 +630,20 @@ static void chip_wakeup(struct wilc *wilc) ret = hif_func->hif_write_reg(wilc, from_host_to_fw_reg, from_host_to_fw_bit); if (ret) - return; + return ret; /* Set wake-up bit */ ret = hif_func->hif_write_reg(wilc, wakeup_reg, wakeup_bit); if (ret) - return; + return ret; while (trials < WAKE_UP_TRIAL_RETRY) { ret = hif_func->hif_read_reg(wilc, clk_status_reg, &clk_status_val); if (ret) { pr_err("Bus error %d %x\n", ret, clk_status_val); - return; + return ret; } if (clk_status_val & clk_status_bit) break; @@ -652,42 +652,63 @@ static void chip_wakeup(struct wilc *wilc) } if (trials >= WAKE_UP_TRIAL_RETRY) { pr_err("Failed to wake-up the chip\n"); - return; + return -ETIMEDOUT; } /* Sometimes spi fail to read clock regs after reading * writing clockless registers */ if (wilc->io_type == WILC_HIF_SPI) wilc->hif_func->hif_reset(wilc); + + return 0; } -static inline void acquire_bus(struct wilc *wilc, enum bus_acquire acquire) +static inline int acquire_bus(struct wilc *wilc, enum bus_acquire acquire) { + int ret = 0; + mutex_lock(&wilc->hif_cs); - if (acquire == WILC_BUS_ACQUIRE_AND_WAKEUP && wilc->power_save_mode) - chip_wakeup(wilc); + if (acquire == WILC_BUS_ACQUIRE_AND_WAKEUP && wilc->power_save_mode) { + ret = chip_wakeup(wilc); + if (ret) + mutex_unlock(&wilc->hif_cs); + } + + return ret; } -static inline void release_bus(struct wilc *wilc, enum bus_release release) +static inline int release_bus(struct wilc *wilc, enum bus_release release) { + int ret = 0; + if (release == WILC_BUS_RELEASE_ALLOW_SLEEP && wilc->power_save_mode) - chip_allow_sleep(wilc); + ret = chip_allow_sleep(wilc); mutex_unlock(&wilc->hif_cs); + + return ret; } -void host_wakeup_notify(struct wilc *wilc) +int host_wakeup_notify(struct wilc *wilc) { - acquire_bus(wilc, WILC_BUS_ACQUIRE_AND_WAKEUP); + int ret = acquire_bus(wilc, WILC_BUS_ACQUIRE_AND_WAKEUP); + + if (ret) + return ret; + wilc->hif_func->hif_write_reg(wilc, WILC_CORTUS_INTERRUPT_2, 1); - release_bus(wilc, WILC_BUS_RELEASE_ALLOW_SLEEP); + return release_bus(wilc, WILC_BUS_RELEASE_ALLOW_SLEEP); } EXPORT_SYMBOL_GPL(host_wakeup_notify); -void host_sleep_notify(struct wilc *wilc) +int host_sleep_notify(struct wilc *wilc) { - acquire_bus(wilc, WILC_BUS_ACQUIRE_AND_WAKEUP); + int ret = acquire_bus(wilc, WILC_BUS_ACQUIRE_AND_WAKEUP); + + if (ret) + return ret; + wilc->hif_func->hif_write_reg(wilc, WILC_CORTUS_INTERRUPT_1, 1); - release_bus(wilc, WILC_BUS_RELEASE_ALLOW_SLEEP); + return release_bus(wilc, WILC_BUS_RELEASE_ALLOW_SLEEP); } EXPORT_SYMBOL_GPL(host_sleep_notify); @@ -714,6 +735,7 @@ int wilc_wlan_handle_txq(struct wilc *wilc, u32 *txq_count) int srcu_idx; u8 *txb = wilc->tx_buffer; struct wilc_vif *vif; + int rv; if (wilc->quit) goto out_update_cnt; @@ -784,7 +806,10 @@ int wilc_wlan_handle_txq(struct wilc *wilc, u32 *txq_count) goto out_unlock; vmm_table[i] = 0x0; - acquire_bus(wilc, WILC_BUS_ACQUIRE_AND_WAKEUP); + ret = acquire_bus(wilc, WILC_BUS_ACQUIRE_AND_WAKEUP); + if (ret) + goto out_unlock; + counter = 0; func = wilc->hif_func; do { @@ -859,7 +884,9 @@ int wilc_wlan_handle_txq(struct wilc *wilc, u32 *txq_count) goto out_release_bus; } - release_bus(wilc, WILC_BUS_RELEASE_ALLOW_SLEEP); + ret = release_bus(wilc, WILC_BUS_RELEASE_ALLOW_SLEEP); + if (ret) + goto out_unlock; offset = 0; i = 0; @@ -921,7 +948,9 @@ int wilc_wlan_handle_txq(struct wilc *wilc, u32 *txq_count) for (i = 0; i < NQUEUES; i++) wilc->txq[i].fw.count += ac_pkt_num_to_chip[i]; - acquire_bus(wilc, WILC_BUS_ACQUIRE_AND_WAKEUP); + ret = acquire_bus(wilc, WILC_BUS_ACQUIRE_AND_WAKEUP); + if (ret) + goto out_unlock; ret = func->hif_clear_int_ext(wilc, ENABLE_TX_VMM); if (ret) @@ -930,7 +959,9 @@ int wilc_wlan_handle_txq(struct wilc *wilc, u32 *txq_count) ret = func->hif_block_tx_ext(wilc, 0, txb, offset); out_release_bus: - release_bus(wilc, WILC_BUS_RELEASE_ALLOW_SLEEP); + rv = release_bus(wilc, WILC_BUS_RELEASE_ALLOW_SLEEP); + if (!ret && rv) + ret = rv; out_unlock: mutex_unlock(&wilc->txq_add_to_head_cs); @@ -1059,8 +1090,14 @@ static void wilc_wlan_handle_isr_ext(struct wilc *wilc, u32 int_status) void wilc_handle_isr(struct wilc *wilc) { u32 int_status; + int ret; + + ret = acquire_bus(wilc, WILC_BUS_ACQUIRE_AND_WAKEUP); + if (ret) { + dev_err_ratelimited(wilc->dev, "Cannot acquire bus\n"); + return; + } - acquire_bus(wilc, WILC_BUS_ACQUIRE_AND_WAKEUP); wilc->hif_func->hif_read_int(wilc, &int_status); if (int_status & DATA_INT_EXT) @@ -1069,7 +1106,9 @@ void wilc_handle_isr(struct wilc *wilc) if (!(int_status & (ALL_INT_EXT))) wilc_unknown_isr_ext(wilc); - release_bus(wilc, WILC_BUS_RELEASE_ALLOW_SLEEP); + ret = release_bus(wilc, WILC_BUS_RELEASE_ALLOW_SLEEP); + if (ret) + dev_err_ratelimited(wilc->dev, "Cannot release bus\n"); } EXPORT_SYMBOL_GPL(wilc_handle_isr); @@ -1081,6 +1120,7 @@ int wilc_wlan_firmware_download(struct wilc *wilc, const u8 *buffer, u8 *dma_buffer; int ret = 0; u32 reg = 0; + int rv; blksz = BIT(12); @@ -1091,7 +1131,9 @@ int wilc_wlan_firmware_download(struct wilc *wilc, const u8 *buffer, offset = 0; pr_debug("%s: Downloading firmware size = %d\n", __func__, buffer_size); - acquire_bus(wilc, WILC_BUS_ACQUIRE_AND_WAKEUP); + ret = acquire_bus(wilc, WILC_BUS_ACQUIRE_AND_WAKEUP); + if (ret) + return ret; wilc->hif_func->hif_read_reg(wilc, WILC_GLB_RESET_0, ®); reg &= ~BIT(10); @@ -1100,11 +1142,17 @@ int wilc_wlan_firmware_download(struct wilc *wilc, const u8 *buffer, if (reg & BIT(10)) pr_err("%s: Failed to reset\n", __func__); - release_bus(wilc, WILC_BUS_RELEASE_ONLY); + ret = release_bus(wilc, WILC_BUS_RELEASE_ONLY); + if (ret) + goto fail; + do { addr = get_unaligned_le32(&buffer[offset]); size = get_unaligned_le32(&buffer[offset + 4]); - acquire_bus(wilc, WILC_BUS_ACQUIRE_AND_WAKEUP); + ret = acquire_bus(wilc, WILC_BUS_ACQUIRE_AND_WAKEUP); + if (ret) + goto fail; + offset += 8; while (((int)size) && (offset < buffer_size)) { if (size <= blksz) @@ -1122,7 +1170,9 @@ int wilc_wlan_firmware_download(struct wilc *wilc, const u8 *buffer, offset += size2; size -= size2; } - release_bus(wilc, WILC_BUS_RELEASE_ALLOW_SLEEP); + rv = release_bus(wilc, WILC_BUS_RELEASE_ALLOW_SLEEP); + if (!ret && rv) + ret = rv; if (ret) { pr_err("%s Bus error\n", __func__); @@ -1141,7 +1191,7 @@ int wilc_wlan_firmware_download(struct wilc *wilc, const u8 *buffer, int wilc_wlan_start(struct wilc *wilc) { u32 reg = 0; - int ret; + int ret, rv; u32 chipid; if (wilc->io_type == WILC_HIF_SDIO) { @@ -1150,7 +1200,10 @@ int wilc_wlan_start(struct wilc *wilc) } else if (wilc->io_type == WILC_HIF_SPI) { reg = 1; } - acquire_bus(wilc, WILC_BUS_ACQUIRE_ONLY); + ret = acquire_bus(wilc, WILC_BUS_ACQUIRE_ONLY); + if (ret) + return ret; + ret = wilc->hif_func->hif_write_reg(wilc, WILC_VMM_CORE_CFG, reg); if (ret) goto release; @@ -1181,16 +1234,18 @@ int wilc_wlan_start(struct wilc *wilc) wilc->hif_func->hif_read_reg(wilc, WILC_GLB_RESET_0, ®); release: - release_bus(wilc, WILC_BUS_RELEASE_ONLY); - return ret; + rv = release_bus(wilc, WILC_BUS_RELEASE_ONLY); + return ret ? ret : rv; } int wilc_wlan_stop(struct wilc *wilc, struct wilc_vif *vif) { u32 reg = 0; - int ret; + int ret, rv; - acquire_bus(wilc, WILC_BUS_ACQUIRE_AND_WAKEUP); + ret = acquire_bus(wilc, WILC_BUS_ACQUIRE_AND_WAKEUP); + if (ret) + return ret; ret = wilc->hif_func->hif_read_reg(wilc, GLOBAL_MODE_CONTROL, ®); if (ret) @@ -1226,9 +1281,9 @@ int wilc_wlan_stop(struct wilc *wilc, struct wilc_vif *vif) ret = 0; release: /* host comm is disabled - we can't issue sleep command anymore: */ - release_bus(wilc, WILC_BUS_RELEASE_ONLY); + rv = release_bus(wilc, WILC_BUS_RELEASE_ONLY); - return ret; + return ret ? ret : rv; } void wilc_wlan_cleanup(struct net_device *dev) @@ -1434,11 +1489,13 @@ EXPORT_SYMBOL_GPL(wilc_get_chipid); static int init_chip(struct net_device *dev) { u32 reg; - int ret = 0; + int ret, rv; struct wilc_vif *vif = netdev_priv(dev); struct wilc *wilc = vif->wilc; - acquire_bus(wilc, WILC_BUS_ACQUIRE_AND_WAKEUP); + ret = acquire_bus(wilc, WILC_BUS_ACQUIRE_AND_WAKEUP); + if (ret) + return ret; ret = wilc_get_chipid(wilc); if (ret) @@ -1470,17 +1527,19 @@ static int init_chip(struct net_device *dev) } release: - release_bus(wilc, WILC_BUS_RELEASE_ALLOW_SLEEP); + rv = release_bus(wilc, WILC_BUS_RELEASE_ALLOW_SLEEP); - return ret; + return ret ? ret : rv; } int wilc_load_mac_from_nv(struct wilc *wl) { - int ret = -EINVAL; + int ret, rv; unsigned int i; - acquire_bus(wl, WILC_BUS_ACQUIRE_AND_WAKEUP); + ret = acquire_bus(wl, WILC_BUS_ACQUIRE_AND_WAKEUP); + if (ret) + return ret; for (i = 0; i < WILC_NVMEM_MAX_NUM_BANK; i++) { int bank_offset = get_bank_offset_from_bank_index(i); @@ -1519,14 +1578,14 @@ int wilc_load_mac_from_nv(struct wilc *wl) break; } - release_bus(wl, WILC_BUS_RELEASE_ALLOW_SLEEP); - return ret; + rv = release_bus(wl, WILC_BUS_RELEASE_ALLOW_SLEEP); + return ret ? ret : rv; } EXPORT_SYMBOL_GPL(wilc_load_mac_from_nv); int wilc_wlan_init(struct net_device *dev) { - int ret = 0; + int ret = 0, rv; struct wilc_vif *vif = netdev_priv(dev); struct wilc *wilc; @@ -1535,11 +1594,16 @@ int wilc_wlan_init(struct net_device *dev) wilc->quit = 0; if (!wilc->hif_func->hif_is_init(wilc)) { - acquire_bus(wilc, WILC_BUS_ACQUIRE_ONLY); + ret = acquire_bus(wilc, WILC_BUS_ACQUIRE_ONLY); + if (ret) + return ret; + ret = wilc->hif_func->hif_init(wilc, false); if (!ret) ret = wilc_get_chipid(wilc); - release_bus(wilc, WILC_BUS_RELEASE_ONLY); + rv = release_bus(wilc, WILC_BUS_RELEASE_ONLY); + if (!ret && rv) + ret = rv; if (ret) goto fail; diff --git a/drivers/net/wireless/microchip/wilc1000/wlan.h b/drivers/net/wireless/microchip/wilc1000/wlan.h index 90ba76cf14dd1..552590823e444 100644 --- a/drivers/net/wireless/microchip/wilc1000/wlan.h +++ b/drivers/net/wireless/microchip/wilc1000/wlan.h @@ -436,8 +436,8 @@ netdev_tx_t wilc_mac_xmit(struct sk_buff *skb, struct net_device *dev); void wilc_wfi_p2p_rx(struct wilc_vif *vif, u8 *buff, u32 size); bool wilc_wfi_mgmt_frame_rx(struct wilc_vif *vif, u8 *buff, u32 size); -void host_wakeup_notify(struct wilc *wilc); -void host_sleep_notify(struct wilc *wilc); +int host_wakeup_notify(struct wilc *wilc); +int host_sleep_notify(struct wilc *wilc); int wilc_send_config_pkt(struct wilc_vif *vif, u8 mode, struct wid *wids, u32 count); int wilc_wlan_init(struct net_device *dev); From patchwork Fri Oct 4 11:44:14 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: Marek Vasut X-Patchwork-Id: 13822199 X-Patchwork-Delegate: kvalo@adurom.com Received: from phobos.denx.de (phobos.denx.de [85.214.62.61]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id BF5A715B145; Fri, 4 Oct 2024 11:46:32 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=85.214.62.61 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1728042394; cv=none; b=S3G6Q9kLcjrA7yOM+8Ulo+VoNA4439J0QRDXZPIfZL3+7hIJUTmbItyFvQySzHB4wYFMVlTmIioMB3QnWyS9PKyzR7T2e1rAF3yAR8P4AIMgJbD+hzBF+A87aePDYhMLRqx2G3WWgR577+PMSkqwxqXQ3CbkijLAGK0cJ8l22Qw= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1728042394; c=relaxed/simple; bh=pLRL4uNAsBdSsl/8297mRFSQhpLkaHVbltaBLL3ow1M=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version:Content-Type; b=cV4CagGW5XcGIoMmU7E8hgEGr3RZ9kycKryiWlFNYops/5LVi1HEI0SyCmeTO3jsalMMJY+xq2thebJovnEixqOmQv4KhNJVxeKvalGjrcmTQ/ch6C+0lNC8B5IrSR1bNTKDicHdeMmefWQt3jX4SqKRp3nsM1snEPsBGozrSTI= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=denx.de; spf=pass smtp.mailfrom=denx.de; dkim=pass (2048-bit key) header.d=denx.de header.i=@denx.de header.b=qwwyS00Z; arc=none smtp.client-ip=85.214.62.61 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=denx.de Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=denx.de Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=denx.de header.i=@denx.de header.b="qwwyS00Z" Received: from tr.lan (ip-86-49-120-218.bb.vodafone.cz [86.49.120.218]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits)) (No client certificate requested) (Authenticated sender: marex@denx.de) by phobos.denx.de (Postfix) with ESMTPSA id 9B86488B99; Fri, 4 Oct 2024 13:46:24 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=denx.de; s=phobos-20191101; t=1728042385; bh=a3nF4CrOMK8QElXjgm9oSZ32dTmvVTGYmLRfuYBNZrM=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=qwwyS00ZixjpiPkkhhIHJCjLnkFuT3nZSJqjATqDAzByDsjzeenrptlKBJ/oup+Ot 8R7Ix76prANrFuEwknZD7NNmE06aExdQoK4ewsh76IrknUX55cGU+op9kJHYm+aqoE KYR73AGIuZG82VOpoWO7U4o4EH4Q6YdV+cvUvstAYv9xt2lBrxnK6ZcZ7uMkScOA5S h4xd43yvCydizXSJDCkDc24mJolJ4TZyBGqcNSuLeoTfFEc2Hk3EklPvMaVtP69lC1 Pt7y6dF5UL87lnSyeU5PcBBEkJrOypvfb22Sfckd/giiZjPXAqSbS+VwLOPn0ujuQ6 d+kv5w8f0RQhQ== From: Marek Vasut To: linux-wireless@vger.kernel.org Cc: Marek Vasut , =?utf-8?q?Alexis_Lothor=C3=A9?= , "David S. Miller" , Adham Abozaeid , Ajay Singh , Claudiu Beznea , Conor Dooley , Eric Dumazet , Jakub Kicinski , Kalle Valo , Krzysztof Kozlowski , Paolo Abeni , Rob Herring , devicetree@vger.kernel.org, netdev@vger.kernel.org Subject: [PATCH v8 5/7] wifi: wilc1000: Fold wilc_create_wiphy() into cfg80211.c Date: Fri, 4 Oct 2024 13:44:14 +0200 Message-ID: <20241004114551.40236-5-marex@denx.de> X-Mailer: git-send-email 2.45.2 In-Reply-To: <20241004114551.40236-1-marex@denx.de> References: <20241004114551.40236-1-marex@denx.de> Precedence: bulk X-Mailing-List: linux-wireless@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 X-Virus-Scanned: clamav-milter 0.103.8 at phobos.denx.de X-Virus-Status: Clean The wilc_create_wiphy() is not used outside of cfg80211.c . Make the function static and remove its entry from cfg80211.h Reviewed-by: Alexis Lothoré Signed-off-by: Marek Vasut --- Cc: "David S. Miller" Cc: Adham Abozaeid Cc: Ajay Singh Cc: Alexis Lothoré Cc: Claudiu Beznea Cc: Conor Dooley Cc: Eric Dumazet Cc: Jakub Kicinski Cc: Kalle Valo Cc: Krzysztof Kozlowski Cc: Paolo Abeni Cc: Rob Herring Cc: devicetree@vger.kernel.org Cc: linux-wireless@vger.kernel.org Cc: netdev@vger.kernel.org --- V5: New patch V6: - Add RB from Alexis - Rebase on next-20240926 V7: - Rebase on next-20241003 / wireless-next/main 5a4d42c1688c with v2 wifi: wilc1000: Keep slot powered on during suspend/resume V8: No change --- .../wireless/microchip/wilc1000/cfg80211.c | 94 +++++++++---------- .../wireless/microchip/wilc1000/cfg80211.h | 1 - 2 files changed, 47 insertions(+), 48 deletions(-) diff --git a/drivers/net/wireless/microchip/wilc1000/cfg80211.c b/drivers/net/wireless/microchip/wilc1000/cfg80211.c index eb37b228d54ea..11e0f8a473467 100644 --- a/drivers/net/wireless/microchip/wilc1000/cfg80211.c +++ b/drivers/net/wireless/microchip/wilc1000/cfg80211.c @@ -1757,53 +1757,7 @@ void wlan_deinit_locks(struct wilc *wilc) cleanup_srcu_struct(&wilc->srcu); } -int wilc_cfg80211_init(struct wilc **wilc, struct device *dev, int io_type, - const struct wilc_hif_func *ops) -{ - struct wilc *wl; - int ret, i; - - wl = wilc_create_wiphy(dev); - if (!wl) - return -EINVAL; - - wlan_init_locks(wl); - - ret = wilc_wlan_cfg_init(wl); - if (ret) - goto free_wl; - - *wilc = wl; - wl->io_type = io_type; - wl->hif_func = ops; - - for (i = 0; i < NQUEUES; i++) - INIT_LIST_HEAD(&wl->txq[i].txq_head.list); - - INIT_LIST_HEAD(&wl->rxq_head.list); - INIT_LIST_HEAD(&wl->vif_list); - - wl->hif_workqueue = alloc_ordered_workqueue("%s", WQ_MEM_RECLAIM, - wiphy_name(wl->wiphy)); - if (!wl->hif_workqueue) { - ret = -ENOMEM; - goto free_cfg; - } - - return 0; - -free_cfg: - wilc_wlan_cfg_deinit(wl); - -free_wl: - wlan_deinit_locks(wl); - wiphy_unregister(wl->wiphy); - wiphy_free(wl->wiphy); - return ret; -} -EXPORT_SYMBOL_GPL(wilc_cfg80211_init); - -struct wilc *wilc_create_wiphy(struct device *dev) +static struct wilc *wilc_create_wiphy(struct device *dev) { struct wiphy *wiphy; struct wilc *wl; @@ -1861,6 +1815,52 @@ struct wilc *wilc_create_wiphy(struct device *dev) return wl; } +int wilc_cfg80211_init(struct wilc **wilc, struct device *dev, int io_type, + const struct wilc_hif_func *ops) +{ + struct wilc *wl; + int ret, i; + + wl = wilc_create_wiphy(dev); + if (!wl) + return -EINVAL; + + wlan_init_locks(wl); + + ret = wilc_wlan_cfg_init(wl); + if (ret) + goto free_wl; + + *wilc = wl; + wl->io_type = io_type; + wl->hif_func = ops; + + for (i = 0; i < NQUEUES; i++) + INIT_LIST_HEAD(&wl->txq[i].txq_head.list); + + INIT_LIST_HEAD(&wl->rxq_head.list); + INIT_LIST_HEAD(&wl->vif_list); + + wl->hif_workqueue = alloc_ordered_workqueue("%s", WQ_MEM_RECLAIM, + wiphy_name(wl->wiphy)); + if (!wl->hif_workqueue) { + ret = -ENOMEM; + goto free_cfg; + } + + return 0; + +free_cfg: + wilc_wlan_cfg_deinit(wl); + +free_wl: + wlan_deinit_locks(wl); + wiphy_unregister(wl->wiphy); + wiphy_free(wl->wiphy); + return ret; +} +EXPORT_SYMBOL_GPL(wilc_cfg80211_init); + int wilc_init_host_int(struct net_device *net) { int ret; diff --git a/drivers/net/wireless/microchip/wilc1000/cfg80211.h b/drivers/net/wireless/microchip/wilc1000/cfg80211.h index 8c65951cfaf96..fc04cc6615c1f 100644 --- a/drivers/net/wireless/microchip/wilc1000/cfg80211.h +++ b/drivers/net/wireless/microchip/wilc1000/cfg80211.h @@ -10,7 +10,6 @@ int wilc_cfg80211_init(struct wilc **wilc, struct device *dev, int io_type, const struct wilc_hif_func *ops); -struct wilc *wilc_create_wiphy(struct device *dev); void wilc_deinit_host_int(struct net_device *net); int wilc_init_host_int(struct net_device *net); void wilc_wfi_monitor_rx(struct net_device *mon_dev, u8 *buff, u32 size); From patchwork Fri Oct 4 11:44:15 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: Marek Vasut X-Patchwork-Id: 13822200 X-Patchwork-Delegate: kvalo@adurom.com Received: from phobos.denx.de (phobos.denx.de [85.214.62.61]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id D481415E5D4; Fri, 4 Oct 2024 11:46:33 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=85.214.62.61 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1728042395; cv=none; b=GFmT4+3XFaBT9hmphhYTQ5tO3LJjcBCpL0HSWCxMQU6+DJW5UQWbrf+s5+EmbiWB25fU9AX1QWrlOc4iAJzVUUbM2wSCnNuk6v2FffzftheC23r/LnVbnzowd+OoV0oDd2rly74Q4Vd/TOcZsu4ATOzLy7lJY3mnV0y05u3YVTA= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1728042395; c=relaxed/simple; bh=0N4cattN9mng7Q87NDzbY459V4mEVcxjye5kyUQYc20=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version:Content-Type; b=X02gnVTFlHhpUeM6mqJu15uLbdCool2wYXLyDznZaYDWxdGQa6Ze8M8jMeyoYO5gX93FGP9NiSyOzn6u5KgKrUoe9voJq9wTFboORE2ZL0KoRKvUEONrobXVXdk4Ylctq9QMA7MNQMLprlKnVcUl6tulqybaV9jjpLW5Q1MtzqI= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=denx.de; spf=pass smtp.mailfrom=denx.de; dkim=pass (2048-bit key) header.d=denx.de header.i=@denx.de header.b=acBQ+0dk; arc=none smtp.client-ip=85.214.62.61 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=denx.de Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=denx.de Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=denx.de header.i=@denx.de header.b="acBQ+0dk" Received: from tr.lan (ip-86-49-120-218.bb.vodafone.cz [86.49.120.218]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits)) (No client certificate requested) (Authenticated sender: marex@denx.de) by phobos.denx.de (Postfix) with ESMTPSA id 38F7488C44; Fri, 4 Oct 2024 13:46:25 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=denx.de; s=phobos-20191101; t=1728042385; bh=yHc9+e6PfN1IBzEjVkkbXHGodLSR1na0x4Zw+gH040U=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=acBQ+0dkhv1KeLsMmFge5g/xMdta2esY6t6QIbRb5fWC2Kf3i7R46ScMIc2KJSvYD juC4w5vP6bUuyx6TpUgBAFEECNlarHZIB1nRqVGl7N6DVGsartH7lcgNqW3YQaSKKY K7PzGIKZzj8djMAAtirzvfrCvDw5+DmV92jUJwQvz3Oa6bLGgBMfhRcbOPOTodZn5E l+NyQFWebV1TjRY9dOF57YsfR3YOwj+5SeBaL5ymrTiaUmhYKpfqZGZNWrP9H0iiLk aCJfmI75egkfBOkY9wTbbGRxAPeDS10IV7/ifHLJCFUZIYRoJ0TIb8lrseOQhBMvbm BfuJgQs9I9ZkA== From: Marek Vasut To: linux-wireless@vger.kernel.org Cc: Marek Vasut , =?utf-8?q?Alexis_Lothor=C3=A9?= , "David S. Miller" , Adham Abozaeid , Ajay Singh , Claudiu Beznea , Conor Dooley , Eric Dumazet , Jakub Kicinski , Kalle Valo , Krzysztof Kozlowski , Paolo Abeni , Rob Herring , devicetree@vger.kernel.org, netdev@vger.kernel.org Subject: [PATCH v8 6/7] wifi: wilc1000: Register wiphy after reading out chipid Date: Fri, 4 Oct 2024 13:44:15 +0200 Message-ID: <20241004114551.40236-6-marex@denx.de> X-Mailer: git-send-email 2.45.2 In-Reply-To: <20241004114551.40236-1-marex@denx.de> References: <20241004114551.40236-1-marex@denx.de> Precedence: bulk X-Mailing-List: linux-wireless@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 X-Virus-Scanned: clamav-milter 0.103.8 at phobos.denx.de X-Virus-Status: Clean Register wiphy after reading out chipid, so the chipid can be used to determine chip features and not advertise WPA3/SAE support to userspace on WILC3000. Note that wilc_netdev_cleanup() will deregister the wiphy in fail path. Tested-by: Alexis Lothoré Tested-on: WILC1000SD 07 SDIO WILC_WIFI_FW_REL_16_1_2 Tested-on: WILC3000 A SDIO WILC_WIFI_FW_REL_16_1_1 Signed-off-by: Marek Vasut --- Cc: "David S. Miller" Cc: Adham Abozaeid Cc: Ajay Singh Cc: Alexis Lothoré Cc: Claudiu Beznea Cc: Conor Dooley Cc: Eric Dumazet Cc: Jakub Kicinski Cc: Kalle Valo Cc: Krzysztof Kozlowski Cc: Paolo Abeni Cc: Rob Herring Cc: devicetree@vger.kernel.org Cc: linux-wireless@vger.kernel.org Cc: netdev@vger.kernel.org --- V5: New patch V6: - Rebase on next-20240926 V7: - Rebase on next-20241003 / wireless-next/main 5a4d42c1688c with v2 wifi: wilc1000: Keep slot powered on during suspend/resume V8: - Drop wiphy_unregister() from wilc_cfg80211_init() - Add TB from Alexis --- .../net/wireless/microchip/wilc1000/cfg80211.c | 16 ++++++++-------- .../net/wireless/microchip/wilc1000/cfg80211.h | 1 + drivers/net/wireless/microchip/wilc1000/sdio.c | 4 ++++ drivers/net/wireless/microchip/wilc1000/spi.c | 4 ++++ 4 files changed, 17 insertions(+), 8 deletions(-) diff --git a/drivers/net/wireless/microchip/wilc1000/cfg80211.c b/drivers/net/wireless/microchip/wilc1000/cfg80211.c index 11e0f8a473467..283f8df046884 100644 --- a/drivers/net/wireless/microchip/wilc1000/cfg80211.c +++ b/drivers/net/wireless/microchip/wilc1000/cfg80211.c @@ -1761,7 +1761,6 @@ static struct wilc *wilc_create_wiphy(struct device *dev) { struct wiphy *wiphy; struct wilc *wl; - int ret; wiphy = wiphy_new(&wilc_cfg80211_ops, sizeof(*wl)); if (!wiphy) @@ -1804,14 +1803,8 @@ static struct wilc *wilc_create_wiphy(struct device *dev) BIT(NL80211_IFTYPE_P2P_GO) | BIT(NL80211_IFTYPE_P2P_CLIENT); wiphy->flags |= WIPHY_FLAG_HAS_REMAIN_ON_CHANNEL; - wiphy->features |= NL80211_FEATURE_SAE; set_wiphy_dev(wiphy, dev); wl->wiphy = wiphy; - ret = wiphy_register(wiphy); - if (ret) { - wiphy_free(wiphy); - return NULL; - } return wl; } @@ -1855,12 +1848,19 @@ int wilc_cfg80211_init(struct wilc **wilc, struct device *dev, int io_type, free_wl: wlan_deinit_locks(wl); - wiphy_unregister(wl->wiphy); wiphy_free(wl->wiphy); return ret; } EXPORT_SYMBOL_GPL(wilc_cfg80211_init); +int wilc_cfg80211_register(struct wilc *wilc) +{ + wilc->wiphy->features |= NL80211_FEATURE_SAE; + + return wiphy_register(wilc->wiphy); +} +EXPORT_SYMBOL_GPL(wilc_cfg80211_register); + int wilc_init_host_int(struct net_device *net) { int ret; diff --git a/drivers/net/wireless/microchip/wilc1000/cfg80211.h b/drivers/net/wireless/microchip/wilc1000/cfg80211.h index fc04cc6615c1f..2dc9c1c42d609 100644 --- a/drivers/net/wireless/microchip/wilc1000/cfg80211.h +++ b/drivers/net/wireless/microchip/wilc1000/cfg80211.h @@ -10,6 +10,7 @@ int wilc_cfg80211_init(struct wilc **wilc, struct device *dev, int io_type, const struct wilc_hif_func *ops); +int wilc_cfg80211_register(struct wilc *wilc); void wilc_deinit_host_int(struct net_device *net); int wilc_init_host_int(struct net_device *net); void wilc_wfi_monitor_rx(struct net_device *mon_dev, u8 *buff, u32 size); diff --git a/drivers/net/wireless/microchip/wilc1000/sdio.c b/drivers/net/wireless/microchip/wilc1000/sdio.c index 9173f6f3beabf..56a929281d6a7 100644 --- a/drivers/net/wireless/microchip/wilc1000/sdio.c +++ b/drivers/net/wireless/microchip/wilc1000/sdio.c @@ -186,6 +186,10 @@ static int wilc_sdio_probe(struct sdio_func *func, if (ret) goto dispose_irq; + ret = wilc_cfg80211_register(wilc); + if (ret) + goto dispose_irq; + ret = wilc_load_mac_from_nv(wilc); if (ret) { pr_err("Can not retrieve MAC address from chip\n"); diff --git a/drivers/net/wireless/microchip/wilc1000/spi.c b/drivers/net/wireless/microchip/wilc1000/spi.c index 81cf82c9175ef..28d211ee60096 100644 --- a/drivers/net/wireless/microchip/wilc1000/spi.c +++ b/drivers/net/wireless/microchip/wilc1000/spi.c @@ -249,6 +249,10 @@ static int wilc_bus_probe(struct spi_device *spi) if (ret) goto power_down; + ret = wilc_cfg80211_register(wilc); + if (ret) + goto power_down; + ret = wilc_load_mac_from_nv(wilc); if (ret) { pr_err("Can not retrieve MAC address from chip\n"); From patchwork Fri Oct 4 11:44:16 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: Marek Vasut X-Patchwork-Id: 13822201 X-Patchwork-Delegate: kvalo@adurom.com Received: from phobos.denx.de (phobos.denx.de [85.214.62.61]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id D61DE15ECDC; Fri, 4 Oct 2024 11:46:33 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=85.214.62.61 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1728042396; cv=none; b=ZiFx7il6ACxVqoOrxAvQo9oMkfm1/UU3iuyEUdpivHArBwpY1UUcEHr6JKgO/VC75MYHAFQZcts1hB5xA1GdGgwBSuqAwQF4z4VlgM6DIFZ1n7khOWrr3WZA2aL+QIMO+NEXtAh9nD2GnXd+Lr+17KdFJgKtFEQH6fVq4XqHtks= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1728042396; c=relaxed/simple; bh=SYIrVgqBede8Uy/eq90YZikgBJVI7mM3mf9bqcLzO7I=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version:Content-Type; b=lpYWrby8id7ECHg6h6pL6aXNTFnkyMsT4w/j8PSyE2tEY3fYe2WujDGkg87Pb4DnQSkLpB/CR0o5ByxQph7MuJ0UNUuXHKrOFYrgTakFXR9qDS18E+oOVduRopXiFTyWWLpQ0XCgn3/Bi8SMtPuUh7kjgdektudGWTAbQdlW6l8= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=denx.de; spf=pass smtp.mailfrom=denx.de; dkim=pass (2048-bit key) header.d=denx.de header.i=@denx.de header.b=YHDaMKz5; arc=none smtp.client-ip=85.214.62.61 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=denx.de Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=denx.de Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=denx.de header.i=@denx.de header.b="YHDaMKz5" Received: from tr.lan (ip-86-49-120-218.bb.vodafone.cz [86.49.120.218]) (using TLSv1.3 with cipher TLS_AES_256_GCM_SHA384 (256/256 bits)) (No client certificate requested) (Authenticated sender: marex@denx.de) by phobos.denx.de (Postfix) with ESMTPSA id CC99588C4C; Fri, 4 Oct 2024 13:46:25 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=denx.de; s=phobos-20191101; t=1728042386; bh=vcmQUqFgkLnrY7+VCQr4/xXEGAPntvoDH/T/S6K70a8=; h=From:To:Cc:Subject:Date:In-Reply-To:References:From; b=YHDaMKz5tTBHGzxk20dFuo9TrBd0rj2uhL37kFPFvXqs3WSoauxu4jyUcs+XFiU/x 6M9h5WSeo+jGyDpcq9SDBVWAoW2Ncy1dblkP+VBWajAnrDPEJ843hun2+NKRYwXMJ1 wXIvjsD8Px6s4Y6mzpAqj1ZoXV9YLp9DzRw7eH1t4ZWLZ5MeDTTJ149w3E5sUffafO xrTTWRR0tnc3u12JOGSRXE80x9UQkCcqMGmEOloBfOZiLuRE9/++Zmt3HcO+7kSKgZ Eo8kfluyjlBhJqBV02zfbYC4QdtEPg4TaXcPMBijry+/FPO+GrCPomqidUShVVTMkn CIfne9AiIkdbw== From: Marek Vasut To: linux-wireless@vger.kernel.org Cc: Ajay Singh , =?utf-8?q?Alexis_Lothor=C3=A9?= , Marek Vasut , "David S. Miller" , Adham Abozaeid , Claudiu Beznea , Conor Dooley , Eric Dumazet , Jakub Kicinski , Kalle Valo , Krzysztof Kozlowski , Paolo Abeni , Rob Herring , devicetree@vger.kernel.org, netdev@vger.kernel.org Subject: [PATCH v8 7/7] wifi: wilc1000: Add WILC3000 support Date: Fri, 4 Oct 2024 13:44:16 +0200 Message-ID: <20241004114551.40236-7-marex@denx.de> X-Mailer: git-send-email 2.45.2 In-Reply-To: <20241004114551.40236-1-marex@denx.de> References: <20241004114551.40236-1-marex@denx.de> Precedence: bulk X-Mailing-List: linux-wireless@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 X-Virus-Scanned: clamav-milter 0.103.8 at phobos.denx.de X-Virus-Status: Clean From: Ajay Singh Add support for the WILC3000 chip. The chip is similar to WILC1000, except that the register layout is slightly different and it does not support WPA3/SAE. Reviewed-by: Alexis Lothoré Tested-by: Alexis Lothoré Tested-on: WILC1000SD 07 SDIO WILC_WIFI_FW_REL_16_1_2 Tested-on: WILC1000SD 07 SPI WILC_WIFI_FW_REL_16_1_2 Tested-on: WILC3000 A SDIO WILC_WIFI_FW_REL_16_1_1 Tested-on: WILC3000 A SPI WILC_WIFI_FW_REL_16_1_1 Signed-off-by: Ajay Singh Signed-off-by: Marek Vasut --- Note: Squashed and updated from the following downstream patches: wifi: wilc1000: wilc3000 support added wifi: wilc1000: wilc3000 interrupt handling wifi: wilc1000: wilc3000 added chip wake and sleep support wifi: wilc1000: wilc3000 FW file sepecific changes --- Cc: "David S. Miller" Cc: Adham Abozaeid Cc: Ajay Singh Cc: Alexis Lothoré Cc: Claudiu Beznea Cc: Conor Dooley Cc: Eric Dumazet Cc: Jakub Kicinski Cc: Kalle Valo Cc: Krzysztof Kozlowski Cc: Paolo Abeni Cc: Rob Herring Cc: devicetree@vger.kernel.org Cc: linux-wireless@vger.kernel.org Cc: netdev@vger.kernel.org --- V2: - Return -EINVAL in wilc_sdio_init() if chip ID is not supported - Dispose of wilc_chip_type, replace with is_wilc1000()/is_wilc3000() - Remove wilc3000 DT compatible string handling, match on wilc1000 only, the device type can be auto-detected based on chipID V3: - Define and use WILC3000_BOOTROM_STATUS and WILC3000_CORTUS_BOOT_REGISTER_2 V4: - Fix up after dropping wilc_get_chipid() in netdev.c in 2/5 V5: - Advertise WPA3/SAE to userspace only on WILC1000 in wilc_create_wiphy() V6: - Rebase on next-20240926 V7: - Fix firmware name printing in wilc_wlan_get_firmware() netdev_info() - Rebase on next-20241003 / wireless-next/main 5a4d42c1688c with v2 wifi: wilc1000: Keep slot powered on during suspend/resume V8: Add RB/TB from Alexis --- .../wireless/microchip/wilc1000/cfg80211.c | 4 +- .../net/wireless/microchip/wilc1000/netdev.c | 29 ++- .../net/wireless/microchip/wilc1000/sdio.c | 62 ++++- drivers/net/wireless/microchip/wilc1000/spi.c | 2 +- .../net/wireless/microchip/wilc1000/wlan.c | 220 +++++++++++++++--- .../net/wireless/microchip/wilc1000/wlan.h | 45 +++- 6 files changed, 299 insertions(+), 63 deletions(-) diff --git a/drivers/net/wireless/microchip/wilc1000/cfg80211.c b/drivers/net/wireless/microchip/wilc1000/cfg80211.c index 283f8df046884..b0dae6f7c633b 100644 --- a/drivers/net/wireless/microchip/wilc1000/cfg80211.c +++ b/drivers/net/wireless/microchip/wilc1000/cfg80211.c @@ -1855,7 +1855,9 @@ EXPORT_SYMBOL_GPL(wilc_cfg80211_init); int wilc_cfg80211_register(struct wilc *wilc) { - wilc->wiphy->features |= NL80211_FEATURE_SAE; + /* WPA3/SAE supported only on WILC1000 */ + if (is_wilc1000(wilc->chipid)) + wilc->wiphy->features |= NL80211_FEATURE_SAE; return wiphy_register(wilc->wiphy); } diff --git a/drivers/net/wireless/microchip/wilc1000/netdev.c b/drivers/net/wireless/microchip/wilc1000/netdev.c index 3e80d29a99ccf..7e84fc0fd9118 100644 --- a/drivers/net/wireless/microchip/wilc1000/netdev.c +++ b/drivers/net/wireless/microchip/wilc1000/netdev.c @@ -23,6 +23,12 @@ #define __WILC1000_FW(api) WILC1000_FW_PREFIX #api ".bin" #define WILC1000_FW(api) __WILC1000_FW(api) +#define WILC3000_API_VER 1 + +#define WILC3000_FW_PREFIX "atmel/wilc3000_wifi_firmware-" +#define __WILC3000_FW(api) WILC3000_FW_PREFIX #api ".bin" +#define WILC3000_FW(api) __WILC3000_FW(api) + static irqreturn_t isr_uh_routine(int irq, void *user_data) { struct wilc *wilc = user_data; @@ -196,19 +202,23 @@ static int wilc_wlan_get_firmware(struct net_device *dev) struct wilc_vif *vif = netdev_priv(dev); struct wilc *wilc = vif->wilc; const struct firmware *wilc_fw; + char *firmware; int ret; - if (!is_wilc1000(wilc->chipid)) + if (is_wilc1000(wilc->chipid)) + firmware = WILC1000_FW(WILC1000_API_VER); + else if (is_wilc3000(wilc->chipid)) + firmware = WILC3000_FW(WILC3000_API_VER); + else return -EINVAL; - netdev_info(dev, "WILC1000 loading firmware [%s]\n", - WILC1000_FW(WILC1000_API_VER)); + netdev_info(dev, "WILC%d loading firmware [%s]\n", + is_wilc1000(wilc->chipid) ? 1000 : 3000, + firmware); - ret = request_firmware(&wilc_fw, WILC1000_FW(WILC1000_API_VER), - wilc->dev); + ret = request_firmware(&wilc_fw, firmware, wilc->dev); if (ret != 0) { - netdev_err(dev, "%s - firmware not available\n", - WILC1000_FW(WILC1000_API_VER)); + netdev_err(dev, "%s - firmware not available\n", firmware); return -EINVAL; } wilc->firmware = wilc_fw; @@ -233,7 +243,7 @@ static int wilc_start_firmware(struct net_device *dev) return 0; } -static int wilc1000_firmware_download(struct net_device *dev) +static int wilc_firmware_download(struct net_device *dev) { struct wilc_vif *vif = netdev_priv(dev); struct wilc *wilc = vif->wilc; @@ -528,7 +538,7 @@ static int wilc_wlan_initialize(struct net_device *dev, struct wilc_vif *vif) if (ret) goto fail_irq_enable; - ret = wilc1000_firmware_download(dev); + ret = wilc_firmware_download(dev); if (ret) goto fail_irq_enable; @@ -1014,3 +1024,4 @@ EXPORT_SYMBOL_GPL(wilc_netdev_ifc_init); MODULE_DESCRIPTION("Atmel WILC1000 core wireless driver"); MODULE_LICENSE("GPL"); MODULE_FIRMWARE(WILC1000_FW(WILC1000_API_VER)); +MODULE_FIRMWARE(WILC3000_FW(WILC3000_API_VER)); diff --git a/drivers/net/wireless/microchip/wilc1000/sdio.c b/drivers/net/wireless/microchip/wilc1000/sdio.c index 56a929281d6a7..5262c8846c13d 100644 --- a/drivers/net/wireless/microchip/wilc1000/sdio.c +++ b/drivers/net/wireless/microchip/wilc1000/sdio.c @@ -810,13 +810,19 @@ static int wilc_sdio_read_int(struct wilc *wilc, u32 *int_status) cmd.address = WILC_SDIO_EXT_IRQ_FLAG_REG; } else { cmd.function = 0; - cmd.address = WILC_SDIO_IRQ_FLAG_REG; + cmd.address = is_wilc1000(wilc->chipid) ? + WILC1000_SDIO_IRQ_FLAG_REG : + WILC3000_SDIO_IRQ_FLAG_REG; } cmd.raw = 0; cmd.read_write = 0; cmd.data = 0; wilc_sdio_cmd52(wilc, &cmd); irq_flags = cmd.data; + + if (sdio_priv->irq_gpio) + irq_flags &= is_wilc1000(wilc->chipid) ? 0x1f : 0x0f; + tmp |= FIELD_PREP(IRG_FLAGS_MASK, cmd.data); if (FIELD_GET(UNHANDLED_IRQ_MASK, irq_flags)) @@ -838,22 +844,56 @@ static int wilc_sdio_clear_int_ext(struct wilc *wilc, u32 val) if (sdio_priv->irq_gpio) reg = val & (BIT(MAX_NUM_INT) - 1); - /* select VMM table 0 */ - if (val & SEL_VMM_TBL0) - reg |= BIT(5); - /* select VMM table 1 */ - if (val & SEL_VMM_TBL1) - reg |= BIT(6); - /* enable VMM */ - if (val & EN_VMM) - reg |= BIT(7); + if (is_wilc1000(wilc->chipid)) { + /* select VMM table 0 */ + if (val & SEL_VMM_TBL0) + reg |= BIT(5); + /* select VMM table 1 */ + if (val & SEL_VMM_TBL1) + reg |= BIT(6); + /* enable VMM */ + if (val & EN_VMM) + reg |= BIT(7); + } else { + if (sdio_priv->irq_gpio && reg) { + struct sdio_cmd52 cmd; + + cmd.read_write = 1; + cmd.function = 0; + cmd.raw = 0; + cmd.address = WILC3000_SDIO_IRQ_FLAG_REG; + cmd.data = reg; + + ret = wilc_sdio_cmd52(wilc, &cmd); + if (ret) { + dev_err(&func->dev, + "Failed cmd52, set 0xfe data (%d) ...\n", + __LINE__); + return ret; + } + } + + reg = 0; + /* select VMM table 0 */ + if (val & SEL_VMM_TBL0) + reg |= BIT(0); + /* select VMM table 1 */ + if (val & SEL_VMM_TBL1) + reg |= BIT(1); + /* enable VMM */ + if (val & EN_VMM) + reg |= BIT(2); + } + if (reg) { struct sdio_cmd52 cmd; cmd.read_write = 1; cmd.function = 0; cmd.raw = 0; - cmd.address = WILC_SDIO_IRQ_CLEAR_FLAG_REG; + cmd.address = is_wilc1000(wilc->chipid) ? + WILC1000_SDIO_IRQ_CLEAR_FLAG_REG : + WILC3000_SDIO_VMM_TBL_CTRL_REG; cmd.data = reg; ret = wilc_sdio_cmd52(wilc, &cmd); diff --git a/drivers/net/wireless/microchip/wilc1000/spi.c b/drivers/net/wireless/microchip/wilc1000/spi.c index 28d211ee60096..ce2a9cdd6aa78 100644 --- a/drivers/net/wireless/microchip/wilc1000/spi.c +++ b/drivers/net/wireless/microchip/wilc1000/spi.c @@ -1233,7 +1233,7 @@ static int wilc_validate_chipid(struct wilc *wilc) dev_err(&spi->dev, "Fail cmd read chip id...\n"); return ret; } - if (!is_wilc1000(chipid)) { + if (!is_wilc1000(chipid) && !is_wilc3000(chipid)) { dev_err(&spi->dev, "Unknown chip id 0x%x\n", chipid); return -ENODEV; } diff --git a/drivers/net/wireless/microchip/wilc1000/wlan.c b/drivers/net/wireless/microchip/wilc1000/wlan.c index 521caa498035e..9d80adc45d6be 100644 --- a/drivers/net/wireless/microchip/wilc1000/wlan.c +++ b/drivers/net/wireless/microchip/wilc1000/wlan.c @@ -541,7 +541,7 @@ static struct rxq_entry_t *wilc_wlan_rxq_remove(struct wilc *wilc) return rqe; } -static int chip_allow_sleep(struct wilc *wilc) +static int chip_allow_sleep_wilc1000(struct wilc *wilc) { u32 reg = 0; const struct wilc_hif_func *hif_func = wilc->hif_func; @@ -601,7 +601,41 @@ static int chip_allow_sleep(struct wilc *wilc) return 0; } -static int chip_wakeup(struct wilc *wilc) +static int chip_allow_sleep_wilc3000(struct wilc *wilc) +{ + u32 reg = 0; + int ret; + const struct wilc_hif_func *hif_func = wilc->hif_func; + + if (wilc->io_type == WILC_HIF_SDIO) { + ret = hif_func->hif_read_reg(wilc, WILC_SDIO_WAKEUP_REG, ®); + if (ret) + return ret; + ret = hif_func->hif_write_reg(wilc, WILC_SDIO_WAKEUP_REG, + reg & ~WILC_SDIO_WAKEUP_BIT); + if (ret) + return ret; + } else { + ret = hif_func->hif_read_reg(wilc, WILC_SPI_WAKEUP_REG, ®); + if (ret) + return ret; + ret = hif_func->hif_write_reg(wilc, WILC_SPI_WAKEUP_REG, + reg & ~WILC_SPI_WAKEUP_BIT); + if (ret) + return ret; + } + return 0; +} + +static int chip_allow_sleep(struct wilc *wilc) +{ + if (is_wilc1000(wilc->chipid)) + return chip_allow_sleep_wilc1000(wilc); + else + return chip_allow_sleep_wilc3000(wilc); +} + +static int chip_wakeup_wilc1000(struct wilc *wilc) { u32 ret = 0; u32 clk_status_val = 0, trials = 0; @@ -613,15 +647,15 @@ static int chip_wakeup(struct wilc *wilc) if (wilc->io_type == WILC_HIF_SDIO) { wakeup_reg = WILC_SDIO_WAKEUP_REG; wakeup_bit = WILC_SDIO_WAKEUP_BIT; - clk_status_reg = WILC_SDIO_CLK_STATUS_REG; - clk_status_bit = WILC_SDIO_CLK_STATUS_BIT; + clk_status_reg = WILC1000_SDIO_CLK_STATUS_REG; + clk_status_bit = WILC1000_SDIO_CLK_STATUS_BIT; from_host_to_fw_reg = WILC_SDIO_HOST_TO_FW_REG; from_host_to_fw_bit = WILC_SDIO_HOST_TO_FW_BIT; } else { wakeup_reg = WILC_SPI_WAKEUP_REG; wakeup_bit = WILC_SPI_WAKEUP_BIT; - clk_status_reg = WILC_SPI_CLK_STATUS_REG; - clk_status_bit = WILC_SPI_CLK_STATUS_BIT; + clk_status_reg = WILC1000_SPI_CLK_STATUS_REG; + clk_status_bit = WILC1000_SPI_CLK_STATUS_BIT; from_host_to_fw_reg = WILC_SPI_HOST_TO_FW_REG; from_host_to_fw_bit = WILC_SPI_HOST_TO_FW_BIT; } @@ -663,6 +697,74 @@ static int chip_wakeup(struct wilc *wilc) return 0; } +static int chip_wakeup_wilc3000(struct wilc *wilc) +{ + u32 wakeup_reg_val, clk_status_reg_val, trials = 0; + u32 wakeup_reg, wakeup_bit; + u32 clk_status_reg, clk_status_bit; + int wake_seq_trials = 5; + const struct wilc_hif_func *hif_func = wilc->hif_func; + + if (wilc->io_type == WILC_HIF_SDIO) { + wakeup_reg = WILC_SDIO_WAKEUP_REG; + wakeup_bit = WILC_SDIO_WAKEUP_BIT; + clk_status_reg = WILC3000_SDIO_CLK_STATUS_REG; + clk_status_bit = WILC3000_SDIO_CLK_STATUS_BIT; + } else { + wakeup_reg = WILC_SPI_WAKEUP_REG; + wakeup_bit = WILC_SPI_WAKEUP_BIT; + clk_status_reg = WILC3000_SPI_CLK_STATUS_REG; + clk_status_bit = WILC3000_SPI_CLK_STATUS_BIT; + } + + hif_func->hif_read_reg(wilc, wakeup_reg, &wakeup_reg_val); + do { + hif_func->hif_write_reg(wilc, wakeup_reg, wakeup_reg_val | + wakeup_bit); + /* Check the clock status */ + hif_func->hif_read_reg(wilc, clk_status_reg, + &clk_status_reg_val); + + /* In case of clocks off, wait 1ms, and check it again. + * if still off, wait for another 1ms, for a total wait of 3ms. + * If still off, redo the wake up sequence + */ + while ((clk_status_reg_val & clk_status_bit) == 0 && + (++trials % 4) != 0) { + /* Wait for the chip to stabilize*/ + usleep_range(1000, 1100); + + /* Make sure chip is awake. This is an extra step that + * can be removed later to avoid the bus access + * overhead + */ + hif_func->hif_read_reg(wilc, clk_status_reg, + &clk_status_reg_val); + } + /* in case of failure, Reset the wakeup bit to introduce a new + * edge on the next loop + */ + if ((clk_status_reg_val & clk_status_bit) == 0) { + hif_func->hif_write_reg(wilc, wakeup_reg, + wakeup_reg_val & (~wakeup_bit)); + /* added wait before wakeup sequence retry */ + usleep_range(200, 300); + } + } while ((clk_status_reg_val & clk_status_bit) == 0 && wake_seq_trials-- > 0); + if (!wake_seq_trials) + dev_err(wilc->dev, "clocks still OFF. Wake up failed\n"); + + return 0; +} + +static int chip_wakeup(struct wilc *wilc) +{ + if (is_wilc1000(wilc->chipid)) + return chip_wakeup_wilc1000(wilc); + else + return chip_wakeup_wilc3000(wilc); +} + static inline int acquire_bus(struct wilc *wilc, enum bus_acquire acquire) { int ret = 0; @@ -695,7 +797,9 @@ int host_wakeup_notify(struct wilc *wilc) if (ret) return ret; - wilc->hif_func->hif_write_reg(wilc, WILC_CORTUS_INTERRUPT_2, 1); + wilc->hif_func->hif_write_reg(wilc, is_wilc1000(wilc->chipid) ? + WILC1000_CORTUS_INTERRUPT_2 : + WILC3000_CORTUS_INTERRUPT_2, 1); return release_bus(wilc, WILC_BUS_RELEASE_ALLOW_SLEEP); } EXPORT_SYMBOL_GPL(host_wakeup_notify); @@ -707,7 +811,9 @@ int host_sleep_notify(struct wilc *wilc) if (ret) return ret; - wilc->hif_func->hif_write_reg(wilc, WILC_CORTUS_INTERRUPT_1, 1); + wilc->hif_func->hif_write_reg(wilc, is_wilc1000(wilc->chipid) ? + WILC1000_CORTUS_INTERRUPT_1 : + WILC3000_CORTUS_INTERRUPT_1, 1); return release_bus(wilc, WILC_BUS_RELEASE_ALLOW_SLEEP); } EXPORT_SYMBOL_GPL(host_sleep_notify); @@ -842,19 +948,45 @@ int wilc_wlan_handle_txq(struct wilc *wilc, u32 *txq_count) if (ret) break; - ret = func->hif_write_reg(wilc, WILC_HOST_VMM_CTL, 0x2); - if (ret) - break; + if (is_wilc1000(wilc->chipid)) { + ret = func->hif_write_reg(wilc, WILC_HOST_VMM_CTL, 0x2); + if (ret) + break; - do { - ret = func->hif_read_reg(wilc, WILC_HOST_VMM_CTL, ®); + do { + ret = func->hif_read_reg(wilc, WILC_HOST_VMM_CTL, ®); + if (ret) + break; + if (FIELD_GET(WILC_VMM_ENTRY_AVAILABLE, reg)) { + entries = FIELD_GET(WILC_VMM_ENTRY_COUNT, reg); + break; + } + } while (--timeout); + } else { + ret = func->hif_write_reg(wilc, WILC_HOST_VMM_CTL, 0); if (ret) break; - if (FIELD_GET(WILC_VMM_ENTRY_AVAILABLE, reg)) { - entries = FIELD_GET(WILC_VMM_ENTRY_COUNT, reg); + + /* interrupt firmware */ + ret = func->hif_write_reg(wilc, WILC_CORTUS_INTERRUPT_BASE, 1); + if (ret) break; - } - } while (--timeout); + + do { + ret = func->hif_read_reg(wilc, WILC_CORTUS_INTERRUPT_BASE, ®); + if (ret) + break; + if (reg == 0) { + /* Get the entries */ + ret = func->hif_read_reg(wilc, WILC_HOST_VMM_CTL, ®); + if (ret) + break; + + entries = FIELD_GET(WILC_VMM_ENTRY_COUNT, reg); + break; + } + } while (--timeout); + } if (timeout <= 0) { ret = func->hif_write_reg(wilc, WILC_HOST_VMM_CTL, 0x0); break; @@ -1212,6 +1344,9 @@ int wilc_wlan_start(struct wilc *wilc) if (wilc->io_type == WILC_HIF_SDIO && wilc->dev_irq_num) reg |= WILC_HAVE_SDIO_IRQ_GPIO; + if (is_wilc3000(wilc->chipid)) + reg |= WILC_HAVE_SLEEP_CLK_SRC_RTC; + ret = wilc->hif_func->hif_write_reg(wilc, WILC_GP_REG_1, reg); if (ret) goto release; @@ -1462,21 +1597,25 @@ int wilc_get_chipid(struct wilc *wilc) u32 rfrevid = 0; if (wilc->chipid == 0) { - wilc->hif_func->hif_read_reg(wilc, WILC_CHIPID, &chipid); - wilc->hif_func->hif_read_reg(wilc, WILC_RF_REVISION_ID, - &rfrevid); - if (!is_wilc1000(chipid)) { - wilc->chipid = 0; - return -EINVAL; - } - if (chipid == WILC_1000_BASE_ID_2A) { /* 0x1002A0 */ - if (rfrevid != 0x1) - chipid = WILC_1000_BASE_ID_2A_REV1; - } else if (chipid == WILC_1000_BASE_ID_2B) { /* 0x1002B0 */ - if (rfrevid == 0x4) - chipid = WILC_1000_BASE_ID_2B_REV1; - else if (rfrevid != 0x3) - chipid = WILC_1000_BASE_ID_2B_REV2; + wilc->hif_func->hif_read_reg(wilc, WILC3000_CHIP_ID, &chipid); + if (!is_wilc3000(chipid)) { + wilc->hif_func->hif_read_reg(wilc, WILC_CHIPID, &chipid); + wilc->hif_func->hif_read_reg(wilc, WILC_RF_REVISION_ID, + &rfrevid); + + if (!is_wilc1000(chipid)) { + wilc->chipid = 0; + return -EINVAL; + } + if (chipid == WILC_1000_BASE_ID_2A) { /* 0x1002A0 */ + if (rfrevid != 0x1) + chipid = WILC_1000_BASE_ID_2A_REV1; + } else if (chipid == WILC_1000_BASE_ID_2B) { /* 0x1002B0 */ + if (rfrevid == 0x4) + chipid = WILC_1000_BASE_ID_2B_REV1; + else if (rfrevid != 0x3) + chipid = WILC_1000_BASE_ID_2B_REV2; + } } wilc->chipid = chipid; @@ -1526,6 +1665,21 @@ static int init_chip(struct net_device *dev) } } + if (is_wilc3000(wilc->chipid)) { + ret = wilc->hif_func->hif_read_reg(wilc, WILC3000_BOOTROM_STATUS, ®); + if (ret) { + netdev_err(dev, "failed to read WILC3000 BootROM status register\n"); + goto release; + } + + ret = wilc->hif_func->hif_write_reg(wilc, WILC3000_CORTUS_BOOT_REGISTER_2, + WILC_CORTUS_BOOT_FROM_IRAM); + if (ret) { + netdev_err(dev, "failed to write WILC3000 Boot register\n"); + goto release; + } + } + release: rv = release_bus(wilc, WILC_BUS_RELEASE_ALLOW_SLEEP); @@ -1607,7 +1761,7 @@ int wilc_wlan_init(struct net_device *dev) if (ret) goto fail; - if (!is_wilc1000(wilc->chipid)) { + if (!is_wilc1000(wilc->chipid) && !is_wilc3000(wilc->chipid)) { netdev_err(dev, "Unsupported chipid: %x\n", wilc->chipid); ret = -EINVAL; goto fail; diff --git a/drivers/net/wireless/microchip/wilc1000/wlan.h b/drivers/net/wireless/microchip/wilc1000/wlan.h index 552590823e444..b9e7f9222eadd 100644 --- a/drivers/net/wireless/microchip/wilc1000/wlan.h +++ b/drivers/net/wireless/microchip/wilc1000/wlan.h @@ -96,8 +96,14 @@ #define WILC_SPI_WAKEUP_REG 0x1 #define WILC_SPI_WAKEUP_BIT BIT(1) -#define WILC_SPI_CLK_STATUS_REG 0x0f -#define WILC_SPI_CLK_STATUS_BIT BIT(2) +/* WILC1000 specific */ +#define WILC1000_SPI_CLK_STATUS_REG 0x0f +#define WILC1000_SPI_CLK_STATUS_BIT BIT(2) + +/* WILC3000 specific */ +#define WILC3000_SPI_CLK_STATUS_REG 0x13 +#define WILC3000_SPI_CLK_STATUS_BIT BIT(2) + #define WILC_SPI_HOST_TO_FW_REG 0x0b #define WILC_SPI_HOST_TO_FW_BIT BIT(0) @@ -123,14 +129,24 @@ #define WILC_SDIO_WAKEUP_REG 0xf0 #define WILC_SDIO_WAKEUP_BIT BIT(0) -#define WILC_SDIO_CLK_STATUS_REG 0xf1 -#define WILC_SDIO_CLK_STATUS_BIT BIT(0) +/* WILC1000 */ +#define WILC1000_SDIO_CLK_STATUS_REG 0xf1 +#define WILC1000_SDIO_CLK_STATUS_BIT BIT(0) + +#define WILC1000_SDIO_IRQ_FLAG_REG 0xf7 +#define WILC1000_SDIO_IRQ_CLEAR_FLAG_REG 0xf8 + +/* WILC3000 specific */ +#define WILC3000_SDIO_CLK_STATUS_REG 0xf0 /* clk & wakeup are on same reg */ +#define WILC3000_SDIO_CLK_STATUS_BIT BIT(4) + +#define WILC3000_SDIO_VMM_TBL_CTRL_REG 0xf1 +#define WILC3000_SDIO_IRQ_FLAG_REG 0xfe +/* Common vendor specific CCCR register */ #define WILC_SDIO_INTERRUPT_DATA_SZ_REG 0xf2 /* Read size (2 bytes) */ #define WILC_SDIO_VMM_TBL_CTRL_REG 0xf6 -#define WILC_SDIO_IRQ_FLAG_REG 0xf7 -#define WILC_SDIO_IRQ_CLEAR_FLAG_REG 0xf8 #define WILC_SDIO_HOST_TO_FW_REG 0xfa #define WILC_SDIO_HOST_TO_FW_BIT BIT(0) @@ -172,8 +188,11 @@ #define WILC_HAVE_USE_IRQ_AS_HOST_WAKE BIT(8) #define WILC_CORTUS_INTERRUPT_BASE 0x10A8 -#define WILC_CORTUS_INTERRUPT_1 (WILC_CORTUS_INTERRUPT_BASE + 0x4) -#define WILC_CORTUS_INTERRUPT_2 (WILC_CORTUS_INTERRUPT_BASE + 0x8) +#define WILC1000_CORTUS_INTERRUPT_1 (WILC_CORTUS_INTERRUPT_BASE + 0x4) +#define WILC3000_CORTUS_INTERRUPT_1 (WILC_CORTUS_INTERRUPT_BASE + 0x14) + +#define WILC1000_CORTUS_INTERRUPT_2 (WILC_CORTUS_INTERRUPT_BASE + 0x8) +#define WILC3000_CORTUS_INTERRUPT_2 (WILC_CORTUS_INTERRUPT_BASE + 0x18) /* tx control register 1 to 4 for RX */ #define WILC_REG_4_TO_1_RX 0x1e1c @@ -183,6 +202,9 @@ #define WILC_CORTUS_RESET_MUX_SEL 0x1118 #define WILC_CORTUS_BOOT_REGISTER 0xc0000 +#define WILC3000_BOOTROM_STATUS 0x207ac +#define WILC3000_CORTUS_BOOT_REGISTER_2 0x4f0000 +#define WILC3000_CHIP_ID 0x3b0000 #define WILC_CORTUS_BOOT_FROM_IRAM 0x71 @@ -195,6 +217,8 @@ #define WILC_1000_BASE_ID_2B_REV1 (WILC_1000_BASE_ID_2B + 1) #define WILC_1000_BASE_ID_2B_REV2 (WILC_1000_BASE_ID_2B + 2) +#define WILC_3000_BASE_ID 0x300000 + #define WILC_CHIP_REV_FIELD GENMASK(11, 0) /******************************************** @@ -413,6 +437,11 @@ static inline bool is_wilc1000(u32 id) return (id & (~WILC_CHIP_REV_FIELD)) == WILC_1000_BASE_ID; } +static inline bool is_wilc3000(u32 id) +{ + return (id & (~WILC_CHIP_REV_FIELD)) == WILC_3000_BASE_ID; +} + int wilc_wlan_firmware_download(struct wilc *wilc, const u8 *buffer, u32 buffer_size); int wilc_wlan_start(struct wilc *wilc);