How do I shut down, restart, sleep programmatically?

4

I would like to add these options to a program, after finishing a task the computer would be shut down / restarted / placed in sleep .

How can I do this?

    
asked by anonymous 21.12.2013 / 03:23

2 answers

4

To manage operations like this I've created a class to call the methods of external DLLs:

public class WinPower
{
    [StructLayout(LayoutKind.Sequential, Pack = 1)]
    internal struct TokPriv1Luid
    {
        public int Count;
        public long Luid;
        public int Attr;
    }

    [DllImport("kernel32.dll", ExactSpelling = true)]
    internal static extern IntPtr GetCurrentProcess();

    [DllImport("advapi32.dll", ExactSpelling = true, SetLastError = true)]
    internal static extern bool OpenProcessToken(IntPtr h, int acc, ref IntPtr
    phtok);

    [DllImport("advapi32.dll", SetLastError = true)]
    internal static extern bool LookupPrivilegeValue(string host, string name,
    ref long pluid);

    [DllImport("advapi32.dll", ExactSpelling = true, SetLastError = true)]
    internal static extern bool AdjustTokenPrivileges(IntPtr htok, bool disall,
    ref TokPriv1Luid newst, int len, IntPtr prev, IntPtr relen);

    [DllImport("user32.dll", ExactSpelling = true, SetLastError = true)]
    internal static extern bool ExitWindowsEx(int flg, int rea);

    [DllImport("Powrprof.dll", CharSet = CharSet.Auto, ExactSpelling = true)]
    public static extern bool SetSuspendState(bool hiberate, bool forceCritical, bool disableWakeEvent);


    internal const int SE_PRIVILEGE_ENABLED = 0x00000002;
    internal const int TOKEN_QUERY = 0x00000008;
    internal const int TOKEN_ADJUST_PRIVILEGES = 0x00000020;
    internal const string SE_SHUTDOWN_NAME = "SeShutdownPrivilege";

    internal const int EWX_LOGOFF = 0x00000000;
    internal const int EWX_SHUTDOWN = 0x00000001;
    internal const int EWX_REBOOT = 0x00000002;
    internal const int EWX_FORCE = 0x00000004;
    internal const int EWX_POWEROFF = 0x00000008;
    internal const int EWX_FORCEIFHUNG = 0x00000010;

    public enum PowerOption
    {
        //Logoff = 0,
        Reboot = 2,
        PowerOff = 8,
        PowerOffForce = 4,
        PowerOffForceIfHung = 10,

        Sleep = 100,
        Hibernate = 102
    }

    public static void Execute(PowerOption option)
    {
        if (option == PowerOption.Sleep)
        {
            SetSuspendState(false, true, true);
            return;
        }
        else if (option == PowerOption.Hibernate)
        {
            SetSuspendState(true, true, true);
            return;
        }
        else
        {
            bool ok;
            TokPriv1Luid tp;
            IntPtr hproc = GetCurrentProcess();
            IntPtr htok = IntPtr.Zero;
            ok = OpenProcessToken(hproc, TOKEN_ADJUST_PRIVILEGES | TOKEN_QUERY, ref htok);
            tp.Count = 1;
            tp.Luid = 0;
            tp.Attr = SE_PRIVILEGE_ENABLED;
            ok = LookupPrivilegeValue(null, SE_SHUTDOWN_NAME, ref tp.Luid);
            ok = AdjustTokenPrivileges(htok, false, ref tp, 0, IntPtr.Zero, IntPtr.Zero);
            ok = ExitWindowsEx((int)option, 0);
        }
    }
}

The Execute method is what will perform the operation, use examples:

WinPower.Execute(WinPower.PowerOption.PowerOff);
WinPower.Execute(WinPower.PowerOption.Reboot);
WinPower.Execute(WinPower.PowerOption.Sleep);
WinPower.Execute(WinPower.PowerOption.Hibernate);

In case you make the computer sleep or hibernate just invoke the method SetSuspendState

rundll32.exe powrprof.dll,SetSuspendState 0,1,1 // dormir
rundll32.exe powrprof.dll,SetSuspendState 1,1,1 // hibernar

In case of shutdown / restart it is necessary to invoke the other methods and finally invoke ExitWindowsEx passing the value (2 = restart, 8 = shutdown)

References (in English):

21.12.2013 / 03:48
3

You can use the System.Diagnostics library >.

Using System.Diagnostics;

Within some action you can enter the command Process.Start :

{
    Process.Start("Shutdown", "-i");
}
    
21.12.2013 / 03:35