2024-10-27 WireGuard Endpoint Watchdog

Task Scheduler

Periodically redo the name resolution of the server address.

Once started a ⎇WireGuard client will never recheck whether the IP behind its endpoint hostname has changes. Unlike IPSec or OpenVPN there is no concept of a session that could timeout either. If the server has an IP change, the client can no longer participate until it gets restarted.

To mitigate this for Windows clients I wrote a PowerShell script that, with the help of the Task Scheduler, does check the endpoint hostname regularly. If the IP differs from what the current running tunnel is using a restart of its service is triggered.
If a tunnel is stopped, either on purpose or by accident, the script will leave it be unless the parameter -AlwaysOnline is used. AlwaysOnline will start a stopped service and even tries to install it if it should be missing.


Download: WireGuard_Endpoint_Watchdog.ps1 Version 1.2 (2026-01-25)
Update from 1.0 to 1.2: Just overwrite the ps1 file. It is encouraged to rerun -InstallTask though.
⍈History


WireGuard_Endpoint_Watchdog.ps1 parameters:

-InstallTask (optional) Installs itself as a task in the Windows Task Scheduler. The default is to rerun every 5 minutes. If you want different times you have to make the edit in the Task Scheduler directly.
IMPORTANT: First copy the ps1 file to C:\Program Files (or whatever) and run it from there! The script will link to itself. So you probably don't want to run it from your downloads folder!

-TunnelName (mandatory) The name of the tunnel you want to check.

-WireGuardInstallPath (optional) Only needed if, for whatever reason, the installation path couldn't be determined automatically.

-EndpointHostname (optional) The hostname is normally read from the tunnel configuration file. In the high likelihood of it being protected/encrypted (filename ending in .dpapi) the script needs to run with SYSTEM privileges. If you don't like the idea you will have to set this parameter.

-DNSServer (optional) If a specific DNS-Server should be used.

-LogFile (optional) Path to a text log file. Highly encouraged to be used. Directly repeating messages will only be logged once.

-AlwaysOnline (optional) Reinstates a stopped or removed tunnel service. Highly encouraged in server settings. (No logged in user necessary. Things come back after a reboot.)

-UninstallTask (optional) Removes a task from the Windows Task Scheduler.


Examples:

./WireGuard_Endpoint_Watchdog.ps1 -InstallTask -TunnelName Office

./WireGuard_Endpoint_Watchdog.ps1 -InstallTask -TunnelName Essential -AlwaysOnline -LogFile C:\foo\bar.txt

./WireGuard_Endpoint_Watchdog.ps1 -InstallTask -TunnelName Business -EndpointHostname dyndns.example.com -DNSServer 198.51.100.9 -LogFile C:\foo\bar.txt

./WireGuard_Endpoint_Watchdog.ps1 -UninstallTask -TunnelName Office


Return codes:

100, 120 Couldn't find the WireGuard installation path. Start the WireGuard GUI or provide the path via the -WireGuardPath argument.

101 Couldn't find C:\Program Files\WireGuard\wg.exe at WireGuardPath C:\Program Files\WireGuard

102 The User XYZ has insufficient rights to check the WireGuard-Tunnel FooBar.

103 The WireGuard-Tunnel FooBar has no Endpoint-Information. Not a client configuration.

104 There are two possible configuration files. C:\Program Files\WireGuard\Data\Configurations\FooBar.conf and C:\Program Files\WireGuard\Data\Configurations\FooBar.conf.dpapi. Unclear which is the correct one. Please remove one.

105 Unable to read the configuration file C:\Program Files\WireGuard\Data\Configurations\FooBar.conf. Please check that XYZ has access rights.

106 Unable to read the protected configuration file C:\Program Files\WireGuard\Data\Configurations\FooBar.conf.dpapi. (As user: XYZ) Usually only SYSTEM has the necessary access.

107 The configuration file is empty. Unable to determine an endpoint.

108 The configured endpoint 198.51.100.1 is not a hostname but an IP.

109 No endpoint found. Not a client configuration.

110 DNS-Resolve-Error: dyndns.example.com : Timeout

111 Unknown DNS-Resolve-Error. dyndns.example.com wasn't resolved.

112 Couldn't find C:\Program Files\WireGuard\wireguard.exe at WireGuardPath C:\Program Files\WireGuard

113 No configuration files for WireGuard Tunnel FooBar found. Check its installation! Make sure to have elevated rights.

114 Error while trying to install service "WireGuard Tunnel: FooBar". Check its installation!

115 No running WireGuard-Tunnel with the name FooBar found. Check its installation!

116 Task "WireGuard FooBar Watchdog" already exists.

117 Encountered an unknown error while trying to install a scheduled task.

118 No Task "WireGuard FooBar Watchdog" to delete found. Make sure to have elevated rights.

119 Encountered an unknown error while trying to remove a scheduled task.

200 No running WireGuard-Tunnel with the name FooBar found. Noting to do.

201 Task "WireGuard FooBar Watchdog" successfully removed.

1 The IP behind dyndns.example.com has changed to 198.51.100.2. Restarting WireGuard tunnel FooBar.

0 Uncanged IP 198.51.100.2. Nothing to do.
Exit Code 0 will only be logged with a singel dot (withouth a line break) to the LogFile.


FAQ:

Q: If I open PowerShell and enter ./WireGuard_Endpoint_Watchdog.ps1 I get:
Cannot be loaded because the execution of scripts is disabled on this system.
A: powershell -ExecutionPolicy Bypass -File ./WireGuard_Endpoint_Watchdog.ps1

Q: Doesn't the WireGuard homepage talk about
⎇"there is full IP roaming on both ends"?
A: Yes it says that. But in my experience it doesn't work. Even with short Keepalive settings on both ends. My WireGuard servers were all behind a port-forwarding router. So it doesn't know its public IP. Maybe that is a factor too. And thinking from the clients perspective, why should its firewall let a packet from a "random" IP through?


History:

Version 1.0 (2024-10-27)
Initial release.

Version 1.2 (2026-01-25)
- Code restructured for a more robust logic.
- Directly repeating messages will only be logged once.
- Always adds -WireGuardInstallPath to a task.
- Introduction of the AlwaysOnline parameter.

This version introduces no breaking changes, even though in retrospect the AlwaysOnline behavior should have been the default from the start. I'm sure most users, like myself, use this script in a server environment. I had misconceptions about the WireGuard Windows services that only cleared recently.

You can just copy the the new file over the old. Even if you don't want to add the -AlwaysOnline parameter I still encourage you to rerun -InstallTask. (Run -UninstallTask first.) Which will now always add a -WireGuardInstallPath parameter. Because, as it did turn out, the path can not always be determined at runtime.


Linux alternative:
⎇https://blog.netways.de/blog/2022/01/06/wireguard-mit-dynamischen-dns-namen/

⍈Homepage

#