# DNS routing — resolving `<vm>.vm` hostnames from the host

banger's owner daemon runs a local DNS server on `127.0.0.1:42069` that
answers queries under the `.vm` zone. Every VM you create gets a
record:

```
devbox.vm   →  172.16.0.9  (whatever guest IP it was assigned)
```

With that plus host-side DNS routing, you can:

```bash
ssh root@devbox.vm
curl http://devbox.vm:3000
```

from anywhere on the host without copy-pasting guest IPs.

## Supported path

The supported host-side path is:

- `systemd` on the host
- `bangerd.service` running as the owner user
- `bangerd-root.service` running as the privileged host helper
- `systemd-resolved` handling `.vm` routing via `resolvectl`

If you're on a non-`systemd` host or a host without `systemd-resolved`,
the recipes below are best-effort guidance, not the primary supported
deployment model.

## systemd-resolved hosts — nothing to configure

If your host uses `systemd-resolved` (most modern Linux desktops —
Ubuntu ≥18.04, Fedora, Arch with the service enabled), banger
auto-wires it. When the banger services start, the owner daemon asks
the root helper to apply the equivalent of:

```
sudo resolvectl dns      <bridge>  127.0.0.1:42069
sudo resolvectl domain   <bridge>  ~vm
sudo resolvectl default-route <bridge> no
```

against the banger bridge (`br-fc` by default). systemd-resolved
routes only `.vm` lookups to banger's DNS; everything else goes to
your normal upstream. No other changes needed.

Verify: `resolvectl status br-fc` should list `127.0.0.1:42069` under
**Current DNS Server** and `~vm` under **DNS Domain**.

Stopping or uninstalling the services reverts the bridge's
`resolvectl` state on shutdown:

```bash
sudo banger daemon stop
sudo banger system uninstall
```

## Non-systemd-resolved hosts

banger detects `resolvectl`'s absence and skips the auto-wire. You
configure your own resolver. Below are recipes for the common cases.
They can be useful in local experiments, but this is outside banger's
supported host/runtime path.

In every case the goal is the same: **route `.vm` queries to
`127.0.0.1` port `42069`, leave everything else alone**.

### dnsmasq

Add a stanza to your dnsmasq config (e.g.
`/etc/dnsmasq.d/banger-vm.conf`):

```
server=/vm/127.0.0.1#42069
```

Reload dnsmasq (`sudo systemctl reload dnsmasq` or equivalent) and
test:

```
dig devbox.vm
```

### NetworkManager with dnsmasq plugin

Same file as above; NetworkManager picks it up automatically if it's
configured to use the dnsmasq plugin (`dns=dnsmasq` in
`/etc/NetworkManager/NetworkManager.conf`). Restart NetworkManager
after editing.

### Raw `/etc/resolv.conf`

If you edit `resolv.conf` directly, there's no per-domain routing —
you'd have to point ALL DNS through banger, which you probably don't
want. Install `dnsmasq` instead and use the stanza above.

### macOS (if you ever run banger on a Linux VM hosted on macOS)

macOS supports per-TLD resolvers out of the box. Create
`/etc/resolver/vm` (as root):

```
nameserver 127.0.0.1
port 42069
```

No daemon reload needed — `scutil --dns` should list `.vm` under
"Resolver configurations" immediately.

### Windows/WSL

WSL2 inherits the Windows resolver by default and cannot be told to
route `.vm` anywhere. Options:

1. Run banger inside WSL but resolve manually: `ssh root@172.16.0.9`.
2. Set up `dnsmasq` on the WSL distro and point its resolv.conf at
   it; then follow the dnsmasq recipe above.

## Verifying the DNS server

Regardless of host-side routing, you can always query banger's DNS
server directly:

```bash
dig @127.0.0.1 -p 42069 devbox.vm
```

Returns the guest IP if the VM is running. If it returns NXDOMAIN,
the VM either doesn't exist under that name or isn't running yet.

`banger vm list` shows the VM names banger knows about.

## Troubleshooting

- **`resolvectl` errors about "system has not been booted with systemd
  as init system"** — you're probably inside a container or on a
  non-`systemd` host. Manual resolver setup may still work, but that's
  outside the supported path.
- **Port 42069 already in use** — another daemon is bound there
  (previous banger instance not shut down cleanly, or an unrelated
  app). `ss -ulpn | grep 42069` shows who. `sudo banger daemon stop`
  stops both banger services and cleans up banger's own listener.
- **`devbox.vm` resolves but SSH hangs** — DNS is fine; the VM
  might not be up yet or the bridge NAT is misconfigured.
  `banger vm ssh devbox` uses the guest IP directly and bypasses
  DNS — try that to isolate.
- **Changes to `default_dns` don't affect `.vm` resolution** —
  `default_dns` is the upstream the GUEST uses; it's unrelated to
  host-side `.vm` routing.

## Port and bridge tuning

| Setting | Default | Notes |
|---|---|---|
| DNS listen addr | `127.0.0.1:42069` | Not configurable in v1. Edit `internal/vmdns/server.go` if you really need to change it. |
| Bridge name | `br-fc` | Configurable via `bridge_name` in `~/.config/banger/config.toml`. |
| Bridge IP | `172.16.0.1` | Configurable via `bridge_ip`. |
| Resolver route domain | `~vm` | Not configurable. |
