From 7d4ee639c2cff6a86dfd77f7f12cf610ccfc9b24 Mon Sep 17 00:00:00 2001 From: lz Date: Tue, 23 Jun 2026 10:56:51 +0000 Subject: [PATCH] Upload files to "/" --- Get-SystemInformation.ps1 | 311 ++++++++++++++++++++++++++++++++++++++ 1 file changed, 311 insertions(+) create mode 100644 Get-SystemInformation.ps1 diff --git a/Get-SystemInformation.ps1 b/Get-SystemInformation.ps1 new file mode 100644 index 0000000..6adc2d6 --- /dev/null +++ b/Get-SystemInformation.ps1 @@ -0,0 +1,311 @@ +[CmdletBinding()] +param( + [string]$OutputPath +) + +$ErrorActionPreference = 'Stop' + +if ([string]::IsNullOrWhiteSpace($OutputPath)) { + $desktop = [Environment]::GetFolderPath('Desktop') + if ([string]::IsNullOrWhiteSpace($desktop)) { + $desktop = $PSScriptRoot + } + + $OutputPath = Join-Path $desktop ("SystemInformation_{0}.txt" -f (Get-Date -Format 'yyyyMMdd_HHmmss')) +} + +$report = New-Object System.Collections.Generic.List[string] +$steps = @( + 'General system information' + 'Windows version and uptime' + 'CPU information' + 'Memory information' + 'GPU information' + 'Network adapters and IP addresses' + 'Windows product key' + 'Windows update history' + 'Writing report' + 'Opening report in Notepad' +) +$stepNumber = 0 + +function Add-Line { + param([AllowEmptyString()][string]$Text = '') + $script:report.Add($Text) +} + +function Add-Section { + param([Parameter(Mandatory = $true)][string]$Title) + + Add-Line + Add-Line ('=' * 78) + Add-Line $Title.ToUpperInvariant() + Add-Line ('=' * 78) +} + +function Start-Step { + param([Parameter(Mandatory = $true)][string]$Name) + + $script:stepNumber++ + $percent = [int](($script:stepNumber / $script:steps.Count) * 100) + Write-Host ("[{0}/{1}] {2}..." -f $script:stepNumber, $script:steps.Count, $Name) -ForegroundColor Cyan + Write-Progress -Activity 'Collecting system information' -Status $Name -PercentComplete $percent +} + +function Add-PropertyLines { + param( + [Parameter(Mandatory = $true)]$InputObject, + [Parameter(Mandatory = $true)][string[]]$Properties + ) + + foreach ($property in $Properties) { + $value = $InputObject.$property + if ($null -eq $value -or "$value" -eq '') { + $value = 'Not available' + } + Add-Line ("{0,-28}: {1}" -f $property, $value) + } +} + +function Invoke-ReportStep { + param( + [Parameter(Mandatory = $true)][string]$Name, + [Parameter(Mandatory = $true)][scriptblock]$Action + ) + + Start-Step $Name + try { + & $Action + Write-Host ' Completed.' -ForegroundColor Green + } + catch { + Add-Line ("Unable to collect this section: {0}" -f $_.Exception.Message) + Write-Warning (" {0}" -f $_.Exception.Message) + } +} + +function ConvertFrom-DigitalProductId { + param([byte[]]$DigitalProductId) + + if ($null -eq $DigitalProductId -or $DigitalProductId.Length -lt 67) { + return $null + } + + $keyCharacters = 'BCDFGHJKMPQRTVWXY2346789' + $keyOffset = 52 + $isWindows8OrLater = [int](($DigitalProductId[66] / 6) -band 1) + $DigitalProductId[66] = [byte](($DigitalProductId[66] -band 0xF7) -bor (($isWindows8OrLater -band 2) * 4)) + $decoded = '' + $last = 0 + + for ($i = 24; $i -ge 0; $i--) { + $current = 0 + for ($j = 14; $j -ge 0; $j--) { + $current = ($current * 256) -bxor $DigitalProductId[$j + $keyOffset] + $DigitalProductId[$j + $keyOffset] = [byte][math]::Floor($current / 24) + $current = $current % 24 + } + $decoded = $keyCharacters[$current] + $decoded + $last = $current + } + + if ($isWindows8OrLater -eq 1) { + $decoded = $decoded.Insert($last, 'N') + if ($decoded.Length -gt 25) { + $decoded = $decoded.Substring(0, 25) + } + } + + for ($i = 5; $i -lt $decoded.Length; $i += 6) { + $decoded = $decoded.Insert($i, '-') + } + + return $decoded +} + +Add-Line 'SYSTEM INFORMATION REPORT' +Add-Line ("Generated : {0}" -f (Get-Date -Format 'yyyy-MM-dd HH:mm:ss K')) + +Invoke-ReportStep 'General system information' { + Add-Section 'General System Information' + $computer = Get-CimInstance Win32_ComputerSystem + $bios = Get-CimInstance Win32_BIOS + + Add-Line ("Hostname : {0}" -f $env:COMPUTERNAME) + Add-Line ("Logged-in user : {0}" -f $(if ($computer.UserName) { $computer.UserName } else { "$env:USERDOMAIN\$env:USERNAME" })) + Add-Line ("User domain : {0}" -f $env:USERDOMAIN) + Add-Line ("Computer domain/workgroup : {0}" -f $computer.Domain) + Add-Line ("Domain joined : {0}" -f $computer.PartOfDomain) + Add-Line ("Manufacturer : {0}" -f $computer.Manufacturer) + Add-Line ("Model : {0}" -f $computer.Model) + Add-Line ("System type : {0}" -f $computer.SystemType) + Add-Line ("Serial number : {0}" -f $bios.SerialNumber) + Add-Line ("BIOS version : {0}" -f ($bios.SMBIOSBIOSVersion -join ', ')) +} + +Invoke-ReportStep 'Windows version and uptime' { + Add-Section 'Windows Version and Uptime' + $os = Get-CimInstance Win32_OperatingSystem + $windowsKey = Get-ItemProperty 'HKLM:\SOFTWARE\Microsoft\Windows NT\CurrentVersion' + $now = Get-Date + $lastBoot = $os.LastBootUpTime + $uptime = $now - $lastBoot + + Add-Line ("Windows product name : {0}" -f $windowsKey.ProductName) + Add-Line ("Edition ID : {0}" -f $windowsKey.EditionID) + Add-Line ("Display version : {0}" -f $windowsKey.DisplayVersion) + Add-Line ("Version : {0}" -f $os.Version) + Add-Line ("Build number : {0}" -f $os.BuildNumber) + Add-Line ("Update build revision (UBR) : {0}" -f $windowsKey.UBR) + Add-Line ("Full build : {0}.{1}" -f $os.BuildNumber, $windowsKey.UBR) + Add-Line ("Architecture : {0}" -f $os.OSArchitecture) + Add-Line ("Install date : {0}" -f $os.InstallDate) + Add-Line ("Last boot : {0}" -f $lastBoot) + Add-Line ("Uptime : {0} days, {1} hours, {2} minutes, {3} seconds" -f + [math]::Floor($uptime.TotalDays), $uptime.Hours, $uptime.Minutes, $uptime.Seconds) +} + +Invoke-ReportStep 'CPU information' { + Add-Section 'CPU Information' + $processors = Get-CimInstance Win32_Processor + $index = 0 + + foreach ($processor in $processors) { + $index++ + Add-Line ("Processor {0}" -f $index) + Add-Line (" Name : {0}" -f $processor.Name.Trim()) + Add-Line (" Manufacturer : {0}" -f $processor.Manufacturer) + Add-Line (" Physical cores : {0}" -f $processor.NumberOfCores) + Add-Line (" Logical processors : {0}" -f $processor.NumberOfLogicalProcessors) + Add-Line (" Current clock speed : {0} MHz" -f $processor.CurrentClockSpeed) + Add-Line (" Maximum clock speed : {0} MHz" -f $processor.MaxClockSpeed) + Add-Line (" Socket : {0}" -f $processor.SocketDesignation) + Add-Line (" Processor ID : {0}" -f $processor.ProcessorId) + } +} + +Invoke-ReportStep 'Memory information' { + Add-Section 'Memory Information' + $computer = Get-CimInstance Win32_ComputerSystem + $os = Get-CimInstance Win32_OperatingSystem + $modules = Get-CimInstance Win32_PhysicalMemory + $totalGB = [math]::Round($computer.TotalPhysicalMemory / 1GB, 2) + $freeGB = [math]::Round($os.FreePhysicalMemory * 1KB / 1GB, 2) + + Add-Line ("Installed RAM : {0} GB" -f $totalGB) + Add-Line ("Available RAM : {0} GB" -f $freeGB) + Add-Line ("Used RAM : {0} GB" -f ([math]::Round($totalGB - $freeGB, 2))) + Add-Line + Add-Line 'Physical memory modules:' + + $slot = 0 + foreach ($module in $modules) { + $slot++ + Add-Line (" Module {0}" -f $slot) + Add-Line (" Bank/slot : {0} / {1}" -f $module.BankLabel, $module.DeviceLocator) + Add-Line (" Capacity : {0} GB" -f ([math]::Round($module.Capacity / 1GB, 2))) + Add-Line (" Speed : {0} MT/s" -f $module.ConfiguredClockSpeed) + Add-Line (" Manufacturer : {0}" -f $module.Manufacturer) + Add-Line (" Part number : {0}" -f $module.PartNumber.Trim()) + Add-Line (" Serial number : {0}" -f $module.SerialNumber) + } +} + +Invoke-ReportStep 'GPU information' { + Add-Section 'GPU Information' + $gpus = Get-CimInstance Win32_VideoController + $index = 0 + + foreach ($gpu in $gpus) { + $index++ + Add-Line ("GPU {0}" -f $index) + Add-Line (" Name : {0}" -f $gpu.Name) + Add-Line (" Adapter RAM : {0} GB" -f $(if ($gpu.AdapterRAM) { [math]::Round($gpu.AdapterRAM / 1GB, 2) } else { 'Not available' })) + Add-Line (" Driver version : {0}" -f $gpu.DriverVersion) + Add-Line (" Driver date : {0}" -f $gpu.DriverDate) + Add-Line (" Video processor : {0}" -f $gpu.VideoProcessor) + Add-Line (" Current resolution : {0} x {1} @ {2} Hz" -f $gpu.CurrentHorizontalResolution, $gpu.CurrentVerticalResolution, $gpu.CurrentRefreshRate) + Add-Line (" Status : {0}" -f $gpu.Status) + } +} + +Invoke-ReportStep 'Network adapters and IP addresses' { + Add-Section 'Network Adapters and IP Addresses' + $adapters = Get-CimInstance Win32_NetworkAdapterConfiguration | + Where-Object { $_.IPEnabled -or $_.MACAddress } | + Sort-Object -Property IPEnabled -Descending + + $index = 0 + foreach ($adapter in $adapters) { + $index++ + Add-Line ("Adapter {0}" -f $index) + Add-Line (" Description : {0}" -f $adapter.Description) + Add-Line (" Enabled : {0}" -f $adapter.IPEnabled) + Add-Line (" MAC address : {0}" -f $adapter.MACAddress) + Add-Line (" DHCP enabled : {0}" -f $adapter.DHCPEnabled) + Add-Line (" DHCP server : {0}" -f $adapter.DHCPServer) + Add-Line (" IP addresses : {0}" -f $(if ($adapter.IPAddress) { $adapter.IPAddress -join ', ' } else { 'None' })) + Add-Line (" Subnets : {0}" -f $(if ($adapter.IPSubnet) { $adapter.IPSubnet -join ', ' } else { 'None' })) + Add-Line (" Default gateways : {0}" -f $(if ($adapter.DefaultIPGateway) { $adapter.DefaultIPGateway -join ', ' } else { 'None' })) + Add-Line (" DNS servers : {0}" -f $(if ($adapter.DNSServerSearchOrder) { $adapter.DNSServerSearchOrder -join ', ' } else { 'None' })) + Add-Line + } +} + +Invoke-ReportStep 'Windows product key' { + Add-Section 'Windows Product Key' + $licensing = Get-CimInstance SoftwareLicensingService + $firmwareKey = $licensing.OA3xOriginalProductKey + $registry = Get-ItemProperty 'HKLM:\SOFTWARE\Microsoft\Windows NT\CurrentVersion' + $decodedKey = ConvertFrom-DigitalProductId -DigitalProductId ([byte[]]$registry.DigitalProductId.Clone()) + + Add-Line ("Firmware/OEM key : {0}" -f $(if ($firmwareKey) { $firmwareKey } else { 'Not embedded or not available' })) + Add-Line ("Registry-decoded key : {0}" -f $(if ($decodedKey) { $decodedKey } else { 'Not available' })) + Add-Line 'Note: Digital licenses and volume licensing may not expose the currently active key.' +} + +Invoke-ReportStep 'Windows update history' { + Add-Section 'Windows Update History' + $hotFixes = Get-HotFix | + Where-Object { $null -ne $_.InstalledOn } | + Sort-Object InstalledOn -Descending + + if ($hotFixes.Count -gt 0) { + Add-Line ("Most recent update installed: {0}" -f $hotFixes[0].InstalledOn) + Add-Line + Add-Line 'Installed updates (newest first):' + foreach ($hotFix in $hotFixes) { + Add-Line (" {0,-12} {1,-14} {2}" -f $hotFix.HotFixID, $hotFix.InstalledOn.ToString('yyyy-MM-dd'), $hotFix.Description) + } + } + else { + Add-Line 'No update installation dates were returned by Get-HotFix.' + } +} + +Start-Step 'Writing report' +try { + $outputDirectory = Split-Path -Parent $OutputPath + if ($outputDirectory -and -not (Test-Path -LiteralPath $outputDirectory)) { + New-Item -ItemType Directory -Path $outputDirectory -Force | Out-Null + } + + $report | Out-File -LiteralPath $OutputPath -Encoding utf8 -Force + Write-Host (" Report saved to: {0}" -f $OutputPath) -ForegroundColor Green +} +catch { + Write-Progress -Activity 'Collecting system information' -Completed + throw "Could not write the report to '$OutputPath': $($_.Exception.Message)" +} + +Start-Step 'Opening report in Notepad' +try { + Start-Process -FilePath 'notepad.exe' -ArgumentList "`"$OutputPath`"" + Write-Host ' Report opened in Notepad.' -ForegroundColor Green +} +catch { + Write-Warning ("Could not open Notepad: {0}" -f $_.Exception.Message) +} + +Write-Progress -Activity 'Collecting system information' -Completed +Write-Host 'System information collection complete.' -ForegroundColor Green