Merge tag 'mvebu-fixes-5.9-1' of git://git.kernel.org/pub/scm/linux/kernel/git/gcleme...
[linux-2.6-microblaze.git] / drivers / net / wireless / realtek / rtlwifi / debug.c
1 // SPDX-License-Identifier: GPL-2.0
2 /* Copyright(c) 2009-2012  Realtek Corporation.*/
3
4 #include "wifi.h"
5 #include "cam.h"
6
7 #include <linux/moduleparam.h>
8 #include <linux/vmalloc.h>
9
10 #ifdef CONFIG_RTLWIFI_DEBUG
11 void _rtl_dbg_print(struct rtl_priv *rtlpriv, u64 comp, int level,
12                     const char *fmt, ...)
13 {
14         if (unlikely((comp & rtlpriv->cfg->mod_params->debug_mask) &&
15                      level <= rtlpriv->cfg->mod_params->debug_level)) {
16                 struct va_format vaf;
17                 va_list args;
18
19                 va_start(args, fmt);
20
21                 vaf.fmt = fmt;
22                 vaf.va = &args;
23
24                 pr_info("%pV", &vaf);
25
26                 va_end(args);
27         }
28 }
29 EXPORT_SYMBOL_GPL(_rtl_dbg_print);
30
31 void _rtl_dbg_print_data(struct rtl_priv *rtlpriv, u64 comp, int level,
32                          const char *titlestring,
33                          const void *hexdata, int hexdatalen)
34 {
35         if (unlikely(((comp) & rtlpriv->cfg->mod_params->debug_mask) &&
36                      ((level) <= rtlpriv->cfg->mod_params->debug_level))) {
37                 pr_info("In process \"%s\" (pid %i): %s\n",
38                         current->comm, current->pid, titlestring);
39                 print_hex_dump_bytes("", DUMP_PREFIX_NONE,
40                                      hexdata, hexdatalen);
41         }
42 }
43 EXPORT_SYMBOL_GPL(_rtl_dbg_print_data);
44
45 struct rtl_debugfs_priv {
46         struct rtl_priv *rtlpriv;
47         int (*cb_read)(struct seq_file *m, void *v);
48         ssize_t (*cb_write)(struct file *filp, const char __user *buffer,
49                             size_t count, loff_t *loff);
50         u32 cb_data;
51 };
52
53 static struct dentry *debugfs_topdir;
54
55 static int rtl_debug_get_common(struct seq_file *m, void *v)
56 {
57         struct rtl_debugfs_priv *debugfs_priv = m->private;
58
59         return debugfs_priv->cb_read(m, v);
60 }
61
62 static int dl_debug_open_common(struct inode *inode, struct file *file)
63 {
64         return single_open(file, rtl_debug_get_common, inode->i_private);
65 }
66
67 static const struct file_operations file_ops_common = {
68         .open = dl_debug_open_common,
69         .read = seq_read,
70         .llseek = seq_lseek,
71         .release = single_release,
72 };
73
74 static int rtl_debug_get_mac_page(struct seq_file *m, void *v)
75 {
76         struct rtl_debugfs_priv *debugfs_priv = m->private;
77         struct rtl_priv *rtlpriv = debugfs_priv->rtlpriv;
78         u32 page = debugfs_priv->cb_data;
79         int i, n;
80         int max = 0xff;
81
82         for (n = 0; n <= max; ) {
83                 seq_printf(m, "\n%8.8x  ", n + page);
84                 for (i = 0; i < 4 && n <= max; i++, n += 4)
85                         seq_printf(m, "%8.8x    ",
86                                    rtl_read_dword(rtlpriv, (page | n)));
87         }
88         seq_puts(m, "\n");
89         return 0;
90 }
91
92 #define RTL_DEBUG_IMPL_MAC_SERIES(page, addr)                   \
93 static struct rtl_debugfs_priv rtl_debug_priv_mac_ ##page = {   \
94         .cb_read = rtl_debug_get_mac_page,                      \
95         .cb_data = addr,                                        \
96 }
97
98 RTL_DEBUG_IMPL_MAC_SERIES(0, 0x0000);
99 RTL_DEBUG_IMPL_MAC_SERIES(1, 0x0100);
100 RTL_DEBUG_IMPL_MAC_SERIES(2, 0x0200);
101 RTL_DEBUG_IMPL_MAC_SERIES(3, 0x0300);
102 RTL_DEBUG_IMPL_MAC_SERIES(4, 0x0400);
103 RTL_DEBUG_IMPL_MAC_SERIES(5, 0x0500);
104 RTL_DEBUG_IMPL_MAC_SERIES(6, 0x0600);
105 RTL_DEBUG_IMPL_MAC_SERIES(7, 0x0700);
106 RTL_DEBUG_IMPL_MAC_SERIES(10, 0x1000);
107 RTL_DEBUG_IMPL_MAC_SERIES(11, 0x1100);
108 RTL_DEBUG_IMPL_MAC_SERIES(12, 0x1200);
109 RTL_DEBUG_IMPL_MAC_SERIES(13, 0x1300);
110 RTL_DEBUG_IMPL_MAC_SERIES(14, 0x1400);
111 RTL_DEBUG_IMPL_MAC_SERIES(15, 0x1500);
112 RTL_DEBUG_IMPL_MAC_SERIES(16, 0x1600);
113 RTL_DEBUG_IMPL_MAC_SERIES(17, 0x1700);
114
115 static int rtl_debug_get_bb_page(struct seq_file *m, void *v)
116 {
117         struct rtl_debugfs_priv *debugfs_priv = m->private;
118         struct rtl_priv *rtlpriv = debugfs_priv->rtlpriv;
119         struct ieee80211_hw *hw = rtlpriv->hw;
120         u32 page = debugfs_priv->cb_data;
121         int i, n;
122         int max = 0xff;
123
124         for (n = 0; n <= max; ) {
125                 seq_printf(m, "\n%8.8x  ", n + page);
126                 for (i = 0; i < 4 && n <= max; i++, n += 4)
127                         seq_printf(m, "%8.8x    ",
128                                    rtl_get_bbreg(hw, (page | n), 0xffffffff));
129         }
130         seq_puts(m, "\n");
131         return 0;
132 }
133
134 #define RTL_DEBUG_IMPL_BB_SERIES(page, addr)                    \
135 static struct rtl_debugfs_priv rtl_debug_priv_bb_ ##page = {    \
136         .cb_read = rtl_debug_get_bb_page,                       \
137         .cb_data = addr,                                        \
138 }
139
140 RTL_DEBUG_IMPL_BB_SERIES(8, 0x0800);
141 RTL_DEBUG_IMPL_BB_SERIES(9, 0x0900);
142 RTL_DEBUG_IMPL_BB_SERIES(a, 0x0a00);
143 RTL_DEBUG_IMPL_BB_SERIES(b, 0x0b00);
144 RTL_DEBUG_IMPL_BB_SERIES(c, 0x0c00);
145 RTL_DEBUG_IMPL_BB_SERIES(d, 0x0d00);
146 RTL_DEBUG_IMPL_BB_SERIES(e, 0x0e00);
147 RTL_DEBUG_IMPL_BB_SERIES(f, 0x0f00);
148 RTL_DEBUG_IMPL_BB_SERIES(18, 0x1800);
149 RTL_DEBUG_IMPL_BB_SERIES(19, 0x1900);
150 RTL_DEBUG_IMPL_BB_SERIES(1a, 0x1a00);
151 RTL_DEBUG_IMPL_BB_SERIES(1b, 0x1b00);
152 RTL_DEBUG_IMPL_BB_SERIES(1c, 0x1c00);
153 RTL_DEBUG_IMPL_BB_SERIES(1d, 0x1d00);
154 RTL_DEBUG_IMPL_BB_SERIES(1e, 0x1e00);
155 RTL_DEBUG_IMPL_BB_SERIES(1f, 0x1f00);
156
157 static int rtl_debug_get_reg_rf(struct seq_file *m, void *v)
158 {
159         struct rtl_debugfs_priv *debugfs_priv = m->private;
160         struct rtl_priv *rtlpriv = debugfs_priv->rtlpriv;
161         struct ieee80211_hw *hw = rtlpriv->hw;
162         enum radio_path rfpath = debugfs_priv->cb_data;
163         int i, n;
164         int max = 0x40;
165
166         if (IS_HARDWARE_TYPE_8822B(rtlpriv))
167                 max = 0xff;
168
169         seq_printf(m, "\nPATH(%d)", rfpath);
170
171         for (n = 0; n <= max; ) {
172                 seq_printf(m, "\n%8.8x  ", n);
173                 for (i = 0; i < 4 && n <= max; n += 1, i++)
174                         seq_printf(m, "%8.8x    ",
175                                    rtl_get_rfreg(hw, rfpath, n, 0xffffffff));
176         }
177         seq_puts(m, "\n");
178         return 0;
179 }
180
181 #define RTL_DEBUG_IMPL_RF_SERIES(page, addr)                    \
182 static struct rtl_debugfs_priv rtl_debug_priv_rf_ ##page = {    \
183         .cb_read = rtl_debug_get_reg_rf,                        \
184         .cb_data = addr,                                        \
185 }
186
187 RTL_DEBUG_IMPL_RF_SERIES(a, RF90_PATH_A);
188 RTL_DEBUG_IMPL_RF_SERIES(b, RF90_PATH_B);
189
190 static int rtl_debug_get_cam_register(struct seq_file *m, void *v)
191 {
192         struct rtl_debugfs_priv *debugfs_priv = m->private;
193         struct rtl_priv *rtlpriv = debugfs_priv->rtlpriv;
194         int start = debugfs_priv->cb_data;
195         u32 target_cmd = 0;
196         u32 target_val = 0;
197         u8 entry_i = 0;
198         u32 ulstatus;
199         int i = 100, j = 0;
200         int end = (start + 11 > TOTAL_CAM_ENTRY ? TOTAL_CAM_ENTRY : start + 11);
201
202         /* This dump the current register page */
203         seq_printf(m,
204                    "\n#################### SECURITY CAM (%d-%d) ##################\n",
205                    start, end - 1);
206
207         for (j = start; j < end; j++) {
208                 seq_printf(m, "\nD:  %2x > ", j);
209                 for (entry_i = 0; entry_i < CAM_CONTENT_COUNT; entry_i++) {
210                         /* polling bit, and No Write enable, and address  */
211                         target_cmd = entry_i + CAM_CONTENT_COUNT * j;
212                         target_cmd = target_cmd | BIT(31);
213
214                         /* Check polling bit is clear */
215                         while ((i--) >= 0) {
216                                 ulstatus =
217                                     rtl_read_dword(rtlpriv,
218                                                    rtlpriv->cfg->maps[RWCAM]);
219                                 if (ulstatus & BIT(31))
220                                         continue;
221                                 else
222                                         break;
223                         }
224
225                         rtl_write_dword(rtlpriv, rtlpriv->cfg->maps[RWCAM],
226                                         target_cmd);
227                         target_val = rtl_read_dword(rtlpriv,
228                                                     rtlpriv->cfg->maps[RCAMO]);
229                         seq_printf(m, "%8.8x ", target_val);
230                 }
231         }
232         seq_puts(m, "\n");
233         return 0;
234 }
235
236 #define RTL_DEBUG_IMPL_CAM_SERIES(page, addr)                   \
237 static struct rtl_debugfs_priv rtl_debug_priv_cam_ ##page = {   \
238         .cb_read = rtl_debug_get_cam_register,                  \
239         .cb_data = addr,                                        \
240 }
241
242 RTL_DEBUG_IMPL_CAM_SERIES(1, 0);
243 RTL_DEBUG_IMPL_CAM_SERIES(2, 11);
244 RTL_DEBUG_IMPL_CAM_SERIES(3, 22);
245
246 static int rtl_debug_get_btcoex(struct seq_file *m, void *v)
247 {
248         struct rtl_debugfs_priv *debugfs_priv = m->private;
249         struct rtl_priv *rtlpriv = debugfs_priv->rtlpriv;
250
251         if (rtlpriv->cfg->ops->get_btc_status())
252                 rtlpriv->btcoexist.btc_ops->btc_display_bt_coex_info(rtlpriv,
253                                                                      m);
254
255         seq_puts(m, "\n");
256
257         return 0;
258 }
259
260 static struct rtl_debugfs_priv rtl_debug_priv_btcoex = {
261         .cb_read = rtl_debug_get_btcoex,
262         .cb_data = 0,
263 };
264
265 static ssize_t rtl_debugfs_set_write_reg(struct file *filp,
266                                          const char __user *buffer,
267                                          size_t count, loff_t *loff)
268 {
269         struct rtl_debugfs_priv *debugfs_priv = filp->private_data;
270         struct rtl_priv *rtlpriv = debugfs_priv->rtlpriv;
271         char tmp[32 + 1];
272         int tmp_len;
273         u32 addr, val, len;
274         int num;
275
276         if (count < 3)
277                 return -EFAULT;
278
279         tmp_len = (count > sizeof(tmp) - 1 ? sizeof(tmp) - 1 : count);
280
281         if (!buffer || copy_from_user(tmp, buffer, tmp_len))
282                 return count;
283
284         tmp[tmp_len] = '\0';
285
286         /* write BB/MAC register */
287         num = sscanf(tmp, "%x %x %x", &addr, &val, &len);
288
289         if (num !=  3)
290                 return count;
291
292         switch (len) {
293         case 1:
294                 rtl_write_byte(rtlpriv, addr, (u8)val);
295                 break;
296         case 2:
297                 rtl_write_word(rtlpriv, addr, (u16)val);
298                 break;
299         case 4:
300                 rtl_write_dword(rtlpriv, addr, val);
301                 break;
302         default:
303                 /*printk("error write length=%d", len);*/
304                 break;
305         }
306
307         return count;
308 }
309
310 static struct rtl_debugfs_priv rtl_debug_priv_write_reg = {
311         .cb_write = rtl_debugfs_set_write_reg,
312 };
313
314 static ssize_t rtl_debugfs_set_write_h2c(struct file *filp,
315                                          const char __user *buffer,
316                                          size_t count, loff_t *loff)
317 {
318         struct rtl_debugfs_priv *debugfs_priv = filp->private_data;
319         struct rtl_priv *rtlpriv = debugfs_priv->rtlpriv;
320         struct ieee80211_hw *hw = rtlpriv->hw;
321         char tmp[32 + 1];
322         int tmp_len;
323         u8 h2c_len, h2c_data_packed[8];
324         int h2c_data[8];        /* idx 0: cmd */
325         int i;
326
327         if (count < 3)
328                 return -EFAULT;
329
330         tmp_len = (count > sizeof(tmp) - 1 ? sizeof(tmp) - 1 : count);
331
332         if (!buffer || copy_from_user(tmp, buffer, tmp_len))
333                 return count;
334
335         tmp[tmp_len] = '\0';
336
337         h2c_len = sscanf(tmp, "%X %X %X %X %X %X %X %X",
338                          &h2c_data[0], &h2c_data[1],
339                          &h2c_data[2], &h2c_data[3],
340                          &h2c_data[4], &h2c_data[5],
341                          &h2c_data[6], &h2c_data[7]);
342
343         if (h2c_len <= 0)
344                 return count;
345
346         for (i = 0; i < h2c_len; i++)
347                 h2c_data_packed[i] = (u8)h2c_data[i];
348
349         rtlpriv->cfg->ops->fill_h2c_cmd(hw, h2c_data_packed[0],
350                                         h2c_len - 1,
351                                         &h2c_data_packed[1]);
352
353         return count;
354 }
355
356 static struct rtl_debugfs_priv rtl_debug_priv_write_h2c = {
357         .cb_write = rtl_debugfs_set_write_h2c,
358 };
359
360 static ssize_t rtl_debugfs_set_write_rfreg(struct file *filp,
361                                            const char __user *buffer,
362                                             size_t count, loff_t *loff)
363 {
364         struct rtl_debugfs_priv *debugfs_priv = filp->private_data;
365         struct rtl_priv *rtlpriv = debugfs_priv->rtlpriv;
366         struct ieee80211_hw *hw = rtlpriv->hw;
367         char tmp[32 + 1];
368         int tmp_len;
369         int num;
370         int path;
371         u32 addr, bitmask, data;
372
373         if (count < 3)
374                 return -EFAULT;
375
376         tmp_len = (count > sizeof(tmp) - 1 ? sizeof(tmp) - 1 : count);
377
378         if (!buffer || copy_from_user(tmp, buffer, tmp_len))
379                 return count;
380
381         tmp[tmp_len] = '\0';
382
383         num = sscanf(tmp, "%X %X %X %X",
384                      &path, &addr, &bitmask, &data);
385
386         if (num != 4) {
387                 rtl_dbg(rtlpriv, COMP_ERR, DBG_DMESG,
388                         "Format is <path> <addr> <mask> <data>\n");
389                 return count;
390         }
391
392         rtl_set_rfreg(hw, path, addr, bitmask, data);
393
394         return count;
395 }
396
397 static struct rtl_debugfs_priv rtl_debug_priv_write_rfreg = {
398         .cb_write = rtl_debugfs_set_write_rfreg,
399 };
400
401 static int rtl_debugfs_close(struct inode *inode, struct file *filp)
402 {
403         return 0;
404 }
405
406 static ssize_t rtl_debugfs_common_write(struct file *filp,
407                                         const char __user *buffer,
408                                         size_t count, loff_t *loff)
409 {
410         struct rtl_debugfs_priv *debugfs_priv = filp->private_data;
411
412         return debugfs_priv->cb_write(filp, buffer, count, loff);
413 }
414
415 static const struct file_operations file_ops_common_write = {
416         .owner = THIS_MODULE,
417         .write = rtl_debugfs_common_write,
418         .open = simple_open,
419         .release = rtl_debugfs_close,
420 };
421
422 #define RTL_DEBUGFS_ADD_CORE(name, mode, fopname)                          \
423         do {                                                               \
424                 rtl_debug_priv_ ##name.rtlpriv = rtlpriv;                  \
425                 debugfs_create_file(#name, mode, parent,                   \
426                                     &rtl_debug_priv_ ##name,               \
427                                     &file_ops_ ##fopname);                 \
428         } while (0)
429
430 #define RTL_DEBUGFS_ADD(name)                                              \
431                 RTL_DEBUGFS_ADD_CORE(name, S_IFREG | 0444, common)
432 #define RTL_DEBUGFS_ADD_W(name)                                            \
433                 RTL_DEBUGFS_ADD_CORE(name, S_IFREG | 0222, common_write)
434
435 void rtl_debug_add_one(struct ieee80211_hw *hw)
436 {
437         struct rtl_priv *rtlpriv = rtl_priv(hw);
438         struct rtl_efuse *rtlefuse = rtl_efuse(rtl_priv(hw));
439         struct dentry *parent;
440
441         snprintf(rtlpriv->dbg.debugfs_name, 18, "%pMF", rtlefuse->dev_addr);
442
443         rtlpriv->dbg.debugfs_dir =
444                 debugfs_create_dir(rtlpriv->dbg.debugfs_name, debugfs_topdir);
445
446         parent = rtlpriv->dbg.debugfs_dir;
447
448         RTL_DEBUGFS_ADD(mac_0);
449         RTL_DEBUGFS_ADD(mac_1);
450         RTL_DEBUGFS_ADD(mac_2);
451         RTL_DEBUGFS_ADD(mac_3);
452         RTL_DEBUGFS_ADD(mac_4);
453         RTL_DEBUGFS_ADD(mac_5);
454         RTL_DEBUGFS_ADD(mac_6);
455         RTL_DEBUGFS_ADD(mac_7);
456         RTL_DEBUGFS_ADD(bb_8);
457         RTL_DEBUGFS_ADD(bb_9);
458         RTL_DEBUGFS_ADD(bb_a);
459         RTL_DEBUGFS_ADD(bb_b);
460         RTL_DEBUGFS_ADD(bb_c);
461         RTL_DEBUGFS_ADD(bb_d);
462         RTL_DEBUGFS_ADD(bb_e);
463         RTL_DEBUGFS_ADD(bb_f);
464         RTL_DEBUGFS_ADD(mac_10);
465         RTL_DEBUGFS_ADD(mac_11);
466         RTL_DEBUGFS_ADD(mac_12);
467         RTL_DEBUGFS_ADD(mac_13);
468         RTL_DEBUGFS_ADD(mac_14);
469         RTL_DEBUGFS_ADD(mac_15);
470         RTL_DEBUGFS_ADD(mac_16);
471         RTL_DEBUGFS_ADD(mac_17);
472         RTL_DEBUGFS_ADD(bb_18);
473         RTL_DEBUGFS_ADD(bb_19);
474         RTL_DEBUGFS_ADD(bb_1a);
475         RTL_DEBUGFS_ADD(bb_1b);
476         RTL_DEBUGFS_ADD(bb_1c);
477         RTL_DEBUGFS_ADD(bb_1d);
478         RTL_DEBUGFS_ADD(bb_1e);
479         RTL_DEBUGFS_ADD(bb_1f);
480         RTL_DEBUGFS_ADD(rf_a);
481         RTL_DEBUGFS_ADD(rf_b);
482
483         RTL_DEBUGFS_ADD(cam_1);
484         RTL_DEBUGFS_ADD(cam_2);
485         RTL_DEBUGFS_ADD(cam_3);
486
487         RTL_DEBUGFS_ADD(btcoex);
488
489         RTL_DEBUGFS_ADD_W(write_reg);
490         RTL_DEBUGFS_ADD_W(write_h2c);
491         RTL_DEBUGFS_ADD_W(write_rfreg);
492 }
493 EXPORT_SYMBOL_GPL(rtl_debug_add_one);
494
495 void rtl_debug_remove_one(struct ieee80211_hw *hw)
496 {
497         struct rtl_priv *rtlpriv = rtl_priv(hw);
498
499         debugfs_remove_recursive(rtlpriv->dbg.debugfs_dir);
500         rtlpriv->dbg.debugfs_dir = NULL;
501 }
502 EXPORT_SYMBOL_GPL(rtl_debug_remove_one);
503
504 void rtl_debugfs_add_topdir(void)
505 {
506         debugfs_topdir = debugfs_create_dir("rtlwifi", NULL);
507 }
508
509 void rtl_debugfs_remove_topdir(void)
510 {
511         debugfs_remove_recursive(debugfs_topdir);
512 }
513
514 #endif