Fix 'Only one usage of each socket address' โ€” Windows Port Already In Use

beginner๐ŸชŸ Windows2026-03-18| Windows 10/11 โ€” Node.js, Python, Java, .NET, or any TCP server application

Error Message

Only one usage of each socket address (protocol/network address/port) is normally permitted
#windows#port#netstat#tcp

You fire up your server and Windows throws:

Only one usage of each socket address (protocol/network address/port) is normally permitted

This is Windows' equivalent of EADDRINUSE on Linux. A TCP port can only be bound by one process at a time โ€” and something else already owns yours. Your app won't start until that port is freed.

Root cause

Three things cause this. Usually it's one of:

  • A previous instance of your app crashed or wasn't shut down cleanly, leaving the port locked
  • A system service (IIS, SQL Server, Apache, Hyper-V virtual switch) grabbed the port at Windows startup
  • Windows itself reserved the port range โ€” this happens after enabling Hyper-V, WSL2, or Docker Desktop

Step 1: Find which process owns the port

Open Command Prompt as Administrator and run:

netstat -ano | findstr :3000

Replace 3000 with your actual port number. Output looks like:

  TCP    0.0.0.0:3000           0.0.0.0:0              LISTENING       12345

The last column is the PID (Process ID). To see the program behind it:

tasklist /FI "PID eq 12345"

Sample output:

Image Name                     PID Session Name        Session#    Mem Usage
========================= ======== ================ =========== ============
node.exe                     12345 Console                    1     52,340 K

Now you know exactly what's holding the port.

Step 2: Kill the process

taskkill /PID 12345 /F

The /F flag forces immediate termination. Getting Access is denied? You need an elevated prompt โ€” right-click the Start menu and choose Windows Terminal (Admin) or Command Prompt (Admin).

PowerShell one-liner

Prefer PowerShell? This finds and kills the process in a single command:

Stop-Process -Id (Get-NetTCPConnection -LocalPort 3000).OwningProcess -Force

Want to preview what you're about to kill before committing:

Get-NetTCPConnection -LocalPort 3000 | Select-Object LocalPort, OwningProcess,
  @{n='ProcessName'; e={(Get-Process -Id $_.OwningProcess).Name}}

Sample output:

LocalPort OwningProcess ProcessName
--------- ------------- -----------
     3000         12345 node

Special case: Windows reserved port ranges

After enabling Hyper-V, WSL2, or Docker Desktop, Windows reserves blocks of dynamic ports at boot. When your port falls inside a reserved block, killing processes won't help โ€” the OS is blocking it at the network stack level.

Check which ports Windows has reserved:

netsh interface ipv4 show excludedportrange protocol=tcp

Spot your port in the output? Switch to a port outside the reserved ranges. Or reset the dynamic port range entirely:

netsh int ipv4 set dynamicport tcp start=49152 num=16384

Restart Windows after changing this. One thing worth knowing: Hyper-V and Docker don't only touch the 49152โ€“65535 range โ€” they can reserve blocks in the 5000โ€“9000 range too. Always verify against the actual netsh output on your machine rather than assuming a port is free.

Step 3: Verify the fix

After killing the process, confirm the port is free:

netstat -ano | findstr :3000

No output means the port is available. Start your server โ€” it should bind without errors this time.

Still seeing a TIME_WAIT entry instead of nothing?

  TCP    0.0.0.0:3000           0.0.0.0:0              TIME_WAIT       0

That's a recently closed connection still draining. Wait 30โ€“60 seconds and retry, or switch to a different port temporarily.

Prevention

If this keeps recurring because your app crashes mid-run without releasing the port:

  • Node.js: Handle SIGTERM/SIGINT explicitly to close the HTTP server before exiting. Running under pm2 also helps โ€” it manages restarts and cleanup automatically.
  • Python: Set SO_REUSEADDR on your socket before calling bind(). Flask's dev server does this by default; Gunicorn handles it correctly in production too.
  • Java / .NET: Add a shutdown hook that calls server.close() โ€” or the framework equivalent โ€” so the port gets released on exit, even on crashes.

Before hardcoding any port in your config, check what's already in use:

netstat -ano | findstr LISTENING

Developer machines often have SQL Server (1433), IIS (80/443), and PostgreSQL (5432) running quietly in the background. Picking a port that's already taken just delays the problem to runtime.

Related Error Notes