[PATCH] server: Do not allow parenting non-empty job.
Paul Gofman
pgofman at codeweavers.com
Thu May 27 10:48:46 CDT 2021
Fixes a regression introduced by 21f5597de417575d476a00b567d972a89903b4b6
Signed-off-by: Paul Gofman <pgofman at codeweavers.com>
---
dlls/kernel32/tests/process.c | 54 +++++++++++++++++++++++++++++++++++
server/process.c | 5 ++++
2 files changed, 59 insertions(+)
diff --git a/dlls/kernel32/tests/process.c b/dlls/kernel32/tests/process.c
index 9b91b6f0998..6b135e7f052 100644
--- a/dlls/kernel32/tests/process.c
+++ b/dlls/kernel32/tests/process.c
@@ -4502,6 +4502,7 @@ done:
static void test_nested_jobs(void)
{
+ BOOL ret, already_in_job = TRUE, create_succeeded = FALSE;
PROCESS_INFORMATION info[2];
char buffer[MAX_PATH + 26];
STARTUPINFOA si = {0};
@@ -4514,6 +4515,59 @@ static void test_nested_jobs(void)
return;
}
+ job1 = pCreateJobObjectW(NULL, NULL);
+ ok(!!job1, "CreateJobObjectW failed, error %u.\n", GetLastError());
+ job2 = pCreateJobObjectW(NULL, NULL);
+ ok(!!job2, "CreateJobObjectW failed, error %u.\n", GetLastError());
+
+ create_succeeded = TRUE;
+ sprintf(buffer, "\"%s\" process wait", selfname);
+ for (i = 0; i < 2; ++i)
+ {
+ ret = CreateProcessA(NULL, buffer, NULL, NULL, FALSE, CREATE_BREAKAWAY_FROM_JOB, NULL, NULL, &si, &info[i]);
+ if (!ret && GetLastError() == ERROR_ACCESS_DENIED)
+ {
+ create_succeeded = FALSE;
+ break;
+ }
+ ok(ret, "CreateProcessA error %u\n", GetLastError());
+ }
+
+ if (create_succeeded)
+ {
+ ret = pIsProcessInJob(info[0].hProcess, NULL, &already_in_job);
+ ok(ret, "IsProcessInJob error %u\n", GetLastError());
+
+ if (!already_in_job)
+ {
+ ret = pAssignProcessToJobObject(job2, info[1].hProcess);
+ ok(ret, "AssignProcessToJobObject error %u\n", GetLastError());
+
+ ret = pAssignProcessToJobObject(job1, info[0].hProcess);
+ ok(ret, "AssignProcessToJobObject error %u\n", GetLastError());
+
+ ret = pAssignProcessToJobObject(job2, info[0].hProcess);
+ ok(!ret, "AssignProcessToJobObject succeeded\n");
+ ok(GetLastError() == ERROR_ACCESS_DENIED, "Got unexpected error %u.\n", GetLastError());
+ }
+
+ for (i = 0; i < 2; ++i)
+ {
+ TerminateProcess(info[i].hProcess, 0);
+ wait_child_process(info[i].hProcess);
+ CloseHandle(info[i].hProcess);
+ CloseHandle(info[i].hThread);
+ }
+ }
+
+ if (already_in_job)
+ {
+ win_skip("Test process is already in job, can't test parenting non-empty job.\n");
+ }
+
+ CloseHandle(job1);
+ CloseHandle(job2);
+
job1 = pCreateJobObjectW(NULL, L"test_nested_jobs_0");
ok(!!job1, "CreateJobObjectW failed, error %u.\n", GetLastError());
job2 = pCreateJobObjectW(NULL, L"test_nested_jobs_1");
diff --git a/server/process.c b/server/process.c
index e8bbe0d3106..bd7c2c5cd8e 100644
--- a/server/process.c
+++ b/server/process.c
@@ -312,6 +312,11 @@ static void add_job_process( struct job *job, struct process *process )
}
else
{
+ if (job->num_processes)
+ {
+ set_error( STATUS_ACCESS_DENIED );
+ return;
+ }
/* transfer reference. */
job->parent = process->job;
list_add_tail( &job->parent->child_job_list, &job->parent_job_entry );
--
2.31.1
More information about the wine-devel
mailing list