1 #include <linux/module.h>
2 #include <linux/dcache.h>
3 #include <linux/debugfs.h>
4 #include <linux/delay.h>
6 #include <linux/string.h>
7 #include <net/iw_handler.h>
9 #include "rda5890_defs.h"
10 #include "rda5890_dev.h"
12 static struct dentry *rda5890_dir = NULL;
14 void dump_buf(char *data, size_t len)
19 memset(temp_buf, 0, 64);
22 sprintf(&temp_buf[off], " ");
25 sprintf(&temp_buf[off], "%02x ", data[i]);
28 RDA5890_DBGLAP(RDA5890_DA_ALL, RDA5890_DL_TRACE,
30 memset(temp_buf, 0, 64);
34 RDA5890_DBGLAP(RDA5890_DA_ALL, RDA5890_DL_TRACE, "\n");
37 static int open_file_generic(struct inode *inode, struct file *file)
39 file->private_data = inode->i_private;
44 static ssize_t rda5890_write_file_dummy(struct file *file, const char __user *buf,
45 size_t count, loff_t *ppos)
51 static ssize_t rda5890_debug_read(struct file *file, char __user *userbuf,
52 size_t count, loff_t *ppos)
54 //struct rda5890_private *priv = file->private_data;
56 unsigned long addr = get_zeroed_page(GFP_KERNEL);
57 char *buf = (char *)addr;
60 RDA5890_DBGLAP(RDA5890_DA_SDIO, RDA5890_DL_TRACE,
63 pos += snprintf(buf+pos, PAGE_SIZE - pos, "state = %s\n",
66 res = simple_read_from_buffer(userbuf, count, ppos, buf, pos);
72 static ssize_t rda5890_debug_write(struct file *file,
73 const char __user *user_buf, size_t count,
76 //struct rda5890_private *priv = file->private_data;
79 unsigned long addr = get_zeroed_page(GFP_KERNEL);
80 char *buf = (char *)addr;
82 RDA5890_DBGLAP(RDA5890_DA_SDIO, RDA5890_DL_TRACE,
85 if (copy_from_user(buf, user_buf, count)) {
89 ret = sscanf(buf, "%d %d %d %d", &p1, &p2, &p3, &p4);
95 RDA5890_DBGLAP(RDA5890_DA_SDIO, RDA5890_DL_TRACE,
96 "input p1 = %d, p2 = %d, p3 = %d, p4 = %d\n",
105 static ssize_t rda5890_debugarea_read(struct file *file, char __user *userbuf,
106 size_t count, loff_t *ppos)
108 //struct rda5890_private *priv = file->private_data;
110 unsigned long addr = get_zeroed_page(GFP_KERNEL);
111 char *buf = (char *)addr;
114 RDA5890_DBGLAP(RDA5890_DA_SDIO, RDA5890_DL_TRACE,
117 RDA5890_DBGLAP(RDA5890_DA_SDIO, RDA5890_DL_TRACE,
118 "get debug_area = 0x%x\n",rda5890_dbg_area);
120 pos += snprintf(buf+pos, PAGE_SIZE - pos, "%x\n",
123 res = simple_read_from_buffer(userbuf, count, ppos, buf, pos);
129 static ssize_t rda5890_debugarea_write(struct file *file,
130 const char __user *user_buf, size_t count,
133 //struct rda5890_private *priv = file->private_data;
136 unsigned long addr = get_zeroed_page(GFP_KERNEL);
137 char *buf = (char *)addr;
139 RDA5890_DBGLAP(RDA5890_DA_SDIO, RDA5890_DL_TRACE,
142 if (copy_from_user(buf, user_buf, count)) {
146 ret = sscanf(buf, "%x", &debug_area);
152 rda5890_dbg_area = debug_area;
153 RDA5890_DBGLAP(RDA5890_DA_SDIO, RDA5890_DL_TRACE,
154 "set debug_area = 0x%x\n",rda5890_dbg_area);
162 static ssize_t rda5890_debuglevel_read(struct file *file, char __user *userbuf,
163 size_t count, loff_t *ppos)
165 //struct rda5890_private *priv = file->private_data;
167 unsigned long addr = get_zeroed_page(GFP_KERNEL);
168 char *buf = (char *)addr;
171 RDA5890_DBGLAP(RDA5890_DA_SDIO, RDA5890_DL_TRACE,
174 RDA5890_DBGLAP(RDA5890_DA_SDIO, RDA5890_DL_TRACE,
175 "get debug_level = 0x%x\n",rda5890_dbg_level);
177 pos += snprintf(buf+pos, PAGE_SIZE - pos, "%x\n",
180 res = simple_read_from_buffer(userbuf, count, ppos, buf, pos);
186 static ssize_t rda5890_debuglevel_write(struct file *file,
187 const char __user *user_buf, size_t count,
190 //struct rda5890_private *priv = file->private_data;
193 unsigned long addr = get_zeroed_page(GFP_KERNEL);
194 char *buf = (char *)addr;
196 RDA5890_DBGLAP(RDA5890_DA_SDIO, RDA5890_DL_TRACE,
199 if (copy_from_user(buf, user_buf, count)) {
203 ret = sscanf(buf, "%x", &debug_level);
209 rda5890_dbg_level = debug_level;
210 RDA5890_DBGLAP(RDA5890_DA_SDIO, RDA5890_DL_TRACE,
211 "set debug_level = 0x%x\n",rda5890_dbg_level);
219 static int debug_read_flag = 0;
221 static ssize_t rda5890_sdio_read(struct file *file,
222 const char __user *user_buf, size_t count,
225 //struct rda5890_private *priv = file->private_data;
226 unsigned long addr = get_zeroed_page(GFP_KERNEL);
227 char *buf = (char *)addr;
230 RDA5890_DBGLAP(RDA5890_DA_SDIO, RDA5890_DL_TRACE,
233 if (copy_from_user(buf, user_buf, count)) {
237 ret = sscanf(buf, "%d", &debug_read_flag);
248 static ssize_t rda5890_sdio_write(struct file *file,
249 const char __user *user_buf, size_t count,
252 struct rda5890_private *priv = file->private_data;
253 unsigned long addr = get_zeroed_page(GFP_KERNEL);
254 char *buf = (char *)addr;
258 RDA5890_DBGLAP(RDA5890_DA_SDIO, RDA5890_DL_TRACE,
261 if (copy_from_user(buf, user_buf, count)) {
265 ret = sscanf(buf, "%d %d", &iter, &len);
276 for (i=0; i<len; i++) {
277 buf[i] = len - i - 1;
280 for (i=0;i<iter;i++) {
281 //RDA5890_DBGLAP(RDA5890_DA_SDIO, RDA5890_DL_TRACE,
282 // "Host to Card, len = %d\n", len);
284 ret = priv->hw_host_to_card(priv, buf, len, DATA_REQUEST_PACKET);
286 //RDA5890_DBGLAP(RDA5890_DA_SDIO, RDA5890_DL_TRACE,
287 // "Host to Card done, ret = %d\n", ret);
295 #define SDIO_TEST_CMD_MAGIC 0x55664433
296 #define SDIO_TEST_CMD_LEN 16
298 #define SDIO_TEST_CMD_TYPE_H2C_START 1
299 #define SDIO_TEST_CMD_TYPE_H2C_STOP 2
300 #define SDIO_TEST_CMD_TYPE_H2C_STATUS 3
301 #define SDIO_TEST_CMD_TYPE_C2H_START 4
302 #define SDIO_TEST_CMD_TYPE_C2H_PILOT 5
303 #define SDIO_TEST_CMD_TYPE_C2H_END 6
305 static int recv_time_start, recv_time_end;
306 static int send_time_start, send_time_end;
308 void rda5890_sdio_test_card_to_host(char *buf, unsigned short len)
311 int cmd, cmd_iter, cmd_len;
313 static int recv_pattern = 0;
314 static int recv_tput_flag = 0;
315 static int recv_pkts = 0;
316 static int recv_bytes = 0;
318 //RDA5890_DBGLAP(RDA5890_DA_SDIO, RDA5890_DL_TRACE,
319 // "SDIO TEST Card to Host, len = %d\n", len);
321 if (debug_read_flag) {
322 RDA5890_DBGLAP(RDA5890_DA_SDIO, RDA5890_DL_TRACE,
323 "DEBUG RX, len = %d\n", len);
327 if ((*(volatile unsigned long *)buf == SDIO_TEST_CMD_MAGIC)
328 && len == SDIO_TEST_CMD_LEN) {
329 cmd = (int)(*(volatile unsigned long *)(buf + 4));
330 cmd_iter = (int)(*(volatile unsigned long *)(buf + 8));
331 cmd_len = (int)(*(volatile unsigned long *)(buf + 12));
332 //RDA5890_DBGLAP(RDA5890_DA_SDIO, RDA5890_DL_TRACE,
333 // "SDIO TEST CMD: cmd = %d, iter = %d, len = %d\n",
334 // cmd, cmd_iter, cmd_len);
336 case SDIO_TEST_CMD_TYPE_H2C_STATUS:
337 RDA5890_DBGLAP(RDA5890_DA_SDIO, RDA5890_DL_TRACE,
338 "H2C STATUS CMD \n");
339 time_ms = jiffies_to_msecs(send_time_end - send_time_start);
340 RDA5890_DBGLAP(RDA5890_DA_SDIO, RDA5890_DL_TRACE,
341 "SDIO H2C STATUS: pkts = %d, bytes = %d, time = %d ms\n",
342 cmd_iter, cmd_len, time_ms);
344 case SDIO_TEST_CMD_TYPE_C2H_PILOT:
345 //RDA5890_DBGLAP(RDA5890_DA_SDIO, RDA5890_DL_TRACE,
346 // "C2H PILOT CMD \n");
351 recv_time_start = jiffies;
353 case SDIO_TEST_CMD_TYPE_C2H_END:
354 //RDA5890_DBGLAP(RDA5890_DA_SDIO, RDA5890_DL_TRACE,
355 // "C2H END CMD \n");
356 recv_time_end = jiffies;
358 time_ms = jiffies_to_msecs(recv_time_end - recv_time_start);
359 RDA5890_DBGLAP(RDA5890_DA_SDIO, RDA5890_DL_TRACE,
360 "SDIO C2H STATUS: pkts = %d, bytes = %d, time = %d ms\n",
361 recv_pkts, recv_bytes, time_ms);
363 case SDIO_TEST_CMD_TYPE_H2C_START:
364 case SDIO_TEST_CMD_TYPE_H2C_STOP:
365 case SDIO_TEST_CMD_TYPE_C2H_START:
367 RDA5890_ERRP("SDIO TEST CMD: Invalid cmd %d\n", cmd);
373 for (i=0;i<len;i++) {
374 if (recv_pattern == 0) {
375 if (buf[i] != (char)(i)) {
376 RDA5890_ERRP("data[%d] error, 0x%02x, should be 0x%02x, len = %d\n",
377 i, buf[i], (char)(i), len);
382 if (buf[i] != (char)(len - i - 1)) {
383 RDA5890_ERRP("data[%d] error, 0x%02x, should be 0x%02x, len = %d\n",
384 i, buf[i], (char)(len - i - 1), len);
391 recv_pattern = !recv_pattern;
393 if (recv_tput_flag && i==len) {
399 static void sdio_tput_test_read(struct rda5890_private *priv, int iter, int len)
401 char cmd[SDIO_TEST_CMD_LEN];
404 RDA5890_DBGLAP(RDA5890_DA_SDIO, RDA5890_DL_TRACE,
405 "%s, iter = %d, len = %d\n", __func__, iter, len);
407 (*(volatile unsigned long *)(cmd + 0)) = SDIO_TEST_CMD_MAGIC;
408 (*(volatile unsigned long *)(cmd + 4)) = SDIO_TEST_CMD_TYPE_C2H_START;
409 (*(volatile unsigned long *)(cmd + 8)) = iter;
410 (*(volatile unsigned long *)(cmd + 12)) = len;
411 ret = priv->hw_host_to_card(priv, cmd, len ,SDIO_TEST_CMD_LEN);
413 RDA5890_ERRP("START cmd send fail, ret = %d\n", ret);
417 static void sdio_tput_test_write(struct rda5890_private *priv, int iter, int len)
419 unsigned long addr = get_zeroed_page(GFP_KERNEL);
420 char *buf_1 = (char *)addr;
421 char *buf_2 = (char *)addr + PAGE_SIZE/2;
422 char cmd[SDIO_TEST_CMD_LEN];
426 RDA5890_DBGLAP(RDA5890_DA_SDIO, RDA5890_DL_TRACE,
427 "%s, iter = %d, len = %d\n", __func__, iter, len);
429 for (i=0; i<len; i++) {
430 buf_1[i] = len - i - 1;
434 (*(volatile unsigned long *)(cmd + 0)) = SDIO_TEST_CMD_MAGIC;
435 (*(volatile unsigned long *)(cmd + 4)) = SDIO_TEST_CMD_TYPE_H2C_START;
436 (*(volatile unsigned long *)(cmd + 8)) = iter;
437 (*(volatile unsigned long *)(cmd + 12)) = len;
438 ret = priv->hw_host_to_card(priv, cmd, len,SDIO_TEST_CMD_LEN);
440 RDA5890_ERRP("START cmd send fail, ret = %d\n", ret);
444 send_time_start = jiffies;
445 for (i=0;i<iter;i++) {
447 ret = priv->hw_host_to_card(priv, buf_1, len, DATA_REQUEST_PACKET);
449 ret = priv->hw_host_to_card(priv, buf_2, len, DATA_REQUEST_PACKET);
451 RDA5890_ERRP("packet %d send fail, ret = %d\n", i, ret);
455 send_time_end = jiffies;
457 (*(volatile unsigned long *)(cmd + 0)) = SDIO_TEST_CMD_MAGIC;
458 (*(volatile unsigned long *)(cmd + 4)) = SDIO_TEST_CMD_TYPE_H2C_STOP;
459 (*(volatile unsigned long *)(cmd + 8)) = iter;
460 (*(volatile unsigned long *)(cmd + 12)) = len;
461 ret = priv->hw_host_to_card(priv, cmd, len, SDIO_TEST_CMD_LEN);
463 RDA5890_ERRP("START cmd send fail, ret = %d\n", ret);
471 static ssize_t rda5890_sdio_tput(struct file *file,
472 const char __user *user_buf, size_t count,
475 struct rda5890_private *priv = file->private_data;
477 unsigned long addr = get_zeroed_page(GFP_KERNEL);
478 char *buf = (char *)addr;
481 RDA5890_DBGLAP(RDA5890_DA_SDIO, RDA5890_DL_TRACE,
484 if (copy_from_user(buf, user_buf, count)) {
488 ret = sscanf(buf, "%d %d %d", &wr, &iter, &len);
490 RDA5890_DBGLAP(RDA5890_DA_SDIO, RDA5890_DL_TRACE,
491 "Error Input, format shall be [wr iter len]\n");
496 RDA5890_DBGLAP(RDA5890_DA_SDIO, RDA5890_DL_TRACE,
497 "input wr = %d, iter = %d, len = %d\n",
501 sdio_tput_test_write(priv, iter, len);
503 sdio_tput_test_read(priv, iter, len);
511 #define FOPS(fread, fwrite) { \
512 .owner = THIS_MODULE, \
513 .open = open_file_generic, \
518 struct rda5890_debugfs_files {
521 struct file_operations fops;
524 static struct rda5890_debugfs_files debugfs_files[] = {
525 { "debug", 0444, FOPS(rda5890_debug_read, rda5890_debug_write), },
526 { "debugarea", 0444, FOPS(rda5890_debugarea_read, rda5890_debugarea_write), },
527 { "debuglevel", 0444, FOPS(rda5890_debuglevel_read, rda5890_debuglevel_write), },
528 { "sdioread", 0444, FOPS(NULL, rda5890_sdio_read), },
529 { "sdiowrite", 0444, FOPS(NULL, rda5890_sdio_write), },
530 { "sdiotput", 0444, FOPS(NULL, rda5890_sdio_tput), },
533 void rda5890_debugfs_init(void)
535 RDA5890_DBGLAP(RDA5890_DA_SDIO, RDA5890_DL_DEBUG,
539 rda5890_dir = debugfs_create_dir("rda5890", NULL);
544 void rda5890_debugfs_remove(void)
546 RDA5890_DBGLAP(RDA5890_DA_SDIO, RDA5890_DL_DEBUG,
550 debugfs_remove(rda5890_dir);
555 void rda5890_debugfs_init_one(struct rda5890_private *priv)
558 struct rda5890_debugfs_files *files;
562 RDA5890_DBGLAP(RDA5890_DA_SDIO, RDA5890_DL_DEBUG,
565 priv->debugfs_dir = debugfs_create_dir("rda5890_dev", rda5890_dir);
566 if (!priv->debugfs_dir)
569 for (i=0; i<ARRAY_SIZE(debugfs_files); i++) {
570 files = &debugfs_files[i];
571 priv->debugfs_files[i] = debugfs_create_file(files->name,
582 void rda5890_debugfs_remove_one(struct rda5890_private *priv)
586 RDA5890_DBGLAP(RDA5890_DA_SDIO, RDA5890_DL_DEBUG,
589 for(i=0; i<ARRAY_SIZE(debugfs_files); i++)
590 debugfs_remove(priv->debugfs_files[i]);
591 debugfs_remove(priv->debugfs_dir);