summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--lldb/include/lldb/API/SBLaunchInfo.h2
-rw-r--r--lldb/include/lldb/Interpreter/Args.h2
-rw-r--r--lldb/packages/Python/lldbsuite/test/functionalities/launch_with_shellexpand/TestLaunchWithShellExpand.py6
-rw-r--r--lldb/source/Interpreter/Args.cpp34
-rw-r--r--lldb/source/Target/Platform.cpp4
-rw-r--r--lldb/source/Target/ProcessLaunchInfo.cpp4
6 files changed, 45 insertions, 7 deletions
diff --git a/lldb/include/lldb/API/SBLaunchInfo.h b/lldb/include/lldb/API/SBLaunchInfo.h
index 68c0f386acd..38d598aec45 100644
--- a/lldb/include/lldb/API/SBLaunchInfo.h
+++ b/lldb/include/lldb/API/SBLaunchInfo.h
@@ -145,7 +145,7 @@ public:
GetShellExpandArguments ();
void
- SetShellExpandArguments (bool glob);
+ SetShellExpandArguments (bool expand);
uint32_t
GetResumeCount ();
diff --git a/lldb/include/lldb/Interpreter/Args.h b/lldb/include/lldb/Interpreter/Args.h
index e79318ba562..c55b2f63173 100644
--- a/lldb/include/lldb/Interpreter/Args.h
+++ b/lldb/include/lldb/Interpreter/Args.h
@@ -403,7 +403,7 @@ public:
StringToVersion (const char *s, uint32_t &major, uint32_t &minor, uint32_t &update);
static const char *
- GetShellSafeArgument (const char *unsafe_arg, std::string &safe_arg);
+ GetShellSafeArgument (const FileSpec& shell, const char *unsafe_arg, std::string &safe_arg);
// EncodeEscapeSequences will change the textual representation of common
// escape sequences like "\n" (two characters) into a single '\n'. It does
diff --git a/lldb/packages/Python/lldbsuite/test/functionalities/launch_with_shellexpand/TestLaunchWithShellExpand.py b/lldb/packages/Python/lldbsuite/test/functionalities/launch_with_shellexpand/TestLaunchWithShellExpand.py
index fa90d79b82d..28d8cccacfc 100644
--- a/lldb/packages/Python/lldbsuite/test/functionalities/launch_with_shellexpand/TestLaunchWithShellExpand.py
+++ b/lldb/packages/Python/lldbsuite/test/functionalities/launch_with_shellexpand/TestLaunchWithShellExpand.py
@@ -30,7 +30,7 @@ class LaunchWithShellExpandTestCase(TestBase):
breakpoint = target.BreakpointCreateBySourceRegex ('break here', lldb.SBFileSpec ("main.cpp", False))
self.assertTrue(breakpoint, VALID_BREAKPOINT)
- self.runCmd("process launch -X true -w %s -- fi*.tx?" % (os.getcwd()))
+ self.runCmd("process launch -X true -w %s -- fi*.tx? () > <" % (os.getcwd()))
process = self.process()
@@ -51,7 +51,11 @@ class LaunchWithShellExpandTestCase(TestBase):
self.expect("frame variable argv[2]", substrs=['file2.txt'])
self.expect("frame variable argv[3]", substrs=['file3.txt'])
self.expect("frame variable argv[4]", substrs=['file4.txy'])
+ self.expect("frame variable argv[5]", substrs=['()'])
+ self.expect("frame variable argv[6]", substrs=['>'])
+ self.expect("frame variable argv[7]", substrs=['<'])
self.expect("frame variable argv[5]", substrs=['file5.tyx'], matching=False)
+ self.expect("frame variable argv[8]", substrs=['file5.tyx'], matching=False)
self.runCmd("process kill")
diff --git a/lldb/source/Interpreter/Args.cpp b/lldb/source/Interpreter/Args.cpp
index 81e6b0aa1db..f6c018f4262 100644
--- a/lldb/source/Interpreter/Args.cpp
+++ b/lldb/source/Interpreter/Args.cpp
@@ -887,14 +887,43 @@ Args::StringToVersion (const char *s, uint32_t &major, uint32_t &minor, uint32_t
}
const char *
-Args::GetShellSafeArgument (const char *unsafe_arg, std::string &safe_arg)
+Args::GetShellSafeArgument (const FileSpec& shell,
+ const char *unsafe_arg,
+ std::string &safe_arg)
{
+ struct ShellDescriptor
+ {
+ ConstString m_basename;
+ const char* m_escapables;
+ };
+
+ static ShellDescriptor g_Shells[] = {
+ {ConstString("bash")," '\"<>()&"},
+ {ConstString("tcsh")," '\"<>()&$"},
+ {ConstString("sh")," '\"<>()&"}
+ };
+
+ // safe minimal set
+ const char* escapables = " '\"";
+
+ if (auto basename = shell.GetFilename())
+ {
+ for (const auto& Shell : g_Shells)
+ {
+ if (Shell.m_basename == basename)
+ {
+ escapables = Shell.m_escapables;
+ break;
+ }
+ }
+ }
+
safe_arg.assign (unsafe_arg);
size_t prev_pos = 0;
while (prev_pos < safe_arg.size())
{
// Escape spaces and quotes
- size_t pos = safe_arg.find_first_of(" '\"", prev_pos);
+ size_t pos = safe_arg.find_first_of(escapables, prev_pos);
if (pos != std::string::npos)
{
safe_arg.insert (pos, 1, '\\');
@@ -906,7 +935,6 @@ Args::GetShellSafeArgument (const char *unsafe_arg, std::string &safe_arg)
return safe_arg.c_str();
}
-
int64_t
Args::StringToOptionEnum (const char *s, OptionEnumValueElement *enum_values, int32_t fail_value, Error &error)
{
diff --git a/lldb/source/Target/Platform.cpp b/lldb/source/Target/Platform.cpp
index 436a710982f..72db562aabc 100644
--- a/lldb/source/Target/Platform.cpp
+++ b/lldb/source/Target/Platform.cpp
@@ -1241,7 +1241,11 @@ Platform::LaunchProcess (ProcessLaunchInfo &launch_info)
{
error = ShellExpandArguments(launch_info);
if (error.Fail())
+ {
+ error.SetErrorStringWithFormat("shell expansion failed (reason: %s). consider launching with 'process launch'.",
+ error.AsCString("unknown"));
return error;
+ }
}
if (log)
diff --git a/lldb/source/Target/ProcessLaunchInfo.cpp b/lldb/source/Target/ProcessLaunchInfo.cpp
index 4e4db8742e5..58e42e7caa1 100644
--- a/lldb/source/Target/ProcessLaunchInfo.cpp
+++ b/lldb/source/Target/ProcessLaunchInfo.cpp
@@ -503,7 +503,9 @@ ProcessLaunchInfo::ConvertArgumentsForLaunchingInShell (Error &error,
{
for (size_t i=0; argv[i] != nullptr; ++i)
{
- const char *arg = Args::GetShellSafeArgument (argv[i], safe_arg);
+ const char *arg = Args::GetShellSafeArgument (m_shell,
+ argv[i],
+ safe_arg);
shell_command.Printf(" %s", arg);
}
}
OpenPOWER on IntegriCloud