From patchwork Sat Aug 21 01:09:13 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Christian Lamparter X-Patchwork-Id: 12450753 X-Patchwork-Delegate: kvalo@adurom.com Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-15.8 required=3.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID,DKIM_VALID_AU,FREEMAIL_FORGED_FROMDOMAIN,FREEMAIL_FROM, HEADER_FROM_DIFFERENT_DOMAINS,INCLUDES_CR_TRAILER,INCLUDES_PATCH, MAILING_LIST_MULTI,SPF_HELO_NONE,SPF_PASS,USER_AGENT_GIT autolearn=unavailable autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id 671FEC4338F for ; Sat, 21 Aug 2021 01:09:23 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 4BCA4611C3 for ; Sat, 21 Aug 2021 01:09:23 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S240908AbhHUBJ6 (ORCPT ); Fri, 20 Aug 2021 21:09:58 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:40268 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S232466AbhHUBJ5 (ORCPT ); Fri, 20 Aug 2021 21:09:57 -0400 Received: from mail-wm1-x330.google.com (mail-wm1-x330.google.com [IPv6:2a00:1450:4864:20::330]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 327F1C061756; Fri, 20 Aug 2021 18:09:18 -0700 (PDT) Received: by mail-wm1-x330.google.com with SMTP id k5-20020a05600c1c85b02902e699a4d20cso7039847wms.2; Fri, 20 Aug 2021 18:09:18 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:subject:date:message-id:mime-version :content-transfer-encoding; bh=AcYSAh37tYGfOcz68oPLczgRQrzJo44tg66hXDfFigc=; b=OG1FxgjXGBWAxGA1anG/qouatpziretSb3btXyjQ0HvbXcQqium0ZqecGus6IbGl+H HzhLD7XrmsuuaHPsNI0ei/6UpTRU9Ro3mKJLEkubLn8rwj6nwEHT3snMDRWpYbRfg8Jt aPPw3S0cB+5/fFWfdQaw4ncloi7juZFnXElENdg0qFHnRManGUDp99u5xsILxjnWg5Gv tfGRmStx8SGrUsD7n68Geg1n/zDriEBhBAcKubbX4z9U8KgObDpvGMerQUKmDreOlkW7 ZVH7lBbl18aKIkmiO4dmXsVKodrUAe6ZZerOvRonTo18BAWL6Lv5H4gk+VDftlL+t7Ma nrog== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:mime-version :content-transfer-encoding; bh=AcYSAh37tYGfOcz68oPLczgRQrzJo44tg66hXDfFigc=; b=W9aYyYagvb2DALE797ijhPsSUQDZ7DnyKsVYf4lzyf/BDWglvdf2Iwr4Ne2+TH9jjQ 1U8ya20kL8EkpABvXCJbZR03rf+OIwY3tV3C3NIeTN3gkwCaCFhnec/g2GY5SAI5d/iY 1vZOaP4+rgKRbiIN8AB56YD1SbdP1K4nrLsBW1avOaytUDXVVfve60QYbnN6xobyCNDh pzKrz0Age9ZVd8WIMrWv1fhkLDq4tDA4slP04hBbB5EhX4ahKyRQln3Jf6oVZ9q7Ep2y hzfMmOPPe6qYs6JlfwYfvyKTWGpz9lW7enTkFUKLCKAGbBFy23+fDCNhHYlG4tAB/wox n69Q== X-Gm-Message-State: AOAM533uHflOs3SkpyKplM8k1jGn7wwKqEPN2mE880Wuzs33tosHLCCI 7IuwPSltKCbkhrednHQDF+RniH/Eq1c= X-Google-Smtp-Source: ABdhPJz8gPzOw/Nwv9WuHVXNJHIvT9HbNHiCjMybUfwnKcGqS3vHqS8ZYOd8sZzoLU3K+xl7zUgYoA== X-Received: by 2002:a1c:a7c2:: with SMTP id q185mr6186956wme.91.1629508156517; Fri, 20 Aug 2021 18:09:16 -0700 (PDT) Received: from debian64.daheim (pd9e297bb.dip0.t-ipconnect.de. [217.226.151.187]) by smtp.gmail.com with ESMTPSA id o6sm7498992wru.92.2021.08.20.18.09.15 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Fri, 20 Aug 2021 18:09:15 -0700 (PDT) Received: from chuck by debian64.daheim with local (Exim 4.94.2) (envelope-from ) id 1mHFVb-0046Wv-7e; Sat, 21 Aug 2021 03:09:15 +0200 From: Christian Lamparter To: linux-wireless@vger.kernel.org, devicetree@vger.kernel.org, ath9k-devel@qca.qualcomm.com Subject: [RFC PATCH v1 1/3] dt-bindings:net:wireless:qca,ath9k: add nvmem-cells for calibration data Date: Sat, 21 Aug 2021 03:09:13 +0200 Message-Id: <91e68ca7f65bee7197ed5829ef91bc526df16e8a.1629508039.git.chunkeey@gmail.com> X-Mailer: git-send-email 2.33.0 MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: linux-wireless@vger.kernel.org On most embedded ath9k devices (like range extenders, routers, accesspoints, ...) the calibration data for the RF/PHY is simply stored in a MTD partition named "ART", "caldata"/"calibration", etc. Any mtd partition is automatically registered in the nvmem subsystem. This makes is possible to fetch the necessary calibration directly from there at the low cost of adding nvmem cell information via the device-tree or via similar means. This speeds up the driver's initialization a lot, because the driver doesn't have to wait for userspace to provide the data via helpers. Signed-off-by: Christian Lamparter Acked-by: Rob Herring --- .../devicetree/bindings/net/wireless/qca,ath9k.txt | 10 ++++++++++ 1 file changed, 10 insertions(+) diff --git a/Documentation/devicetree/bindings/net/wireless/qca,ath9k.txt b/Documentation/devicetree/bindings/net/wireless/qca,ath9k.txt index aaaeeb5f935b..88b322b55dd8 100644 --- a/Documentation/devicetree/bindings/net/wireless/qca,ath9k.txt +++ b/Documentation/devicetree/bindings/net/wireless/qca,ath9k.txt @@ -34,6 +34,13 @@ Optional properties: ath9k wireless chip (in this case the calibration / EEPROM data will be loaded from userspace using the kernel firmware loader). +- nvmem-cells: A phandle pointing to a nvmem-cells node representing registers + that has information about the MAC-Address or + calibration data. + Please refer the for nvmem-cells bindings + Documentation/devicetree/bindings/nvmem/nvmem.yaml. +- nvmem-cell-names: Should be "address" for the MAC address. "calibration" + for ART/caldata. The MAC address will be determined using the optional properties defined in net/ethernet.txt. @@ -44,5 +51,8 @@ In this example, the node is defined as child node of the PCI controller: compatible = "pci168c,002d"; reg = <0x7000 0 0 0 0x1000>; qca,no-eeprom; + + nvmem-cells = <&macaddr_art_c>, <&cal_art_1000>; + nvmem-cell-names = "mac-address", "calibration"; }; }; From patchwork Sat Aug 21 01:09:14 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Christian Lamparter X-Patchwork-Id: 12450751 X-Patchwork-Delegate: kvalo@adurom.com Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-15.8 required=3.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID,DKIM_VALID_AU,FREEMAIL_FORGED_FROMDOMAIN,FREEMAIL_FROM, HEADER_FROM_DIFFERENT_DOMAINS,INCLUDES_CR_TRAILER,INCLUDES_PATCH, MAILING_LIST_MULTI,SPF_HELO_NONE,SPF_PASS,USER_AGENT_GIT autolearn=unavailable autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id AAD84C432BE for ; Sat, 21 Aug 2021 01:09:20 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 821F5611C3 for ; Sat, 21 Aug 2021 01:09:20 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S240854AbhHUBJ5 (ORCPT ); Fri, 20 Aug 2021 21:09:57 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:40270 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S232300AbhHUBJ5 (ORCPT ); Fri, 20 Aug 2021 21:09:57 -0400 Received: from mail-wr1-x42a.google.com (mail-wr1-x42a.google.com [IPv6:2a00:1450:4864:20::42a]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 38AF8C061757; Fri, 20 Aug 2021 18:09:18 -0700 (PDT) Received: by mail-wr1-x42a.google.com with SMTP id q10so16608150wro.2; Fri, 20 Aug 2021 18:09:18 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:subject:date:message-id:in-reply-to:references:mime-version :content-transfer-encoding; bh=1t5xO/vCozsm6qTyQvSV3wCxmTDXYEFQ4QrCefdVVb4=; b=UT79z/7za2bFRV8JcSGpblgfIvtPTQMS1q3EcoDR1u2ZQTDYOGrAjat2+VIN6znABT s744DbjKzO2BFYWRvtU1hBi9/RE7CcObV0q/Y74tL1OZZeioRYmOUtJuuUdqpXv3SDYR ZOBDbI4pvDT9Jn4ZbtBlDjMt1lU/eKypZiTtsj5hgIKju66O2gkmLheuTAF/6xk+tjfu MprGGFBS2C+7QofsQZokmaZuW0kUdml4CwB69han9uYDksPVB9pM9VTYRhV4oqdrw+i+ 3i7hrpijG+CVMcKsOv6EV2gdwTCGR9FUo1jb04iOs8DQRYg1Sw6xULqVBCKSaKNt7IM6 wViQ== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=1t5xO/vCozsm6qTyQvSV3wCxmTDXYEFQ4QrCefdVVb4=; b=K1gXY2E4HEfotPRydhMKRNbTEAZNCYh6M+cs2aSQDpFWWk4vgzIvr+XNnnE8+JvuTl +kgcuxcBTGnyR16HSkqeta/UJucrUBtThB9V/nSkns5DQwhGrUM0ZbyMhZQ7lnTqJoRc jdFUQJDJTCD+oglCacSaHTzdqSKQc5C/c6+NveXyGGg6ezEzV/XNcCvnvfiexrCUFUZG MMwb7QR3q2D5tSdoEhVx/FlfyVs26oLh83vPXogbud1d0uL5yfv2VFgtQFhnOoBlG78n xprT/hJaH0kjC6Hl5Me3msNb22LHplI8q308P0rzLEelSo/cdShSj+ldhX7X5l0Uen7R /YUQ== X-Gm-Message-State: AOAM531pkPjZxCrkmsKy9AYDTnFhjQx3wgWa8OjaxV0/FomWCPmXBMZO olGGh3uucPaeU6wa+RtMu4sOPdmuuFk= X-Google-Smtp-Source: ABdhPJw4z3kdnmiOMiQAsevSygP5qrdnYZiLRh8mcomr0VNIxHLrdtIUfpXub60Px7D+b7E3fbJbLA== X-Received: by 2002:adf:f707:: with SMTP id r7mr1368438wrp.175.1629508156661; Fri, 20 Aug 2021 18:09:16 -0700 (PDT) Received: from debian64.daheim (pd9e297bb.dip0.t-ipconnect.de. [217.226.151.187]) by smtp.gmail.com with ESMTPSA id u16sm7441259wmc.41.2021.08.20.18.09.15 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Fri, 20 Aug 2021 18:09:16 -0700 (PDT) Received: from chuck by debian64.daheim with local (Exim 4.94.2) (envelope-from ) id 1mHFVb-0046Wx-8U; Sat, 21 Aug 2021 03:09:15 +0200 From: Christian Lamparter To: linux-wireless@vger.kernel.org, devicetree@vger.kernel.org, ath9k-devel@qca.qualcomm.com Subject: [RFC PATCH v1 2/3] ath9k: fetch calibration data via nvmem subsystem Date: Sat, 21 Aug 2021 03:09:14 +0200 Message-Id: X-Mailer: git-send-email 2.33.0 In-Reply-To: <91e68ca7f65bee7197ed5829ef91bc526df16e8a.1629508039.git.chunkeey@gmail.com> References: <91e68ca7f65bee7197ed5829ef91bc526df16e8a.1629508039.git.chunkeey@gmail.com> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: linux-wireless@vger.kernel.org On most embedded ath9k devices (like range extenders, routers, accesspoints, ...) the calibration data is stored in a MTD partitions named "ART", or "caldata"/ "calibration". Since commit 4b361cfa8624 ("mtd: core: add OTP nvmem provider support"): All MTD partitions are all automatically available through the nvmem subsystem. This feature - together with an nvmem cell definition in the device-tree - allows drivers like ath9k to get the data necessary for starting the WIFI, without having to wait around for the filesystem and userspace to do the extractions. Signed-off-by: Christian Lamparter --- drivers/net/wireless/ath/ath9k/eeprom.c | 12 +++++- drivers/net/wireless/ath/ath9k/hw.h | 2 + drivers/net/wireless/ath/ath9k/init.c | 56 +++++++++++++++++++++++++ 3 files changed, 69 insertions(+), 1 deletion(-) diff --git a/drivers/net/wireless/ath/ath9k/eeprom.c b/drivers/net/wireless/ath/ath9k/eeprom.c index c22d457dbc54..e6b3cd49ea18 100644 --- a/drivers/net/wireless/ath/ath9k/eeprom.c +++ b/drivers/net/wireless/ath/ath9k/eeprom.c @@ -135,13 +135,23 @@ static bool ath9k_hw_nvram_read_firmware(const struct firmware *eeprom_blob, offset, data); } +static bool ath9k_hw_nvram_read_nvmem(struct ath_hw *ah, off_t offset, + u16 *data) +{ + return ath9k_hw_nvram_read_array(ah->nvmem_blob, + ah->nvmem_blob_len / sizeof(u16), + offset, data); +} + bool ath9k_hw_nvram_read(struct ath_hw *ah, u32 off, u16 *data) { struct ath_common *common = ath9k_hw_common(ah); struct ath9k_platform_data *pdata = ah->dev->platform_data; bool ret; - if (ah->eeprom_blob) + if (ah->nvmem_blob) + ret = ath9k_hw_nvram_read_nvmem(ah, off, data); + else if (ah->eeprom_blob) ret = ath9k_hw_nvram_read_firmware(ah->eeprom_blob, off, data); else if (pdata && !pdata->use_eeprom) ret = ath9k_hw_nvram_read_pdata(pdata, off, data); diff --git a/drivers/net/wireless/ath/ath9k/hw.h b/drivers/net/wireless/ath/ath9k/hw.h index b7b65b1c90e8..096a206f49ed 100644 --- a/drivers/net/wireless/ath/ath9k/hw.h +++ b/drivers/net/wireless/ath/ath9k/hw.h @@ -977,6 +977,8 @@ struct ath_hw { bool disable_5ghz; const struct firmware *eeprom_blob; + u16 *nvmem_blob; /* devres managed */ + size_t nvmem_blob_len; struct ath_dynack dynack; diff --git a/drivers/net/wireless/ath/ath9k/init.c b/drivers/net/wireless/ath/ath9k/init.c index e9a36dd7144f..1568730fc01e 100644 --- a/drivers/net/wireless/ath/ath9k/init.c +++ b/drivers/net/wireless/ath/ath9k/init.c @@ -22,6 +22,7 @@ #include #include #include +#include #include #include #include @@ -568,6 +569,57 @@ static void ath9k_eeprom_release(struct ath_softc *sc) release_firmware(sc->sc_ah->eeprom_blob); } +static int ath9k_nvmem_request_eeprom(struct ath_softc *sc) +{ + struct ath_hw *ah = sc->sc_ah; + struct nvmem_cell *cell; + void *buf; + size_t len; + int err; + + cell = devm_nvmem_cell_get(sc->dev, "calibration"); + if (IS_ERR(cell)) { + err = PTR_ERR(cell); + + /* nvmem cell might not be defined, or the nvmem + * subsystem isn't included. In this case, follow + * the established "just return 0;" convention of + * ath9k_init_platform to say: + * "All good. Nothing to see here. Please go on." + */ + if (err == -ENOENT || err == -EOPNOTSUPP) + return 0; + + return err; + } + + buf = nvmem_cell_read(cell, &len); + if (IS_ERR(buf)) + return PTR_ERR(buf); + + /* run basic sanity checks on the returned nvram cell length. + * That length has to be a multiple of a "u16" (i.e.: & 1). + * Furthermore, it has to be more than "let's say" 512 bytes + * but less than the maximum of AR9300_EEPROM_SIZE (16kb). + */ + if ((len & 1) == 1 || len < 512 || len >= AR9300_EEPROM_SIZE) { + kfree(buf); + return -EINVAL; + } + + /* devres manages the calibration values release on shutdown */ + ah->nvmem_blob = (u16 *)devm_kmemdup(sc->dev, buf, len, GFP_KERNEL); + kfree(buf); + if (IS_ERR(ah->nvmem_blob)) + return PTR_ERR(ah->nvmem_blob); + + ah->nvmem_blob_len = len; + ah->ah_flags &= ~AH_USE_EEPROM; + ah->ah_flags |= AH_NO_EEP_SWAP; + + return 0; +} + static int ath9k_init_platform(struct ath_softc *sc) { struct ath9k_platform_data *pdata = sc->dev->platform_data; @@ -704,6 +756,10 @@ static int ath9k_init_softc(u16 devid, struct ath_softc *sc, if (ret) return ret; + ret = ath9k_nvmem_request_eeprom(sc); + if (ret) + return ret; + if (ath9k_led_active_high != -1) ah->config.led_active_high = ath9k_led_active_high == 1; From patchwork Sat Aug 21 01:09:15 2021 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Christian Lamparter X-Patchwork-Id: 12450755 X-Patchwork-Delegate: kvalo@adurom.com Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-15.8 required=3.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID,DKIM_VALID_AU,FREEMAIL_FORGED_FROMDOMAIN,FREEMAIL_FROM, HEADER_FROM_DIFFERENT_DOMAINS,INCLUDES_CR_TRAILER,INCLUDES_PATCH, MAILING_LIST_MULTI,SPF_HELO_NONE,SPF_PASS,USER_AGENT_GIT autolearn=unavailable autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id 805B7C4320A for ; Sat, 21 Aug 2021 01:09:23 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id 58590611C4 for ; Sat, 21 Aug 2021 01:09:23 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S240927AbhHUBJ6 (ORCPT ); Fri, 20 Aug 2021 21:09:58 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:40266 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S229783AbhHUBJ5 (ORCPT ); Fri, 20 Aug 2021 21:09:57 -0400 Received: from mail-wr1-x42a.google.com (mail-wr1-x42a.google.com [IPv6:2a00:1450:4864:20::42a]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 2BD4BC061575; Fri, 20 Aug 2021 18:09:18 -0700 (PDT) Received: by mail-wr1-x42a.google.com with SMTP id u16so16580841wrn.5; Fri, 20 Aug 2021 18:09:18 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=from:to:subject:date:message-id:in-reply-to:references:mime-version :content-transfer-encoding; bh=/oZ+KBthaGg5R0Lga8JYmghLqYOInCSyoGhUWJuf5Fg=; b=up9NvqsaE1X2uNtv+tk/1rrTTQbblNZNzEcLUB/WChGmUnCXK84hnflgjqpxQYSvqa W3t+8i0SMMwOXyQ0oQjZx2vK4BBCswkRNp3qWl/T0KSg3pJzZ5SwtjKBsVae0Cpa5aMq gOYroB91h7ce52yYY73Llpl1mhdNO+HbsOmgjdjTdyMDUq2iTm/ZEHA+AC4pR5H3jK7z kXigEL3kWzcxZNjK0i/7t1SdgmUjA9tDV3/mfkxgQrGL4IFScDR9nX233/A1p38kV9+l iiupy6Bt4ePOGv5HcFY5YJOQxaUjhZ2CoGRxSoQMcqnTmw2pk/twPUBhsMZIfFQ0JSI+ 8EQQ== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=/oZ+KBthaGg5R0Lga8JYmghLqYOInCSyoGhUWJuf5Fg=; b=ZON41UBmch/HXDXswhZT7MyCgj7BgGTH+EApIneGb8NrVZRcksKd/ygHDZWksRMg5i CDcEvKVmTY3DrWWrBAzmwLaQoKKKk1X9k36CvkCyw1Bm82IwZXZsQDIuvO+z6PeHL4NC Vi8ALbZCHJAwhkyE/d+DSzzsk7cjLWprHvBMOuMvvjKb9nfOGsuhKx6urBD6fhwEvv8d HUBl0HG3u6X6ZCa4wLXob8yk93dvFpo3+l0PSfitko63QuBcQx5vE9HBnHLsSzzm9x7z j8e1laN20e3Ue2JBqBmCjkTqR3Eui23EoqO55CJwRd7tb/bvB8FqMrywETus9haGx6T6 UtZQ== X-Gm-Message-State: AOAM530sjKRZmxNtnaglhellFKhRxlrqZyUKGTPxFipoEkLSngL9BgVK J+QzEx+RSC2dUGqz346z1hoWon/niAI= X-Google-Smtp-Source: ABdhPJwpdjjbaIAnSrbGQoygE55Z+vBB6F0UybfUhi+lUEQsOdkvJMCBE+2qRupVS6Q4O+aRf9SLJA== X-Received: by 2002:adf:c006:: with SMTP id z6mr1442666wre.157.1629508156374; Fri, 20 Aug 2021 18:09:16 -0700 (PDT) Received: from debian64.daheim (pd9e297bb.dip0.t-ipconnect.de. [217.226.151.187]) by smtp.gmail.com with ESMTPSA id u5sm7349201wrr.94.2021.08.20.18.09.15 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Fri, 20 Aug 2021 18:09:15 -0700 (PDT) Received: from chuck by debian64.daheim with local (Exim 4.94.2) (envelope-from ) id 1mHFVb-0046Wz-9A; Sat, 21 Aug 2021 03:09:15 +0200 From: Christian Lamparter To: linux-wireless@vger.kernel.org, devicetree@vger.kernel.org, ath9k-devel@qca.qualcomm.com Subject: [RFC PATCH v1 3/3] ath9k: owl-loader: fetch pci init values through nvmem Date: Sat, 21 Aug 2021 03:09:15 +0200 Message-Id: X-Mailer: git-send-email 2.33.0 In-Reply-To: <91e68ca7f65bee7197ed5829ef91bc526df16e8a.1629508039.git.chunkeey@gmail.com> References: <91e68ca7f65bee7197ed5829ef91bc526df16e8a.1629508039.git.chunkeey@gmail.com> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: linux-wireless@vger.kernel.org extends the owl loader to fetch important pci initialization values - which are stored together with the calibration data - through the nvmem subsystem. This allows for much faster WIFI/ath9k initializations on devices that do not require to perform any post-processing (like XOR'ing/ reversal or unpacking) since no userspace helper is required. Signed-off-by: Christian Lamparter --- .../wireless/ath/ath9k/ath9k_pci_owl_loader.c | 105 +++++++++++++----- 1 file changed, 76 insertions(+), 29 deletions(-) diff --git a/drivers/net/wireless/ath/ath9k/ath9k_pci_owl_loader.c b/drivers/net/wireless/ath/ath9k/ath9k_pci_owl_loader.c index 56d1a7764b9f..708c8969b503 100644 --- a/drivers/net/wireless/ath/ath9k/ath9k_pci_owl_loader.c +++ b/drivers/net/wireless/ath/ath9k/ath9k_pci_owl_loader.c @@ -19,9 +19,14 @@ #include #include #include +#include +#include struct owl_ctx { + struct pci_dev *pdev; struct completion eeprom_load; + struct work_struct work; + struct nvmem_cell *cell; }; #define EEPROM_FILENAME_LEN 100 @@ -42,6 +47,12 @@ static int ath9k_pci_fixup(struct pci_dev *pdev, const u16 *cal_data, u32 bar0; bool swap_needed = false; + /* also note that we are doing *u16 operations on the file */ + if (cal_len > 4096 || cal_len < 0x200 || (cal_len & 1) == 1) { + dev_err(&pdev->dev, "eeprom has an invalid size.\n"); + return -EINVAL; + } + if (*cal_data != AR5416_EEPROM_MAGIC) { if (*cal_data != swab16(AR5416_EEPROM_MAGIC)) { dev_err(&pdev->dev, "invalid calibration data\n"); @@ -99,38 +110,31 @@ static int ath9k_pci_fixup(struct pci_dev *pdev, const u16 *cal_data, return 0; } -static void owl_fw_cb(const struct firmware *fw, void *context) +static void owl_rescan(struct pci_dev *pdev) { - struct pci_dev *pdev = (struct pci_dev *)context; - struct owl_ctx *ctx = (struct owl_ctx *)pci_get_drvdata(pdev); - struct pci_bus *bus; - - complete(&ctx->eeprom_load); - - if (!fw) { - dev_err(&pdev->dev, "no eeprom data received.\n"); - goto release; - } - - /* also note that we are doing *u16 operations on the file */ - if (fw->size > 4096 || fw->size < 0x200 || (fw->size & 1) == 1) { - dev_err(&pdev->dev, "eeprom file has an invalid size.\n"); - goto release; - } - - if (ath9k_pci_fixup(pdev, (const u16 *)fw->data, fw->size)) - goto release; + struct pci_bus *bus = pdev->bus; pci_lock_rescan_remove(); - bus = pdev->bus; pci_stop_and_remove_bus_device(pdev); /* the device should come back with the proper * ProductId. But we have to initiate a rescan. */ pci_rescan_bus(bus); pci_unlock_rescan_remove(); +} + +static void owl_fw_cb(const struct firmware *fw, void *context) +{ + struct owl_ctx *ctx = (struct owl_ctx *)context; + + complete(&ctx->eeprom_load); -release: + if (fw) { + ath9k_pci_fixup(ctx->pdev, (const u16 *)fw->data, fw->size); + owl_rescan(ctx->pdev); + } else { + dev_err(&ctx->pdev->dev, "no eeprom data received.\n"); + } release_firmware(fw); } @@ -152,6 +156,43 @@ static const char *owl_get_eeprom_name(struct pci_dev *pdev) return eeprom_name; } +static void owl_nvmem_work(struct work_struct *work) +{ + struct owl_ctx *ctx = container_of(work, struct owl_ctx, work); + void *buf; + size_t len; + + complete(&ctx->eeprom_load); + + buf = nvmem_cell_read(ctx->cell, &len); + if (!IS_ERR(buf)) { + ath9k_pci_fixup(ctx->pdev, buf, len); + kfree(buf); + owl_rescan(ctx->pdev); + } else { + dev_err(&ctx->pdev->dev, "no nvmem data received.\n"); + } +} + +static int owl_nvmem_probe(struct owl_ctx *ctx) +{ + int err; + + ctx->cell = devm_nvmem_cell_get(&ctx->pdev->dev, "calibration"); + if (IS_ERR(ctx->cell)) { + err = PTR_ERR(ctx->cell); + if (err == -ENOENT || err == -EOPNOTSUPP) + return 1; /* not present, try firmware_request */ + + return err; + } + + INIT_WORK(&ctx->work, owl_nvmem_work); + schedule_work(&ctx->work); + + return 0; +} + static int owl_probe(struct pci_dev *pdev, const struct pci_device_id *id) { @@ -164,21 +205,27 @@ static int owl_probe(struct pci_dev *pdev, pcim_pin_device(pdev); - eeprom_name = owl_get_eeprom_name(pdev); - if (!eeprom_name) { - dev_err(&pdev->dev, "no eeprom filename found.\n"); - return -ENODEV; - } - ctx = devm_kzalloc(&pdev->dev, sizeof(*ctx), GFP_KERNEL); if (!ctx) return -ENOMEM; init_completion(&ctx->eeprom_load); + ctx->pdev = pdev; pci_set_drvdata(pdev, ctx); + + err = owl_nvmem_probe(ctx); + if (err <= 0) + return err; + + eeprom_name = owl_get_eeprom_name(pdev); + if (!eeprom_name) { + dev_err(&pdev->dev, "no eeprom filename found.\n"); + return -ENODEV; + } + err = request_firmware_nowait(THIS_MODULE, true, eeprom_name, - &pdev->dev, GFP_KERNEL, pdev, owl_fw_cb); + &pdev->dev, GFP_KERNEL, ctx, owl_fw_cb); if (err) dev_err(&pdev->dev, "failed to request caldata (%d).\n", err);