A megoldáshoz fontos tudnunk, hogy milyen operációs rendszer alatt fut a programunk, mivel Win9x sorozat alatt más a módja mint WinNT alatt.
Win 95, 98, Me
Ez esetben a SetSuspendState függvény hívása lesz a kulcs. A függvény a Delphi unit-jaiban nem deklarált, így használatához ezt pótolnunk kell:
function SetSuspendState (Hibernate: boolean; ForceCritical: boolean; DisableWakeEvent: boolean): boolean; stdcall; external ‘Powrprof.dll’;
Ha a függvény Hibernate nevű paramétere igaz, akkor hibernálás funkció kerül végrehajtásra, különben a készenléti állapot.
A ForceCritical paraméter igaz értéke esetén egy PBT_APMSUSPEND üzenet kerül elküldésre minden alkalmazásnak és driver-nek, míg hamis érték esetén PBT_APMQUERYSUSPEND üzenet. Az első esetben feltétel nélkül megtörténik a kért funkció, míg a második esetben valamely alkalmazás, vagy driver megakadályozhatja a hibernálást, készenléti állapotba kerülést.
A DisableWakeEvent paraméter igaz értéke esetén letiltjuk a feléledés eseményét, míg hamis érték esetén létrejön ez az esemény újrainduláskor.
Win NT, 2000, XP, .NET
Windows NT vonalon a SetSystemPowerState függvény használatos, mellékelt példánkban is ezt valósítottuk meg.
E függvény használata valamivel bonyolultabb, mivel szüksége van alkalmazásunknak a SE_SHUTDOWN_NAME jog megszerzésére is.
A SetSystemPowerState függvény első paramétere ha igaz, akkor készenléti állapotba kerül a gép, míg hamis érték esetén hibernálva lesz. A második paraméter igaz értéke esetén egy PBT_APMSUSPEND üzenet kerül elküldésre minden alkalmazásnak és driver-nek, míg hamis érték esetén PBT_APMQUERYSUSPEND üzenet. Az első esetben feltétel nélkül megtörténik a kért funkció, míg a második esetben valamely alkalmazás, vagy driver megakadályozhatja a hibernálást, készenléti állapotba kerülést.
A függvény hívása előtt megfelelő jogokat kell szereznünk alkalmazásunknak, melyhez az AdjustTokenPrivileges függvény használata segít hozzá bennünket.
procedure TForm1.Button1Click(Sender: TObject);
begin
FillChar(tp1, SizeOf(tp1), 0);
if OpenProcessToken(GetCurrentProcess, TOKEN_ADJUST_PRIVILEGES+TOKEN_QUERY, h) then begin
LookupPrivilegeValue(nil, 'SeShutdownPrivilege', tp1.Privileges[0].Luid);
tp1.PrivilegeCount:=1;
tp1.Privileges[0].Attributes:=SE_PRIVILEGE_ENABLED;
AdjustTokenPrivileges(h, false, tp1, sizeof(tp2), tp2, c);
SetSystemPowerState(true, true);
end;
end;