1
2
3
4
5
6
7
8
9
10
11
12#include <linux/module.h>
13#include <linux/types.h>
14#include <linux/ctype.h>
15#include <linux/kernel.h>
16#include <linux/init.h>
17#include <linux/kdev_t.h>
18#include <linux/console.h>
19#include <linux/string.h>
20#include <linux/sched.h>
21#include <linux/smp.h>
22#include <linux/nmi.h>
23#include <linux/delay.h>
24#include <linux/kgdb.h>
25#include <linux/kdb.h>
26#include <linux/kallsyms.h>
27#include "kdb_private.h"
28
29#define CMD_BUFLEN 256
30char kdb_prompt_str[CMD_BUFLEN];
31
32int kdb_trap_printk;
33
34static int kgdb_transition_check(char *buffer)
35{
36 if (buffer[0] != '+' && buffer[0] != '$') {
37 KDB_STATE_SET(KGDB_TRANS);
38 kdb_printf("%s", buffer);
39 } else {
40 int slen = strlen(buffer);
41 if (slen > 3 && buffer[slen - 3] == '#') {
42 kdb_gdb_state_pass(buffer);
43 strcpy(buffer, "kgdb");
44 KDB_STATE_SET(DOING_KGDB);
45 return 1;
46 }
47 }
48 return 0;
49}
50
51static int kdb_read_get_key(char *buffer, size_t bufsize)
52{
53#define ESCAPE_UDELAY 1000
54#define ESCAPE_DELAY (2*1000000/ESCAPE_UDELAY)
55 char escape_data[5];
56 char *ped = escape_data;
57 int escape_delay = 0;
58 get_char_func *f, *f_escape = NULL;
59 int key;
60
61 for (f = &kdb_poll_funcs[0]; ; ++f) {
62 if (*f == NULL) {
63
64 touch_nmi_watchdog();
65 f = &kdb_poll_funcs[0];
66 }
67 if (escape_delay == 2) {
68 *ped = '\0';
69 ped = escape_data;
70 --escape_delay;
71 }
72 if (escape_delay == 1) {
73 key = *ped++;
74 if (!*ped)
75 --escape_delay;
76 break;
77 }
78 key = (*f)();
79 if (key == -1) {
80 if (escape_delay) {
81 udelay(ESCAPE_UDELAY);
82 --escape_delay;
83 }
84 continue;
85 }
86 if (bufsize <= 2) {
87 if (key == '\r')
88 key = '\n';
89 *buffer++ = key;
90 *buffer = '\0';
91 return -1;
92 }
93 if (escape_delay == 0 && key == '\e') {
94 escape_delay = ESCAPE_DELAY;
95 ped = escape_data;
96 f_escape = f;
97 }
98 if (escape_delay) {
99 *ped++ = key;
100 if (f_escape != f) {
101 escape_delay = 2;
102 continue;
103 }
104 if (ped - escape_data == 1) {
105
106 continue;
107 } else if (ped - escape_data == 2) {
108
109 if (key != '[')
110 escape_delay = 2;
111 continue;
112 } else if (ped - escape_data == 3) {
113
114 int mapkey = 0;
115 switch (key) {
116 case 'A':
117 mapkey = 16;
118 break;
119 case 'B':
120 mapkey = 14;
121 break;
122 case 'C':
123 mapkey = 6;
124 break;
125 case 'D':
126 mapkey = 2;
127 break;
128 case '1':
129 case '3':
130
131 case '4':
132 mapkey = -1;
133 break;
134 }
135 if (mapkey != -1) {
136 if (mapkey > 0) {
137 escape_data[0] = mapkey;
138 escape_data[1] = '\0';
139 }
140 escape_delay = 2;
141 }
142 continue;
143 } else if (ped - escape_data == 4) {
144
145 int mapkey = 0;
146 if (key == '~') {
147 switch (escape_data[2]) {
148 case '1':
149 mapkey = 1;
150 break;
151 case '3':
152 mapkey = 4;
153 break;
154 case '4':
155 mapkey = 5;
156 break;
157 }
158 }
159 if (mapkey > 0) {
160 escape_data[0] = mapkey;
161 escape_data[1] = '\0';
162 }
163 escape_delay = 2;
164 continue;
165 }
166 }
167 break;
168 }
169 return key;
170}
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203static char *kdb_read(char *buffer, size_t bufsize)
204{
205 char *cp = buffer;
206 char *bufend = buffer+bufsize-2;
207
208 char *lastchar;
209 char *p_tmp;
210 char tmp;
211 static char tmpbuffer[CMD_BUFLEN];
212 int len = strlen(buffer);
213 int len_tmp;
214 int tab = 0;
215 int count;
216 int i;
217 int diag, dtab_count;
218 int key;
219
220
221 diag = kdbgetintenv("DTABCOUNT", &dtab_count);
222 if (diag)
223 dtab_count = 30;
224
225 if (len > 0) {
226 cp += len;
227 if (*(buffer+len-1) == '\n')
228 cp--;
229 }
230
231 lastchar = cp;
232 *cp = '\0';
233 kdb_printf("%s", buffer);
234poll_again:
235 key = kdb_read_get_key(buffer, bufsize);
236 if (key == -1)
237 return buffer;
238 if (key != 9)
239 tab = 0;
240 switch (key) {
241 case 8:
242 if (cp > buffer) {
243 if (cp < lastchar) {
244 memcpy(tmpbuffer, cp, lastchar - cp);
245 memcpy(cp-1, tmpbuffer, lastchar - cp);
246 }
247 *(--lastchar) = '\0';
248 --cp;
249 kdb_printf("\b%s \r", cp);
250 tmp = *cp;
251 *cp = '\0';
252 kdb_printf(kdb_prompt_str);
253 kdb_printf("%s", buffer);
254 *cp = tmp;
255 }
256 break;
257 case 13:
258 *lastchar++ = '\n';
259 *lastchar++ = '\0';
260 if (!KDB_STATE(KGDB_TRANS)) {
261 KDB_STATE_SET(KGDB_TRANS);
262 kdb_printf("%s", buffer);
263 }
264 kdb_printf("\n");
265 return buffer;
266 case 4:
267 if (cp < lastchar) {
268 memcpy(tmpbuffer, cp+1, lastchar - cp - 1);
269 memcpy(cp, tmpbuffer, lastchar - cp - 1);
270 *(--lastchar) = '\0';
271 kdb_printf("%s \r", cp);
272 tmp = *cp;
273 *cp = '\0';
274 kdb_printf(kdb_prompt_str);
275 kdb_printf("%s", buffer);
276 *cp = tmp;
277 }
278 break;
279 case 1:
280 if (cp > buffer) {
281 kdb_printf("\r");
282 kdb_printf(kdb_prompt_str);
283 cp = buffer;
284 }
285 break;
286 case 5:
287 if (cp < lastchar) {
288 kdb_printf("%s", cp);
289 cp = lastchar;
290 }
291 break;
292 case 2:
293 if (cp > buffer) {
294 kdb_printf("\b");
295 --cp;
296 }
297 break;
298 case 14:
299 memset(tmpbuffer, ' ',
300 strlen(kdb_prompt_str) + (lastchar-buffer));
301 *(tmpbuffer+strlen(kdb_prompt_str) +
302 (lastchar-buffer)) = '\0';
303 kdb_printf("\r%s\r", tmpbuffer);
304 *lastchar = (char)key;
305 *(lastchar+1) = '\0';
306 return lastchar;
307 case 6:
308 if (cp < lastchar) {
309 kdb_printf("%c", *cp);
310 ++cp;
311 }
312 break;
313 case 16:
314 memset(tmpbuffer, ' ',
315 strlen(kdb_prompt_str) + (lastchar-buffer));
316 *(tmpbuffer+strlen(kdb_prompt_str) +
317 (lastchar-buffer)) = '\0';
318 kdb_printf("\r%s\r", tmpbuffer);
319 *lastchar = (char)key;
320 *(lastchar+1) = '\0';
321 return lastchar;
322 case 9:
323 if (tab < 2)
324 ++tab;
325 p_tmp = buffer;
326 while (*p_tmp == ' ')
327 p_tmp++;
328 if (p_tmp > cp)
329 break;
330 memcpy(tmpbuffer, p_tmp, cp-p_tmp);
331 *(tmpbuffer + (cp-p_tmp)) = '\0';
332 p_tmp = strrchr(tmpbuffer, ' ');
333 if (p_tmp)
334 ++p_tmp;
335 else
336 p_tmp = tmpbuffer;
337 len = strlen(p_tmp);
338 count = kallsyms_symbol_complete(p_tmp,
339 sizeof(tmpbuffer) -
340 (p_tmp - tmpbuffer));
341 if (tab == 2 && count > 0) {
342 kdb_printf("\n%d symbols are found.", count);
343 if (count > dtab_count) {
344 count = dtab_count;
345 kdb_printf(" But only first %d symbols will"
346 " be printed.\nYou can change the"
347 " environment variable DTABCOUNT.",
348 count);
349 }
350 kdb_printf("\n");
351 for (i = 0; i < count; i++) {
352 if (kallsyms_symbol_next(p_tmp, i) < 0)
353 break;
354 kdb_printf("%s ", p_tmp);
355 *(p_tmp + len) = '\0';
356 }
357 if (i >= dtab_count)
358 kdb_printf("...");
359 kdb_printf("\n");
360 kdb_printf(kdb_prompt_str);
361 kdb_printf("%s", buffer);
362 } else if (tab != 2 && count > 0) {
363 len_tmp = strlen(p_tmp);
364 strncpy(p_tmp+len_tmp, cp, lastchar-cp+1);
365 len_tmp = strlen(p_tmp);
366 strncpy(cp, p_tmp+len, len_tmp-len + 1);
367 len = len_tmp - len;
368 kdb_printf("%s", cp);
369 cp += len;
370 lastchar += len;
371 }
372 kdb_nextline = 1;
373 break;
374 default:
375 if (key >= 32 && lastchar < bufend) {
376 if (cp < lastchar) {
377 memcpy(tmpbuffer, cp, lastchar - cp);
378 memcpy(cp+1, tmpbuffer, lastchar - cp);
379 *++lastchar = '\0';
380 *cp = key;
381 kdb_printf("%s\r", cp);
382 ++cp;
383 tmp = *cp;
384 *cp = '\0';
385 kdb_printf(kdb_prompt_str);
386 kdb_printf("%s", buffer);
387 *cp = tmp;
388 } else {
389 *++lastchar = '\0';
390 *cp++ = key;
391
392
393
394
395 if (!KDB_STATE(KGDB_TRANS)) {
396 if (kgdb_transition_check(buffer))
397 return buffer;
398 } else {
399 kdb_printf("%c", key);
400 }
401 }
402
403 if (lastchar - buffer >= 5 &&
404 strcmp(lastchar - 5, "$?#3f") == 0) {
405 kdb_gdb_state_pass(lastchar - 5);
406 strcpy(buffer, "kgdb");
407 KDB_STATE_SET(DOING_KGDB);
408 return buffer;
409 }
410 if (lastchar - buffer >= 11 &&
411 strcmp(lastchar - 11, "$qSupported") == 0) {
412 kdb_gdb_state_pass(lastchar - 11);
413 strcpy(buffer, "kgdb");
414 KDB_STATE_SET(DOING_KGDB);
415 return buffer;
416 }
417 }
418 break;
419 }
420 goto poll_again;
421}
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442char *kdb_getstr(char *buffer, size_t bufsize, const char *prompt)
443{
444 if (prompt && kdb_prompt_str != prompt)
445 strncpy(kdb_prompt_str, prompt, CMD_BUFLEN);
446 kdb_printf(kdb_prompt_str);
447 kdb_nextline = 1;
448 return kdb_read(buffer, bufsize);
449}
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468static void kdb_input_flush(void)
469{
470 get_char_func *f;
471 int res;
472 int flush_delay = 1;
473 while (flush_delay) {
474 flush_delay--;
475empty:
476 touch_nmi_watchdog();
477 for (f = &kdb_poll_funcs[0]; *f; ++f) {
478 res = (*f)();
479 if (res != -1) {
480 flush_delay = 1;
481 goto empty;
482 }
483 }
484 if (flush_delay)
485 mdelay(1);
486 }
487}
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510static char kdb_buffer[256];
511static char *next_avail = kdb_buffer;
512static int size_avail;
513static int suspend_grep;
514
515
516
517
518
519
520
521static int kdb_search_string(char *searched, char *searchfor)
522{
523 char firstchar, *cp;
524 int len1, len2;
525
526
527 len1 = strlen(searched)-1;
528 len2 = strlen(searchfor);
529 if (len1 < len2)
530 return 0;
531 if (kdb_grep_leading && kdb_grep_trailing && len1 != len2)
532 return 0;
533 if (kdb_grep_leading) {
534 if (!strncmp(searched, searchfor, len2))
535 return 1;
536 } else if (kdb_grep_trailing) {
537 if (!strncmp(searched+len1-len2, searchfor, len2))
538 return 1;
539 } else {
540 firstchar = *searchfor;
541 cp = searched;
542 while ((cp = strchr(cp, firstchar))) {
543 if (!strncmp(cp, searchfor, len2))
544 return 1;
545 cp++;
546 }
547 }
548 return 0;
549}
550
551int vkdb_printf(enum kdb_msgsrc src, const char *fmt, va_list ap)
552{
553 int diag;
554 int linecount;
555 int colcount;
556 int logging, saved_loglevel = 0;
557 int saved_trap_printk;
558 int got_printf_lock = 0;
559 int retlen = 0;
560 int fnd, len;
561 char *cp, *cp2, *cphold = NULL, replaced_byte = ' ';
562 char *moreprompt = "more> ";
563 struct console *c = console_drivers;
564 static DEFINE_SPINLOCK(kdb_printf_lock);
565 unsigned long uninitialized_var(flags);
566
567 preempt_disable();
568 saved_trap_printk = kdb_trap_printk;
569 kdb_trap_printk = 0;
570
571
572
573
574
575 if (!KDB_STATE(PRINTF_LOCK)) {
576 KDB_STATE_SET(PRINTF_LOCK);
577 spin_lock_irqsave(&kdb_printf_lock, flags);
578 got_printf_lock = 1;
579 atomic_inc(&kdb_event);
580 } else {
581 __acquire(kdb_printf_lock);
582 }
583
584 diag = kdbgetintenv("LINES", &linecount);
585 if (diag || linecount <= 1)
586 linecount = 24;
587
588 diag = kdbgetintenv("COLUMNS", &colcount);
589 if (diag || colcount <= 1)
590 colcount = 80;
591
592 diag = kdbgetintenv("LOGGING", &logging);
593 if (diag)
594 logging = 0;
595
596 if (!kdb_grepping_flag || suspend_grep) {
597
598 next_avail = kdb_buffer;
599 size_avail = sizeof(kdb_buffer);
600 }
601 vsnprintf(next_avail, size_avail, fmt, ap);
602
603
604
605
606
607
608
609
610
611
612 if (!suspend_grep && kdb_grepping_flag) {
613 cp = strchr(kdb_buffer, '\n');
614 if (!cp) {
615
616
617
618
619
620
621
622
623
624
625
626
627
628 if (next_avail == kdb_buffer) {
629
630
631
632
633
634 cp2 = kdb_buffer;
635 len = strlen(kdb_prompt_str);
636 if (!strncmp(cp2, kdb_prompt_str, len)) {
637
638
639
640
641
642 kdb_grepping_flag = 0;
643 goto kdb_printit;
644 }
645 }
646
647
648 len = strlen(kdb_buffer);
649 next_avail = kdb_buffer + len;
650 size_avail = sizeof(kdb_buffer) - len;
651 goto kdb_print_out;
652 }
653
654
655
656
657
658 cp++;
659 replaced_byte = *cp;
660 cphold = cp;
661 *cp = '\0';
662
663
664
665
666
667
668 fnd = kdb_search_string(kdb_buffer, kdb_grep_string);
669 if (!fnd) {
670
671
672
673
674
675
676 *cphold = replaced_byte;
677 strcpy(kdb_buffer, cphold);
678 len = strlen(kdb_buffer);
679 next_avail = kdb_buffer + len;
680 size_avail = sizeof(kdb_buffer) - len;
681 goto kdb_print_out;
682 }
683 if (kdb_grepping_flag >= KDB_GREPPING_FLAG_SEARCH)
684
685
686
687
688 kdb_grepping_flag = 0;
689
690
691
692
693 }
694kdb_printit:
695
696
697
698
699 retlen = strlen(kdb_buffer);
700 cp = (char *) printk_skip_level(kdb_buffer);
701 if (!dbg_kdb_mode && kgdb_connected) {
702 gdbstub_msg_write(cp, retlen - (cp - kdb_buffer));
703 } else {
704 if (dbg_io_ops && !dbg_io_ops->is_console) {
705 len = retlen - (cp - kdb_buffer);
706 cp2 = cp;
707 while (len--) {
708 dbg_io_ops->write_char(*cp2);
709 cp2++;
710 }
711 }
712 while (c) {
713 c->write(c, cp, retlen - (cp - kdb_buffer));
714 touch_nmi_watchdog();
715 c = c->next;
716 }
717 }
718 if (logging) {
719 saved_loglevel = console_loglevel;
720 console_loglevel = CONSOLE_LOGLEVEL_SILENT;
721 if (printk_get_level(kdb_buffer) || src == KDB_MSGSRC_PRINTK)
722 printk("%s", kdb_buffer);
723 else
724 pr_info("%s", kdb_buffer);
725 }
726
727 if (KDB_STATE(PAGER)) {
728
729
730
731
732
733 int got = 0;
734 len = retlen;
735 while (len--) {
736 if (kdb_buffer[len] == '\n') {
737 kdb_nextline++;
738 got = 0;
739 } else if (kdb_buffer[len] == '\r') {
740 got = 0;
741 } else {
742 got++;
743 }
744 }
745 kdb_nextline += got / (colcount + 1);
746 }
747
748
749 if (kdb_nextline >= linecount) {
750 char buf1[16] = "";
751
752
753
754
755
756 kdb_nextline = 1;
757
758
759
760
761 moreprompt = kdbgetenv("MOREPROMPT");
762 if (moreprompt == NULL)
763 moreprompt = "more> ";
764
765 kdb_input_flush();
766 c = console_drivers;
767
768 if (dbg_io_ops && !dbg_io_ops->is_console) {
769 len = strlen(moreprompt);
770 cp = moreprompt;
771 while (len--) {
772 dbg_io_ops->write_char(*cp);
773 cp++;
774 }
775 }
776 while (c) {
777 c->write(c, moreprompt, strlen(moreprompt));
778 touch_nmi_watchdog();
779 c = c->next;
780 }
781
782 if (logging)
783 printk("%s", moreprompt);
784
785 kdb_read(buf1, 2);
786
787 kdb_nextline = 1;
788
789
790 kdb_buffer[0] = '\0';
791 next_avail = kdb_buffer;
792 size_avail = sizeof(kdb_buffer);
793 if ((buf1[0] == 'q') || (buf1[0] == 'Q')) {
794
795 KDB_FLAG_SET(CMD_INTERRUPT);
796 KDB_STATE_CLEAR(PAGER);
797
798 kdb_grepping_flag = 0;
799 kdb_printf("\n");
800 } else if (buf1[0] == ' ') {
801 kdb_printf("\r");
802 suspend_grep = 1;
803 } else if (buf1[0] == '\n') {
804 kdb_nextline = linecount - 1;
805 kdb_printf("\r");
806 suspend_grep = 1;
807 } else if (buf1[0] == '/' && !kdb_grepping_flag) {
808 kdb_printf("\r");
809 kdb_getstr(kdb_grep_string, KDB_GREP_STRLEN,
810 kdbgetenv("SEARCHPROMPT") ?: "search> ");
811 *strchrnul(kdb_grep_string, '\n') = '\0';
812 kdb_grepping_flag += KDB_GREPPING_FLAG_SEARCH;
813 suspend_grep = 1;
814 } else if (buf1[0] && buf1[0] != '\n') {
815
816 suspend_grep = 1;
817 if (buf1[0] != '/')
818 kdb_printf(
819 "\nOnly 'q', 'Q' or '/' are processed at "
820 "more prompt, input ignored\n");
821 else
822 kdb_printf("\n'/' cannot be used during | "
823 "grep filtering, input ignored\n");
824 } else if (kdb_grepping_flag) {
825
826 suspend_grep = 1;
827 kdb_printf("\n");
828 }
829 kdb_input_flush();
830 }
831
832
833
834
835
836
837
838 if (kdb_grepping_flag && !suspend_grep) {
839 *cphold = replaced_byte;
840 strcpy(kdb_buffer, cphold);
841 len = strlen(kdb_buffer);
842 next_avail = kdb_buffer + len;
843 size_avail = sizeof(kdb_buffer) - len;
844 }
845
846kdb_print_out:
847 suspend_grep = 0;
848 if (logging)
849 console_loglevel = saved_loglevel;
850 if (KDB_STATE(PRINTF_LOCK) && got_printf_lock) {
851 got_printf_lock = 0;
852 spin_unlock_irqrestore(&kdb_printf_lock, flags);
853 KDB_STATE_CLEAR(PRINTF_LOCK);
854 atomic_dec(&kdb_event);
855 } else {
856 __release(kdb_printf_lock);
857 }
858 kdb_trap_printk = saved_trap_printk;
859 preempt_enable();
860 return retlen;
861}
862
863int kdb_printf(const char *fmt, ...)
864{
865 va_list ap;
866 int r;
867
868 va_start(ap, fmt);
869 r = vkdb_printf(KDB_MSGSRC_INTERNAL, fmt, ap);
870 va_end(ap);
871
872 return r;
873}
874EXPORT_SYMBOL_GPL(kdb_printf);
875