WSL Configuration
WSL (Windows Subsystem for Linux) configuration tasks: SSH access, networking modes, firewall rules, and calling Windows tools from the Linux side.
Trigger conditions
Load this skill when the user:
- Wants SSH access into their WSL from another device
- Asks about WSL networking (IP, port forwarding, mirrored mode)
- Runs PowerShell commands from WSL and they fail mysteriously
- Needs to expose a WSL service to the LAN
- Needs Docker in WSL but
dockercommand is missing (Docker Desktop is installed on Windows side)
Docker Desktop integration (WSL)
Docker Desktop installed on Windows but not reachable from WSL. The docker CLI is missing in WSL's PATH even though docker.exe works from PowerShell.
Detection
# Docker CLI missing in WSL
which docker # → not found
# But docker.exe IS reachable via WSL interop
which docker.exe # → /mnt/c/Program Files/Docker/Docker/resources/bin/docker.exe
docker.exe --version # → Docker version 28.x.x
Fix
# 1. Symlink docker.exe → docker in WSL PATH
ln -sf "/mnt/c/Program Files/Docker/Docker/resources/bin/docker.exe" ~/.local/bin/docker
# 2. Verify
which docker && docker --version
Starting Docker Desktop from WSL
If Docker Desktop isn't running:
# Start it
"/mnt/c/Program Files/Docker/Docker/Docker Desktop.exe" &
# Wait for the daemon to be ready (up to 30s)
for i in $(seq 1 30); do
docker ps >/dev/null 2>&1 && echo "Docker is ready!" && break
sleep 1
done
Pitfalls
shutil.which("docker")won't finddocker.exe. Python'sshutil.which()and shellwhich dockerlook for an executable named exactlydocker— they don't try.exeextensions. The symlink is required for tools that probe fordockerby name (Strix, Docker SDKs, CI scripts).Some CLIs hang without Docker. Strix's
main()callscheck_docker_installed()before argument parsing, so even--helphangs if Docker isn't available. Always resolve Docker availability first.Docker Desktop must be running for the daemon. The
dockerCLI is useless without the daemon. Starting Docker Desktop via the.exefrom WSL works — the GUI window will appear on the Windows desktop and the daemon becomes available in ~10-20 seconds.
SSH access into WSL (from phone, other machines)
Goal: SSH into WSL as if it were a normal Linux box on the LAN.
1. Install & configure SSH server
sudo apt install openssh-server -y
sudo systemctl enable ssh --now
Verify: sudo systemctl status ssh — should show "Server listening on 0.0.0.0 port 22."
Default config allows password auth out of the box on Ubuntu. Confirm the user has a password set: sudo passwd -S <user> — status "P" means password is set.
2. Enable mirrored networking
WSL2 by default uses NAT (internal IP like 172.x.x.x) — unreachable from LAN. Mirrored mode makes WSL share the Windows host IP.
Write to C:\Users\<user>\.wslconfig:
[wsl2]
networkingMode=mirrored
This requires a WSL restart to take effect: from PowerShell/CMD, run wsl --shutdown, then reopen WSL.
3. Open Windows Firewall
Windows Firewall blocks incoming SSH by default. From an admin PowerShell:
New-NetFirewallRule -DisplayName "WSL SSH" -Direction Inbound -Protocol TCP -LocalPort 22 -Action Allow -Profile Private
4. Get the Windows LAN IP
ipconfig.exe | grep -B1 -A3 'Wi-Fi'
Look for the Wi-Fi adapter's IPv4 (e.g., 192.168.1.78).
5. Connect
From phone/remote: ssh <user>@<windows-lan-ip> with the WSL user's password.
Pitfall: PowerShell $_ gets eaten by bash
When calling powershell.exe from WSL bash, the PowerShell pipeline variable $_ gets expanded by bash as a shell variable (to empty string), silently breaking Where-Object and ForEach-Object blocks.
Symptom: PowerShell errors like '/mnt/c/Users/Lenovo.PropertyName' is not recognized — bash expanded $_.PropertyName to /mnt/c/Users/Lenovo.PropertyName.
Fix: Use ipconfig.exe directly instead of PowerShell for network info:
# Works — no $ escaping
ipconfig.exe | grep 'Wi-Fi'
# Avoid — $_ gets bash-expanded silently
powershell.exe -Command "Get-NetIPAddress | Where-Object { $_.InterfaceAlias -match 'Wi-Fi' }"
For non-avoidable PowerShell, escape the $:
powershell.exe -Command "Get-NetIPAddress | Where-Object { \$_.InterfaceAlias -match 'Wi-Fi' }"
Pitfall: Firewall rules need admin
New-NetFirewallRule and netsh advfirewall both require elevated PowerShell. Non-admin calls fail with "Access is denied." The user must run these manually.