2012-03-13 Hui Zhu <teawater@gmail.com>
[deliverable/binutils-gdb.git] / gdb / mi / mi-cmd-break.c
CommitLineData
fb40c209 1/* MI Command Set - breakpoint and watchpoint commands.
0b302171 2 Copyright (C) 2000-2002, 2007-2012 Free Software Foundation, Inc.
ab91fdd5 3 Contributed by Cygnus Solutions (a Red Hat company).
fb40c209
AC
4
5 This file is part of GDB.
6
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
a9762ec7 9 the Free Software Foundation; either version 3 of the License, or
fb40c209
AC
10 (at your option) any later version.
11
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
16
17 You should have received a copy of the GNU General Public License
a9762ec7 18 along with this program. If not, see <http://www.gnu.org/licenses/>. */
fb40c209
AC
19
20#include "defs.h"
a6d9a66e 21#include "arch-utils.h"
fb40c209
AC
22#include "mi-cmds.h"
23#include "ui-out.h"
24#include "mi-out.h"
25#include "breakpoint.h"
26#include "gdb_string.h"
27#include "mi-getopt.h"
5b7f31a4 28#include "gdb.h"
98deb0da 29#include "exceptions.h"
383f836e 30#include "observer.h"
8d3788bd 31#include "mi-main.h"
fb40c209 32
fb40c209
AC
33enum
34 {
35 FROM_TTY = 0
36 };
37
383f836e
TT
38/* True if MI breakpoint observers have been registered. */
39
40static int mi_breakpoint_observers_installed;
41
42/* Control whether breakpoint_notify may act. */
43
44static int mi_can_breakpoint_notify;
45
2b03b41d 46/* Output a single breakpoint, when allowed. */
fb40c209
AC
47
48static void
8d3788bd 49breakpoint_notify (struct breakpoint *b)
fb40c209 50{
383f836e 51 if (mi_can_breakpoint_notify)
79a45e25 52 gdb_breakpoint_query (current_uiout, b->number, NULL);
fb40c209
AC
53}
54
fb40c209
AC
55enum bp_type
56 {
57 REG_BP,
58 HW_BP,
59 REGEXP_BP
60 };
61
afe8ab22
VP
62/* Implements the -break-insert command.
63 See the MI manual for the list of possible options. */
fb40c209 64
ce8f13f8 65void
fb40c209
AC
66mi_cmd_break_insert (char *command, char **argv, int argc)
67{
68 char *address = NULL;
8cdf0e15 69 int hardware = 0;
fb40c209
AC
70 int temp_p = 0;
71 int thread = -1;
72 int ignore_count = 0;
73 char *condition = NULL;
afe8ab22 74 int pending = 0;
41447f92 75 int enabled = 1;
6534d786 76 int tracepoint = 0;
8cdf0e15 77 struct cleanup *back_to;
0fb4aa4b 78 enum bptype type_wanted;
41447f92 79
fb40c209
AC
80 enum opt
81 {
8cdf0e15 82 HARDWARE_OPT, TEMP_OPT, CONDITION_OPT,
6534d786
VP
83 IGNORE_COUNT_OPT, THREAD_OPT, PENDING_OPT, DISABLE_OPT,
84 TRACEPOINT_OPT,
fb40c209 85 };
91174723 86 static const struct mi_opt opts[] =
fb40c209
AC
87 {
88 {"h", HARDWARE_OPT, 0},
89 {"t", TEMP_OPT, 0},
90 {"c", CONDITION_OPT, 1},
91 {"i", IGNORE_COUNT_OPT, 1},
92 {"p", THREAD_OPT, 1},
afe8ab22 93 {"f", PENDING_OPT, 0},
41447f92 94 {"d", DISABLE_OPT, 0},
6534d786 95 {"a", TRACEPOINT_OPT, 0},
d5d6fca5 96 { 0, 0, 0 }
fb40c209
AC
97 };
98
99 /* Parse arguments. It could be -r or -h or -t, <location> or ``--''
100 to denote the end of the option list. */
f8c000a2
AS
101 int oind = 0;
102 char *oarg;
102040f0 103
fb40c209
AC
104 while (1)
105 {
1b05df00 106 int opt = mi_getopt ("-break-insert", argc, argv,
f8c000a2 107 opts, &oind, &oarg);
fb40c209
AC
108 if (opt < 0)
109 break;
110 switch ((enum opt) opt)
111 {
112 case TEMP_OPT:
113 temp_p = 1;
114 break;
115 case HARDWARE_OPT:
8cdf0e15 116 hardware = 1;
fb40c209 117 break;
fb40c209 118 case CONDITION_OPT:
f8c000a2 119 condition = oarg;
fb40c209
AC
120 break;
121 case IGNORE_COUNT_OPT:
f8c000a2 122 ignore_count = atol (oarg);
fb40c209
AC
123 break;
124 case THREAD_OPT:
f8c000a2 125 thread = atol (oarg);
fb40c209 126 break;
afe8ab22
VP
127 case PENDING_OPT:
128 pending = 1;
129 break;
41447f92
VP
130 case DISABLE_OPT:
131 enabled = 0;
6534d786
VP
132 break;
133 case TRACEPOINT_OPT:
134 tracepoint = 1;
135 break;
fb40c209
AC
136 }
137 }
138
f8c000a2 139 if (oind >= argc)
1b05df00 140 error (_("-break-insert: Missing <location>"));
f8c000a2 141 if (oind < argc - 1)
1b05df00 142 error (_("-break-insert: Garbage following <location>"));
f8c000a2 143 address = argv[oind];
fb40c209 144
2b03b41d 145 /* Now we have what we need, let's insert the breakpoint! */
383f836e
TT
146 if (! mi_breakpoint_observers_installed)
147 {
148 observer_attach_breakpoint_created (breakpoint_notify);
383f836e
TT
149 mi_breakpoint_observers_installed = 1;
150 }
151
8cdf0e15 152 back_to = make_cleanup_restore_integer (&mi_can_breakpoint_notify);
383f836e 153 mi_can_breakpoint_notify = 1;
0fb4aa4b
PA
154
155 /* Note that to request a fast tracepoint, the client uses the
156 "hardware" flag, although there's nothing of hardware related to
157 fast tracepoints -- one can implement slow tracepoints with
158 hardware breakpoints, but fast tracepoints are always software.
159 "fast" is a misnomer, actually, "jump" would be more appropriate.
160 A simulator or an emulator could conceivably implement fast
161 regular non-jump based tracepoints. */
162 type_wanted = (tracepoint
163 ? (hardware ? bp_fast_tracepoint : bp_tracepoint)
164 : (hardware ? bp_hardware_breakpoint : bp_breakpoint));
165
8cdf0e15
VP
166 create_breakpoint (get_current_arch (), address, condition, thread,
167 0 /* condition and thread are valid. */,
0fb4aa4b 168 temp_p, type_wanted,
8cdf0e15
VP
169 ignore_count,
170 pending ? AUTO_BOOLEAN_TRUE : AUTO_BOOLEAN_FALSE,
44f238bb 171 &bkpt_breakpoint_ops, 0, enabled, 0, 0);
8cdf0e15
VP
172 do_cleanups (back_to);
173
fb40c209
AC
174}
175
176enum wp_type
177{
178 REG_WP,
179 READ_WP,
180 ACCESS_WP
181};
182
9b4c786c
VP
183void
184mi_cmd_break_passcount (char *command, char **argv, int argc)
185{
186 int n;
187 int p;
d9b3f62e 188 struct tracepoint *t;
9b4c786c
VP
189
190 if (argc != 2)
191 error (_("Usage: tracepoint-number passcount"));
192
193 n = atoi (argv[0]);
194 p = atoi (argv[1]);
195 t = get_tracepoint (n);
196
197 if (t)
198 {
199 t->pass_count = p;
200 observer_notify_tracepoint_modified (n);
201 }
202 else
203 {
401a70b8 204 error (_("Could not find tracepoint %d"), n);
9b4c786c
VP
205 }
206}
207
fb40c209
AC
208/* Insert a watchpoint. The type of watchpoint is specified by the
209 first argument:
210 -break-watch <expr> --> insert a regular wp.
211 -break-watch -r <expr> --> insert a read watchpoint.
2b03b41d 212 -break-watch -a <expr> --> insert an access wp. */
fb40c209 213
ce8f13f8 214void
fb40c209
AC
215mi_cmd_break_watch (char *command, char **argv, int argc)
216{
217 char *expr = NULL;
218 enum wp_type type = REG_WP;
219 enum opt
220 {
221 READ_OPT, ACCESS_OPT
222 };
91174723 223 static const struct mi_opt opts[] =
fb40c209
AC
224 {
225 {"r", READ_OPT, 0},
226 {"a", ACCESS_OPT, 0},
d5d6fca5 227 { 0, 0, 0 }
fb40c209
AC
228 };
229
230 /* Parse arguments. */
f8c000a2
AS
231 int oind = 0;
232 char *oarg;
102040f0 233
fb40c209
AC
234 while (1)
235 {
1b05df00 236 int opt = mi_getopt ("-break-watch", argc, argv,
f8c000a2 237 opts, &oind, &oarg);
102040f0 238
fb40c209
AC
239 if (opt < 0)
240 break;
241 switch ((enum opt) opt)
242 {
243 case READ_OPT:
244 type = READ_WP;
245 break;
246 case ACCESS_OPT:
247 type = ACCESS_WP;
248 break;
249 }
250 }
f8c000a2 251 if (oind >= argc)
1b05df00 252 error (_("-break-watch: Missing <expression>"));
f8c000a2 253 if (oind < argc - 1)
1b05df00 254 error (_("-break-watch: Garbage following <expression>"));
f8c000a2 255 expr = argv[oind];
fb40c209 256
2b03b41d 257 /* Now we have what we need, let's insert the watchpoint! */
fb40c209
AC
258 switch (type)
259 {
260 case REG_WP:
84f4c1fe 261 watch_command_wrapper (expr, FROM_TTY, 0);
fb40c209
AC
262 break;
263 case READ_WP:
84f4c1fe 264 rwatch_command_wrapper (expr, FROM_TTY, 0);
fb40c209
AC
265 break;
266 case ACCESS_WP:
84f4c1fe 267 awatch_command_wrapper (expr, FROM_TTY, 0);
fb40c209
AC
268 break;
269 default:
1b05df00 270 error (_("-break-watch: Unknown watchpoint type."));
fb40c209 271 }
fb40c209 272}
48cb2d85
VP
273
274/* The mi_read_next_line consults these variable to return successive
275 command lines. While it would be clearer to use a closure pointer,
276 it is not expected that any future code will use read_command_lines_1,
277 therefore no point of overengineering. */
278
279static char **mi_command_line_array;
280static int mi_command_line_array_cnt;
281static int mi_command_line_array_ptr;
282
283static char *
a58d7472 284mi_read_next_line (void)
48cb2d85
VP
285{
286 if (mi_command_line_array_ptr == mi_command_line_array_cnt)
287 return NULL;
288 else
289 return mi_command_line_array[mi_command_line_array_ptr++];
290}
291
292void
293mi_cmd_break_commands (char *command, char **argv, int argc)
294{
295 struct command_line *break_command;
296 char *endptr;
297 int bnum;
298 struct breakpoint *b;
299
300 if (argc < 1)
9b20d036 301 error (_("USAGE: %s <BKPT> [<COMMAND> [<COMMAND>...]]"), command);
48cb2d85
VP
302
303 bnum = strtol (argv[0], &endptr, 0);
304 if (endptr == argv[0])
9b20d036 305 error (_("breakpoint number argument \"%s\" is not a number."),
48cb2d85
VP
306 argv[0]);
307 else if (*endptr != '\0')
9b20d036 308 error (_("junk at the end of breakpoint number argument \"%s\"."),
48cb2d85
VP
309 argv[0]);
310
311 b = get_breakpoint (bnum);
312 if (b == NULL)
9b20d036 313 error (_("breakpoint %d not found."), bnum);
48cb2d85
VP
314
315 mi_command_line_array = argv;
316 mi_command_line_array_ptr = 1;
317 mi_command_line_array_cnt = argc;
318
d77f58be 319 if (is_tracepoint (b))
a7bdde9e
VP
320 break_command = read_command_lines_1 (mi_read_next_line, 1,
321 check_tracepoint_command, b);
322 else
323 break_command = read_command_lines_1 (mi_read_next_line, 1, 0, 0);
324
48cb2d85
VP
325 breakpoint_set_commands (b, break_command);
326}
327
This page took 1.484744 seconds and 4 git commands to generate.