Kako ne bih doprineo sirenju navike, da se traze _kompletna_ resenja "domacih zadataka", slede samo neophodni delovi, umesto kompletnog programa.
Za Win9x OS-e, dovoljan je poziv API funkcije
Code:
ExitWindowsEx(EWX_POWEROFF | EWX_FORCE, 0);
Medjutim, na OS-ima zasnovanim na NT jezgru (WinNT/2k/XP) potrebno je omoguciti tu "privilegiju" (ako je dozvoljeno) za tekuci proces.
Funkcija koja bi omogucavala tu "privilegiju" mogla bi da izgleda ovako:
Code:
BOOL EnablePrivilege(LPTSTR privilege)
{
BOOL success;
HANDLE token;
LUID luid;
TOKEN_PRIVILEGES tokenPrivileges;
/* dobijanje vrednosti "token-a" za tekuci (ovaj) proces */
success = OpenProcessToken(GetCurrentProcess(), TOKEN_ADJUST_PRIVILEGES | TOKEN_QUERY,
&token);
if (!success)
return FALSE;
/* dobijanje vrednosti za datu "privilegiju" */
success = LookupPrivilegeValue(0, privilege, &luid);
if (!success)
return FALSE;
/* omogucavanje same "privilegije" */
tokenPrivileges.PrivilegeCount = 1;
tokenPrivileges.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED;
tokenPrivileges.Privileges[0].Luid = luid;
success = AdjustTokenPrivileges(token, FALSE, &tokenPrivileges, 0, 0, 0);
/* ako se dogodila greska, vraca se "pogresno" (FALSE - 0). U suprotnom... */
if (GetLastError() != ERROR_SUCCESS)
return FALSE;
/* vraca se "tacno" (TRUE - 1) */
return TRUE;
}
odnosno za onemogucavanje te "privilegije":
Code:
BOOL DisablePrivilege(LPTSTR privilege)
{
HANDLE token;
LUID luid;
BOOL success;
TOKEN_PRIVILEGES tokenPrivileges;
/* dobijanje vrednosti "token-a" za tekuci (ovaj) proces */
success = OpenProcessToken(GetCurrentProcess(), TOKEN_ADJUST_PRIVILEGES | TOKEN_QUERY,
&token);
if (!success)
return FALSE;
/* dobijanje vrednosti za datu "privilegiju" */
success = LookupPrivilegeValue(0, privilege, &luid);
if (!success)
return FALSE;
/* onemogucavanje "privilegije" */
tokenPrivileges.PrivilegeCount = 1;
tokenPrivileges.Privileges[0].Luid = luid;
tokenPrivileges.Privileges[0].Attributes = 0;
success = AdjustTokenPrivileges(token, FALSE, &tokenPrivileges, 0, 0, 0);
if (GetLastError() != ERROR_SUCCESS)
HandleError("AjdustTokenPrivilege()");
return TRUE;
}
Nakon omogucavanje "privilegije" za tekuci proces, na isti nacin kao i kod Win9x se poziva funkcija ExitWindowsEx(), nakon cega se "privilegija" uobicajeno onemogucava.
Za gasenje racunara nakon odredjenog vremenskog perioda, moze se umesto ExitWindowsEx() pozvati funkcija InitiateSystemShutdown(), ili uz naknadni poziv ExitWindowsEx() funkcije, funkcija Sleep(), (opet) ili (ako je u pitanju "event-driven" Win32 API program) meriti proteklo vreme obradjivnajem poruke WM_TIMER...