/********************************************************************** * AbortSystemShutdownA * * @unimplemented */ BOOL WINAPI AbortSystemShutdownA(LPCSTR lpMachineName) { ANSI_STRING MachineNameA; UNICODE_STRING MachineNameW; NTSTATUS Status; BOOL rv; RtlInitAnsiString(&MachineNameA, (LPSTR)lpMachineName); Status = RtlAnsiStringToUnicodeString(&MachineNameW, &MachineNameA, TRUE); if (STATUS_SUCCESS != Status) { SetLastError(RtlNtStatusToDosError(Status)); return FALSE; } rv = AbortSystemShutdownW(MachineNameW.Buffer); RtlFreeUnicodeString(&MachineNameW); SetLastError(ERROR_SUCCESS); return rv; }
/* Main entry for program */ int wmain(int argc, WCHAR *argv[]) { DWORD error = ERROR_SUCCESS; struct CommandLineOptions opts; if (argc == 1) /* i.e. no commandline arguments given */ { PrintResourceString(IDS_USAGE); return EXIT_SUCCESS; } error = ParseArguments(&opts, argc, argv); if (error != ERROR_SUCCESS) { DisplayError(error); return EXIT_FAILURE; } /* If the user wants to abort a shutdown */ if (opts.abort) { /* First, the program has to determine if the shutdown/restart is local or remote. This is done since each one requires separate privileges. */ if (opts.remote_system == NULL) EnablePrivilege(SE_SHUTDOWN_NAME, TRUE); else EnablePrivilege(SE_REMOTE_SHUTDOWN_NAME, TRUE); /* Abort the delayed system shutdown specified. */ if (!AbortSystemShutdownW(opts.remote_system)) { PrintResourceString(IDS_ERROR_ABORT); DisplayError(GetLastError()); return EXIT_FAILURE; } else { return EXIT_SUCCESS; } } /* * If the user wants to hibernate the computer. Assume * that the user wants to wake the computer up from * hibernation and it should not force it on the system. */ if (opts.hibernate) { if (IsPwrHibernateAllowed()) { EnablePrivilege(SE_SHUTDOWN_NAME, TRUE); /* The shutdown utility cannot hibernate remote systems */ if (opts.remote_system != NULL) { return EXIT_FAILURE; } if (!SetSuspendState(TRUE, FALSE, FALSE)) { PrintResourceString(IDS_ERROR_HIBERNATE); DisplayError(GetLastError()); return EXIT_FAILURE; } else { PrintResourceString(IDS_ERROR_HIBERNATE_ENABLED); return EXIT_SUCCESS; } } else { return EXIT_FAILURE; } } /* Both shutdown and restart flags cannot both be true */ if (opts.shutdown && opts.restart) { PrintResourceString(IDS_ERROR_SHUTDOWN_REBOOT); return EXIT_FAILURE; } /* Ensure that the timout amount is not too high or a negative number */ if ((opts.shutdown_delay < 0) || (opts.shutdown_delay > MAX_TIMEOUT)) { PrintResourceString(IDS_ERROR_TIMEOUT, opts.shutdown_delay); return EXIT_FAILURE; } /* If the user wants a GUI environment */ if (opts.show_gui) { if (ShutdownGuiMain(opts)) return EXIT_SUCCESS; else return EXIT_FAILURE; } if (opts.logoff && (opts.remote_system == NULL)) { /* * NOTE: Sometimes, shutdown and logoff are used together. If the logoff * flag is used by itself, then simply logoff. But if used with shutdown, * then skip logging off of the computer and eventually go to the action * for shutdown. */ if (!opts.shutdown && !opts.restart) { EnablePrivilege(SE_SHUTDOWN_NAME, TRUE); if (ExitWindowsEx(EWX_LOGOFF, opts.reason)) { return EXIT_SUCCESS; } else { PrintResourceString(IDS_ERROR_LOGOFF); DisplayError(GetLastError()); return EXIT_FAILURE; } } } /* * Since both shutting down the system and restarting calls the exact same * function, all we need to know is if we wanted to restart or shutdown. */ if (opts.shutdown || opts.restart) { /* * First, the program has to determine if the shutdown/restart is local * or remote. This is done since each one requires separate privileges. */ if (opts.remote_system == NULL) { EnablePrivilege(SE_SHUTDOWN_NAME, TRUE); } else { /* TODO: Remote shutdown is not supported yet */ // EnablePrivilege(SE_REMOTE_SHUTDOWN_NAME, TRUE); return EXIT_SUCCESS; } /** ** HACK: When InitiateSystemShutdownExW will become really implemented, ** activate this line and delete the other... ** if(!InitiateSystemShutdownExW(opts.remote_system, opts.message, opts.shutdown_delay, opts.force, opts.restart, opts.reason)) ***/ if (!ExitWindowsEx((opts.shutdown ? EWX_SHUTDOWN : EWX_REBOOT) | (opts.force ? EWX_FORCE : 0), opts.reason)) { /* * If there is an error, give the proper output depending * on whether the user wanted to shutdown or restart. */ if (opts.restart) PrintResourceString(IDS_ERROR_RESTART); else PrintResourceString(IDS_ERROR_SHUTDOWN); DisplayError(GetLastError()); return EXIT_FAILURE; } else { return EXIT_SUCCESS; } } return EXIT_SUCCESS; }