fix(security): add path validation for Defender exclusions

Validates that paths are within safe boundaries (project directory or
user AppData) before excluding them from Defender. Prevents accidental
or malicious exclusion of system directories.

- Adds safePrefixes validation (project dir + user AppData only)
- Checks each path against allowed prefixes
- Normalizes paths for consistent comparison
- Warns but processes non-existent paths (they may be created later)

Fixes potential security issue where modified script could exclude
system directories like C:\Windows or C:\Program Files.
This commit is contained in:
e-cesar9
2026-02-12 17:29:00 +01:00
parent 7a17c115d3
commit 79dfd90068
+36
View File
@@ -122,6 +122,18 @@ function Test-DefenderExclusions {
#>
param([string[]]$Paths)
# Security: Define safe path prefixes (project + user directories only)
$safePrefixes = @(
$ScriptDir, # Project directory
$env:LOCALAPPDATA, # User local appdata
$env:APPDATA # User roaming appdata
)
# Normalize and filter null/empty values
$safePrefixes = $safePrefixes | Where-Object { $_ } | ForEach-Object {
[System.IO.Path]::GetFullPath($_)
}
try {
# Check if Defender cmdlets are available (may not exist on older Windows)
$mpModule = Get-Module -ListAvailable -Name Defender -ErrorAction SilentlyContinue
@@ -146,11 +158,35 @@ function Test-DefenderExclusions {
$existing = $prefs.ExclusionPath
if (-not $existing) { $existing = @() }
# Normalize existing paths for comparison
$existing = $existing | Where-Object { $_ } | ForEach-Object {
[System.IO.Path]::GetFullPath($_)
}
# Normalize paths and find missing exclusions
$missing = @()
foreach ($path in $Paths) {
$normalized = [System.IO.Path]::GetFullPath($path)
# Security: Ensure path is within safe boundaries
$isSafe = $false
foreach ($prefix in $safePrefixes) {
if ($normalized -like "$prefix*") {
$isSafe = $true
break
}
}
if (-not $isSafe) {
Write-Warn "Security: Refusing to exclude path outside safe boundaries: $normalized"
continue
}
# Info: Warn if path doesn't exist yet (but still process it)
if (-not (Test-Path $path -ErrorAction SilentlyContinue)) {
Write-Verbose "Path does not exist yet: $path (will be excluded when created)"
}
# Check if path or any parent is already excluded
$alreadyExcluded = $false
foreach ($excluded in $existing) {