Skip to content

Instantly share code, notes, and snippets.

@ahhh
Created February 15, 2026 02:04
Show Gist options
  • Select an option

  • Save ahhh/fbc20c56620288134ceba9086ce20257 to your computer and use it in GitHub Desktop.

Select an option

Save ahhh/fbc20c56620288134ceba9086ce20257 to your computer and use it in GitHub Desktop.
quick and dirty powershell script to loop over netstat connections and tie them to a process w/ a little supporting info. Added a good bit of caching and state comparison to get htop-like display
$seen = @{}
$dnsCache = @{}
$geoCache = @{}
function Resolve-Name($ip) {
if ($dnsCache.ContainsKey($ip)) {
return $dnsCache[$ip]
}
try {
$name = (Resolve-DnsName $ip -ErrorAction Stop).NameHost
} catch {
$name = $ip
}
$dnsCache[$ip] = $name
return $name
}
function Get-Geo($ip) {
if ($geoCache.ContainsKey($ip)) { return $geoCache[$ip] }
try {
$r = Invoke-RestMethod "http://ip-api.com/json/$ip" -TimeoutSec 3
$info = [PSCustomObject]@{
country = $r.countryCode
region = $r.regionName
city = $r.city
isp = $r.isp
}
} catch {
$info = [PSCustomObject]@{
country = "?"
region = "?"
city = "?"
isp = "?"
}
}
$geoCache[$ip] = $info
return $info
}
while ($true) {
# Get connections
$connections = netstat -ano | Select-String ESTABLISHED
# Build fingerprint snapshot for display refresh
$currentKeys = @()
foreach ($line in $connections) {
$parts = ($line -replace "\s+", " ").Trim().Split(" ")
$remote = $parts[2]
$procId = $parts[-1]
if ($remote -match "127\.0\.0\.1|::1") { continue }
$ip = $remote.Split(":")[0]
$currentKeys += "$ip-$procId"
}
$currentSnapshot = ($currentKeys | Sort-Object) -join "`n"
if ($currentSnapshot -eq $lastSnapshot) {
Start-Sleep 0.3
continue
}
$lastSnapshot = $currentSnapshot
Clear-Host
Write-Host "External connections"
Write-Host "==================================="
# Loop and display connections
foreach ($line in $connections) {
$parts = ($line -replace "\s+", " ").Trim().Split(" ")
$remote = $parts[2]
$procId = $parts[-1]
if ($remote -match "127\.0\.0\.1|::1") { continue }
$ip = $remote.Split(":")[0]
$proc = (Get-Process -Id $procId -ErrorAction SilentlyContinue).ProcessName
if ($procId -eq $PID) { continue }
if (!$proc) { $proc = "?" }
$name = Resolve-Name $ip
$geo = Get-Geo $ip
$key = "$ip-$procId"
if (-not $seen.ContainsKey($key)) {
Write-Host "NEW: $proc -> $name [$ip] $($geo.country) $($geo.region) $($geo.city) $($geo.isp)" -ForegroundColor Yellow
$seen[$key] = $true
}
else {
Write-Host "$proc -> $name [$ip] $($geo.country) $($geo.region) $($geo.city) $($geo.isp)"
}
}
Start-Sleep 0.3
}
REM inspiration behind watcher script
@echo off
:loop
cls
echo Established connections (refresh every 2 seconds)
echo =================================================
netstat -ano | findstr /v "127.0.0.1 ::1" | find "ESTABLISHED"
timeout /t 2 /nobreak >nul
goto loop
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment