Public/Test-WindowsDeviceLinkSupport.ps1

function Test-WindowsDeviceLinkSupport {
    [CmdletBinding()]
    param(
        [ValidateNotNullOrEmpty()]
        [string]$WindowsManagementServicePath
    )

    $isWinPE = Test-Path -LiteralPath 'HKLM:\SYSTEM\CurrentControlSet\Control\MiniNT'
    $environment = if ($isWinPE) { 'WindowsPE' } else { 'Windows' }
    $processArchitecture = $env:PROCESSOR_ARCHITECTURE
    $operatingSystemArchitecture = $processArchitecture
    try {
        $processArchitecture = [Runtime.InteropServices.RuntimeInformation]::ProcessArchitecture.ToString().ToUpperInvariant()
        $operatingSystemArchitecture = [Runtime.InteropServices.RuntimeInformation]::OSArchitecture.ToString().ToUpperInvariant()
        if ($processArchitecture -eq 'X64') { $processArchitecture = 'AMD64' }
        if ($operatingSystemArchitecture -eq 'X64') { $operatingSystemArchitecture = 'AMD64' }
    }
    catch { }

    if ($PSBoundParameters.ContainsKey('WindowsManagementServicePath')) {
        $candidatePath = $WindowsManagementServicePath
        $dllSource = 'Explicit'
        $activationMode = 'DirectDll'
    }
    elseif ($isWinPE) {
        $candidatePath = $script:BundledWindowsManagementServicePath
        $dllSource = 'Bundled'
        $activationMode = 'DirectDll'
    }
    else {
        $candidatePath = Join-Path $env:SystemRoot 'System32\Windows.Management.Service.dll'
        $dllSource = 'System'
        $activationMode = 'RegisteredWinRT'
    }

    try {
        $resolvedPath = (Resolve-Path -LiteralPath $candidatePath -ErrorAction Stop).Path
    }
    catch {
        $missingReason = if ($dllSource -eq 'System') {
            'The Windows system copy of Windows.Management.Service.dll was not found.'
        }
        elseif ($isWinPE -and -not $PSBoundParameters.ContainsKey('WindowsManagementServicePath')) {
            'Windows.Management.Service.dll was not found. PowerShell Gallery packages intentionally do not include this Microsoft binary because redistribution rights have not been confirmed. For WinPE, place a compatible copy in the module Runtime folder or supply -WindowsManagementServicePath explicitly.'
        }
        else {
            'Windows.Management.Service.dll was not found at the supplied path.'
        }

        return [pscustomobject]@{
            Supported        = $false
            Environment      = $environment
            Architecture     = $processArchitecture
            DllSource        = $dllSource
            ActivationMode   = $activationMode
            DllPath          = $candidatePath
            DllVersion       = $null
            SignatureStatus  = $null
            MicrosoftSigned  = $false
            NativeProbe      = $null
            Warning          = $null
            Reason           = $missingReason
        }
    }

    $signatureStatus = $null
    $isMicrosoftSigned = $false
    $signatureWarning = $null
    try {
        $signature = Get-AuthenticodeSignature -LiteralPath $resolvedPath -ErrorAction Stop
        $signatureStatus = [string]$signature.Status
        $isMicrosoftSigned = $signature.Status -eq 'Valid' -and $signature.SignerCertificate -and $signature.SignerCertificate.Subject -match 'Microsoft'
        if (-not $isMicrosoftSigned) {
            $signatureWarning = "Authenticode could not validate the DLL as Microsoft-signed in the current environment (status: $signatureStatus). This is informational and does not block the native probe."
        }
    }
    catch {
        $signatureStatus = 'Unavailable'
        $signatureWarning = "Authenticode validation was unavailable: $($_.Exception.Message)"
    }

    $isEmulatedAmd64OnArm64 = $processArchitecture -eq 'AMD64' -and $operatingSystemArchitecture -eq 'ARM64'
    $isAmd64Host = [Environment]::Is64BitProcess -and
        $processArchitecture -eq 'AMD64' -and
        -not $isEmulatedAmd64OnArm64
    $isArm64RegisteredWindows = [Environment]::Is64BitProcess -and
        $processArchitecture -eq 'ARM64' -and
        $operatingSystemArchitecture -eq 'ARM64' -and
        -not $isWinPE -and
        $dllSource -eq 'System' -and
        $activationMode -eq 'RegisteredWinRT'
    $architectureSupported = $isAmd64Host -or $isArm64RegisteredWindows
    if ($architectureSupported) {
        if ($activationMode -eq 'RegisteredWinRT') {
            $nativeProbe = [WinPEDeviceLink.Native.DeviceLinkClient]::TestRegistered()
        }
        else {
            $nativeProbe = [WinPEDeviceLink.Native.DeviceLinkClient]::Test($resolvedPath)
        }
    }
    else {
        $nativeProbe = [pscustomobject]@{ Success = $false; Message = 'Native probe skipped because this architecture and activation route is not supported.' }
    }

    [pscustomobject]@{
        Supported        = $architectureSupported -and $nativeProbe.Success
        Environment      = $environment
        Architecture     = $processArchitecture
        DllSource        = $dllSource
        ActivationMode   = $activationMode
        DllPath          = $resolvedPath
        DllVersion       = (Get-Item -LiteralPath $resolvedPath).VersionInfo.FileVersion
        SignatureStatus  = $signatureStatus
        MicrosoftSigned  = $isMicrosoftSigned
        NativeProbe      = $nativeProbe.Message
        Warning          = $signatureWarning
        Reason           = if ($isEmulatedAmd64OnArm64) { 'An emulated AMD64 PowerShell process cannot use the ARM64 Windows DeviceLink runtime. Start native ARM64 Windows PowerShell or PowerShell 7 ARM64.' } elseif (-not $architectureSupported) { 'Supported routes are native 64-bit AMD64 PowerShell, or native 64-bit ARM64 PowerShell on full Windows using the registered system runtime. ARM64 Windows PE and direct ARM64 DLL activation are not supported.' } elseif (-not $nativeProbe.Success) { $nativeProbe.Message } else { $null }
    }
}