Skip to content

Commit 93d0f4b

Browse files
committed
Configurable limits, PS logging checks, report suppressed count (v0.4.8)
- Add BackdoorPorts, KnownDNSServers, AbuseIPDBMaxChecks, MaxVTLookups config fields; use TrustedPorts for commonPorts in Check-Network.ps1 - Add Module Logging and Transcription detection in Check-DefenseEvasion - Show suppressed finding count in HTML report stats grid - Document new config fields in README Made-with: Cursor
1 parent ce364b7 commit 93d0f4b

9 files changed

Lines changed: 72 additions & 16 deletions

File tree

AmIHacked.ps1

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -80,7 +80,7 @@ if ($script:NonInteractive) {
8080
$script:RedactMap = @{}
8181
$script:SuppressedCount = 0
8282

83-
$script:Version = "0.4.7"
83+
$script:Version = "0.4.8"
8484

8585
# ── Helpers (loaded first) ───────────────────────────────────────────────────
8686

@@ -284,7 +284,8 @@ Generate-HtmlReport -Findings $script:Findings `
284284
-SystemInfo $script:SystemInfo `
285285
-OutputFile $reportFile `
286286
-Duration $duration `
287-
-Version $script:Version
287+
-Version $script:Version `
288+
-SuppressedCount $script:SuppressedCount
288289

289290
Write-SectionEnd
290291

CHANGELOG.md

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,14 @@ All notable changes to this project will be documented in this file.
44

55
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.1.0/).
66

7+
## [0.4.8] - 2026-03-15
8+
9+
### Added
10+
- **Configurable network/API limits** -- `BackdoorPorts`, `KnownDNSServers`, `AbuseIPDBMaxChecks`, `MaxVTLookups` config fields with sensible defaults; `commonPorts` in Check-Network.ps1 now uses `TrustedPorts` from config
11+
- **Module Logging detection** -- Check-DefenseEvasion.ps1 flags when PowerShell Module Logging is not enabled (INFO, T1562.002)
12+
- **Transcription detection** -- Check-DefenseEvasion.ps1 flags when PowerShell Transcription is not enabled (INFO, T1562.002)
13+
- **Report suppressed count** -- HTML report stats grid shows a "Suppressed" card when findings have been suppressed via config
14+
715
## [0.4.7] - 2026-03-15
816

917
### Added

README.md

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,7 @@
1212
[![PowerShell 5.1+](https://img.shields.io/badge/PowerShell-5.1%2B-0d1117?style=for-the-badge&logo=powershell&logoColor=5391FE)](https://docs.microsoft.com/powershell/)
1313
[![Windows 10/11](https://img.shields.io/badge/Windows-10%20%2F%2011-0d1117?style=for-the-badge&logo=windows&logoColor=white)](https://www.microsoft.com/windows)
1414
[![License: MIT](https://img.shields.io/badge/License-MIT-0d1117?style=for-the-badge&logoColor=white)](LICENSE)
15-
[![Version](https://img.shields.io/badge/Version-0.4.7-FF6B6B?style=for-the-badge)](#changelog)
15+
[![Version](https://img.shields.io/badge/Version-0.4.8-FF6B6B?style=for-the-badge)](#changelog)
1616

1717
[![Zero Dependencies](https://img.shields.io/badge/Dependencies-Zero-0d1117?style=flat-square&labelColor=0d1117)](#)
1818
[![MITRE ATT&CK](https://img.shields.io/badge/MITRE%20ATT%26CK-40%2B%20Techniques-ff3333?style=flat-square&labelColor=0d1117)](#mitre-attck-coverage)
@@ -140,7 +140,7 @@ Baselines enable **change detection** — the most powerful signal for catching
140140

141141
```
142142
---AMIHACKED-SUMMARY-JSON---
143-
{"verdict":"CAUTION","critical":0,"warning":3,"info":12,"suppressed":0,"total":15,"duration":28.4,"reportPath":"...","version":"0.4.7"}
143+
{"verdict":"CAUTION","critical":0,"warning":3,"info":12,"suppressed":0,"total":15,"duration":28.4,"reportPath":"...","version":"0.4.8"}
144144
```
145145

146146
- Exit code reflects findings: **0** = clean, **1** = warnings only, **2** = critical findings detected
@@ -242,6 +242,10 @@ Then edit `config/config.json` (gitignored — API keys stay local):
242242
| `SuspiciousTempExtensions` | `string[]` | Extensions flagged in temp directories |
243243
| `TrustedAppDirs` | `string[]` | App directory names to skip during temp-dir scanning |
244244
| `Suppressions` | `object[]` | Findings to silence permanently. Each entry has a `pattern` (wildcard, matched against Title) and optional `reason` |
245+
| `BackdoorPorts` | `int[]` | Ports that trigger CRITICAL instead of WARNING on listeners |
246+
| `KnownDNSServers` | `string[]` | DNS servers considered legitimate (Google, Cloudflare, etc.) |
247+
| `AbuseIPDBMaxChecks` | `int` | Max IPs to check against AbuseIPDB per scan (default: 30) |
248+
| `MaxVTLookups` | `int` | Max file hashes to check against VirusTotal per scan (default: 4) |
245249
| `AccountMaxAgeDays` | `int` | Flag accounts created within N days |
246250
| `FileSystemMaxAgeDays` | `int` | Flag recently modified system executables |
247251
| `MaxEventLogEntries` | `int` | Max events to scan per log |

config/config.example.json

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -74,6 +74,10 @@
7474
".cloudfront.net", ".slack-msgs.com", ".googleapis.com",
7575
".gstatic.com", ".steamcontent.com"
7676
],
77+
"BackdoorPorts": [4444, 5555, 6666, 1234, 31337, 12345, 54321, 9999, 1337],
78+
"KnownDNSServers": ["8.8.8.8","8.8.4.4","1.1.1.1","1.0.0.1","9.9.9.9","149.112.112.112","208.67.222.222","208.67.220.220","76.76.2.0","76.76.10.0"],
79+
"AbuseIPDBMaxChecks": 30,
80+
"MaxVTLookups": 4,
7781
"Suppressions": [
7882
{ "pattern": "New Listening Port: 6463", "reason": "Discord RPC — expected on this machine" },
7983
{ "pattern": "Unquoted Service Path*", "reason": "Vendor bug, not exploitable — no write access to intermediate paths" }

lib/Helpers.ps1

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -292,6 +292,20 @@ function Get-DefaultConfig {
292292
".gstatic.com", ".steamcontent.com"
293293
)
294294

295+
BackdoorPorts = @(4444, 5555, 6666, 1234, 31337, 12345, 54321, 9999, 1337)
296+
297+
KnownDNSServers = @(
298+
"8.8.8.8", "8.8.4.4",
299+
"1.1.1.1", "1.0.0.1",
300+
"9.9.9.9", "149.112.112.112",
301+
"208.67.222.222", "208.67.220.220",
302+
"76.76.2.0", "76.76.10.0"
303+
)
304+
305+
AbuseIPDBMaxChecks = 30
306+
307+
MaxVTLookups = 4
308+
295309
Suppressions = @()
296310
}
297311
}

lib/ReportGenerator.ps1

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,8 @@ function Generate-HtmlReport {
99
[hashtable]$SystemInfo,
1010
[string]$OutputFile,
1111
[timespan]$Duration,
12-
[string]$Version
12+
[string]$Version,
13+
[int]$SuppressedCount = 0
1314
)
1415

1516
$critCount = ($Findings | Where-Object { $_.Severity -eq "CRITICAL" }).Count
@@ -385,6 +386,7 @@ function Generate-HtmlReport {
385386
.stat-warning .stat-value { color: var(--warning); }
386387
.stat-info .stat-value { color: var(--info); }
387388
.stat-total .stat-value { color: var(--text-primary); }
389+
.stat-suppressed .stat-value { color: var(--text-secondary); }
388390
389391
/* -- System Info -- */
390392
.system-info {
@@ -731,6 +733,7 @@ function Generate-HtmlReport {
731733
<div class="stat-value">${totalCount}</div>
732734
<div class="stat-label">Total Findings</div>
733735
</div>
736+
$(if ($SuppressedCount -gt 0) { "<div class=`"stat-card stat-suppressed`"><div class=`"stat-value`">$SuppressedCount</div><div class=`"stat-label`">Suppressed</div></div>" })
734737
</div>
735738
736739
<div class="system-info">

modules/Check-DefenseEvasion.ps1

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -121,6 +121,34 @@ function Invoke-DefenseEvasionChecks {
121121
Write-Verbose "Could not check ScriptBlockLogging policy: $_"
122122
}
123123

124+
try {
125+
$ml = Get-ItemProperty "HKLM:\SOFTWARE\Policies\Microsoft\Windows\PowerShell\ModuleLogging" -ErrorAction SilentlyContinue
126+
if (-not $ml -or -not $ml.EnableModuleLogging -or $ml.EnableModuleLogging -eq 0) {
127+
Add-Finding -Severity "INFO" -Category "DefenseEvasion" `
128+
-Title "PowerShell Module Logging Not Enabled" `
129+
-Description "Module logging is not enabled via policy. When enabled, PowerShell logs pipeline execution details to the event log (Event ID 4103), helping detect malicious module usage." `
130+
-Remediation "Set-ItemProperty 'HKLM:\SOFTWARE\Policies\Microsoft\Windows\PowerShell\ModuleLogging' -Name EnableModuleLogging -Value 1" `
131+
-Details @{ Key = "HKLM:\SOFTWARE\Policies\Microsoft\Windows\PowerShell\ModuleLogging\EnableModuleLogging"; Value = "absent or 0" } `
132+
-MITRE @("T1562.002")
133+
}
134+
} catch {
135+
Write-Verbose "Could not check ModuleLogging policy: $_"
136+
}
137+
138+
try {
139+
$transcript = Get-ItemProperty "HKLM:\SOFTWARE\Policies\Microsoft\Windows\PowerShell\Transcription" -ErrorAction SilentlyContinue
140+
if (-not $transcript -or -not $transcript.EnableTranscripting -or $transcript.EnableTranscripting -eq 0) {
141+
Add-Finding -Severity "INFO" -Category "DefenseEvasion" `
142+
-Title "PowerShell Transcription Not Enabled" `
143+
-Description "PowerShell transcription is not enabled via policy. When enabled, PowerShell logs all input and output to text files, providing a full audit trail of PowerShell activity on the system." `
144+
-Remediation "Set-ItemProperty 'HKLM:\SOFTWARE\Policies\Microsoft\Windows\PowerShell\Transcription' -Name EnableTranscripting -Value 1" `
145+
-Details @{ Key = "HKLM:\SOFTWARE\Policies\Microsoft\Windows\PowerShell\Transcription\EnableTranscripting"; Value = "absent or 0" } `
146+
-MITRE @("T1562.002")
147+
}
148+
} catch {
149+
Write-Verbose "Could not check Transcription policy: $_"
150+
}
151+
124152
# ── 3. Windows Defender Real-Time Protection ─────────────────────────
125153

126154
Write-Status "Checking Defender real-time protection..."

modules/Check-FileSystem.ps1

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -199,7 +199,7 @@ function Invoke-FileSystemChecks {
199199
Write-Status "Checking file hashes against VirusTotal..."
200200

201201
$checked = 0
202-
$maxVT = 4
202+
$maxVT = if ($script:Config.MaxVTLookups) { [int]$script:Config.MaxVTLookups } else { 4 }
203203

204204
foreach ($file in $vtCandidates) {
205205
if ($checked -ge $maxVT) {

modules/Check-Network.ps1

Lines changed: 4 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -75,8 +75,8 @@ function Invoke-NetworkChecks {
7575
-MITRE @("T1071.001")
7676
}
7777

78+
$commonPorts = if ($script:Config.TrustedPorts) { $script:Config.TrustedPorts } else { @(80, 443, 8080, 8443, 993, 995, 587, 465, 53, 22) }
7879
foreach ($c in $connList) {
79-
$commonPorts = @(80, 443, 8080, 8443, 993, 995, 587, 465, 53, 22)
8080
if ($c.RemotePort -notin $commonPorts -and $c.RemotePort -lt 1024) {
8181
Add-Finding -Severity "WARNING" -Category "Network" `
8282
-Title "Connection on Uncommon Port: $($c.Process)${ip}:$($c.RemotePort)" `
@@ -95,7 +95,7 @@ function Invoke-NetworkChecks {
9595
Write-Status "Checking external IPs against AbuseIPDB..."
9696

9797
$checkedCount = 0
98-
$maxChecks = 30
98+
$maxChecks = if ($script:Config.AbuseIPDBMaxChecks) { [int]$script:Config.AbuseIPDBMaxChecks } else { 30 }
9999

100100
foreach ($ip in $externalIPs.Keys) {
101101
if ($checkedCount -ge $maxChecks) {
@@ -187,7 +187,7 @@ function Invoke-NetworkChecks {
187187
foreach ($key in $seenListeners.Keys) {
188188
$entry = $seenListeners[$key]
189189
$severity = "WARNING"
190-
$backdoorPorts = @(4444, 5555, 6666, 1234, 31337, 12345, 54321, 9999, 1337)
190+
$backdoorPorts = if ($script:Config.BackdoorPorts) { $script:Config.BackdoorPorts } else { @(4444, 5555, 6666, 1234, 31337, 12345, 54321, 9999, 1337) }
191191
if ($entry.Port -in $backdoorPorts) { $severity = "CRITICAL" }
192192
$addrStr = ($entry.Addresses | Sort-Object -Unique) -join ", "
193193

@@ -212,13 +212,7 @@ function Invoke-NetworkChecks {
212212
$adapters = Get-DnsClientServerAddress -ErrorAction SilentlyContinue |
213213
Where-Object { $_.ServerAddresses.Count -gt 0 }
214214

215-
$knownDNS = @(
216-
"8.8.8.8", "8.8.4.4",
217-
"1.1.1.1", "1.0.0.1",
218-
"9.9.9.9", "149.112.112.112",
219-
"208.67.222.222", "208.67.220.220",
220-
"76.76.2.0", "76.76.10.0"
221-
)
215+
$knownDNS = if ($script:Config.KnownDNSServers) { $script:Config.KnownDNSServers } else { @("8.8.8.8","8.8.4.4","1.1.1.1","1.0.0.1","9.9.9.9","149.112.112.112","208.67.222.222","208.67.220.220","76.76.2.0","76.76.10.0") }
222216

223217
$seenDns = @{}
224218
foreach ($adapter in $adapters) {

0 commit comments

Comments
 (0)