See also https://bugs.winehq.org/show_bug.cgi?id=56361
This patch makes piped commands work like for example "echo os get version|wmic" or "type file.txt | wmic" where file.txt contains some commands. (probably used by program in aforementioned bugreport)
Also support interactive mode (wine wmic.exe)
Marked for now as draft.
From: Louis Lenders xerox.xerox2000x@gmail.com
See also https://bugs.winehq.org/show_bug.cgi?id=56361
This patch makes piped commands work like for example "echo os get version|wmic" or "type file.txt | wmic" where file.txt contains some commands. (probably used by program in aforementioned bugreport)
Also support interactive mode (wine wmic.exe)
Marked for now as draft. --- programs/wmic/main.c | 39 +++++++++++++++++++++++++++++++++++++++ programs/wmic/wmic.h | 1 + programs/wmic/wmic.rc | 1 + 3 files changed, 41 insertions(+)
diff --git a/programs/wmic/main.c b/programs/wmic/main.c index 936fe45139d..2475d2c4942 100644 --- a/programs/wmic/main.c +++ b/programs/wmic/main.c @@ -34,6 +34,7 @@
WINE_DEFAULT_DEBUG_CHANNEL(wmic);
+#define MAX_STRING 4096 static const struct { const WCHAR *alias; @@ -337,9 +338,47 @@ int __cdecl wmain(int argc, WCHAR *argv[]) { const WCHAR *class, *value; int i; + WCHAR cmd[MAX_STRING];
setlocale( LC_ALL, "" );
+ if(argc == 1) + { + STARTUPINFOW si = {0}; + PROCESS_INFORMATION pi = {0}; + + output_error( STRING_INTERACTIVE ); + + while (fgetws(cmd, sizeof(cmd), stdin) != NULL) + { + WCHAR wmic[MAX_STRING] = L"wmic.exe ", stripped[MAX_STRING], *ptr, *token; + + cmd[wcslen(cmd)-1] = 0; /* remove trailing '\n' */ + + stripped[0] = 0; /* FIXME: remove extra spaces from comma seperated list, by breaking it up and rebuild it, is there a better way? */ + token = wcstok( cmd, L",", &ptr ); + while (token) + { + wcscat( stripped, strip_spaces(token) ); + token = wcstok( NULL, L",", &ptr ); + if (token) wcscat( stripped, L"," ); + } + + WINE_TRACE("stripped command %s.\n", debugstr_w(stripped)); + if (!wcsicmp( strip_spaces(cmd), L"exit" ) || !wcsicmp(strip_spaces(cmd), L"quit" )) + return 0; + + CreateProcessW( 0, wcscat( wmic, stripped ), 0, 0, 0, 0, 0, 0, &si, &pi ); + WaitForSingleObject( pi.hProcess, INFINITE ); + CloseHandle( pi.hProcess ); + CloseHandle( pi.hThread ); + + output_newline(); + output_error( STRING_INTERACTIVE ); + } + return 0; + } + for (i = 1; i < argc && argv[i][0] == '/'; i++) WINE_FIXME( "command line switch %s not supported\n", debugstr_w(argv[i]) );
diff --git a/programs/wmic/wmic.h b/programs/wmic/wmic.h index 27272706af5..bb095169c8b 100644 --- a/programs/wmic/wmic.h +++ b/programs/wmic/wmic.h @@ -22,3 +22,4 @@ #define STRING_ALIAS_NOT_FOUND 102 #define STRING_INVALID_QUERY 103 #define STRING_INVALID_PATH 104 +#define STRING_INTERACTIVE 105 diff --git a/programs/wmic/wmic.rc b/programs/wmic/wmic.rc index 0789ef34631..309582c5140 100644 --- a/programs/wmic/wmic.rc +++ b/programs/wmic/wmic.rc @@ -28,4 +28,5 @@ STRINGTABLE STRING_ALIAS_NOT_FOUND, "Error: Alias not found\n" STRING_INVALID_QUERY, "Error: Invalid query\n" STRING_INVALID_PATH, "Error: Invalid syntax for PATH\n" + STRING_INTERACTIVE, "wmic:root\cli>" }
Marked for now as draft.
Any particular reason?
I'm unsure about a few parts, like how to remove extra spaces from comma seperated list (like when you start wmic, and then do 'os get version , list') so I'm waiting for review from Hans really.
I see this site also removes extra spaces... What I meant is just add some extra spaces before and after the comma.
I'm unsure about a few parts, like how to remove extra spaces from comma seperated list (like when you start wmic, and then do 'os get version , list') so I'm waiting for review from Hans really.
If you want review, I don't think marking it as a draft is a way to accomplish that? My impression is that when someone submits a draft, it's not ready to be reviewed yet.
ok, i think i removed draft now
Hans Leidekker (@hans) commented about programs/wmic/main.c:
{ const WCHAR *class, *value; int i;
WCHAR cmd[MAX_STRING];
setlocale( LC_ALL, "" );
if(argc == 1)
{
STARTUPINFOW si = {0};
PROCESS_INFORMATION pi = {0};
output_error( STRING_INTERACTIVE );
This is not an error and the string doesn't need translation.
Hans Leidekker (@hans) commented about programs/wmic/main.c:
{ const WCHAR *class, *value; int i;
WCHAR cmd[MAX_STRING];
setlocale( LC_ALL, "" );
if(argc == 1)
Please add a space after 'if'.
Hans Leidekker (@hans) commented about programs/wmic/main.c:
- if(argc == 1)
- {
STARTUPINFOW si = {0};
PROCESS_INFORMATION pi = {0};
output_error( STRING_INTERACTIVE );
while (fgetws(cmd, sizeof(cmd), stdin) != NULL)
{
WCHAR wmic[MAX_STRING] = L"wmic.exe ", stripped[MAX_STRING], *ptr, *token;
cmd[wcslen(cmd)-1] = 0; /* remove trailing '\n' */
stripped[0] = 0; /* FIXME: remove extra spaces from comma seperated list, by breaking it up and rebuild it, is there a better way? */
token = wcstok( cmd, L",", &ptr );
I see no need to create a new process. Commands should be handled the same as when passed on the command line, so you need to split the buffer into class, verb and properties. The existing code already handles spaces in the property list.
Hi, I guess there's no need but it makes the code much simpler afaict, so is it a real problem? If I have to split the buffer I really need (more or less) duplicate the rest of the code that handles the arguments inside the loop, and if in future maybe handling other arguments are added (like where clause) this code has to be added in the loop as well afaict. I already tried before something like send the buffer to SHCommandLineToArgvw and pass the arguments down rest of the code, but then again it won't stay in the loop and interactive mode won't work. Or am I overlooking something?
The existing code already handles spaces in the property list.
If I type something like 'wmic os get name , version' I only get the first property and not the second