Module: wine
Branch: master
Commit: c7ad47e9b29971509d8ea76e918b6f623ca52a17
URL: http://source.winehq.org/git/wine.git/?a=commit;h=c7ad47e9b29971509d8ea76e9…
Author: Jacob Lifshay <programmerjake(a)gmail.com>
Date: Thu Feb 9 16:26:36 2017 -0800
kernel32: Fix improper escaping of quotes in command line.
Signed-off-by: Jacob Lifshay <programmerjake(a)gmail.com>
Signed-off-by: Alexandre Julliard <julliard(a)winehq.org>
---
dlls/kernel32/process.c | 19 ++++++++++++++-----
1 file changed, 14 insertions(+), 5 deletions(-)
diff --git a/dlls/kernel32/process.c b/dlls/kernel32/process.c
index 70c38eb..5b8a3d3 100644
--- a/dlls/kernel32/process.c
+++ b/dlls/kernel32/process.c
@@ -745,6 +745,10 @@ static void update_library_argv0( const WCHAR *argv0 )
* resulting in an odd number of '\' followed by a '"'
* '\"' -> '\\\"'
* '\\"' -> '\\\\\"'
+ * - '\'s are followed by the closing '"' must be doubled,
+ * resulting in an even number of '\' followed by a '"'
+ * ' \' -> '" \\"'
+ * ' \\' -> '" \\\\"'
* - '\'s that are not followed by a '"' can be left as is
* 'a\b' == 'a\b'
* 'a\\b' == 'a\\b'
@@ -787,7 +791,7 @@ static BOOL build_command_line( WCHAR **argv )
}
len+=(a-*arg)+1 /* for the separating space */;
if (has_space)
- len+=2; /* for the quotes */
+ len+=2+bcount; /* for the quotes and doubling of '\' preceding the closing quote */
}
if (!(rupp->CommandLine.Buffer = RtlAllocateHeap( GetProcessHeap(), 0, len * sizeof(WCHAR))))
@@ -800,6 +804,7 @@ static BOOL build_command_line( WCHAR **argv )
{
BOOL has_space,has_quote;
WCHAR* a;
+ int bcount;
/* Check for quotes and spaces in this argument */
has_space=has_quote=FALSE;
@@ -821,9 +826,7 @@ static BOOL build_command_line( WCHAR **argv )
/* Now transfer it to the command line */
if (has_space)
*p++='"';
- if (has_quote) {
- int bcount;
-
+ if (has_quote || has_space) {
bcount=0;
a=*arg;
while (*a!='\0') {
@@ -849,8 +852,14 @@ static BOOL build_command_line( WCHAR **argv )
WCHAR* x = *arg;
while ((*p=*x++)) p++;
}
- if (has_space)
+ if (has_space) {
+ int i;
+
+ /* Double all the '\' preceding the closing quote */
+ for (i=0;i<bcount;i++)
+ *p++='\\';
*p++='"';
+ }
*p++=' ';
}
if (p > rupp->CommandLine.Buffer)