Files
mxaccess/tools/Setup-LiveProbeEnv.ps1
T
Joseph Doherty fe2a6db786
rust / build / test / clippy / fmt (push) Has been cancelled
Initial project state: .NET reference, design, Rust port (M0+M1), evidence
Layout:
- src/                    .NET 10 x64 reference: MxNativeCodec, MxNativeClient,
                          MxAsbClient, probes, tests, harnesses. Executable spec.
- design/                 Architectural plan for the Rust port (M0–M6), error
                          model, protocol invariants, risks (R1–R16), adversarial
                          review log (review.md).
- rust/                   Rust workspace. M0 skeleton + M1 codec parity.
                          mxaccess-codec: 215 unit tests + 2 cross-implementation
                          parity tests (byte-identical against .NET reference).
                          Other crates are M0 stubs awaiting M2+.
- captures/               Frida + netsh + pcap evidence per CLAUDE.md
                          ("captures are evidence, not throwaway logs").
- analysis/               Decompiled C# (frida/proxy/decompiled-*),
                          Ghidra exports for native DLLs (`exports/` only —
                          working state at `projects/` and AVEVA's input
                          binaries at `input/` are gitignored).
- docs/                   Reverse-engineering reference docs.
- tools/                  Setup-LiveProbeEnv.ps1 (Infisical credential fetcher),
                          Compute-Crc.ps1 (.NET parity helper).
- .github/workflows/      Rust CI: fmt + build + test + clippy on Windows.
- LICENSE                 MIT (Joseph Doherty, 2026).

Verified:
- cargo test --workspace → 217 passed (215 unit + 2 .NET parity), 0 failed
- cargo clippy --workspace -- -D warnings → clean
- cargo fmt --all -- --check → clean
- cargo publish --dry-run -p mxaccess-codec → packages cleanly

Excluded from history (see .gitignore):
- **/bin, **/obj, **/target — build artifacts
- analysis/ghidra/projects/ — Ghidra working state (regenerable)
- analysis/ghidra/input/ — AVEVA proprietary DLLs (vendor IP)

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-05 06:21:00 -04:00

122 lines
5.8 KiB
PowerShell

