Signed-off-by: Rafał Miłecki <rafal@milecki.pl>master
parent
c29a2a4283
commit
e52e8480ad
@ -0,0 +1,434 @@ |
||||
From fdd0bd88ceaecf729db103ac8836af5805dd2dc1 Mon Sep 17 00:00:00 2001
|
||||
From: Chung-Hsien Hsu <stanley.hsu@cypress.com>
|
||||
Date: Fri, 10 Nov 2017 17:27:15 +0800
|
||||
Subject: [PATCH] brcmfmac: add CLM download support
|
||||
|
||||
The firmware for brcmfmac devices includes information regarding
|
||||
regulatory constraints. For certain devices this information is kept
|
||||
separately in a binary form that needs to be downloaded to the device.
|
||||
This patch adds support to download this so-called CLM blob file. It
|
||||
uses the same naming scheme as the other firmware files with extension
|
||||
of .clm_blob.
|
||||
|
||||
The CLM blob file is optional. If the file does not exist, the download
|
||||
process will be bypassed. It will not affect the driver loading.
|
||||
|
||||
Reviewed-by: Arend van Spriel <arend.vanspriel@broadcom.com>
|
||||
Signed-off-by: Chung-Hsien Hsu <stanley.hsu@cypress.com>
|
||||
Signed-off-by: Kalle Valo <kvalo@codeaurora.org>
|
||||
---
|
||||
.../net/wireless/broadcom/brcm80211/brcmfmac/bus.h | 10 ++
|
||||
.../wireless/broadcom/brcm80211/brcmfmac/common.c | 157 +++++++++++++++++++++
|
||||
.../wireless/broadcom/brcm80211/brcmfmac/core.c | 2 +
|
||||
.../wireless/broadcom/brcm80211/brcmfmac/core.h | 2 +
|
||||
.../broadcom/brcm80211/brcmfmac/fwil_types.h | 31 ++++
|
||||
.../wireless/broadcom/brcm80211/brcmfmac/pcie.c | 19 +++
|
||||
.../wireless/broadcom/brcm80211/brcmfmac/sdio.c | 19 +++
|
||||
.../net/wireless/broadcom/brcm80211/brcmfmac/usb.c | 18 +++
|
||||
8 files changed, 258 insertions(+)
|
||||
|
||||
--- a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/bus.h
|
||||
+++ b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/bus.h
|
||||
@@ -71,6 +71,7 @@ struct brcmf_bus_dcmd {
|
||||
* @wowl_config: specify if dongle is configured for wowl when going to suspend
|
||||
* @get_ramsize: obtain size of device memory.
|
||||
* @get_memdump: obtain device memory dump in provided buffer.
|
||||
+ * @get_fwname: obtain firmware name.
|
||||
*
|
||||
* This structure provides an abstract interface towards the
|
||||
* bus specific driver. For control messages to common driver
|
||||
@@ -87,6 +88,8 @@ struct brcmf_bus_ops {
|
||||
void (*wowl_config)(struct device *dev, bool enabled);
|
||||
size_t (*get_ramsize)(struct device *dev);
|
||||
int (*get_memdump)(struct device *dev, void *data, size_t len);
|
||||
+ int (*get_fwname)(struct device *dev, uint chip, uint chiprev,
|
||||
+ unsigned char *fw_name);
|
||||
};
|
||||
|
||||
|
||||
@@ -224,6 +227,13 @@ int brcmf_bus_get_memdump(struct brcmf_b
|
||||
return bus->ops->get_memdump(bus->dev, data, len);
|
||||
}
|
||||
|
||||
+static inline
|
||||
+int brcmf_bus_get_fwname(struct brcmf_bus *bus, uint chip, uint chiprev,
|
||||
+ unsigned char *fw_name)
|
||||
+{
|
||||
+ return bus->ops->get_fwname(bus->dev, chip, chiprev, fw_name);
|
||||
+}
|
||||
+
|
||||
/*
|
||||
* interface functions from common layer
|
||||
*/
|
||||
--- a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/common.c
|
||||
+++ b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/common.c
|
||||
@@ -18,6 +18,7 @@
|
||||
#include <linux/string.h>
|
||||
#include <linux/netdevice.h>
|
||||
#include <linux/module.h>
|
||||
+#include <linux/firmware.h>
|
||||
#include <brcmu_wifi.h>
|
||||
#include <brcmu_utils.h>
|
||||
#include "core.h"
|
||||
@@ -28,6 +29,7 @@
|
||||
#include "tracepoint.h"
|
||||
#include "common.h"
|
||||
#include "of.h"
|
||||
+#include "firmware.h"
|
||||
|
||||
MODULE_AUTHOR("Broadcom Corporation");
|
||||
MODULE_DESCRIPTION("Broadcom 802.11 wireless LAN fullmac driver.");
|
||||
@@ -104,12 +106,140 @@ void brcmf_c_set_joinpref_default(struct
|
||||
brcmf_err("Set join_pref error (%d)\n", err);
|
||||
}
|
||||
|
||||
+static int brcmf_c_download(struct brcmf_if *ifp, u16 flag,
|
||||
+ struct brcmf_dload_data_le *dload_buf,
|
||||
+ u32 len)
|
||||
+{
|
||||
+ s32 err;
|
||||
+
|
||||
+ flag |= (DLOAD_HANDLER_VER << DLOAD_FLAG_VER_SHIFT);
|
||||
+ dload_buf->flag = cpu_to_le16(flag);
|
||||
+ dload_buf->dload_type = cpu_to_le16(DL_TYPE_CLM);
|
||||
+ dload_buf->len = cpu_to_le32(len);
|
||||
+ dload_buf->crc = cpu_to_le32(0);
|
||||
+ len = sizeof(*dload_buf) + len - 1;
|
||||
+
|
||||
+ err = brcmf_fil_iovar_data_set(ifp, "clmload", dload_buf, len);
|
||||
+
|
||||
+ return err;
|
||||
+}
|
||||
+
|
||||
+static int brcmf_c_get_clm_name(struct brcmf_if *ifp, u8 *clm_name)
|
||||
+{
|
||||
+ struct brcmf_bus *bus = ifp->drvr->bus_if;
|
||||
+ struct brcmf_rev_info *ri = &ifp->drvr->revinfo;
|
||||
+ u8 fw_name[BRCMF_FW_NAME_LEN];
|
||||
+ u8 *ptr;
|
||||
+ size_t len;
|
||||
+ s32 err;
|
||||
+
|
||||
+ memset(fw_name, 0, BRCMF_FW_NAME_LEN);
|
||||
+ err = brcmf_bus_get_fwname(bus, ri->chipnum, ri->chiprev, fw_name);
|
||||
+ if (err) {
|
||||
+ brcmf_err("get firmware name failed (%d)\n", err);
|
||||
+ goto done;
|
||||
+ }
|
||||
+
|
||||
+ /* generate CLM blob file name */
|
||||
+ ptr = strrchr(fw_name, '.');
|
||||
+ if (!ptr) {
|
||||
+ err = -ENOENT;
|
||||
+ goto done;
|
||||
+ }
|
||||
+
|
||||
+ len = ptr - fw_name + 1;
|
||||
+ if (len + strlen(".clm_blob") > BRCMF_FW_NAME_LEN) {
|
||||
+ err = -E2BIG;
|
||||
+ } else {
|
||||
+ strlcpy(clm_name, fw_name, len);
|
||||
+ strlcat(clm_name, ".clm_blob", BRCMF_FW_NAME_LEN);
|
||||
+ }
|
||||
+done:
|
||||
+ return err;
|
||||
+}
|
||||
+
|
||||
+static int brcmf_c_process_clm_blob(struct brcmf_if *ifp)
|
||||
+{
|
||||
+ struct device *dev = ifp->drvr->bus_if->dev;
|
||||
+ struct brcmf_dload_data_le *chunk_buf;
|
||||
+ const struct firmware *clm = NULL;
|
||||
+ u8 clm_name[BRCMF_FW_NAME_LEN];
|
||||
+ u32 chunk_len;
|
||||
+ u32 datalen;
|
||||
+ u32 cumulative_len;
|
||||
+ u16 dl_flag = DL_BEGIN;
|
||||
+ u32 status;
|
||||
+ s32 err;
|
||||
+
|
||||
+ brcmf_dbg(TRACE, "Enter\n");
|
||||
+
|
||||
+ memset(clm_name, 0, BRCMF_FW_NAME_LEN);
|
||||
+ err = brcmf_c_get_clm_name(ifp, clm_name);
|
||||
+ if (err) {
|
||||
+ brcmf_err("get CLM blob file name failed (%d)\n", err);
|
||||
+ return err;
|
||||
+ }
|
||||
+
|
||||
+ err = request_firmware(&clm, clm_name, dev);
|
||||
+ if (err) {
|
||||
+ if (err == -ENOENT) {
|
||||
+ brcmf_dbg(INFO, "continue with CLM data currently present in firmware\n");
|
||||
+ return 0;
|
||||
+ }
|
||||
+ brcmf_err("request CLM blob file failed (%d)\n", err);
|
||||
+ return err;
|
||||
+ }
|
||||
+
|
||||
+ chunk_buf = kzalloc(sizeof(*chunk_buf) + MAX_CHUNK_LEN - 1, GFP_KERNEL);
|
||||
+ if (!chunk_buf) {
|
||||
+ err = -ENOMEM;
|
||||
+ goto done;
|
||||
+ }
|
||||
+
|
||||
+ datalen = clm->size;
|
||||
+ cumulative_len = 0;
|
||||
+ do {
|
||||
+ if (datalen > MAX_CHUNK_LEN) {
|
||||
+ chunk_len = MAX_CHUNK_LEN;
|
||||
+ } else {
|
||||
+ chunk_len = datalen;
|
||||
+ dl_flag |= DL_END;
|
||||
+ }
|
||||
+ memcpy(chunk_buf->data, clm->data + cumulative_len, chunk_len);
|
||||
+
|
||||
+ err = brcmf_c_download(ifp, dl_flag, chunk_buf, chunk_len);
|
||||
+
|
||||
+ dl_flag &= ~DL_BEGIN;
|
||||
+
|
||||
+ cumulative_len += chunk_len;
|
||||
+ datalen -= chunk_len;
|
||||
+ } while ((datalen > 0) && (err == 0));
|
||||
+
|
||||
+ if (err) {
|
||||
+ brcmf_err("clmload (%zu byte file) failed (%d); ",
|
||||
+ clm->size, err);
|
||||
+ /* Retrieve clmload_status and print */
|
||||
+ err = brcmf_fil_iovar_int_get(ifp, "clmload_status", &status);
|
||||
+ if (err)
|
||||
+ brcmf_err("get clmload_status failed (%d)\n", err);
|
||||
+ else
|
||||
+ brcmf_dbg(INFO, "clmload_status=%d\n", status);
|
||||
+ err = -EIO;
|
||||
+ }
|
||||
+
|
||||
+ kfree(chunk_buf);
|
||||
+done:
|
||||
+ release_firmware(clm);
|
||||
+ return err;
|
||||
+}
|
||||
+
|
||||
int brcmf_c_preinit_dcmds(struct brcmf_if *ifp)
|
||||
{
|
||||
s8 eventmask[BRCMF_EVENTING_MASK_LEN];
|
||||
u8 buf[BRCMF_DCMD_SMLEN];
|
||||
struct brcmf_rev_info_le revinfo;
|
||||
struct brcmf_rev_info *ri;
|
||||
+ char *clmver;
|
||||
char *ptr;
|
||||
s32 err;
|
||||
|
||||
@@ -148,6 +278,13 @@ int brcmf_c_preinit_dcmds(struct brcmf_i
|
||||
}
|
||||
ri->result = err;
|
||||
|
||||
+ /* Do any CLM downloading */
|
||||
+ err = brcmf_c_process_clm_blob(ifp);
|
||||
+ if (err < 0) {
|
||||
+ brcmf_err("download CLM blob file failed, %d\n", err);
|
||||
+ goto done;
|
||||
+ }
|
||||
+
|
||||
/* query for 'ver' to get version info from firmware */
|
||||
memset(buf, 0, sizeof(buf));
|
||||
strcpy(buf, "ver");
|
||||
@@ -167,6 +304,26 @@ int brcmf_c_preinit_dcmds(struct brcmf_i
|
||||
ptr = strrchr(buf, ' ') + 1;
|
||||
strlcpy(ifp->drvr->fwver, ptr, sizeof(ifp->drvr->fwver));
|
||||
|
||||
+ /* Query for 'clmver' to get CLM version info from firmware */
|
||||
+ memset(buf, 0, sizeof(buf));
|
||||
+ err = brcmf_fil_iovar_data_get(ifp, "clmver", buf, sizeof(buf));
|
||||
+ if (err) {
|
||||
+ brcmf_dbg(TRACE, "retrieving clmver failed, %d\n", err);
|
||||
+ } else {
|
||||
+ clmver = (char *)buf;
|
||||
+ /* store CLM version for adding it to revinfo debugfs file */
|
||||
+ memcpy(ifp->drvr->clmver, clmver, sizeof(ifp->drvr->clmver));
|
||||
+
|
||||
+ /* Replace all newline/linefeed characters with space
|
||||
+ * character
|
||||
+ */
|
||||
+ ptr = clmver;
|
||||
+ while ((ptr = strnchr(ptr, '\n', sizeof(buf))) != NULL)
|
||||
+ *ptr = ' ';
|
||||
+
|
||||
+ brcmf_dbg(INFO, "CLM version = %s\n", clmver);
|
||||
+ }
|
||||
+
|
||||
/* set mpc */
|
||||
err = brcmf_fil_iovar_int_set(ifp, "mpc", 1);
|
||||
if (err) {
|
||||
--- a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/core.c
|
||||
+++ b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/core.c
|
||||
@@ -1009,6 +1009,8 @@ static int brcmf_revinfo_read(struct seq
|
||||
seq_printf(s, "anarev: %u\n", ri->anarev);
|
||||
seq_printf(s, "nvramrev: %08x\n", ri->nvramrev);
|
||||
|
||||
+ seq_printf(s, "clmver: %s\n", bus_if->drvr->clmver);
|
||||
+
|
||||
return 0;
|
||||
}
|
||||
|
||||
--- a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/core.h
|
||||
+++ b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/core.h
|
||||
@@ -141,6 +141,8 @@ struct brcmf_pub {
|
||||
struct notifier_block inetaddr_notifier;
|
||||
struct notifier_block inet6addr_notifier;
|
||||
struct brcmf_mp_device *settings;
|
||||
+
|
||||
+ u8 clmver[BRCMF_DCMD_SMLEN];
|
||||
};
|
||||
|
||||
/* forward declarations */
|
||||
--- a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/fwil_types.h
|
||||
+++ b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/fwil_types.h
|
||||
@@ -155,6 +155,21 @@
|
||||
#define BRCMF_MFP_CAPABLE 1
|
||||
#define BRCMF_MFP_REQUIRED 2
|
||||
|
||||
+/* MAX_CHUNK_LEN is the maximum length for data passing to firmware in each
|
||||
+ * ioctl. It is relatively small because firmware has small maximum size input
|
||||
+ * playload restriction for ioctls.
|
||||
+ */
|
||||
+#define MAX_CHUNK_LEN 1400
|
||||
+
|
||||
+#define DLOAD_HANDLER_VER 1 /* Downloader version */
|
||||
+#define DLOAD_FLAG_VER_MASK 0xf000 /* Downloader version mask */
|
||||
+#define DLOAD_FLAG_VER_SHIFT 12 /* Downloader version shift */
|
||||
+
|
||||
+#define DL_BEGIN 0x0002
|
||||
+#define DL_END 0x0004
|
||||
+
|
||||
+#define DL_TYPE_CLM 2
|
||||
+
|
||||
/* join preference types for join_pref iovar */
|
||||
enum brcmf_join_pref_types {
|
||||
BRCMF_JOIN_PREF_RSSI = 1,
|
||||
@@ -827,6 +842,22 @@ struct brcmf_pno_macaddr_le {
|
||||
};
|
||||
|
||||
/**
|
||||
+ * struct brcmf_dload_data_le - data passing to firmware for downloading
|
||||
+ * @flag: flags related to download data.
|
||||
+ * @dload_type: type of download data.
|
||||
+ * @len: length in bytes of download data.
|
||||
+ * @crc: crc of download data.
|
||||
+ * @data: download data.
|
||||
+ */
|
||||
+struct brcmf_dload_data_le {
|
||||
+ __le16 flag;
|
||||
+ __le16 dload_type;
|
||||
+ __le32 len;
|
||||
+ __le32 crc;
|
||||
+ u8 data[1];
|
||||
+};
|
||||
+
|
||||
+/**
|
||||
* struct brcmf_pno_bssid_le - bssid configuration for PNO scan.
|
||||
*
|
||||
* @bssid: BSS network identifier.
|
||||
--- a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/pcie.c
|
||||
+++ b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/pcie.c
|
||||
@@ -1350,6 +1350,24 @@ static int brcmf_pcie_get_memdump(struct
|
||||
return 0;
|
||||
}
|
||||
|
||||
+static int brcmf_pcie_get_fwname(struct device *dev, u32 chip, u32 chiprev,
|
||||
+ u8 *fw_name)
|
||||
+{
|
||||
+ struct brcmf_bus *bus_if = dev_get_drvdata(dev);
|
||||
+ struct brcmf_pciedev *buspub = bus_if->bus_priv.pcie;
|
||||
+ struct brcmf_pciedev_info *devinfo = buspub->devinfo;
|
||||
+ int ret = 0;
|
||||
+
|
||||
+ if (devinfo->fw_name[0] != '\0')
|
||||
+ strlcpy(fw_name, devinfo->fw_name, BRCMF_FW_NAME_LEN);
|
||||
+ else
|
||||
+ ret = brcmf_fw_map_chip_to_name(chip, chiprev,
|
||||
+ brcmf_pcie_fwnames,
|
||||
+ ARRAY_SIZE(brcmf_pcie_fwnames),
|
||||
+ fw_name, NULL);
|
||||
+
|
||||
+ return ret;
|
||||
+}
|
||||
|
||||
static const struct brcmf_bus_ops brcmf_pcie_bus_ops = {
|
||||
.txdata = brcmf_pcie_tx,
|
||||
@@ -1359,6 +1377,7 @@ static const struct brcmf_bus_ops brcmf_
|
||||
.wowl_config = brcmf_pcie_wowl_config,
|
||||
.get_ramsize = brcmf_pcie_get_ramsize,
|
||||
.get_memdump = brcmf_pcie_get_memdump,
|
||||
+ .get_fwname = brcmf_pcie_get_fwname,
|
||||
};
|
||||
|
||||
|
||||
--- a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/sdio.c
|
||||
+++ b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/sdio.c
|
||||
@@ -3985,6 +3985,24 @@ brcmf_sdio_watchdog(unsigned long data)
|
||||
}
|
||||
}
|
||||
|
||||
+static int brcmf_sdio_get_fwname(struct device *dev, u32 chip, u32 chiprev,
|
||||
+ u8 *fw_name)
|
||||
+{
|
||||
+ struct brcmf_bus *bus_if = dev_get_drvdata(dev);
|
||||
+ struct brcmf_sdio_dev *sdiodev = bus_if->bus_priv.sdio;
|
||||
+ int ret = 0;
|
||||
+
|
||||
+ if (sdiodev->fw_name[0] != '\0')
|
||||
+ strlcpy(fw_name, sdiodev->fw_name, BRCMF_FW_NAME_LEN);
|
||||
+ else
|
||||
+ ret = brcmf_fw_map_chip_to_name(chip, chiprev,
|
||||
+ brcmf_sdio_fwnames,
|
||||
+ ARRAY_SIZE(brcmf_sdio_fwnames),
|
||||
+ fw_name, NULL);
|
||||
+
|
||||
+ return ret;
|
||||
+}
|
||||
+
|
||||
static const struct brcmf_bus_ops brcmf_sdio_bus_ops = {
|
||||
.stop = brcmf_sdio_bus_stop,
|
||||
.preinit = brcmf_sdio_bus_preinit,
|
||||
@@ -3995,6 +4013,7 @@ static const struct brcmf_bus_ops brcmf_
|
||||
.wowl_config = brcmf_sdio_wowl_config,
|
||||
.get_ramsize = brcmf_sdio_bus_get_ramsize,
|
||||
.get_memdump = brcmf_sdio_bus_get_memdump,
|
||||
+ .get_fwname = brcmf_sdio_get_fwname,
|
||||
};
|
||||
|
||||
static void brcmf_sdio_firmware_callback(struct device *dev, int err,
|
||||
--- a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/usb.c
|
||||
+++ b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/usb.c
|
||||
@@ -1128,12 +1128,30 @@ static void brcmf_usb_wowl_config(struct
|
||||
device_set_wakeup_enable(devinfo->dev, false);
|
||||
}
|
||||
|
||||
+static int brcmf_usb_get_fwname(struct device *dev, u32 chip, u32 chiprev,
|
||||
+ u8 *fw_name)
|
||||
+{
|
||||
+ struct brcmf_usbdev_info *devinfo = brcmf_usb_get_businfo(dev);
|
||||
+ int ret = 0;
|
||||
+
|
||||
+ if (devinfo->fw_name[0] != '\0')
|
||||
+ strlcpy(fw_name, devinfo->fw_name, BRCMF_FW_NAME_LEN);
|
||||
+ else
|
||||
+ ret = brcmf_fw_map_chip_to_name(chip, chiprev,
|
||||
+ brcmf_usb_fwnames,
|
||||
+ ARRAY_SIZE(brcmf_usb_fwnames),
|
||||
+ fw_name, NULL);
|
||||
+
|
||||
+ return ret;
|
||||
+}
|
||||
+
|
||||
static const struct brcmf_bus_ops brcmf_usb_bus_ops = {
|
||||
.txdata = brcmf_usb_tx,
|
||||
.stop = brcmf_usb_down,
|
||||
.txctl = brcmf_usb_tx_ctlpkt,
|
||||
.rxctl = brcmf_usb_rx_ctlpkt,
|
||||
.wowl_config = brcmf_usb_wowl_config,
|
||||
+ .get_fwname = brcmf_usb_get_fwname,
|
||||
};
|
||||
|
||||
static int brcmf_usb_bus_setup(struct brcmf_usbdev_info *devinfo)
|
@ -0,0 +1,37 @@ |
||||
From 5c3de777bdaf48bd0cfb43097c0d0fb85056cab7 Mon Sep 17 00:00:00 2001
|
||||
From: Arend Van Spriel <arend.vanspriel@broadcom.com>
|
||||
Date: Sat, 25 Nov 2017 21:39:25 +0100
|
||||
Subject: [PATCH] brcmfmac: change driver unbind order of the sdio function
|
||||
devices
|
||||
|
||||
In the function brcmf_sdio_firmware_callback() the driver is
|
||||
unbound from the sdio function devices in the error path.
|
||||
However, the order in which it is done resulted in a use-after-free
|
||||
issue (see brcmf_ops_sdio_remove() in bcmsdh.c). Hence change
|
||||
the order and first unbind sdio function #2 device and then
|
||||
unbind sdio function #1 device.
|
||||
|
||||
Cc: stable@vger.kernel.org # v4.12.x
|
||||
Fixes: 7a51461fc2da ("brcmfmac: unbind all devices upon failure in firmware callback")
|
||||
Reported-by: Stefan Wahren <stefan.wahren@i2se.com>
|
||||
Reviewed-by: Hante Meuleman <hante.meuleman@broadcom.com>
|
||||
Reviewed-by: Pieter-Paul Giesberts <pieter-paul.giesberts@broadcom.com>
|
||||
Reviewed-by: Franky Lin <franky.lin@broadcom.com>
|
||||
Signed-off-by: Arend van Spriel <arend.vanspriel@broadcom.com>
|
||||
Signed-off-by: Kalle Valo <kvalo@codeaurora.org>
|
||||
---
|
||||
drivers/net/wireless/broadcom/brcm80211/brcmfmac/sdio.c | 2 +-
|
||||
1 file changed, 1 insertion(+), 1 deletion(-)
|
||||
|
||||
--- a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/sdio.c
|
||||
+++ b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/sdio.c
|
||||
@@ -4121,8 +4121,8 @@ release:
|
||||
sdio_release_host(sdiodev->func[1]);
|
||||
fail:
|
||||
brcmf_dbg(TRACE, "failed: dev=%s, err=%d\n", dev_name(dev), err);
|
||||
- device_release_driver(dev);
|
||||
device_release_driver(&sdiodev->func[2]->dev);
|
||||
+ device_release_driver(dev);
|
||||
}
|
||||
|
||||
struct brcmf_sdio *brcmf_sdio_probe(struct brcmf_sdio_dev *sdiodev)
|
@ -0,0 +1,33 @@ |
||||
From 51ef7925e10688c57186d438e784532e063492e4 Mon Sep 17 00:00:00 2001
|
||||
From: Andy Shevchenko <andriy.shevchenko@linux.intel.com>
|
||||
Date: Thu, 23 Nov 2017 17:57:04 +0200
|
||||
Subject: [PATCH] brcmfmac: Avoid build error with make W=1
|
||||
|
||||
When I run make W=1 on gcc (Debian 7.2.0-16) 7.2.0 I got an error for
|
||||
the first run, all next ones are okay.
|
||||
|
||||
CC [M] drivers/net/wireless/broadcom/brcm80211/brcmfmac/sdio.o
|
||||
drivers/net/wireless/broadcom/brcm80211/brcmfmac/sdio.c:2078: error: Cannot parse struct or union!
|
||||
scripts/Makefile.build:310: recipe for target 'drivers/net/wireless/broadcom/brcm80211/brcmfmac/sdio.o' failed
|
||||
|
||||
Seems like something happened with W=1 and wrong kernel doc format.
|
||||
As a quick fix remove dubious /** in the code.
|
||||
|
||||
Signed-off-by: Andy Shevchenko <andriy.shevchenko@linux.intel.com>
|
||||
Acked-by: Arend van Spriel <arend.vanspriel@broadcom.com>
|
||||
Signed-off-by: Kalle Valo <kvalo@codeaurora.org>
|
||||
---
|
||||
drivers/net/wireless/broadcom/brcm80211/brcmfmac/sdio.c | 2 +-
|
||||
1 file changed, 1 insertion(+), 1 deletion(-)
|
||||
|
||||
--- a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/sdio.c
|
||||
+++ b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/sdio.c
|
||||
@@ -2070,7 +2070,7 @@ static int brcmf_sdio_txpkt_hdalign(stru
|
||||
return head_pad;
|
||||
}
|
||||
|
||||
-/**
|
||||
+/*
|
||||
* struct brcmf_skbuff_cb reserves first two bytes in sk_buff::cb for
|
||||
* bus layer usage.
|
||||
*/
|
@ -0,0 +1,40 @@ |
||||
From cc124d5cc8d81985c3511892d7a6d546552ff754 Mon Sep 17 00:00:00 2001
|
||||
From: Wright Feng <wright.feng@cypress.com>
|
||||
Date: Tue, 16 Jan 2018 17:26:50 +0800
|
||||
Subject: [PATCH] brcmfmac: fix CLM load error for legacy chips when user
|
||||
helper is enabled
|
||||
|
||||
For legacy chips without CLM blob files, kernel with user helper function
|
||||
returns -EAGAIN when we request_firmware(), and then driver got failed
|
||||
when bringing up legacy chips. We expect the CLM blob file for legacy chip
|
||||
is not existence in firmware path, but the -ENOENT error is transferred to
|
||||
-EAGAIN in firmware_class.c with user helper.
|
||||
Because of that, we continue with CLM data currently present in firmware
|
||||
if getting error from doing request_firmware().
|
||||
|
||||
Cc: stable@vger.kernel.org # v4.15.y
|
||||
Reviewed-by: Arend van Spriel <arend.vanspriel@broadcom.com>
|
||||
Signed-off-by: Wright Feng <wright.feng@cypress.com>
|
||||
Signed-off-by: Kalle Valo <kvalo@codeaurora.org>
|
||||
---
|
||||
drivers/net/wireless/broadcom/brcm80211/brcmfmac/common.c | 9 +++------
|
||||
1 file changed, 3 insertions(+), 6 deletions(-)
|
||||
|
||||
--- a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/common.c
|
||||
+++ b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/common.c
|
||||
@@ -182,12 +182,9 @@ static int brcmf_c_process_clm_blob(stru
|
||||
|
||||
err = request_firmware(&clm, clm_name, dev);
|
||||
if (err) {
|
||||
- if (err == -ENOENT) {
|
||||
- brcmf_dbg(INFO, "continue with CLM data currently present in firmware\n");
|
||||
- return 0;
|
||||
- }
|
||||
- brcmf_err("request CLM blob file failed (%d)\n", err);
|
||||
- return err;
|
||||
+ brcmf_info("no clm_blob available(err=%d), device may have limited channels available\n",
|
||||
+ err);
|
||||
+ return 0;
|
||||
}
|
||||
|
||||
chunk_buf = kzalloc(sizeof(*chunk_buf) + MAX_CHUNK_LEN - 1, GFP_KERNEL);
|
Loading…
Reference in new issue