Delphi 如何仅使用作业\对象\基本\限制\信息调用SetInformationJobObject?
我有作业API的基本翻译,如下所示:Delphi 如何仅使用作业\对象\基本\限制\信息调用SetInformationJobObject?,delphi,winapi,delphi-2010,Delphi,Winapi,Delphi 2010,我有作业API的基本翻译,如下所示: type TJobObjectInfoClass = ( JobObjectBasicLimitInformation = 2, JobObjectExtendedLimitInformation = 9 ); TJobObjectBasicLimitInformation = record PerProcessUserTimeLimit: TLargeInteger; PerJobUserTimeLimit:
type
TJobObjectInfoClass = (
JobObjectBasicLimitInformation = 2,
JobObjectExtendedLimitInformation = 9
);
TJobObjectBasicLimitInformation = record
PerProcessUserTimeLimit: TLargeInteger;
PerJobUserTimeLimit: TLargeInteger;
LimitFlags: DWORD;
MinimumWorkingSetSize: DWORD;
MaximumWorkingSetSize: DWORD;
ActiveProcessLimit: DWORD;
Affinity: DWORD;
PriorityClass: DWORD;
SchedulingClass: DWORD;
end;
TIOCounters = record
ReadOperationCount: UInt64;
WriteOperationCount: UInt64;
OtherOperationCount: UInt64;
ReadTransferCount: UInt64;
WriteTransferCount: UInt64;
OtherTransferCount: UInt64;
end;
TJobObjectExtendedLimitInformation = record
BasicLimitInformation: TJobObjectBasicLimitInformation;
IoInfo: TIOCounters;
ProcessMemoryLimit: DWORD;
JobMemoryLimit: DWORD;
PeakProcessMemoryUsed: DWORD;
PeakJobMemoryUsed: DWORD;
end;
const
CREATE_BREAKAWAY_FROM_JOB = $01000000;
JOB_OBJECT_LIMIT_KILL_ON_JOB_CLOSE = $00002000;
function AssignProcessToJobObject(const hJob, hProcess: THandle): BOOL; stdcall;
external kernel32 name 'AssignProcessToJobObject';
function CreateJobObject(const lpJobAttributes: PSecurityAttributes;
const lpName: PChar): THandle; stdcall;
external kernel32 name {$IFDEF UNICODE}'CreateJobObjectW'{$ELSE}'CreateJobObjectA'{$ENDIF};
function SetInformationJobObject(const hJob: THandle;
const JobObjectInformationClass: TJobObjectInfoClass;
const lpJobObjectInformation: Pointer;
const cbJobObjectInformationLength: DWORD): BOOL; stdcall;
external kernel32 name 'SetInformationJobObject';
当我按如下方式使用它时,它工作得很好:
Job := CreateJobObject(nil, nil);
if Job = 0 then
RaiseLastOSError;
ZeroMemory(@JELI, SizeOf(JELI));
JELI.BasicLimitInformation.LimitFlags := JOB_OBJECT_LIMIT_KILL_ON_JOB_CLOSE;
Win32Check(SetInformationJobObject(
Job, JobObjectExtendedLimitInformation, @JELI, SizeOf(JELI))
);
由于我只设置了basiclitinformation
,因此我希望能够调用SetInformationJobObject
,只需这样做:
ZeroMemory(@JBLI, SizeOf(JBLI));
JBLI.LimitFlags := JOB_OBJECT_LIMIT_KILL_ON_JOB_CLOSE;
Win32Check(SetInformationJobObject(
Job, JobObjectBasicLimitInformation, @JBLI, SizeOf(JBLI))
);
MSDN上的文档没有给我任何不支持的指示。那么为什么它会失败,代码为87(“参数不正确”)
我最好的猜测是,我的记录与Windows期望的结构不完全匹配,这意味着一些位位于错误的位置。然而,当它嵌入到另一个中时,它工作得很好。在这里,它是第一个字段,因此不太可能是填充造成的。来自以下文档: [
JOB\u OBJECT\u LIMIT\u KILL\u ON\u JOB\u CLOSE
]需要使用JOBOBJECT\u EXTENDED\u LIMIT\u INFORMATION
结构。其basiclitinformation
成员是JOBOBJECT\u BASIC\u LIMIT\u INFORMATION
结构。”
extended
结构以一个basic
结构开始,因此这两个结构至少部分兼容,这就是为什么不能得到随机结果的原因
这将给出正确的结果:
ZeroMemory(@JELI, SizeOf(JELI));
JELI.BasicLimitInformation.LimitFlags := JOB_OBJECT_LIMIT_KILL_ON_JOB_CLOSE;
Win32Check(SetInformationJobObject(
Job, JobObjectBasicLimitInformation, @JELI, SizeOf(JELI))
);
不是经常使用MSDN,并且忘记检查此特定标志的注释。这就是原因;谢谢!