# Setup-LiveProbeEnv.ps1 — populate the env vars the mxaccess Rust port's
# `live`-feature integration tests and probes expect, fetching credentials
# from the homelab Infisical instance via wwtools/secrets/Get-Secret.ps1.
#
# Usage:
# . .\tools\Setup-LiveProbeEnv.ps1 # dot-source — env vars persist in the calling session
# . .\tools\Setup-LiveProbeEnv.ps1 -SkipAsbSecret # no Infisical lookup for ASB shared secret (CI/dev fallback)
# .\tools\Setup-LiveProbeEnv.ps1 -DryRun # print what would be set without exporting
#
# Hard rules (per design/00-overview.md "Adjacent tooling" section):
# - Credentials are fetched via `wwtools\secrets\Get-Secret.ps1`, which logs
# into Infisical fresh on each call (DPAPI session storage doesn't survive
# non-interactive contexts).
# - We never inline plaintext secrets here. New AVEVA-specific secrets go
# into Infisical at `homelab/aveva/system-platform/<KEY>` (suggested path).
# - Sets `MX_LIVE=1` to enable the `live` feature gate in cargo tests.
#
# Env vars set:
# MX_LIVE — "1", enables the `live` cargo feature
# MX_NMX_HOST — NMX hostname (default: localhost)
# MX_GALAXY_DB — tiberius / SQL Server connection string with integrated security
# MX_GALAXY_NAME — Galaxy name (default: $env:MX_GALAXY_NAME or 'ZB' from wwtools/grdb)
# MX_TEST_USER — fetched from Infisical: homelab/infrastructure/windows-hosts/WW_VM_ADMIN_USER
# MX_TEST_DOMAIN — fetched from Infisical: ...WW_VM_ADMIN_DOMAIN
# MX_TEST_PASSWORD — fetched from Infisical: ...WW_VM_ADMIN_PWD
# MX_ASB_SHARED_SECRET — fetched from Infisical: homelab/aveva/system-platform/ASB_SHARED_SECRET
# (TODO: add this entry to Infisical — currently optional with -SkipAsbSecret)
[CmdletBinding()]
param(
[string]$NmxHost = 'localhost',
[string]$GalaxyName = $(if ($env:MX_GALAXY_NAME) { $env:MX_GALAXY_NAME } else { 'ZB' }),
[string]$GalaxyServer = 'localhost',
[switch]$SkipAsbSecret,
[switch]$DryRun
)
$ErrorActionPreference = 'Stop'
$GetSecret = 'C:\Users\dohertj2\Desktop\wwtools\secrets\Get-Secret.ps1'
if (-not (Test-Path $GetSecret)) {
throw "Get-Secret.ps1 not found at $GetSecret. wwtools must be installed at C:\Users\dohertj2\Desktop\wwtools per design/00-overview.md 'Adjacent tooling' section."
}
# Hydrate User-scope env vars into Process scope. Necessary in non-interactive
# contexts (Bash → pwsh, scheduled tasks, CI runners) where the User-scope
# block from HKCU\Environment is not auto-merged into the process env.
foreach ($name in @('INFISICAL_API_URL','INFISICAL_UNIVERSAL_AUTH_CLIENT_ID','INFISICAL_UNIVERSAL_AUTH_CLIENT_SECRET')) {
if (-not (Get-Item -Path "Env:$name" -ErrorAction SilentlyContinue)) {
$userValue = [Environment]::GetEnvironmentVariable($name, 'User')
if ($userValue) {
Set-Item -Path "Env:$name" -Value $userValue
}
}
}
function Set-LiveEnvVar {
param([string]$Name, [string]$Value, [switch]$Sensitive)
$display = if ($Sensitive) { '***redacted***' } else { $Value }
if ($DryRun) {
Write-Host "[DRY] $Name = $display" -ForegroundColor Yellow
} else {
Set-Item -Path "Env:$Name" -Value $Value
Write-Host "[SET] $Name = $display" -ForegroundColor Green
}
}
function Get-InfisicalSecret {
param([string]$Key, [string]$Env = 'infrastructure', [string]$Path = '/windows-hosts')
try {
$value = & $GetSecret -Key $Key -Env $Env -Path $Path 2>&1
if ($LASTEXITCODE -ne 0 -or -not $value) {
throw "Get-Secret returned empty for $Env$Path/$Key (exit code $LASTEXITCODE)"
}
# Trim any trailing whitespace from the CLI output
return ($value | Out-String).Trim()
} catch {
throw "Failed to fetch $Env$Path/$Key from Infisical: $_"
}
}
Write-Host "mxaccess live-probe env setup" -ForegroundColor Cyan
Write-Host " source: wwtools/secrets/Get-Secret.ps1 -> https://infisical.dohertylan.com" -ForegroundColor DarkGray
Write-Host ""
# Non-secret env vars
Set-LiveEnvVar -Name 'MX_LIVE' -Value '1'
Set-LiveEnvVar -Name 'MX_NMX_HOST' -Value $NmxHost
Set-LiveEnvVar -Name 'MX_GALAXY_NAME' -Value $GalaxyName
$galaxyDb = "Server=$GalaxyServer;Database=$GalaxyName;Integrated Security=True;TrustServerCertificate=True"
Set-LiveEnvVar -Name 'MX_GALAXY_DB' -Value $galaxyDb
# Secret-backed env vars
Write-Host ""
Write-Host "Fetching credentials from Infisical..." -ForegroundColor Cyan
$user = Get-InfisicalSecret -Key 'WW_VM_ADMIN_USER'
Set-LiveEnvVar -Name 'MX_TEST_USER' -Value $user
$domain = Get-InfisicalSecret -Key 'WW_VM_ADMIN_DOMAIN'
Set-LiveEnvVar -Name 'MX_TEST_DOMAIN' -Value $domain
$password = Get-InfisicalSecret -Key 'WW_VM_ADMIN_PWD'
Set-LiveEnvVar -Name 'MX_TEST_PASSWORD' -Value $password -Sensitive
if ($SkipAsbSecret) {
Write-Host "[SKIP] MX_ASB_SHARED_SECRET (use AsbCredentials::shared_secret(&[u8]) constructor or set manually)" -ForegroundColor Yellow
} else {
try {
$asbSecret = Get-InfisicalSecret -Key 'ASB_SHARED_SECRET' -Env 'aveva' -Path '/system-platform'
Set-LiveEnvVar -Name 'MX_ASB_SHARED_SECRET' -Value $asbSecret -Sensitive
} catch {
Write-Warning "MX_ASB_SHARED_SECRET not yet in Infisical. Add it at homelab/aveva/system-platform/ASB_SHARED_SECRET, or rerun with -SkipAsbSecret. Underlying error: $_"
Set-LiveEnvVar -Name 'MX_ASB_SHARED_SECRET' -Value '' -Sensitive
}
}
Write-Host ""
Write-Host "Done. Live-probe env is ready." -ForegroundColor Green
Write-Host " Run cargo tests with the 'live' feature: cargo test -p mxaccess --features live -- --ignored" -ForegroundColor DarkGray
Write-Host " Run a probe example: cargo run -p mxaccess --example session-write" -ForegroundColor DarkGray