kernelbase: Add support for CREATE_NO_WINDOW flag in CreateProcess.

Based on patches by Eric Pouech and Torge Matthies.

Signed-off-by: Eric Pouech <eric.pouech@gmail.com>
Signed-off-by: Jacek Caban <jacek@codeweavers.com>
Signed-off-by: Alexandre Julliard <julliard@winehq.org>
This commit is contained in:
Jacek Caban 2022-04-11 15:04:56 +02:00 committed by Alexandre Julliard
parent 313b10991b
commit b4d91adb16
7 changed files with 36 additions and 18 deletions

View File

@ -4754,7 +4754,6 @@ static void test_CreateProcessCUI(void)
res = check_child_console_bits(cuiexec, CREATE_NEW_CONSOLE);
ok(res == (CP_WITH_CONSOLE | CP_WITH_HANDLE | CP_WITH_WINDOW | CP_ALONE), "Unexpected result %x\n", res);
res = check_child_console_bits(cuiexec, CREATE_NO_WINDOW);
todo_wine
ok(res == (CP_WITH_CONSOLE | CP_WITH_HANDLE | CP_ALONE), "Unexpected result %x\n", res);
res = check_child_console_bits(cuiexec, DETACHED_PROCESS | CREATE_NO_WINDOW);
ok(res == 0, "Unexpected result %x\n", res);
@ -4771,7 +4770,6 @@ static void test_CreateProcessCUI(void)
res = check_child_console_bits(guiexec, CREATE_NEW_CONSOLE);
ok(res == 0, "Unexpected result %x\n", res);
res = check_child_console_bits(guiexec, CREATE_NO_WINDOW);
todo_wine
ok(res == 0, "Unexpected result %x\n", res);
res = check_child_console_bits(guiexec, DETACHED_PROCESS | CREATE_NO_WINDOW);
ok(res == 0, "Unexpected result %x\n", res);
@ -4785,7 +4783,6 @@ static void test_CreateProcessCUI(void)
res = check_child_console_bits(cuiexec, CREATE_NEW_CONSOLE);
ok(res == (CP_WITH_CONSOLE | CP_WITH_HANDLE | CP_WITH_WINDOW | CP_ALONE), "Unexpected result %x\n", res);
res = check_child_console_bits(cuiexec, CREATE_NO_WINDOW);
todo_wine
ok(res == (CP_WITH_CONSOLE | CP_WITH_HANDLE | CP_ALONE), "Unexpected result %x\n", res);
res = check_child_console_bits(cuiexec, DETACHED_PROCESS | CREATE_NO_WINDOW);
ok(res == 0, "Unexpected result %x\n", res);

View File

@ -361,10 +361,7 @@ BOOL WINAPI DECLSPEC_HOTPATCH AttachConsole( DWORD pid )
}
/******************************************************************
* AllocConsole (kernelbase.@)
*/
BOOL WINAPI AllocConsole(void)
static BOOL alloc_console( BOOL headless )
{
SECURITY_ATTRIBUTES inheritable_attr = { sizeof(inheritable_attr), NULL, TRUE };
STARTUPINFOW app_si, console_si;
@ -419,6 +416,7 @@ BOOL WINAPI AllocConsole(void)
swprintf( conhost_path, ARRAY_SIZE(conhost_path), L"%s\\conhost.exe", system_dir );
swprintf( cmd, ARRAY_SIZE(cmd), L"\"%s\" --server 0x%x", conhost_path, condrv_handle( server ));
if (headless) wcscat( cmd, L" --headless" );
Wow64DisableWow64FsRedirection( &redir );
ret = CreateProcessW( conhost_path, cmd, NULL, NULL, TRUE, DETACHED_PROCESS, NULL, NULL, &console_si, &pi );
Wow64RevertWow64FsRedirection( redir );
@ -444,6 +442,15 @@ error:
}
/******************************************************************
* AllocConsole (kernelbase.@)
*/
BOOL WINAPI AllocConsole(void)
{
return alloc_console( FALSE );
}
/******************************************************************************
* CreateConsoleScreenBuffer (kernelbase.@)
*/
@ -2287,12 +2294,14 @@ void init_console( void )
init_console_std_handles( FALSE );
}
}
else if (params->ConsoleHandle == CONSOLE_HANDLE_ALLOC)
else if (params->ConsoleHandle == CONSOLE_HANDLE_ALLOC ||
params->ConsoleHandle == CONSOLE_HANDLE_ALLOC_NO_WINDOW)
{
BOOL no_window = params->ConsoleHandle == CONSOLE_HANDLE_ALLOC_NO_WINDOW;
HMODULE mod = GetModuleHandleW( NULL );
params->ConsoleHandle = NULL;
if (RtlImageNtHeader( mod )->OptionalHeader.Subsystem == IMAGE_SUBSYSTEM_WINDOWS_CUI)
AllocConsole();
alloc_console( no_window );
}
else if (params->ConsoleHandle) create_console_connection( params->ConsoleHandle );
}

