1 /******************************************************************************
5 * Copyright(c) 2008 - 2011 Intel Corporation. All rights reserved.
7 * This program is free software; you can redistribute it and/or modify
8 * it under the terms of version 2 of the GNU General Public License as
9 * published by the Free Software Foundation.
11 * This program is distributed in the hope that it will be useful, but
12 * WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * General Public License for more details.
16 * You should have received a copy of the GNU General Public License
17 * along with this program; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110,
21 * The full GNU General Public License is included in this distribution
22 * in the file called LICENSE.GPL.
24 * Contact Information:
25 * Intel Linux Wireless <ilw@linux.intel.com>
26 * Intel Corporation, 5200 N.E. Elam Young Parkway, Hillsboro, OR 97124-6497
27 *****************************************************************************/
28 #include <linux/ieee80211.h>
29 #include <linux/export.h>
30 #include <net/mac80211.h>
34 /* create and remove of files */
35 #define DEBUGFS_ADD_FILE(name, parent, mode) do { \
36 if (!debugfs_create_file(#name, mode, parent, il, \
37 &il_dbgfs_##name##_ops)) \
41 #define DEBUGFS_ADD_BOOL(name, parent, ptr) do { \
42 struct dentry *__tmp; \
43 __tmp = debugfs_create_bool(#name, S_IWUSR | S_IRUSR, \
45 if (IS_ERR(__tmp) || !__tmp) \
49 #define DEBUGFS_ADD_X32(name, parent, ptr) do { \
50 struct dentry *__tmp; \
51 __tmp = debugfs_create_x32(#name, S_IWUSR | S_IRUSR, \
53 if (IS_ERR(__tmp) || !__tmp) \
58 #define DEBUGFS_READ_FUNC(name) \
59 static ssize_t il_dbgfs_##name##_read(struct file *file, \
60 char __user *user_buf, \
61 size_t count, loff_t *ppos);
63 #define DEBUGFS_WRITE_FUNC(name) \
64 static ssize_t il_dbgfs_##name##_write(struct file *file, \
65 const char __user *user_buf, \
66 size_t count, loff_t *ppos);
69 il_dbgfs_open_file_generic(struct inode *inode, struct file *file)
71 file->private_data = inode->i_private;
75 #define DEBUGFS_READ_FILE_OPS(name) \
76 DEBUGFS_READ_FUNC(name); \
77 static const struct file_operations il_dbgfs_##name##_ops = { \
78 .read = il_dbgfs_##name##_read, \
79 .open = il_dbgfs_open_file_generic, \
80 .llseek = generic_file_llseek, \
83 #define DEBUGFS_WRITE_FILE_OPS(name) \
84 DEBUGFS_WRITE_FUNC(name); \
85 static const struct file_operations il_dbgfs_##name##_ops = { \
86 .write = il_dbgfs_##name##_write, \
87 .open = il_dbgfs_open_file_generic, \
88 .llseek = generic_file_llseek, \
91 #define DEBUGFS_READ_WRITE_FILE_OPS(name) \
92 DEBUGFS_READ_FUNC(name); \
93 DEBUGFS_WRITE_FUNC(name); \
94 static const struct file_operations il_dbgfs_##name##_ops = { \
95 .write = il_dbgfs_##name##_write, \
96 .read = il_dbgfs_##name##_read, \
97 .open = il_dbgfs_open_file_generic, \
98 .llseek = generic_file_llseek, \
102 il_dbgfs_tx_stats_read(struct file *file, char __user *user_buf, size_t count,
106 struct il_priv *il = file->private_data;
113 100 + sizeof(char) * 50 * (MANAGEMENT_MAX + CONTROL_MAX);
114 buf = kzalloc(bufsz, GFP_KERNEL);
117 pos += scnprintf(buf + pos, bufsz - pos, "Management:\n");
118 for (cnt = 0; cnt < MANAGEMENT_MAX; cnt++) {
120 scnprintf(buf + pos, bufsz - pos, "\t%25s\t\t: %u\n",
121 il_get_mgmt_string(cnt), il->tx_stats.mgmt[cnt]);
123 pos += scnprintf(buf + pos, bufsz - pos, "Control\n");
124 for (cnt = 0; cnt < CONTROL_MAX; cnt++) {
126 scnprintf(buf + pos, bufsz - pos, "\t%25s\t\t: %u\n",
127 il_get_ctrl_string(cnt), il->tx_stats.ctrl[cnt]);
129 pos += scnprintf(buf + pos, bufsz - pos, "Data:\n");
131 scnprintf(buf + pos, bufsz - pos, "\tcnt: %u\n",
132 il->tx_stats.data_cnt);
134 scnprintf(buf + pos, bufsz - pos, "\tbytes: %llu\n",
135 il->tx_stats.data_bytes);
136 ret = simple_read_from_buffer(user_buf, count, ppos, buf, pos);
142 il_dbgfs_clear_traffic_stats_write(struct file *file,
143 const char __user *user_buf, size_t count,
146 struct il_priv *il = file->private_data;
151 memset(buf, 0, sizeof(buf));
152 buf_size = min(count, sizeof(buf) - 1);
153 if (copy_from_user(buf, user_buf, buf_size))
155 if (sscanf(buf, "%x", &clear_flag) != 1)
157 il_clear_traffic_stats(il);
163 il_dbgfs_rx_stats_read(struct file *file, char __user *user_buf, size_t count,
167 struct il_priv *il = file->private_data;
173 100 + sizeof(char) * 50 * (MANAGEMENT_MAX + CONTROL_MAX);
174 buf = kzalloc(bufsz, GFP_KERNEL);
178 pos += scnprintf(buf + pos, bufsz - pos, "Management:\n");
179 for (cnt = 0; cnt < MANAGEMENT_MAX; cnt++) {
181 scnprintf(buf + pos, bufsz - pos, "\t%25s\t\t: %u\n",
182 il_get_mgmt_string(cnt), il->rx_stats.mgmt[cnt]);
184 pos += scnprintf(buf + pos, bufsz - pos, "Control:\n");
185 for (cnt = 0; cnt < CONTROL_MAX; cnt++) {
187 scnprintf(buf + pos, bufsz - pos, "\t%25s\t\t: %u\n",
188 il_get_ctrl_string(cnt), il->rx_stats.ctrl[cnt]);
190 pos += scnprintf(buf + pos, bufsz - pos, "Data:\n");
192 scnprintf(buf + pos, bufsz - pos, "\tcnt: %u\n",
193 il->rx_stats.data_cnt);
195 scnprintf(buf + pos, bufsz - pos, "\tbytes: %llu\n",
196 il->rx_stats.data_bytes);
198 ret = simple_read_from_buffer(user_buf, count, ppos, buf, pos);
203 #define BYTE1_MASK 0x000000ff;
204 #define BYTE2_MASK 0x0000ffff;
205 #define BYTE3_MASK 0x00ffffff;
207 il_dbgfs_sram_read(struct file *file, char __user *user_buf, size_t count,
215 struct il_priv *il = file->private_data;
218 /* default is to dump the entire data segment */
219 if (!il->dbgfs_sram_offset && !il->dbgfs_sram_len) {
220 il->dbgfs_sram_offset = 0x800000;
221 if (il->ucode_type == UCODE_INIT)
222 il->dbgfs_sram_len = il->ucode_init_data.len;
224 il->dbgfs_sram_len = il->ucode_data.len;
226 bufsz = 30 + il->dbgfs_sram_len * sizeof(char) * 10;
227 buf = kmalloc(bufsz, GFP_KERNEL);
231 scnprintf(buf + pos, bufsz - pos, "sram_len: 0x%x\n",
234 scnprintf(buf + pos, bufsz - pos, "sram_offset: 0x%x\n",
235 il->dbgfs_sram_offset);
236 for (i = il->dbgfs_sram_len; i > 0; i -= 4) {
239 il->dbgfs_sram_offset +
240 il->dbgfs_sram_len - i);
255 pos += scnprintf(buf + pos, bufsz - pos, "\n");
256 pos += scnprintf(buf + pos, bufsz - pos, "0x%08x ", val);
258 pos += scnprintf(buf + pos, bufsz - pos, "\n");
260 ret = simple_read_from_buffer(user_buf, count, ppos, buf, pos);
266 il_dbgfs_sram_write(struct file *file, const char __user *user_buf,
267 size_t count, loff_t *ppos)
269 struct il_priv *il = file->private_data;
274 memset(buf, 0, sizeof(buf));
275 buf_size = min(count, sizeof(buf) - 1);
276 if (copy_from_user(buf, user_buf, buf_size))
279 if (sscanf(buf, "%x,%x", &offset, &len) == 2) {
280 il->dbgfs_sram_offset = offset;
281 il->dbgfs_sram_len = len;
283 il->dbgfs_sram_offset = 0;
284 il->dbgfs_sram_len = 0;
291 il_dbgfs_stations_read(struct file *file, char __user *user_buf, size_t count,
294 struct il_priv *il = file->private_data;
295 struct il_station_entry *station;
296 int max_sta = il->hw_params.max_stations;
300 /* Add 30 for initial string */
301 const size_t bufsz = 30 + sizeof(char) * 500 * (il->num_stations);
303 buf = kmalloc(bufsz, GFP_KERNEL);
308 scnprintf(buf + pos, bufsz - pos, "num of stations: %d\n\n",
311 for (i = 0; i < max_sta; i++) {
312 station = &il->stations[i];
316 scnprintf(buf + pos, bufsz - pos,
317 "station %d - addr: %pM, flags: %#x\n", i,
318 station->sta.sta.addr,
319 station->sta.station_flags_msk);
321 scnprintf(buf + pos, bufsz - pos,
322 "TID\tseq_num\ttxq_id\tframes\ttfds\t");
324 scnprintf(buf + pos, bufsz - pos,
325 "start_idx\tbitmap\t\t\trate_n_flags\n");
327 for (j = 0; j < MAX_TID_COUNT; j++) {
329 scnprintf(buf + pos, bufsz - pos,
330 "%d:\t%#x\t%#x\t%u\t%u\t%u\t\t%#.16llx\t%#x",
331 j, station->tid[j].seq_number,
332 station->tid[j].agg.txq_id,
333 station->tid[j].agg.frame_count,
334 station->tid[j].tfds_in_queue,
335 station->tid[j].agg.start_idx,
336 station->tid[j].agg.bitmap,
337 station->tid[j].agg.rate_n_flags);
339 if (station->tid[j].agg.wait_for_ba)
341 scnprintf(buf + pos, bufsz - pos,
343 pos += scnprintf(buf + pos, bufsz - pos, "\n");
346 pos += scnprintf(buf + pos, bufsz - pos, "\n");
349 ret = simple_read_from_buffer(user_buf, count, ppos, buf, pos);
355 il_dbgfs_nvm_read(struct file *file, char __user *user_buf, size_t count,
359 struct il_priv *il = file->private_data;
360 int pos = 0, ofs = 0, buf_size = 0;
364 size_t eeprom_len = il->cfg->base_params->eeprom_size;
365 buf_size = 4 * eeprom_len + 256;
367 if (eeprom_len % 16) {
368 IL_ERR("NVM size is not multiple of 16.\n");
374 IL_ERR("Invalid EEPROM memory\n");
378 /* 4 characters for byte 0xYY */
379 buf = kzalloc(buf_size, GFP_KERNEL);
381 IL_ERR("Can not allocate Buffer\n");
384 eeprom_ver = il_eeprom_query16(il, EEPROM_VERSION);
386 scnprintf(buf + pos, buf_size - pos, "EEPROM " "version: 0x%x\n",
388 for (ofs = 0; ofs < eeprom_len; ofs += 16) {
389 pos += scnprintf(buf + pos, buf_size - pos, "0x%.4x ", ofs);
390 hex_dump_to_buffer(ptr + ofs, 16, 16, 2, buf + pos,
392 pos += strlen(buf + pos);
393 if (buf_size - pos > 0)
397 ret = simple_read_from_buffer(user_buf, count, ppos, buf, pos);
403 il_dbgfs_channels_read(struct file *file, char __user *user_buf, size_t count,
406 struct il_priv *il = file->private_data;
407 struct ieee80211_channel *channels = NULL;
408 const struct ieee80211_supported_band *supp_band = NULL;
409 int pos = 0, i, bufsz = PAGE_SIZE;
413 if (!test_bit(S_GEO_CONFIGURED, &il->status))
416 buf = kzalloc(bufsz, GFP_KERNEL);
418 IL_ERR("Can not allocate Buffer\n");
422 supp_band = il_get_hw_mode(il, IEEE80211_BAND_2GHZ);
424 channels = supp_band->channels;
427 scnprintf(buf + pos, bufsz - pos,
428 "Displaying %d channels in 2.4GHz band 802.11bg):\n",
429 supp_band->n_channels);
431 for (i = 0; i < supp_band->n_channels; i++)
433 scnprintf(buf + pos, bufsz - pos,
434 "%d: %ddBm: BSS%s%s, %s.\n",
435 channels[i].hw_value,
436 channels[i].max_power,
438 flags & IEEE80211_CHAN_RADAR ?
439 " (IEEE 802.11h required)" : "",
441 flags & IEEE80211_CHAN_NO_IBSS) ||
443 flags & IEEE80211_CHAN_RADAR)) ? "" :
446 flags & IEEE80211_CHAN_PASSIVE_SCAN ?
447 "passive only" : "active/passive");
449 supp_band = il_get_hw_mode(il, IEEE80211_BAND_5GHZ);
451 channels = supp_band->channels;
454 scnprintf(buf + pos, bufsz - pos,
455 "Displaying %d channels in 5.2GHz band (802.11a)\n",
456 supp_band->n_channels);
458 for (i = 0; i < supp_band->n_channels; i++)
460 scnprintf(buf + pos, bufsz - pos,
461 "%d: %ddBm: BSS%s%s, %s.\n",
462 channels[i].hw_value,
463 channels[i].max_power,
465 flags & IEEE80211_CHAN_RADAR ?
466 " (IEEE 802.11h required)" : "",
468 flags & IEEE80211_CHAN_NO_IBSS) ||
470 flags & IEEE80211_CHAN_RADAR)) ? "" :
473 flags & IEEE80211_CHAN_PASSIVE_SCAN ?
474 "passive only" : "active/passive");
476 ret = simple_read_from_buffer(user_buf, count, ppos, buf, pos);
482 il_dbgfs_status_read(struct file *file, char __user *user_buf, size_t count,
486 struct il_priv *il = file->private_data;
489 const size_t bufsz = sizeof(buf);
492 scnprintf(buf + pos, bufsz - pos, "S_HCMD_ACTIVE:\t %d\n",
493 test_bit(S_HCMD_ACTIVE, &il->status));
495 scnprintf(buf + pos, bufsz - pos, "S_INT_ENABLED:\t %d\n",
496 test_bit(S_INT_ENABLED, &il->status));
498 scnprintf(buf + pos, bufsz - pos, "S_RF_KILL_HW:\t %d\n",
499 test_bit(S_RF_KILL_HW, &il->status));
501 scnprintf(buf + pos, bufsz - pos, "S_CT_KILL:\t\t %d\n",
502 test_bit(S_CT_KILL, &il->status));
504 scnprintf(buf + pos, bufsz - pos, "S_INIT:\t\t %d\n",
505 test_bit(S_INIT, &il->status));
507 scnprintf(buf + pos, bufsz - pos, "S_ALIVE:\t\t %d\n",
508 test_bit(S_ALIVE, &il->status));
510 scnprintf(buf + pos, bufsz - pos, "S_READY:\t\t %d\n",
511 test_bit(S_READY, &il->status));
513 scnprintf(buf + pos, bufsz - pos, "S_TEMPERATURE:\t %d\n",
514 test_bit(S_TEMPERATURE, &il->status));
516 scnprintf(buf + pos, bufsz - pos, "S_GEO_CONFIGURED:\t %d\n",
517 test_bit(S_GEO_CONFIGURED, &il->status));
519 scnprintf(buf + pos, bufsz - pos, "S_EXIT_PENDING:\t %d\n",
520 test_bit(S_EXIT_PENDING, &il->status));
522 scnprintf(buf + pos, bufsz - pos, "S_STATS:\t %d\n",
523 test_bit(S_STATS, &il->status));
525 scnprintf(buf + pos, bufsz - pos, "S_SCANNING:\t %d\n",
526 test_bit(S_SCANNING, &il->status));
528 scnprintf(buf + pos, bufsz - pos, "S_SCAN_ABORTING:\t %d\n",
529 test_bit(S_SCAN_ABORTING, &il->status));
531 scnprintf(buf + pos, bufsz - pos, "S_SCAN_HW:\t\t %d\n",
532 test_bit(S_SCAN_HW, &il->status));
534 scnprintf(buf + pos, bufsz - pos, "S_POWER_PMI:\t %d\n",
535 test_bit(S_POWER_PMI, &il->status));
537 scnprintf(buf + pos, bufsz - pos, "S_FW_ERROR:\t %d\n",
538 test_bit(S_FW_ERROR, &il->status));
539 return simple_read_from_buffer(user_buf, count, ppos, buf, pos);
543 il_dbgfs_interrupt_read(struct file *file, char __user *user_buf, size_t count,
547 struct il_priv *il = file->private_data;
551 int bufsz = 24 * 64; /* 24 items * 64 char per item */
554 buf = kzalloc(bufsz, GFP_KERNEL);
556 IL_ERR("Can not allocate Buffer\n");
561 scnprintf(buf + pos, bufsz - pos, "Interrupt Statistics Report:\n");
564 scnprintf(buf + pos, bufsz - pos, "HW Error:\t\t\t %u\n",
567 scnprintf(buf + pos, bufsz - pos, "SW Error:\t\t\t %u\n",
569 if (il->isr_stats.sw || il->isr_stats.hw) {
571 scnprintf(buf + pos, bufsz - pos,
572 "\tLast Restarting Code: 0x%X\n",
573 il->isr_stats.err_code);
575 #ifdef CONFIG_IWLEGACY_DEBUG
577 scnprintf(buf + pos, bufsz - pos, "Frame transmitted:\t\t %u\n",
580 scnprintf(buf + pos, bufsz - pos, "Alive interrupt:\t\t %u\n",
581 il->isr_stats.alive);
584 scnprintf(buf + pos, bufsz - pos,
585 "HW RF KILL switch toggled:\t %u\n",
586 il->isr_stats.rfkill);
589 scnprintf(buf + pos, bufsz - pos, "CT KILL:\t\t\t %u\n",
590 il->isr_stats.ctkill);
593 scnprintf(buf + pos, bufsz - pos, "Wakeup Interrupt:\t\t %u\n",
594 il->isr_stats.wakeup);
597 scnprintf(buf + pos, bufsz - pos, "Rx command responses:\t\t %u\n",
599 for (cnt = 0; cnt < IL_CN_MAX; cnt++) {
600 if (il->isr_stats.handlers[cnt] > 0)
602 scnprintf(buf + pos, bufsz - pos,
603 "\tRx handler[%36s]:\t\t %u\n",
604 il_get_cmd_string(cnt),
605 il->isr_stats.handlers[cnt]);
609 scnprintf(buf + pos, bufsz - pos, "Tx/FH interrupt:\t\t %u\n",
613 scnprintf(buf + pos, bufsz - pos, "Unexpected INTA:\t\t %u\n",
614 il->isr_stats.unhandled);
616 ret = simple_read_from_buffer(user_buf, count, ppos, buf, pos);
622 il_dbgfs_interrupt_write(struct file *file, const char __user *user_buf,
623 size_t count, loff_t *ppos)
625 struct il_priv *il = file->private_data;
630 memset(buf, 0, sizeof(buf));
631 buf_size = min(count, sizeof(buf) - 1);
632 if (copy_from_user(buf, user_buf, buf_size))
634 if (sscanf(buf, "%x", &reset_flag) != 1)
637 il_clear_isr_stats(il);
643 il_dbgfs_qos_read(struct file *file, char __user *user_buf, size_t count,
646 struct il_priv *il = file->private_data;
647 struct il_rxon_context *ctx = &il->ctx;
650 const size_t bufsz = sizeof(buf);
652 pos += scnprintf(buf + pos, bufsz - pos, "context %d:\n", ctx->ctxid);
653 for (i = 0; i < AC_NUM; i++) {
655 scnprintf(buf + pos, bufsz - pos,
656 "\tcw_min\tcw_max\taifsn\ttxop\n");
658 scnprintf(buf + pos, bufsz - pos,
659 "AC[%d]\t%u\t%u\t%u\t%u\n", i,
660 ctx->qos_data.def_qos_parm.ac[i].cw_min,
661 ctx->qos_data.def_qos_parm.ac[i].cw_max,
662 ctx->qos_data.def_qos_parm.ac[i].aifsn,
663 ctx->qos_data.def_qos_parm.ac[i].edca_txop);
666 return simple_read_from_buffer(user_buf, count, ppos, buf, pos);
670 il_dbgfs_disable_ht40_write(struct file *file, const char __user *user_buf,
671 size_t count, loff_t *ppos)
673 struct il_priv *il = file->private_data;
678 memset(buf, 0, sizeof(buf));
679 buf_size = min(count, sizeof(buf) - 1);
680 if (copy_from_user(buf, user_buf, buf_size))
682 if (sscanf(buf, "%d", &ht40) != 1)
684 if (!il_is_any_associated(il))
685 il->disable_ht40 = ht40 ? true : false;
687 IL_ERR("Sta associated with AP - "
688 "Change to 40MHz channel support is not allowed\n");
696 il_dbgfs_disable_ht40_read(struct file *file, char __user *user_buf,
697 size_t count, loff_t *ppos)
699 struct il_priv *il = file->private_data;
702 const size_t bufsz = sizeof(buf);
705 scnprintf(buf + pos, bufsz - pos, "11n 40MHz Mode: %s\n",
706 il->disable_ht40 ? "Disabled" : "Enabled");
707 return simple_read_from_buffer(user_buf, count, ppos, buf, pos);
710 DEBUGFS_READ_WRITE_FILE_OPS(sram);
711 DEBUGFS_READ_FILE_OPS(nvm);
712 DEBUGFS_READ_FILE_OPS(stations);
713 DEBUGFS_READ_FILE_OPS(channels);
714 DEBUGFS_READ_FILE_OPS(status);
715 DEBUGFS_READ_WRITE_FILE_OPS(interrupt);
716 DEBUGFS_READ_FILE_OPS(qos);
717 DEBUGFS_READ_WRITE_FILE_OPS(disable_ht40);
720 il_dbgfs_traffic_log_read(struct file *file, char __user *user_buf,
721 size_t count, loff_t *ppos)
723 struct il_priv *il = file->private_data;
724 int pos = 0, ofs = 0;
726 struct il_tx_queue *txq;
728 struct il_rx_queue *rxq = &il->rxq;
731 ((IL_TRAFFIC_ENTRIES * IL_TRAFFIC_ENTRY_SIZE * 64) * 2) +
732 (il->cfg->base_params->num_of_queues * 32 * 8) + 400;
737 IL_ERR("txq not ready\n");
740 buf = kzalloc(bufsz, GFP_KERNEL);
742 IL_ERR("Can not allocate buffer\n");
745 pos += scnprintf(buf + pos, bufsz - pos, "Tx Queue\n");
746 for (cnt = 0; cnt < il->hw_params.max_txq_num; cnt++) {
750 scnprintf(buf + pos, bufsz - pos,
751 "q[%d]: read_ptr: %u, write_ptr: %u\n", cnt,
752 q->read_ptr, q->write_ptr);
754 if (il->tx_traffic && (il_debug_level & IL_DL_TX)) {
755 ptr = il->tx_traffic;
757 scnprintf(buf + pos, bufsz - pos, "Tx Traffic idx: %u\n",
759 for (cnt = 0, ofs = 0; cnt < IL_TRAFFIC_ENTRIES; cnt++) {
760 for (entry = 0; entry < IL_TRAFFIC_ENTRY_SIZE / 16;
761 entry++, ofs += 16) {
763 scnprintf(buf + pos, bufsz - pos, "0x%.4x ",
765 hex_dump_to_buffer(ptr + ofs, 16, 16, 2,
766 buf + pos, bufsz - pos, 0);
767 pos += strlen(buf + pos);
774 pos += scnprintf(buf + pos, bufsz - pos, "Rx Queue\n");
776 scnprintf(buf + pos, bufsz - pos, "read: %u, write: %u\n",
777 rxq->read, rxq->write);
779 if (il->rx_traffic && (il_debug_level & IL_DL_RX)) {
780 ptr = il->rx_traffic;
782 scnprintf(buf + pos, bufsz - pos, "Rx Traffic idx: %u\n",
784 for (cnt = 0, ofs = 0; cnt < IL_TRAFFIC_ENTRIES; cnt++) {
785 for (entry = 0; entry < IL_TRAFFIC_ENTRY_SIZE / 16;
786 entry++, ofs += 16) {
788 scnprintf(buf + pos, bufsz - pos, "0x%.4x ",
790 hex_dump_to_buffer(ptr + ofs, 16, 16, 2,
791 buf + pos, bufsz - pos, 0);
792 pos += strlen(buf + pos);
799 ret = simple_read_from_buffer(user_buf, count, ppos, buf, pos);
805 il_dbgfs_traffic_log_write(struct file *file, const char __user *user_buf,
806 size_t count, loff_t *ppos)
808 struct il_priv *il = file->private_data;
813 memset(buf, 0, sizeof(buf));
814 buf_size = min(count, sizeof(buf) - 1);
815 if (copy_from_user(buf, user_buf, buf_size))
817 if (sscanf(buf, "%d", &traffic_log) != 1)
819 if (traffic_log == 0)
820 il_reset_traffic_log(il);
826 il_dbgfs_tx_queue_read(struct file *file, char __user *user_buf, size_t count,
830 struct il_priv *il = file->private_data;
831 struct il_tx_queue *txq;
838 sizeof(char) * 64 * il->cfg->base_params->num_of_queues;
841 IL_ERR("txq not ready\n");
844 buf = kzalloc(bufsz, GFP_KERNEL);
848 for (cnt = 0; cnt < il->hw_params.max_txq_num; cnt++) {
852 scnprintf(buf + pos, bufsz - pos,
853 "hwq %.2d: read=%u write=%u stop=%d"
854 " swq_id=%#.2x (ac %d/hwq %d)\n", cnt,
855 q->read_ptr, q->write_ptr,
856 !!test_bit(cnt, il->queue_stopped),
857 txq->swq_id, txq->swq_id & 3,
858 (txq->swq_id >> 2) & 0x1f);
861 /* for the ACs, display the stop count too */
863 scnprintf(buf + pos, bufsz - pos,
865 atomic_read(&il->queue_stop_count[cnt]));
867 ret = simple_read_from_buffer(user_buf, count, ppos, buf, pos);
873 il_dbgfs_rx_queue_read(struct file *file, char __user *user_buf, size_t count,
877 struct il_priv *il = file->private_data;
878 struct il_rx_queue *rxq = &il->rxq;
881 const size_t bufsz = sizeof(buf);
883 pos += scnprintf(buf + pos, bufsz - pos, "read: %u\n", rxq->read);
884 pos += scnprintf(buf + pos, bufsz - pos, "write: %u\n", rxq->write);
886 scnprintf(buf + pos, bufsz - pos, "free_count: %u\n",
890 scnprintf(buf + pos, bufsz - pos, "closed_rb_num: %u\n",
891 le16_to_cpu(rxq->rb_stts->
892 closed_rb_num) & 0x0FFF);
895 scnprintf(buf + pos, bufsz - pos,
896 "closed_rb_num: Not Allocated\n");
898 return simple_read_from_buffer(user_buf, count, ppos, buf, pos);
902 il_dbgfs_ucode_rx_stats_read(struct file *file, char __user *user_buf,
903 size_t count, loff_t *ppos)
905 struct il_priv *il = file->private_data;
906 return il->cfg->ops->lib->debugfs_ops.rx_stats_read(file, user_buf,
911 il_dbgfs_ucode_tx_stats_read(struct file *file, char __user *user_buf,
912 size_t count, loff_t *ppos)
914 struct il_priv *il = file->private_data;
915 return il->cfg->ops->lib->debugfs_ops.tx_stats_read(file, user_buf,
920 il_dbgfs_ucode_general_stats_read(struct file *file, char __user *user_buf,
921 size_t count, loff_t *ppos)
923 struct il_priv *il = file->private_data;
924 return il->cfg->ops->lib->debugfs_ops.general_stats_read(file, user_buf,
929 il_dbgfs_sensitivity_read(struct file *file, char __user *user_buf,
930 size_t count, loff_t *ppos)
933 struct il_priv *il = file->private_data;
937 int bufsz = sizeof(struct il_sensitivity_data) * 4 + 100;
939 struct il_sensitivity_data *data;
941 data = &il->sensitivity_data;
942 buf = kzalloc(bufsz, GFP_KERNEL);
944 IL_ERR("Can not allocate Buffer\n");
949 scnprintf(buf + pos, bufsz - pos, "auto_corr_ofdm:\t\t\t %u\n",
950 data->auto_corr_ofdm);
952 scnprintf(buf + pos, bufsz - pos, "auto_corr_ofdm_mrc:\t\t %u\n",
953 data->auto_corr_ofdm_mrc);
955 scnprintf(buf + pos, bufsz - pos, "auto_corr_ofdm_x1:\t\t %u\n",
956 data->auto_corr_ofdm_x1);
958 scnprintf(buf + pos, bufsz - pos, "auto_corr_ofdm_mrc_x1:\t\t %u\n",
959 data->auto_corr_ofdm_mrc_x1);
961 scnprintf(buf + pos, bufsz - pos, "auto_corr_cck:\t\t\t %u\n",
962 data->auto_corr_cck);
964 scnprintf(buf + pos, bufsz - pos, "auto_corr_cck_mrc:\t\t %u\n",
965 data->auto_corr_cck_mrc);
967 scnprintf(buf + pos, bufsz - pos,
968 "last_bad_plcp_cnt_ofdm:\t\t %u\n",
969 data->last_bad_plcp_cnt_ofdm);
971 scnprintf(buf + pos, bufsz - pos, "last_fa_cnt_ofdm:\t\t %u\n",
972 data->last_fa_cnt_ofdm);
974 scnprintf(buf + pos, bufsz - pos, "last_bad_plcp_cnt_cck:\t\t %u\n",
975 data->last_bad_plcp_cnt_cck);
977 scnprintf(buf + pos, bufsz - pos, "last_fa_cnt_cck:\t\t %u\n",
978 data->last_fa_cnt_cck);
980 scnprintf(buf + pos, bufsz - pos, "nrg_curr_state:\t\t\t %u\n",
981 data->nrg_curr_state);
983 scnprintf(buf + pos, bufsz - pos, "nrg_prev_state:\t\t\t %u\n",
984 data->nrg_prev_state);
985 pos += scnprintf(buf + pos, bufsz - pos, "nrg_value:\t\t\t");
986 for (cnt = 0; cnt < 10; cnt++) {
988 scnprintf(buf + pos, bufsz - pos, " %u",
989 data->nrg_value[cnt]);
991 pos += scnprintf(buf + pos, bufsz - pos, "\n");
992 pos += scnprintf(buf + pos, bufsz - pos, "nrg_silence_rssi:\t\t");
993 for (cnt = 0; cnt < NRG_NUM_PREV_STAT_L; cnt++) {
995 scnprintf(buf + pos, bufsz - pos, " %u",
996 data->nrg_silence_rssi[cnt]);
998 pos += scnprintf(buf + pos, bufsz - pos, "\n");
1000 scnprintf(buf + pos, bufsz - pos, "nrg_silence_ref:\t\t %u\n",
1001 data->nrg_silence_ref);
1003 scnprintf(buf + pos, bufsz - pos, "nrg_energy_idx:\t\t\t %u\n",
1004 data->nrg_energy_idx);
1006 scnprintf(buf + pos, bufsz - pos, "nrg_silence_idx:\t\t %u\n",
1007 data->nrg_silence_idx);
1009 scnprintf(buf + pos, bufsz - pos, "nrg_th_cck:\t\t\t %u\n",
1012 scnprintf(buf + pos, bufsz - pos,
1013 "nrg_auto_corr_silence_diff:\t %u\n",
1014 data->nrg_auto_corr_silence_diff);
1016 scnprintf(buf + pos, bufsz - pos, "num_in_cck_no_fa:\t\t %u\n",
1017 data->num_in_cck_no_fa);
1019 scnprintf(buf + pos, bufsz - pos, "nrg_th_ofdm:\t\t\t %u\n",
1022 ret = simple_read_from_buffer(user_buf, count, ppos, buf, pos);
1028 il_dbgfs_chain_noise_read(struct file *file, char __user *user_buf,
1029 size_t count, loff_t *ppos)
1032 struct il_priv *il = file->private_data;
1036 int bufsz = sizeof(struct il_chain_noise_data) * 4 + 100;
1038 struct il_chain_noise_data *data;
1040 data = &il->chain_noise_data;
1041 buf = kzalloc(bufsz, GFP_KERNEL);
1043 IL_ERR("Can not allocate Buffer\n");
1048 scnprintf(buf + pos, bufsz - pos, "active_chains:\t\t\t %u\n",
1049 data->active_chains);
1051 scnprintf(buf + pos, bufsz - pos, "chain_noise_a:\t\t\t %u\n",
1052 data->chain_noise_a);
1054 scnprintf(buf + pos, bufsz - pos, "chain_noise_b:\t\t\t %u\n",
1055 data->chain_noise_b);
1057 scnprintf(buf + pos, bufsz - pos, "chain_noise_c:\t\t\t %u\n",
1058 data->chain_noise_c);
1060 scnprintf(buf + pos, bufsz - pos, "chain_signal_a:\t\t\t %u\n",
1061 data->chain_signal_a);
1063 scnprintf(buf + pos, bufsz - pos, "chain_signal_b:\t\t\t %u\n",
1064 data->chain_signal_b);
1066 scnprintf(buf + pos, bufsz - pos, "chain_signal_c:\t\t\t %u\n",
1067 data->chain_signal_c);
1069 scnprintf(buf + pos, bufsz - pos, "beacon_count:\t\t\t %u\n",
1070 data->beacon_count);
1072 pos += scnprintf(buf + pos, bufsz - pos, "disconn_array:\t\t\t");
1073 for (cnt = 0; cnt < NUM_RX_CHAINS; cnt++) {
1075 scnprintf(buf + pos, bufsz - pos, " %u",
1076 data->disconn_array[cnt]);
1078 pos += scnprintf(buf + pos, bufsz - pos, "\n");
1079 pos += scnprintf(buf + pos, bufsz - pos, "delta_gain_code:\t\t");
1080 for (cnt = 0; cnt < NUM_RX_CHAINS; cnt++) {
1082 scnprintf(buf + pos, bufsz - pos, " %u",
1083 data->delta_gain_code[cnt]);
1085 pos += scnprintf(buf + pos, bufsz - pos, "\n");
1087 scnprintf(buf + pos, bufsz - pos, "radio_write:\t\t\t %u\n",
1090 scnprintf(buf + pos, bufsz - pos, "state:\t\t\t\t %u\n",
1093 ret = simple_read_from_buffer(user_buf, count, ppos, buf, pos);
1099 il_dbgfs_power_save_status_read(struct file *file, char __user *user_buf,
1100 size_t count, loff_t *ppos)
1102 struct il_priv *il = file->private_data;
1105 const size_t bufsz = sizeof(buf);
1109 _il_rd(il, CSR_GP_CNTRL) & CSR_GP_REG_POWER_SAVE_STATUS_MSK;
1111 pos += scnprintf(buf + pos, bufsz - pos, "Power Save Status: ");
1113 scnprintf(buf + pos, bufsz - pos, "%s\n",
1114 (pwrsave_status == CSR_GP_REG_NO_POWER_SAVE) ? "none" :
1115 (pwrsave_status == CSR_GP_REG_MAC_POWER_SAVE) ? "MAC" :
1116 (pwrsave_status == CSR_GP_REG_PHY_POWER_SAVE) ? "PHY" :
1119 return simple_read_from_buffer(user_buf, count, ppos, buf, pos);
1123 il_dbgfs_clear_ucode_stats_write(struct file *file,
1124 const char __user *user_buf, size_t count,
1127 struct il_priv *il = file->private_data;
1132 memset(buf, 0, sizeof(buf));
1133 buf_size = min(count, sizeof(buf) - 1);
1134 if (copy_from_user(buf, user_buf, buf_size))
1136 if (sscanf(buf, "%d", &clear) != 1)
1139 /* make request to uCode to retrieve stats information */
1140 mutex_lock(&il->mutex);
1141 il_send_stats_request(il, CMD_SYNC, true);
1142 mutex_unlock(&il->mutex);
1148 il_dbgfs_rxon_flags_read(struct file *file, char __user *user_buf,
1149 size_t count, loff_t *ppos)
1152 struct il_priv *il = file->private_data;
1156 len = sprintf(buf, "0x%04X\n", le32_to_cpu(il->ctx.active.flags));
1157 return simple_read_from_buffer(user_buf, count, ppos, buf, len);
1161 il_dbgfs_rxon_filter_flags_read(struct file *file, char __user *user_buf,
1162 size_t count, loff_t *ppos)
1165 struct il_priv *il = file->private_data;
1170 sprintf(buf, "0x%04X\n", le32_to_cpu(il->ctx.active.filter_flags));
1171 return simple_read_from_buffer(user_buf, count, ppos, buf, len);
1175 il_dbgfs_fh_reg_read(struct file *file, char __user *user_buf, size_t count,
1178 struct il_priv *il = file->private_data;
1181 ssize_t ret = -EFAULT;
1183 if (il->cfg->ops->lib->dump_fh) {
1184 ret = pos = il->cfg->ops->lib->dump_fh(il, &buf, true);
1187 simple_read_from_buffer(user_buf, count, ppos, buf,
1197 il_dbgfs_missed_beacon_read(struct file *file, char __user *user_buf,
1198 size_t count, loff_t *ppos)
1201 struct il_priv *il = file->private_data;
1204 const size_t bufsz = sizeof(buf);
1207 scnprintf(buf + pos, bufsz - pos, "%d\n",
1208 il->missed_beacon_threshold);
1210 return simple_read_from_buffer(user_buf, count, ppos, buf, pos);
1214 il_dbgfs_missed_beacon_write(struct file *file, const char __user *user_buf,
1215 size_t count, loff_t *ppos)
1217 struct il_priv *il = file->private_data;
1222 memset(buf, 0, sizeof(buf));
1223 buf_size = min(count, sizeof(buf) - 1);
1224 if (copy_from_user(buf, user_buf, buf_size))
1226 if (sscanf(buf, "%d", &missed) != 1)
1229 if (missed < IL_MISSED_BEACON_THRESHOLD_MIN ||
1230 missed > IL_MISSED_BEACON_THRESHOLD_MAX)
1231 il->missed_beacon_threshold = IL_MISSED_BEACON_THRESHOLD_DEF;
1233 il->missed_beacon_threshold = missed;
1239 il_dbgfs_force_reset_read(struct file *file, char __user *user_buf,
1240 size_t count, loff_t *ppos)
1243 struct il_priv *il = file->private_data;
1246 const size_t bufsz = sizeof(buf);
1247 struct il_force_reset *force_reset;
1249 force_reset = &il->force_reset;
1252 scnprintf(buf + pos, bufsz - pos, "\tnumber of reset request: %d\n",
1253 force_reset->reset_request_count);
1255 scnprintf(buf + pos, bufsz - pos,
1256 "\tnumber of reset request success: %d\n",
1257 force_reset->reset_success_count);
1259 scnprintf(buf + pos, bufsz - pos,
1260 "\tnumber of reset request reject: %d\n",
1261 force_reset->reset_reject_count);
1263 scnprintf(buf + pos, bufsz - pos, "\treset duration: %lu\n",
1264 force_reset->reset_duration);
1266 return simple_read_from_buffer(user_buf, count, ppos, buf, pos);
1270 il_dbgfs_force_reset_write(struct file *file, const char __user *user_buf,
1271 size_t count, loff_t *ppos)
1275 struct il_priv *il = file->private_data;
1277 ret = il_force_reset(il, true);
1279 return ret ? ret : count;
1283 il_dbgfs_wd_timeout_write(struct file *file, const char __user *user_buf,
1284 size_t count, loff_t *ppos)
1287 struct il_priv *il = file->private_data;
1292 memset(buf, 0, sizeof(buf));
1293 buf_size = min(count, sizeof(buf) - 1);
1294 if (copy_from_user(buf, user_buf, buf_size))
1296 if (sscanf(buf, "%d", &timeout) != 1)
1298 if (timeout < 0 || timeout > IL_MAX_WD_TIMEOUT)
1299 timeout = IL_DEF_WD_TIMEOUT;
1301 il->cfg->base_params->wd_timeout = timeout;
1302 il_setup_watchdog(il);
1306 DEBUGFS_READ_FILE_OPS(rx_stats);
1307 DEBUGFS_READ_FILE_OPS(tx_stats);
1308 DEBUGFS_READ_WRITE_FILE_OPS(traffic_log);
1309 DEBUGFS_READ_FILE_OPS(rx_queue);
1310 DEBUGFS_READ_FILE_OPS(tx_queue);
1311 DEBUGFS_READ_FILE_OPS(ucode_rx_stats);
1312 DEBUGFS_READ_FILE_OPS(ucode_tx_stats);
1313 DEBUGFS_READ_FILE_OPS(ucode_general_stats);
1314 DEBUGFS_READ_FILE_OPS(sensitivity);
1315 DEBUGFS_READ_FILE_OPS(chain_noise);
1316 DEBUGFS_READ_FILE_OPS(power_save_status);
1317 DEBUGFS_WRITE_FILE_OPS(clear_ucode_stats);
1318 DEBUGFS_WRITE_FILE_OPS(clear_traffic_stats);
1319 DEBUGFS_READ_FILE_OPS(fh_reg);
1320 DEBUGFS_READ_WRITE_FILE_OPS(missed_beacon);
1321 DEBUGFS_READ_WRITE_FILE_OPS(force_reset);
1322 DEBUGFS_READ_FILE_OPS(rxon_flags);
1323 DEBUGFS_READ_FILE_OPS(rxon_filter_flags);
1324 DEBUGFS_WRITE_FILE_OPS(wd_timeout);
1327 * Create the debugfs files and directories
1331 il_dbgfs_register(struct il_priv *il, const char *name)
1333 struct dentry *phyd = il->hw->wiphy->debugfsdir;
1334 struct dentry *dir_drv, *dir_data, *dir_rf, *dir_debug;
1336 dir_drv = debugfs_create_dir(name, phyd);
1340 il->debugfs_dir = dir_drv;
1342 dir_data = debugfs_create_dir("data", dir_drv);
1345 dir_rf = debugfs_create_dir("rf", dir_drv);
1348 dir_debug = debugfs_create_dir("debug", dir_drv);
1352 DEBUGFS_ADD_FILE(nvm, dir_data, S_IRUSR);
1353 DEBUGFS_ADD_FILE(sram, dir_data, S_IWUSR | S_IRUSR);
1354 DEBUGFS_ADD_FILE(stations, dir_data, S_IRUSR);
1355 DEBUGFS_ADD_FILE(channels, dir_data, S_IRUSR);
1356 DEBUGFS_ADD_FILE(status, dir_data, S_IRUSR);
1357 DEBUGFS_ADD_FILE(interrupt, dir_data, S_IWUSR | S_IRUSR);
1358 DEBUGFS_ADD_FILE(qos, dir_data, S_IRUSR);
1359 DEBUGFS_ADD_FILE(disable_ht40, dir_data, S_IWUSR | S_IRUSR);
1360 DEBUGFS_ADD_FILE(rx_stats, dir_debug, S_IRUSR);
1361 DEBUGFS_ADD_FILE(tx_stats, dir_debug, S_IRUSR);
1362 DEBUGFS_ADD_FILE(traffic_log, dir_debug, S_IWUSR | S_IRUSR);
1363 DEBUGFS_ADD_FILE(rx_queue, dir_debug, S_IRUSR);
1364 DEBUGFS_ADD_FILE(tx_queue, dir_debug, S_IRUSR);
1365 DEBUGFS_ADD_FILE(power_save_status, dir_debug, S_IRUSR);
1366 DEBUGFS_ADD_FILE(clear_ucode_stats, dir_debug, S_IWUSR);
1367 DEBUGFS_ADD_FILE(clear_traffic_stats, dir_debug, S_IWUSR);
1368 DEBUGFS_ADD_FILE(fh_reg, dir_debug, S_IRUSR);
1369 DEBUGFS_ADD_FILE(missed_beacon, dir_debug, S_IWUSR);
1370 DEBUGFS_ADD_FILE(force_reset, dir_debug, S_IWUSR | S_IRUSR);
1371 DEBUGFS_ADD_FILE(ucode_rx_stats, dir_debug, S_IRUSR);
1372 DEBUGFS_ADD_FILE(ucode_tx_stats, dir_debug, S_IRUSR);
1373 DEBUGFS_ADD_FILE(ucode_general_stats, dir_debug, S_IRUSR);
1375 if (il->cfg->base_params->sensitivity_calib_by_driver)
1376 DEBUGFS_ADD_FILE(sensitivity, dir_debug, S_IRUSR);
1377 if (il->cfg->base_params->chain_noise_calib_by_driver)
1378 DEBUGFS_ADD_FILE(chain_noise, dir_debug, S_IRUSR);
1379 DEBUGFS_ADD_FILE(rxon_flags, dir_debug, S_IWUSR);
1380 DEBUGFS_ADD_FILE(rxon_filter_flags, dir_debug, S_IWUSR);
1381 DEBUGFS_ADD_FILE(wd_timeout, dir_debug, S_IWUSR);
1382 if (il->cfg->base_params->sensitivity_calib_by_driver)
1383 DEBUGFS_ADD_BOOL(disable_sensitivity, dir_rf,
1384 &il->disable_sens_cal);
1385 if (il->cfg->base_params->chain_noise_calib_by_driver)
1386 DEBUGFS_ADD_BOOL(disable_chain_noise, dir_rf,
1387 &il->disable_chain_noise_cal);
1388 DEBUGFS_ADD_BOOL(disable_tx_power, dir_rf, &il->disable_tx_power_cal);
1392 IL_ERR("Can't create the debugfs directory\n");
1393 il_dbgfs_unregister(il);
1396 EXPORT_SYMBOL(il_dbgfs_register);
1399 * Remove the debugfs files and directories
1403 il_dbgfs_unregister(struct il_priv *il)
1405 if (!il->debugfs_dir)
1408 debugfs_remove_recursive(il->debugfs_dir);
1409 il->debugfs_dir = NULL;
1411 EXPORT_SYMBOL(il_dbgfs_unregister);