3 * COPYRIGHT: See COPYING in the top level directory
4 * PROJECT: ReactOS system libraries
5 * FILE: lib/kernel32/process/job.c
6 * PURPOSE: Job functions
7 * PROGRAMMER: Thomas Weidenmueller <w3seek@reactos.com>
12 /* INCLUDES *******************************************************************/
19 /* FUNCTIONS ******************************************************************/
26 CreateJobObjectA(IN LPSECURITY_ATTRIBUTES lpJobAttributes
,
29 /* Call the W(ide) function */
30 ConvertWin32AnsiObjectApiToUnicodeApi(JobObject
, lpName
, lpJobAttributes
);
38 CreateJobObjectW(IN LPSECURITY_ATTRIBUTES lpJobAttributes
,
41 /* Create the NT object */
42 CreateNtObjectFromWin32Api(JobObject
, JobObject
, JOB
, lpJobAttributes
, lpName
);
50 OpenJobObjectW(IN DWORD dwDesiredAccess
,
51 IN BOOL bInheritHandle
,
54 /* Open the NT object */
55 OpenNtObjectFromWin32Api(JobObject
, dwDesiredAccess
, bInheritHandle
, lpName
);
64 OpenJobObjectA(IN DWORD dwDesiredAccess
,
65 IN BOOL bInheritHandle
,
68 /* Call the W(ide) function */
69 ConvertOpenWin32AnsiObjectApiToUnicodeApi(JobObject
, dwDesiredAccess
, bInheritHandle
, lpName
);
77 IsProcessInJob(IN HANDLE ProcessHandle
,
83 Status
= NtIsProcessInJob(ProcessHandle
, JobHandle
);
84 if (NT_SUCCESS(Status
))
86 *Result
= (Status
== STATUS_PROCESS_IN_JOB
);
90 BaseSetLastNTError(Status
);
99 AssignProcessToJobObject(IN HANDLE hJob
,
104 Status
= NtAssignProcessToJobObject(hJob
, hProcess
);
105 if (!NT_SUCCESS(Status
))
107 BaseSetLastNTError(Status
);
119 QueryInformationJobObject(IN HANDLE hJob
,
120 IN JOBOBJECTINFOCLASS JobObjectInformationClass
,
121 IN LPVOID lpJobObjectInformation
,
122 IN DWORD cbJobObjectInformationLength
,
123 OUT LPDWORD lpReturnLength
)
127 JOBOBJECT_EXTENDED_LIMIT_INFORMATION LocalInfo
;
130 if (JobObjectInformationClass
== JobObjectBasicLimitInformation
)
132 ExpectedSize
= sizeof(JOBOBJECT_BASIC_LIMIT_INFORMATION
);
133 JobInfo
= &LocalInfo
;
135 else if (JobObjectInformationClass
== JobObjectBasicLimitInformation
)
137 ExpectedSize
= sizeof(JOBOBJECT_EXTENDED_LIMIT_INFORMATION
);
138 JobInfo
= &LocalInfo
;
142 ExpectedSize
= cbJobObjectInformationLength
;
143 JobInfo
= lpJobObjectInformation
;
146 if (cbJobObjectInformationLength
!= ExpectedSize
)
148 BaseSetLastNTError(STATUS_INFO_LENGTH_MISMATCH
);
152 Status
= NtQueryInformationJobObject(hJob
,
153 JobObjectInformationClass
,
157 if (NT_SUCCESS(Status
))
159 if (JobInfo
!= &LocalInfo
) return TRUE
;
161 switch (LocalInfo
.BasicLimitInformation
.PriorityClass
)
163 case PROCESS_PRIORITY_CLASS_IDLE
:
164 LocalInfo
.BasicLimitInformation
.PriorityClass
=
168 case PROCESS_PRIORITY_CLASS_BELOW_NORMAL
:
169 LocalInfo
.BasicLimitInformation
.PriorityClass
=
170 BELOW_NORMAL_PRIORITY_CLASS
;
173 case PROCESS_PRIORITY_CLASS_NORMAL
:
174 LocalInfo
.BasicLimitInformation
.PriorityClass
=
175 NORMAL_PRIORITY_CLASS
;
178 case PROCESS_PRIORITY_CLASS_ABOVE_NORMAL
:
179 LocalInfo
.BasicLimitInformation
.PriorityClass
=
180 ABOVE_NORMAL_PRIORITY_CLASS
;
183 case PROCESS_PRIORITY_CLASS_HIGH
:
184 LocalInfo
.BasicLimitInformation
.PriorityClass
=
188 case PROCESS_PRIORITY_CLASS_REALTIME
:
189 LocalInfo
.BasicLimitInformation
.PriorityClass
=
190 REALTIME_PRIORITY_CLASS
;
194 LocalInfo
.BasicLimitInformation
.PriorityClass
=
195 NORMAL_PRIORITY_CLASS
;
199 RtlCopyMemory(lpJobObjectInformation
, &LocalInfo
, ExpectedSize
);
203 BaseSetLastNTError(Status
);
212 SetInformationJobObject(IN HANDLE hJob
,
213 IN JOBOBJECTINFOCLASS JobObjectInformationClass
,
214 IN LPVOID lpJobObjectInformation
,
215 IN DWORD cbJobObjectInformationLength
)
219 JOBOBJECT_EXTENDED_LIMIT_INFORMATION LocalInfo
;
222 ULONG Privilege
= SE_INC_BASE_PRIORITY_PRIVILEGE
;
224 if (JobObjectInformationClass
== JobObjectBasicLimitInformation
)
226 ExpectedSize
= sizeof(JOBOBJECT_BASIC_LIMIT_INFORMATION
);
227 JobInfo
= &LocalInfo
;
229 else if (JobObjectInformationClass
== JobObjectBasicLimitInformation
)
231 ExpectedSize
= sizeof(JOBOBJECT_EXTENDED_LIMIT_INFORMATION
);
232 JobInfo
= &LocalInfo
;
236 ExpectedSize
= cbJobObjectInformationLength
;
237 JobInfo
= lpJobObjectInformation
;
240 if (cbJobObjectInformationLength
!= ExpectedSize
)
242 BaseSetLastNTError(STATUS_INFO_LENGTH_MISMATCH
);
246 if (JobInfo
== &LocalInfo
)
248 RtlCopyMemory(&LocalInfo
, lpJobObjectInformation
, ExpectedSize
);
250 if (LocalInfo
.BasicLimitInformation
.LimitFlags
&
251 JOB_OBJECT_LIMIT_PRIORITY_CLASS
)
253 switch (LocalInfo
.BasicLimitInformation
.PriorityClass
)
255 case IDLE_PRIORITY_CLASS
:
256 LocalInfo
.BasicLimitInformation
.PriorityClass
=
257 PROCESS_PRIORITY_CLASS_IDLE
;
260 case BELOW_NORMAL_PRIORITY_CLASS
:
261 LocalInfo
.BasicLimitInformation
.PriorityClass
=
262 PROCESS_PRIORITY_CLASS_BELOW_NORMAL
;
265 case NORMAL_PRIORITY_CLASS
:
266 LocalInfo
.BasicLimitInformation
.PriorityClass
=
267 PROCESS_PRIORITY_CLASS_NORMAL
;
270 case ABOVE_NORMAL_PRIORITY_CLASS
:
271 LocalInfo
.BasicLimitInformation
.PriorityClass
=
272 PROCESS_PRIORITY_CLASS_ABOVE_NORMAL
;
275 case HIGH_PRIORITY_CLASS
:
276 LocalInfo
.BasicLimitInformation
.PriorityClass
=
277 PROCESS_PRIORITY_CLASS_HIGH
;
280 case REALTIME_PRIORITY_CLASS
:
281 LocalInfo
.BasicLimitInformation
.PriorityClass
=
282 PROCESS_PRIORITY_CLASS_REALTIME
;
286 LocalInfo
.BasicLimitInformation
.PriorityClass
=
287 PROCESS_PRIORITY_CLASS_NORMAL
;
292 if (LocalInfo
.BasicLimitInformation
.LimitFlags
&
293 JOB_OBJECT_LIMIT_WORKINGSET
)
295 Status
= RtlAcquirePrivilege(&Privilege
, TRUE
, FALSE
, &State
);
299 Status
= NtSetInformationJobObject(hJob
,
300 JobObjectInformationClass
,
303 if (NT_SUCCESS(Status
))
305 if (State
!= NULL
) RtlReleasePrivilege(State
);
309 BaseSetLastNTError(Status
);
318 TerminateJobObject(IN HANDLE hJob
,
323 Status
= NtTerminateJobObject(hJob
, uExitCode
);
324 if (!NT_SUCCESS(Status
))
326 BaseSetLastNTError(Status
);
338 CreateJobSet(IN ULONG NumJob
,
339 IN PJOB_SET_ARRAY UserJobSet
,
344 Status
= NtCreateJobSet(NumJob
, UserJobSet
, Flags
);
345 if (!NT_SUCCESS(Status
))
347 BaseSetLastNTError(Status
);