blob: 9dd532be37c0ee300b9514841d7c53bff886c19a [file] [log] [blame]
Chris Lattner24943d22010-06-08 16:52:24 +00001//===-- CommandObjectBreakpoint.cpp -----------------------------*- C++ -*-===//
2//
3// The LLVM Compiler Infrastructure
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
9
10#include "CommandObjectBreakpoint.h"
11#include "CommandObjectBreakpointCommand.h"
12
13// C Includes
14// C++ Includes
15// Other libraries and framework includes
16// Project includes
17#include "lldb/Breakpoint/Breakpoint.h"
18#include "lldb/Breakpoint/BreakpointIDList.h"
19#include "lldb/Breakpoint/BreakpointLocation.h"
Jim Ingham84cdc152010-06-15 19:49:27 +000020#include "lldb/Interpreter/Options.h"
Chris Lattner24943d22010-06-08 16:52:24 +000021#include "lldb/Core/RegularExpression.h"
22#include "lldb/Core/StreamString.h"
23#include "lldb/Interpreter/CommandInterpreter.h"
24#include "lldb/Interpreter/CommandReturnObject.h"
25#include "lldb/Target/Target.h"
26#include "lldb/Interpreter/CommandCompletions.h"
27#include "lldb/Target/StackFrame.h"
Jim Ingham3c7b5b92010-06-16 02:00:15 +000028#include "lldb/Target/Thread.h"
29#include "lldb/Target/ThreadSpec.h"
Chris Lattner24943d22010-06-08 16:52:24 +000030
Johnny Chena62ad7c2010-10-28 17:27:46 +000031#include <vector>
32
Chris Lattner24943d22010-06-08 16:52:24 +000033using namespace lldb;
34using namespace lldb_private;
35
36static void
Jim Ingham2e8cb8a2011-02-19 02:53:09 +000037AddBreakpointDescription (Stream *s, Breakpoint *bp, lldb::DescriptionLevel level)
Chris Lattner24943d22010-06-08 16:52:24 +000038{
39 s->IndentMore();
40 bp->GetDescription (s, level, true);
41 s->IndentLess();
42 s->EOL();
43}
44
45//-------------------------------------------------------------------------
46// CommandObjectBreakpointSet::CommandOptions
47//-------------------------------------------------------------------------
Jim Ingham10622a22010-06-18 00:58:52 +000048#pragma mark Set::CommandOptions
Chris Lattner24943d22010-06-08 16:52:24 +000049
Greg Claytonf15996e2011-04-07 22:46:35 +000050CommandObjectBreakpointSet::CommandOptions::CommandOptions(CommandInterpreter &interpreter) :
51 Options (interpreter),
Chris Lattner24943d22010-06-08 16:52:24 +000052 m_filename (),
53 m_line_num (0),
54 m_column (0),
Greg Clayton2dfe4c62010-11-02 03:02:38 +000055 m_check_inlines (true),
Chris Lattner24943d22010-06-08 16:52:24 +000056 m_func_name (),
Greg Clayton12bec712010-06-28 21:30:43 +000057 m_func_name_type_mask (0),
Chris Lattner24943d22010-06-08 16:52:24 +000058 m_func_regexp (),
59 m_modules (),
Jim Ingham3c7b5b92010-06-16 02:00:15 +000060 m_load_addr(),
Greg Clayton54e7afa2010-07-09 20:39:50 +000061 m_ignore_count (0),
Jim Ingham3c7b5b92010-06-16 02:00:15 +000062 m_thread_id(LLDB_INVALID_THREAD_ID),
Greg Clayton54e7afa2010-07-09 20:39:50 +000063 m_thread_index (UINT32_MAX),
Jim Ingham3c7b5b92010-06-16 02:00:15 +000064 m_thread_name(),
Greg Clayton54e7afa2010-07-09 20:39:50 +000065 m_queue_name()
Chris Lattner24943d22010-06-08 16:52:24 +000066{
Chris Lattner24943d22010-06-08 16:52:24 +000067}
68
69CommandObjectBreakpointSet::CommandOptions::~CommandOptions ()
70{
71}
72
Greg Claytonb3448432011-03-24 21:19:54 +000073OptionDefinition
Chris Lattner24943d22010-06-08 16:52:24 +000074CommandObjectBreakpointSet::CommandOptions::g_option_table[] =
75{
Caroline Tice4d6675c2010-10-01 19:59:14 +000076 { LLDB_OPT_SET_ALL, false, "shlib", 's', required_argument, NULL, CommandCompletions::eModuleCompletion, eArgTypeShlibName,
Jim Ingham34e9a982010-06-15 18:47:14 +000077 "Set the breakpoint only in this shared library (can use this option multiple times for multiple shlibs)."},
78
Caroline Tice4d6675c2010-10-01 19:59:14 +000079 { LLDB_OPT_SET_ALL, false, "ignore-count", 'i', required_argument, NULL, 0, eArgTypeCount,
80 "Set the number of times this breakpoint is skipped before stopping." },
Jim Ingham3c7b5b92010-06-16 02:00:15 +000081
Caroline Tice4d6675c2010-10-01 19:59:14 +000082 { LLDB_OPT_SET_ALL, false, "thread-index", 'x', required_argument, NULL, NULL, eArgTypeThreadIndex,
Greg Claytonfe424a92010-09-18 03:37:20 +000083 "The breakpoint stops only for the thread whose index matches this argument."},
Jim Ingham3c7b5b92010-06-16 02:00:15 +000084
Caroline Tice4d6675c2010-10-01 19:59:14 +000085 { LLDB_OPT_SET_ALL, false, "thread-id", 't', required_argument, NULL, NULL, eArgTypeThreadID,
Jim Ingham3c7b5b92010-06-16 02:00:15 +000086 "The breakpoint stops only for the thread whose TID matches this argument."},
87
Caroline Tice4d6675c2010-10-01 19:59:14 +000088 { LLDB_OPT_SET_ALL, false, "thread-name", 'T', required_argument, NULL, NULL, eArgTypeThreadName,
Jim Ingham3c7b5b92010-06-16 02:00:15 +000089 "The breakpoint stops only for the thread whose thread name matches this argument."},
90
Caroline Tice4d6675c2010-10-01 19:59:14 +000091 { LLDB_OPT_SET_ALL, false, "queue-name", 'q', required_argument, NULL, NULL, eArgTypeQueueName,
Jim Ingham3c7b5b92010-06-16 02:00:15 +000092 "The breakpoint stops only for threads in the queue whose name is given by this argument."},
93
Caroline Tice4d6675c2010-10-01 19:59:14 +000094 { LLDB_OPT_SET_1, false, "file", 'f', required_argument, NULL, CommandCompletions::eSourceFileCompletion, eArgTypeFilename,
Chris Lattner24943d22010-06-08 16:52:24 +000095 "Set the breakpoint by source location in this particular file."},
96
Caroline Tice4d6675c2010-10-01 19:59:14 +000097 { LLDB_OPT_SET_1, true, "line", 'l', required_argument, NULL, 0, eArgTypeLineNum,
Chris Lattner24943d22010-06-08 16:52:24 +000098 "Set the breakpoint by source location at this particular line."},
99
Chris Lattner24943d22010-06-08 16:52:24 +0000100 // Comment out this option for the moment, as we don't actually use it, but will in the future.
101 // This way users won't see it, but the infrastructure is left in place.
102 // { 0, false, "column", 'c', required_argument, NULL, "<column>",
103 // "Set the breakpoint by source location at this particular column."},
104
Caroline Tice4d6675c2010-10-01 19:59:14 +0000105 { LLDB_OPT_SET_2, true, "address", 'a', required_argument, NULL, 0, eArgTypeAddress,
Chris Lattner24943d22010-06-08 16:52:24 +0000106 "Set the breakpoint by address, at the specified address."},
107
Caroline Tice4d6675c2010-10-01 19:59:14 +0000108 { LLDB_OPT_SET_3, true, "name", 'n', required_argument, NULL, CommandCompletions::eSymbolCompletion, eArgTypeFunctionName,
Greg Clayton48fbdf72010-10-12 04:29:14 +0000109 "Set the breakpoint by function name." },
Chris Lattner24943d22010-06-08 16:52:24 +0000110
Caroline Tice4d6675c2010-10-01 19:59:14 +0000111 { LLDB_OPT_SET_4, true, "fullname", 'F', required_argument, NULL, CommandCompletions::eSymbolCompletion, eArgTypeFullName,
Jim Inghamd9e2b762010-08-26 23:56:11 +0000112 "Set the breakpoint by fully qualified function names. For C++ this means namespaces and all arguemnts, and "
113 "for Objective C this means a full function prototype with class and selector." },
Greg Clayton12bec712010-06-28 21:30:43 +0000114
Caroline Tice4d6675c2010-10-01 19:59:14 +0000115 { LLDB_OPT_SET_5, true, "selector", 'S', required_argument, NULL, 0, eArgTypeSelector,
Jim Inghamd9e2b762010-08-26 23:56:11 +0000116 "Set the breakpoint by ObjC selector name." },
Greg Clayton12bec712010-06-28 21:30:43 +0000117
Caroline Tice4d6675c2010-10-01 19:59:14 +0000118 { LLDB_OPT_SET_6, true, "method", 'M', required_argument, NULL, 0, eArgTypeMethod,
Jim Inghamd9e2b762010-08-26 23:56:11 +0000119 "Set the breakpoint by C++ method names." },
Greg Clayton12bec712010-06-28 21:30:43 +0000120
Caroline Tice4d6675c2010-10-01 19:59:14 +0000121 { LLDB_OPT_SET_7, true, "func-regex", 'r', required_argument, NULL, 0, eArgTypeRegularExpression,
Chris Lattner24943d22010-06-08 16:52:24 +0000122 "Set the breakpoint by function name, evaluating a regular-expression to find the function name(s)." },
123
Greg Clayton48fbdf72010-10-12 04:29:14 +0000124 { LLDB_OPT_SET_8, true, "basename", 'b', required_argument, NULL, CommandCompletions::eSymbolCompletion, eArgTypeFunctionName,
125 "Set the breakpoint by function basename (C++ namespaces and arguments will be ignored)." },
126
Caroline Tice4d6675c2010-10-01 19:59:14 +0000127 { 0, false, NULL, 0, 0, NULL, 0, eArgTypeNone, NULL }
Chris Lattner24943d22010-06-08 16:52:24 +0000128};
129
Greg Claytonb3448432011-03-24 21:19:54 +0000130const OptionDefinition*
Chris Lattner24943d22010-06-08 16:52:24 +0000131CommandObjectBreakpointSet::CommandOptions::GetDefinitions ()
132{
133 return g_option_table;
134}
135
136Error
Greg Clayton143fcc32011-04-13 00:18:08 +0000137CommandObjectBreakpointSet::CommandOptions::SetOptionValue (uint32_t option_idx, const char *option_arg)
Chris Lattner24943d22010-06-08 16:52:24 +0000138{
139 Error error;
140 char short_option = (char) m_getopt_table[option_idx].val;
141
142 switch (short_option)
143 {
144 case 'a':
Jim Ingham7a4c8ea2011-03-22 01:53:33 +0000145 m_load_addr = Args::StringToUInt64(option_arg, LLDB_INVALID_ADDRESS, 0);
Chris Lattner24943d22010-06-08 16:52:24 +0000146 if (m_load_addr == LLDB_INVALID_ADDRESS)
Jim Ingham7a4c8ea2011-03-22 01:53:33 +0000147 m_load_addr = Args::StringToUInt64(option_arg, LLDB_INVALID_ADDRESS, 16);
Chris Lattner24943d22010-06-08 16:52:24 +0000148
149 if (m_load_addr == LLDB_INVALID_ADDRESS)
Jim Ingham7a4c8ea2011-03-22 01:53:33 +0000150 error.SetErrorStringWithFormat ("Invalid address string '%s'.\n", option_arg);
Chris Lattner24943d22010-06-08 16:52:24 +0000151 break;
152
153 case 'c':
154 m_column = Args::StringToUInt32 (option_arg, 0);
155 break;
Greg Clayton12bec712010-06-28 21:30:43 +0000156
Chris Lattner24943d22010-06-08 16:52:24 +0000157 case 'f':
Greg Clayton889fbd02011-03-26 19:14:58 +0000158 m_filename.assign (option_arg);
Chris Lattner24943d22010-06-08 16:52:24 +0000159 break;
Greg Clayton12bec712010-06-28 21:30:43 +0000160
Chris Lattner24943d22010-06-08 16:52:24 +0000161 case 'l':
162 m_line_num = Args::StringToUInt32 (option_arg, 0);
163 break;
Greg Clayton12bec712010-06-28 21:30:43 +0000164
Greg Clayton48fbdf72010-10-12 04:29:14 +0000165 case 'b':
Greg Clayton889fbd02011-03-26 19:14:58 +0000166 m_func_name.assign (option_arg);
Greg Clayton12bec712010-06-28 21:30:43 +0000167 m_func_name_type_mask |= eFunctionNameTypeBase;
168 break;
169
Greg Clayton48fbdf72010-10-12 04:29:14 +0000170 case 'n':
Greg Clayton889fbd02011-03-26 19:14:58 +0000171 m_func_name.assign (option_arg);
Greg Clayton48fbdf72010-10-12 04:29:14 +0000172 m_func_name_type_mask |= eFunctionNameTypeAuto;
173 break;
174
Greg Clayton12bec712010-06-28 21:30:43 +0000175 case 'F':
Greg Clayton889fbd02011-03-26 19:14:58 +0000176 m_func_name.assign (option_arg);
Greg Clayton12bec712010-06-28 21:30:43 +0000177 m_func_name_type_mask |= eFunctionNameTypeFull;
178 break;
179
180 case 'S':
Greg Clayton889fbd02011-03-26 19:14:58 +0000181 m_func_name.assign (option_arg);
Greg Clayton12bec712010-06-28 21:30:43 +0000182 m_func_name_type_mask |= eFunctionNameTypeSelector;
183 break;
184
Jim Inghamd9e2b762010-08-26 23:56:11 +0000185 case 'M':
Greg Clayton889fbd02011-03-26 19:14:58 +0000186 m_func_name.assign (option_arg);
Greg Clayton12bec712010-06-28 21:30:43 +0000187 m_func_name_type_mask |= eFunctionNameTypeMethod;
188 break;
189
Chris Lattner24943d22010-06-08 16:52:24 +0000190 case 'r':
Greg Clayton889fbd02011-03-26 19:14:58 +0000191 m_func_regexp.assign (option_arg);
Chris Lattner24943d22010-06-08 16:52:24 +0000192 break;
Greg Clayton12bec712010-06-28 21:30:43 +0000193
Chris Lattner24943d22010-06-08 16:52:24 +0000194 case 's':
195 {
196 m_modules.push_back (std::string (option_arg));
197 break;
198 }
Greg Claytonfe424a92010-09-18 03:37:20 +0000199 case 'i':
Jim Ingham3c7b5b92010-06-16 02:00:15 +0000200 {
Jim Ingham7a4c8ea2011-03-22 01:53:33 +0000201 m_ignore_count = Args::StringToUInt32(option_arg, UINT32_MAX, 0);
Greg Clayton54e7afa2010-07-09 20:39:50 +0000202 if (m_ignore_count == UINT32_MAX)
Jim Ingham7a4c8ea2011-03-22 01:53:33 +0000203 error.SetErrorStringWithFormat ("Invalid ignore count '%s'.\n", option_arg);
Jim Ingham3c7b5b92010-06-16 02:00:15 +0000204 }
Jim Ingham10622a22010-06-18 00:58:52 +0000205 break;
Jim Ingham3c7b5b92010-06-16 02:00:15 +0000206 case 't' :
207 {
Jim Ingham7a4c8ea2011-03-22 01:53:33 +0000208 m_thread_id = Args::StringToUInt64(option_arg, LLDB_INVALID_THREAD_ID, 0);
Jim Ingham3c7b5b92010-06-16 02:00:15 +0000209 if (m_thread_id == LLDB_INVALID_THREAD_ID)
Jim Ingham7a4c8ea2011-03-22 01:53:33 +0000210 error.SetErrorStringWithFormat ("Invalid thread id string '%s'.\n", option_arg);
Jim Ingham3c7b5b92010-06-16 02:00:15 +0000211 }
212 break;
213 case 'T':
Greg Clayton889fbd02011-03-26 19:14:58 +0000214 m_thread_name.assign (option_arg);
Jim Ingham3c7b5b92010-06-16 02:00:15 +0000215 break;
216 case 'q':
Greg Clayton889fbd02011-03-26 19:14:58 +0000217 m_queue_name.assign (option_arg);
Jim Ingham3c7b5b92010-06-16 02:00:15 +0000218 break;
219 case 'x':
220 {
Jim Ingham7a4c8ea2011-03-22 01:53:33 +0000221 m_thread_index = Args::StringToUInt32(option_arg, UINT32_MAX, 0);
Greg Clayton54e7afa2010-07-09 20:39:50 +0000222 if (m_thread_id == UINT32_MAX)
Jim Ingham7a4c8ea2011-03-22 01:53:33 +0000223 error.SetErrorStringWithFormat ("Invalid thread index string '%s'.\n", option_arg);
Jim Ingham3c7b5b92010-06-16 02:00:15 +0000224
225 }
226 break;
Chris Lattner24943d22010-06-08 16:52:24 +0000227 default:
228 error.SetErrorStringWithFormat ("Unrecognized option '%c'.\n", short_option);
229 break;
230 }
231
232 return error;
233}
234
235void
Greg Clayton143fcc32011-04-13 00:18:08 +0000236CommandObjectBreakpointSet::CommandOptions::OptionParsingStarting ()
Chris Lattner24943d22010-06-08 16:52:24 +0000237{
Chris Lattner24943d22010-06-08 16:52:24 +0000238 m_filename.clear();
239 m_line_num = 0;
240 m_column = 0;
Chris Lattner24943d22010-06-08 16:52:24 +0000241 m_func_name.clear();
Greg Clayton12bec712010-06-28 21:30:43 +0000242 m_func_name_type_mask = 0;
Chris Lattner24943d22010-06-08 16:52:24 +0000243 m_func_regexp.clear();
244 m_load_addr = LLDB_INVALID_ADDRESS;
245 m_modules.clear();
Greg Clayton54e7afa2010-07-09 20:39:50 +0000246 m_ignore_count = 0;
Jim Ingham3c7b5b92010-06-16 02:00:15 +0000247 m_thread_id = LLDB_INVALID_THREAD_ID;
Greg Clayton54e7afa2010-07-09 20:39:50 +0000248 m_thread_index = UINT32_MAX;
Jim Ingham3c7b5b92010-06-16 02:00:15 +0000249 m_thread_name.clear();
250 m_queue_name.clear();
Chris Lattner24943d22010-06-08 16:52:24 +0000251}
252
253//-------------------------------------------------------------------------
254// CommandObjectBreakpointSet
255//-------------------------------------------------------------------------
Jim Ingham10622a22010-06-18 00:58:52 +0000256#pragma mark Set
Chris Lattner24943d22010-06-08 16:52:24 +0000257
Greg Clayton238c0a12010-09-18 01:14:36 +0000258CommandObjectBreakpointSet::CommandObjectBreakpointSet (CommandInterpreter &interpreter) :
259 CommandObject (interpreter,
260 "breakpoint set",
261 "Sets a breakpoint or set of breakpoints in the executable.",
Greg Claytonf15996e2011-04-07 22:46:35 +0000262 "breakpoint set <cmd-options>"),
263 m_options (interpreter)
Chris Lattner24943d22010-06-08 16:52:24 +0000264{
265}
266
267CommandObjectBreakpointSet::~CommandObjectBreakpointSet ()
268{
269}
270
271Options *
272CommandObjectBreakpointSet::GetOptions ()
273{
274 return &m_options;
275}
276
277bool
278CommandObjectBreakpointSet::Execute
279(
280 Args& command,
Chris Lattner24943d22010-06-08 16:52:24 +0000281 CommandReturnObject &result
282)
283{
Greg Clayton238c0a12010-09-18 01:14:36 +0000284 Target *target = m_interpreter.GetDebugger().GetSelectedTarget().get();
Chris Lattner24943d22010-06-08 16:52:24 +0000285 if (target == NULL)
286 {
Greg Claytone1f50b92011-05-03 22:09:39 +0000287 result.AppendError ("Invalid target. Must set target before setting breakpoints (see 'target create' command).");
Chris Lattner24943d22010-06-08 16:52:24 +0000288 result.SetStatus (eReturnStatusFailed);
289 return false;
290 }
291
292 // The following are the various types of breakpoints that could be set:
293 // 1). -f -l -p [-s -g] (setting breakpoint by source location)
294 // 2). -a [-s -g] (setting breakpoint by address)
295 // 3). -n [-s -g] (setting breakpoint by function name)
296 // 4). -r [-s -g] (setting breakpoint by function name regular expression)
297
298 BreakpointSetType break_type = eSetTypeInvalid;
299
300 if (m_options.m_line_num != 0)
301 break_type = eSetTypeFileAndLine;
302 else if (m_options.m_load_addr != LLDB_INVALID_ADDRESS)
303 break_type = eSetTypeAddress;
304 else if (!m_options.m_func_name.empty())
305 break_type = eSetTypeFunctionName;
306 else if (!m_options.m_func_regexp.empty())
307 break_type = eSetTypeFunctionRegexp;
308
309 ModuleSP module_sp = target->GetExecutableModule();
310 Breakpoint *bp = NULL;
Greg Clayton537a7a82010-10-20 20:54:39 +0000311 FileSpec module_spec;
Chris Lattner24943d22010-06-08 16:52:24 +0000312 bool use_module = false;
313 int num_modules = m_options.m_modules.size();
314
315 if ((num_modules > 0) && (break_type != eSetTypeAddress))
316 use_module = true;
Jim Ingham3c7b5b92010-06-16 02:00:15 +0000317
Chris Lattner24943d22010-06-08 16:52:24 +0000318 switch (break_type)
319 {
320 case eSetTypeFileAndLine: // Breakpoint by source position
Chris Lattner24943d22010-06-08 16:52:24 +0000321 {
Greg Clayton887aa282010-10-11 01:05:37 +0000322 FileSpec file;
323 if (m_options.m_filename.empty())
Chris Lattner24943d22010-06-08 16:52:24 +0000324 {
Greg Claytonb72d0f02011-04-12 05:54:46 +0000325 StackFrame *cur_frame = m_interpreter.GetExecutionContext().frame;
Greg Clayton887aa282010-10-11 01:05:37 +0000326 if (cur_frame == NULL)
Chris Lattner24943d22010-06-08 16:52:24 +0000327 {
Greg Clayton887aa282010-10-11 01:05:37 +0000328 result.AppendError ("Attempting to set breakpoint by line number alone with no selected frame.");
Chris Lattner24943d22010-06-08 16:52:24 +0000329 result.SetStatus (eReturnStatusFailed);
330 break;
331 }
Greg Clayton887aa282010-10-11 01:05:37 +0000332 else if (!cur_frame->HasDebugInformation())
Chris Lattner24943d22010-06-08 16:52:24 +0000333 {
Greg Clayton887aa282010-10-11 01:05:37 +0000334 result.AppendError ("Attempting to set breakpoint by line number alone but selected frame has no debug info.");
335 result.SetStatus (eReturnStatusFailed);
336 break;
Chris Lattner24943d22010-06-08 16:52:24 +0000337 }
338 else
339 {
Greg Clayton52c8b6e2011-04-19 04:19:37 +0000340 const SymbolContext &sc = cur_frame->GetSymbolContext (eSymbolContextLineEntry);
341 if (sc.line_entry.file)
Greg Clayton887aa282010-10-11 01:05:37 +0000342 {
Greg Clayton52c8b6e2011-04-19 04:19:37 +0000343 file = sc.line_entry.file;
Greg Clayton887aa282010-10-11 01:05:37 +0000344 }
345 else
346 {
347 result.AppendError ("Attempting to set breakpoint by line number alone but can't find the file for the selected frame.");
348 result.SetStatus (eReturnStatusFailed);
349 break;
350 }
Chris Lattner24943d22010-06-08 16:52:24 +0000351 }
352 }
Greg Clayton887aa282010-10-11 01:05:37 +0000353 else
354 {
Greg Clayton537a7a82010-10-20 20:54:39 +0000355 file.SetFile(m_options.m_filename.c_str(), false);
Greg Clayton887aa282010-10-11 01:05:37 +0000356 }
357
358 if (use_module)
359 {
360 for (int i = 0; i < num_modules; ++i)
361 {
Greg Clayton537a7a82010-10-20 20:54:39 +0000362 module_spec.SetFile(m_options.m_modules[i].c_str(), false);
363 bp = target->CreateBreakpoint (&module_spec,
Greg Clayton887aa282010-10-11 01:05:37 +0000364 file,
365 m_options.m_line_num,
Greg Clayton2dfe4c62010-11-02 03:02:38 +0000366 m_options.m_check_inlines).get();
Greg Clayton887aa282010-10-11 01:05:37 +0000367 if (bp)
368 {
Jim Ingham2e8cb8a2011-02-19 02:53:09 +0000369 Stream &output_stream = result.GetOutputStream();
370 result.AppendMessage ("Breakpoint created: ");
Greg Clayton887aa282010-10-11 01:05:37 +0000371 bp->GetDescription(&output_stream, lldb::eDescriptionLevelBrief);
372 output_stream.EOL();
Caroline Ticecf2f3052010-10-28 16:28:56 +0000373 if (bp->GetNumLocations() == 0)
374 output_stream.Printf ("WARNING: Unable to resolve breakpoint to any actual"
375 " locations.\n");
Greg Clayton887aa282010-10-11 01:05:37 +0000376 result.SetStatus (eReturnStatusSuccessFinishResult);
377 }
378 else
379 {
380 result.AppendErrorWithFormat("Breakpoint creation failed: No breakpoint created in module '%s'.\n",
381 m_options.m_modules[i].c_str());
382 result.SetStatus (eReturnStatusFailed);
383 }
384 }
385 }
386 else
387 bp = target->CreateBreakpoint (NULL,
388 file,
389 m_options.m_line_num,
Greg Clayton2dfe4c62010-11-02 03:02:38 +0000390 m_options.m_check_inlines).get();
Chris Lattner24943d22010-06-08 16:52:24 +0000391 }
Greg Clayton887aa282010-10-11 01:05:37 +0000392 break;
393
Chris Lattner24943d22010-06-08 16:52:24 +0000394 case eSetTypeAddress: // Breakpoint by address
395 bp = target->CreateBreakpoint (m_options.m_load_addr, false).get();
396 break;
Greg Clayton12bec712010-06-28 21:30:43 +0000397
Chris Lattner24943d22010-06-08 16:52:24 +0000398 case eSetTypeFunctionName: // Breakpoint by function name
Chris Lattner24943d22010-06-08 16:52:24 +0000399 {
Greg Clayton12bec712010-06-28 21:30:43 +0000400 uint32_t name_type_mask = m_options.m_func_name_type_mask;
401
402 if (name_type_mask == 0)
Greg Clayton48fbdf72010-10-12 04:29:14 +0000403 name_type_mask = eFunctionNameTypeAuto;
404
Greg Clayton12bec712010-06-28 21:30:43 +0000405 if (use_module)
406 {
407 for (int i = 0; i < num_modules; ++i)
Chris Lattner24943d22010-06-08 16:52:24 +0000408 {
Greg Clayton537a7a82010-10-20 20:54:39 +0000409 module_spec.SetFile(m_options.m_modules[i].c_str(), false);
410 bp = target->CreateBreakpoint (&module_spec,
411 m_options.m_func_name.c_str(),
412 name_type_mask,
413 Breakpoint::Exact).get();
Greg Clayton12bec712010-06-28 21:30:43 +0000414 if (bp)
415 {
Jim Ingham2e8cb8a2011-02-19 02:53:09 +0000416 Stream &output_stream = result.GetOutputStream();
Greg Clayton12bec712010-06-28 21:30:43 +0000417 output_stream.Printf ("Breakpoint created: ");
418 bp->GetDescription(&output_stream, lldb::eDescriptionLevelBrief);
419 output_stream.EOL();
Caroline Ticecf2f3052010-10-28 16:28:56 +0000420 if (bp->GetNumLocations() == 0)
421 output_stream.Printf ("WARNING: Unable to resolve breakpoint to any actual"
422 " locations.\n");
Greg Clayton12bec712010-06-28 21:30:43 +0000423 result.SetStatus (eReturnStatusSuccessFinishResult);
424 }
425 else
426 {
427 result.AppendErrorWithFormat("Breakpoint creation failed: No breakpoint created in module '%s'.\n",
428 m_options.m_modules[i].c_str());
429 result.SetStatus (eReturnStatusFailed);
430 }
Chris Lattner24943d22010-06-08 16:52:24 +0000431 }
432 }
Greg Clayton12bec712010-06-28 21:30:43 +0000433 else
434 bp = target->CreateBreakpoint (NULL, m_options.m_func_name.c_str(), name_type_mask, Breakpoint::Exact).get();
Chris Lattner24943d22010-06-08 16:52:24 +0000435 }
Chris Lattner24943d22010-06-08 16:52:24 +0000436 break;
Greg Clayton12bec712010-06-28 21:30:43 +0000437
Chris Lattner24943d22010-06-08 16:52:24 +0000438 case eSetTypeFunctionRegexp: // Breakpoint by regular expression function name
439 {
440 RegularExpression regexp(m_options.m_func_regexp.c_str());
441 if (use_module)
442 {
443 for (int i = 0; i < num_modules; ++i)
444 {
Greg Clayton537a7a82010-10-20 20:54:39 +0000445 module_spec.SetFile(m_options.m_modules[i].c_str(), false);
446 bp = target->CreateBreakpoint (&module_spec, regexp).get();
Chris Lattner24943d22010-06-08 16:52:24 +0000447 if (bp)
448 {
Jim Ingham2e8cb8a2011-02-19 02:53:09 +0000449 Stream &output_stream = result.GetOutputStream();
Chris Lattner24943d22010-06-08 16:52:24 +0000450 output_stream.Printf ("Breakpoint created: ");
451 bp->GetDescription(&output_stream, lldb::eDescriptionLevelBrief);
452 output_stream.EOL();
Caroline Ticecf2f3052010-10-28 16:28:56 +0000453 if (bp->GetNumLocations() == 0)
454 output_stream.Printf ("WARNING: Unable to resolve breakpoint to any actual"
455 " locations.\n");
Chris Lattner24943d22010-06-08 16:52:24 +0000456 result.SetStatus (eReturnStatusSuccessFinishResult);
457 }
458 else
459 {
460 result.AppendErrorWithFormat("Breakpoint creation failed: No breakpoint created in module '%s'.\n",
461 m_options.m_modules[i].c_str());
462 result.SetStatus (eReturnStatusFailed);
463 }
464 }
465 }
466 else
467 bp = target->CreateBreakpoint (NULL, regexp).get();
468 }
469 break;
Greg Clayton12bec712010-06-28 21:30:43 +0000470
Chris Lattner24943d22010-06-08 16:52:24 +0000471 default:
472 break;
473 }
474
Jim Ingham3c7b5b92010-06-16 02:00:15 +0000475 // Now set the various options that were passed in:
476 if (bp)
477 {
478 if (m_options.m_thread_id != LLDB_INVALID_THREAD_ID)
479 bp->SetThreadID (m_options.m_thread_id);
480
Greg Clayton54e7afa2010-07-09 20:39:50 +0000481 if (m_options.m_thread_index != UINT32_MAX)
Jim Ingham3c7b5b92010-06-16 02:00:15 +0000482 bp->GetOptions()->GetThreadSpec()->SetIndex(m_options.m_thread_index);
483
484 if (!m_options.m_thread_name.empty())
485 bp->GetOptions()->GetThreadSpec()->SetName(m_options.m_thread_name.c_str());
486
487 if (!m_options.m_queue_name.empty())
488 bp->GetOptions()->GetThreadSpec()->SetQueueName(m_options.m_queue_name.c_str());
489
Greg Clayton54e7afa2010-07-09 20:39:50 +0000490 if (m_options.m_ignore_count != 0)
Jim Ingham3c7b5b92010-06-16 02:00:15 +0000491 bp->GetOptions()->SetIgnoreCount(m_options.m_ignore_count);
492 }
493
Chris Lattner24943d22010-06-08 16:52:24 +0000494 if (bp && !use_module)
495 {
Jim Ingham2e8cb8a2011-02-19 02:53:09 +0000496 Stream &output_stream = result.GetOutputStream();
Chris Lattner24943d22010-06-08 16:52:24 +0000497 output_stream.Printf ("Breakpoint created: ");
498 bp->GetDescription(&output_stream, lldb::eDescriptionLevelBrief);
499 output_stream.EOL();
Caroline Ticecf2f3052010-10-28 16:28:56 +0000500 if (bp->GetNumLocations() == 0)
501 output_stream.Printf ("WARNING: Unable to resolve breakpoint to any actual locations.\n");
Chris Lattner24943d22010-06-08 16:52:24 +0000502 result.SetStatus (eReturnStatusSuccessFinishResult);
503 }
504 else if (!bp)
505 {
506 result.AppendError ("Breakpoint creation failed: No breakpoint created.");
507 result.SetStatus (eReturnStatusFailed);
508 }
509
510 return result.Succeeded();
511}
512
Chris Lattner24943d22010-06-08 16:52:24 +0000513//-------------------------------------------------------------------------
514// CommandObjectMultiwordBreakpoint
515//-------------------------------------------------------------------------
Jim Ingham10622a22010-06-18 00:58:52 +0000516#pragma mark MultiwordBreakpoint
Chris Lattner24943d22010-06-08 16:52:24 +0000517
Greg Clayton63094e02010-06-23 01:19:29 +0000518CommandObjectMultiwordBreakpoint::CommandObjectMultiwordBreakpoint (CommandInterpreter &interpreter) :
Greg Clayton238c0a12010-09-18 01:14:36 +0000519 CommandObjectMultiword (interpreter,
520 "breakpoint",
521 "A set of commands for operating on breakpoints. Also see regexp-break.",
522 "breakpoint <command> [<command-options>]")
Chris Lattner24943d22010-06-08 16:52:24 +0000523{
524 bool status;
525
Greg Clayton238c0a12010-09-18 01:14:36 +0000526 CommandObjectSP list_command_object (new CommandObjectBreakpointList (interpreter));
Greg Clayton238c0a12010-09-18 01:14:36 +0000527 CommandObjectSP enable_command_object (new CommandObjectBreakpointEnable (interpreter));
528 CommandObjectSP disable_command_object (new CommandObjectBreakpointDisable (interpreter));
Johnny Chena62ad7c2010-10-28 17:27:46 +0000529 CommandObjectSP clear_command_object (new CommandObjectBreakpointClear (interpreter));
530 CommandObjectSP delete_command_object (new CommandObjectBreakpointDelete (interpreter));
Greg Clayton238c0a12010-09-18 01:14:36 +0000531 CommandObjectSP set_command_object (new CommandObjectBreakpointSet (interpreter));
Chris Lattner24943d22010-06-08 16:52:24 +0000532 CommandObjectSP command_command_object (new CommandObjectBreakpointCommand (interpreter));
Greg Clayton238c0a12010-09-18 01:14:36 +0000533 CommandObjectSP modify_command_object (new CommandObjectBreakpointModify(interpreter));
Chris Lattner24943d22010-06-08 16:52:24 +0000534
Johnny Chena62ad7c2010-10-28 17:27:46 +0000535 list_command_object->SetCommandName ("breakpoint list");
Chris Lattner24943d22010-06-08 16:52:24 +0000536 enable_command_object->SetCommandName("breakpoint enable");
537 disable_command_object->SetCommandName("breakpoint disable");
Johnny Chena62ad7c2010-10-28 17:27:46 +0000538 clear_command_object->SetCommandName("breakpoint clear");
539 delete_command_object->SetCommandName("breakpoint delete");
Jim Ingham10622a22010-06-18 00:58:52 +0000540 set_command_object->SetCommandName("breakpoint set");
Johnny Chena62ad7c2010-10-28 17:27:46 +0000541 command_command_object->SetCommandName ("breakpoint command");
542 modify_command_object->SetCommandName ("breakpoint modify");
Chris Lattner24943d22010-06-08 16:52:24 +0000543
Greg Clayton238c0a12010-09-18 01:14:36 +0000544 status = LoadSubCommand ("list", list_command_object);
545 status = LoadSubCommand ("enable", enable_command_object);
546 status = LoadSubCommand ("disable", disable_command_object);
Johnny Chena62ad7c2010-10-28 17:27:46 +0000547 status = LoadSubCommand ("clear", clear_command_object);
Greg Clayton238c0a12010-09-18 01:14:36 +0000548 status = LoadSubCommand ("delete", delete_command_object);
549 status = LoadSubCommand ("set", set_command_object);
550 status = LoadSubCommand ("command", command_command_object);
551 status = LoadSubCommand ("modify", modify_command_object);
Chris Lattner24943d22010-06-08 16:52:24 +0000552}
553
554CommandObjectMultiwordBreakpoint::~CommandObjectMultiwordBreakpoint ()
555{
556}
557
558void
559CommandObjectMultiwordBreakpoint::VerifyBreakpointIDs (Args &args, Target *target, CommandReturnObject &result,
560 BreakpointIDList *valid_ids)
561{
562 // args can be strings representing 1). integers (for breakpoint ids)
563 // 2). the full breakpoint & location canonical representation
564 // 3). the word "to" or a hyphen, representing a range (in which case there
565 // had *better* be an entry both before & after of one of the first two types.
Jim Inghamd1686902010-10-14 23:45:03 +0000566 // If args is empty, we will use the last created breakpoint (if there is one.)
Chris Lattner24943d22010-06-08 16:52:24 +0000567
568 Args temp_args;
569
Jim Inghamd1686902010-10-14 23:45:03 +0000570 if (args.GetArgumentCount() == 0)
571 {
572 if (target->GetLastCreatedBreakpoint() != NULL)
573 {
574 valid_ids->AddBreakpointID (BreakpointID(target->GetLastCreatedBreakpoint()->GetID(), LLDB_INVALID_BREAK_ID));
575 result.SetStatus (eReturnStatusSuccessFinishNoResult);
576 }
577 else
578 {
579 result.AppendError("No breakpoint specified and no last created breakpoint.");
580 result.SetStatus (eReturnStatusFailed);
581 }
582 return;
583 }
584
Chris Lattner24943d22010-06-08 16:52:24 +0000585 // Create a new Args variable to use; copy any non-breakpoint-id-ranges stuff directly from the old ARGS to
586 // the new TEMP_ARGS. Do not copy breakpoint id range strings over; instead generate a list of strings for
587 // all the breakpoint ids in the range, and shove all of those breakpoint id strings into TEMP_ARGS.
588
589 BreakpointIDList::FindAndReplaceIDRanges (args, target, result, temp_args);
590
591 // NOW, convert the list of breakpoint id strings in TEMP_ARGS into an actual BreakpointIDList:
592
Greg Clayton54e7afa2010-07-09 20:39:50 +0000593 valid_ids->InsertStringArray (temp_args.GetConstArgumentVector(), temp_args.GetArgumentCount(), result);
Chris Lattner24943d22010-06-08 16:52:24 +0000594
595 // At this point, all of the breakpoint ids that the user passed in have been converted to breakpoint IDs
596 // and put into valid_ids.
597
598 if (result.Succeeded())
599 {
600 // Now that we've converted everything from args into a list of breakpoint ids, go through our tentative list
601 // of breakpoint id's and verify that they correspond to valid/currently set breakpoints.
602
Greg Clayton54e7afa2010-07-09 20:39:50 +0000603 const size_t count = valid_ids->GetSize();
604 for (size_t i = 0; i < count; ++i)
Chris Lattner24943d22010-06-08 16:52:24 +0000605 {
606 BreakpointID cur_bp_id = valid_ids->GetBreakpointIDAtIndex (i);
607 Breakpoint *breakpoint = target->GetBreakpointByID (cur_bp_id.GetBreakpointID()).get();
608 if (breakpoint != NULL)
609 {
610 int num_locations = breakpoint->GetNumLocations();
611 if (cur_bp_id.GetLocationID() > num_locations)
612 {
613 StreamString id_str;
Greg Clayton54e7afa2010-07-09 20:39:50 +0000614 BreakpointID::GetCanonicalReference (&id_str,
615 cur_bp_id.GetBreakpointID(),
616 cur_bp_id.GetLocationID());
617 i = valid_ids->GetSize() + 1;
Chris Lattner24943d22010-06-08 16:52:24 +0000618 result.AppendErrorWithFormat ("'%s' is not a currently valid breakpoint/location id.\n",
619 id_str.GetData());
620 result.SetStatus (eReturnStatusFailed);
621 }
622 }
623 else
624 {
Greg Clayton54e7afa2010-07-09 20:39:50 +0000625 i = valid_ids->GetSize() + 1;
Chris Lattner24943d22010-06-08 16:52:24 +0000626 result.AppendErrorWithFormat ("'%d' is not a currently valid breakpoint id.\n", cur_bp_id.GetBreakpointID());
627 result.SetStatus (eReturnStatusFailed);
628 }
629 }
630 }
631}
632
633//-------------------------------------------------------------------------
634// CommandObjectBreakpointList::Options
635//-------------------------------------------------------------------------
Jim Ingham10622a22010-06-18 00:58:52 +0000636#pragma mark List::CommandOptions
Chris Lattner24943d22010-06-08 16:52:24 +0000637
Greg Claytonf15996e2011-04-07 22:46:35 +0000638CommandObjectBreakpointList::CommandOptions::CommandOptions(CommandInterpreter &interpreter) :
639 Options (interpreter),
Caroline Tice41950cc2011-02-04 22:59:41 +0000640 m_level (lldb::eDescriptionLevelBrief) // Breakpoint List defaults to brief descriptions
Chris Lattner24943d22010-06-08 16:52:24 +0000641{
Chris Lattner24943d22010-06-08 16:52:24 +0000642}
643
644CommandObjectBreakpointList::CommandOptions::~CommandOptions ()
645{
646}
647
Greg Claytonb3448432011-03-24 21:19:54 +0000648OptionDefinition
Chris Lattner24943d22010-06-08 16:52:24 +0000649CommandObjectBreakpointList::CommandOptions::g_option_table[] =
650{
Caroline Tice4d6675c2010-10-01 19:59:14 +0000651 { LLDB_OPT_SET_ALL, false, "internal", 'i', no_argument, NULL, 0, eArgTypeNone,
Jim Ingham34e9a982010-06-15 18:47:14 +0000652 "Show debugger internal breakpoints" },
653
Caroline Tice4d6675c2010-10-01 19:59:14 +0000654 { LLDB_OPT_SET_1, false, "brief", 'b', no_argument, NULL, 0, eArgTypeNone,
Chris Lattner24943d22010-06-08 16:52:24 +0000655 "Give a brief description of the breakpoint (no location info)."},
656
657 // FIXME: We need to add an "internal" command, and then add this sort of thing to it.
658 // But I need to see it for now, and don't want to wait.
Caroline Tice4d6675c2010-10-01 19:59:14 +0000659 { LLDB_OPT_SET_2, false, "full", 'f', no_argument, NULL, 0, eArgTypeNone,
Chris Lattner24943d22010-06-08 16:52:24 +0000660 "Give a full description of the breakpoint and its locations."},
Chris Lattner24943d22010-06-08 16:52:24 +0000661
Caroline Tice4d6675c2010-10-01 19:59:14 +0000662 { LLDB_OPT_SET_3, false, "verbose", 'v', no_argument, NULL, 0, eArgTypeNone,
Chris Lattner24943d22010-06-08 16:52:24 +0000663 "Explain everything we know about the breakpoint (for debugging debugger bugs)." },
Chris Lattner24943d22010-06-08 16:52:24 +0000664
Caroline Tice4d6675c2010-10-01 19:59:14 +0000665 { 0, false, NULL, 0, 0, NULL, 0, eArgTypeNone, NULL }
Chris Lattner24943d22010-06-08 16:52:24 +0000666};
667
Greg Claytonb3448432011-03-24 21:19:54 +0000668const OptionDefinition*
Chris Lattner24943d22010-06-08 16:52:24 +0000669CommandObjectBreakpointList::CommandOptions::GetDefinitions ()
670{
671 return g_option_table;
672}
673
674Error
Greg Clayton143fcc32011-04-13 00:18:08 +0000675CommandObjectBreakpointList::CommandOptions::SetOptionValue (uint32_t option_idx, const char *option_arg)
Chris Lattner24943d22010-06-08 16:52:24 +0000676{
677 Error error;
678 char short_option = (char) m_getopt_table[option_idx].val;
679
680 switch (short_option)
681 {
682 case 'b':
683 m_level = lldb::eDescriptionLevelBrief;
684 break;
685 case 'f':
686 m_level = lldb::eDescriptionLevelFull;
687 break;
688 case 'v':
689 m_level = lldb::eDescriptionLevelVerbose;
690 break;
691 case 'i':
692 m_internal = true;
693 break;
694 default:
695 error.SetErrorStringWithFormat ("Unrecognized option '%c'.\n", short_option);
696 break;
697 }
698
699 return error;
700}
701
702void
Greg Clayton143fcc32011-04-13 00:18:08 +0000703CommandObjectBreakpointList::CommandOptions::OptionParsingStarting ()
Chris Lattner24943d22010-06-08 16:52:24 +0000704{
Jim Inghamdc259052011-05-17 01:21:41 +0000705 m_level = lldb::eDescriptionLevelFull;
Chris Lattner24943d22010-06-08 16:52:24 +0000706 m_internal = false;
707}
708
709//-------------------------------------------------------------------------
710// CommandObjectBreakpointList
711//-------------------------------------------------------------------------
Jim Ingham10622a22010-06-18 00:58:52 +0000712#pragma mark List
Chris Lattner24943d22010-06-08 16:52:24 +0000713
Greg Clayton238c0a12010-09-18 01:14:36 +0000714CommandObjectBreakpointList::CommandObjectBreakpointList (CommandInterpreter &interpreter) :
715 CommandObject (interpreter,
716 "breakpoint list",
717 "List some or all breakpoints at configurable levels of detail.",
Greg Claytonf15996e2011-04-07 22:46:35 +0000718 NULL),
719 m_options (interpreter)
Chris Lattner24943d22010-06-08 16:52:24 +0000720{
Caroline Ticefb355112010-10-01 17:46:38 +0000721 CommandArgumentEntry arg;
722 CommandArgumentData bp_id_arg;
723
724 // Define the first (and only) variant of this arg.
725 bp_id_arg.arg_type = eArgTypeBreakpointID;
Caroline Tice43b014a2010-10-04 22:28:36 +0000726 bp_id_arg.arg_repetition = eArgRepeatOptional;
Caroline Ticefb355112010-10-01 17:46:38 +0000727
728 // There is only one variant this argument could be; put it into the argument entry.
729 arg.push_back (bp_id_arg);
730
731 // Push the data for the first argument into the m_arguments vector.
732 m_arguments.push_back (arg);
Chris Lattner24943d22010-06-08 16:52:24 +0000733}
734
735CommandObjectBreakpointList::~CommandObjectBreakpointList ()
736{
737}
738
739Options *
740CommandObjectBreakpointList::GetOptions ()
741{
742 return &m_options;
743}
744
745bool
746CommandObjectBreakpointList::Execute
747(
748 Args& args,
Chris Lattner24943d22010-06-08 16:52:24 +0000749 CommandReturnObject &result
750)
751{
Greg Clayton238c0a12010-09-18 01:14:36 +0000752 Target *target = m_interpreter.GetDebugger().GetSelectedTarget().get();
Chris Lattner24943d22010-06-08 16:52:24 +0000753 if (target == NULL)
754 {
Caroline Tice17dce1c2010-09-29 19:42:33 +0000755 result.AppendError ("Invalid target. No current target or breakpoints.");
Chris Lattner24943d22010-06-08 16:52:24 +0000756 result.SetStatus (eReturnStatusSuccessFinishNoResult);
757 return true;
758 }
759
760 const BreakpointList &breakpoints = target->GetBreakpointList(m_options.m_internal);
Jim Ingham3c7b5b92010-06-16 02:00:15 +0000761 Mutex::Locker locker;
762 target->GetBreakpointList(m_options.m_internal).GetListMutex(locker);
763
Chris Lattner24943d22010-06-08 16:52:24 +0000764 size_t num_breakpoints = breakpoints.GetSize();
765
766 if (num_breakpoints == 0)
767 {
768 result.AppendMessage ("No breakpoints currently set.");
769 result.SetStatus (eReturnStatusSuccessFinishNoResult);
770 return true;
771 }
772
Jim Ingham2e8cb8a2011-02-19 02:53:09 +0000773 Stream &output_stream = result.GetOutputStream();
Chris Lattner24943d22010-06-08 16:52:24 +0000774
775 if (args.GetArgumentCount() == 0)
776 {
777 // No breakpoint selected; show info about all currently set breakpoints.
778 result.AppendMessage ("Current breakpoints:");
Greg Clayton54e7afa2010-07-09 20:39:50 +0000779 for (size_t i = 0; i < num_breakpoints; ++i)
Chris Lattner24943d22010-06-08 16:52:24 +0000780 {
Greg Claytonc7f5d5c2010-07-23 23:33:17 +0000781 Breakpoint *breakpoint = breakpoints.GetBreakpointAtIndex (i).get();
Greg Clayton63094e02010-06-23 01:19:29 +0000782 AddBreakpointDescription (&output_stream, breakpoint, m_options.m_level);
Chris Lattner24943d22010-06-08 16:52:24 +0000783 }
784 result.SetStatus (eReturnStatusSuccessFinishNoResult);
785 }
786 else
787 {
788 // Particular breakpoints selected; show info about that breakpoint.
789 BreakpointIDList valid_bp_ids;
790 CommandObjectMultiwordBreakpoint::VerifyBreakpointIDs (args, target, result, &valid_bp_ids);
791
792 if (result.Succeeded())
793 {
Greg Clayton54e7afa2010-07-09 20:39:50 +0000794 for (size_t i = 0; i < valid_bp_ids.GetSize(); ++i)
Chris Lattner24943d22010-06-08 16:52:24 +0000795 {
796 BreakpointID cur_bp_id = valid_bp_ids.GetBreakpointIDAtIndex (i);
797 Breakpoint *breakpoint = target->GetBreakpointByID (cur_bp_id.GetBreakpointID()).get();
Greg Clayton63094e02010-06-23 01:19:29 +0000798 AddBreakpointDescription (&output_stream, breakpoint, m_options.m_level);
Chris Lattner24943d22010-06-08 16:52:24 +0000799 }
800 result.SetStatus (eReturnStatusSuccessFinishNoResult);
801 }
802 else
803 {
804 result.AppendError ("Invalid breakpoint id.");
805 result.SetStatus (eReturnStatusFailed);
806 }
807 }
808
809 return result.Succeeded();
810}
811
812//-------------------------------------------------------------------------
813// CommandObjectBreakpointEnable
814//-------------------------------------------------------------------------
Jim Ingham10622a22010-06-18 00:58:52 +0000815#pragma mark Enable
Chris Lattner24943d22010-06-08 16:52:24 +0000816
Greg Clayton238c0a12010-09-18 01:14:36 +0000817CommandObjectBreakpointEnable::CommandObjectBreakpointEnable (CommandInterpreter &interpreter) :
818 CommandObject (interpreter,
819 "enable",
Caroline Ticefb355112010-10-01 17:46:38 +0000820 "Enable the specified disabled breakpoint(s). If no breakpoints are specified, enable all of them.",
821 NULL)
Chris Lattner24943d22010-06-08 16:52:24 +0000822{
Caroline Ticefb355112010-10-01 17:46:38 +0000823 CommandArgumentEntry arg;
824 CommandArgumentData bp_id_arg;
825 CommandArgumentData bp_id_range_arg;
826
827 // Create the first variant for the first (and only) argument for this command.
828 bp_id_arg.arg_type = eArgTypeBreakpointID;
Caroline Tice43b014a2010-10-04 22:28:36 +0000829 bp_id_arg.arg_repetition = eArgRepeatOptional;
Caroline Ticefb355112010-10-01 17:46:38 +0000830
831 // Create the second variant for the first (and only) argument for this command.
832 bp_id_range_arg.arg_type = eArgTypeBreakpointIDRange;
Caroline Tice43b014a2010-10-04 22:28:36 +0000833 bp_id_range_arg.arg_repetition = eArgRepeatOptional;
Caroline Ticefb355112010-10-01 17:46:38 +0000834
835 // The first (and only) argument for this command could be either a bp_id or a bp_id_range.
836 // Push both variants into the entry for the first argument for this command.
837 arg.push_back (bp_id_arg);
838 arg.push_back (bp_id_range_arg);
839
840 // Add the entry for the first argument for this command to the object's arguments vector.
841 m_arguments.push_back (arg);
Chris Lattner24943d22010-06-08 16:52:24 +0000842}
843
844
845CommandObjectBreakpointEnable::~CommandObjectBreakpointEnable ()
846{
847}
848
849
850bool
Greg Clayton63094e02010-06-23 01:19:29 +0000851CommandObjectBreakpointEnable::Execute
852(
Greg Clayton63094e02010-06-23 01:19:29 +0000853 Args& args,
854 CommandReturnObject &result
855)
Chris Lattner24943d22010-06-08 16:52:24 +0000856{
Greg Clayton238c0a12010-09-18 01:14:36 +0000857 Target *target = m_interpreter.GetDebugger().GetSelectedTarget().get();
Chris Lattner24943d22010-06-08 16:52:24 +0000858 if (target == NULL)
859 {
Caroline Tice17dce1c2010-09-29 19:42:33 +0000860 result.AppendError ("Invalid target. No existing target or breakpoints.");
Chris Lattner24943d22010-06-08 16:52:24 +0000861 result.SetStatus (eReturnStatusFailed);
862 return false;
863 }
864
Jim Ingham3c7b5b92010-06-16 02:00:15 +0000865 Mutex::Locker locker;
866 target->GetBreakpointList().GetListMutex(locker);
867
Chris Lattner24943d22010-06-08 16:52:24 +0000868 const BreakpointList &breakpoints = target->GetBreakpointList();
Jim Ingham3c7b5b92010-06-16 02:00:15 +0000869
Chris Lattner24943d22010-06-08 16:52:24 +0000870 size_t num_breakpoints = breakpoints.GetSize();
871
872 if (num_breakpoints == 0)
873 {
874 result.AppendError ("No breakpoints exist to be enabled.");
875 result.SetStatus (eReturnStatusFailed);
876 return false;
877 }
878
879 if (args.GetArgumentCount() == 0)
880 {
881 // No breakpoint selected; enable all currently set breakpoints.
882 target->EnableAllBreakpoints ();
883 result.AppendMessageWithFormat ("All breakpoints enabled. (%d breakpoints)\n", num_breakpoints);
884 result.SetStatus (eReturnStatusSuccessFinishNoResult);
885 }
886 else
887 {
888 // Particular breakpoint selected; enable that breakpoint.
889 BreakpointIDList valid_bp_ids;
890 CommandObjectMultiwordBreakpoint::VerifyBreakpointIDs (args, target, result, &valid_bp_ids);
891
892 if (result.Succeeded())
893 {
894 int enable_count = 0;
895 int loc_count = 0;
Greg Clayton54e7afa2010-07-09 20:39:50 +0000896 const size_t count = valid_bp_ids.GetSize();
897 for (size_t i = 0; i < count; ++i)
Chris Lattner24943d22010-06-08 16:52:24 +0000898 {
899 BreakpointID cur_bp_id = valid_bp_ids.GetBreakpointIDAtIndex (i);
900
901 if (cur_bp_id.GetBreakpointID() != LLDB_INVALID_BREAK_ID)
902 {
903 Breakpoint *breakpoint = target->GetBreakpointByID (cur_bp_id.GetBreakpointID()).get();
904 if (cur_bp_id.GetLocationID() != LLDB_INVALID_BREAK_ID)
905 {
906 BreakpointLocation *location = breakpoint->FindLocationByID (cur_bp_id.GetLocationID()).get();
907 if (location)
908 {
909 location->SetEnabled (true);
Chris Lattner24943d22010-06-08 16:52:24 +0000910 ++loc_count;
911 }
912 }
913 else
914 {
Jim Ingham10622a22010-06-18 00:58:52 +0000915 breakpoint->SetEnabled (true);
Chris Lattner24943d22010-06-08 16:52:24 +0000916 ++enable_count;
Chris Lattner24943d22010-06-08 16:52:24 +0000917 }
918 }
919 }
920 result.AppendMessageWithFormat ("%d breakpoints enabled.\n", enable_count + loc_count);
921 result.SetStatus (eReturnStatusSuccessFinishNoResult);
922 }
923 }
924
925 return result.Succeeded();
926}
927
928//-------------------------------------------------------------------------
929// CommandObjectBreakpointDisable
930//-------------------------------------------------------------------------
Jim Ingham10622a22010-06-18 00:58:52 +0000931#pragma mark Disable
Chris Lattner24943d22010-06-08 16:52:24 +0000932
Greg Clayton238c0a12010-09-18 01:14:36 +0000933CommandObjectBreakpointDisable::CommandObjectBreakpointDisable (CommandInterpreter &interpreter) :
934 CommandObject (interpreter,
Caroline Ticefb355112010-10-01 17:46:38 +0000935 "breakpoint disable",
Caroline Ticeabb507a2010-09-08 21:06:11 +0000936 "Disable the specified breakpoint(s) without removing it/them. If no breakpoints are specified, disable them all.",
Caroline Ticefb355112010-10-01 17:46:38 +0000937 NULL)
Chris Lattner24943d22010-06-08 16:52:24 +0000938{
Caroline Ticefb355112010-10-01 17:46:38 +0000939 CommandArgumentEntry arg;
940 CommandArgumentData bp_id_arg;
941 CommandArgumentData bp_id_range_arg;
942
943 // Create the first variant for the first (and only) argument for this command.
944 bp_id_arg.arg_type = eArgTypeBreakpointID;
Caroline Tice43b014a2010-10-04 22:28:36 +0000945 bp_id_arg.arg_repetition = eArgRepeatOptional;
Caroline Ticefb355112010-10-01 17:46:38 +0000946
947 // Create the second variant for the first (and only) argument for this command.
948 bp_id_range_arg.arg_type = eArgTypeBreakpointIDRange;
Caroline Tice43b014a2010-10-04 22:28:36 +0000949 bp_id_range_arg.arg_repetition = eArgRepeatOptional;
Caroline Ticefb355112010-10-01 17:46:38 +0000950
951 // The first (and only) argument for this command could be either a bp_id or a bp_id_range.
952 // Push both variants into the entry for the first argument for this command.
953 arg.push_back (bp_id_arg);
954 arg.push_back (bp_id_range_arg);
955
956 // Add the entry for the first argument for this command to the object's arguments vector.
957 m_arguments.push_back (arg);
Chris Lattner24943d22010-06-08 16:52:24 +0000958}
959
960CommandObjectBreakpointDisable::~CommandObjectBreakpointDisable ()
961{
962}
963
964bool
Greg Clayton63094e02010-06-23 01:19:29 +0000965CommandObjectBreakpointDisable::Execute
966(
Greg Clayton63094e02010-06-23 01:19:29 +0000967 Args& args,
968 CommandReturnObject &result
969)
Chris Lattner24943d22010-06-08 16:52:24 +0000970{
Greg Clayton238c0a12010-09-18 01:14:36 +0000971 Target *target = m_interpreter.GetDebugger().GetSelectedTarget().get();
Chris Lattner24943d22010-06-08 16:52:24 +0000972 if (target == NULL)
973 {
Caroline Tice17dce1c2010-09-29 19:42:33 +0000974 result.AppendError ("Invalid target. No existing target or breakpoints.");
Chris Lattner24943d22010-06-08 16:52:24 +0000975 result.SetStatus (eReturnStatusFailed);
976 return false;
977 }
978
Jim Ingham3c7b5b92010-06-16 02:00:15 +0000979 Mutex::Locker locker;
980 target->GetBreakpointList().GetListMutex(locker);
981
Chris Lattner24943d22010-06-08 16:52:24 +0000982 const BreakpointList &breakpoints = target->GetBreakpointList();
983 size_t num_breakpoints = breakpoints.GetSize();
984
985 if (num_breakpoints == 0)
986 {
987 result.AppendError ("No breakpoints exist to be disabled.");
988 result.SetStatus (eReturnStatusFailed);
989 return false;
990 }
991
992 if (args.GetArgumentCount() == 0)
993 {
994 // No breakpoint selected; disable all currently set breakpoints.
995 target->DisableAllBreakpoints ();
996 result.AppendMessageWithFormat ("All breakpoints disabled. (%d breakpoints)\n", num_breakpoints);
997 result.SetStatus (eReturnStatusSuccessFinishNoResult);
998 }
999 else
1000 {
1001 // Particular breakpoint selected; disable that breakpoint.
1002 BreakpointIDList valid_bp_ids;
1003
1004 CommandObjectMultiwordBreakpoint::VerifyBreakpointIDs (args, target, result, &valid_bp_ids);
1005
1006 if (result.Succeeded())
1007 {
1008 int disable_count = 0;
1009 int loc_count = 0;
Greg Clayton54e7afa2010-07-09 20:39:50 +00001010 const size_t count = valid_bp_ids.GetSize();
1011 for (size_t i = 0; i < count; ++i)
Chris Lattner24943d22010-06-08 16:52:24 +00001012 {
1013 BreakpointID cur_bp_id = valid_bp_ids.GetBreakpointIDAtIndex (i);
1014
1015 if (cur_bp_id.GetBreakpointID() != LLDB_INVALID_BREAK_ID)
1016 {
1017 Breakpoint *breakpoint = target->GetBreakpointByID (cur_bp_id.GetBreakpointID()).get();
1018 if (cur_bp_id.GetLocationID() != LLDB_INVALID_BREAK_ID)
1019 {
1020 BreakpointLocation *location = breakpoint->FindLocationByID (cur_bp_id.GetLocationID()).get();
1021 if (location)
1022 {
1023 location->SetEnabled (false);
1024 ++loc_count;
1025 }
1026 }
1027 else
1028 {
Jim Ingham10622a22010-06-18 00:58:52 +00001029 breakpoint->SetEnabled (false);
Chris Lattner24943d22010-06-08 16:52:24 +00001030 ++disable_count;
Chris Lattner24943d22010-06-08 16:52:24 +00001031 }
1032 }
1033 }
1034 result.AppendMessageWithFormat ("%d breakpoints disabled.\n", disable_count + loc_count);
1035 result.SetStatus (eReturnStatusSuccessFinishNoResult);
1036 }
1037 }
1038
1039 return result.Succeeded();
1040}
1041
1042//-------------------------------------------------------------------------
Johnny Chena62ad7c2010-10-28 17:27:46 +00001043// CommandObjectBreakpointClear::CommandOptions
1044//-------------------------------------------------------------------------
1045#pragma mark Clear::CommandOptions
1046
Greg Claytonf15996e2011-04-07 22:46:35 +00001047CommandObjectBreakpointClear::CommandOptions::CommandOptions(CommandInterpreter &interpreter) :
1048 Options (interpreter),
Johnny Chena62ad7c2010-10-28 17:27:46 +00001049 m_filename (),
1050 m_line_num (0)
1051{
1052}
1053
1054CommandObjectBreakpointClear::CommandOptions::~CommandOptions ()
1055{
1056}
1057
Greg Claytonb3448432011-03-24 21:19:54 +00001058OptionDefinition
Johnny Chena62ad7c2010-10-28 17:27:46 +00001059CommandObjectBreakpointClear::CommandOptions::g_option_table[] =
1060{
1061 { LLDB_OPT_SET_1, false, "file", 'f', required_argument, NULL, CommandCompletions::eSourceFileCompletion, eArgTypeFilename,
1062 "Specify the breakpoint by source location in this particular file."},
1063
1064 { LLDB_OPT_SET_1, true, "line", 'l', required_argument, NULL, 0, eArgTypeLineNum,
1065 "Specify the breakpoint by source location at this particular line."},
1066
1067 { 0, false, NULL, 0, 0, NULL, 0, eArgTypeNone, NULL }
1068};
1069
Greg Claytonb3448432011-03-24 21:19:54 +00001070const OptionDefinition*
Johnny Chena62ad7c2010-10-28 17:27:46 +00001071CommandObjectBreakpointClear::CommandOptions::GetDefinitions ()
1072{
1073 return g_option_table;
1074}
1075
1076Error
Greg Clayton143fcc32011-04-13 00:18:08 +00001077CommandObjectBreakpointClear::CommandOptions::SetOptionValue (uint32_t option_idx, const char *option_arg)
Johnny Chena62ad7c2010-10-28 17:27:46 +00001078{
1079 Error error;
1080 char short_option = (char) m_getopt_table[option_idx].val;
1081
1082 switch (short_option)
1083 {
1084 case 'f':
Greg Clayton889fbd02011-03-26 19:14:58 +00001085 m_filename.assign (option_arg);
Johnny Chena62ad7c2010-10-28 17:27:46 +00001086 break;
1087
1088 case 'l':
1089 m_line_num = Args::StringToUInt32 (option_arg, 0);
1090 break;
1091
1092 default:
1093 error.SetErrorStringWithFormat ("Unrecognized option '%c'.\n", short_option);
1094 break;
1095 }
1096
1097 return error;
1098}
1099
1100void
Greg Clayton143fcc32011-04-13 00:18:08 +00001101CommandObjectBreakpointClear::CommandOptions::OptionParsingStarting ()
Johnny Chena62ad7c2010-10-28 17:27:46 +00001102{
Johnny Chena62ad7c2010-10-28 17:27:46 +00001103 m_filename.clear();
1104 m_line_num = 0;
1105}
1106
1107//-------------------------------------------------------------------------
1108// CommandObjectBreakpointClear
1109//-------------------------------------------------------------------------
1110#pragma mark Clear
1111
1112CommandObjectBreakpointClear::CommandObjectBreakpointClear (CommandInterpreter &interpreter) :
1113 CommandObject (interpreter,
1114 "breakpoint clear",
1115 "Clears a breakpoint or set of breakpoints in the executable.",
Greg Claytonf15996e2011-04-07 22:46:35 +00001116 "breakpoint clear <cmd-options>"),
1117 m_options (interpreter)
Johnny Chena62ad7c2010-10-28 17:27:46 +00001118{
1119}
1120
1121CommandObjectBreakpointClear::~CommandObjectBreakpointClear ()
1122{
1123}
1124
1125Options *
1126CommandObjectBreakpointClear::GetOptions ()
1127{
1128 return &m_options;
1129}
1130
1131bool
1132CommandObjectBreakpointClear::Execute
1133(
1134 Args& command,
1135 CommandReturnObject &result
1136)
1137{
1138 Target *target = m_interpreter.GetDebugger().GetSelectedTarget().get();
1139 if (target == NULL)
1140 {
1141 result.AppendError ("Invalid target. No existing target or breakpoints.");
1142 result.SetStatus (eReturnStatusFailed);
1143 return false;
1144 }
1145
1146 // The following are the various types of breakpoints that could be cleared:
1147 // 1). -f -l (clearing breakpoint by source location)
1148
1149 BreakpointClearType break_type = eClearTypeInvalid;
1150
1151 if (m_options.m_line_num != 0)
1152 break_type = eClearTypeFileAndLine;
1153
1154 Mutex::Locker locker;
1155 target->GetBreakpointList().GetListMutex(locker);
1156
1157 BreakpointList &breakpoints = target->GetBreakpointList();
1158 size_t num_breakpoints = breakpoints.GetSize();
1159
1160 // Early return if there's no breakpoint at all.
1161 if (num_breakpoints == 0)
1162 {
1163 result.AppendError ("Breakpoint clear: No breakpoint cleared.");
1164 result.SetStatus (eReturnStatusFailed);
1165 return result.Succeeded();
1166 }
1167
1168 // Find matching breakpoints and delete them.
1169
1170 // First create a copy of all the IDs.
1171 std::vector<break_id_t> BreakIDs;
1172 for (size_t i = 0; i < num_breakpoints; ++i)
1173 BreakIDs.push_back(breakpoints.GetBreakpointAtIndex(i).get()->GetID());
1174
1175 int num_cleared = 0;
1176 StreamString ss;
1177 switch (break_type)
1178 {
1179 case eClearTypeFileAndLine: // Breakpoint by source position
1180 {
1181 const ConstString filename(m_options.m_filename.c_str());
1182 BreakpointLocationCollection loc_coll;
1183
1184 for (size_t i = 0; i < num_breakpoints; ++i)
1185 {
1186 Breakpoint *bp = breakpoints.FindBreakpointByID(BreakIDs[i]).get();
1187
1188 if (bp->GetMatchingFileLine(filename, m_options.m_line_num, loc_coll))
1189 {
1190 // If the collection size is 0, it's a full match and we can just remove the breakpoint.
1191 if (loc_coll.GetSize() == 0)
1192 {
1193 bp->GetDescription(&ss, lldb::eDescriptionLevelBrief);
1194 ss.EOL();
1195 target->RemoveBreakpointByID (bp->GetID());
1196 ++num_cleared;
1197 }
1198 }
1199 }
1200 }
1201 break;
1202
1203 default:
1204 break;
1205 }
1206
1207 if (num_cleared > 0)
1208 {
Jim Ingham2e8cb8a2011-02-19 02:53:09 +00001209 Stream &output_stream = result.GetOutputStream();
Johnny Chena62ad7c2010-10-28 17:27:46 +00001210 output_stream.Printf ("%d breakpoints cleared:\n", num_cleared);
1211 output_stream << ss.GetData();
1212 output_stream.EOL();
1213 result.SetStatus (eReturnStatusSuccessFinishNoResult);
1214 }
1215 else
1216 {
1217 result.AppendError ("Breakpoint clear: No breakpoint cleared.");
1218 result.SetStatus (eReturnStatusFailed);
1219 }
1220
1221 return result.Succeeded();
1222}
1223
1224//-------------------------------------------------------------------------
Chris Lattner24943d22010-06-08 16:52:24 +00001225// CommandObjectBreakpointDelete
1226//-------------------------------------------------------------------------
Jim Ingham10622a22010-06-18 00:58:52 +00001227#pragma mark Delete
Chris Lattner24943d22010-06-08 16:52:24 +00001228
Greg Clayton238c0a12010-09-18 01:14:36 +00001229CommandObjectBreakpointDelete::CommandObjectBreakpointDelete(CommandInterpreter &interpreter) :
1230 CommandObject (interpreter,
1231 "breakpoint delete",
Caroline Ticeabb507a2010-09-08 21:06:11 +00001232 "Delete the specified breakpoint(s). If no breakpoints are specified, delete them all.",
Caroline Ticefb355112010-10-01 17:46:38 +00001233 NULL)
Chris Lattner24943d22010-06-08 16:52:24 +00001234{
Caroline Ticefb355112010-10-01 17:46:38 +00001235 CommandArgumentEntry arg;
1236 CommandArgumentData bp_id_arg;
1237 CommandArgumentData bp_id_range_arg;
1238
1239 // Create the first variant for the first (and only) argument for this command.
1240 bp_id_arg.arg_type = eArgTypeBreakpointID;
Caroline Tice43b014a2010-10-04 22:28:36 +00001241 bp_id_arg.arg_repetition = eArgRepeatOptional;
Caroline Ticefb355112010-10-01 17:46:38 +00001242
1243 // Create the second variant for the first (and only) argument for this command.
1244 bp_id_range_arg.arg_type = eArgTypeBreakpointIDRange;
Caroline Tice43b014a2010-10-04 22:28:36 +00001245 bp_id_range_arg.arg_repetition = eArgRepeatOptional;
Caroline Ticefb355112010-10-01 17:46:38 +00001246
1247 // The first (and only) argument for this command could be either a bp_id or a bp_id_range.
1248 // Push both variants into the entry for the first argument for this command.
1249 arg.push_back (bp_id_arg);
1250 arg.push_back (bp_id_range_arg);
1251
1252 // Add the entry for the first argument for this command to the object's arguments vector.
1253 m_arguments.push_back (arg);
Chris Lattner24943d22010-06-08 16:52:24 +00001254}
1255
1256
1257CommandObjectBreakpointDelete::~CommandObjectBreakpointDelete ()
1258{
1259}
1260
1261bool
Greg Clayton63094e02010-06-23 01:19:29 +00001262CommandObjectBreakpointDelete::Execute
1263(
Greg Clayton63094e02010-06-23 01:19:29 +00001264 Args& args,
1265 CommandReturnObject &result
1266)
Chris Lattner24943d22010-06-08 16:52:24 +00001267{
Greg Clayton238c0a12010-09-18 01:14:36 +00001268 Target *target = m_interpreter.GetDebugger().GetSelectedTarget().get();
Chris Lattner24943d22010-06-08 16:52:24 +00001269 if (target == NULL)
1270 {
Caroline Tice17dce1c2010-09-29 19:42:33 +00001271 result.AppendError ("Invalid target. No existing target or breakpoints.");
Chris Lattner24943d22010-06-08 16:52:24 +00001272 result.SetStatus (eReturnStatusFailed);
1273 return false;
1274 }
1275
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001276 Mutex::Locker locker;
1277 target->GetBreakpointList().GetListMutex(locker);
1278
Chris Lattner24943d22010-06-08 16:52:24 +00001279 const BreakpointList &breakpoints = target->GetBreakpointList();
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001280
Chris Lattner24943d22010-06-08 16:52:24 +00001281 size_t num_breakpoints = breakpoints.GetSize();
1282
1283 if (num_breakpoints == 0)
1284 {
1285 result.AppendError ("No breakpoints exist to be deleted.");
1286 result.SetStatus (eReturnStatusFailed);
1287 return false;
1288 }
1289
1290 if (args.GetArgumentCount() == 0)
1291 {
Jim Inghamd1686902010-10-14 23:45:03 +00001292 if (!m_interpreter.Confirm ("About to delete all breakpoints, do you want to do that?", true))
Chris Lattner24943d22010-06-08 16:52:24 +00001293 {
Jim Inghamd1686902010-10-14 23:45:03 +00001294 result.AppendMessage("Operation cancelled...");
Chris Lattner24943d22010-06-08 16:52:24 +00001295 }
Jim Inghamd1686902010-10-14 23:45:03 +00001296 else
1297 {
1298 target->RemoveAllBreakpoints ();
1299 result.AppendMessageWithFormat ("All breakpoints removed. (%d breakpoints)\n", num_breakpoints);
1300 }
Chris Lattner24943d22010-06-08 16:52:24 +00001301 result.SetStatus (eReturnStatusSuccessFinishNoResult);
1302 }
1303 else
1304 {
1305 // Particular breakpoint selected; disable that breakpoint.
1306 BreakpointIDList valid_bp_ids;
1307 CommandObjectMultiwordBreakpoint::VerifyBreakpointIDs (args, target, result, &valid_bp_ids);
1308
1309 if (result.Succeeded())
1310 {
1311 int delete_count = 0;
1312 int disable_count = 0;
Greg Clayton54e7afa2010-07-09 20:39:50 +00001313 const size_t count = valid_bp_ids.GetSize();
1314 for (size_t i = 0; i < count; ++i)
Chris Lattner24943d22010-06-08 16:52:24 +00001315 {
1316 BreakpointID cur_bp_id = valid_bp_ids.GetBreakpointIDAtIndex (i);
1317
1318 if (cur_bp_id.GetBreakpointID() != LLDB_INVALID_BREAK_ID)
1319 {
1320 if (cur_bp_id.GetLocationID() != LLDB_INVALID_BREAK_ID)
1321 {
1322 Breakpoint *breakpoint = target->GetBreakpointByID (cur_bp_id.GetBreakpointID()).get();
1323 BreakpointLocation *location = breakpoint->FindLocationByID (cur_bp_id.GetLocationID()).get();
1324 // It makes no sense to try to delete individual locations, so we disable them instead.
1325 if (location)
1326 {
1327 location->SetEnabled (false);
1328 ++disable_count;
1329 }
1330 }
1331 else
1332 {
1333 target->RemoveBreakpointByID (cur_bp_id.GetBreakpointID());
1334 ++delete_count;
1335 }
1336 }
1337 }
1338 result.AppendMessageWithFormat ("%d breakpoints deleted; %d breakpoint locations disabled.\n",
1339 delete_count, disable_count);
1340 result.SetStatus (eReturnStatusSuccessFinishNoResult);
1341 }
1342 }
1343 return result.Succeeded();
1344}
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001345
1346//-------------------------------------------------------------------------
Jim Ingham10622a22010-06-18 00:58:52 +00001347// CommandObjectBreakpointModify::CommandOptions
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001348//-------------------------------------------------------------------------
Jim Ingham10622a22010-06-18 00:58:52 +00001349#pragma mark Modify::CommandOptions
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001350
Greg Claytonf15996e2011-04-07 22:46:35 +00001351CommandObjectBreakpointModify::CommandOptions::CommandOptions(CommandInterpreter &interpreter) :
1352 Options (interpreter),
Greg Clayton54e7afa2010-07-09 20:39:50 +00001353 m_ignore_count (0),
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001354 m_thread_id(LLDB_INVALID_THREAD_ID),
Jim Ingham9a7b2912010-12-03 23:04:19 +00001355 m_thread_id_passed(false),
Greg Clayton54e7afa2010-07-09 20:39:50 +00001356 m_thread_index (UINT32_MAX),
Jim Ingham9a7b2912010-12-03 23:04:19 +00001357 m_thread_index_passed(false),
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001358 m_thread_name(),
1359 m_queue_name(),
Jim Inghamd1686902010-10-14 23:45:03 +00001360 m_condition (),
Greg Clayton54e7afa2010-07-09 20:39:50 +00001361 m_enable_passed (false),
1362 m_enable_value (false),
1363 m_name_passed (false),
Jim Inghamd1686902010-10-14 23:45:03 +00001364 m_queue_passed (false),
1365 m_condition_passed (false)
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001366{
1367}
1368
Jim Ingham10622a22010-06-18 00:58:52 +00001369CommandObjectBreakpointModify::CommandOptions::~CommandOptions ()
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001370{
1371}
1372
Greg Claytonb3448432011-03-24 21:19:54 +00001373OptionDefinition
Jim Ingham10622a22010-06-18 00:58:52 +00001374CommandObjectBreakpointModify::CommandOptions::g_option_table[] =
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001375{
Caroline Tice4d6675c2010-10-01 19:59:14 +00001376{ LLDB_OPT_SET_ALL, false, "ignore-count", 'i', required_argument, NULL, NULL, eArgTypeCount, "Set the number of times this breakpoint is skipped before stopping." },
1377{ LLDB_OPT_SET_ALL, false, "thread-index", 'x', required_argument, NULL, NULL, eArgTypeThreadIndex, "The breakpoint stops only for the thread whose indeX matches this argument."},
1378{ LLDB_OPT_SET_ALL, false, "thread-id", 't', required_argument, NULL, NULL, eArgTypeThreadID, "The breakpoint stops only for the thread whose TID matches this argument."},
1379{ LLDB_OPT_SET_ALL, false, "thread-name", 'T', required_argument, NULL, NULL, eArgTypeThreadName, "The breakpoint stops only for the thread whose thread name matches this argument."},
1380{ LLDB_OPT_SET_ALL, false, "queue-name", 'q', required_argument, NULL, NULL, eArgTypeQueueName, "The breakpoint stops only for threads in the queue whose name is given by this argument."},
Jim Inghamd1686902010-10-14 23:45:03 +00001381{ LLDB_OPT_SET_ALL, false, "condition", 'c', required_argument, NULL, NULL, eArgTypeExpression, "The breakpoint stops only if this condition expression evaluates to true."},
Caroline Tice4d6675c2010-10-01 19:59:14 +00001382{ LLDB_OPT_SET_1, false, "enable", 'e', no_argument, NULL, NULL, eArgTypeNone, "Enable the breakpoint."},
1383{ LLDB_OPT_SET_2, false, "disable", 'd', no_argument, NULL, NULL, eArgTypeNone, "Disable the breakpoint."},
Jim Inghamd1686902010-10-14 23:45:03 +00001384{ 0, false, NULL, 0 , 0, NULL, 0, eArgTypeNone, NULL }
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001385};
1386
Greg Claytonb3448432011-03-24 21:19:54 +00001387const OptionDefinition*
Jim Ingham10622a22010-06-18 00:58:52 +00001388CommandObjectBreakpointModify::CommandOptions::GetDefinitions ()
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001389{
1390 return g_option_table;
1391}
1392
1393Error
Greg Clayton143fcc32011-04-13 00:18:08 +00001394CommandObjectBreakpointModify::CommandOptions::SetOptionValue (uint32_t option_idx, const char *option_arg)
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001395{
1396 Error error;
1397 char short_option = (char) m_getopt_table[option_idx].val;
1398
1399 switch (short_option)
1400 {
Jim Inghamd1686902010-10-14 23:45:03 +00001401 case 'c':
1402 if (option_arg != NULL)
Greg Clayton889fbd02011-03-26 19:14:58 +00001403 m_condition.assign (option_arg);
Jim Inghamd1686902010-10-14 23:45:03 +00001404 else
1405 m_condition.clear();
1406 m_condition_passed = true;
1407 break;
Jim Ingham10622a22010-06-18 00:58:52 +00001408 case 'd':
1409 m_enable_passed = true;
1410 m_enable_value = false;
1411 break;
1412 case 'e':
1413 m_enable_passed = true;
1414 m_enable_value = true;
1415 break;
Greg Claytonfe424a92010-09-18 03:37:20 +00001416 case 'i':
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001417 {
Jim Ingham7a4c8ea2011-03-22 01:53:33 +00001418 m_ignore_count = Args::StringToUInt32(option_arg, UINT32_MAX, 0);
Greg Clayton54e7afa2010-07-09 20:39:50 +00001419 if (m_ignore_count == UINT32_MAX)
Jim Ingham7a4c8ea2011-03-22 01:53:33 +00001420 error.SetErrorStringWithFormat ("Invalid ignore count '%s'.\n", option_arg);
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001421 }
Jim Ingham10622a22010-06-18 00:58:52 +00001422 break;
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001423 case 't' :
1424 {
Jim Ingham7a4c8ea2011-03-22 01:53:33 +00001425 if (option_arg[0] == '\0')
Jim Ingham9a7b2912010-12-03 23:04:19 +00001426 {
1427 m_thread_id = LLDB_INVALID_THREAD_ID;
1428 m_thread_id_passed = true;
1429 }
1430 else
1431 {
Jim Ingham7a4c8ea2011-03-22 01:53:33 +00001432 m_thread_id = Args::StringToUInt64(option_arg, LLDB_INVALID_THREAD_ID, 0);
Jim Ingham9a7b2912010-12-03 23:04:19 +00001433 if (m_thread_id == LLDB_INVALID_THREAD_ID)
Jim Ingham7a4c8ea2011-03-22 01:53:33 +00001434 error.SetErrorStringWithFormat ("Invalid thread id string '%s'.\n", option_arg);
Jim Ingham9a7b2912010-12-03 23:04:19 +00001435 else
1436 m_thread_id_passed = true;
1437 }
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001438 }
1439 break;
1440 case 'T':
Jim Inghamd4571222010-06-19 04:35:20 +00001441 if (option_arg != NULL)
Greg Clayton889fbd02011-03-26 19:14:58 +00001442 m_thread_name.assign (option_arg);
Jim Inghamd4571222010-06-19 04:35:20 +00001443 else
1444 m_thread_name.clear();
1445 m_name_passed = true;
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001446 break;
1447 case 'q':
Jim Inghamd4571222010-06-19 04:35:20 +00001448 if (option_arg != NULL)
Greg Clayton889fbd02011-03-26 19:14:58 +00001449 m_queue_name.assign (option_arg);
Jim Inghamd4571222010-06-19 04:35:20 +00001450 else
1451 m_queue_name.clear();
1452 m_queue_passed = true;
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001453 break;
1454 case 'x':
1455 {
Jim Ingham7a4c8ea2011-03-22 01:53:33 +00001456 if (option_arg[0] == '\n')
Jim Ingham9a7b2912010-12-03 23:04:19 +00001457 {
1458 m_thread_index = UINT32_MAX;
1459 m_thread_index_passed = true;
1460 }
1461 else
1462 {
Jim Ingham7a4c8ea2011-03-22 01:53:33 +00001463 m_thread_index = Args::StringToUInt32 (option_arg, UINT32_MAX, 0);
Jim Ingham9a7b2912010-12-03 23:04:19 +00001464 if (m_thread_id == UINT32_MAX)
Jim Ingham7a4c8ea2011-03-22 01:53:33 +00001465 error.SetErrorStringWithFormat ("Invalid thread index string '%s'.\n", option_arg);
Jim Ingham9a7b2912010-12-03 23:04:19 +00001466 else
1467 m_thread_index_passed = true;
1468 }
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001469 }
1470 break;
1471 default:
1472 error.SetErrorStringWithFormat ("Unrecognized option '%c'.\n", short_option);
1473 break;
1474 }
1475
1476 return error;
1477}
1478
1479void
Greg Clayton143fcc32011-04-13 00:18:08 +00001480CommandObjectBreakpointModify::CommandOptions::OptionParsingStarting ()
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001481{
Greg Clayton54e7afa2010-07-09 20:39:50 +00001482 m_ignore_count = 0;
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001483 m_thread_id = LLDB_INVALID_THREAD_ID;
Jim Ingham9a7b2912010-12-03 23:04:19 +00001484 m_thread_id_passed = false;
Greg Clayton54e7afa2010-07-09 20:39:50 +00001485 m_thread_index = UINT32_MAX;
Jim Ingham9a7b2912010-12-03 23:04:19 +00001486 m_thread_index_passed = false;
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001487 m_thread_name.clear();
1488 m_queue_name.clear();
Jim Inghamd1686902010-10-14 23:45:03 +00001489 m_condition.clear();
Jim Ingham10622a22010-06-18 00:58:52 +00001490 m_enable_passed = false;
Jim Inghamd4571222010-06-19 04:35:20 +00001491 m_queue_passed = false;
1492 m_name_passed = false;
Jim Inghamd1686902010-10-14 23:45:03 +00001493 m_condition_passed = false;
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001494}
1495
1496//-------------------------------------------------------------------------
Jim Ingham10622a22010-06-18 00:58:52 +00001497// CommandObjectBreakpointModify
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001498//-------------------------------------------------------------------------
Jim Ingham10622a22010-06-18 00:58:52 +00001499#pragma mark Modify
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001500
Greg Clayton238c0a12010-09-18 01:14:36 +00001501CommandObjectBreakpointModify::CommandObjectBreakpointModify (CommandInterpreter &interpreter) :
1502 CommandObject (interpreter,
1503 "breakpoint modify",
Jim Ingham19ac0bd2010-12-03 22:37:19 +00001504 "Modify the options on a breakpoint or set of breakpoints in the executable. "
Jim Ingham9a7b2912010-12-03 23:04:19 +00001505 "If no breakpoint is specified, acts on the last created breakpoint. "
1506 "With the exception of -e, -d and -i, passing an empty argument clears the modification.",
Greg Claytonf15996e2011-04-07 22:46:35 +00001507 NULL),
1508 m_options (interpreter)
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001509{
Caroline Ticefb355112010-10-01 17:46:38 +00001510 CommandArgumentEntry arg;
1511 CommandArgumentData bp_id_arg;
1512 CommandArgumentData bp_id_range_arg;
1513
1514 // Create the first variant for the first (and only) argument for this command.
1515 bp_id_arg.arg_type = eArgTypeBreakpointID;
Caroline Tice43b014a2010-10-04 22:28:36 +00001516 bp_id_arg.arg_repetition = eArgRepeatPlain;
Caroline Ticefb355112010-10-01 17:46:38 +00001517
1518 // Create the second variant for the first (and only) argument for this command.
1519 bp_id_range_arg.arg_type = eArgTypeBreakpointIDRange;
Caroline Tice43b014a2010-10-04 22:28:36 +00001520 bp_id_range_arg.arg_repetition = eArgRepeatPlain;
Caroline Ticefb355112010-10-01 17:46:38 +00001521
1522 // The first (and only) argument for this command could be either a bp_id or a bp_id_range.
1523 // Push both variants into the entry for the first argument for this command.
1524 arg.push_back (bp_id_arg);
1525 arg.push_back (bp_id_range_arg);
1526
1527 // Add the entry for the first argument for this command to the object's arguments vector.
1528 m_arguments.push_back (arg);
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001529}
1530
Jim Ingham10622a22010-06-18 00:58:52 +00001531CommandObjectBreakpointModify::~CommandObjectBreakpointModify ()
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001532{
1533}
1534
1535Options *
Jim Ingham10622a22010-06-18 00:58:52 +00001536CommandObjectBreakpointModify::GetOptions ()
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001537{
1538 return &m_options;
1539}
1540
1541bool
Jim Ingham10622a22010-06-18 00:58:52 +00001542CommandObjectBreakpointModify::Execute
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001543(
1544 Args& command,
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001545 CommandReturnObject &result
1546)
1547{
Greg Clayton238c0a12010-09-18 01:14:36 +00001548 Target *target = m_interpreter.GetDebugger().GetSelectedTarget().get();
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001549 if (target == NULL)
1550 {
Caroline Tice17dce1c2010-09-29 19:42:33 +00001551 result.AppendError ("Invalid target. No existing target or breakpoints.");
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001552 result.SetStatus (eReturnStatusFailed);
1553 return false;
1554 }
1555
1556 Mutex::Locker locker;
1557 target->GetBreakpointList().GetListMutex(locker);
1558
1559 BreakpointIDList valid_bp_ids;
1560
1561 CommandObjectMultiwordBreakpoint::VerifyBreakpointIDs (command, target, result, &valid_bp_ids);
1562
1563 if (result.Succeeded())
1564 {
Greg Clayton54e7afa2010-07-09 20:39:50 +00001565 const size_t count = valid_bp_ids.GetSize();
1566 for (size_t i = 0; i < count; ++i)
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001567 {
1568 BreakpointID cur_bp_id = valid_bp_ids.GetBreakpointIDAtIndex (i);
1569
1570 if (cur_bp_id.GetBreakpointID() != LLDB_INVALID_BREAK_ID)
1571 {
1572 Breakpoint *bp = target->GetBreakpointByID (cur_bp_id.GetBreakpointID()).get();
1573 if (cur_bp_id.GetLocationID() != LLDB_INVALID_BREAK_ID)
1574 {
1575 BreakpointLocation *location = bp->FindLocationByID (cur_bp_id.GetLocationID()).get();
1576 if (location)
1577 {
Jim Ingham9a7b2912010-12-03 23:04:19 +00001578 if (m_options.m_thread_id_passed)
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001579 location->SetThreadID (m_options.m_thread_id);
1580
Jim Ingham9a7b2912010-12-03 23:04:19 +00001581 if (m_options.m_thread_index_passed)
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001582 location->GetLocationOptions()->GetThreadSpec()->SetIndex(m_options.m_thread_index);
1583
Jim Inghamd4571222010-06-19 04:35:20 +00001584 if (m_options.m_name_passed)
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001585 location->GetLocationOptions()->GetThreadSpec()->SetName(m_options.m_thread_name.c_str());
1586
Jim Inghamd4571222010-06-19 04:35:20 +00001587 if (m_options.m_queue_passed)
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001588 location->GetLocationOptions()->GetThreadSpec()->SetQueueName(m_options.m_queue_name.c_str());
1589
Greg Clayton54e7afa2010-07-09 20:39:50 +00001590 if (m_options.m_ignore_count != 0)
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001591 location->GetLocationOptions()->SetIgnoreCount(m_options.m_ignore_count);
Jim Ingham10622a22010-06-18 00:58:52 +00001592
1593 if (m_options.m_enable_passed)
1594 location->SetEnabled (m_options.m_enable_value);
Jim Inghamd1686902010-10-14 23:45:03 +00001595
1596 if (m_options.m_condition_passed)
1597 location->SetCondition (m_options.m_condition.c_str());
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001598 }
1599 }
1600 else
1601 {
Jim Ingham9a7b2912010-12-03 23:04:19 +00001602 if (m_options.m_thread_id_passed)
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001603 bp->SetThreadID (m_options.m_thread_id);
1604
Jim Ingham9a7b2912010-12-03 23:04:19 +00001605 if (m_options.m_thread_index_passed)
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001606 bp->GetOptions()->GetThreadSpec()->SetIndex(m_options.m_thread_index);
1607
Jim Inghamd4571222010-06-19 04:35:20 +00001608 if (m_options.m_name_passed)
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001609 bp->GetOptions()->GetThreadSpec()->SetName(m_options.m_thread_name.c_str());
1610
Jim Inghamd4571222010-06-19 04:35:20 +00001611 if (m_options.m_queue_passed)
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001612 bp->GetOptions()->GetThreadSpec()->SetQueueName(m_options.m_queue_name.c_str());
1613
Greg Clayton54e7afa2010-07-09 20:39:50 +00001614 if (m_options.m_ignore_count != 0)
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001615 bp->GetOptions()->SetIgnoreCount(m_options.m_ignore_count);
Jim Ingham10622a22010-06-18 00:58:52 +00001616
1617 if (m_options.m_enable_passed)
1618 bp->SetEnabled (m_options.m_enable_value);
Jim Inghamd1686902010-10-14 23:45:03 +00001619
1620 if (m_options.m_condition_passed)
1621 bp->SetCondition (m_options.m_condition.c_str());
Jim Ingham3c7b5b92010-06-16 02:00:15 +00001622 }
1623 }
1624 }
1625 }
1626
1627 return result.Succeeded();
1628}
1629
1630