<# .SYNOPSIS A short one-line action-based description, e.g. 'Tests if a function is valid' .DESCRIPTION A longer description of the function, its purpose, common use cases, etc. .NOTES Information or caveats about the function e.g. 'This function is not supported in Linux' .LINK Specify a URI to a help page, this will show when Get-Help -Online is used. .EXAMPLE $NewITDWindowsVmVMwareParams = @{ ComputerName = 'itdzmtest300.nd.gov'; Environment = "Test"; AppName = "ITD-POC-zmeier"; Credential = $PrvCred; } New-ITDWindowsVmVMware @NewITDWindowsVmVMwareParams #> function New-ITDWindowsVmVMwareStep2 { [CmdletBinding()] param ( [string] $FQDN, [string] $AppName, [string] $VMEnvironment, [PSCredential] $Credential ) begin { } process { Write-Verbose -Message "Start New-ITDWindowsVmVMwareStep2" $FQDN = $FQDN.ToLower() $HostName = $FQDN.split('.')[0] $DomainName = $FQDN.Substring($FQDN.IndexOf(".") + 1) $VM = Get-VM -Name $FQDN $ViServer = $VM.Uid.split('@')[1].split(':')[0] $VMTagAssignments = Get-TagAssignment -Entity $VM #$AppName = $VMTagAssignments | Where-Object { $_.Tag.Category.Name -eq "AppName" } #$DTAP = $VMTagAssignments | Where-Object { $_.Tag.Category.Name -eq "DTAP" } Write-Verbose -Message "FQDN: $FQDN" Write-Verbose -Message "HostName: $HostName" $GuestVMLocalCredential = Get-ITDPassword -Title $FQDN -UserName itdadmin -Credential $Credential -ErrorAction SilentlyContinue $GuestCredentialAB = New-Object System.Management.Automation.PSCredential ('itdadmin', ($GuestVMLocalCredential.GetNetworkCredential().Password | ConvertTo-SecureString -AsPlainText -Force)) $GuestCredentialBB = New-Object System.Management.Automation.PSCredential ('Administrator', ($GuestVMLocalCredential.GetNetworkCredential().Password | ConvertTo-SecureString -AsPlainText -Force)) If ($null -eq $GuestVMLocalCredential) { Write-Error -Message "Credentials not found in Passwordstate" -ErrorAction Stop } Else { Write-Verbose -Message "Credentials found in Passwordstate" Write-Verbose -Message ("username: + " + $GuestVMLocalCredential.UserName) } <# Wait for Customization to finish $VMStarted = $false $VMCustomizationStarted = $false $VMCustomizationResult = $false While ($VMStarted -eq $false -or $VMCustomizationStarted -eq $false -or $VMCustomizationResult -eq $false) { Write-Warning ("Customization wait loop started " + (Get-Date)) Write-Verbose "Current Status:" Write-Verbose ("VMStarted: " + $VMStarted) Write-Verbose ("VMCustomizationStarted: " + $VMCustomizationStarted) Write-Verbose ("VMCustomizationResult: " + $VMCustomizationResult) $GetVIEventRuntime = Measure-Command -Expression { $VMEvents = Get-VIEvent -Entity $VM -Server $ViServer -ErrorAction SilentlyContinue } ## takes a long time to execute Write-Verbose ("Get-VIEvent last run time: " + $GetVIEventRuntime.TotalSeconds + " seconds") If ($VMStarted -eq $false) { If (@($VMEvents | Where-Object { $_.GetType().Name -eq "VMStartingEvent" })) { $VMStarted = $true Write-Warning "[$FQDN]:Virtual machine started" } } If ($VMCustomizationStarted -eq $false) { If (@($VMEvents | Where-Object { $_.GetType().Name -eq "CustomizationStartedEvent" })) { $VMCustomizationStarted = $true Write-Warning "[$FQDN]:Virtual machine customization started" } } If ($VMCustomizationResult -eq $false) { If (@($VMEvents | Where-Object { $_.GetType().Name -eq "CustomizationFailed" })) { $VMCustomizationResult = $true Write-Error "[$FQDN]:Virtual machine customization failed" Exit Exit } If (@($VMEvents | Where-Object { $_.GetType().Name -eq "CustomizationSucceeded" })) { $VMCustomizationResult = $true Write-Warning "[$FQDN]:Virtual machine customization completed" } } } #> # OS Write-Verbose -Message "Begin Post-Sysprep OS Guest Customization" Write-Verbose -Message "Assigning WMI Tag 000-Prod, SCCM will change it later if required" Get-VM -Name $FQDN | Invoke-VMScript -GuestCredential $GuestCredentialBB -ScriptType PowerShell -ScriptText { # Move DVD Drive Mount try { Write-Verbose "Create new Class" $Class = New-Object System.Management.ManagementClass("root\cimv2", [String]::Empty, $null); $Class["__CLASS"] = "ITD"; $Class.Qualifiers.Add("Static", $true) $Class.Properties.Add("MyKey", [System.Management.CimType]::String, $false) $Class.Properties["MyKey"].Qualifiers.Add("Key", $true) $Class.Properties.Add("LastModified", [System.Management.CimType]::String, $false) $Class.Properties.Add("DTAP", [System.Management.CimType]::String, $false) $Class.Properties.Add("Baseline", [System.Management.CimType]::String, $false) $Class.Put() Write-Verbose "Create single ITD Object" Set-WmiInstance -Class ITD -Arguments @{LastModified = (Get-Date); DTAP = "Prod"; Baseline = "000" } } catch { Throw $_ Break } } Write-Verbose -Message "Checking for DVD drive, and moving it to Z:\" Get-VM -Name $FQDN | Invoke-VMScript -GuestCredential $GuestCredentialBB -ScriptType PowerShell -ScriptText { Write-Host "hello1" # Move DVD Drive Mount try { $dvd_letter = 'Z' $dvd = Get-WmiObject -Class Win32_Volume -Filter "DriveType=5" | Select-Object -First 1 if ($dvd.Name -notmatch $dvd_letter) { Write-Verbose -Message "Found DVD drive, switching to $dvd_letter`:" Set-WmiInstance -InputObject $dvd -Arguments @{DriveLetter = "$dvd_letter`:" } | Out-Null Write-Verbose -Message "DVD drive moved to drive letter $dvd_letter`:" } else { Write-Verbose -Message "No DVD drive changes required, continuing..." } } catch { Throw $_ Break } } Write-Verbose -Message "Checking for unpartitioned space on C: volume and expanding" Get-VM -Name $FQDN | Invoke-VMScript -GuestCredential $GuestCredentialBB -ScriptType PowerShell -ScriptText { Write-Host "hello1" # Expand C: Partition To Maximum Extent try { $cSize = ( Get-Partition -DriveLetter C ).Size $cMaxSize = ( Get-PartitionSupportedSize -DriveLetter C ).SizeMax if ($cSize -lt $cMaxSize) { Write-Verbose -Message "Expanding C: from $($csize / 1GB)GB to $($cMaxSize / 1GB)GB..." Resize-Partition -DriveLetter C -Size $cMaxSize Write-Verbose -Message "C: expanded to $($cMaxSize / 1GB)GB." } else { Write-Verbose -Message "C: is already at maximum size, continuing..." } } catch { Throw $_ Break } } Write-Verbose -Message "Start Extra Disk(s) config" Get-VM -Name $FQDN | Invoke-VMScript -GuestCredential $GuestCredentialBB -ScriptType PowerShell -ScriptText { # Initialize Additional Disks try { # Non-initialized and MBR-initialized disks will have 0 partitions by default, but GPT-initialized disks will have 1 system reserved partition by default $Disks = Get-Disk | Where-Object { $_.NumberOfPartitions -eq 0 -or ( $_.PartitionStyle -eq 'GPT' -and $_.NumberOfPartitions -eq 1 ) } | Sort-Object -Property Number If ($Disks) { Write-Verbose -Message "Found $(@($disks).Count) unpartitioned disks." ForEach ($disk in $disks) { if ($disk.IsOffline) { Set-Disk $disk.Number -IsOffline $false Write-Verbose -Message "Brought disk $($disk.Number)($("{0:n0}GB" -f ($disk.Size / 1GB))) online..." } if ($disk.IsReadOnly) { Set-Disk $disk.Number -IsReadOnly $false } if ($disk.PartitionStyle -eq 'RAW') { Initialize-Disk $disk.Number -PartitionStyle GPT -ErrorAction SilentlyContinue } $diskParam = @{ FileSystem = 'NTFS' Confirm = $false } $driveLetter = [Int][Char]'D' while (Get-Volume -DriveLetter $([Char]$driveLetter) -ErrorAction SilentlyContinue) { $driveLetter++ } $diskParam.DriveLetter = [Char]$driveLetter if (@($disks).IndexOf($disk) -eq 0 -and (-not (Get-Volume -DriveLetter D -ErrorAction SilentlyContinue))) { $diskParam.NewFileSystemLabel = 'Temporary Storage' } elseif (@($disks).IndexOf($disk) -eq 1 -and (-not (Get-Volume -DriveLetter E -ErrorAction SilentlyContinue))) { $diskParam.NewFileSystemLabel = 'Data' } [void](New-Partition -DiskNumber $disk.Number -DriveLetter $diskParam.DriveLetter -UseMaximumSize) [void](Format-Volume @diskParam) } } Else { Write-Verbose -Message "No unpartitioned disks found, continuing..." -Verbose } } catch { Throw $_ Break } } Write-Verbose -Message "Start Page File Configuration" Get-VM -Name $FQDN | Invoke-VMScript -GuestCredential $GuestCredentialBB -ScriptType PowerShell -ScriptText { # Configure Page File if (Get-Partition -DriveLetter D -ErrorAction SilentlyContinue) { Write-Verbose -Message "Setting up pagefile.sys on D:..." -Verbose try { if (-not [IO.File]::Exists('D:\pagefile.sys')) { $autoPage = Get-WmiObject -Class Win32_ComputerSystem -EnableAllPrivileges $autoPage.AutomaticManagedPagefile = $false [void]$autoPage.Put() Write-Verbose -Message "Disabled automatic pagefile management." -Verbose $pageFile = Get-WmiObject -Class Win32_PageFileSetting -EnableAllPrivileges $pageFile.Delete() Write-Verbose -Message "Deleted C:\pagefile.sys." -Verbose Set-WmiInstance -Class Win32_PageFileSetting -Arguments @{ Name = "D:\pagefile.sys"; InitialSize = 0; MaximumSize = 0; } -EnableAllPrivileges | Out-Null Write-Verbose -Message "System managed page file created on D:\pagefile.sys." -Verbose } else { Write-Verbose -Message "Pagefile already configured on D:, continuing..." -Verbose } } catch { Throw $_ Break } } else { Write-Verbose -Message "Page file drive not found, cannot set up page file. Continuing server configuration..." -Verbose Write-Warning "Page file drive not found, cannot set up page file. Continuing server configuration..." } } Write-Verbose -Message "Enabling Remote Management" Get-VM -Name $FQDN | Invoke-VMScript -GuestCredential $GuestCredentialBB -ScriptType PowerShell -ScriptText { # Configure Remote Management (RDP/PoSH) try { Write-Verbose -Message "Checking WinRM..." -Verbose if (Test-WSMan -ErrorAction SilentlyContinue) { Write-Verbose -Message "WinRM is already enabled." } else { Enable-PSRemoting -Force Write-Verbose -Message "WinRM is now enabled." } Write-Verbose -Message "Checking RDP..." -Verbose $RDP = Get-WmiObject Win32_TerminalServiceSetting -Namespace root\cimv2\TerminalServices $NLA = Get-WmiObject Win32_TSGeneralSetting -Namespace root\cimv2\TerminalServices -Filter "TerminalName='RDP-tcp'" if ($RDP.AllowTSConnections -eq 0) { Write-Verbose -Message "RDP is disabled, enabling..." $RDP.SetAllowTSConnections(1, 1) | Out-Null Write-Verbose -Message "RDP is enabled." } else { Write-Verbose -Message "RDP is already enabled, checking NLA security..." } if ($NLA.UserAuthenticationRequired -eq 0) { Write-Verbose -Message "RDP is not NLA secured, enabling..." $NLA.SetUserAuthenticationRequired(1) | Out-Null Write-Verbose -Message "RDP is now NLA secured." } else { Write-Verbose -Message "RDP is already NLA secured." } } catch { Throw $_ Break } } Write-Verbose -Message "Checking current power plan, set to High Performance" Get-VM -Name $FQDN | Invoke-VMScript -GuestCredential $GuestCredentialBB -ScriptType PowerShell -ScriptText { # Configure Power Plan try { $powerPlans = powercfg -l if ($powerPlans -match '\*$' -notmatch 'High performance') { $currentPlan = [regex]::Match($powerPlans, '(?<=(\())[^)]+(?=(\)\s\*))').Value Write-Verbose -Message "Power plan is currently set to $currentPlan, changing to High Performance..." -Verbose $highPerformance = [regex]::Match($powerPlans, '([\d\w-\S]+)(?=\s+\(High performance\))').Value [void](powercfg -setactive $highPerformance) Write-Verbose -Message "Power plan set to High Performance." -Verbose } else { Write-Verbose -Message "Power plan already configured for High Performance." -Verbose } [void](& w32tm.exe /resync /nowait) } catch { Throw $_ Break } } $TimeSyncFunc = { # Configure Time/Date Settings Write-Verbose -Message "Checking current time/date settings..." $Domain = "" try { if ((Get-TimeZone).Id -ne 'Central Standard Time') { Write-Verbose -Message "Current time zone set to $((Get-TimeZone).Id), setting to Central Standard Time." -Verbose Set-TimeZone -Id 'Central Standard Time' Write-Verbose -Message "Time zone set to Central Standard Time." -Verbose } else { Write-Verbose -Message "Time zone is already set to Central Standard Time." -Verbose } } catch { Throw $_ Break } } $TimeSyncScriptBlock = $TimeSyncFunc -replace '', $DomainName $VM | Invoke-VMScript -GuestCredential $GuestCredentialBB -ScriptType PowerShell -ScriptText $TimeSyncScriptBlock #> Write-Verbose -Message "Enable the server manager performance monitors" Get-VM -Name $FQDN | Invoke-VMScript -GuestCredential $GuestCredentialBB -ScriptType PowerShell -ScriptText { # Enable Performance Counters try { if (Get-ScheduledTask -TaskName "Server Manager Performance Monitor" | Where-Object State -NE "Running" -ErrorAction SilentlyContinue) { Enable-ScheduledTask -TaskPath "\Microsoft\Windows\PLA\" -TaskName "Server Manager Performance Monitor" | Start-ScheduledTask Write-Verbose -Message "Performance monitors enabled." -Verbose } else { Write-Verbose -Message "Performance monitors already enabled, continuing..." -Verbose } } catch { Throw $_ Break } } Write-Verbose -Message "Disable Windows Firewall" Get-VM -Name $FQDN | Invoke-VMScript -GuestCredential $GuestCredentialBB -ScriptType PowerShell -ScriptText { # Disable Windows Firewall Write-Verbose -Message "Checking for active Windows Firewall..." -Verbose if ((Get-NetFirewallProfile).Enabled -contains 'True') { Write-Verbose -Message "Windows Firewall is still enabled, disabling it..." Set-NetFirewallProfile -Profile Domain, Public, Private -Enabled False Write-Verbose -Message "Windows Firewall disabled." -Verbose } else { Write-Verbose -Message "Windows Firewall already disabled, continuing..." -Verbose } } # Active Directory Write-Verbose -Message "Join Active Directory" Write-Verbose -Message "Domain is $DomainName" Write-Verbose -Message "AppName is $AppName" switch ($DomainName) { 'nd.gov' { $SearchBaseDomain = "dc=nd,dc=gov" } 'ndcloud.gov' { $SearchBaseDomain = "dc=ndcloud,dc=gov" } } ### Shared-PeopleSoft-HigherEd is not found because of the extra space character in the OU name ### commented out section below is the original code, swapped out for new code 2025/01/13 # Determine if the AppName has a dedicated OU, and pick it... or choose the All-General OU If ($DomainName -eq 'nd.gov') { $OUAppName = Get-ADOrganizationalUnit -Server $DomainName -SearchBase ("OU=Windows,OU=SERVERS,ou=COMPUTERS,ou=ITD," + $SearchBaseDomain) -Filter { Name -eq $AppName } If ($null -eq $OUAppName) { Write-Verbose -Message "Dedicated AppName OU not found, placing in All-General OU" $OUAppName = Get-ADOrganizationalUnit -Server $DomainName -SearchBase ("OU=Windows,OU=SERVERS,ou=COMPUTERS,ou=ITD," + $SearchBaseDomain) -Filter { Name -eq "All-General" } } # Determine if the Environment sub-ou is special for the selected AppName switch ($OUAppName.Name) { 'Shared-PeopleSoft-HigherEd' { switch ($VMEnvironment) { 'Test' { $EnvString = "Non-Prod" } 'Production' { $EnvString = "Prod" } } } 'Shared-PeopleSoft-State' { switch ($VMEnvironment) { 'Test' { $EnvString = "Non-Prod" } 'Production' { $EnvString = "Prod" } } } Default { switch ($VMEnvironment) { 'Test' { $EnvString = "Test" } 'Production' { $EnvString = "Prod" } } } } # Gather all sub OUs for the AppName OU $SubOUs = Get-ADOrganizationalUnit -Server $DomainName -SearchBase $OUAppName -Filter * If (@($SubOUs).count -eq 1) { $OUToUse = $SubOUs } Else { $OUToUse = $SubOUs | Where-Object { $_.DistinguishedName -like ("OU=$EnvString,OU=" + $OUAppName.Name + "*") } } # Determine if AD Computer object already exists $ExistingADComputer = Get-ADComputer -Filter { Name -eq $HostName } If ($ExistingADComputer) { Write-Verbose -Message "AD Object already exists in AD" # Determine if AD Computer object is in the correct OU, or a sub-OU of the correct OU If ($ExistingADComputer.DistinguishedName -like ("*" + $OUToUse.DistinguishedName)) { Write-Verbose -Message "AD Object is in the correct OU, will attempt domain join" $AttemptDomainJoin = $true } Else { Write-Verbose -Message "AD Object is NOT in the correct OU, domain join will not occur, needs human review" $AttemptDomainJoin = $false } } Else { $AttemptDomainJoin = $true } If ($AttemptDomainJoin) { $OuFinal = $OUToUse.DistinguishedName $FirstScriptBlock = { $DomainJoinCred = New-Object System.Management.Automation.PSCredential('svcitdvmdomainjoin', ('hypes-Vgv8h89' | ConvertTo-SecureString -AsPlainText -Force)) } $SecondScriptText = 'Add-Computer -DomainName -OUPath "" -Credential $DomainJoinCred -Server itddc42.nd.gov' $SecondScriptText = $SecondScriptText -replace '', $DomainName $SecondScriptText = $SecondScriptText -replace '', $OuFinal Write-Verbose -Message "[$FQDN]:Invoke-VMScript to AD join" $InvokeVMScriptFunc = [System.Management.Automation.ScriptBlock]::Create("$FirstScriptBlock ; $SecondScriptText") Get-VM -Name $FQDN | Invoke-VMScript -GuestCredential $GuestCredentialBB -ScriptType PowerShell -ScriptText $InvokeVMScriptFunc Write-Warning -Message "[$FQDN]:Restart VMGuest, wait for Tools, then 90 seconds after" Get-VM -Name $FQDN | Restart-VMGuest -Confirm:$false Wait-Tools -VM (Get-VM -Name $FQDN) Start-Sleep -Seconds 90 } } else { $GuestCredentialAB = $GuestCredentialBB } <# Write-Verbose -Message ("[$FQDN]:Copying SCCM client installer to C:\temp... " + (Get-Date)) Copy-VMGuestFile -Source C:\SCCM_Client\ -Destination C:\temp\SCCM_Client -VM (Get-VM -Name $FQDN) -LocalToGuest -GuestCredential $GuestCredentialAB -Force Write-Verbose -Message ("[$FQDN]:SCCM client copy complete " + (Get-Date)) #E:\AutoBuild\SCCM_Client\ # Check if SCCM automatically installed the SCCM client and registered it $CcmRegistered = $false $CcmRegistration = Get-VM -Name $FQDN | Invoke-VMScript -GuestCredential $GuestCredentialAB -ScriptType PowerShell -ScriptText { Get-Content C:\windows\ccm\logs\ClientIDManagerStartup.log } If ($CcmRegistration.ScriptOutput -match "Client is registered") { Write-Warning "Client is registered." $CcmRegistered = $true } ElseIf ($CcmRegistration.ScriptOutput -match "Client is already registered") { Write-Warning "Client is already registered." $CcmRegistered = $true } If ($CcmRegistered -eq $false) { Get-VM -Name $FQDN | Invoke-VMScript -GuestCredential $GuestCredentialAB -ScriptType PowerShell -ScriptText { If (Get-Process -Name ccmsetup -ErrorAction SilentlyContinue) { Write-Warning "CCM client is already installing" $CcmRegistered = $true } ElseIf (Get-Process -Name ccmexec -ErrorAction SilentlyContinue) { Write-Warning "CCM client is already installed" $CcmRegistered = $true } Else { Write-Warning -Message "Installing SCCM Client..." Invoke-Expression -Command "C:\temp\SCCM_Client\ccmsetup.exe SMSSITECODE=ITD SMSMP=itdsccmp2.nd.gov DNSSUFFIX=nd.gov" } } } Write-Verbose -Message "[$FQDN]:Register SCCM Client" While ($CcmRegistered -eq $false) { $CcmRegistration = Get-VM -Name $FQDN | Invoke-VMScript -GuestCredential $GuestCredentialAB -ScriptType PowerShell -ScriptText { Get-Content C:\windows\ccm\logs\ClientIDManagerStartup.log } If ($CcmRegistration.ScriptOutput -match "Client is registered") { Write-Warning "Client is registered." $CcmRegistered = $true } ElseIf ($CcmRegistration.ScriptOutput -match "Client is already registered") { Write-Warning "Client is already registered." $CcmRegistered = $true } ElseIf ($CcmRegistered -eq $false) { Start-Sleep -Seconds 30 } } Write-Verbose -Message "[$FQDN]:Approve SCCM Client" #Start-Sleep -Seconds 30 # ADD LOOP/SMARTS TO WAIT FOR DISCOVERY AND ANOTHER FOR APPROVAL Invoke-Command -ComputerName itdsccmp2.nd.gov -Credential $Credential -ArgumentList $Hostname -ScriptBlock { Import-Module 'D:\Program Files\Microsoft Configuration Manager\AdminConsole\bin\ConfigurationManager.psd1' $PSDrives = Get-PSDrive If ($PSDrives | Where-Object Name -EQ "ITD") { # ITD Drive exists, do nothing } else { New-PSDrive -Name "ITD" -PSProvider AdminUI.PS.Provider\CMSite -Root itdsccmp2.nd.gov } Set-Location ITD:\ $Device = Get-CMDevice -Name $args[0] If ($Device.IsApproved -eq 0) { Approve-CMDevice -DeviceName $args[0] } } Write-Verbose -Message "Trigger SCCM MachinePolicy First Check-in" Get-VM -Name $FQDN | Invoke-VMScript -GuestCredential $GuestCredentialAB -ScriptType PowerShell -ScriptText { [void] ([wmiclass] "\\localhost\root\ccm:SMS_Client").TriggerSchedule("{00000000-0000-0000-0000-000000000021}"); } Write-Verbose -Message "Trigger SCCM MachinePolicy" Get-VM -Name $FQDN | Invoke-VMScript -GuestCredential $GuestCredentialAB -ScriptType PowerShell -ScriptText { [void] ([wmiclass] "\\localhost\root\ccm:SMS_Client").TriggerSchedule("{00000000-0000-0000-0000-000000000021}"); } <#Write-Verbose -Message "Waiting for network connectivity / Then KVM Activation..." Get-VM -Name $FQDN | Invoke-VMScript -GuestCredential $GuestCredentialAB -ScriptType PowerShell -ScriptText { # Pause until network connectivity is available $KMS = 'kms.nd.gov' try { $nwJob = Start-Job -Name 'NetworkCheck' -ScriptBlock { Param ( [String]$KMS ) do { $nwStatus = Test-NetConnection -ComputerName $KMS -Port 1688 -InformationLevel Quiet Start-Sleep -Seconds 10 } until($nwStatus) } -ArgumentList $KMS # If after 30 seconds the network connection is not responding continue on if ((Wait-Job -Job $nwJob -Timeout 30).State -eq 'Completed') { Write-Verbose -Message 'Network connectivity has been verified.' } else { [void](Stop-Job -Job $nwJob) Write-Verbose -Message 'Network connectivity could not be verified.' } } catch { Throw $_ Break } Activate via KMS Write-Verbose -Message "Activating windows against $KMS..." if (!([Security.Principal.WindowsPrincipal][Security.Principal.WindowsIdentity]::GetCurrent()).IsInRole([Security.Principal.WindowsBuiltInRole] "Administrator")) { Start-Process powershell.exe "-NoProfile -ExecutionPolicy Bypass -File `"$PSCommandPath`"" -Verb RunAs; exit } try { cscript C:\Windows\System32\slmgr.vbs /skms $KMS | Out-Null cscript C:\Windows\System32\slmgr.vbs /ato | Out-Null Write-Verbose -Message "Checking activation status..." $kmsOut = cscript C:\Windows\System32\slmgr.vbs /dli if (($kmsOut | Select-String -Pattern '^License Status:') -match 'Licensed') { Write-Verbose -Message "Windows successfully activated." } else { Write-Verbose -Message "Windows failed to activate, run slmgr commands manually. Ensure server time is correct." Write-Warning -Message "Windows failed to activate, run slmgr commands manually. Ensure server time is correct." } } catch { Throw $_ Break } } #> Write-Verbose -Message ("[$FQDN]:Add to Solarwinds") $Func = { param($C) Import-Module -Name ITDSolarwinds -Verbose Import-SWDiscovery -ComputerName $C -Integration ServiceNow } Invoke-Command -ComputerName itdslrwnds.nd.gov -ScriptBlock $Func -ArgumentList $FQDN -Credential $Credential Write-Verbose -Message "[$FQDN]:End" } end { } }