1 //===-- CommandObjectTarget.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 "CommandObjectTarget.h" 11 12 // C Includes 13 #include <errno.h> 14 #include <sys/errno.h> 15 // C++ Includes 16 // Other libraries and framework includes 17 // Project includes 18 #include "lldb/Interpreter/Args.h" 19 #include "lldb/Core/Debugger.h" 20 #include "lldb/Core/Timer.h" 21 #include "lldb/Core/Debugger.h" 22 #include "lldb/Interpreter/CommandInterpreter.h" 23 #include "lldb/Interpreter/CommandReturnObject.h" 24 #include "lldb/Target/Process.h" 25 #include "lldb/Target/StackFrame.h" 26 #include "lldb/Target/Thread.h" 27 28 using namespace lldb; 29 using namespace lldb_private; 30 31 #pragma mark CommandObjectTargetImageSearchPaths 32 33 class CommandObjectTargetImageSearchPathsAdd : public CommandObject 34 { 35 public: 36 37 CommandObjectTargetImageSearchPathsAdd (CommandInterpreter &interpreter) : 38 CommandObject (interpreter, 39 "target image-search-paths add", 40 "Add new image search paths substitution pairs to the current target.", 41 "target image-search-paths add <path-prefix> <new-path-prefix> [<path-prefix> <new-path-prefix>] ...") 42 { 43 } 44 45 ~CommandObjectTargetImageSearchPathsAdd () 46 { 47 } 48 49 bool 50 Execute (Args& command, 51 CommandReturnObject &result) 52 { 53 Target *target = m_interpreter.GetDebugger().GetSelectedTarget().get(); 54 if (target) 55 { 56 uint32_t argc = command.GetArgumentCount(); 57 if (argc & 1) 58 { 59 result.AppendError ("add requires an even number of arguments"); 60 result.SetStatus (eReturnStatusFailed); 61 } 62 else 63 { 64 for (uint32_t i=0; i<argc; i+=2) 65 { 66 const char *from = command.GetArgumentAtIndex(i); 67 const char *to = command.GetArgumentAtIndex(i+1); 68 69 if (from[0] && to[0]) 70 { 71 bool last_pair = ((argc - i) == 2); 72 target->GetImageSearchPathList().Append (ConstString(from), 73 ConstString(to), 74 last_pair); // Notify if this is the last pair 75 } 76 else 77 { 78 if (from[0]) 79 result.AppendError ("<path-prefix> can't be empty"); 80 else 81 result.AppendError ("<new-path-prefix> can't be empty"); 82 result.SetStatus (eReturnStatusFailed); 83 } 84 } 85 } 86 } 87 else 88 { 89 result.AppendError ("invalid target"); 90 result.SetStatus (eReturnStatusFailed); 91 } 92 return result.Succeeded(); 93 } 94 }; 95 96 class CommandObjectTargetImageSearchPathsClear : public CommandObject 97 { 98 public: 99 100 CommandObjectTargetImageSearchPathsClear (CommandInterpreter &interpreter) : 101 CommandObject (interpreter, 102 "target image-search-paths clear", 103 "Clear all current image search path substitution pairs from the current target.", 104 "target image-search-paths clear") 105 { 106 } 107 108 ~CommandObjectTargetImageSearchPathsClear () 109 { 110 } 111 112 bool 113 Execute (Args& command, 114 CommandReturnObject &result) 115 { 116 Target *target = m_interpreter.GetDebugger().GetSelectedTarget().get(); 117 if (target) 118 { 119 bool notify = true; 120 target->GetImageSearchPathList().Clear(notify); 121 } 122 else 123 { 124 result.AppendError ("invalid target"); 125 result.SetStatus (eReturnStatusFailed); 126 } 127 return result.Succeeded(); 128 } 129 }; 130 131 class CommandObjectTargetImageSearchPathsInsert : public CommandObject 132 { 133 public: 134 135 CommandObjectTargetImageSearchPathsInsert (CommandInterpreter &interpreter) : 136 CommandObject (interpreter, 137 "target image-search-paths insert", 138 "Insert a new image search path substitution pair into the current target at the specified index.", 139 "target image-search-paths insert <index> <path-prefix> <new-path-prefix> [<path-prefix> <new-path-prefix>] ...") 140 { 141 } 142 143 ~CommandObjectTargetImageSearchPathsInsert () 144 { 145 } 146 147 bool 148 Execute (Args& command, 149 CommandReturnObject &result) 150 { 151 Target *target = m_interpreter.GetDebugger().GetSelectedTarget().get(); 152 if (target) 153 { 154 uint32_t argc = command.GetArgumentCount(); 155 // check for at least 3 arguments and an odd nubmer of parameters 156 if (argc >= 3 && argc & 1) 157 { 158 bool success = false; 159 160 uint32_t insert_idx = Args::StringToUInt32(command.GetArgumentAtIndex(0), UINT32_MAX, 0, &success); 161 162 if (!success) 163 { 164 result.AppendErrorWithFormat("<index> parameter is not an integer: '%s'.\n", command.GetArgumentAtIndex(0)); 165 result.SetStatus (eReturnStatusFailed); 166 return result.Succeeded(); 167 } 168 169 // shift off the index 170 command.Shift(); 171 argc = command.GetArgumentCount(); 172 173 for (uint32_t i=0; i<argc; i+=2, ++insert_idx) 174 { 175 const char *from = command.GetArgumentAtIndex(i); 176 const char *to = command.GetArgumentAtIndex(i+1); 177 178 if (from[0] && to[0]) 179 { 180 bool last_pair = ((argc - i) == 2); 181 target->GetImageSearchPathList().Insert (ConstString(from), 182 ConstString(to), 183 insert_idx, 184 last_pair); 185 } 186 else 187 { 188 if (from[0]) 189 result.AppendError ("<path-prefix> can't be empty"); 190 else 191 result.AppendError ("<new-path-prefix> can't be empty"); 192 result.SetStatus (eReturnStatusFailed); 193 return false; 194 } 195 } 196 } 197 else 198 { 199 result.AppendError ("insert requires at least three arguments"); 200 result.SetStatus (eReturnStatusFailed); 201 return result.Succeeded(); 202 } 203 204 } 205 else 206 { 207 result.AppendError ("invalid target"); 208 result.SetStatus (eReturnStatusFailed); 209 } 210 return result.Succeeded(); 211 } 212 }; 213 214 class CommandObjectTargetImageSearchPathsList : public CommandObject 215 { 216 public: 217 218 CommandObjectTargetImageSearchPathsList (CommandInterpreter &interpreter) : 219 CommandObject (interpreter, 220 "target image-search-paths list", 221 "List all current image search path substitution pairs in the current target.", 222 "target image-search-paths list") 223 { 224 } 225 226 ~CommandObjectTargetImageSearchPathsList () 227 { 228 } 229 230 bool 231 Execute (Args& command, 232 CommandReturnObject &result) 233 { 234 Target *target = m_interpreter.GetDebugger().GetSelectedTarget().get(); 235 if (target) 236 { 237 if (command.GetArgumentCount() != 0) 238 { 239 result.AppendError ("list takes no arguments"); 240 result.SetStatus (eReturnStatusFailed); 241 return result.Succeeded(); 242 } 243 244 target->GetImageSearchPathList().Dump(&result.GetOutputStream()); 245 } 246 else 247 { 248 result.AppendError ("invalid target"); 249 result.SetStatus (eReturnStatusFailed); 250 } 251 return result.Succeeded(); 252 } 253 }; 254 255 class CommandObjectTargetImageSearchPathsQuery : public CommandObject 256 { 257 public: 258 259 CommandObjectTargetImageSearchPathsQuery (CommandInterpreter &interpreter) : 260 CommandObject (interpreter, 261 "target image-search-paths query", 262 "Transform a path using the first applicable image search path.", 263 "target image-search-paths query <path>") 264 { 265 } 266 267 ~CommandObjectTargetImageSearchPathsQuery () 268 { 269 } 270 271 bool 272 Execute (Args& command, 273 CommandReturnObject &result) 274 { 275 Target *target = m_interpreter.GetDebugger().GetSelectedTarget().get(); 276 if (target) 277 { 278 if (command.GetArgumentCount() != 1) 279 { 280 result.AppendError ("query requires one argument"); 281 result.SetStatus (eReturnStatusFailed); 282 return result.Succeeded(); 283 } 284 285 ConstString orig(command.GetArgumentAtIndex(0)); 286 ConstString transformed; 287 if (target->GetImageSearchPathList().RemapPath(orig, transformed)) 288 result.GetOutputStream().Printf("%s\n", transformed.GetCString()); 289 else 290 result.GetOutputStream().Printf("%s\n", orig.GetCString()); 291 } 292 else 293 { 294 result.AppendError ("invalid target"); 295 result.SetStatus (eReturnStatusFailed); 296 } 297 return result.Succeeded(); 298 } 299 }; 300 301 // TODO: implement the target select later when we start doing multiple targets 302 //#pragma mark CommandObjectTargetSelect 303 // 304 ////------------------------------------------------------------------------- 305 //// CommandObjectTargetSelect 306 ////------------------------------------------------------------------------- 307 // 308 //class CommandObjectTargetSelect : public CommandObject 309 //{ 310 //public: 311 // 312 // CommandObjectTargetSelect () : 313 // CommandObject (interpreter, 314 // frame select", 315 // "Select the current frame by index in the current thread.", 316 // "frame select <frame-index>") 317 // { 318 // } 319 // 320 // ~CommandObjectTargetSelect () 321 // { 322 // } 323 // 324 // bool 325 // Execute (Args& command, 326 // Debugger *context, 327 // CommandInterpreter &m_interpreter, 328 // CommandReturnObject &result) 329 // { 330 // ExecutionContext exe_ctx (context->GetExecutionContext()); 331 // if (exe_ctx.thread) 332 // { 333 // if (command.GetArgumentCount() == 1) 334 // { 335 // const char *frame_idx_cstr = command.GetArgumentAtIndex(0); 336 // 337 // const uint32_t num_frames = exe_ctx.thread->GetStackFrameCount(); 338 // const uint32_t frame_idx = Args::StringToUInt32 (frame_idx_cstr, UINT32_MAX, 0); 339 // if (frame_idx < num_frames) 340 // { 341 // exe_ctx.thread->SetSelectedFrameByIndex (frame_idx); 342 // exe_ctx.frame = exe_ctx.thread->GetSelectedFrame ().get(); 343 // 344 // if (exe_ctx.frame) 345 // { 346 // if (DisplayFrameForExecutionContext (exe_ctx.thread, 347 // exe_ctx.frame, 348 // m_interpreter, 349 // result.GetOutputStream(), 350 // true, 351 // true, 352 // 3, 353 // 3)) 354 // { 355 // result.SetStatus (eReturnStatusSuccessFinishResult); 356 // return result.Succeeded(); 357 // } 358 // } 359 // } 360 // if (frame_idx == UINT32_MAX) 361 // result.AppendErrorWithFormat ("Invalid frame index: %s.\n", frame_idx_cstr); 362 // else 363 // result.AppendErrorWithFormat ("Frame index (%u) out of range.\n", frame_idx); 364 // } 365 // else 366 // { 367 // result.AppendError ("invalid arguments"); 368 // result.AppendErrorWithFormat ("Usage: %s\n", m_cmd_syntax.c_str()); 369 // } 370 // } 371 // else 372 // { 373 // result.AppendError ("no current thread"); 374 // } 375 // result.SetStatus (eReturnStatusFailed); 376 // return false; 377 // } 378 //}; 379 380 381 #pragma mark CommandObjectMultiwordTarget 382 383 //------------------------------------------------------------------------- 384 // CommandObjectMultiwordImageSearchPaths 385 //------------------------------------------------------------------------- 386 387 class CommandObjectMultiwordImageSearchPaths : public CommandObjectMultiword 388 { 389 public: 390 391 CommandObjectMultiwordImageSearchPaths (CommandInterpreter &interpreter) : 392 CommandObjectMultiword (interpreter, 393 "target image-search-paths", 394 "A set of commands for operating on debugger target image search paths.", 395 "target image-search-paths <subcommand> [<subcommand-options>]") 396 { 397 LoadSubCommand ("add", CommandObjectSP (new CommandObjectTargetImageSearchPathsAdd (interpreter))); 398 LoadSubCommand ("clear", CommandObjectSP (new CommandObjectTargetImageSearchPathsClear (interpreter))); 399 LoadSubCommand ("insert", CommandObjectSP (new CommandObjectTargetImageSearchPathsInsert (interpreter))); 400 LoadSubCommand ("list", CommandObjectSP (new CommandObjectTargetImageSearchPathsList (interpreter))); 401 LoadSubCommand ("query", CommandObjectSP (new CommandObjectTargetImageSearchPathsQuery (interpreter))); 402 } 403 404 ~CommandObjectMultiwordImageSearchPaths() 405 { 406 } 407 }; 408 409 410 #pragma mark CommandObjectMultiwordTarget 411 412 //------------------------------------------------------------------------- 413 // CommandObjectMultiwordTarget 414 //------------------------------------------------------------------------- 415 416 CommandObjectMultiwordTarget::CommandObjectMultiwordTarget (CommandInterpreter &interpreter) : 417 CommandObjectMultiword (interpreter, 418 "target", 419 "A set of commands for operating on debugger targets.", 420 "target <subcommand> [<subcommand-options>]") 421 { 422 LoadSubCommand ("image-search-paths", CommandObjectSP (new CommandObjectMultiwordImageSearchPaths (interpreter))); 423 } 424 425 CommandObjectMultiwordTarget::~CommandObjectMultiwordTarget () 426 { 427 } 428 429