kernelbase: Pass inherited handles list when creating new process.
Signed-off-by: Nikolay Sivov <nsivov@codeweavers.com> Signed-off-by: Alexandre Julliard <julliard@winehq.org>
This commit is contained in:
parent
3a9c50e3ff
commit
1721f0ff27
|
@ -242,26 +242,89 @@ static RTL_USER_PROCESS_PARAMETERS *create_process_params( const WCHAR *filename
|
|||
return params;
|
||||
}
|
||||
|
||||
struct proc_thread_attr
|
||||
{
|
||||
DWORD_PTR attr;
|
||||
SIZE_T size;
|
||||
void *value;
|
||||
};
|
||||
|
||||
struct _PROC_THREAD_ATTRIBUTE_LIST
|
||||
{
|
||||
DWORD mask; /* bitmask of items in list */
|
||||
DWORD size; /* max number of items in list */
|
||||
DWORD count; /* number of items in list */
|
||||
DWORD pad;
|
||||
DWORD_PTR unk;
|
||||
struct proc_thread_attr attrs[1];
|
||||
};
|
||||
|
||||
/***********************************************************************
|
||||
* create_nt_process
|
||||
*/
|
||||
static NTSTATUS create_nt_process( SECURITY_ATTRIBUTES *psa, SECURITY_ATTRIBUTES *tsa,
|
||||
BOOL inherit, DWORD flags, RTL_USER_PROCESS_PARAMETERS *params,
|
||||
RTL_USER_PROCESS_INFORMATION *info, HANDLE parent )
|
||||
RTL_USER_PROCESS_INFORMATION *info, HANDLE parent,
|
||||
const struct proc_thread_attr *handle_list )
|
||||
{
|
||||
NTSTATUS status;
|
||||
OBJECT_ATTRIBUTES process_attr, thread_attr;
|
||||
PS_CREATE_INFO create_info;
|
||||
ULONG_PTR buffer[offsetof( PS_ATTRIBUTE_LIST, Attributes[5] ) / sizeof(ULONG_PTR)];
|
||||
PS_ATTRIBUTE_LIST *attr = (PS_ATTRIBUTE_LIST *)buffer;
|
||||
UNICODE_STRING nameW;
|
||||
NTSTATUS status;
|
||||
UINT pos = 0;
|
||||
|
||||
if (!params->ImagePathName.Buffer[0]) return STATUS_OBJECT_PATH_NOT_FOUND;
|
||||
status = RtlDosPathNameToNtPathName_U_WithStatus( params->ImagePathName.Buffer, &nameW, NULL, NULL );
|
||||
if (!status)
|
||||
{
|
||||
params->DebugFlags = flags; /* hack, cf. RtlCreateUserProcess implementation */
|
||||
status = RtlCreateUserProcess( &nameW, OBJ_CASE_INSENSITIVE, params,
|
||||
psa ? psa->lpSecurityDescriptor : NULL,
|
||||
tsa ? tsa->lpSecurityDescriptor : NULL,
|
||||
parent, inherit, 0, 0, info );
|
||||
|
||||
RtlNormalizeProcessParams( params );
|
||||
|
||||
attr->Attributes[pos].Attribute = PS_ATTRIBUTE_IMAGE_NAME;
|
||||
attr->Attributes[pos].Size = nameW.Length;
|
||||
attr->Attributes[pos].ValuePtr = nameW.Buffer;
|
||||
attr->Attributes[pos].ReturnLength = NULL;
|
||||
pos++;
|
||||
attr->Attributes[pos].Attribute = PS_ATTRIBUTE_CLIENT_ID;
|
||||
attr->Attributes[pos].Size = sizeof(info->ClientId);
|
||||
attr->Attributes[pos].ValuePtr = &info->ClientId;
|
||||
attr->Attributes[pos].ReturnLength = NULL;
|
||||
pos++;
|
||||
attr->Attributes[pos].Attribute = PS_ATTRIBUTE_IMAGE_INFO;
|
||||
attr->Attributes[pos].Size = sizeof(info->ImageInformation);
|
||||
attr->Attributes[pos].ValuePtr = &info->ImageInformation;
|
||||
attr->Attributes[pos].ReturnLength = NULL;
|
||||
pos++;
|
||||
if (parent)
|
||||
{
|
||||
attr->Attributes[pos].Attribute = PS_ATTRIBUTE_PARENT_PROCESS;
|
||||
attr->Attributes[pos].Size = sizeof(parent);
|
||||
attr->Attributes[pos].ValuePtr = parent;
|
||||
attr->Attributes[pos].ReturnLength = NULL;
|
||||
pos++;
|
||||
}
|
||||
if (inherit && handle_list)
|
||||
{
|
||||
attr->Attributes[pos].Attribute = PS_ATTRIBUTE_HANDLE_LIST;
|
||||
attr->Attributes[pos].Size = handle_list->size;
|
||||
attr->Attributes[pos].ValuePtr = handle_list->value;
|
||||
attr->Attributes[pos].ReturnLength = NULL;
|
||||
pos++;
|
||||
}
|
||||
attr->TotalLength = offsetof( PS_ATTRIBUTE_LIST, Attributes[pos] );
|
||||
|
||||
InitializeObjectAttributes( &process_attr, NULL, 0, NULL, psa ? psa->lpSecurityDescriptor : NULL );
|
||||
InitializeObjectAttributes( &thread_attr, NULL, 0, NULL, tsa ? tsa->lpSecurityDescriptor : NULL );
|
||||
|
||||
status = NtCreateUserProcess( &info->Process, &info->Thread, PROCESS_ALL_ACCESS, THREAD_ALL_ACCESS,
|
||||
&process_attr, &thread_attr,
|
||||
inherit ? PROCESS_CREATE_FLAGS_INHERIT_HANDLES : 0,
|
||||
THREAD_CREATE_FLAGS_CREATE_SUSPENDED, params,
|
||||
&create_info, attr );
|
||||
|
||||
RtlFreeUnicodeString( &nameW );
|
||||
}
|
||||
return status;
|
||||
|
@ -292,7 +355,7 @@ static NTSTATUS create_vdm_process( SECURITY_ATTRIBUTES *psa, SECURITY_ATTRIBUTE
|
|||
winevdm, params->ImagePathName.Buffer, params->CommandLine.Buffer );
|
||||
RtlInitUnicodeString( ¶ms->ImagePathName, winevdm );
|
||||
RtlInitUnicodeString( ¶ms->CommandLine, newcmdline );
|
||||
status = create_nt_process( psa, tsa, inherit, flags, params, info, NULL );
|
||||
status = create_nt_process( psa, tsa, inherit, flags, params, info, NULL, NULL );
|
||||
HeapFree( GetProcessHeap(), 0, newcmdline );
|
||||
return status;
|
||||
}
|
||||
|
@ -320,7 +383,7 @@ static NTSTATUS create_cmd_process( SECURITY_ATTRIBUTES *psa, SECURITY_ATTRIBUTE
|
|||
swprintf( newcmdline, len, L"%s /s/c \"%s\"", comspec, params->CommandLine.Buffer );
|
||||
RtlInitUnicodeString( ¶ms->ImagePathName, comspec );
|
||||
RtlInitUnicodeString( ¶ms->CommandLine, newcmdline );
|
||||
status = create_nt_process( psa, tsa, inherit, flags, params, info, NULL );
|
||||
status = create_nt_process( psa, tsa, inherit, flags, params, info, NULL, NULL );
|
||||
RtlFreeHeap( GetProcessHeap(), 0, newcmdline );
|
||||
return status;
|
||||
}
|
||||
|
@ -414,23 +477,6 @@ done:
|
|||
return ret;
|
||||
}
|
||||
|
||||
struct proc_thread_attr
|
||||
{
|
||||
DWORD_PTR attr;
|
||||
SIZE_T size;
|
||||
void *value;
|
||||
};
|
||||
|
||||
struct _PROC_THREAD_ATTRIBUTE_LIST
|
||||
{
|
||||
DWORD mask; /* bitmask of items in list */
|
||||
DWORD size; /* max number of items in list */
|
||||
DWORD count; /* number of items in list */
|
||||
DWORD pad;
|
||||
DWORD_PTR unk;
|
||||
struct proc_thread_attr attrs[1];
|
||||
};
|
||||
|
||||
/**********************************************************************
|
||||
* CreateProcessInternalW (kernelbase.@)
|
||||
*/
|
||||
|
@ -441,6 +487,7 @@ BOOL WINAPI DECLSPEC_HOTPATCH CreateProcessInternalW( HANDLE token, const WCHAR
|
|||
const WCHAR *cur_dir, STARTUPINFOW *startup_info,
|
||||
PROCESS_INFORMATION *info, HANDLE *new_token )
|
||||
{
|
||||
const struct proc_thread_attr *handle_list = NULL;
|
||||
WCHAR name[MAX_PATH];
|
||||
WCHAR *p, *tidy_cmdline = cmd_line;
|
||||
RTL_USER_PROCESS_PARAMETERS *params = NULL;
|
||||
|
@ -517,6 +564,10 @@ BOOL WINAPI DECLSPEC_HOTPATCH CreateProcessInternalW( HANDLE token, const WCHAR
|
|||
goto done;
|
||||
}
|
||||
break;
|
||||
case PROC_THREAD_ATTRIBUTE_HANDLE_LIST:
|
||||
handle_list = &attrs->attrs[i];
|
||||
TRACE("PROC_THREAD_ATTRIBUTE_HANDLE_LIST handle count %Iu.\n", attrs->attrs[i].size / sizeof(HANDLE));
|
||||
break;
|
||||
default:
|
||||
FIXME("Unsupported attribute %#Ix.\n", attrs->attrs[i].attr);
|
||||
break;
|
||||
|
@ -525,7 +576,7 @@ BOOL WINAPI DECLSPEC_HOTPATCH CreateProcessInternalW( HANDLE token, const WCHAR
|
|||
}
|
||||
}
|
||||
|
||||
status = create_nt_process( process_attr, thread_attr, inherit, flags, params, &rtl_info, parent );
|
||||
status = create_nt_process( process_attr, thread_attr, inherit, flags, params, &rtl_info, parent, handle_list );
|
||||
switch (status)
|
||||
{
|
||||
case STATUS_SUCCESS:
|
||||
|
|
Loading…
Reference in New Issue