AdministrativeAddOn.psm1
function Get-LastBoot ( [Parameter(Mandatory=$false)][string]$ComputerName, [Parameter(Mandatory=$false)][ValidateNotNull()] [System.Management.Automation.PSCredential][System.Management.Automation.Credential()] $Credential = [System.Management.Automation.PSCredential]::Empty ) { <# .Synopsis Retrieves last system boot time .Description The Get-LastBoot function queries the system to report the last OS boot time. This command may be run locally or remotely using the 'ComputerName' parameter. ` The 'Credential' parameter may be necessary when querying remote systems. .Inputs N/A .Outputs System.DateTime .Example Get-LastBoot Saturday, November 20, 2020 4:32:06 AM .Example $Creds = Get-Credential Get-LastBoot -ComputerName 'Server1' -Credential $Creds Wednesday, April 14, 2018 6:05:01 AM .Link N/A #> # RETRIEVES OS START TIME If ($ComputerName -ne $null) { (Get-CimInstance -ClassName Win32_OperatingSystem -ComputerName $ComputerName).LastBootUpTime } Else { (Get-CimInstance -ClassName Win32_OperatingSystem).LastBootUpTime } } function Get-UpTime ( [Parameter(Mandatory=$false)][string]$ComputerName, [Parameter(Mandatory=$false)][ValidateNotNull()] [System.Management.Automation.PSCredential][System.Management.Automation.Credential()] $Credential = [System.Management.Automation.PSCredential]::Empty ) { <# .Synopsis Calculates uptime for system .Description The Get-UpTime function calculates the amount of time since the last system boot time. This command may be run locally or remotely using the 'ComputerName' ` parameter. The 'Credential' parameter may be necessary when querying remote systems. .Inputs N/A .Outputs System.TimeSpan .Example Get-UpTime Days Hours Minutes Seconds ---- ----- ------- ------- 2 19 11 42 .Example Get-UpTime -ComputerName 'Server1' Days Hours Minutes Seconds ---- ----- ------- ------- 52 12 55 17 .Link N/A #> # GATHERS DATA $CompData = Get-CimInstance -ClassName Win32_OperatingSystem # CALCULATES UP TIME AND REMOVES UNUSABLE DATA $CompData.LocalDateTime - $CompData.LastBootUpTime | Select-Object -Property Days,Hours,Minutes,Seconds } function Get-UserSession ( [Parameter(Mandatory=$false)][string]$ComputerName, [Parameter(Mandatory=$false)][string]$UserName, [Parameter(Mandatory=$false)][ValidateSet("Active","Disc","Idle")][string]$State ) { <# .Synopsis Reports all console, RDP, and ICA sessions. .Description The Get-UserSession function executes a 'quser' command but converts it into a custom PS object. This can then be piped into a Remove-UserSession command to force log off of all sessions on a system or specific sesssions. .Inputs N/A .Outputs System.Management.Automation.PSCustomObject .Example Get-UserSession USERNAME : john.doe SESSIONNAME : console ID : 4 STATE : Active IDLE_TIME : none LOGON_TIME : 11/24/2020 9:54 AM SERVER : Workstation1 USERNAME : jane.doe SESSIONNAME : rdp-tcp#10 ID : 5 STATE : Idle IDLE_TIME : 16:45 LOGON_TIME : 11/24/2020 3:10 PM SERVER : Workstation1 .Example Get-UserSession -State Active USERNAME : john.doe SESSIONNAME : console ID : 4 STATE : Active IDLE_TIME : none LOGON_TIME : 11/24/2020 9:54 AM SERVER : Workstation1 .Example Get-UserSession -UserName jane.doe USERNAME : jane.doe SESSIONNAME : rdp-tcp#10 ID : 5 STATE : Idle IDLE_TIME : 16:45 LOGON_TIME : 11/24/2020 3:10 PM SERVER : Workstation1 .Link N/A #> # RESERVES VARIABLES $UserSession = @() $Session = $null $SessionCnt = $null # RUNS QUSER AND CAPTURES DATA, REMOVES ALL BULK SPACES AND REPLACES WITH A SINGLE SPACE If ($ComputerName -eq "") { $QResults = quser $ComputerName = $env:COMPUTERNAME } Else { $QResults = quser /SERVER:$ComputerName } $QResults = $QResults -replace '\s+', ' ' # CREATES OBJECT FOR EACH RETURNED RESULT Foreach ($Line in $QResults[1..$QResults.GetUpperBound(0)]) { #Separates the data $Split = $Line.Split(' ').Split('>') # SESSIONNAME IS BLANK WHEN THE SESSION IS DISCONNECTED. MODIFIES DATA ACCORDINGLY. If ($Split[3] -eq 'Disc') { $Session = "" $SessionCnt = 1 } Else { $Session = $Split[2] $SessionCnt = 2 } # CREATES OBJECTS $UserSession += [pscustomobject]@{ USERNAME = $Split[1] SESSIONNAME = $Session ID = $Split[$SessionCnt + 1] STATE = $Split[$SessionCnt + 2] IDLE_TIME = $Split[$SessionCnt + 3] LOGON_TIME = ($Split[($SessionCnt + 4)..($SessionCnt + 6)] -join ' ') SERVER = $ComputerName } # RESETS LOOP VARIABLES $Session = $null $SessionCnt = $null } # FILTERS ALL USER SESSIONS BY USERNAME If ($UserName -ne "") { $UserSession = $UserSession | Where-Object {$_.UserName -eq $UserName} } # FILTERS ALL USER SESSIONS BY STATE If ($State -ne "") { $UserSession = $UserSession | Where-Object {$_.State -eq $State} } # RETURNS ALL REQUESTED USER SESSIONS Return $UserSession } function Remove-UserSession ( [Parameter(ParameterSetName="ID", Mandatory=$true)][int]$ID, [Parameter(ParameterSetName="ID", Mandatory=$false)][string]$ComputerName, [Parameter(ParameterSetName="InputObject", ValueFromPipeline, Mandatory=$true)]$InputObject ) { <# .SYNOPSIS Forces a logoff of the selected session by Id number. .DESCRIPTION The Remove-UserSession function logs off all user sessions provide by the 'ID' parameter or from the pipeline. The 'ComputerName' parameter can be utilized to logoff users on remote computers. .INPUTS System.Management.Automation.PSCustomObject .OUTPUTS N/A .EXAMPLE Remove-UserSession -Id 5 .EXAMPLE Get-UserSession -State Disc | Remove-UserSession .LINK N/A #> # LOGS OFF THE SESSION EITHER LOCALLY OR REMOTELY BASED UPON USAGE OF SERVER PARAMETER If ($null -ne $InputObject) { Foreach ($InObj in $InputObject) { logoff $($InObj.ID) /SERVER:$($InObj.SERVER) } } ElseIf ($null -ne $ID) { If ($ComputerName -eq "") { $ComputerName = $env:COMPUTERNAME } logoff $ID /SERVER:$ComputerName } } function Get-InstalledSoftware ( [CmdletBinding(DefaultParameterSetName="Name")] [Parameter(ParameterSetName="Name", Mandatory=$false)][string]$Name, [Parameter(ParameterSetName="All", Mandatory=$false)][switch]$All, [Parameter(ParameterSetName="Filter", Mandatory=$false)][string]$Filter ) { <# .SYNOPSIS Gathers list of non-metro applications that are installed. .DESCRIPTION The Get-InstalledSoftware function gathers a list from the registry of standard installed applications. The 'Name' parameter can be used if you know the exact name of the software otherwise 'Filter' should be used as it will provide all software with a matching name. The 'All' parameter will output all install software. .INPUTS N/A .OUTPUTS System.Management.Automation.PSCustomObject .EXAMPLE Get-InstalledSoftware -All Name : PuTTY release 0.70 (64-bit) Publisher : Simon Tatham Version : 0.70.0.0 InstallDate : 20201126 InstallLocation : UninstallString : MsiExec.exe /X{45B3032F-22CC-40CD-9E97-4DA7095FA5A2} QuietUninstallString : Name : Google Chrome Publisher : Google LLC Version : 87.0.4280.66 InstallDate : 20201126 InstallLocation : C:\Program Files\Google\Chrome\Application UninstallString : "C:\Program Files\Google\Chrome\Application\87.0.4280.66\Installer\setup.exe" --uninstall --system-level --verbose-logging QuietUninstallString : .EXAMPLE Get-InstalledSoftware -Name "Google Chrome" Name : Google Chrome Publisher : Google LLC Version : 87.0.4280.66 InstallDate : 20201126 InstallLocation : C:\Program Files\Google\Chrome\Application UninstallString : "C:\Program Files\Google\Chrome\Application\87.0.4280.66\Installer\setup.exe" --uninstall --system-level --verbose-logging QuietUninstallString : .EXAMPLE Get-InstalledSoftware -Filter "Chrome" Name : Google Chrome Publisher : Google LLC Version : 87.0.4280.66 InstallDate : 20201126 InstallLocation : C:\Program Files\Google\Chrome\Application UninstallString : "C:\Program Files\Google\Chrome\Application\87.0.4280.66\Installer\setup.exe" --uninstall --system-level --verbose-logging QuietUninstallString : .LINK N/A #> # ENSURES FUNCTION VARIABLES ARE RESET $OutputArray = @() $SoftData = @() # GATHERS INSTALLED PROGRAMS $SoftData += Get-ItemProperty -Path "HKLM:\SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall\*" $SoftData += Get-ItemProperty -Path "HKLM:\SOFTWARE\WOW6432Node\Microsoft\Windows\CurrentVersion\Uninstall\*" # CREATES CUSTOM OUTPUT OBJECTS Foreach ($Soft in $SoftData) { If (($null -ne $Soft.DisplayName) -and ($null -ne $Soft.Publisher)) { $OutputArray += [PSCustomObject]@{ Name = $Soft.DisplayName Publisher = $Soft.Publisher Version = $Soft.DisplayVersion InstallDate = $Soft.InstallDate InstallLocation = $Soft.InstallLocation UninstallString = $Soft.UninstallString QuietUninstallString = $Soft.QuietUninstallString } } } # OUTPUTS BASED UPON PARAMETER SELECTION If ($All) { Return $OutputArray } ElseIf ($Name -ne "") { Return $OutputArray | Where-Object {$_.Name -eq $Name} } ElseIf ($Filter -ne "") { Return $OutputArray | Where-Object {$_.Name -match $Filter} } } function Remove-InstalledSoftware ( [Parameter(ParameterSetName="Name", Mandatory = $false)][string]$Name, [Parameter(ValueFromPipeline, ParameterSetName="InputObject", Mandatory=$false)]$InputObject, [Parameter(ParameterSetName="Name", Mandatory=$false)][Parameter(ParameterSetName="InputObject")][switch]$Quiet ) { <# .SYNOPSIS Kicks off uninstallation of designated software. .DESCRIPTION The Remove-InstalledSoftware function initiates an uninstallation of software provide by name or provided from the pipeline from Get-InstalledSoftware. The 'Quiet' switch will initiate quiet uninstallations of each piece of software selected. If the UninstallString in the registry refers to MsiExec the standard switches for quiet uninstall '/qn' are appended to initiate uninstallation. .INPUTS System.Management.Automation.PSCustomObject .OUTPUTS N/A .EXAMPLE Remove-InstalledSoftware -Name "Google Chrome" .EXAMPLE Get-InstalledSoftware -Filter "PuTTY" | Remove-InstalledSoftware -Quiet .LINK N/A #> Process { # GETS VALID PIPELINE DATA If ($null -ne $InputObject) { $Name = $InputObject.Name $UninstallString = $InputObject.UninstallString $QuietUninstallString = $InputObject.QuietUninstallString } # ADJUSTS APPROACH IF QUIET WAS SELECTED If ($Quiet) { If ($Name -ne "") { $Soft = Get-InstalledSoftware -Name $Name $UninstallString = $Soft.UninstallString $QuietUninstallString = $Soft.QuietUninstallString } # ADDS STANDARD QUIET UNINSTALL PARAMETERS FOR MSIEXEC PROGRAMS If ($UninstallString -match "MsiExec.exe") { $QuietUninstallString = "$UninstallString /qn" } # RETURNS ERROR IF THERE IS NO QUIET UNINSTALL DATA If ($null -eq $QuietUninstallString) { Write-Error -Message "Quiet uninstall string unavailable for selected software: $($Name)." Break } # PASSES QUIET UNINSTALL FOR FUTURE PROCESSING $UninstallString = $QuietUninstallString Write-Host -ForegroundColor Yellow "Beginning uninstallation of `'$Name`'..." } Else { If ($Name -ne "") { $Soft = Get-InstalledSoftware -Name $Name $UninstallString = $Soft.UninstallString } } # PARSES UNINSTALLSTRING TO GET THE EXECUTABLE PATH AND ARGUMENT LIST $UninstallSplit = $UninstallString.TrimStart('"').Replace('.exe ','.exe" ').Split('"').TrimStart() $UninstallPath = $UninstallSplit[0] $UninstallParameters = $UninstallSplit[1] # INITIATES UNINSTALL If ($UninstallParameters -ne "") { Start-Process -FilePath $UninstallPath -ArgumentList $UninstallParameters -Wait } Else { Start-Process -FilePath $UninstallPath -Wait } } End { } } function Get-HardwareInfo ( [Parameter(Mandatory=$false)][string]$ComputerName, [Parameter(Mandatory=$false)][ValidateNotNull()] [System.Management.Automation.PSCredential][System.Management.Automation.Credential()] $Credential = [System.Management.Automation.PSCredential]::Empty ) { <# .SYNOPSIS Gathers all major hardware component info to provide a picture of the core hardware of the system. .DESCRIPTION The Get-HardwareInfo function gets info from the motherboard, processor(s), RAM DIMM(s), GPU(s), Drive(s) and NIC(s). If there are mulitple items for any component except motherboard each items information will be emunerated. .INPUTS N/A .OUTPUTS System.Management.Automation.PSCustomObject .EXAMPLE Get-HardwareInfo Gathering system data, please wait... Computer : System1 Manufacturer : Micro-Star International Co., Ltd. Model : MS-7A33 Motherboard : X370 KRAIT GAMING (MS-7A33) SerialNumber : 6301-3908-3237-3716-4735-3460-25 BIOSVerions : 1.H0 BIOSReleaseDate : 1/20/2019 5:00:00 PM CPU0 : AMD Ryzen 5 1600X Six-Core Processor CPU0_Socket : AM4 There is more data but is cut off by the limitations of the Example function. .LINK N/A #> # RESETS BASE VARIABLES TO ENSURE CLEAN EXECUTION $cnt = 0 $HData = $null $CrossRefNIC = $null If ($ComputerName -eq "") { Write-Host -ForegroundColor Yellow "Gathering system data, please wait..." # GET MOTHERBOARD INFO $CompData = Get-CimInstance -ClassName CIM_ComputerSystem -Property * $MoboData = Get-CimInstance -ClassName CIM_PhysicalPackage -Property * $BIOSData = Get-CimInstance -ClassName CIM_BIOSElement -Property * # GETS PROCESSOR INFO $ProcData = Get-CimInstance -ClassName CIM_Processor -Property * # GETS RAM INFO $DIMMData = Get-CimInstance -ClassName CIM_PhysicalMemory -Property * # GETS GRAPHICS CARD INFO $GPUData = Get-CimInstance -ClassName CIM_VideoController -Property * # GETS DISK DRIVE INFO $DriveData = Get-CimInstance -ClassName CIM_DiskDrive -Property * # GETS NETWORK INTERFACE CARD INFO $NetData = Get-NetAdapterHardwareInfo $MoreNetData = Get-NetAdapter } Else { Write-Host -ForegroundColor Yellow "Gathering system data, please wait..." # GET MOTHERBOARD INFO $CompData = Invoke-Command -ScriptBlock {Get-CimInstance -ClassName CIM_ComputerSystem -Property *} -ComputerName $ComputerName -Credential $Credential $MoboData = Invoke-Command -ScriptBlock {Get-CimInstance -ClassName CIM_PhysicalPackage -Property *} -ComputerName $ComputerName -Credential $Credential $BIOSData = Invoke-Command -ScriptBlock {Get-CimInstance -ClassName CIM_BIOSElement -Property *} -ComputerName $ComputerName -Credential $Credential # GETS PROCESSOR INFO $ProcData = Invoke-Command -ScriptBlock {Get-CimInstance -ClassName CIM_Processor -Property *} -ComputerName $ComputerName -Credential $Credential # GETS RAM INFO $DIMMData = Invoke-Command -ScriptBlock {Get-CimInstance -ClassName CIM_PhysicalMemory -Property *} -ComputerName $ComputerName -Credential $Credential # GETS GRAPHICS CARD INFO $GPUData = Invoke-Command -ScriptBlock {Get-CimInstance -ClassName CIM_VideoController -Property *} -ComputerName $ComputerName -Credential $Credential # GETS DISK DRIVE INFO $DriveData = Invoke-Command -ScriptBlock {Get-CimInstance -ClassName CIM_DiskDrive -Property *} -ComputerName $ComputerName -Credential $Credential # GETS NETWORK INTERFACE CARD INFO $NetData = Invoke-Command -ScriptBlock {Get-NetAdapterHardwareInfo} -ComputerName $ComputerName -Credential $Credential $MoreNetData = Invoke-Command -ScriptBlock {Get-NetAdapter} -ComputerName $ComputerName -Credential $Credential } # CREATES OUPUT OBJECT $HData = [pscustomobject]@{ Computer = $CompData.DNSHostName Manufacturer = $CompData.Manufacturer Model = $CompData.Model Motherboard = ($MoboData | Where-Object {$_.Name -match "Base Board"}).Product SerialNumber = $BIOSData.SerialNumber BIOSVerions = $BIOSData.SMBIOSBIOSVersion BIOSReleaseDate = $BIOSData.ReleaseDate } # GENERATES OUTPUT FOR EACH PROCESSOR Foreach ($Proc in $ProcData) { $HData | Add-Member -MemberType NoteProperty -Name "CPU$cnt" -Value $Proc.Name $HData | Add-Member -MemberType NoteProperty -Name "CPU$($cnt)_Socket" -Value $Proc.SocketDesignation $HData | Add-Member -MemberType NoteProperty -Name "CPU$($cnt)_Clock" -Value $Proc.CurrentClockSpeed $HData | Add-Member -MemberType NoteProperty -Name "CPU$($cnt)_Cores" -Value $Proc.NumberOfCores $HData | Add-Member -MemberType NoteProperty -Name "CPU$($cnt)_Threads" -Value $Proc.ThreadCount $HData | Add-Member -MemberType NoteProperty -Name "CPU$($cnt)_L3CacheSize" -Value "$($Proc.L3CacheSize / 1024) MBs" $cnt++ } $cnt = 0 # GENERATES OUTPUT FOR EACH STICK OF RAM Foreach ($DIMM in $DIMMData) { $HData | Add-Member -MemberType NoteProperty -Name "DIMM$cnt" -Value $DIMM.PartNumber $HData | Add-Member -MemberType NoteProperty -Name "DIMM$($cnt)_Capacity" -Value "$($DIMM.Capacity / 1073741824) GBs" $HData | Add-Member -MemberType NoteProperty -Name "DIMM$($cnt)_Speed" -Value $DIMM.Speed $HData | Add-Member -MemberType NoteProperty -Name "DIMM$($cnt)_ClockSpeed" -Value "$($DIMM.ConfiguredClockSpeed) MHz" $cnt++ } $cnt = 0 # GENERATES OUTPUT FOR EACH GRAPHICS CARD Foreach ($GPU in $GPUData) { $HData | Add-Member -MemberType NoteProperty -Name "GPU$cnt" -Value $GPU.Name $HData | Add-Member -MemberType NoteProperty -Name "GPU$($cnt)_RAM" -Value "$([math]::Round($GPU.AdapterRAM / 1073741824,2)) GBs" $HData | Add-Member -MemberType NoteProperty -Name "GPU$($cnt)_DriverVersion" -Value $GPU.DriverVersion $HData | Add-Member -MemberType NoteProperty -Name "GPU$($cnt)_DriverReleaseDate" -Value $GPU.DriverDate $HData | Add-Member -MemberType NoteProperty -Name "GPU$($cnt)_RefreshRate" -Value $GPU.CurrentRefreshRate $HData | Add-Member -MemberType NoteProperty -Name "GPU$($cnt)_MaxRefreshRate" -Value $GPU.MaxRefreshRate $cnt++ } $cnt = 0 # GENERATES OUTPUT FOR EACH DISK DRIVE Foreach ($Drive in $DriveData) { $HData | Add-Member -MemberType NoteProperty -Name "Drive$cnt" -Value $Drive.Model $HData | Add-Member -MemberType NoteProperty -Name "Drive$($cnt)_Interface" -Value $Drive.InterfaceType $HData | Add-Member -MemberType NoteProperty -Name "Drive$($cnt)_Capacity" -Value "$([math]::Round($Drive.Size / 1073741824,2)) GBs" $HData | Add-Member -MemberType NoteProperty -Name "Drive$($cnt)_FirmwareRevision" -Value $Drive.FirmwareRevision $cnt++ } $cnt = 0 # GENERATES OUTPUT FOR EACH NETWORK INTERFACE CARD Foreach ($NIC in $NetData) { $CrossRefNIC = $MoreNetData | Where-Object {$_.InterfaceDescription -eq $NIC.InterfaceDescription} $HData | Add-Member -MemberType NoteProperty -Name "NIC$($cnt)_Name" -Value $CrossRefNIC.Name $HData | Add-Member -MemberType NoteProperty -Name "NIC$($cnt)_Description" -Value $CrossRefNIC.InterfaceDescription $HData | Add-Member -MemberType NoteProperty -Name "NIC$($cnt)_LinkSpeed" -Value $CrossRefNIC.LinkSpeed $HData | Add-Member -MemberType NoteProperty -Name "NIC$($cnt)_MacAddress" -Value $CrossRefNIC.MacAddress $cnt++ } # RETURNS ALL GATHERED DATA Return $HData } |