Commit d610cde3 authored by Franky Lin's avatar Franky Lin Committed by John W. Linville

brcmfmac: use firmware data buffer directly for nvram

The nvram file could be parsed directly in the data buffer in the
firmware structure passed by request_firmware function. This patch
gets rid of the redundant memcpy.
Reviewed-by: default avatarArend van Spriel <arend@broadcom.com>
Signed-off-by: default avatarFranky Lin <frankyl@broadcom.com>
Signed-off-by: default avatarJohn W. Linville <linville@tuxdriver.com>
parent c3d2bc35
...@@ -3336,39 +3336,6 @@ brcmf_sdbrcm_bus_rxctl(struct device *dev, unsigned char *msg, uint msglen) ...@@ -3336,39 +3336,6 @@ brcmf_sdbrcm_bus_rxctl(struct device *dev, unsigned char *msg, uint msglen)
return rxlen ? (int)rxlen : -ETIMEDOUT; return rxlen ? (int)rxlen : -ETIMEDOUT;
} }
static int brcmf_sdbrcm_downloadvars(struct brcmf_sdio *bus, void *arg, int len)
{
int bcmerror = 0;
brcmf_dbg(TRACE, "Enter\n");
/* Basic sanity checks */
if (bus->sdiodev->bus_if->drvr_up) {
bcmerror = -EISCONN;
goto err;
}
if (!len) {
bcmerror = -EOVERFLOW;
goto err;
}
/* Free the old ones and replace with passed variables */
kfree(bus->vars);
bus->vars = kmalloc(len, GFP_ATOMIC);
bus->varsz = bus->vars ? len : 0;
if (bus->vars == NULL) {
bcmerror = -ENOMEM;
goto err;
}
/* Copy the passed variables, which should include the
terminating double-null */
memcpy(bus->vars, arg, bus->varsz);
err:
return bcmerror;
}
static int brcmf_sdbrcm_write_vars(struct brcmf_sdio *bus) static int brcmf_sdbrcm_write_vars(struct brcmf_sdio *bus)
{ {
int bcmerror = 0; int bcmerror = 0;
...@@ -3573,13 +3540,21 @@ static int brcmf_sdbrcm_download_code_file(struct brcmf_sdio *bus) ...@@ -3573,13 +3540,21 @@ static int brcmf_sdbrcm_download_code_file(struct brcmf_sdio *bus)
* by two NULs. * by two NULs.
*/ */
static uint brcmf_process_nvram_vars(char *varbuf, uint len) static int brcmf_process_nvram_vars(struct brcmf_sdio *bus)
{ {
char *varbuf;
char *dp; char *dp;
bool findNewline; bool findNewline;
int column; int column;
uint buf_len, n; int ret = 0;
uint buf_len, n, len;
len = bus->firmware->size;
varbuf = vmalloc(len);
if (!varbuf)
return -ENOMEM;
memcpy(varbuf, bus->firmware->data, len);
dp = varbuf; dp = varbuf;
findNewline = false; findNewline = false;
...@@ -3608,56 +3583,44 @@ static uint brcmf_process_nvram_vars(char *varbuf, uint len) ...@@ -3608,56 +3583,44 @@ static uint brcmf_process_nvram_vars(char *varbuf, uint len)
column++; column++;
} }
buf_len = dp - varbuf; buf_len = dp - varbuf;
while (dp < varbuf + n) while (dp < varbuf + n)
*dp++ = 0; *dp++ = 0;
return buf_len; kfree(bus->vars);
bus->varsz = buf_len + 1;
bus->vars = kmalloc(bus->varsz, GFP_KERNEL);
if (bus->vars == NULL) {
bus->varsz = 0;
ret = -ENOMEM;
goto err;
}
/* copy the processed variables and add null termination */
memcpy(bus->vars, varbuf, buf_len);
bus->vars[buf_len] = 0;
err:
vfree(varbuf);
return ret;
} }
static int brcmf_sdbrcm_download_nvram(struct brcmf_sdio *bus) static int brcmf_sdbrcm_download_nvram(struct brcmf_sdio *bus)
{ {
uint len;
char *memblock = NULL;
char *bufp;
int ret; int ret;
if (bus->sdiodev->bus_if->drvr_up)
return -EISCONN;
ret = request_firmware(&bus->firmware, BRCMF_SDIO_NV_NAME, ret = request_firmware(&bus->firmware, BRCMF_SDIO_NV_NAME,
&bus->sdiodev->func[2]->dev); &bus->sdiodev->func[2]->dev);
if (ret) { if (ret) {
brcmf_dbg(ERROR, "Fail to request nvram %d\n", ret); brcmf_dbg(ERROR, "Fail to request nvram %d\n", ret);
return ret; return ret;
} }
bus->fw_ptr = 0;
memblock = kmalloc(MEMBLOCK, GFP_ATOMIC);
if (memblock == NULL) {
ret = -ENOMEM;
goto err;
}
len = brcmf_sdbrcm_get_image(memblock, MEMBLOCK, bus);
if (len > 0 && len < MEMBLOCK) {
bufp = (char *)memblock;
bufp[len] = 0;
len = brcmf_process_nvram_vars(bufp, len);
bufp += len;
*bufp++ = 0;
if (len)
ret = brcmf_sdbrcm_downloadvars(bus, memblock, len + 1);
if (ret)
brcmf_dbg(ERROR, "error downloading vars: %d\n", ret);
} else {
brcmf_dbg(ERROR, "error reading nvram file: %d\n", len);
ret = -EIO;
}
err: ret = brcmf_process_nvram_vars(bus);
kfree(memblock);
release_firmware(bus->firmware); release_firmware(bus->firmware);
bus->fw_ptr = 0;
return ret; return ret;
} }
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment