more wolsperiments

This commit is contained in:
alisceon 2026-01-27 16:00:34 +01:00
parent 041440c889
commit 7bedb4c8aa
2 changed files with 36 additions and 6 deletions

View file

@ -61,6 +61,6 @@
}; };
systemPackages = [ systemPackages = [
pkgs.efibootmgr pkgs.efibootmgr
] ];
}; };
} # end file } # end file

View file

@ -11,10 +11,12 @@ TARGET_HOSTNAME = "tower.home.the.malice.zone"
TARGET_IP = socket.gethostbyname(TARGET_HOSTNAME) TARGET_IP = socket.gethostbyname(TARGET_HOSTNAME)
def remote_cmd(command): def remote_cmd(command):
response = subprocess.run(f"ssh tower '{command}", shell=True, capture_output=True, text=True) print(f"Executing: ssh tower '{command}'")
response = subprocess.run(f"ssh tower '{command}'", shell=True, capture_output=True, text=True)
return (response.returncode, response.stdout, response.stderr) return (response.returncode, response.stdout, response.stderr)
def weboot(): def weboot():
print("Rebooting to windows")
code, stdout, stderr = remote_cmd("sudo efibootmgr -n 0000") code, stdout, stderr = remote_cmd("sudo efibootmgr -n 0000")
if code == 0: if code == 0:
code, stdout, stderr = remote_cmd("sudo reboot") code, stdout, stderr = remote_cmd("sudo reboot")
@ -24,19 +26,23 @@ def weboot():
return code, stdout, stderr return code, stdout, stderr
def send_wol(): def send_wol():
print(f"Broadcasting WOL packet to {TARGET_LINK}")
response = subprocess.run(f"wakeonlan {TARGET_LINK}", shell=True, capture_output=True, text=True) response = subprocess.run(f"wakeonlan {TARGET_LINK}", shell=True, capture_output=True, text=True)
return (response.returncode, response.stdout, response.stderr) return (response.returncode, response.stdout, response.stderr)
def get_os(): def get_os():
print("Determining target OS")
code, stdout, stderr = remote_cmd("whoami") code, stdout, stderr = remote_cmd("whoami")
if code == 255 and "No route to host" in stderr: if code == 255 and "No route to host" in stderr:
print("Target is offline")
return "offline" return "offline"
elif code != 0: elif code != 0:
raise RuntimeError(f"win_or_linux failed {stderr}") raise RuntimeError(f"win_or_linux failed {stderr}")
if "Windows" in stdout: if "windows" in stdout.lower():
print("Target is running Windows")
return "windows" return "windows"
else: else:
print("Target is running Linux")
return "linux" return "linux"
def swap_os(): def swap_os():
@ -50,23 +56,31 @@ def swap_os():
return True return True
def boot_linux(): def boot_linux():
print("Booting Linux")
match get_os(): match get_os():
case "windows": case "windows":
print("Tower is busy")
return False return False
case "linux": case "linux":
print("Linux is already running")
return True return True
case "offline": case "offline":
print("Booting via WOL")
send_wol() send_wol()
time.sleep(60) time.sleep(60)
return True return True
def boot_windows(): def boot_windows():
print("Booting Windows")
match get_os(): match get_os():
case "windows": case "windows":
print("Windows is already running")
return True return True
case "linux": case "linux":
print("Tower is busy")
return False return False
case "offline": case "offline":
print("Booting via WOL")
boot_linux() boot_linux()
weboot() weboot()
if get_os() == "windows": if get_os() == "windows":
@ -75,6 +89,7 @@ def boot_windows():
return False return False
def reboot(): def reboot():
print("Rebooting target")
orig_os = get_os() orig_os = get_os()
match orig_os: match orig_os:
case "windows": case "windows":
@ -86,21 +101,29 @@ def reboot():
code, stdout, stderr = remote_cmd("sudo reboot") code, stdout, stderr = remote_cmd("sudo reboot")
return True return True
case "offline": case "offline":
print("Target is offline, cannot reboot")
return False return False
def shutdown(): def shutdown():
print("Shutting down target")
match get_os(): match get_os():
case "windows": case "windows":
code, stdout, stderr = remote_cmd("shutdown /s") code, stdout, stderr = remote_cmd("shutdown /s")
time.sleep(30)
return True return True
case "linux": case "linux":
code, stdout, stderr = remote_cmd("sudo shutdown -h now") code, stdout, stderr = remote_cmd("sudo shutdown -h now")
time.sleep(30)
return True return True
case "offline": case "offline":
print("Target is already offline")
return False return False
def action_do(action): def action_do(action):
match action: match action:
case "get_os":
os = get_os()
print(f"Current OS: {os}")
case "boot_linux": case "boot_linux":
if boot_linux(): if boot_linux():
print("Linux is now running") print("Linux is now running")
@ -131,6 +154,11 @@ def action_do(action):
print("Target is in use, belaying update 1h") print("Target is in use, belaying update 1h")
time.sleep(3600) time.sleep(3600)
action_do("winupdate") action_do("winupdate")
if boot_windows():
print("Initiating Windows update")
else:
print("Failed to boot Windows for update")
return
code, stdout, stderr = remote_cmd("powershell -Command \"& {Install-WindowsUpdate -AcceptAll -AutoReboot}\"") code, stdout, stderr = remote_cmd("powershell -Command \"& {Install-WindowsUpdate -AcceptAll -AutoReboot}\"")
if code == 0: if code == 0:
print("Windows update initiated successfully") print("Windows update initiated successfully")
@ -146,8 +174,10 @@ def action_do(action):
time.sleep(300) time.sleep(300)
shutdown() shutdown()
def main():: def main():
parser = argparse.ArgumentParser(description="WOL and reboot utility") parser = argparse.ArgumentParser(description="WOL and reboot utility")
parser.add_argument("action", choices=["boot_linux", "boot_windows", "swap_os", "reboot", "shutdown", "winupdate"], help="Action to perform") parser.add_argument("action", choices=["get_os", "boot_linux", "boot_windows", "swap_os", "reboot", "shutdown", "winupdate"], help="Action to perform")
action_do(parser.parse_args().action) action_do(parser.parse_args().action)
if __name__ == "__main__":
main()