123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121 |
- From 4ab2cf03da91785f2c34d79a302e53da06928bc1 Mon Sep 17 00:00:00 2001
- From: Arend van Spriel <[email protected]>
- Date: Thu, 14 Feb 2019 13:43:51 +0100
- Subject: [PATCH] brcmfmac: check and dump trap info during sdio probe
- When the firmware crashes during the probe sequence we provide little
- information on what really failed. This patch checks the sdpcm shared
- location and show the trap information if a firmware trap has happened.
- Reviewed-by: Hante Meuleman <[email protected]>
- Reviewed-by: Pieter-Paul Giesberts <[email protected]>
- Reviewed-by: Franky Lin <[email protected]>
- Signed-off-by: Arend van Spriel <[email protected]>
- Signed-off-by: Kalle Valo <[email protected]>
- ---
- .../broadcom/brcm80211/brcmfmac/sdio.c | 59 +++++++++++++------
- 1 file changed, 40 insertions(+), 19 deletions(-)
- --- a/drivers/net/wireless/broadcom/brcm80211/brcmfmac/sdio.c
- +++ b/drivers/net/wireless/broadcom/brcm80211/brcmfmac/sdio.c
- @@ -2999,21 +2999,35 @@ static int brcmf_sdio_trap_info(struct s
- if (error < 0)
- return error;
-
- - seq_printf(seq,
- - "dongle trap info: type 0x%x @ epc 0x%08x\n"
- - " cpsr 0x%08x spsr 0x%08x sp 0x%08x\n"
- - " lr 0x%08x pc 0x%08x offset 0x%x\n"
- - " r0 0x%08x r1 0x%08x r2 0x%08x r3 0x%08x\n"
- - " r4 0x%08x r5 0x%08x r6 0x%08x r7 0x%08x\n",
- - le32_to_cpu(tr.type), le32_to_cpu(tr.epc),
- - le32_to_cpu(tr.cpsr), le32_to_cpu(tr.spsr),
- - le32_to_cpu(tr.r13), le32_to_cpu(tr.r14),
- - le32_to_cpu(tr.pc), sh->trap_addr,
- - le32_to_cpu(tr.r0), le32_to_cpu(tr.r1),
- - le32_to_cpu(tr.r2), le32_to_cpu(tr.r3),
- - le32_to_cpu(tr.r4), le32_to_cpu(tr.r5),
- - le32_to_cpu(tr.r6), le32_to_cpu(tr.r7));
- -
- + if (seq)
- + seq_printf(seq,
- + "dongle trap info: type 0x%x @ epc 0x%08x\n"
- + " cpsr 0x%08x spsr 0x%08x sp 0x%08x\n"
- + " lr 0x%08x pc 0x%08x offset 0x%x\n"
- + " r0 0x%08x r1 0x%08x r2 0x%08x r3 0x%08x\n"
- + " r4 0x%08x r5 0x%08x r6 0x%08x r7 0x%08x\n",
- + le32_to_cpu(tr.type), le32_to_cpu(tr.epc),
- + le32_to_cpu(tr.cpsr), le32_to_cpu(tr.spsr),
- + le32_to_cpu(tr.r13), le32_to_cpu(tr.r14),
- + le32_to_cpu(tr.pc), sh->trap_addr,
- + le32_to_cpu(tr.r0), le32_to_cpu(tr.r1),
- + le32_to_cpu(tr.r2), le32_to_cpu(tr.r3),
- + le32_to_cpu(tr.r4), le32_to_cpu(tr.r5),
- + le32_to_cpu(tr.r6), le32_to_cpu(tr.r7));
- + else
- + pr_debug("dongle trap info: type 0x%x @ epc 0x%08x\n"
- + " cpsr 0x%08x spsr 0x%08x sp 0x%08x\n"
- + " lr 0x%08x pc 0x%08x offset 0x%x\n"
- + " r0 0x%08x r1 0x%08x r2 0x%08x r3 0x%08x\n"
- + " r4 0x%08x r5 0x%08x r6 0x%08x r7 0x%08x\n",
- + le32_to_cpu(tr.type), le32_to_cpu(tr.epc),
- + le32_to_cpu(tr.cpsr), le32_to_cpu(tr.spsr),
- + le32_to_cpu(tr.r13), le32_to_cpu(tr.r14),
- + le32_to_cpu(tr.pc), sh->trap_addr,
- + le32_to_cpu(tr.r0), le32_to_cpu(tr.r1),
- + le32_to_cpu(tr.r2), le32_to_cpu(tr.r3),
- + le32_to_cpu(tr.r4), le32_to_cpu(tr.r5),
- + le32_to_cpu(tr.r6), le32_to_cpu(tr.r7));
- return 0;
- }
-
- @@ -3067,8 +3081,10 @@ static int brcmf_sdio_checkdied(struct b
- else if (sh.flags & SDPCM_SHARED_ASSERT)
- brcmf_err("assertion in dongle\n");
-
- - if (sh.flags & SDPCM_SHARED_TRAP)
- + if (sh.flags & SDPCM_SHARED_TRAP) {
- brcmf_err("firmware trap in dongle\n");
- + brcmf_sdio_trap_info(NULL, bus, &sh);
- + }
-
- return 0;
- }
- @@ -4199,7 +4215,7 @@ static void brcmf_sdio_firmware_callback
- } else {
- /* Disable F2 again */
- sdio_disable_func(sdiod->func2);
- - goto release;
- + goto checkdied;
- }
-
- if (brcmf_chip_sr_capable(bus->ci)) {
- @@ -4220,8 +4236,10 @@ static void brcmf_sdio_firmware_callback
- }
-
- /* If we didn't come up, turn off backplane clock */
- - if (err != 0)
- + if (err != 0) {
- brcmf_sdio_clkctl(bus, CLK_NONE, false);
- + goto checkdied;
- + }
-
- sdio_release_host(sdiod->func1);
-
- @@ -4235,12 +4253,15 @@ static void brcmf_sdio_firmware_callback
- err = brcmf_attach(sdiod->dev, sdiod->settings);
- if (err != 0) {
- brcmf_err("brcmf_attach failed\n");
- - goto fail;
- + sdio_claim_host(sdiod->func1);
- + goto checkdied;
- }
-
- /* ready */
- return;
-
- +checkdied:
- + brcmf_sdio_checkdied(bus);
- release:
- sdio_release_host(sdiod->func1);
- fail:
|