SPDX-License-Identifier: GPL-3.0-only
This project provides a custom mDNS responder/announcer for Windows using PowerShell.
It publishes custom .local hostnames from a text file and responds to mDNS queries over UDP 5353, including:
- A (IPv4) records
- AAAA (IPv6) records when a usable IPv6 is available
- Unicast responses when requested by the mDNS QU bit
- Multicast periodic announcements
- Loads aliases from a file (ignores empty lines and comments beginning with
#) - Normalizes names to
.local - Auto-detects the primary local IPv4 interface and pins multicast traffic to it
- Optional IPv6 support for AAAA answers, including IPv6 mDNS transport on the same interface
- Verbose query/response diagnostics (
-Verbose) - Optional transcript logging (
-LogToFile) - Startup network profile self-check (warns for Public profile)
- Windows PowerShell 5.1+ (or PowerShell 7+ on Windows)
- Administrative rights recommended (binding/inspection/firewall/task setup)
- Local network allows mDNS multicast (
224.0.0.251:5353)
mdns_alias_announce.ps1: main scriptaliases.txt: alias input file (you can also pass a custom path with-FilePath)
Example aliases.txt:
# Comments are allowed
TestBox
WIN-ANY-NAME.domain.local
domain.local
Notes:
TestBoxbecomesTestBox.local- Name matching is case-insensitive
Basic run:
powershell -ExecutionPolicy Bypass -File C:\programdata\mdns_alias_announce\mdns_alias_announce.ps1 -FilePath C:\programdata\mdns_alias_announce\aliases.txtWith verbose and logging:
powershell -ExecutionPolicy Bypass -File C:\programdata\mdns_alias_announce\mdns_alias_announce.ps1 -FilePath C:\programdata\mdns_alias_announce\aliases.txt -Verbose -LogToFile -LogFilePath C:\programdata\mdns_alias_announce\mdns_alias_announce.log-FilePath <string>: alias input file path-IntervalSeconds <int>: periodic announcement interval in seconds (range:1..86400, default:30)-LogToFile: enable transcript logging-LogFilePath <string>: transcript destination path (default:mdns_alias_announce.lognext to script)
Run in an elevated PowerShell session:
# Inbound mDNS to local UDP 5353
New-NetFirewallRule `
-DisplayName "mDNS Alias Responder Inbound UDP 5353" `
-Direction Inbound `
-Action Allow `
-Protocol UDP `
-LocalPort 5353 `
-Profile Private,Domain `
-RemoteAddress LocalSubnet
# Outbound mDNS multicast to UDP 5353
New-NetFirewallRule `
-DisplayName "mDNS Alias Responder Outbound UDP 5353" `
-Direction Outbound `
-Action Allow `
-Protocol UDP `
-RemotePort 5353 `
-Profile Private,Domain `
-RemoteAddress 224.0.0.251Verify rules:
Get-NetFirewallRule -DisplayName "mDNS Alias Responder *" | Format-Table -Auto Name, DisplayName, Enabled, Direction, ActionRemove rules:
Remove-NetFirewallRule -DisplayName "mDNS Alias Responder Inbound UDP 5353"
Remove-NetFirewallRule -DisplayName "mDNS Alias Responder Outbound UDP 5353"Run in an elevated PowerShell session:
$ScriptPath = "C:\programdata\mdns_alias_announce\mdns_alias_announce.ps1"
$AliasFile = "C:\programdata\mdns_alias_announce\aliases.txt"
$LogFile = "C:\programdata\mdns_alias_announce\mdns_alias_announce.log"
$Action = New-ScheduledTaskAction `
-Execute "powershell.exe" `
-Argument "-NoProfile -ExecutionPolicy Bypass -File `"$ScriptPath`" -FilePath `"$AliasFile`" -IntervalSeconds 30 -LogToFile -LogFilePath `"$LogFile`""
$Trigger = New-ScheduledTaskTrigger -AtStartup
$Principal = New-ScheduledTaskPrincipal `
-UserId "SYSTEM" `
-LogonType ServiceAccount `
-RunLevel Highest
$Settings = New-ScheduledTaskSettingsSet `
-StartWhenAvailable `
-RestartCount 999 `
-RestartInterval (New-TimeSpan -Minutes 1)
Register-ScheduledTask `
-TaskName "mDNS Alias Announcer" `
-Action $Action `
-Trigger $Trigger `
-Principal $Principal `
-Settings $Settings `
-Description "Starts custom PowerShell mDNS alias responder at boot"Start now without reboot:
Start-ScheduledTask -TaskName "mDNS Alias Announcer"Check status:
Get-ScheduledTask -TaskName "mDNS Alias Announcer" | Get-ScheduledTaskInfoUpdate task (replace existing):
Unregister-ScheduledTask -TaskName "mDNS Alias Announcer" -Confirm:$false
# Then run the Register-ScheduledTask block againUse this quick checklist after install or reboot:
- Confirm
aliases.txtexists and contains at least one alias. - Confirm UDP 5353 firewall rules are present for the network profile in use.
- Confirm the host is on a trusted LAN segment (same L2 domain / VLAN as clients).
- Start the script or scheduled task and watch startup output for selected interface/IP.
- Run one client-side lookup test (A/AAAA) before considering setup complete.
Quick checks on Windows:
Get-Content C:\programdata\mdns_alias_announce\aliases.txt
Get-NetFirewallRule -DisplayName "mDNS Alias Responder *"
Get-ScheduledTask -TaskName "mDNS Alias Announcer" | Get-ScheduledTaskInfo- This script is focused on host A/AAAA answers only (no PTR/SRV/TXT service discovery records).
- IPv6 transport requires usable IPv6 on the selected interface; link-local-only (
fe80::/10) addresses are ignored. - Multi-homed hosts can still have edge cases if the default route does not match the LAN where clients query.
- This implementation does not perform mDNS conflict probing/defense logic before announcing names.
- Network equipment with client isolation, strict multicast filtering, or cross-VLAN boundaries may block discovery.
Use this sequence to validate behavior end-to-end.
- Start responder with verbose logging:
powershell -ExecutionPolicy Bypass -File C:\programdata\mdns_alias_announce\mdns_alias_announce.ps1 -FilePath C:\programdata\mdns_alias_announce\aliases.txt -Verbose- Query from a client (macOS example):
dns-sd -G v4v6 testbox.local- Capture multicast traffic if results are inconsistent:
sudo tcpdump -ni en0 udp port 5353Expected result:
- Verbose logs show
match=Truefor the queried name. - Client receives A response (and AAAA when usable IPv6 is configured).
- Script runs, but macOS cannot resolve names:
- Confirm firewall rules exist for UDP 5353
- Ensure both devices are in the same L2 broadcast domain / VLAN
- Verify no AP/client isolation is enabled on Wi-Fi
- Verbose logs show queries but
match=False:
- Check alias spelling in
aliases.txt - Ensure queried name exists as
.local
- Only AAAA queries seen from client:
- Script will answer AAAA only when a usable non-link-local IPv6 exists on selected interface
- Otherwise it still answers A queries when requested
- Confirm mDNS traffic on macOS:
dns-sd -G v4v6 testbox.local
sudo tcpdump -ni en0 udp port 5353See LICENSE.