1 //===-- CommandObjectPlatform.cpp -------------------------------*- C++ -*-===//
3 // The LLVM Compiler Infrastructure
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
8 //===----------------------------------------------------------------------===//
10 #include "lldb/lldb-python.h"
12 #include "CommandObjectPlatform.h"
16 // Other libraries and framework includes
18 #include "lldb/Core/DataExtractor.h"
19 #include "lldb/Core/Debugger.h"
20 #include "lldb/Core/Module.h"
21 #include "lldb/Core/PluginManager.h"
22 #include "lldb/Host/StringConvert.h"
23 #include "lldb/Interpreter/Args.h"
24 #include "lldb/Interpreter/CommandInterpreter.h"
25 #include "lldb/Interpreter/CommandOptionValidators.h"
26 #include "lldb/Interpreter/CommandReturnObject.h"
27 #include "lldb/Interpreter/OptionGroupFile.h"
28 #include "lldb/Interpreter/OptionGroupPlatform.h"
29 #include "lldb/Target/ExecutionContext.h"
30 #include "lldb/Target/Platform.h"
31 #include "lldb/Target/Process.h"
32 #include "lldb/Utility/Utils.h"
35 using namespace lldb_private;
38 ParsePermissionString(const char* permissions)
40 if (strlen(permissions) != 9)
42 bool user_r,user_w,user_x,
43 group_r,group_w,group_x,
44 world_r,world_w,world_x;
46 user_r = (permissions[0] == 'r');
47 user_w = (permissions[1] == 'w');
48 user_x = (permissions[2] == 'x');
50 group_r = (permissions[3] == 'r');
51 group_w = (permissions[4] == 'w');
52 group_x = (permissions[5] == 'x');
54 world_r = (permissions[6] == 'r');
55 world_w = (permissions[7] == 'w');
56 world_x = (permissions[8] == 'x');
58 mode_t user,group,world;
59 user = (user_r ? 4 : 0) | (user_w ? 2 : 0) | (user_x ? 1 : 0);
60 group = (group_r ? 4 : 0) | (group_w ? 2 : 0) | (group_x ? 1 : 0);
61 world = (world_r ? 4 : 0) | (world_w ? 2 : 0) | (world_x ? 1 : 0);
63 return user | group | world;
66 static OptionDefinition
67 g_permissions_options[] =
69 { LLDB_OPT_SET_ALL, false, "permissions-value", 'v', OptionParser::eRequiredArgument, NULL, NULL, 0, eArgTypePermissionsNumber , "Give out the numeric value for permissions (e.g. 757)" },
70 { LLDB_OPT_SET_ALL, false, "permissions-string", 's', OptionParser::eRequiredArgument, NULL, NULL, 0, eArgTypePermissionsString , "Give out the string value for permissions (e.g. rwxr-xr--)." },
71 { LLDB_OPT_SET_ALL, false, "user-read", 'r', OptionParser::eNoArgument, NULL, NULL, 0, eArgTypeNone , "Allow user to read." },
72 { LLDB_OPT_SET_ALL, false, "user-write", 'w', OptionParser::eNoArgument, NULL, NULL, 0, eArgTypeNone , "Allow user to write." },
73 { LLDB_OPT_SET_ALL, false, "user-exec", 'x', OptionParser::eNoArgument, NULL, NULL, 0, eArgTypeNone , "Allow user to execute." },
75 { LLDB_OPT_SET_ALL, false, "group-read", 'R', OptionParser::eNoArgument, NULL, NULL, 0, eArgTypeNone , "Allow group to read." },
76 { LLDB_OPT_SET_ALL, false, "group-write", 'W', OptionParser::eNoArgument, NULL, NULL, 0, eArgTypeNone , "Allow group to write." },
77 { LLDB_OPT_SET_ALL, false, "group-exec", 'X', OptionParser::eNoArgument, NULL, NULL, 0, eArgTypeNone , "Allow group to execute." },
79 { LLDB_OPT_SET_ALL, false, "world-read", 'd', OptionParser::eNoArgument, NULL, NULL, 0, eArgTypeNone , "Allow world to read." },
80 { LLDB_OPT_SET_ALL, false, "world-write", 't', OptionParser::eNoArgument, NULL, NULL, 0, eArgTypeNone , "Allow world to write." },
81 { LLDB_OPT_SET_ALL, false, "world-exec", 'e', OptionParser::eNoArgument, NULL, NULL, 0, eArgTypeNone , "Allow world to execute." },
84 class OptionPermissions : public lldb_private::OptionGroup
96 virtual lldb_private::Error
97 SetOptionValue (CommandInterpreter &interpreter,
99 const char *option_arg)
102 char short_option = (char) GetDefinitions()[option_idx].short_option;
103 switch (short_option)
108 uint32_t perms = StringConvert::ToUInt32(option_arg, 777, 8, &ok);
110 error.SetErrorStringWithFormat("invalid value for permissions: %s", option_arg);
112 m_permissions = perms;
117 mode_t perms = ParsePermissionString(option_arg);
118 if (perms == (mode_t)-1)
119 error.SetErrorStringWithFormat("invalid value for permissions: %s", option_arg);
121 m_permissions = perms;
124 m_permissions |= lldb::eFilePermissionsUserRead;
127 m_permissions |= lldb::eFilePermissionsUserWrite;
130 m_permissions |= lldb::eFilePermissionsUserExecute;
133 m_permissions |= lldb::eFilePermissionsGroupRead;
136 m_permissions |= lldb::eFilePermissionsGroupWrite;
139 m_permissions |= lldb::eFilePermissionsGroupExecute;
142 m_permissions |= lldb::eFilePermissionsWorldRead;
145 m_permissions |= lldb::eFilePermissionsWorldWrite;
148 m_permissions |= lldb::eFilePermissionsWorldExecute;
152 error.SetErrorStringWithFormat ("unrecognized option '%c'", short_option);
160 OptionParsingStarting (CommandInterpreter &interpreter)
168 return llvm::array_lengthof(g_permissions_options);
171 const lldb_private::OptionDefinition*
174 return g_permissions_options;
177 // Instance variables to hold the values for command options.
179 uint32_t m_permissions;
181 DISALLOW_COPY_AND_ASSIGN(OptionPermissions);
184 //----------------------------------------------------------------------
185 // "platform select <platform-name>"
186 //----------------------------------------------------------------------
187 class CommandObjectPlatformSelect : public CommandObjectParsed
190 CommandObjectPlatformSelect (CommandInterpreter &interpreter) :
191 CommandObjectParsed (interpreter,
193 "Create a platform if needed and select it as the current platform.",
194 "platform select <platform-name>",
196 m_option_group (interpreter),
197 m_platform_options (false) // Don't include the "--platform" option by passing false
199 m_option_group.Append (&m_platform_options, LLDB_OPT_SET_ALL, 1);
200 m_option_group.Finalize();
204 ~CommandObjectPlatformSelect ()
209 HandleCompletion (Args &input,
211 int &cursor_char_position,
212 int match_start_point,
213 int max_return_elements,
217 std::string completion_str (input.GetArgumentAtIndex(cursor_index));
218 completion_str.erase (cursor_char_position);
220 CommandCompletions::PlatformPluginNames (m_interpreter,
221 completion_str.c_str(),
227 return matches.GetSize();
233 return &m_option_group;
238 DoExecute (Args& args, CommandReturnObject &result)
240 if (args.GetArgumentCount() == 1)
242 const char *platform_name = args.GetArgumentAtIndex (0);
243 if (platform_name && platform_name[0])
245 const bool select = true;
246 m_platform_options.SetPlatformName (platform_name);
248 ArchSpec platform_arch;
249 PlatformSP platform_sp (m_platform_options.CreatePlatformWithOptions (m_interpreter, ArchSpec(), select, error, platform_arch));
252 m_interpreter.GetDebugger().GetPlatformList().SetSelectedPlatform(platform_sp);
254 platform_sp->GetStatus (result.GetOutputStream());
255 result.SetStatus (eReturnStatusSuccessFinishResult);
259 result.AppendError(error.AsCString());
260 result.SetStatus (eReturnStatusFailed);
265 result.AppendError ("invalid platform name");
266 result.SetStatus (eReturnStatusFailed);
271 result.AppendError ("platform create takes a platform name as an argument\n");
272 result.SetStatus (eReturnStatusFailed);
274 return result.Succeeded();
277 OptionGroupOptions m_option_group;
278 OptionGroupPlatform m_platform_options;
281 //----------------------------------------------------------------------
283 //----------------------------------------------------------------------
284 class CommandObjectPlatformList : public CommandObjectParsed
287 CommandObjectPlatformList (CommandInterpreter &interpreter) :
288 CommandObjectParsed (interpreter,
290 "List all platforms that are available.",
297 ~CommandObjectPlatformList ()
303 DoExecute (Args& args, CommandReturnObject &result)
305 Stream &ostrm = result.GetOutputStream();
306 ostrm.Printf("Available platforms:\n");
308 PlatformSP host_platform_sp (Platform::GetHostPlatform());
309 ostrm.Printf ("%s: %s\n",
310 host_platform_sp->GetPluginName().GetCString(),
311 host_platform_sp->GetDescription());
314 for (idx = 0; 1; ++idx)
316 const char *plugin_name = PluginManager::GetPlatformPluginNameAtIndex (idx);
317 if (plugin_name == NULL)
319 const char *plugin_desc = PluginManager::GetPlatformPluginDescriptionAtIndex (idx);
320 if (plugin_desc == NULL)
322 ostrm.Printf("%s: %s\n", plugin_name, plugin_desc);
327 result.AppendError ("no platforms are available\n");
328 result.SetStatus (eReturnStatusFailed);
331 result.SetStatus (eReturnStatusSuccessFinishResult);
332 return result.Succeeded();
336 //----------------------------------------------------------------------
338 //----------------------------------------------------------------------
339 class CommandObjectPlatformStatus : public CommandObjectParsed
342 CommandObjectPlatformStatus (CommandInterpreter &interpreter) :
343 CommandObjectParsed (interpreter,
345 "Display status for the currently selected platform.",
352 ~CommandObjectPlatformStatus ()
358 DoExecute (Args& args, CommandReturnObject &result)
360 Stream &ostrm = result.GetOutputStream();
362 Target *target = m_interpreter.GetDebugger().GetSelectedTarget().get();
363 PlatformSP platform_sp;
366 platform_sp = target->GetPlatform();
370 platform_sp = m_interpreter.GetDebugger().GetPlatformList().GetSelectedPlatform();
374 platform_sp->GetStatus (ostrm);
375 result.SetStatus (eReturnStatusSuccessFinishResult);
379 result.AppendError ("no platform us currently selected\n");
380 result.SetStatus (eReturnStatusFailed);
382 return result.Succeeded();
386 //----------------------------------------------------------------------
387 // "platform connect <connect-url>"
388 //----------------------------------------------------------------------
389 class CommandObjectPlatformConnect : public CommandObjectParsed
392 CommandObjectPlatformConnect (CommandInterpreter &interpreter) :
393 CommandObjectParsed (interpreter,
395 "Connect a platform by name to be the currently selected platform.",
396 "platform connect <connect-url>",
402 ~CommandObjectPlatformConnect ()
408 DoExecute (Args& args, CommandReturnObject &result)
410 Stream &ostrm = result.GetOutputStream();
412 PlatformSP platform_sp (m_interpreter.GetDebugger().GetPlatformList().GetSelectedPlatform());
415 Error error (platform_sp->ConnectRemote (args));
418 platform_sp->GetStatus (ostrm);
419 result.SetStatus (eReturnStatusSuccessFinishResult);
423 result.AppendErrorWithFormat ("%s\n", error.AsCString());
424 result.SetStatus (eReturnStatusFailed);
429 result.AppendError ("no platform is currently selected\n");
430 result.SetStatus (eReturnStatusFailed);
432 return result.Succeeded();
438 PlatformSP platform_sp (m_interpreter.GetDebugger().GetPlatformList().GetSelectedPlatform());
439 OptionGroupOptions* m_platform_options = NULL;
442 m_platform_options = platform_sp->GetConnectionOptions(m_interpreter);
443 if (m_platform_options != NULL && !m_platform_options->m_did_finalize)
444 m_platform_options->Finalize();
446 return m_platform_options;
451 //----------------------------------------------------------------------
452 // "platform disconnect"
453 //----------------------------------------------------------------------
454 class CommandObjectPlatformDisconnect : public CommandObjectParsed
457 CommandObjectPlatformDisconnect (CommandInterpreter &interpreter) :
458 CommandObjectParsed (interpreter,
459 "platform disconnect",
460 "Disconnect a platform by name to be the currently selected platform.",
461 "platform disconnect",
467 ~CommandObjectPlatformDisconnect ()
473 DoExecute (Args& args, CommandReturnObject &result)
475 PlatformSP platform_sp (m_interpreter.GetDebugger().GetPlatformList().GetSelectedPlatform());
478 if (args.GetArgumentCount() == 0)
482 if (platform_sp->IsConnected())
484 // Cache the instance name if there is one since we are
485 // about to disconnect and the name might go with it.
486 const char *hostname_cstr = platform_sp->GetHostname();
487 std::string hostname;
489 hostname.assign (hostname_cstr);
491 error = platform_sp->DisconnectRemote ();
494 Stream &ostrm = result.GetOutputStream();
495 if (hostname.empty())
496 ostrm.Printf ("Disconnected from \"%s\"\n", platform_sp->GetPluginName().GetCString());
498 ostrm.Printf ("Disconnected from \"%s\"\n", hostname.c_str());
499 result.SetStatus (eReturnStatusSuccessFinishResult);
503 result.AppendErrorWithFormat ("%s", error.AsCString());
504 result.SetStatus (eReturnStatusFailed);
510 result.AppendErrorWithFormat ("not connected to '%s'", platform_sp->GetPluginName().GetCString());
511 result.SetStatus (eReturnStatusFailed);
517 result.AppendError ("\"platform disconnect\" doesn't take any arguments");
518 result.SetStatus (eReturnStatusFailed);
523 result.AppendError ("no platform is currently selected");
524 result.SetStatus (eReturnStatusFailed);
526 return result.Succeeded();
530 //----------------------------------------------------------------------
531 // "platform settings"
532 //----------------------------------------------------------------------
533 class CommandObjectPlatformSettings : public CommandObjectParsed
536 CommandObjectPlatformSettings (CommandInterpreter &interpreter) :
537 CommandObjectParsed (interpreter,
539 "Set settings for the current target's platform, or for a platform by name.",
542 m_options (interpreter),
543 m_option_working_dir (LLDB_OPT_SET_1, false, "working-dir", 'w', 0, eArgTypePath, "The working directory for the platform.")
545 m_options.Append (&m_option_working_dir, LLDB_OPT_SET_ALL, LLDB_OPT_SET_1);
549 ~CommandObjectPlatformSettings ()
555 DoExecute (Args& args, CommandReturnObject &result)
557 PlatformSP platform_sp (m_interpreter.GetDebugger().GetPlatformList().GetSelectedPlatform());
560 if (m_option_working_dir.GetOptionValue().OptionWasSet())
561 platform_sp->SetWorkingDirectory (ConstString(m_option_working_dir.GetOptionValue().GetCurrentValue().GetPath().c_str()));
565 result.AppendError ("no platform is currently selected");
566 result.SetStatus (eReturnStatusFailed);
568 return result.Succeeded();
574 if (m_options.DidFinalize() == false)
576 m_options.Append(new OptionPermissions());
577 m_options.Finalize();
583 OptionGroupOptions m_options;
584 OptionGroupFile m_option_working_dir;
589 //----------------------------------------------------------------------
591 //----------------------------------------------------------------------
592 class CommandObjectPlatformMkDir : public CommandObjectParsed
595 CommandObjectPlatformMkDir (CommandInterpreter &interpreter) :
596 CommandObjectParsed (interpreter,
598 "Make a new directory on the remote end.",
601 m_options(interpreter)
606 ~CommandObjectPlatformMkDir ()
611 DoExecute (Args& args, CommandReturnObject &result)
613 PlatformSP platform_sp (m_interpreter.GetDebugger().GetPlatformList().GetSelectedPlatform());
616 std::string cmd_line;
617 args.GetCommandString(cmd_line);
619 const OptionPermissions* options_permissions = (const OptionPermissions*)m_options.GetGroupWithOption('r');
620 if (options_permissions)
621 mode = options_permissions->m_permissions;
623 mode = lldb::eFilePermissionsUserRWX | lldb::eFilePermissionsGroupRWX | lldb::eFilePermissionsWorldRX;
624 Error error = platform_sp->MakeDirectory(cmd_line.c_str(), mode);
627 result.SetStatus (eReturnStatusSuccessFinishResult);
631 result.AppendError(error.AsCString());
632 result.SetStatus (eReturnStatusFailed);
637 result.AppendError ("no platform currently selected\n");
638 result.SetStatus (eReturnStatusFailed);
640 return result.Succeeded();
646 if (m_options.DidFinalize() == false)
648 m_options.Append(new OptionPermissions());
649 m_options.Finalize();
653 OptionGroupOptions m_options;
657 //----------------------------------------------------------------------
659 //----------------------------------------------------------------------
660 class CommandObjectPlatformFOpen : public CommandObjectParsed
663 CommandObjectPlatformFOpen (CommandInterpreter &interpreter) :
664 CommandObjectParsed (interpreter,
665 "platform file open",
666 "Open a file on the remote end.",
669 m_options(interpreter)
674 ~CommandObjectPlatformFOpen ()
679 DoExecute (Args& args, CommandReturnObject &result)
681 PlatformSP platform_sp (m_interpreter.GetDebugger().GetPlatformList().GetSelectedPlatform());
685 std::string cmd_line;
686 args.GetCommandString(cmd_line);
688 const OptionPermissions* options_permissions = (const OptionPermissions*)m_options.GetGroupWithOption('r');
689 if (options_permissions)
690 perms = options_permissions->m_permissions;
692 perms = lldb::eFilePermissionsUserRW | lldb::eFilePermissionsGroupRW | lldb::eFilePermissionsWorldRead;
693 lldb::user_id_t fd = platform_sp->OpenFile(FileSpec(cmd_line.c_str(),false),
694 File::eOpenOptionRead | File::eOpenOptionWrite |
695 File::eOpenOptionAppend | File::eOpenOptionCanCreate,
700 result.AppendMessageWithFormat("File Descriptor = %" PRIu64 "\n",fd);
701 result.SetStatus (eReturnStatusSuccessFinishResult);
705 result.AppendError(error.AsCString());
706 result.SetStatus (eReturnStatusFailed);
711 result.AppendError ("no platform currently selected\n");
712 result.SetStatus (eReturnStatusFailed);
714 return result.Succeeded();
719 if (m_options.DidFinalize() == false)
721 m_options.Append(new OptionPermissions());
722 m_options.Finalize();
726 OptionGroupOptions m_options;
729 //----------------------------------------------------------------------
731 //----------------------------------------------------------------------
732 class CommandObjectPlatformFClose : public CommandObjectParsed
735 CommandObjectPlatformFClose (CommandInterpreter &interpreter) :
736 CommandObjectParsed (interpreter,
737 "platform file close",
738 "Close a file on the remote end.",
745 ~CommandObjectPlatformFClose ()
750 DoExecute (Args& args, CommandReturnObject &result)
752 PlatformSP platform_sp (m_interpreter.GetDebugger().GetPlatformList().GetSelectedPlatform());
755 std::string cmd_line;
756 args.GetCommandString(cmd_line);
757 const lldb::user_id_t fd = StringConvert::ToUInt64(cmd_line.c_str(), UINT64_MAX);
759 bool success = platform_sp->CloseFile(fd, error);
762 result.AppendMessageWithFormat("file %" PRIu64 " closed.\n", fd);
763 result.SetStatus (eReturnStatusSuccessFinishResult);
767 result.AppendError(error.AsCString());
768 result.SetStatus (eReturnStatusFailed);
773 result.AppendError ("no platform currently selected\n");
774 result.SetStatus (eReturnStatusFailed);
776 return result.Succeeded();
780 //----------------------------------------------------------------------
782 //----------------------------------------------------------------------
783 class CommandObjectPlatformFRead : public CommandObjectParsed
786 CommandObjectPlatformFRead (CommandInterpreter &interpreter) :
787 CommandObjectParsed (interpreter,
788 "platform file read",
789 "Read data from a file on the remote end.",
792 m_options (interpreter)
797 ~CommandObjectPlatformFRead ()
802 DoExecute (Args& args, CommandReturnObject &result)
804 PlatformSP platform_sp (m_interpreter.GetDebugger().GetPlatformList().GetSelectedPlatform());
807 std::string cmd_line;
808 args.GetCommandString(cmd_line);
809 const lldb::user_id_t fd = StringConvert::ToUInt64(cmd_line.c_str(), UINT64_MAX);
810 std::string buffer(m_options.m_count,0);
812 uint32_t retcode = platform_sp->ReadFile(fd, m_options.m_offset, &buffer[0], m_options.m_count, error);
813 result.AppendMessageWithFormat("Return = %d\n",retcode);
814 result.AppendMessageWithFormat("Data = \"%s\"\n",buffer.c_str());
815 result.SetStatus (eReturnStatusSuccessFinishResult);
819 result.AppendError ("no platform currently selected\n");
820 result.SetStatus (eReturnStatusFailed);
822 return result.Succeeded();
831 class CommandOptions : public Options
835 CommandOptions (CommandInterpreter &interpreter) :
836 Options (interpreter)
846 SetOptionValue (uint32_t option_idx, const char *option_arg)
849 char short_option = (char) m_getopt_table[option_idx].val;
850 bool success = false;
852 switch (short_option)
855 m_offset = StringConvert::ToUInt32(option_arg, 0, 0, &success);
857 error.SetErrorStringWithFormat("invalid offset: '%s'", option_arg);
860 m_count = StringConvert::ToUInt32(option_arg, 0, 0, &success);
862 error.SetErrorStringWithFormat("invalid offset: '%s'", option_arg);
866 error.SetErrorStringWithFormat ("unrecognized option '%c'", short_option);
874 OptionParsingStarting ()
880 const OptionDefinition*
883 return g_option_table;
886 // Options table: Required for subclasses of Options.
888 static OptionDefinition g_option_table[];
890 // Instance variables to hold the values for command options.
895 CommandOptions m_options;
898 CommandObjectPlatformFRead::CommandOptions::g_option_table[] =
900 { LLDB_OPT_SET_1, false, "offset" , 'o', OptionParser::eRequiredArgument, NULL, NULL, 0, eArgTypeIndex , "Offset into the file at which to start reading." },
901 { LLDB_OPT_SET_1, false, "count" , 'c', OptionParser::eRequiredArgument, NULL, NULL, 0, eArgTypeCount , "Number of bytes to read from the file." },
902 { 0 , false, NULL , 0 , 0 , NULL, NULL, 0, eArgTypeNone , NULL }
906 //----------------------------------------------------------------------
908 //----------------------------------------------------------------------
909 class CommandObjectPlatformFWrite : public CommandObjectParsed
912 CommandObjectPlatformFWrite (CommandInterpreter &interpreter) :
913 CommandObjectParsed (interpreter,
914 "platform file write",
915 "Write data to a file on the remote end.",
918 m_options (interpreter)
923 ~CommandObjectPlatformFWrite ()
928 DoExecute (Args& args, CommandReturnObject &result)
930 PlatformSP platform_sp (m_interpreter.GetDebugger().GetPlatformList().GetSelectedPlatform());
933 std::string cmd_line;
934 args.GetCommandString(cmd_line);
936 const lldb::user_id_t fd = StringConvert::ToUInt64(cmd_line.c_str(), UINT64_MAX);
937 uint32_t retcode = platform_sp->WriteFile (fd,
939 &m_options.m_data[0],
940 m_options.m_data.size(),
942 result.AppendMessageWithFormat("Return = %d\n",retcode);
943 result.SetStatus (eReturnStatusSuccessFinishResult);
947 result.AppendError ("no platform currently selected\n");
948 result.SetStatus (eReturnStatusFailed);
950 return result.Succeeded();
959 class CommandOptions : public Options
963 CommandOptions (CommandInterpreter &interpreter) :
964 Options (interpreter)
974 SetOptionValue (uint32_t option_idx, const char *option_arg)
977 char short_option = (char) m_getopt_table[option_idx].val;
978 bool success = false;
980 switch (short_option)
983 m_offset = StringConvert::ToUInt32(option_arg, 0, 0, &success);
985 error.SetErrorStringWithFormat("invalid offset: '%s'", option_arg);
988 m_data.assign(option_arg);
992 error.SetErrorStringWithFormat ("unrecognized option '%c'", short_option);
1000 OptionParsingStarting ()
1006 const OptionDefinition*
1009 return g_option_table;
1012 // Options table: Required for subclasses of Options.
1014 static OptionDefinition g_option_table[];
1016 // Instance variables to hold the values for command options.
1021 CommandOptions m_options;
1024 CommandObjectPlatformFWrite::CommandOptions::g_option_table[] =
1026 { LLDB_OPT_SET_1, false, "offset" , 'o', OptionParser::eRequiredArgument, NULL, NULL, 0, eArgTypeIndex , "Offset into the file at which to start reading." },
1027 { LLDB_OPT_SET_1, false, "data" , 'd', OptionParser::eRequiredArgument , NULL, NULL, 0, eArgTypeValue , "Text to write to the file." },
1028 { 0 , false, NULL , 0 , 0 , NULL, NULL, 0, eArgTypeNone , NULL }
1031 class CommandObjectPlatformFile : public CommandObjectMultiword
1034 //------------------------------------------------------------------
1035 // Constructors and Destructors
1036 //------------------------------------------------------------------
1037 CommandObjectPlatformFile (CommandInterpreter &interpreter) :
1038 CommandObjectMultiword (interpreter,
1040 "A set of commands to manage file access through a platform",
1041 "platform file [open|close|read|write] ...")
1043 LoadSubCommand ("open", CommandObjectSP (new CommandObjectPlatformFOpen (interpreter)));
1044 LoadSubCommand ("close", CommandObjectSP (new CommandObjectPlatformFClose (interpreter)));
1045 LoadSubCommand ("read", CommandObjectSP (new CommandObjectPlatformFRead (interpreter)));
1046 LoadSubCommand ("write", CommandObjectSP (new CommandObjectPlatformFWrite (interpreter)));
1050 ~CommandObjectPlatformFile ()
1055 //------------------------------------------------------------------
1056 // For CommandObjectPlatform only
1057 //------------------------------------------------------------------
1058 DISALLOW_COPY_AND_ASSIGN (CommandObjectPlatformFile);
1061 //----------------------------------------------------------------------
1062 // "platform get-file remote-file-path host-file-path"
1063 //----------------------------------------------------------------------
1064 class CommandObjectPlatformGetFile : public CommandObjectParsed
1067 CommandObjectPlatformGetFile (CommandInterpreter &interpreter) :
1068 CommandObjectParsed (interpreter,
1069 "platform get-file",
1070 "Transfer a file from the remote end to the local host.",
1071 "platform get-file <remote-file-spec> <local-file-spec>",
1077 platform get-file /the/remote/file/path /the/local/file/path\n\
1078 # Transfer a file from the remote end with file path /the/remote/file/path to the local host.\n");
1080 CommandArgumentEntry arg1, arg2;
1081 CommandArgumentData file_arg_remote, file_arg_host;
1083 // Define the first (and only) variant of this arg.
1084 file_arg_remote.arg_type = eArgTypeFilename;
1085 file_arg_remote.arg_repetition = eArgRepeatPlain;
1086 // There is only one variant this argument could be; put it into the argument entry.
1087 arg1.push_back (file_arg_remote);
1089 // Define the second (and only) variant of this arg.
1090 file_arg_host.arg_type = eArgTypeFilename;
1091 file_arg_host.arg_repetition = eArgRepeatPlain;
1092 // There is only one variant this argument could be; put it into the argument entry.
1093 arg2.push_back (file_arg_host);
1095 // Push the data for the first and the second arguments into the m_arguments vector.
1096 m_arguments.push_back (arg1);
1097 m_arguments.push_back (arg2);
1101 ~CommandObjectPlatformGetFile ()
1106 DoExecute (Args& args, CommandReturnObject &result)
1108 // If the number of arguments is incorrect, issue an error message.
1109 if (args.GetArgumentCount() != 2)
1111 result.GetErrorStream().Printf("error: required arguments missing; specify both the source and destination file paths\n");
1112 result.SetStatus(eReturnStatusFailed);
1116 PlatformSP platform_sp (m_interpreter.GetDebugger().GetPlatformList().GetSelectedPlatform());
1119 const char *remote_file_path = args.GetArgumentAtIndex(0);
1120 const char *local_file_path = args.GetArgumentAtIndex(1);
1121 Error error = platform_sp->GetFile(FileSpec(remote_file_path, false),
1122 FileSpec(local_file_path, false));
1123 if (error.Success())
1125 result.AppendMessageWithFormat("successfully get-file from %s (remote) to %s (host)\n",
1126 remote_file_path, local_file_path);
1127 result.SetStatus (eReturnStatusSuccessFinishResult);
1131 result.AppendMessageWithFormat("get-file failed: %s\n", error.AsCString());
1132 result.SetStatus (eReturnStatusFailed);
1137 result.AppendError ("no platform currently selected\n");
1138 result.SetStatus (eReturnStatusFailed);
1140 return result.Succeeded();
1144 //----------------------------------------------------------------------
1145 // "platform get-size remote-file-path"
1146 //----------------------------------------------------------------------
1147 class CommandObjectPlatformGetSize : public CommandObjectParsed
1150 CommandObjectPlatformGetSize (CommandInterpreter &interpreter) :
1151 CommandObjectParsed (interpreter,
1152 "platform get-size",
1153 "Get the file size from the remote end.",
1154 "platform get-size <remote-file-spec>",
1160 platform get-size /the/remote/file/path\n\
1161 # Get the file size from the remote end with path /the/remote/file/path.\n");
1163 CommandArgumentEntry arg1;
1164 CommandArgumentData file_arg_remote;
1166 // Define the first (and only) variant of this arg.
1167 file_arg_remote.arg_type = eArgTypeFilename;
1168 file_arg_remote.arg_repetition = eArgRepeatPlain;
1169 // There is only one variant this argument could be; put it into the argument entry.
1170 arg1.push_back (file_arg_remote);
1172 // Push the data for the first argument into the m_arguments vector.
1173 m_arguments.push_back (arg1);
1177 ~CommandObjectPlatformGetSize ()
1182 DoExecute (Args& args, CommandReturnObject &result)
1184 // If the number of arguments is incorrect, issue an error message.
1185 if (args.GetArgumentCount() != 1)
1187 result.GetErrorStream().Printf("error: required argument missing; specify the source file path as the only argument\n");
1188 result.SetStatus(eReturnStatusFailed);
1192 PlatformSP platform_sp (m_interpreter.GetDebugger().GetPlatformList().GetSelectedPlatform());
1195 std::string remote_file_path(args.GetArgumentAtIndex(0));
1196 user_id_t size = platform_sp->GetFileSize(FileSpec(remote_file_path.c_str(), false));
1197 if (size != UINT64_MAX)
1199 result.AppendMessageWithFormat("File size of %s (remote): %" PRIu64 "\n", remote_file_path.c_str(), size);
1200 result.SetStatus (eReturnStatusSuccessFinishResult);
1204 result.AppendMessageWithFormat("Eroor getting file size of %s (remote)\n", remote_file_path.c_str());
1205 result.SetStatus (eReturnStatusFailed);
1210 result.AppendError ("no platform currently selected\n");
1211 result.SetStatus (eReturnStatusFailed);
1213 return result.Succeeded();
1217 //----------------------------------------------------------------------
1218 // "platform put-file"
1219 //----------------------------------------------------------------------
1220 class CommandObjectPlatformPutFile : public CommandObjectParsed
1223 CommandObjectPlatformPutFile (CommandInterpreter &interpreter) :
1224 CommandObjectParsed (interpreter,
1225 "platform put-file",
1226 "Transfer a file from this system to the remote end.",
1233 ~CommandObjectPlatformPutFile ()
1238 DoExecute (Args& args, CommandReturnObject &result)
1240 const char* src = args.GetArgumentAtIndex(0);
1241 const char* dst = args.GetArgumentAtIndex(1);
1243 FileSpec src_fs(src, true);
1244 FileSpec dst_fs(dst, false);
1246 PlatformSP platform_sp (m_interpreter.GetDebugger().GetPlatformList().GetSelectedPlatform());
1249 Error error (platform_sp->PutFile(src_fs, dst_fs));
1250 if (error.Success())
1252 result.SetStatus (eReturnStatusSuccessFinishNoResult);
1256 result.AppendError (error.AsCString());
1257 result.SetStatus (eReturnStatusFailed);
1262 result.AppendError ("no platform currently selected\n");
1263 result.SetStatus (eReturnStatusFailed);
1265 return result.Succeeded();
1269 //----------------------------------------------------------------------
1270 // "platform process launch"
1271 //----------------------------------------------------------------------
1272 class CommandObjectPlatformProcessLaunch : public CommandObjectParsed
1275 CommandObjectPlatformProcessLaunch (CommandInterpreter &interpreter) :
1276 CommandObjectParsed (interpreter,
1277 "platform process launch",
1278 "Launch a new process on a remote platform.",
1279 "platform process launch program",
1280 eFlagRequiresTarget | eFlagTryTargetAPILock),
1281 m_options (interpreter)
1286 ~CommandObjectPlatformProcessLaunch ()
1298 DoExecute (Args& args, CommandReturnObject &result)
1300 Target *target = m_interpreter.GetDebugger().GetSelectedTarget().get();
1301 PlatformSP platform_sp;
1304 platform_sp = target->GetPlatform();
1308 platform_sp = m_interpreter.GetDebugger().GetPlatformList().GetSelectedPlatform();
1314 const size_t argc = args.GetArgumentCount();
1315 Target *target = m_exe_ctx.GetTargetPtr();
1316 Module *exe_module = target->GetExecutableModulePointer();
1319 m_options.launch_info.GetExecutableFile () = exe_module->GetFileSpec();
1320 char exe_path[PATH_MAX];
1321 if (m_options.launch_info.GetExecutableFile ().GetPath (exe_path, sizeof(exe_path)))
1322 m_options.launch_info.GetArguments().AppendArgument (exe_path);
1323 m_options.launch_info.GetArchitecture() = exe_module->GetArchitecture();
1328 if (m_options.launch_info.GetExecutableFile ())
1330 // We already have an executable file, so we will use this
1331 // and all arguments to this function are extra arguments
1332 m_options.launch_info.GetArguments().AppendArguments (args);
1336 // We don't have any file yet, so the first argument is our
1337 // executable, and the rest are program arguments
1338 const bool first_arg_is_executable = true;
1339 m_options.launch_info.SetArguments (args, first_arg_is_executable);
1343 if (m_options.launch_info.GetExecutableFile ())
1345 Debugger &debugger = m_interpreter.GetDebugger();
1348 target->GetRunArguments(m_options.launch_info.GetArguments());
1350 ProcessSP process_sp (platform_sp->DebugProcess (m_options.launch_info,
1354 if (process_sp && process_sp->IsAlive())
1356 result.SetStatus (eReturnStatusSuccessFinishNoResult);
1360 if (error.Success())
1361 result.AppendError ("process launch failed");
1363 result.AppendError (error.AsCString());
1364 result.SetStatus (eReturnStatusFailed);
1368 result.AppendError ("'platform process launch' uses the current target file and arguments, or the executable and its arguments can be specified in this command");
1369 result.SetStatus (eReturnStatusFailed);
1375 result.AppendError ("no platform is selected\n");
1377 return result.Succeeded();
1381 ProcessLaunchCommandOptions m_options;
1386 //----------------------------------------------------------------------
1387 // "platform process list"
1388 //----------------------------------------------------------------------
1389 class CommandObjectPlatformProcessList : public CommandObjectParsed
1392 CommandObjectPlatformProcessList (CommandInterpreter &interpreter) :
1393 CommandObjectParsed (interpreter,
1394 "platform process list",
1395 "List processes on a remote platform by name, pid, or many other matching attributes.",
1396 "platform process list",
1398 m_options (interpreter)
1403 ~CommandObjectPlatformProcessList ()
1415 DoExecute (Args& args, CommandReturnObject &result)
1417 Target *target = m_interpreter.GetDebugger().GetSelectedTarget().get();
1418 PlatformSP platform_sp;
1421 platform_sp = target->GetPlatform();
1425 platform_sp = m_interpreter.GetDebugger().GetPlatformList().GetSelectedPlatform();
1431 if (args.GetArgumentCount() == 0)
1436 Stream &ostrm = result.GetOutputStream();
1438 lldb::pid_t pid = m_options.match_info.GetProcessInfo().GetProcessID();
1439 if (pid != LLDB_INVALID_PROCESS_ID)
1441 ProcessInstanceInfo proc_info;
1442 if (platform_sp->GetProcessInfo (pid, proc_info))
1444 ProcessInstanceInfo::DumpTableHeader (ostrm, platform_sp.get(), m_options.show_args, m_options.verbose);
1445 proc_info.DumpAsTableRow(ostrm, platform_sp.get(), m_options.show_args, m_options.verbose);
1446 result.SetStatus (eReturnStatusSuccessFinishResult);
1450 result.AppendErrorWithFormat ("no process found with pid = %" PRIu64 "\n", pid);
1451 result.SetStatus (eReturnStatusFailed);
1456 ProcessInstanceInfoList proc_infos;
1457 const uint32_t matches = platform_sp->FindProcesses (m_options.match_info, proc_infos);
1458 const char *match_desc = NULL;
1459 const char *match_name = m_options.match_info.GetProcessInfo().GetName();
1460 if (match_name && match_name[0])
1462 switch (m_options.match_info.GetNameMatchType())
1464 case eNameMatchIgnore: break;
1465 case eNameMatchEquals: match_desc = "matched"; break;
1466 case eNameMatchContains: match_desc = "contained"; break;
1467 case eNameMatchStartsWith: match_desc = "started with"; break;
1468 case eNameMatchEndsWith: match_desc = "ended with"; break;
1469 case eNameMatchRegularExpression: match_desc = "matched the regular expression"; break;
1476 result.AppendErrorWithFormat ("no processes were found that %s \"%s\" on the \"%s\" platform\n",
1479 platform_sp->GetPluginName().GetCString());
1481 result.AppendErrorWithFormat ("no processes were found on the \"%s\" platform\n", platform_sp->GetPluginName().GetCString());
1482 result.SetStatus (eReturnStatusFailed);
1486 result.AppendMessageWithFormat ("%u matching process%s found on \"%s\"",
1488 matches > 1 ? "es were" : " was",
1489 platform_sp->GetName().GetCString());
1491 result.AppendMessageWithFormat (" whose name %s \"%s\"",
1494 result.AppendMessageWithFormat ("\n");
1495 ProcessInstanceInfo::DumpTableHeader (ostrm, platform_sp.get(), m_options.show_args, m_options.verbose);
1496 for (uint32_t i=0; i<matches; ++i)
1498 proc_infos.GetProcessInfoAtIndex(i).DumpAsTableRow(ostrm, platform_sp.get(), m_options.show_args, m_options.verbose);
1506 result.AppendError ("invalid args: process list takes only options\n");
1507 result.SetStatus (eReturnStatusFailed);
1512 result.AppendError ("no platform is selected\n");
1513 result.SetStatus (eReturnStatusFailed);
1515 return result.Succeeded();
1518 class CommandOptions : public Options
1522 CommandOptions (CommandInterpreter &interpreter) :
1523 Options (interpreter),
1534 SetOptionValue (uint32_t option_idx, const char *option_arg)
1537 const int short_option = m_getopt_table[option_idx].val;
1538 bool success = false;
1540 switch (short_option)
1543 match_info.GetProcessInfo().SetProcessID (StringConvert::ToUInt32 (option_arg, LLDB_INVALID_PROCESS_ID, 0, &success));
1545 error.SetErrorStringWithFormat("invalid process ID string: '%s'", option_arg);
1549 match_info.GetProcessInfo().SetParentProcessID (StringConvert::ToUInt32 (option_arg, LLDB_INVALID_PROCESS_ID, 0, &success));
1551 error.SetErrorStringWithFormat("invalid parent process ID string: '%s'", option_arg);
1555 match_info.GetProcessInfo().SetUserID (StringConvert::ToUInt32 (option_arg, UINT32_MAX, 0, &success));
1557 error.SetErrorStringWithFormat("invalid user ID string: '%s'", option_arg);
1561 match_info.GetProcessInfo().SetEffectiveUserID (StringConvert::ToUInt32 (option_arg, UINT32_MAX, 0, &success));
1563 error.SetErrorStringWithFormat("invalid effective user ID string: '%s'", option_arg);
1567 match_info.GetProcessInfo().SetGroupID (StringConvert::ToUInt32 (option_arg, UINT32_MAX, 0, &success));
1569 error.SetErrorStringWithFormat("invalid group ID string: '%s'", option_arg);
1573 match_info.GetProcessInfo().SetEffectiveGroupID (StringConvert::ToUInt32 (option_arg, UINT32_MAX, 0, &success));
1575 error.SetErrorStringWithFormat("invalid effective group ID string: '%s'", option_arg);
1579 match_info.GetProcessInfo().GetArchitecture().SetTriple (option_arg, m_interpreter.GetDebugger().GetPlatformList().GetSelectedPlatform().get());
1583 match_info.GetProcessInfo().GetExecutableFile().SetFile (option_arg, false);
1584 match_info.SetNameMatchType (eNameMatchEquals);
1588 match_info.GetProcessInfo().GetExecutableFile().SetFile (option_arg, false);
1589 match_info.SetNameMatchType (eNameMatchEndsWith);
1593 match_info.GetProcessInfo().GetExecutableFile().SetFile (option_arg, false);
1594 match_info.SetNameMatchType (eNameMatchStartsWith);
1598 match_info.GetProcessInfo().GetExecutableFile().SetFile (option_arg, false);
1599 match_info.SetNameMatchType (eNameMatchContains);
1603 match_info.GetProcessInfo().GetExecutableFile().SetFile (option_arg, false);
1604 match_info.SetNameMatchType (eNameMatchRegularExpression);
1616 error.SetErrorStringWithFormat ("unrecognized option '%c'", short_option);
1624 OptionParsingStarting ()
1631 const OptionDefinition*
1634 return g_option_table;
1637 // Options table: Required for subclasses of Options.
1639 static OptionDefinition g_option_table[];
1641 // Instance variables to hold the values for command options.
1643 ProcessInstanceInfoMatch match_info;
1647 CommandOptions m_options;
1652 PosixPlatformCommandOptionValidator g_posix_validator;
1656 CommandObjectPlatformProcessList::CommandOptions::g_option_table[] =
1658 { LLDB_OPT_SET_1 , false, "pid" , 'p', OptionParser::eRequiredArgument, NULL, NULL, 0, eArgTypePid , "List the process info for a specific process ID." },
1659 { LLDB_OPT_SET_2 , true , "name" , 'n', OptionParser::eRequiredArgument, NULL, NULL, 0, eArgTypeProcessName , "Find processes with executable basenames that match a string." },
1660 { LLDB_OPT_SET_3 , true , "ends-with" , 'e', OptionParser::eRequiredArgument, NULL, NULL, 0, eArgTypeProcessName , "Find processes with executable basenames that end with a string." },
1661 { LLDB_OPT_SET_4 , true , "starts-with", 's', OptionParser::eRequiredArgument, NULL, NULL, 0, eArgTypeProcessName , "Find processes with executable basenames that start with a string." },
1662 { LLDB_OPT_SET_5 , true , "contains" , 'c', OptionParser::eRequiredArgument, NULL, NULL, 0, eArgTypeProcessName , "Find processes with executable basenames that contain a string." },
1663 { LLDB_OPT_SET_6 , true , "regex" , 'r', OptionParser::eRequiredArgument, NULL, NULL, 0, eArgTypeRegularExpression, "Find processes with executable basenames that match a regular expression." },
1664 { LLDB_OPT_SET_FROM_TO(2, 6), false, "parent" , 'P', OptionParser::eRequiredArgument, NULL, NULL, 0, eArgTypePid , "Find processes that have a matching parent process ID." },
1665 { LLDB_OPT_SET_FROM_TO(2, 6), false, "uid" , 'u', OptionParser::eRequiredArgument, &g_posix_validator, NULL, 0, eArgTypeUnsignedInteger , "Find processes that have a matching user ID." },
1666 { LLDB_OPT_SET_FROM_TO(2, 6), false, "euid" , 'U', OptionParser::eRequiredArgument, &g_posix_validator, NULL, 0, eArgTypeUnsignedInteger , "Find processes that have a matching effective user ID." },
1667 { LLDB_OPT_SET_FROM_TO(2, 6), false, "gid" , 'g', OptionParser::eRequiredArgument, &g_posix_validator, NULL, 0, eArgTypeUnsignedInteger , "Find processes that have a matching group ID." },
1668 { LLDB_OPT_SET_FROM_TO(2, 6), false, "egid" , 'G', OptionParser::eRequiredArgument, &g_posix_validator, NULL, 0, eArgTypeUnsignedInteger , "Find processes that have a matching effective group ID." },
1669 { LLDB_OPT_SET_FROM_TO(2, 6), false, "arch" , 'a', OptionParser::eRequiredArgument, NULL, NULL, 0, eArgTypeArchitecture , "Find processes that have a matching architecture." },
1670 { LLDB_OPT_SET_FROM_TO(1, 6), false, "show-args" , 'A', OptionParser::eNoArgument , NULL, NULL, 0, eArgTypeNone , "Show process arguments instead of the process executable basename." },
1671 { LLDB_OPT_SET_FROM_TO(1, 6), false, "verbose" , 'v', OptionParser::eNoArgument , NULL, NULL, 0, eArgTypeNone , "Enable verbose output." },
1672 { 0 , false, NULL , 0 , 0 , NULL, NULL, 0, eArgTypeNone , NULL }
1675 //----------------------------------------------------------------------
1676 // "platform process info"
1677 //----------------------------------------------------------------------
1678 class CommandObjectPlatformProcessInfo : public CommandObjectParsed
1681 CommandObjectPlatformProcessInfo (CommandInterpreter &interpreter) :
1682 CommandObjectParsed (interpreter,
1683 "platform process info",
1684 "Get detailed information for one or more process by process ID.",
1685 "platform process info <pid> [<pid> <pid> ...]",
1688 CommandArgumentEntry arg;
1689 CommandArgumentData pid_args;
1691 // Define the first (and only) variant of this arg.
1692 pid_args.arg_type = eArgTypePid;
1693 pid_args.arg_repetition = eArgRepeatStar;
1695 // There is only one variant this argument could be; put it into the argument entry.
1696 arg.push_back (pid_args);
1698 // Push the data for the first argument into the m_arguments vector.
1699 m_arguments.push_back (arg);
1703 ~CommandObjectPlatformProcessInfo ()
1709 DoExecute (Args& args, CommandReturnObject &result)
1711 Target *target = m_interpreter.GetDebugger().GetSelectedTarget().get();
1712 PlatformSP platform_sp;
1715 platform_sp = target->GetPlatform();
1719 platform_sp = m_interpreter.GetDebugger().GetPlatformList().GetSelectedPlatform();
1724 const size_t argc = args.GetArgumentCount();
1729 if (platform_sp->IsConnected())
1731 Stream &ostrm = result.GetOutputStream();
1733 for (size_t i=0; i<argc; ++ i)
1735 const char *arg = args.GetArgumentAtIndex(i);
1736 lldb::pid_t pid = StringConvert::ToUInt32 (arg, LLDB_INVALID_PROCESS_ID, 0, &success);
1739 ProcessInstanceInfo proc_info;
1740 if (platform_sp->GetProcessInfo (pid, proc_info))
1742 ostrm.Printf ("Process information for process %" PRIu64 ":\n", pid);
1743 proc_info.Dump (ostrm, platform_sp.get());
1747 ostrm.Printf ("error: no process information is available for process %" PRIu64 "\n", pid);
1753 result.AppendErrorWithFormat ("invalid process ID argument '%s'", arg);
1754 result.SetStatus (eReturnStatusFailed);
1762 result.AppendErrorWithFormat ("not connected to '%s'", platform_sp->GetPluginName().GetCString());
1763 result.SetStatus (eReturnStatusFailed);
1769 result.AppendError ("one or more process id(s) must be specified");
1770 result.SetStatus (eReturnStatusFailed);
1775 result.AppendError ("no platform is currently selected");
1776 result.SetStatus (eReturnStatusFailed);
1778 return result.Succeeded();
1782 class CommandObjectPlatformProcessAttach : public CommandObjectParsed
1786 class CommandOptions : public Options
1790 CommandOptions (CommandInterpreter &interpreter) :
1791 Options(interpreter)
1793 // Keep default values of all options in one place: OptionParsingStarting ()
1794 OptionParsingStarting ();
1802 SetOptionValue (uint32_t option_idx, const char *option_arg)
1805 char short_option = (char) m_getopt_table[option_idx].val;
1806 bool success = false;
1807 switch (short_option)
1811 lldb::pid_t pid = StringConvert::ToUInt32 (option_arg, LLDB_INVALID_PROCESS_ID, 0, &success);
1812 if (!success || pid == LLDB_INVALID_PROCESS_ID)
1814 error.SetErrorStringWithFormat("invalid process ID '%s'", option_arg);
1818 attach_info.SetProcessID (pid);
1824 attach_info.SetProcessPluginName (option_arg);
1828 attach_info.GetExecutableFile().SetFile(option_arg, false);
1832 attach_info.SetWaitForLaunch(true);
1836 error.SetErrorStringWithFormat("invalid short option character '%c'", short_option);
1843 OptionParsingStarting ()
1845 attach_info.Clear();
1848 const OptionDefinition*
1851 return g_option_table;
1855 HandleOptionArgumentCompletion (Args &input,
1858 OptionElementVector &opt_element_vector,
1859 int opt_element_index,
1860 int match_start_point,
1861 int max_return_elements,
1862 bool &word_complete,
1863 StringList &matches)
1865 int opt_arg_pos = opt_element_vector[opt_element_index].opt_arg_pos;
1866 int opt_defs_index = opt_element_vector[opt_element_index].opt_defs_index;
1868 // We are only completing the name option for now...
1870 const OptionDefinition *opt_defs = GetDefinitions();
1871 if (opt_defs[opt_defs_index].short_option == 'n')
1873 // Are we in the name?
1875 // Look to see if there is a -P argument provided, and if so use that plugin, otherwise
1876 // use the default plugin.
1878 const char *partial_name = NULL;
1879 partial_name = input.GetArgumentAtIndex(opt_arg_pos);
1881 PlatformSP platform_sp (m_interpreter.GetPlatform (true));
1884 ProcessInstanceInfoList process_infos;
1885 ProcessInstanceInfoMatch match_info;
1888 match_info.GetProcessInfo().GetExecutableFile().SetFile(partial_name, false);
1889 match_info.SetNameMatchType(eNameMatchStartsWith);
1891 platform_sp->FindProcesses (match_info, process_infos);
1892 const uint32_t num_matches = process_infos.GetSize();
1893 if (num_matches > 0)
1895 for (uint32_t i=0; i<num_matches; ++i)
1897 matches.AppendString (process_infos.GetProcessNameAtIndex(i),
1898 process_infos.GetProcessNameLengthAtIndex(i));
1907 // Options table: Required for subclasses of Options.
1909 static OptionDefinition g_option_table[];
1911 // Instance variables to hold the values for command options.
1913 ProcessAttachInfo attach_info;
1916 CommandObjectPlatformProcessAttach (CommandInterpreter &interpreter) :
1917 CommandObjectParsed (interpreter,
1918 "platform process attach",
1919 "Attach to a process.",
1920 "platform process attach <cmd-options>"),
1921 m_options (interpreter)
1925 ~CommandObjectPlatformProcessAttach ()
1930 DoExecute (Args& command,
1931 CommandReturnObject &result)
1933 PlatformSP platform_sp (m_interpreter.GetDebugger().GetPlatformList().GetSelectedPlatform());
1937 ProcessSP remote_process_sp =
1938 platform_sp->Attach(m_options.attach_info, m_interpreter.GetDebugger(), NULL, err);
1941 result.AppendError(err.AsCString());
1942 result.SetStatus (eReturnStatusFailed);
1944 else if (remote_process_sp.get() == NULL)
1946 result.AppendError("could not attach: unknown reason");
1947 result.SetStatus (eReturnStatusFailed);
1950 result.SetStatus (eReturnStatusSuccessFinishResult);
1954 result.AppendError ("no platform is currently selected");
1955 result.SetStatus (eReturnStatusFailed);
1957 return result.Succeeded();
1968 CommandOptions m_options;
1973 CommandObjectPlatformProcessAttach::CommandOptions::g_option_table[] =
1975 { LLDB_OPT_SET_ALL, false, "plugin", 'P' , OptionParser::eRequiredArgument, NULL, NULL, 0, eArgTypePlugin, "Name of the process plugin you want to use."},
1976 { LLDB_OPT_SET_1, false, "pid", 'p' , OptionParser::eRequiredArgument, NULL, NULL, 0, eArgTypePid, "The process ID of an existing process to attach to."},
1977 { LLDB_OPT_SET_2, false, "name", 'n' , OptionParser::eRequiredArgument, NULL, NULL, 0, eArgTypeProcessName, "The name of the process to attach to."},
1978 { LLDB_OPT_SET_2, false, "waitfor", 'w' , OptionParser::eNoArgument , NULL, NULL, 0, eArgTypeNone, "Wait for the the process with <process-name> to launch."},
1979 { 0, false, NULL , 0 , 0 , NULL, NULL, 0, eArgTypeNone, NULL }
1983 class CommandObjectPlatformProcess : public CommandObjectMultiword
1986 //------------------------------------------------------------------
1987 // Constructors and Destructors
1988 //------------------------------------------------------------------
1989 CommandObjectPlatformProcess (CommandInterpreter &interpreter) :
1990 CommandObjectMultiword (interpreter,
1992 "A set of commands to query, launch and attach to platform processes",
1993 "platform process [attach|launch|list] ...")
1995 LoadSubCommand ("attach", CommandObjectSP (new CommandObjectPlatformProcessAttach (interpreter)));
1996 LoadSubCommand ("launch", CommandObjectSP (new CommandObjectPlatformProcessLaunch (interpreter)));
1997 LoadSubCommand ("info" , CommandObjectSP (new CommandObjectPlatformProcessInfo (interpreter)));
1998 LoadSubCommand ("list" , CommandObjectSP (new CommandObjectPlatformProcessList (interpreter)));
2003 ~CommandObjectPlatformProcess ()
2008 //------------------------------------------------------------------
2009 // For CommandObjectPlatform only
2010 //------------------------------------------------------------------
2011 DISALLOW_COPY_AND_ASSIGN (CommandObjectPlatformProcess);
2014 //----------------------------------------------------------------------
2016 //----------------------------------------------------------------------
2017 class CommandObjectPlatformShell : public CommandObjectRaw
2021 class CommandOptions : public Options
2025 CommandOptions (CommandInterpreter &interpreter) :
2026 Options(interpreter),
2037 GetNumDefinitions ()
2042 virtual const OptionDefinition*
2045 return g_option_table;
2049 SetOptionValue (uint32_t option_idx,
2050 const char *option_value)
2054 const char short_option = (char) g_option_table[option_idx].short_option;
2056 switch (short_option)
2061 timeout = StringConvert::ToUInt32(option_value, 10, 10, &success);
2063 error.SetErrorStringWithFormat("could not convert \"%s\" to a numeric value.", option_value);
2067 error.SetErrorStringWithFormat("invalid short option character '%c'", short_option);
2075 OptionParsingStarting ()
2079 // Options table: Required for subclasses of Options.
2081 static OptionDefinition g_option_table[];
2085 CommandObjectPlatformShell (CommandInterpreter &interpreter) :
2086 CommandObjectRaw (interpreter,
2088 "Run a shell command on a the selected platform.",
2089 "platform shell <shell-command>",
2091 m_options(interpreter)
2096 ~CommandObjectPlatformShell ()
2108 DoExecute (const char *raw_command_line, CommandReturnObject &result)
2110 m_options.NotifyOptionParsingStarting();
2112 const char* expr = NULL;
2114 // Print out an usage syntax on an empty command line.
2115 if (raw_command_line[0] == '\0')
2117 result.GetOutputStream().Printf("%s\n", this->GetSyntax());
2121 if (raw_command_line[0] == '-')
2123 // We have some options and these options MUST end with --.
2124 const char *end_options = NULL;
2125 const char *s = raw_command_line;
2128 end_options = ::strstr (s, "--");
2131 end_options += 2; // Get past the "--"
2132 if (::isspace (end_options[0]))
2135 while (::isspace (*expr))
2145 Args args (raw_command_line, end_options - raw_command_line);
2146 if (!ParseOptions (args, result))
2152 expr = raw_command_line;
2154 PlatformSP platform_sp (m_interpreter.GetDebugger().GetPlatformList().GetSelectedPlatform());
2158 const char *working_dir = NULL;
2162 error = (platform_sp->RunShellCommand (expr, working_dir, &status, &signo, &output, m_options.timeout));
2163 if (!output.empty())
2164 result.GetOutputStream().PutCString(output.c_str());
2169 const char *signo_cstr = Host::GetSignalAsCString(signo);
2171 result.GetOutputStream().Printf("error: command returned with status %i and signal %s\n", status, signo_cstr);
2173 result.GetOutputStream().Printf("error: command returned with status %i and signal %i\n", status, signo);
2176 result.GetOutputStream().Printf("error: command returned with status %i\n", status);
2181 result.GetOutputStream().Printf("error: cannot run remote shell commands without a platform\n");
2182 error.SetErrorString("error: cannot run remote shell commands without a platform");
2187 result.AppendError(error.AsCString());
2188 result.SetStatus (eReturnStatusFailed);
2192 result.SetStatus (eReturnStatusSuccessFinishResult);
2196 CommandOptions m_options;
2200 CommandObjectPlatformShell::CommandOptions::g_option_table[] =
2202 { LLDB_OPT_SET_ALL, false, "timeout", 't', OptionParser::eRequiredArgument, NULL, NULL, 0, eArgTypeValue, "Seconds to wait for the remote host to finish running the command."},
2203 { 0, false, NULL, 0, 0, NULL, NULL, 0, eArgTypeNone, NULL }
2207 //----------------------------------------------------------------------
2208 // "platform install" - install a target to a remote end
2209 //----------------------------------------------------------------------
2210 class CommandObjectPlatformInstall : public CommandObjectParsed
2213 CommandObjectPlatformInstall (CommandInterpreter &interpreter) :
2214 CommandObjectParsed (interpreter,
2215 "platform target-install",
2216 "Install a target (bundle or executable file) to the remote end.",
2217 "platform target-install <local-thing> <remote-sandbox>",
2223 ~CommandObjectPlatformInstall ()
2228 DoExecute (Args& args, CommandReturnObject &result)
2230 if (args.GetArgumentCount() != 2)
2232 result.AppendError("platform target-install takes two arguments");
2233 result.SetStatus(eReturnStatusFailed);
2236 // TODO: move the bulk of this code over to the platform itself
2237 FileSpec src(args.GetArgumentAtIndex(0), true);
2238 FileSpec dst(args.GetArgumentAtIndex(1), false);
2239 if (src.Exists() == false)
2241 result.AppendError("source location does not exist or is not accessible");
2242 result.SetStatus(eReturnStatusFailed);
2245 PlatformSP platform_sp (m_interpreter.GetDebugger().GetPlatformList().GetSelectedPlatform());
2248 result.AppendError ("no platform currently selected");
2249 result.SetStatus (eReturnStatusFailed);
2253 Error error = platform_sp->Install(src, dst);
2254 if (error.Success())
2256 result.SetStatus(eReturnStatusSuccessFinishNoResult);
2260 result.AppendErrorWithFormat("install failed: %s", error.AsCString());
2261 result.SetStatus(eReturnStatusFailed);
2263 return result.Succeeded();
2269 //----------------------------------------------------------------------
2270 // CommandObjectPlatform constructor
2271 //----------------------------------------------------------------------
2272 CommandObjectPlatform::CommandObjectPlatform(CommandInterpreter &interpreter) :
2273 CommandObjectMultiword (interpreter,
2275 "A set of commands to manage and create platforms.",
2276 "platform [connect|disconnect|info|list|status|select] ...")
2278 LoadSubCommand ("select", CommandObjectSP (new CommandObjectPlatformSelect (interpreter)));
2279 LoadSubCommand ("list" , CommandObjectSP (new CommandObjectPlatformList (interpreter)));
2280 LoadSubCommand ("status", CommandObjectSP (new CommandObjectPlatformStatus (interpreter)));
2281 LoadSubCommand ("connect", CommandObjectSP (new CommandObjectPlatformConnect (interpreter)));
2282 LoadSubCommand ("disconnect", CommandObjectSP (new CommandObjectPlatformDisconnect (interpreter)));
2283 LoadSubCommand ("settings", CommandObjectSP (new CommandObjectPlatformSettings (interpreter)));
2284 LoadSubCommand ("mkdir", CommandObjectSP (new CommandObjectPlatformMkDir (interpreter)));
2285 LoadSubCommand ("file", CommandObjectSP (new CommandObjectPlatformFile (interpreter)));
2286 LoadSubCommand ("get-file", CommandObjectSP (new CommandObjectPlatformGetFile (interpreter)));
2287 LoadSubCommand ("get-size", CommandObjectSP (new CommandObjectPlatformGetSize (interpreter)));
2288 LoadSubCommand ("put-file", CommandObjectSP (new CommandObjectPlatformPutFile (interpreter)));
2289 LoadSubCommand ("process", CommandObjectSP (new CommandObjectPlatformProcess (interpreter)));
2290 LoadSubCommand ("shell", CommandObjectSP (new CommandObjectPlatformShell (interpreter)));
2291 LoadSubCommand ("target-install", CommandObjectSP (new CommandObjectPlatformInstall (interpreter)));
2294 //----------------------------------------------------------------------
2296 //----------------------------------------------------------------------
2297 CommandObjectPlatform::~CommandObjectPlatform()