]> CyberLeo.Net >> Repos - FreeBSD/FreeBSD.git/blob - contrib/llvm/tools/lldb/source/Commands/CommandObjectSettings.cpp
Update lldb to upstream trunk r242221.
[FreeBSD/FreeBSD.git] / contrib / llvm / tools / lldb / source / Commands / CommandObjectSettings.cpp
1 //===-- CommandObjectSettings.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 "CommandObjectSettings.h"
11
12 // C Includes
13 // C++ Includes
14 // Other libraries and framework includes
15 // Project includes
16 #include "lldb/Interpreter/CommandInterpreter.h"
17 #include "lldb/Interpreter/CommandReturnObject.h"
18 #include "lldb/Interpreter/CommandCompletions.h"
19 #include "lldb/Interpreter/OptionValueProperties.h"
20
21 using namespace lldb;
22 using namespace lldb_private;
23 #include "llvm/ADT/StringRef.h"
24
25 //-------------------------------------------------------------------------
26 // CommandObjectSettingsSet
27 //-------------------------------------------------------------------------
28
29 class CommandObjectSettingsSet : public CommandObjectRaw
30 {
31 public:
32     CommandObjectSettingsSet (CommandInterpreter &interpreter) :
33         CommandObjectRaw (interpreter,
34                           "settings set",
35                           "Set or change the value of a single debugger setting variable.",
36                           NULL),
37         m_options (interpreter)
38     {
39         CommandArgumentEntry arg1;
40         CommandArgumentEntry arg2;
41         CommandArgumentData var_name_arg;
42         CommandArgumentData value_arg;
43
44         // Define the first (and only) variant of this arg.
45         var_name_arg.arg_type = eArgTypeSettingVariableName;
46         var_name_arg.arg_repetition = eArgRepeatPlain;
47
48         // There is only one variant this argument could be; put it into the argument entry.
49         arg1.push_back (var_name_arg);
50
51         // Define the first (and only) variant of this arg.
52         value_arg.arg_type = eArgTypeValue;
53         value_arg.arg_repetition = eArgRepeatPlain;
54
55         // There is only one variant this argument could be; put it into the argument entry.
56         arg2.push_back (value_arg);
57
58         // Push the data for the first argument into the m_arguments vector.
59         m_arguments.push_back (arg1);
60         m_arguments.push_back (arg2);
61         
62         SetHelpLong (
63 "\nWhen setting a dictionary or array variable, you can set multiple entries \
64 at once by giving the values to the set command.  For example:" R"(
65
66 (lldb) settings set target.run-args value1 value2 value3
67 (lldb) settings set target.env-vars MYPATH=~/.:/usr/bin  SOME_ENV_VAR=12345
68
69 (lldb) settings show target.run-args
70   [0]: 'value1'
71   [1]: 'value2'
72   [3]: 'value3'
73 (lldb) settings show target.env-vars
74   'MYPATH=~/.:/usr/bin'
75   'SOME_ENV_VAR=12345'
76
77 )" "Warning:  The 'set' command re-sets the entire array or dictionary.  If you \
78 just want to add, remove or update individual values (or add something to \
79 the end), use one of the other settings sub-commands: append, replace, \
80 insert-before or insert-after."
81         );
82
83     }
84
85
86     virtual
87     ~CommandObjectSettingsSet () {}
88
89     // Overrides base class's behavior where WantsCompletion = !WantsRawCommandString.
90     virtual bool
91     WantsCompletion() { return true; }
92
93     virtual Options *
94     GetOptions ()
95     {
96         return &m_options;
97     }
98     
99     class CommandOptions : public Options
100     {
101     public:
102
103         CommandOptions (CommandInterpreter &interpreter) :
104             Options (interpreter),
105             m_global (false)
106         {
107         }
108
109         virtual
110         ~CommandOptions () {}
111
112         virtual Error
113         SetOptionValue (uint32_t option_idx, const char *option_arg)
114         {
115             Error error;
116             const int short_option = m_getopt_table[option_idx].val;
117
118             switch (short_option)
119             {
120                 case 'g':
121                     m_global = true;
122                     break;
123                 default:
124                     error.SetErrorStringWithFormat ("unrecognized options '%c'", short_option);
125                     break;
126             }
127
128             return error;
129         }
130
131         void
132         OptionParsingStarting ()
133         {
134             m_global = false;
135         }
136         
137         const OptionDefinition*
138         GetDefinitions ()
139         {
140             return g_option_table;
141         }
142
143         // Options table: Required for subclasses of Options.
144
145         static OptionDefinition g_option_table[];
146
147         // Instance variables to hold the values for command options.
148
149         bool m_global;
150     };
151
152     virtual int
153     HandleArgumentCompletion (Args &input,
154                               int &cursor_index,
155                               int &cursor_char_position,
156                               OptionElementVector &opt_element_vector,
157                               int match_start_point,
158                               int max_return_elements,
159                               bool &word_complete,
160                               StringList &matches)
161     {
162         std::string completion_str (input.GetArgumentAtIndex (cursor_index), cursor_char_position);
163
164         const size_t argc = input.GetArgumentCount();
165         const char *arg = NULL;
166         int setting_var_idx;
167         for (setting_var_idx = 1; setting_var_idx < static_cast<int>(argc);
168              ++setting_var_idx)
169         {
170             arg = input.GetArgumentAtIndex(setting_var_idx);
171             if (arg && arg[0] != '-')
172                 break; // We found our setting variable name index
173         }
174         if (cursor_index == setting_var_idx)
175         {
176             // Attempting to complete setting variable name
177             CommandCompletions::InvokeCommonCompletionCallbacks (m_interpreter,
178                                                                  CommandCompletions::eSettingsNameCompletion,
179                                                                  completion_str.c_str(),
180                                                                  match_start_point,
181                                                                  max_return_elements,
182                                                                  NULL,
183                                                                  word_complete,
184                                                                  matches);
185         }
186         else
187         {
188             arg = input.GetArgumentAtIndex(cursor_index);
189             
190             if (arg)
191             {
192                 if (arg[0] == '-')
193                 {
194                     // Complete option name
195                 }
196                 else
197                 {
198                     // Complete setting value
199                     const char *setting_var_name = input.GetArgumentAtIndex(setting_var_idx);
200                     Error error;
201                     lldb::OptionValueSP value_sp (m_interpreter.GetDebugger().GetPropertyValue(&m_exe_ctx, setting_var_name, false, error));
202                     if (value_sp)
203                     {
204                         value_sp->AutoComplete (m_interpreter,
205                                                 completion_str.c_str(),
206                                                 match_start_point,
207                                                 max_return_elements,
208                                                 word_complete,
209                                                 matches);
210                     }
211                 }
212             }
213         }
214         return matches.GetSize();
215     }
216     
217 protected:
218     virtual bool
219     DoExecute (const char *command, CommandReturnObject &result)
220     {
221         Args cmd_args(command);
222
223         // Process possible options.
224         if (!ParseOptions (cmd_args, result))
225             return false;
226
227         const size_t argc = cmd_args.GetArgumentCount ();
228         if ((argc < 2) && (!m_options.m_global))
229         {
230             result.AppendError ("'settings set' takes more arguments");
231             result.SetStatus (eReturnStatusFailed);
232             return false;
233         }
234
235         const char *var_name = cmd_args.GetArgumentAtIndex (0);
236         if ((var_name == NULL) || (var_name[0] == '\0'))
237         {
238             result.AppendError ("'settings set' command requires a valid variable name");
239             result.SetStatus (eReturnStatusFailed);
240             return false;
241         }
242
243         // Split the raw command into var_name and value pair.
244         llvm::StringRef raw_str(command);
245         std::string var_value_string = raw_str.split(var_name).second.str();
246         const char *var_value_cstr = Args::StripSpaces(var_value_string, true, false, false);
247
248         Error error;
249         if (m_options.m_global)
250         {
251             error = m_interpreter.GetDebugger().SetPropertyValue (NULL,
252                                                                   eVarSetOperationAssign,
253                                                                   var_name,
254                                                                   var_value_cstr);
255         }
256         
257         if (error.Success())
258         {
259             // FIXME this is the same issue as the one in commands script import
260             // we could be setting target.load-script-from-symbol-file which would cause
261             // Python scripts to be loaded, which could run LLDB commands
262             // (e.g. settings set target.process.python-os-plugin-path) and cause a crash
263             // if we did not clear the command's exe_ctx first
264             ExecutionContext exe_ctx(m_exe_ctx);
265             m_exe_ctx.Clear();
266             error = m_interpreter.GetDebugger().SetPropertyValue (&exe_ctx,
267                                                                   eVarSetOperationAssign,
268                                                                   var_name,
269                                                                   var_value_cstr);
270         }
271
272         if (error.Fail())
273         {
274             result.AppendError (error.AsCString());
275             result.SetStatus (eReturnStatusFailed);
276             return false;
277         }
278         else
279         {
280             result.SetStatus (eReturnStatusSuccessFinishResult);
281         }
282
283         return result.Succeeded();
284     }
285 private:
286     CommandOptions m_options;
287 };
288
289 OptionDefinition
290 CommandObjectSettingsSet::CommandOptions::g_option_table[] =
291 {
292     { LLDB_OPT_SET_2, false, "global", 'g', OptionParser::eNoArgument,   NULL, NULL, 0, eArgTypeNone, "Apply the new value to the global default value." },
293     { 0, false, NULL, 0, 0, NULL, NULL, 0, eArgTypeNone, NULL }
294 };
295
296
297 //-------------------------------------------------------------------------
298 // CommandObjectSettingsShow -- Show current values
299 //-------------------------------------------------------------------------
300
301 class CommandObjectSettingsShow : public CommandObjectParsed
302 {
303 public:
304     CommandObjectSettingsShow (CommandInterpreter &interpreter) :
305         CommandObjectParsed (interpreter,
306                              "settings show",
307                              "Show the specified internal debugger setting variable and its value, or show all the currently set variables and their values, if nothing is specified.",
308                              NULL)
309     {
310         CommandArgumentEntry arg1;
311         CommandArgumentData var_name_arg;
312
313         // Define the first (and only) variant of this arg.
314         var_name_arg.arg_type = eArgTypeSettingVariableName;
315         var_name_arg.arg_repetition = eArgRepeatOptional;
316
317         // There is only one variant this argument could be; put it into the argument entry.
318         arg1.push_back (var_name_arg);
319
320         // Push the data for the first argument into the m_arguments vector.
321         m_arguments.push_back (arg1);
322     }
323
324     virtual
325     ~CommandObjectSettingsShow () {}
326
327
328     virtual int
329     HandleArgumentCompletion (Args &input,
330                               int &cursor_index,
331                               int &cursor_char_position,
332                               OptionElementVector &opt_element_vector,
333                               int match_start_point,
334                               int max_return_elements,
335                               bool &word_complete,
336                               StringList &matches)
337     {
338         std::string completion_str (input.GetArgumentAtIndex (cursor_index), cursor_char_position);
339
340         CommandCompletions::InvokeCommonCompletionCallbacks (m_interpreter,
341                                                              CommandCompletions::eSettingsNameCompletion,
342                                                              completion_str.c_str(),
343                                                              match_start_point,
344                                                              max_return_elements,
345                                                              NULL,
346                                                              word_complete,
347                                                              matches);
348         return matches.GetSize();
349     }
350
351 protected:
352     virtual bool
353     DoExecute (Args& args, CommandReturnObject &result)
354     {
355         result.SetStatus (eReturnStatusSuccessFinishResult);
356
357         const size_t argc = args.GetArgumentCount ();
358         if (argc > 0)
359         {
360             for (size_t i=0; i<argc; ++i)
361             {
362                 const char *property_path = args.GetArgumentAtIndex (i);
363
364                 Error error(m_interpreter.GetDebugger().DumpPropertyValue (&m_exe_ctx, result.GetOutputStream(), property_path, OptionValue::eDumpGroupValue));
365                 if (error.Success())
366                 {
367                     result.GetOutputStream().EOL();
368                 }
369                 else
370                 {
371                     result.AppendError (error.AsCString());
372                     result.SetStatus (eReturnStatusFailed);
373                 }
374             }
375         }
376         else
377         {
378             m_interpreter.GetDebugger().DumpAllPropertyValues (&m_exe_ctx, result.GetOutputStream(), OptionValue::eDumpGroupValue);
379         }
380
381         return result.Succeeded();
382     }
383 };
384
385 //-------------------------------------------------------------------------
386 // CommandObjectSettingsList -- List settable variables
387 //-------------------------------------------------------------------------
388
389 class CommandObjectSettingsList : public CommandObjectParsed
390 {
391 public: 
392     CommandObjectSettingsList (CommandInterpreter &interpreter) :
393         CommandObjectParsed (interpreter,
394                              "settings list",
395                              "List and describe all the internal debugger settings variables that are available to the user to 'set' or 'show', or describe a particular variable or set of variables (by specifying the variable name or a common prefix).",
396                              NULL)
397     {
398         CommandArgumentEntry arg;
399         CommandArgumentData var_name_arg;
400         CommandArgumentData prefix_name_arg;
401
402         // Define the first variant of this arg.
403         var_name_arg.arg_type = eArgTypeSettingVariableName;
404         var_name_arg.arg_repetition = eArgRepeatOptional;
405
406         // Define the second variant of this arg.
407         prefix_name_arg.arg_type = eArgTypeSettingPrefix;
408         prefix_name_arg.arg_repetition = eArgRepeatOptional;
409
410         arg.push_back (var_name_arg);
411         arg.push_back (prefix_name_arg);
412
413         // Push the data for the first argument into the m_arguments vector.
414         m_arguments.push_back (arg);
415     }
416
417     virtual
418     ~CommandObjectSettingsList () {}
419
420     virtual int
421     HandleArgumentCompletion (Args &input,
422                               int &cursor_index,
423                               int &cursor_char_position,
424                               OptionElementVector &opt_element_vector,
425                               int match_start_point,
426                               int max_return_elements,
427                               bool &word_complete,
428                               StringList &matches)
429     {
430         std::string completion_str (input.GetArgumentAtIndex (cursor_index), cursor_char_position);
431
432         CommandCompletions::InvokeCommonCompletionCallbacks (m_interpreter,
433                                                              CommandCompletions::eSettingsNameCompletion,
434                                                              completion_str.c_str(),
435                                                              match_start_point,
436                                                              max_return_elements,
437                                                              NULL,
438                                                              word_complete,
439                                                              matches);
440         return matches.GetSize();
441     }
442
443 protected:
444     virtual bool
445     DoExecute (Args& args, CommandReturnObject &result)
446     {
447         result.SetStatus (eReturnStatusSuccessFinishResult);
448
449         const bool will_modify = false;
450         const size_t argc = args.GetArgumentCount ();
451         if (argc > 0)
452         {
453             const bool dump_qualified_name = true;
454
455             for (size_t i=0; i<argc; ++i)
456             {
457                 const char *property_path = args.GetArgumentAtIndex (i);
458                 
459                 const Property *property = m_interpreter.GetDebugger().GetValueProperties()->GetPropertyAtPath (&m_exe_ctx, will_modify, property_path);
460
461                 if (property)
462                 {
463                     property->DumpDescription (m_interpreter, result.GetOutputStream(), 0, dump_qualified_name);
464                 }
465                 else
466                 {
467                     result.AppendErrorWithFormat ("invalid property path '%s'", property_path);
468                     result.SetStatus (eReturnStatusFailed);
469                 }
470             }
471         }
472         else
473         {
474             m_interpreter.GetDebugger().DumpAllDescriptions (m_interpreter, result.GetOutputStream());
475         }
476
477         return result.Succeeded();
478     }
479 };
480
481 //-------------------------------------------------------------------------
482 // CommandObjectSettingsRemove
483 //-------------------------------------------------------------------------
484
485 class CommandObjectSettingsRemove : public CommandObjectRaw
486 {
487 public:
488     CommandObjectSettingsRemove (CommandInterpreter &interpreter) :
489         CommandObjectRaw (interpreter,
490                           "settings remove",
491                           "Remove the specified element from an array or dictionary settings variable.",
492                           NULL)
493     {
494         CommandArgumentEntry arg1;
495         CommandArgumentEntry arg2;
496         CommandArgumentData var_name_arg;
497         CommandArgumentData index_arg;
498         CommandArgumentData key_arg;
499
500         // Define the first (and only) variant of this arg.
501         var_name_arg.arg_type = eArgTypeSettingVariableName;
502         var_name_arg.arg_repetition = eArgRepeatPlain;
503
504         // There is only one variant this argument could be; put it into the argument entry.
505         arg1.push_back (var_name_arg);
506
507         // Define the first variant of this arg.
508         index_arg.arg_type = eArgTypeSettingIndex;
509         index_arg.arg_repetition = eArgRepeatPlain;
510
511         // Define the second variant of this arg.
512         key_arg.arg_type = eArgTypeSettingKey;
513         key_arg.arg_repetition = eArgRepeatPlain;
514
515         // Push both variants into this arg
516         arg2.push_back (index_arg);
517         arg2.push_back (key_arg);
518
519         // Push the data for the first argument into the m_arguments vector.
520         m_arguments.push_back (arg1);
521         m_arguments.push_back (arg2);
522     }
523
524     virtual
525     ~CommandObjectSettingsRemove () {}
526
527     virtual int
528     HandleArgumentCompletion (Args &input,
529                               int &cursor_index,
530                               int &cursor_char_position,
531                               OptionElementVector &opt_element_vector,
532                               int match_start_point,
533                               int max_return_elements,
534                               bool &word_complete,
535                               StringList &matches)
536     {
537         std::string completion_str (input.GetArgumentAtIndex (cursor_index), cursor_char_position);
538
539         // Attempting to complete variable name
540         if (cursor_index < 2)
541             CommandCompletions::InvokeCommonCompletionCallbacks (m_interpreter,
542                                                                  CommandCompletions::eSettingsNameCompletion,
543                                                                  completion_str.c_str(),
544                                                                  match_start_point,
545                                                                  max_return_elements,
546                                                                  NULL,
547                                                                  word_complete,
548                                                                  matches);
549
550         return matches.GetSize();
551     }
552
553 protected:
554     virtual bool
555     DoExecute (const char *command, CommandReturnObject &result)
556     {
557         result.SetStatus (eReturnStatusSuccessFinishNoResult);
558      
559         Args cmd_args(command);
560         
561         // Process possible options.
562         if (!ParseOptions (cmd_args, result))
563             return false;
564         
565         const size_t argc = cmd_args.GetArgumentCount ();
566         if (argc == 0)
567         {
568             result.AppendError ("'settings set' takes an array or dictionary item, or an array followed by one or more indexes, or a dictionary followed by one or more key names to remove");
569             result.SetStatus (eReturnStatusFailed);
570             return false;
571         }
572         
573         const char *var_name = cmd_args.GetArgumentAtIndex (0);
574         if ((var_name == NULL) || (var_name[0] == '\0'))
575         {
576             result.AppendError ("'settings set' command requires a valid variable name");
577             result.SetStatus (eReturnStatusFailed);
578             return false;
579         }
580         
581         // Split the raw command into var_name and value pair.
582         llvm::StringRef raw_str(command);
583         std::string var_value_string = raw_str.split(var_name).second.str();
584         const char *var_value_cstr = Args::StripSpaces(var_value_string, true, true, false);
585         
586         Error error (m_interpreter.GetDebugger().SetPropertyValue (&m_exe_ctx,
587                                                                    eVarSetOperationRemove,
588                                                                    var_name,
589                                                                    var_value_cstr));
590         if (error.Fail())
591         {
592             result.AppendError (error.AsCString());
593             result.SetStatus (eReturnStatusFailed);
594             return false;
595         }
596         
597         return result.Succeeded();
598     }
599 };
600
601 //-------------------------------------------------------------------------
602 // CommandObjectSettingsReplace
603 //-------------------------------------------------------------------------
604
605 class CommandObjectSettingsReplace : public CommandObjectRaw
606 {
607 public:
608     CommandObjectSettingsReplace (CommandInterpreter &interpreter) :
609         CommandObjectRaw (interpreter,
610                           "settings replace",
611                           "Replace the specified element from an internal debugger settings array or dictionary variable with the specified new value.",
612                           NULL)
613     {
614         CommandArgumentEntry arg1;
615         CommandArgumentEntry arg2;
616         CommandArgumentEntry arg3;
617         CommandArgumentData var_name_arg;
618         CommandArgumentData index_arg;
619         CommandArgumentData key_arg;
620         CommandArgumentData value_arg;
621
622         // Define the first (and only) variant of this arg.
623         var_name_arg.arg_type = eArgTypeSettingVariableName;
624         var_name_arg.arg_repetition = eArgRepeatPlain;
625
626         // There is only one variant this argument could be; put it into the argument entry.
627         arg1.push_back (var_name_arg);
628
629         // Define the first (variant of this arg.
630         index_arg.arg_type = eArgTypeSettingIndex;
631         index_arg.arg_repetition = eArgRepeatPlain;
632
633         // Define the second (variant of this arg.
634         key_arg.arg_type = eArgTypeSettingKey;
635         key_arg.arg_repetition = eArgRepeatPlain;
636
637         // Put both variants into this arg
638         arg2.push_back (index_arg);
639         arg2.push_back (key_arg);
640
641         // Define the first (and only) variant of this arg.
642         value_arg.arg_type = eArgTypeValue;
643         value_arg.arg_repetition = eArgRepeatPlain;
644
645         // There is only one variant this argument could be; put it into the argument entry.
646         arg3.push_back (value_arg);
647
648         // Push the data for the first argument into the m_arguments vector.
649         m_arguments.push_back (arg1);
650         m_arguments.push_back (arg2);
651         m_arguments.push_back (arg3);
652     }
653
654
655     virtual
656     ~CommandObjectSettingsReplace () {}
657
658     // Overrides base class's behavior where WantsCompletion = !WantsRawCommandString.
659     virtual bool
660     WantsCompletion() { return true; }
661
662     virtual int
663     HandleArgumentCompletion (Args &input,
664                               int &cursor_index,
665                               int &cursor_char_position,
666                               OptionElementVector &opt_element_vector,
667                               int match_start_point,
668                               int max_return_elements,
669                               bool &word_complete,
670                               StringList &matches)
671     {
672         std::string completion_str (input.GetArgumentAtIndex (cursor_index), cursor_char_position);
673
674         // Attempting to complete variable name
675         if (cursor_index < 2)
676             CommandCompletions::InvokeCommonCompletionCallbacks (m_interpreter,
677                                                                  CommandCompletions::eSettingsNameCompletion,
678                                                                  completion_str.c_str(),
679                                                                  match_start_point,
680                                                                  max_return_elements,
681                                                                  NULL,
682                                                                  word_complete,
683                                                                  matches);
684
685         return matches.GetSize();
686     }
687
688 protected:
689     virtual bool
690     DoExecute (const char *command, CommandReturnObject &result)
691     {
692         result.SetStatus (eReturnStatusSuccessFinishNoResult);
693
694         Args cmd_args(command);
695         const char *var_name = cmd_args.GetArgumentAtIndex (0);
696         if ((var_name == NULL) || (var_name[0] == '\0'))
697         {
698             result.AppendError ("'settings replace' command requires a valid variable name; No value supplied");
699             result.SetStatus (eReturnStatusFailed);
700             return false;
701         }
702
703
704         // Split the raw command into var_name, index_value, and value triple.
705         llvm::StringRef raw_str(command);
706         std::string var_value_string = raw_str.split(var_name).second.str();
707         const char *var_value_cstr = Args::StripSpaces(var_value_string, true, true, false);
708
709         Error error(m_interpreter.GetDebugger().SetPropertyValue (&m_exe_ctx,
710                                                                   eVarSetOperationReplace,
711                                                                   var_name,
712                                                                   var_value_cstr));
713         if (error.Fail())
714         {
715             result.AppendError (error.AsCString());
716             result.SetStatus (eReturnStatusFailed);
717             return false;
718         }
719         else
720         {
721             result.SetStatus (eReturnStatusSuccessFinishNoResult);
722
723         }
724
725         return result.Succeeded();
726     }
727 };
728
729 //-------------------------------------------------------------------------
730 // CommandObjectSettingsInsertBefore
731 //-------------------------------------------------------------------------
732
733 class CommandObjectSettingsInsertBefore : public CommandObjectRaw
734 {
735 public:
736     CommandObjectSettingsInsertBefore (CommandInterpreter &interpreter) :
737         CommandObjectRaw (interpreter,
738                           "settings insert-before",
739                           "Insert value(s) into an internal debugger settings array variable, immediately before the specified element.",
740                           NULL)
741     {
742         CommandArgumentEntry arg1;
743         CommandArgumentEntry arg2;
744         CommandArgumentEntry arg3;
745         CommandArgumentData var_name_arg;
746         CommandArgumentData index_arg;
747         CommandArgumentData value_arg;
748
749         // Define the first (and only) variant of this arg.
750         var_name_arg.arg_type = eArgTypeSettingVariableName;
751         var_name_arg.arg_repetition = eArgRepeatPlain;
752
753         // There is only one variant this argument could be; put it into the argument entry.
754         arg1.push_back (var_name_arg);
755
756         // Define the first (variant of this arg.
757         index_arg.arg_type = eArgTypeSettingIndex;
758         index_arg.arg_repetition = eArgRepeatPlain;
759
760         // There is only one variant this argument could be; put it into the argument entry.
761         arg2.push_back (index_arg);
762
763         // Define the first (and only) variant of this arg.
764         value_arg.arg_type = eArgTypeValue;
765         value_arg.arg_repetition = eArgRepeatPlain;
766
767         // There is only one variant this argument could be; put it into the argument entry.
768         arg3.push_back (value_arg);
769
770         // Push the data for the first argument into the m_arguments vector.
771         m_arguments.push_back (arg1);
772         m_arguments.push_back (arg2);
773         m_arguments.push_back (arg3);
774     }
775
776     virtual
777     ~CommandObjectSettingsInsertBefore () {}
778
779     // Overrides base class's behavior where WantsCompletion = !WantsRawCommandString.
780     virtual bool
781     WantsCompletion() { return true; }
782
783     virtual int
784     HandleArgumentCompletion (Args &input,
785                               int &cursor_index,
786                               int &cursor_char_position,
787                               OptionElementVector &opt_element_vector,
788                               int match_start_point,
789                               int max_return_elements,
790                               bool &word_complete,
791                               StringList &matches)
792     {
793         std::string completion_str (input.GetArgumentAtIndex (cursor_index), cursor_char_position);
794
795         // Attempting to complete variable name
796         if (cursor_index < 2)
797             CommandCompletions::InvokeCommonCompletionCallbacks (m_interpreter,
798                                                                  CommandCompletions::eSettingsNameCompletion,
799                                                                  completion_str.c_str(),
800                                                                  match_start_point,
801                                                                  max_return_elements,
802                                                                  NULL,
803                                                                  word_complete,
804                                                                  matches);
805
806         return matches.GetSize();
807     }
808
809 protected:
810     virtual bool
811     DoExecute (const char *command, CommandReturnObject &result)
812     {
813         result.SetStatus (eReturnStatusSuccessFinishNoResult);
814
815         Args cmd_args(command);
816         const size_t argc = cmd_args.GetArgumentCount ();
817
818         if (argc < 3)
819         {
820             result.AppendError ("'settings insert-before' takes more arguments");
821             result.SetStatus (eReturnStatusFailed);
822             return false;
823         }
824
825         const char *var_name = cmd_args.GetArgumentAtIndex (0);
826         if ((var_name == NULL) || (var_name[0] == '\0'))
827         {
828             result.AppendError ("'settings insert-before' command requires a valid variable name; No value supplied");
829             result.SetStatus (eReturnStatusFailed);
830             return false;
831         }
832
833         // Split the raw command into var_name, index_value, and value triple.
834         llvm::StringRef raw_str(command);
835         std::string var_value_string = raw_str.split(var_name).second.str();
836         const char *var_value_cstr = Args::StripSpaces(var_value_string, true, true, false);
837
838         Error error(m_interpreter.GetDebugger().SetPropertyValue (&m_exe_ctx,
839                                                                   eVarSetOperationInsertBefore,
840                                                                   var_name,
841                                                                   var_value_cstr));
842         if (error.Fail())
843         {
844             result.AppendError (error.AsCString());
845             result.SetStatus (eReturnStatusFailed);
846             return false;
847         }
848
849         return result.Succeeded();
850     }
851 };
852
853 //-------------------------------------------------------------------------
854 // CommandObjectSettingInsertAfter
855 //-------------------------------------------------------------------------
856
857 class CommandObjectSettingsInsertAfter : public CommandObjectRaw
858 {
859 public:
860     CommandObjectSettingsInsertAfter (CommandInterpreter &interpreter) :
861         CommandObjectRaw (interpreter,
862                           "settings insert-after",
863                           "Insert value(s) into an internal debugger settings array variable, immediately after the specified element.",
864                           NULL)
865     {
866         CommandArgumentEntry arg1;
867         CommandArgumentEntry arg2;
868         CommandArgumentEntry arg3;
869         CommandArgumentData var_name_arg;
870         CommandArgumentData index_arg;
871         CommandArgumentData value_arg;
872
873         // Define the first (and only) variant of this arg.
874         var_name_arg.arg_type = eArgTypeSettingVariableName;
875         var_name_arg.arg_repetition = eArgRepeatPlain;
876
877         // There is only one variant this argument could be; put it into the argument entry.
878         arg1.push_back (var_name_arg);
879
880         // Define the first (variant of this arg.
881         index_arg.arg_type = eArgTypeSettingIndex;
882         index_arg.arg_repetition = eArgRepeatPlain;
883
884         // There is only one variant this argument could be; put it into the argument entry.
885         arg2.push_back (index_arg);
886
887         // Define the first (and only) variant of this arg.
888         value_arg.arg_type = eArgTypeValue;
889         value_arg.arg_repetition = eArgRepeatPlain;
890
891         // There is only one variant this argument could be; put it into the argument entry.
892         arg3.push_back (value_arg);
893
894         // Push the data for the first argument into the m_arguments vector.
895         m_arguments.push_back (arg1);
896         m_arguments.push_back (arg2);
897         m_arguments.push_back (arg3);
898     }
899
900     virtual
901     ~CommandObjectSettingsInsertAfter () {}
902
903     // Overrides base class's behavior where WantsCompletion = !WantsRawCommandString.
904     virtual bool
905     WantsCompletion() { return true; }
906
907     virtual int
908     HandleArgumentCompletion (Args &input,
909                               int &cursor_index,
910                               int &cursor_char_position,
911                               OptionElementVector &opt_element_vector,
912                               int match_start_point,
913                               int max_return_elements,
914                               bool &word_complete,
915                               StringList &matches)
916     {
917         std::string completion_str (input.GetArgumentAtIndex (cursor_index), cursor_char_position);
918
919         // Attempting to complete variable name
920         if (cursor_index < 2)
921             CommandCompletions::InvokeCommonCompletionCallbacks (m_interpreter,
922                                                                  CommandCompletions::eSettingsNameCompletion,
923                                                                  completion_str.c_str(),
924                                                                  match_start_point,
925                                                                  max_return_elements,
926                                                                  NULL,
927                                                                  word_complete,
928                                                                  matches);
929
930         return matches.GetSize();
931     }
932     
933 protected:
934     virtual bool
935     DoExecute (const char *command, CommandReturnObject &result)
936     {
937         result.SetStatus (eReturnStatusSuccessFinishNoResult);
938
939         Args cmd_args(command);
940         const size_t argc = cmd_args.GetArgumentCount ();
941
942         if (argc < 3)
943         {
944             result.AppendError ("'settings insert-after' takes more arguments");
945             result.SetStatus (eReturnStatusFailed);
946             return false;
947         }
948
949         const char *var_name = cmd_args.GetArgumentAtIndex (0);
950         if ((var_name == NULL) || (var_name[0] == '\0'))
951         {
952             result.AppendError ("'settings insert-after' command requires a valid variable name; No value supplied");
953             result.SetStatus (eReturnStatusFailed);
954             return false;
955         }
956
957         // Split the raw command into var_name, index_value, and value triple.
958         llvm::StringRef raw_str(command);
959         std::string var_value_string = raw_str.split(var_name).second.str();
960         const char *var_value_cstr = Args::StripSpaces(var_value_string, true, true, false);
961
962         Error error(m_interpreter.GetDebugger().SetPropertyValue (&m_exe_ctx,
963                                                                   eVarSetOperationInsertAfter,
964                                                                   var_name,
965                                                                   var_value_cstr));
966         if (error.Fail())
967         {
968             result.AppendError (error.AsCString());
969             result.SetStatus (eReturnStatusFailed);
970             return false;
971         }
972
973         return result.Succeeded();
974     }
975 };
976
977 //-------------------------------------------------------------------------
978 // CommandObjectSettingsAppend
979 //-------------------------------------------------------------------------
980
981 class CommandObjectSettingsAppend : public CommandObjectRaw
982 {
983 public:
984     CommandObjectSettingsAppend (CommandInterpreter &interpreter) :
985         CommandObjectRaw (interpreter,
986                           "settings append",
987                           "Append a new value to the end of an internal debugger settings array, dictionary or string variable.",
988                           NULL)
989     {
990         CommandArgumentEntry arg1;
991         CommandArgumentEntry arg2;
992         CommandArgumentData var_name_arg;
993         CommandArgumentData value_arg;
994
995         // Define the first (and only) variant of this arg.
996         var_name_arg.arg_type = eArgTypeSettingVariableName;
997         var_name_arg.arg_repetition = eArgRepeatPlain;
998
999         // There is only one variant this argument could be; put it into the argument entry.
1000         arg1.push_back (var_name_arg);
1001
1002         // Define the first (and only) variant of this arg.
1003         value_arg.arg_type = eArgTypeValue;
1004         value_arg.arg_repetition = eArgRepeatPlain;
1005
1006         // There is only one variant this argument could be; put it into the argument entry.
1007         arg2.push_back (value_arg);
1008
1009         // Push the data for the first argument into the m_arguments vector.
1010         m_arguments.push_back (arg1);
1011         m_arguments.push_back (arg2);
1012     }
1013
1014     virtual
1015     ~CommandObjectSettingsAppend () {}
1016
1017     // Overrides base class's behavior where WantsCompletion = !WantsRawCommandString.
1018     virtual bool
1019     WantsCompletion() { return true; }
1020
1021     virtual int
1022     HandleArgumentCompletion (Args &input,
1023                               int &cursor_index,
1024                               int &cursor_char_position,
1025                               OptionElementVector &opt_element_vector,
1026                               int match_start_point,
1027                               int max_return_elements,
1028                               bool &word_complete,
1029                               StringList &matches)
1030     {
1031         std::string completion_str (input.GetArgumentAtIndex (cursor_index), cursor_char_position);
1032
1033         // Attempting to complete variable name
1034         if (cursor_index < 2)
1035             CommandCompletions::InvokeCommonCompletionCallbacks (m_interpreter,
1036                                                                  CommandCompletions::eSettingsNameCompletion,
1037                                                                  completion_str.c_str(),
1038                                                                  match_start_point,
1039                                                                  max_return_elements,
1040                                                                  NULL,
1041                                                                  word_complete,
1042                                                                  matches);
1043
1044         return matches.GetSize();
1045     }
1046
1047 protected:
1048     virtual bool
1049     DoExecute (const char *command, CommandReturnObject &result)
1050     {
1051         result.SetStatus (eReturnStatusSuccessFinishNoResult);
1052         Args cmd_args(command);
1053         const size_t argc = cmd_args.GetArgumentCount ();
1054
1055         if (argc < 2)
1056         {
1057             result.AppendError ("'settings append' takes more arguments");
1058             result.SetStatus (eReturnStatusFailed);
1059             return false;
1060         }
1061
1062         const char *var_name = cmd_args.GetArgumentAtIndex (0);
1063         if ((var_name == NULL) || (var_name[0] == '\0'))
1064         {
1065             result.AppendError ("'settings append' command requires a valid variable name; No value supplied");
1066             result.SetStatus (eReturnStatusFailed);
1067             return false;
1068         }
1069
1070         // Do not perform cmd_args.Shift() since StringRef is manipulating the
1071         // raw character string later on.
1072
1073         // Split the raw command into var_name and value pair.
1074         llvm::StringRef raw_str(command);
1075         std::string var_value_string = raw_str.split(var_name).second.str();
1076         const char *var_value_cstr = Args::StripSpaces(var_value_string, true, true, false);
1077
1078         Error error(m_interpreter.GetDebugger().SetPropertyValue (&m_exe_ctx,
1079                                                                   eVarSetOperationAppend,
1080                                                                   var_name,
1081                                                                   var_value_cstr));
1082         if (error.Fail())
1083         {
1084             result.AppendError (error.AsCString());
1085             result.SetStatus (eReturnStatusFailed);
1086             return false;
1087         }
1088
1089         return result.Succeeded();
1090     }
1091 };
1092
1093 //-------------------------------------------------------------------------
1094 // CommandObjectSettingsClear
1095 //-------------------------------------------------------------------------
1096
1097 class CommandObjectSettingsClear : public CommandObjectParsed
1098 {
1099 public:
1100     CommandObjectSettingsClear (CommandInterpreter &interpreter) :
1101         CommandObjectParsed (interpreter,
1102                              "settings clear",
1103                              "Erase all the contents of an internal debugger settings variables; this is only valid for variables with clearable types, i.e. strings, arrays or dictionaries.",
1104                              NULL)
1105     {
1106         CommandArgumentEntry arg;
1107         CommandArgumentData var_name_arg;
1108
1109         // Define the first (and only) variant of this arg.
1110         var_name_arg.arg_type = eArgTypeSettingVariableName;
1111         var_name_arg.arg_repetition = eArgRepeatPlain;
1112
1113         // There is only one variant this argument could be; put it into the argument entry.
1114         arg.push_back (var_name_arg);
1115
1116         // Push the data for the first argument into the m_arguments vector.
1117         m_arguments.push_back (arg);
1118     }
1119
1120     virtual
1121     ~CommandObjectSettingsClear () {}
1122
1123     virtual int
1124     HandleArgumentCompletion (Args &input,
1125                               int &cursor_index,
1126                               int &cursor_char_position,
1127                               OptionElementVector &opt_element_vector,
1128                               int match_start_point,
1129                               int max_return_elements,
1130                               bool &word_complete,
1131                               StringList &matches)
1132     {
1133         std::string completion_str (input.GetArgumentAtIndex (cursor_index), cursor_char_position);
1134
1135         // Attempting to complete variable name
1136         if (cursor_index < 2)
1137             CommandCompletions::InvokeCommonCompletionCallbacks (m_interpreter,
1138                                                                  CommandCompletions::eSettingsNameCompletion,
1139                                                                  completion_str.c_str(),
1140                                                                  match_start_point,
1141                                                                  max_return_elements,
1142                                                                  NULL,
1143                                                                  word_complete,
1144                                                                  matches);
1145
1146         return matches.GetSize();
1147     }
1148
1149 protected:
1150     virtual bool
1151     DoExecute (Args& command, CommandReturnObject &result)
1152     {
1153         result.SetStatus (eReturnStatusSuccessFinishNoResult);
1154         const size_t argc = command.GetArgumentCount ();
1155
1156         if (argc != 1)
1157         {
1158             result.AppendError ("'settings clear' takes exactly one argument");
1159             result.SetStatus (eReturnStatusFailed);
1160             return false;
1161         }
1162
1163         const char *var_name = command.GetArgumentAtIndex (0);
1164         if ((var_name == NULL) || (var_name[0] == '\0'))
1165         {
1166             result.AppendError ("'settings clear' command requires a valid variable name; No value supplied");
1167             result.SetStatus (eReturnStatusFailed);
1168             return false;
1169         }
1170         
1171         Error error (m_interpreter.GetDebugger().SetPropertyValue (&m_exe_ctx,
1172                                                                    eVarSetOperationClear,
1173                                                                    var_name,
1174                                                                    NULL));
1175         if (error.Fail())
1176         {
1177             result.AppendError (error.AsCString());
1178             result.SetStatus (eReturnStatusFailed);
1179             return false;
1180         }
1181
1182         return result.Succeeded();
1183     }
1184 };
1185
1186 //-------------------------------------------------------------------------
1187 // CommandObjectMultiwordSettings
1188 //-------------------------------------------------------------------------
1189
1190 CommandObjectMultiwordSettings::CommandObjectMultiwordSettings (CommandInterpreter &interpreter) :
1191     CommandObjectMultiword (interpreter,
1192                             "settings",
1193                             "A set of commands for manipulating internal settable debugger variables.",
1194                             "settings <command> [<command-options>]")
1195 {
1196     LoadSubCommand ("set",           CommandObjectSP (new CommandObjectSettingsSet (interpreter)));
1197     LoadSubCommand ("show",          CommandObjectSP (new CommandObjectSettingsShow (interpreter)));
1198     LoadSubCommand ("list",          CommandObjectSP (new CommandObjectSettingsList (interpreter)));
1199     LoadSubCommand ("remove",        CommandObjectSP (new CommandObjectSettingsRemove (interpreter)));
1200     LoadSubCommand ("replace",       CommandObjectSP (new CommandObjectSettingsReplace (interpreter)));
1201     LoadSubCommand ("insert-before", CommandObjectSP (new CommandObjectSettingsInsertBefore (interpreter)));
1202     LoadSubCommand ("insert-after",  CommandObjectSP (new CommandObjectSettingsInsertAfter (interpreter)));
1203     LoadSubCommand ("append",        CommandObjectSP (new CommandObjectSettingsAppend (interpreter)));
1204     LoadSubCommand ("clear",         CommandObjectSP (new CommandObjectSettingsClear (interpreter)));
1205 }
1206
1207 CommandObjectMultiwordSettings::~CommandObjectMultiwordSettings ()
1208 {
1209 }