View File

@ -193,8 +193,12 @@ static RTL_USER_PROCESS_PARAMETERS *create_process_params( const WCHAR *filename
if (flags & CREATE_NEW_CONSOLE) params->ConsoleHandle = CONSOLE_HANDLE_ALLOC;
else if (!(flags & DETACHED_PROCESS))
{
params->ConsoleHandle = NtCurrentTeb()->Peb->ProcessParameters->ConsoleHandle;
if (!params->ConsoleHandle) params->ConsoleHandle = CONSOLE_HANDLE_ALLOC;
if (flags & CREATE_NO_WINDOW) params->ConsoleHandle = CONSOLE_HANDLE_ALLOC_NO_WINDOW;
else
{
params->ConsoleHandle = NtCurrentTeb()->Peb->ProcessParameters->ConsoleHandle;
if (!params->ConsoleHandle) params->ConsoleHandle = CONSOLE_HANDLE_ALLOC;
}
}
if (startup->dwFlags & STARTF_USESTDHANDLES)
@ -532,8 +536,7 @@ BOOL WINAPI DECLSPEC_HOTPATCH CreateProcessInternalW( HANDLE token, const WCHAR
/* Warn if unsupported features are used */
if (flags & (IDLE_PRIORITY_CLASS | HIGH_PRIORITY_CLASS | REALTIME_PRIORITY_CLASS |
CREATE_DEFAULT_ERROR_MODE | CREATE_NO_WINDOW |
PROFILE_USER | PROFILE_KERNEL | PROFILE_SERVER))
CREATE_DEFAULT_ERROR_MODE | PROFILE_USER | PROFILE_KERNEL | PROFILE_SERVER))
WARN( "(%s,...): ignoring some flags in %lx\n", debugstr_w(app_name), flags );
if (cur_dir)

View File

@ -445,6 +445,7 @@ static NTSTATUS spawn_process( const RTL_USER_PROCESS_PARAMETERS *params, int so
{
if (params->ConsoleFlags ||
params->ConsoleHandle == CONSOLE_HANDLE_ALLOC ||
params->ConsoleHandle == CONSOLE_HANDLE_ALLOC_NO_WINDOW ||
(params->hStdInput == INVALID_HANDLE_VALUE && params->hStdOutput == INVALID_HANDLE_VALUE))
{
setsid();
@ -585,6 +586,7 @@ static NTSTATUS fork_and_exec( OBJECT_ATTRIBUTES *attr, int unixdir,
if (params->ConsoleFlags ||
params->ConsoleHandle == CONSOLE_HANDLE_ALLOC ||
params->ConsoleHandle == CONSOLE_HANDLE_ALLOC_NO_WINDOW ||
(params->hStdInput == INVALID_HANDLE_VALUE && params->hStdOutput == INVALID_HANDLE_VALUE))
{
setsid();

View File

@ -188,7 +188,8 @@ struct condrv_ctrl_event
};
/* Wine specific values for console inheritance (params->ConsoleHandle) */
#define CONSOLE_HANDLE_ALLOC ((HANDLE)1)
#define CONSOLE_HANDLE_SHELL ((HANDLE)2)
#define CONSOLE_HANDLE_ALLOC UlongToHandle(1)
#define CONSOLE_HANDLE_ALLOC_NO_WINDOW UlongToHandle(2)
#define CONSOLE_HANDLE_SHELL UlongToHandle(3)
#endif /* _INC_CONDRV */

View File

@ -2650,7 +2650,7 @@ static NTSTATUS console_input_ioctl( struct console *console, unsigned int code,
TRACE( "get window\n" );
if (in_size || *out_size != sizeof(*result)) return STATUS_INVALID_PARAMETER;
if (!(result = alloc_ioctl_buffer( sizeof(*result )))) return STATUS_NO_MEMORY;
if (!console->win) init_message_window( console );
if (!console->win && !console->no_window) init_message_window( console );
*result = condrv_handle( console->win );
return STATUS_SUCCESS;
}
@ -2929,8 +2929,13 @@ int __cdecl wmain(int argc, WCHAR *argv[])
{
console.tty_input = GetStdHandle( STD_INPUT_HANDLE );
console.tty_output = GetStdHandle( STD_OUTPUT_HANDLE );
init_tty_output( &console );
if (!console.is_unix && !ensure_tty_input_thread( &console )) return 1;
if (console.tty_input || console.tty_output)
{
init_tty_output( &console );
if (!console.is_unix && !ensure_tty_input_thread( &console )) return 1;
}
else console.no_window = TRUE;
}
else
{

View File

@ -79,6 +79,7 @@ struct console
struct screen_buffer *active; /* active screen buffer */
int is_unix; /* UNIX terminal mode */
int use_relative_cursor; /* use relative cursor positionning */
int no_window; /* don't create console window */
INPUT_RECORD *records; /* input records */
unsigned int record_count; /* number of input records */
unsigned int record_size; /* size of input records buffer */