PortWho documentation · CLI

JSON output

The schema version 1 contract of portwho --json, the full document shape, every field with its type and meaning, the exact enumerations, the stability promise and a PowerShell example that filters the result.

Product
PortWho
Section
CLI
Page
4 of 7

portwho --json (or -j) writes one JSON document to standard output instead of text. It combines with every filter and always wins over the table and details views, so portwho 8080 --json is a JSON answer for port 8080.

The contract

  • The document carries "schemaVersion": 1.
  • Field names and the spellings of protocol, addressFamily, process.status and signature.status are a contract. Incompatible changes bump schemaVersion; check it before reading anything else.
  • The document is always written, even when nothing matched: you then get "endpointCount": 0, an empty endpoints array and exit code 1.
  • Properties are camelCase, the output is indented, and absent values are written as null rather than omitted, so every field below is always present.
  • Endpoints are sorted by port, then protocol (TCP before UDP), then address family (IPv4 before IPv6), then address, then process id.

Document shape

{
  "schemaVersion": 1,
  "generatedAt": "2026-10-08T12:00:00+00:00",
  "endpointCount": 1,
  "endpoints": [
    {
      "protocol": "tcp",
      "addressFamily": "ipv4",
      "localAddress": "0.0.0.0",
      "localPort": 135,
      "processId": 1116,
      "process": {
        "status": "resolved",
        "name": "svchost",
        "executablePath": "C:\\Windows\\System32\\svchost.exe",
        "services": [
          { "name": "RpcEptMapper", "displayName": "RPC Endpoint Mapper" },
          { "name": "RpcSs", "displayName": "Remote Procedure Call (RPC)" }
        ],
        "signature": {
          "status": "signed",
          "signer": "Microsoft Windows",
          "organization": "Microsoft Corporation",
          "issuer": "Microsoft Windows Production PCA 2011",
          "detail": null
        },
        "detail": null
      }
    }
  ]
}

Fields

Top level

Field Type Meaning
schemaVersion integer Always 1 for this contract.
generatedAt string When the run happened: an ISO 8601 timestamp in UTC, with offset.
endpointCount integer Number of entries in endpoints.
endpoints array One entry per endpoint, exactly as Windows reports them. Two UDP sockets sharing an address and port through SO_REUSEADDR appear twice.

Endpoint

Field Type Meaning
protocol string tcp (listening socket) or udp (bound socket).
addressFamily string ipv4 or ipv6.
localAddress string The bound local address, without brackets for IPv6.
localPort integer The local port, 0–65535.
processId integer Owning process id as reported by Windows.
process object What PortWho knows about the owning process.

Process

Field Type Meaning
status string How far the lookup got; see the enumeration below.
name string or null Process name without extension (as Get-Process shows it). May be known even when status is accessDenied.
executablePath string or null Full path of the executable image, when the process could be opened.
services array Windows services hosted by the process; empty when none or unknown.
signature object Authenticode verdict for the executable image.
detail string or null Human-readable explanation of a partial or failed lookup.

Service

Field Type Meaning
name string Service key name, as used by sc and Get-Service -Name.
displayName string Human-readable service name.

Signature

Field Type Meaning
status string Verification outcome; see the enumeration below.
signer string or null Common name of the signing certificate’s subject, as Windows shows it under “Name of signer”.
organization string or null Organization (O=) of the signing certificate’s subject; often more recognizable than signer.
issuer string or null Common name of the certificate issuer.
detail string or null Extra explanation, typically the Windows error text and code for a failed verification or an unreadable file.

For a catalog-signed file, signer, organization and issuer describe the catalog’s signer.

Enumerations

process.status:

Value Meaning
resolved The process was opened and its image path read.
accessDenied Windows refused to open the process; usually a protected or higher-privileged process. name may still be known.
notFound The process no longer exists; it exited between the endpoint snapshot and the lookup.
system A kernel-owned pseudo process (PID 0 or 4) with no user-mode executable. services is empty and the signature is notChecked.
failed The lookup failed for another reason; see detail.

signature.status:

Value Meaning
notChecked No check was attempted: --no-signature was given, or no executable path was available.
signed The file carries a valid embedded Authenticode signature.
catalogSigned The file is unsigned itself but is listed in a valid Windows security catalog.
unsigned No embedded signature and no catalog entry were found.
invalid A signature or catalog entry exists but failed verification (bad digest, untrusted chain, expired, and so on).
unavailable The file could not be read, so no verdict is possible.

All values are lowercase literals exactly as spelled here.

Stability promise

Within schema version 1, field names and enumeration spellings do not change. Any incompatible change ships with a new schemaVersion, so treat an unknown version as “stop and update the consumer” rather than guessing.

PowerShell example

ConvertFrom-Json turns the document into objects you can filter and project:

$report = portwho --json | ConvertFrom-Json

if ($report.schemaVersion -ne 1) {
    throw "Unexpected PortWho schema version $($report.schemaVersion)."
}

# Listeners that are not signed by a verified publisher
$report.endpoints |
    Where-Object { $_.process.signature.status -in 'unsigned', 'invalid', 'unavailable' } |
    Select-Object protocol, localAddress, localPort, processId,
        @{ Name = 'process'; Expression = { $_.process.name } },
        @{ Name = 'services'; Expression = { $_.process.services.name -join ', ' } } |
    Format-Table

Remember that the exit code is 1 when nothing matched even though a valid document was written; check $LASTEXITCODE if your script treats “no owner” differently from “owner found”.