aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorKalle Valo <kvalo@qca.qualcomm.com>2011-10-30 15:16:41 -0400
committerKalle Valo <kvalo@qca.qualcomm.com>2011-11-11 05:58:59 -0500
commit6250aac6dfc01a0e3e02a8e1eef41d7fbfedb6c7 (patch)
tree7940206ded04fd6d1761f97c4e3b72982c0cb4e1
parent68469341f32b566481bfccb776ee03146b63bae5 (diff)
ath6kl: print firmware crashes always
Currently firmware crash dump is printed only if debug is enabled. Change it so that the crash dump is always printed. Also move the code from init.c to hif.c. Signed-off-by: Kalle Valo <kvalo@qca.qualcomm.com>
-rw-r--r--drivers/net/wireless/ath/ath6kl/core.h1
-rw-r--r--drivers/net/wireless/ath/ath6kl/hif.c69
-rw-r--r--drivers/net/wireless/ath/ath6kl/init.c55
3 files changed, 61 insertions, 64 deletions
diff --git a/drivers/net/wireless/ath/ath6kl/core.h b/drivers/net/wireless/ath/ath6kl/core.h
index 1ac0dd1a035b..95aed7d0fab5 100644
--- a/drivers/net/wireless/ath/ath6kl/core.h
+++ b/drivers/net/wireless/ath/ath6kl/core.h
@@ -654,7 +654,6 @@ void aggr_recv_delba_req_evt(struct ath6kl_vif *vif, u8 tid);
654void aggr_recv_addba_req_evt(struct ath6kl_vif *vif, u8 tid, u16 seq_no, 654void aggr_recv_addba_req_evt(struct ath6kl_vif *vif, u8 tid, u16 seq_no,
655 u8 win_sz); 655 u8 win_sz);
656void ath6kl_wakeup_event(void *dev); 656void ath6kl_wakeup_event(void *dev);
657void ath6kl_target_failure(struct ath6kl *ar);
658 657
659void ath6kl_reset_device(struct ath6kl *ar, u32 target_type, 658void ath6kl_reset_device(struct ath6kl *ar, u32 target_type,
660 bool wait_fot_compltn, bool cold_reset); 659 bool wait_fot_compltn, bool cold_reset);
diff --git a/drivers/net/wireless/ath/ath6kl/hif.c b/drivers/net/wireless/ath/ath6kl/hif.c
index 309be9823e02..e57da35e59fa 100644
--- a/drivers/net/wireless/ath/ath6kl/hif.c
+++ b/drivers/net/wireless/ath/ath6kl/hif.c
@@ -59,26 +59,79 @@ int ath6kl_hif_rw_comp_handler(void *context, int status)
59 59
60 return 0; 60 return 0;
61} 61}
62#define REG_DUMP_COUNT_AR6003 60
63#define REGISTER_DUMP_LEN_MAX 60
64
65static void ath6kl_hif_dump_fw_crash(struct ath6kl *ar)
66{
67 __le32 regdump_val[REGISTER_DUMP_LEN_MAX];
68 u32 i, address, regdump_addr = 0;
69 int ret;
70
71 if (ar->target_type != TARGET_TYPE_AR6003)
72 return;
73
74 /* the reg dump pointer is copied to the host interest area */
75 address = ath6kl_get_hi_item_addr(ar, HI_ITEM(hi_failure_state));
76 address = TARG_VTOP(ar->target_type, address);
77
78 /* read RAM location through diagnostic window */
79 ret = ath6kl_diag_read32(ar, address, &regdump_addr);
80
81 if (ret || !regdump_addr) {
82 ath6kl_warn("failed to get ptr to register dump area: %d\n",
83 ret);
84 return;
85 }
86
87 ath6kl_dbg(ATH6KL_DBG_IRQ, "register dump data address 0x%x\n",
88 regdump_addr);
89 regdump_addr = TARG_VTOP(ar->target_type, regdump_addr);
90
91 /* fetch register dump data */
92 ret = ath6kl_diag_read(ar, regdump_addr, (u8 *)&regdump_val[0],
93 REG_DUMP_COUNT_AR6003 * (sizeof(u32)));
94 if (ret) {
95 ath6kl_warn("failed to get register dump: %d\n", ret);
96 return;
97 }
98
99 ath6kl_info("crash dump:\n");
100 ath6kl_info("hw 0x%x fw %s\n", ar->wiphy->hw_version,
101 ar->wiphy->fw_version);
102
103 BUILD_BUG_ON(REG_DUMP_COUNT_AR6003 % 4);
104
105 for (i = 0; i < REG_DUMP_COUNT_AR6003 / 4; i++) {
106 ath6kl_info("%d: 0x%8.8x 0x%8.8x 0x%8.8x 0x%8.8x\n",
107 4 * i,
108 le32_to_cpu(regdump_val[i]),
109 le32_to_cpu(regdump_val[i + 1]),
110 le32_to_cpu(regdump_val[i + 2]),
111 le32_to_cpu(regdump_val[i + 3]));
112 }
113
114}
62 115
63static int ath6kl_hif_proc_dbg_intr(struct ath6kl_device *dev) 116static int ath6kl_hif_proc_dbg_intr(struct ath6kl_device *dev)
64{ 117{
65 u32 dummy; 118 u32 dummy;
66 int status; 119 int ret;
67 120
68 ath6kl_err("target debug interrupt\n"); 121 ath6kl_warn("firmware crashed\n");
69
70 ath6kl_target_failure(dev->ar);
71 122
72 /* 123 /*
73 * read counter to clear the interrupt, the debug error interrupt is 124 * read counter to clear the interrupt, the debug error interrupt is
74 * counter 0. 125 * counter 0.
75 */ 126 */
76 status = hif_read_write_sync(dev->ar, COUNT_DEC_ADDRESS, 127 ret = hif_read_write_sync(dev->ar, COUNT_DEC_ADDRESS,
77 (u8 *)&dummy, 4, HIF_RD_SYNC_BYTE_INC); 128 (u8 *)&dummy, 4, HIF_RD_SYNC_BYTE_INC);
78 if (status) 129 if (ret)
79 WARN_ON(1); 130 ath6kl_warn("Failed to clear debug interrupt: %d\n", ret);
80 131
81 return status; 132 ath6kl_hif_dump_fw_crash(dev->ar);
133
134 return ret;
82} 135}
83 136
84/* mailbox recv message polling */ 137/* mailbox recv message polling */
diff --git a/drivers/net/wireless/ath/ath6kl/init.c b/drivers/net/wireless/ath/ath6kl/init.c
index 237b73c6f42a..3f1f2547d142 100644
--- a/drivers/net/wireless/ath/ath6kl/init.c
+++ b/drivers/net/wireless/ath/ath6kl/init.c
@@ -298,61 +298,6 @@ out:
298 return status; 298 return status;
299} 299}
300 300
301#define REG_DUMP_COUNT_AR6003 60
302#define REGISTER_DUMP_LEN_MAX 60
303
304static void ath6kl_dump_target_assert_info(struct ath6kl *ar)
305{
306 u32 address;
307 u32 regdump_loc = 0;
308 int status;
309 u32 regdump_val[REGISTER_DUMP_LEN_MAX];
310 u32 i;
311
312 if (ar->target_type != TARGET_TYPE_AR6003)
313 return;
314
315 /* the reg dump pointer is copied to the host interest area */
316 address = ath6kl_get_hi_item_addr(ar, HI_ITEM(hi_failure_state));
317 address = TARG_VTOP(ar->target_type, address);
318
319 /* read RAM location through diagnostic window */
320 status = ath6kl_diag_read32(ar, address, &regdump_loc);
321
322 if (status || !regdump_loc) {
323 ath6kl_err("failed to get ptr to register dump area\n");
324 return;
325 }
326
327 ath6kl_dbg(ATH6KL_DBG_TRC, "location of register dump data: 0x%X\n",
328 regdump_loc);
329 regdump_loc = TARG_VTOP(ar->target_type, regdump_loc);
330
331 /* fetch register dump data */
332 status = ath6kl_diag_read(ar, regdump_loc, (u8 *)&regdump_val[0],
333 REG_DUMP_COUNT_AR6003 * (sizeof(u32)));
334
335 if (status) {
336 ath6kl_err("failed to get register dump\n");
337 return;
338 }
339 ath6kl_dbg(ATH6KL_DBG_TRC, "Register Dump:\n");
340
341 for (i = 0; i < REG_DUMP_COUNT_AR6003; i++)
342 ath6kl_dbg(ATH6KL_DBG_TRC, " %d : 0x%8.8X\n",
343 i, regdump_val[i]);
344
345}
346
347void ath6kl_target_failure(struct ath6kl *ar)
348{
349 ath6kl_err("target asserted\n");
350
351 /* try dumping target assertion information (if any) */
352 ath6kl_dump_target_assert_info(ar);
353
354}
355
356static int ath6kl_target_config_wlan_params(struct ath6kl *ar, int idx) 301static int ath6kl_target_config_wlan_params(struct ath6kl *ar, int idx)
357{ 302{
358 int status = 0; 303 int status = 0;