|
27 | 27 | #include <linux/kgdb.h> |
28 | 28 | #include <linux/kdb.h> |
29 | 29 |
|
30 | | -static int kgdb_nmi_knock = 1; |
31 | | -module_param_named(knock, kgdb_nmi_knock, int, 0600); |
32 | | -MODULE_PARM_DESC(knock, "if set to 1 (default), the special '$3#33' command " \ |
33 | | - "must be used to enter the debugger; when set to 0, " \ |
34 | | - "hitting return key is enough to enter the debugger; " \ |
35 | | - "when set to -1, the debugger is entered immediately " \ |
36 | | - "upon NMI"); |
37 | | - |
38 | | -static char *kgdb_nmi_magic = "$3#33"; |
39 | | -module_param_named(magic, kgdb_nmi_magic, charp, 0600); |
40 | | -MODULE_PARM_DESC(magic, "magic sequence to enter NMI debugger (default $3#33)"); |
41 | | - |
42 | 30 | static atomic_t kgdb_nmi_num_readers = ATOMIC_INIT(0); |
43 | 31 |
|
44 | 32 | static int kgdb_nmi_console_setup(struct console *co, char *options) |
@@ -95,95 +83,6 @@ struct kgdb_nmi_tty_priv { |
95 | 83 |
|
96 | 84 | static struct tty_port *kgdb_nmi_port; |
97 | 85 |
|
98 | | -static void kgdb_tty_recv(int ch) |
99 | | -{ |
100 | | - struct kgdb_nmi_tty_priv *priv; |
101 | | - char c = ch; |
102 | | - |
103 | | - if (!kgdb_nmi_port || ch < 0) |
104 | | - return; |
105 | | - /* |
106 | | - * Can't use port->tty->driver_data as tty might be not there. Timer |
107 | | - * will check for tty and will get the ref, but here we don't have to |
108 | | - * do that, and actually, we can't: we're in NMI context, no locks are |
109 | | - * possible. |
110 | | - */ |
111 | | - priv = container_of(kgdb_nmi_port, struct kgdb_nmi_tty_priv, port); |
112 | | - kfifo_in(&priv->fifo, &c, 1); |
113 | | -} |
114 | | - |
115 | | -static int kgdb_nmi_poll_one_knock(void) |
116 | | -{ |
117 | | - static int n; |
118 | | - int c; |
119 | | - const char *magic = kgdb_nmi_magic; |
120 | | - size_t m = strlen(magic); |
121 | | - bool printch = false; |
122 | | - |
123 | | - c = dbg_io_ops->read_char(); |
124 | | - if (c == NO_POLL_CHAR) |
125 | | - return c; |
126 | | - |
127 | | - if (!kgdb_nmi_knock && (c == '\r' || c == '\n')) { |
128 | | - return 1; |
129 | | - } else if (c == magic[n]) { |
130 | | - n = (n + 1) % m; |
131 | | - if (!n) |
132 | | - return 1; |
133 | | - printch = true; |
134 | | - } else { |
135 | | - n = 0; |
136 | | - } |
137 | | - |
138 | | - if (atomic_read(&kgdb_nmi_num_readers)) { |
139 | | - kgdb_tty_recv(c); |
140 | | - return 0; |
141 | | - } |
142 | | - |
143 | | - if (printch) { |
144 | | - kdb_printf("%c", c); |
145 | | - return 0; |
146 | | - } |
147 | | - |
148 | | - kdb_printf("\r%s %s to enter the debugger> %*s", |
149 | | - kgdb_nmi_knock ? "Type" : "Hit", |
150 | | - kgdb_nmi_knock ? magic : "<return>", (int)m, ""); |
151 | | - while (m--) |
152 | | - kdb_printf("\b"); |
153 | | - return 0; |
154 | | -} |
155 | | - |
156 | | -/** |
157 | | - * kgdb_nmi_poll_knock - Check if it is time to enter the debugger |
158 | | - * |
159 | | - * "Serial ports are often noisy, especially when muxed over another port (we |
160 | | - * often use serial over the headset connector). Noise on the async command |
161 | | - * line just causes characters that are ignored, on a command line that blocked |
162 | | - * execution noise would be catastrophic." -- Colin Cross |
163 | | - * |
164 | | - * So, this function implements KGDB/KDB knocking on the serial line: we won't |
165 | | - * enter the debugger until we receive a known magic phrase (which is actually |
166 | | - * "$3#33", known as "escape to KDB" command. There is also a relaxed variant |
167 | | - * of knocking, i.e. just pressing the return key is enough to enter the |
168 | | - * debugger. And if knocking is disabled, the function always returns 1. |
169 | | - */ |
170 | | -bool kgdb_nmi_poll_knock(void) |
171 | | -{ |
172 | | - if (kgdb_nmi_knock < 0) |
173 | | - return true; |
174 | | - |
175 | | - while (1) { |
176 | | - int ret; |
177 | | - |
178 | | - ret = kgdb_nmi_poll_one_knock(); |
179 | | - if (ret == NO_POLL_CHAR) |
180 | | - return false; |
181 | | - else if (ret == 1) |
182 | | - break; |
183 | | - } |
184 | | - return true; |
185 | | -} |
186 | | - |
187 | 86 | /* |
188 | 87 | * The tasklet is cheap, it does not cause wakeups when reschedules itself, |
189 | 88 | * instead it waits for the next tick. |
|
0 commit comments