XFE Git
XFE Studio Git
Git 首页 全局搜索
XFE 主站 文档 NuGet

XFESystem

【Rust】XFE系统,基于Rust和汇编

公开
关注 0 Fork 0 Star 0
UTF-8
param()
$ErrorActionPreference = 'Stop'
$taskRoot = [IO.Path]::GetFullPath((Join-Path $PSScriptRoot '../..'))
$output = Join-Path $taskRoot ('build/CSharpBoot/AcceleratorProbe-' + [DateTimeOffset]::UtcNow.ToUnixTimeMilliseconds())
[void][IO.Directory]::CreateDirectory($output)
$computer = Get-CimInstance Win32_ComputerSystem | Select-Object HypervisorPresent,Model,Manufacturer
$processors = @(Get-CimInstance Win32_Processor | Select-Object Name,VirtualizationFirmwareEnabled,VMMonitorModeExtensions,SecondLevelAddressTranslationExtensions)
$qemu = Join-Path $taskRoot '.tools/qemu/qemu-system-x86_64.exe'
$accelHelp = & $qemu '-accel' 'help' | Out-String
if ($LASTEXITCODE -ne 0) { throw 'QEMU accelerator inventory failed.' }
if ($null -eq ('XfeWhpxCapabilityProbe' -as [type])) {
    Add-Type -TypeDefinition @'
using System;
using System.Runtime.InteropServices;
public static class XfeWhpxCapabilityProbe
{
    [DllImport("WinHvPlatform.dll", ExactSpelling=true)]
    private static extern int WHvGetCapability(int code, out uint value, uint bytes, out uint written);
    public static string Read()
    {
        try { uint value, written; int status = WHvGetCapability(0, out value, 4, out written);
            return "HRESULT=0x" + status.ToString("X8") + ";HypervisorPresent=" + value + ";Bytes=" + written; }
        catch (Exception error) { return error.GetType().Name + ": " + error.Message; }
    }
}
'@
}
$capability = [XfeWhpxCapabilityProbe]::Read()
$result = [ordered]@{Kind='ReadOnlyAcceleratorProbe';Host=$computer;Processors=$processors;QemuAccelerators=$accelHelp.Trim();WhpxCapability=$capability;WindowsFeaturesChanged=$false;HostRestarted=$false;PhysicalDiskAccess=$false;Cpu='max';Acceleration='whpx';PausedProbeSurvived=$false}
$arguments = '-machine q35 -accel whpx -cpu max -smp 1 -m 64M -S -nodefaults -display none -monitor none -serial none'
$process = $null
try {
    $process = Start-Process -FilePath $qemu -ArgumentList $arguments -WindowStyle Hidden -PassThru -RedirectStandardOutput (Join-Path $output 'QemuStdout.log') -RedirectStandardError (Join-Path $output 'QemuStderr.log')
    Start-Sleep -Milliseconds 2000
    $process.Refresh()
    $result.ProcessId = $process.Id
    $result.PausedProbeSurvived = !$process.HasExited
    if ($process.HasExited) { $result.QemuExitCode = $process.ExitCode }
} finally {
    if ($null -ne $process -and !$process.HasExited) { $process.Kill(); $process.WaitForExit(); $result.OwnPausedProbeStopped = $true }
}
$result.Stdout = Get-Content -LiteralPath (Join-Path $output 'QemuStdout.log') -Raw -Encoding UTF8
$result.Stderr = Get-Content -LiteralPath (Join-Path $output 'QemuStderr.log') -Raw -Encoding UTF8
$result | ConvertTo-Json -Depth 6 | Set-Content -LiteralPath (Join-Path $output 'Result.json') -Encoding UTF8
Write-Output (Join-Path $output 'Result.json')
$result | ConvertTo-Json -Depth 6