Back to problems

problem hub

Read-only first

Port already in use on Linux

Find the listener, process, bind address, and firewall context before killing or restarting anything.

Safest first command

ss -ltnp

Before you run this

Expected output: Listening TCP sockets with local address, port, and process information when permissions allow it.

When not to use it: Do not kill a process just because it owns a port. It may be the intended service, a database, or a supervisor-managed worker.

Expected output example

LISTEN 0 4096 0.0.0.0:3000 0.0.0.0:* users:(("node",pid=4242,fd=23))

How to read the result

The local address shows whether the service is local-only or public. The process field identifies the owner when permissions allow; use sudo if process details are hidden.

What to check next

The listener is bound to 127.0.0.1

Means: The service is local-only and may need a proxy or config check, not firewall changes.

Next step: Inspect listening addresses and the intended exposure before changing config.

Show Publicly Bound Listeners

The listener process is hidden or missing

Means: Permissions may hide process details from a non-root shell.

Next step: Run a scoped listener inspection with elevated permissions.

Check What Is Actually Listening

Docker owns the host port

Means: A container publish rule may be conflicting with the host service.

Next step: Map container port bindings before stopping containers or changing host services.

Show Published Container Ports

Port conflict decision tree

Start by proving whether anything is listening on the exact port and address. If the process column is hidden, rerun the same inspection with sudo. If the listener is on 127.0.0.1, treat it as local-only exposure before changing firewalls. If Docker owns the port, map published container ports before stopping host services. If systemd owns or restarts the process, inspect the unit before killing the PID.

  1. ss -ltnp 'sport = :80'
  2. sudo lsof -nP -iTCP:80 -sTCP:LISTEN
  3. systemctl status nginx --no-pager --lines=30
  4. docker ps --format 'table {{.Names}}\t{{.Ports}}'

Check service and config context

Once the owner is known, inspect why it is bound there. For Nginx or Apache, list listen directives and validate config. For a dev server, confirm whether it was launched from a shell, package manager, or supervisor. For a database or queue, check whether the new service is trying to use the wrong port.

  1. grep -RInE 'listen +80|listen +443' /etc/nginx /etc/apache2 2>/dev/null
  2. sudo nginx -t
  3. ps -fp 4242
  4. systemctl status docker --no-pager --lines=30

Owner before kill branch

Find whether the listener is owned by systemd, Docker, a process manager, or a user shell before stopping anything. LISTEN rows explain bind conflicts; ESTABLISHED rows are client sessions.

  1. ss -ltnp
  2. sudo ss -ltnp
  3. ps -fp 1234
  4. systemctl status nginx --no-pager --lines=30

Bad fixes to avoid

Do not kill the PID until you know whether systemd, Docker, a process manager, or a login shell owns it. Do not move a production service to a random open port without updating proxies, health checks, and firewall rules. Do not open firewall ports when the failure is a bind conflict on the host.

Common causes

  • Old dev server still running
  • Nginx/Apache already bound to 80 or 443
  • Docker published the same host port
  • Service configured to bind the wrong address
  • Supervisor restarted the process after it was killed

What not to change yet

  • Do not kill a PID until you know what service owns it.
  • Do not change firewall rules before proving the process is listening.
  • Do not bind a second service to a production port without checking config.

Stop and escalate if

  • The listener belongs to an unknown service or a process serving production traffic.
  • Killing the process could drop active users, jobs, or long-running writes.
  • Firewall or bind-address changes could cut off remote access.

platform notes

Distro and service notes

sudo

Process names may be hidden without elevated permissions.

Docker

docker ps and port mappings can explain listeners that do not look like normal host services.

macOS

Use the Apple Terminal lsof pages for local dev ports.

supporting commands

Command path

Guides and drills