driverautomationtool.ps1 - Modified to pass UseBasicParsing parameter. See: http://www.scconfigmgr.com/2017/03/01/driver-automation-tool/
<# | |
.SYNOPSIS | |
Driver Automation GUI Tool for Dell,HP,Lenovo,Acer and Microsoft systems | |
.DESCRIPTION | |
This script allows you to automate the process of keeping your Dell, Lenovo | |
and HP drives packages up to date. The script reads the Dell, Lenovo and HP | |
SCCM driver pack site for models you have specified and then downloads | |
the corresponding latest driver packs and BIOS updates(Dell only). | |
.NOTES | |
FileName: DriverDownloadTool.ps1 | |
Blog: http://www.scconfigmgr.com | |
Author: Maurice Daly | |
Twitter: @Modaly_IT | |
Created: 2017-01-01 | |
Updated: 2017-06-09 | |
Version history: | |
3.9 - (2017-06-09) Script XML use optimisations. Lenovo BIOS extract and packaging. Minor bug fixes. | |
#> | |
#region Source: Startup.pss | |
#---------------------------------------------- | |
#region Import Assemblies | |
#---------------------------------------------- | |
[void][Reflection.Assembly]::Load('System.Windows.Forms, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089') | |
[void][Reflection.Assembly]::Load('System.Data, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089') | |
[void][Reflection.Assembly]::Load('System.Drawing, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a') | |
[void][Reflection.Assembly]::Load('System.DirectoryServices, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a') | |
#endregion Import Assemblies | |
#Define a Param block to use custom parameters in the project | |
#Param ($CustomParameter) | |
function Main { | |
Param ([String]$Commandline) | |
if ((Show-MainForm_psf) -eq 'OK') | |
{ | |
} | |
$script:ExitCode = 0 #Set the exit code for the Packager | |
} | |
#endregion Source: Startup.pss | |
#region Source: MainForm.psf | |
function Show-MainForm_psf | |
{ | |
#---------------------------------------------- | |
#region Import the Assemblies | |
#---------------------------------------------- | |
[void][reflection.assembly]::Load('System.Windows.Forms, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089') | |
[void][reflection.assembly]::Load('System.Data, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089') | |
[void][reflection.assembly]::Load('System.Drawing, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a') | |
[void][reflection.assembly]::Load('System.DirectoryServices, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a') | |
#endregion Import Assemblies | |
#---------------------------------------------- | |
#region Define SAPIEN Types | |
#---------------------------------------------- | |
try{ | |
[ProgressBarOverlay] | Out-Null | |
} | |
catch | |
{ | |
Add-Type -ReferencedAssemblies ('System.Windows.Forms', 'System.Drawing') -TypeDefinition @" | |
using System; | |
using System.Windows.Forms; | |
using System.Drawing; | |
namespace SAPIENTypes | |
{ | |
public class ProgressBarOverlay : System.Windows.Forms.ProgressBar | |
{ | |
public ProgressBarOverlay() : base() { SetStyle(ControlStyles.OptimizedDoubleBuffer | ControlStyles.AllPaintingInWmPaint, true); } | |
protected override void WndProc(ref Message m) | |
{ | |
base.WndProc(ref m); | |
if (m.Msg == 0x000F)// WM_PAINT | |
{ | |
if (Style != System.Windows.Forms.ProgressBarStyle.Marquee || !string.IsNullOrEmpty(this.Text)) | |
{ | |
using (Graphics g = this.CreateGraphics()) | |
{ | |
using (StringFormat stringFormat = new StringFormat(StringFormatFlags.NoWrap)) | |
{ | |
stringFormat.Alignment = StringAlignment.Center; | |
stringFormat.LineAlignment = StringAlignment.Center; | |
if (!string.IsNullOrEmpty(this.Text)) | |
g.DrawString(this.Text, this.Font, Brushes.Black, this.ClientRectangle, stringFormat); | |
else | |
{ | |
int percent = (int)(((double)Value / (double)Maximum) * 100); | |
g.DrawString(percent.ToString() + "%", this.Font, Brushes.Black, this.ClientRectangle, stringFormat); | |
} | |
} | |
} | |
} | |
} | |
} | |
public string TextOverlay | |
{ | |
get | |
{ | |
return base.Text; | |
} | |
set | |
{ | |
base.Text = value; | |
Invalidate(); | |
} | |
} | |
} | |
} | |
"@ -IgnoreWarnings | Out-Null | |
} | |
try{ | |
[FolderBrowserModernDialog] | Out-Null | |
} | |
catch | |
{ | |
Add-Type -ReferencedAssemblies ('System.Windows.Forms') -TypeDefinition @" | |
using System; | |
using System.Windows.Forms; | |
using System.Reflection; | |
namespace SAPIENTypes | |
{ | |
public class FolderBrowserModernDialog : System.Windows.Forms.CommonDialog | |
{ | |
private System.Windows.Forms.OpenFileDialog fileDialog; | |
public FolderBrowserModernDialog() | |
{ | |
fileDialog = new System.Windows.Forms.OpenFileDialog(); | |
fileDialog.Filter = "Folders|\n"; | |
fileDialog.AddExtension = false; | |
fileDialog.CheckFileExists = false; | |
fileDialog.DereferenceLinks = true; | |
fileDialog.Multiselect = false; | |
fileDialog.Title = "Select a folder"; | |
} | |
public string Title | |
{ | |
get { return fileDialog.Title; } | |
set { fileDialog.Title = value; } | |
} | |
public string InitialDirectory | |
{ | |
get { return fileDialog.InitialDirectory; } | |
set { fileDialog.InitialDirectory = value; } | |
} | |
public string SelectedPath | |
{ | |
get { return fileDialog.FileName; } | |
set { fileDialog.FileName = value; } | |
} | |
object InvokeMethod(Type type, object obj, string method, object[] parameters) | |
{ | |
MethodInfo methInfo = type.GetMethod(method, BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic); | |
return methInfo.Invoke(obj, parameters); | |
} | |
bool ShowOriginalBrowserDialog(IntPtr hwndOwner) | |
{ | |
FolderBrowserDialog folderBrowserDialog = new FolderBrowserDialog(); | |
folderBrowserDialog.Description = this.Title; | |
folderBrowserDialog.SelectedPath = !string.IsNullOrEmpty(this.SelectedPath) ? this.SelectedPath : this.InitialDirectory; | |
folderBrowserDialog.ShowNewFolderButton = false; | |
if (folderBrowserDialog.ShowDialog() == DialogResult.OK) | |
{ | |
fileDialog.FileName = folderBrowserDialog.SelectedPath; | |
return true; | |
} | |
return false; | |
} | |
protected override bool RunDialog(IntPtr hwndOwner) | |
{ | |
if (Environment.OSVersion.Version.Major >= 6) | |
{ | |
try | |
{ | |
bool flag = false; | |
System.Reflection.Assembly assembly = Assembly.Load("System.Windows.Forms, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089"); | |
Type typeIFileDialog = assembly.GetType("System.Windows.Forms.FileDialogNative").GetNestedType("IFileDialog", BindingFlags.NonPublic); | |
uint num = 0; | |
object dialog = InvokeMethod(fileDialog.GetType(), fileDialog, "CreateVistaDialog", null); | |
InvokeMethod(fileDialog.GetType(), fileDialog, "OnBeforeVistaDialog", new object[] { dialog }); | |
uint options = (uint)InvokeMethod(typeof(System.Windows.Forms.FileDialog), fileDialog, "GetOptions", null) | (uint)0x20; | |
InvokeMethod(typeIFileDialog, dialog, "SetOptions", new object[] { options }); | |
Type vistaDialogEventsType = assembly.GetType("System.Windows.Forms.FileDialog").GetNestedType("VistaDialogEvents", BindingFlags.NonPublic); | |
object pfde = Activator.CreateInstance(vistaDialogEventsType, fileDialog); | |
object[] parameters = new object[] { pfde, num }; | |
InvokeMethod(typeIFileDialog, dialog, "Advise", parameters); | |
num = (uint)parameters[1]; | |
try | |
{ | |
int num2 = (int)InvokeMethod(typeIFileDialog, dialog, "Show", new object[] { hwndOwner }); | |
flag = 0 == num2; | |
} | |
finally | |
{ | |
InvokeMethod(typeIFileDialog, dialog, "Unadvise", new object[] { num }); | |
GC.KeepAlive(pfde); | |
} | |
return flag; | |
} | |
catch | |
{ | |
return ShowOriginalBrowserDialog(hwndOwner); | |
} | |
} | |
else | |
return ShowOriginalBrowserDialog(hwndOwner); | |
} | |
public override void Reset() | |
{ | |
fileDialog.Reset(); | |
} | |
} | |
} | |
"@ -IgnoreWarnings | Out-Null | |
} | |
#endregion Define SAPIEN Types | |
#---------------------------------------------- | |
#region Generated Form Objects | |
#---------------------------------------------- | |
[System.Windows.Forms.Application]::EnableVisualStyles() | |
$MainForm = New-Object 'System.Windows.Forms.Form' | |
$ProductListBox = New-Object 'System.Windows.Forms.ListBox' | |
$SCConfigMgrLogo = New-Object 'System.Windows.Forms.PictureBox' | |
$DescriptionText = New-Object 'System.Windows.Forms.TextBox' | |
$RemoveItemsButton = New-Object 'System.Windows.Forms.Button' | |
$SelectionTabs = New-Object 'System.Windows.Forms.TabControl' | |
$OSTab = New-Object 'System.Windows.Forms.TabPage' | |
$PleaseNnoteText = New-Object 'System.Windows.Forms.TextBox' | |
$PleaseNoteLabel = New-Object 'System.Windows.Forms.Label' | |
$ArchitectureComboxBox = New-Object 'System.Windows.Forms.ComboBox' | |
$DownloadComboBox = New-Object 'System.Windows.Forms.ComboBox' | |
$PlatformComboBox = New-Object 'System.Windows.Forms.ComboBox' | |
$OSComboBox = New-Object 'System.Windows.Forms.ComboBox' | |
$ArchitectureCheckBox = New-Object 'System.Windows.Forms.Label' | |
$SelectDeployLabel = New-Object 'System.Windows.Forms.Label' | |
$OperatingSysLabel = New-Object 'System.Windows.Forms.Label' | |
$DownloadTypeLabel = New-Object 'System.Windows.Forms.Label' | |
$ManufacturerTab = New-Object 'System.Windows.Forms.TabPage' | |
$MicrosoftCheckBox = New-Object 'System.Windows.Forms.CheckBox' | |
$FindModelsButton = New-Object 'System.Windows.Forms.Button' | |
$PleaseSelectManufactLabel = New-Object 'System.Windows.Forms.Label' | |
$LenovoCheckBox = New-Object 'System.Windows.Forms.CheckBox' | |
$HPCheckBox = New-Object 'System.Windows.Forms.CheckBox' | |
$DellCheckBox = New-Object 'System.Windows.Forms.CheckBox' | |
$FullModelListBox = New-Object 'System.Windows.Forms.ListBox' | |
$AddToListButton = New-Object 'System.Windows.Forms.Button' | |
$AcerCheckbox = New-Object 'System.Windows.Forms.CheckBox' | |
$DriverStorageTab = New-Object 'System.Windows.Forms.TabPage' | |
$PackageBrowseButton = New-Object 'System.Windows.Forms.Button' | |
$PackagePathTextBox = New-Object 'System.Windows.Forms.TextBox' | |
$RepositoryBrowseButton = New-Object 'System.Windows.Forms.Button' | |
$RepositoryTextBox = New-Object 'System.Windows.Forms.TextBox' | |
$PleaseNoteStorageText = New-Object 'System.Windows.Forms.TextBox' | |
$PleaseNoteStorageLabel = New-Object 'System.Windows.Forms.Label' | |
$PackagePathLabel = New-Object 'System.Windows.Forms.Label' | |
$RepositoryLabel = New-Object 'System.Windows.Forms.Label' | |
$DistributionTab = New-Object 'System.Windows.Forms.TabPage' | |
$EnableBinaryDifCheckBox = New-Object 'System.Windows.Forms.CheckBox' | |
$DGGroupBox = New-Object 'System.Windows.Forms.GroupBox' | |
$DPGListBox = New-Object 'System.Windows.Forms.ListBox' | |
$DPGroupBox = New-Object 'System.Windows.Forms.GroupBox' | |
$DPListBox = New-Object 'System.Windows.Forms.ListBox' | |
$DriverCleanTab = New-Object 'System.Windows.Forms.TabPage' | |
$RemoveSourceLabel = New-Object 'System.Windows.Forms.Label' | |
$RemoveDriverSourceCheckbox = New-Object 'System.Windows.Forms.CheckBox' | |
$RemoveSupersededLabel = New-Object 'System.Windows.Forms.Label' | |
$RemoveLegacyDriverCheckbox = New-Object 'System.Windows.Forms.CheckBox' | |
$labelSelectingThisOptionW = New-Object 'System.Windows.Forms.Label' | |
$CleanUnusedCheckBox = New-Object 'System.Windows.Forms.CheckBox' | |
$SCConfigMgrLink = New-Object 'System.Windows.Forms.LinkLabel' | |
$SCCMDellTabControl = New-Object 'System.Windows.Forms.TabControl' | |
$ConfigMgrTabPage1 = New-Object 'System.Windows.Forms.TabPage' | |
$SiteCodeText = New-Object 'System.Windows.Forms.TextBox' | |
$SiteServerInput = New-Object 'System.Windows.Forms.TextBox' | |
$ConnectSCCMButton = New-Object 'System.Windows.Forms.Button' | |
$SiteCodeLabel = New-Object 'System.Windows.Forms.Label' | |
$SiteServerLabel = New-Object 'System.Windows.Forms.Label' | |
$ConfigMgrTabPage2 = New-Object 'System.Windows.Forms.TabPage' | |
$UseProxyServerCheckbox = New-Object 'System.Windows.Forms.CheckBox' | |
$ProxyPswdInput = New-Object 'System.Windows.Forms.TextBox' | |
$PasswordLabel = New-Object 'System.Windows.Forms.Label' | |
$ProxyUserInput = New-Object 'System.Windows.Forms.TextBox' | |
$UsernameLabel = New-Object 'System.Windows.Forms.Label' | |
$ProxyServerInput = New-Object 'System.Windows.Forms.TextBox' | |
$ProxyServerLabel = New-Object 'System.Windows.Forms.Label' | |
$ClearSelectionButton = New-Object 'System.Windows.Forms.Button' | |
$ModelProgressOverlay = New-Object 'SAPIENTypes.ProgressBarOverlay' | |
$ProgressBar = New-Object 'System.Windows.Forms.ProgressBar' | |
$ProgressListBox = New-Object 'System.Windows.Forms.ListBox' | |
$AutomationLabel = New-Object 'System.Windows.Forms.Label' | |
$StartDownloadButton = New-Object 'System.Windows.Forms.Button' | |
$SelectedLabel = New-Object 'System.Windows.Forms.Label' | |
$LoggingLabel = New-Object 'System.Windows.Forms.Label' | |
$ModelProgressLabel = New-Object 'System.Windows.Forms.Label' | |
$labelThisScriptIsUsedAtYo = New-Object 'System.Windows.Forms.Label' | |
$RepositoryBrowseFolderDialogue = New-Object 'SAPIENTypes.FolderBrowserModernDialog' | |
$PackageBrowseFolderDialogue = New-Object 'SAPIENTypes.FolderBrowserModernDialog' | |
$InitialFormWindowState = New-Object 'System.Windows.Forms.FormWindowState' | |
#endregion Generated Form Objects | |
#---------------------------------------------- | |
# User Generated Script | |
#---------------------------------------------- | |
$MainForm_Load = { | |
# Initialise Form | |
$MainForm.Visible = $true | |
Write-CMLogEntry -Value "======== INITIALISING LOG FILE & CHECKING PREREQUISITES ========" -Severity 1 | |
Write-CMLogEntry -Value "Info: Log File Location - $TempDirectory" -Severity 1 | |
If (($ScriptRelease -ne $null) -and ($ScriptRelease -lt $NewRelease)) | |
{ | |
Write-CMLogEntry -Value "Update Alert: Newer Version Available - $NewRelease" -Severity 2 -SkipGuiLog $true | |
Write-CMLogEntry -Value "Update Alert: Opening New Version Form" -Severity 2 -SkipGuiLog $true | |
Show-UpdateForm_psf | |
} | |
# Attempt ConfigMgr Site Code & MP Detection | |
Write-CMLogEntry -Value "Info: Checking WMI for ConfigMgr SMS_Authority Values" -Severity 1 -SkipGuiLog $true | |
$SCCMWMI = Get-CIMInstance -ClassName SMS_Authority -NameSpace root\ccm | |
if ($SCCMWMI.CurrentManagementPoint -ne $null) | |
{ | |
Write-CMLogEntry -Value "======== ConfigMgr Site Discovery ========" -Severity 1 | |
$SiteServerInput.Text = $SCCMWMI.CurrentManagementPoint | |
Write-CMLogEntry -Value "Info: ConfigMgr WMI Query Results - Site Server (Local MP) Found: $($SiteServerInput.Text)" -Severity 1 -SkipGuiLog $true | |
$SiteCodeText.Text = ($SCCMWMI.Name).TrimStart("SMS:") | |
Write-CMLogEntry -Value "Info: ConfigMgr WMI Query Results - Site Code Found: $($SiteCodeText.Text)" -Severity 1 -SkipGuiLog $true | |
ConnectSCCM | |
} | |
# Check PS Version Compatibilty | |
if ($PSVersionTable.PSVersion.Major -lt "3") | |
{ | |
Write-CMLogEntry -Value "======== COMPATIBILITY ISSUE DETECTED ========" -Severity 3 | |
Write-CMLogEntry -Value "Error: PowerShell Version Incompatible - Please Update PS Installation" -Severity 3 | |
} | |
# Check for 7Zip Installation for Acer Drivers | |
Write-CMLogEntry -Value "Info: Checking For 7-Zip Installation" -Severity 1 -SkipGuiLog $true | |
# Read registry installed applications | |
$64BitApps = Get-ChildItem -Path HKLM:\Software\Microsoft\Windows\CurrentVersion\Uninstall -Recurse | Get-ItemProperty | |
$32BitApps = Get-ChildItem -Path HKLM:\SOFTWARE\WOW6432Node\Microsoft\Windows\CurrentVersion\Uninstall -Recurse | Get-ItemProperty | |
foreach ($App in $64BitApps) | |
{ | |
if ($App.DisplayName -match "7-Zip") | |
{ | |
$7ZipInstalled = $true | |
} | |
} | |
foreach ($App in $32BitApps) | |
{ | |
if ($App.DisplayName -match "7-Zip") | |
{ | |
$7ZipInstalled = $true | |
} | |
} | |
if ($7ZipInstalled -eq $true) | |
{ | |
$AcerCheckbox.Enabled = $true | |
} | |
else | |
{ | |
$AcerCheckbox.Enabled = $false | |
Write-CMLogEntry -Value "======== ACER COMPATIBILITY ISSUE DETECTED ========" -Severity 3 | |
Write-CMLogEntry -Value "Error: Prerequisite 7-Zip Not Found - Acer Support Disabled" -Severity 3 | |
} | |
# // Default Selection - Edit this section for your standard paths etc | |
$OSComboBox.SelectedIndex = 2 | |
$PlatformComboBox.SelectedIndex = 1 | |
$ArchitectureComboxBox.SelectedIndex = 0 | |
$DownloadComboBox.SelectedIndex = 0 | |
#$PackagePathTextBox.Text = "\\SERVER\UNCPATH" | |
#$RepositoryTextBox.Text = "\\SERVER\UNCPATH" | |
} | |
$StartDownloadButton_Click = { | |
# Reset Progress Bar | |
$ProgressBar.Value = "0" | |
$ModelProgressOverlay.Value = "0" | |
$ProgressListBox.ForeColor = 'Black' | |
# Set Variables Retrieved From GUI | |
$ImportInto = [string]$PlatformComboBox.SelectedItem | |
Write-CMLogEntry -Value "Info: Importing Into Products: $ImportInto" -Severity 1 -SkipGuiLog $true | |
$DownloadType = [string]$DownloadComboBox.SelectedItem | |
Write-CMLogEntry -Value "Info: Download Type: $DownloadType" -Severity 1 -SkipGuiLog $true | |
$SiteCode = $SiteCodeText.Text | |
# Set Models | |
if ($($ProductListBox.SelectedItems).count -gt 0) | |
{ | |
$ImportModels = $ProductListBox.SelectedItems | |
} | |
else | |
{ | |
$ImportModels = $ProductListBox.Items | |
} | |
# Set Initial Validation State | |
$ValidationErrors = 0 | |
# ============ Validation Selection Details and Prerequisites ============== | |
# Reset Job Process Log Dialog | |
if (($ProgressListBox.ForeColor) -eq "Red") { $ProgressListBox.Items.Clear() } | |
# Validate Selected Models | |
if (($ImportModels.Count) -lt "1") | |
{ | |
Write-CMLogEntry -Value "Error: No Models Selected" -Severity 3 | |
$ValidationErrors++ | |
} | |
# Validate Repository Path For BIOS & Driver Downloads | |
if ((Test-Path -Path $RepositoryTextBox.Text) -eq $true) | |
{ | |
$RepositoryPath = [string]$RepositoryTextBox.Text | |
Write-CMLogEntry -Value "Pre-Check: Respository Path Set To $RepositoryPath" -Severity 1 | |
} | |
else | |
{ | |
Write-CMLogEntry -Value "Error: UNC Repository Path Specified Could Not Be Found $($RepositoryTextBox.Text)" -Severity 3 | |
$ValidationErrors++ | |
} | |
# Validate Package Path For ConfigMgr Driver Imports | |
if (($ImportInto -like "ConfigMgr*") -or ($ImportInto -like "Both*")) | |
{ | |
if ($DownloadType -ne "BIOS") | |
{ | |
if ((Test-Path -path $PackagePathTextBox.Text) -eq $true) | |
{ | |
$PackagePath = [string]$PackagePathTextBox.Text | |
} | |
else | |
{ | |
Write-CMLogEntry -Value "Error: UNC Package Path Specified Could Not Be Found $($PackagePathTextBox.Text)" -Severity 3 | |
$ValidationErrors++ | |
} | |
} | |
} | |
# Validate OS Selection | |
if (($OSComboBox).Text -ne $null) | |
{ | |
$WindowsVersion = (($OSComboBox).Text).Split(" ")[1] | |
} | |
else | |
{ | |
Write-CMLogEntry -Value "Error: Operating System Not Specified" -Severity 3 | |
$ValidationErrors++ | |
} | |
# Validate OS Architecture Selection | |
if (($ArchitectureComboxBox).Text -ne $null) | |
{ | |
$Architecture = "x" + ($ArchitectureComboxBox.Text).Trim(" bit") | |
} | |
else | |
{ | |
Write-CMLogEntry -Value "Error: Operating System Architecture Not Specified" -Severity 3 | |
$ValidationErrors++ | |
} | |
# Set Proxy Variables | |
if ($UseProxyServerCheckbox.Checked -eq $true) | |
{ | |
$ProxyUser = [string]$ProxyUserInput.Text | |
$ProxyPswd = ConvertTo-SecureString $([string]$ProxyPswdInput.Text) -AsPlainText -Force | |
$ProxyServer = [string]$ProxyServerInput.Text | |
$ProxyCred = New-Object -TypeName System.Management.Automation.PSCredential -ArgumentList $ProxyUser, $ProxyPswd | |
Write-CMLogEntry -Value "Info: Downloading through proxy $ProxyServer" -Severity 1 | |
$ProxyValidated = $true | |
} | |
# Download ScriptBlock | |
$DriverDownloadJob = { | |
Param ([string]$DriverRepositoryRoot, | |
[string]$Model, | |
[string]$DriverCab, | |
[string]$DriverDownloadURL, | |
$ProxyServer, | |
$ProxyCred) | |
# Start Driver Download | |
if ($ProxyCred -ne $null) | |
{ | |
Start-BitsTransfer -DisplayName "$Model-DriverDownload" -Source $DriverDownloadURL -Destination "$($DriverRepositoryRoot + $Model + '\Driver Cab\' + $DriverCab)" -RetryTimeout 90 -RetryInterval 180 -Asynchronous -ProxyList $ProxyServer -ProxyAuthentication NTLM -ProxyCredential $ProxyCred -ProxyUsage SystemDefault -Priority Foreground | |
} | |
else | |
{ | |
Start-BitsTransfer -DisplayName "$Model-DriverDownload" -Source $DriverDownloadURL -Destination "$($DriverRepositoryRoot + $Model + '\Driver Cab\' + $DriverCab)" -RetryTimeout 90 -RetryInterval 180 -Asynchronous | |
} | |
} | |
# MDT Import SriptBlock | |
$MDTImportJob = { | |
Param ([string]$PSDriveName, | |
[string]$MDTDriverPath, | |
[string]$Make, | |
[string]$Model, | |
[string]$DriverRevision, | |
[string]$OperatingSystemDir, | |
[string]$DriverExtractDest, | |
[string]$DeploymentShare, | |
[string]$Architecture) | |
Import-Module "C:\Program Files\Microsoft Deployment Toolkit\bin\MicrosoftDeploymentToolkit.psd1" | |
Write-CMLogEntry -Value "$($Product): Reading MDT PS Module from C:\Program Files\Microsoft Deployment Toolkit\bin\MicrosoftDeploymentToolkit.psd1" -Severity 1 -SkipGuiLog $true | |
New-PSDrive -Name $PSDriveName -PSProvider MDTProvider -Root $DeploymentShare | |
# =============== MDT Driver Import ==================== | |
if ($Make -eq "Dell") | |
{ | |
$DriverFolder = (Get-ChildItem -Path "$DriverExtractDest" -Recurse | Where-Object { ($_.PSisContainer -eq $true) -and ($_.Name -eq "$Architecture") } | Select -first 1).FullName | |
Write-CMLogEntry -Value "$($Product): Importing MDT Drivers from $DriverExtractDest" -Severity 1 -SkipGuiLog $true | |
Import-MDTDriver -path "$MDTDriverPath\$OperatingSystemDir\$Make\$Model\$DriverRevision" -SourcePath "$DriverFolder" | |
} | |
else | |
{ | |
Write-CMLogEntry -Value "$($Product): Importing MDT Drivers from $DriverExtractDest" -Severity 1 -SkipGuiLog $true | |
Import-MDTDriver -path "$MDTDriverPath\$OperatingSystemDir\$Make\$Model\$DriverRevision" -SourcePath "$DriverExtractDest" | |
} | |
} | |
# Move HP Driver Function | |
$MoveHPDrivers = { | |
Param ($HPExtract, | |
$DriverExtractDest) | |
Get-ChildItem -Path "$HPExtract" | Move-Item -Destination "$DriverExtractDest" -Verbose | |
#Remove-Item -Path "$HPExtract" | |
} | |
# Copy Drivers To Package Location (Standard) | |
$PackageDrivers = { | |
Param ($Make, | |
$DriverExtractDest, | |
$Architecture, | |
$DriverPackageDest) | |
if ($Make -eq "Dell") | |
{ | |
Copy-Item -Path $(Get-ChildItem -Path "$DriverExtractDest" -Recurse -Directory | Where-Object { $_.Name -eq "$Architecture" } | Select-Object -First 1).FullName -Destination "$DriverPackageDest" -Container -Recurse | |
Write-CMLogEntry -Value "$($Product): Copying Drivers from $DriverExtractDest to $DriverPackageDest" -Severity 1 -SkipGuiLog $True | |
} | |
else | |
{ | |
Copy-Item -Path "$DriverExtractDest" -Destination "$DriverPackageDest" -Container -Recurse | |
Write-CMLogEntry -Value "$($Product): Copying Drivers from $DriverExtractDest to $DriverPackageDest" -Severity 1 -SkipGuiLog $True | |
} | |
} | |
# Validate MDT PowerShell Commandlets / Install | |
if ((($ImportInto) -like ("MDT" -or "Both*")) -and ($ValidationErrors -eq 0)) | |
{ | |
# Validate MDT PS Commandlets | |
if ((Test-Path -Path $MDTPSCommandlets) -eq $true) | |
{ | |
# Import MDT Module | |
Write-CMLogEntry -Value "$($Product): Importing: MDT PowerShell Commandlets" -Severity 1 | |
Import-Module $MDTPSCommandlets | |
} | |
else | |
{ | |
Write-CMLogEntry -Value "Error: MDT PowerShell Commandlets file not found at $MDTPSCommandlets" -Severity 1 | |
$ValidationErrors++ | |
} | |
} | |
if ($ValidationErrors -eq 0) | |
{ | |
Write-CMLogEntry -Value "======== Starting Download Processes ========" -Severity 1 | |
if ($ProductListBox.SelectedItems -ge 1) | |
{ | |
Write-CMLogEntry -Value "Info: Models selected: $($ProductListBox.SelectedItems)" -Severity 1 | |
} | |
else | |
{ | |
Write-CMLogEntry -Value "Info: Models selected: $($ProductListBox.Items)" -Severity 1 | |
} | |
Write-CMLogEntry -Value "Info: Operating System specified: Windows $($WindowsVersion)" -Severity 1 | |
Write-CMLogEntry -Value "Info: Operating System architecture specified: $($Architecture)" -Severity 1 | |
Write-CMLogEntry -Value "Info: Site Code specified: $($SiteCode)" -Severity 1 | |
Write-CMLogEntry -Value "Info: Respository Path specified: $($RepositoryPath)" -Severity 1 | |
Write-CMLogEntry -Value "Info: Package Path specified: $($PackagePath)" -Severity 1 | |
# Operating System Version | |
$OperatingSystem = ("Windows " + $($WindowsVersion)) | |
if ($ProductListBox.SelectedItems.Count -ge 1) | |
{ | |
$TotalModelCount = $ProductListBox.SelectedItems.Count | |
} | |
else | |
{ | |
$TotalModelCount = $ProductListBox.Items.Count | |
} | |
$RemainingModels = $TotalModelCount | |
# Initialise Job Progress Bar | |
$ProgressBar.Maximum = $TotalModelCount | |
$ModelProgressOverlay.Maximum = $TotalModelCount | |
foreach ($Model in $ImportModels) | |
{ | |
Write-CMLogEntry -Value "======== Processing $Model Downloads ========" -Severity 1 | |
# Vendor Make | |
$Make = $($Model).split(" ")[0] | |
$Model = $($Model).TrimStart("$Make") | |
$Model = $Model.Trim() | |
# Lookup OS Build Number | |
if ($OSComboBox.Text -like "Windows 10 1*") | |
{ | |
Write-CMLogEntry -Value "Info: Windows 10 Build Lookup Required" -Severity 1 -SkipGuiLog $true | |
# Extract Windows 10 Version Number | |
$OSVersion = ([string]($OSComboBox).Text).Split(' ')[2] | |
# Get Windows Build Number From Version Hash Table | |
$OSBuild = $WindowsBuildHashTable.Item([int]$OSVersion) | |
Write-CMLogEntry -Value "Info: Windows 10 Build $OSBuild Identified For Driver Match" -Severity 1 -SkipGuiLog $true | |
} | |
Write-CMLogEntry -Value "Info: Starting Download,Extract And Import Processes For $Make Model: $($Model)" -Severity 1 -SkipGuiLog $true | |
# =================== DEFINE VARIABLES ===================== | |
# Directory used for driver and BIOS downloads | |
$DriverRepositoryRoot = ($RepositoryPath.Trimend("\") + "\$Make\") | |
# Directory used by ConfigMgr for driver packages | |
if (($ImportInto -like "*ConfigMgr*") -and ($DownloadType -ne "BIOS")) { $DriverPackageRoot = ($PackagePath.Trimend("\") + "\$Make\") } | |
# =================== VENDOR SPECIFIC UPDATES ==================== | |
if ($Make -eq "Dell") | |
{ | |
Write-CMLogEntry -Value "Info: Setting Dell Variables" -Severity 1 -SkipGuiLog $true | |
if ($global:DellModelCabFiles -eq $null) | |
{ | |
[xml]$DellModelXML = Get-Content -Path $TempDirectory\$DellXMLFile | |
# Set XML Object | |
$DellModelXML.GetType().FullName | |
$global:DellModelCabFiles = $DellModelXML.driverpackmanifest.driverpackage | |
} | |
$ModelURL = $DellDownloadBase + "/" + ($global:DellModelCabFiles | Where-Object { ((($_.SupportedOperatingSystems).OperatingSystem).osCode -like "*$WindowsVersion*") -and ($_.SupportedSystems.Brand.Model.Name -like "*$Model*") }).delta | |
$ModelURL = $ModelURL.Replace("\", "/") | |
$DriverDownload = $DellDownloadBase + "/" + ($global:DellModelCabFiles | Where-Object { ((($_.SupportedOperatingSystems).OperatingSystem).osCode -like "*$WindowsVersion*") -and ($_.SupportedSystems.Brand.Model.Name -like "*$Model") }).path | |
$DriverCab = (($global:DellModelCabFiles | Where-Object { ((($_.SupportedOperatingSystems).OperatingSystem).osCode -like "*$WindowsVersion*") -and ($_.SupportedSystems.Brand.Model.Name -like "*$Model") }).path).Split("/") | select -Last 1 | |
$DriverRevision = (($DriverCab).Split("-")[2]).Trim(".cab") | |
} | |
if ($Make -eq "HP") | |
{ | |
Write-CMLogEntry -Value "Info: Setting HP Variables" -Severity 1 -SkipGuiLog $true | |
if ($global:HPModelSoftPaqs -eq $null) | |
{ | |
[xml]$global:HPModelXML = Get-Content -Path $TempDirectory\$HPXMLFile | |
# Set XML Object | |
$global:HPModelXML.GetType().FullName | |
$global:HPModelSoftPaqs = $global:HPModelXML.NewDataSet.HPClientDriverPackCatalog.ProductOSDriverPackList.ProductOSDriverPack | |
} | |
if ($OSComboBox.Text -like "Windows 10 1*") | |
{ | |
$HPSoftPaqSummary = $global:HPModelSoftPaqs | Where-Object { ($_.SystemName -like "*$Model*") -and ($_.OSName -like "Windows*$(($OSComboBox.Text).Split(' ')[1])*$(($ArchitectureComboxBox.Text).Trim(' bit'))*$((($OSComboBox.Text).Split(' ')[2]).Trim())*") } | |
} | |
else | |
{ | |
$HPSoftPaqSummary = $global:HPModelSoftPaqs | Where-Object { ($_.SystemName -like "*$Model*") -and ($_.OSName -like "Windows*$(($OSComboBox.Text).Split(' ')[1])*$(($ArchitectureComboxBox.Text).Trim(' bit'))*") } | |
} | |
$HPSoftPaq = $HPSoftPaqSummary.SoftPaqID | |
$HPSoftPaqDetails = $global:HPModelXML.newdataset.hpclientdriverpackcatalog.softpaqlist.softpaq | Where-Object { $_.ID -eq "$HPSoftPaq" } | |
$ModelURL = $HPSoftPaqDetails.URL | |
# Replace FTP for HTTP for Bits Transfer Job | |
$DriverDownload = "http:" + ($HPSoftPaqDetails.URL).TrimStart("ftp:") | |
$DriverCab = $ModelURL | Split-Path -Leaf | |
$DriverRevision = "$($HPSoftPaqDetails.Version)" | |
} | |
if ($Make -eq "Lenovo") | |
{ | |
Write-CMLogEntry -Value "Info: Setting Lenovo Variables" -Severity 1 -SkipGuiLog $true | |
LenovoModelTypeFinder -Model $Model -OS $OS | |
Write-CMLogEntry -Value "Info: $Make $Model matching model type: $global:LenovoModelType" -Severity 1 -SkipGuiLog $false | |
if ($global:LenovoModelDrivers -ne $null) | |
{ | |
[xml]$global:LenovoModelXML = (New-Object System.Net.WebClient).DownloadString("$LenovoXMLSource") | |
# Set XML Object | |
$global:LenovoModelXML.GetType().FullName | |
$global:LenovoModelDrivers = $global:LenovoModelXML.Products | |
$LenovoDriver = (($global:LenovoModelDrivers.Product | Where-Object { $_.model -eq $Model }).driverPack | Where-Object { $_.id -eq "SCCM" })."#text" | |
} | |
if ($WindowsVersion -ne "7") | |
{ | |
Write-CMLogEntry -Value "Info: Looking Up Lenovo $Model URL For Windows Version win$(($WindowsVersion).Trim('.'))" -Severity 1 -SkipGuiLog $true | |
$ModelURL = (($global:LenovoModelDrivers.Product | Where-Object { ($_.model -eq "$Model") -and ($_.os -eq "win$(($WindowsVersion -replace '[.]', ''))") }).driverPack | Where-Object { $_.id -eq "SCCM" })."#text" | Select -First 1 | |
} | |
else | |
{ | |
Write-CMLogEntry -Value "Info: Looking Up Lenovo $Model URL For Windows Version win$(($WindowsVersion).Trim('.'))" -Severity 1 -SkipGuiLog $true | |
$ModelURL = (($global:LenovoModelDrivers.Product | Where-Object { ($_.model -eq "$Model") -and ($_.os -eq "win$WindowsVersion$(($ArchitectureComboxBox.Text).Split(' ')[0])") }).driverPack | Where-Object { $_.id -eq "SCCM" })."#text" | Select -First 1 | |
} | |
if ($DownloadType -ne "BIOS") | |
{ | |
if ($Architecture -eq "x86") | |
{ | |
$DriverDownload = FindDriver -URI $ModelURL -os $WindowsVersion -64bit $false -ProxyServer $ProxyServer -ProxyCred $ProxyCred | |
} | |
else | |
{ | |
$DriverDownload = FindDriver -URI $ModelURL -os $WindowsVersion -64bit $true -ProxyServer $ProxyServer -ProxyCred $ProxyCred | |
} | |
If ($DriverDownload -ne "badlink") | |
{ | |
$DriverCab = $DriverDownload | Split-Path -Leaf | |
$DriverRevision = ($DriverCab.Split("_") | Select -Last 1).Trim(".exe") | |
} | |
else | |
{ | |
Write-CMLogEntry -Value "Error: Unable to find driver for $Make $Model" -Severity 1 -SkipGuiLog $false | |
} | |
} | |
} | |
if ($Make -eq "Acer") | |
{ | |
Write-CMLogEntry -Value "Info: Setting Acer Variables" -Severity 1 -SkipGuiLog $true | |
$AcerModelDrivers = (Invoke-WebRequest -Uri $AcerSCCMSource).Links | |
$AcerDriver = $AcerModelDrivers | Where-Object { $_.outerText -match $Model } | |
$ModelURL = (($AcerDriver | Where-Object { $_.OuterText -like "*$($WindowsVersion)*$(($ArchitectureComboxBox.Text).Split(' ')[0])*" }).href) | |
$DriverDownload = "http:" + $ModelURL | |
$DriverCab = $DriverDownload | Split-Path -Leaf | |
$DriverRevision = "NA" | |
} | |
if ($Make -eq "Microsoft") | |
{ | |
Write-CMLogEntry -Value "Info: Setting Microsoft Variables" -Severity 1 -SkipGuiLog $true | |
[xml]$MicrosoftModelXML = (New-Object System.Net.WebClient).DownloadString("$MicrosoftXMLSource") | |
# Set XML Object | |
$MicrosoftModelXML.GetType().FullName | |
$MicrosoftModelDrivers = $MicrosoftModelXML.Drivers | |
$ModelURL = ((($MicrosoftModelDrivers.Model | Where-Object { ($_.name -match "$Model") }).OSSupport) | Where-Object { $_.Name -eq "win$(($WindowsVersion).Trim("."))" }).DownloadURL | |
$DriverDownload = Get-RedirectedUrl -URL "$ModelURL" -ErrorAction Continue -WarningAction Continue | |
$DriverCab = $DriverDownload | Split-Path -Leaf | |
$DriverRevision = ($DriverCab.Split("_") | Select -Last 2).Trim(".msi")[0] | |
} | |
if ($DownloadType -ne "BIOS") | |
{ | |
# Driver variables & switches | |
$DriverSourceCab = ($DriverRepositoryRoot + $Model + "\Driver Cab\" + $DriverCab) | |
$DriverPackageDir = ($DriverCab).Substring(0, $DriverCab.length - 4) | |
$DriverCabDest = $DriverPackageRoot + $DriverPackageDir | |
} | |
# Cater for Dell driver packages (both x86 and x64 drivers contained within a single package) | |
if ($Make -eq "Dell") | |
{ | |
$DriverExtractDest = ("$DriverRepositoryRoot" + $Model + "\" + "Windows$WindowsVersion-$DriverRevision") | |
Write-CMLogEntry -Value "Info: Driver Extract Location Set - $DriverExtractDest" -Severity 1 -SkipGuiLog $true | |
$DriverPackageDest = ("$DriverPackageRoot" + "$Model" + "-" + "Windows$WindowsVersion-$Architecture-$DriverRevision") | |
Write-CMLogEntry -Value "Info: Driver Package Location Set - $DriverPackageDest" -Severity 1 -SkipGuiLog $true | |
} | |
else | |
{ | |
If ($OSBuild -eq $null) | |
{ | |
$DriverExtractDest = ("$DriverRepositoryRoot" + $Model + "\" + "Windows$WindowsVersion-$Architecture-$DriverRevision") | |
Write-CMLogEntry -Value "Info: Driver Extract Location Set - $DriverExtractDest" -Severity 1 -SkipGuiLog $true | |
$DriverPackageDest = ("$DriverPackageRoot" + "$Model" + "\" + "Windows$WindowsVersion-$Architecture-$DriverRevision") | |
Write-CMLogEntry -Value "Info: Driver Package Location Set - $DriverPackageDest" -Severity 1 -SkipGuiLog $true | |
} | |
else | |
{ | |
$DriverExtractDest = ("$DriverRepositoryRoot" + $Model + "\" + "Windows$WindowsVersion-$OSBuild-$Architecture-$DriverRevision") | |
Write-CMLogEntry -Value "Info: Driver Extract Location Set - $DriverExtractDest" -Severity 1 -SkipGuiLog $true | |
$DriverPackageDest = ("$DriverPackageRoot" + "$Model" + "\" + "Windows$WindowsVersion-$OSBuild-$Architecture-$DriverRevision") | |
Write-CMLogEntry -Value "Info: Driver Package Location Set - $DriverPackageDest" -Severity 1 -SkipGuiLog $true | |
} | |
# Replace HP Model Slash | |
$DriverExtractDest = $DriverExtractDest -replace '/', '-' | |
$DriverPackageDest = $DriverPackageDest -replace '/', '-' | |
} | |
# Allow for both Driver & Standard Program Packages destinations | |
if ($ImportInto -like "*Driver*") | |
{ | |
$DriverPackageDest = $DriverPackageDest + "\DriverPkg\" | |
} | |
if ($ImportInto -like "*Standard*") | |
{ | |
$DriverPackageDest = $DriverPackageDest + "\StandardPkg\" | |
} | |
# Driver variables & switches | |
$DriverCategoryName = $Make + "-" + $Model + "-" + $OperatingSystem + "-" + $DriverRevision | |
# =================== INITIATE DOWNLOADS =================== | |
if ($ImportInto -ne "MDT") | |
{ | |
# Product Type Display | |
if ($ImportInto -eq "Download Only") | |
{ | |
$Product = "Download Only" | |
} | |
else | |
{ | |
$Product = "ConfigMgr" | |
} | |
if ($DownloadType -ne "Drivers") | |
{ | |
Write-CMLogEntry -Value "======== $MODEL BIOS PROCESSING STARTED ========" -Severity 1 | |
if ($Make -eq "Dell") | |
{ | |
# ================= Dell BIOS Upgrade Download ================== | |
$DellBIOSDownload = DellBiosFinder -Model $Model | |
$BIOSDownload = $DellDownloadBase + "/" + $($DellBIOSDownload.Path) | |
$BIOSVer = $DellBIOSDownload.DellVersion | |
Write-CMLogEntry -Value "Info: Latest available BIOS version is $BIOSVer" -Severity 1 | |
$BIOSFile = $DellBIOSDownload.Path | Split-Path -Leaf | |
$BIOSVerDir = $BIOSVer -replace '\.', '-' | |
$BIOSUpdateRoot = ($DriverRepositoryRoot + $Model + "\BIOS\" + $BIOSVerDir + "\") | |
if (($BIOSDownload -like "*.exe") -and ($Make -eq "Dell")) | |
{ | |
Write-CMLogEntry -Value "Info: BIOS Download URL Found: $BIOSDownload" -Severity 2 | |
# Check for destination directory, create if required and download the BIOS upgrade file | |
if ((Test-Path -Path "$($DriverRepositoryRoot + $Model + '\BIOS\' + $BIOSVerDir + '\' + $BIOSFile)") -eq $false) | |
{ | |
If ((Test-Path -Path $BIOSUpdateRoot) -eq $false) | |
{ | |
Write-CMLogEntry -Value "Info: Creating $BIOSUpdateRoot folder" -Severity 1 | |
New-Item -Path $BIOSUpdateRoot -ItemType Directory | |
} | |
Write-CMLogEntry -Value "Info: Downloading $($BIOSFile) BIOS update file" -Severity 1 | |
if ($UseProxyServerCheckbox.Checked -eq $true) | |
{ | |
Start-BitsTransfer $BIOSDownload -Destination "$($BIOSUpdateRoot + $BIOSFile)" -RetryTimeout 90 -RetryInterval 180 -ProxyList $ProxyServer -ProxyList $ProxyServer -ProxyAuthentication NTLM -ProxyCredential $ProxyCred -ProxyUsage SystemDefault | |
} | |
else | |
{ | |
Start-BitsTransfer $BIOSDownload -Destination "$($BIOSUpdateRoot + $BIOSFile)" -RetryTimeout 90 -RetryInterval 180 | |
} | |
} | |
else | |
{ | |
Write-CMLogEntry -Value "Info: Skipping $BIOSFile... File already downloaded." -Severity 2 | |
} | |
} | |
if ($Product -ne "Download Only") | |
{ | |
# ================= Create BIOS Update Package ================== | |
Set-Location -Path ($SiteCode + ":") | |
$BIOSUpdatePackage = ("BIOS Update - " + "$Make" + " " + $Model) | |
$BIOSModelPackage = Get-CMPackage | Where-Object { $_.Name -match $BIOSUpdatePackage } | Sort-Object SourceDate -Descending | select -First 1 | |
if (($BIOSModelPackage.Version -ne $BIOSVer) -or ($BIOSModelPackage -eq $null)) | |
{ | |
Write-CMLogEntry -Value "$($Product): Creating BIOS Package" -Severity 1 | |
New-CMPackage -Name "$BIOSUpdatePackage" -Path "$BIOSUpdateRoot" -Description "$Make $Model BIOS Updates" -Manufacturer "$Make" -Language English -version $BIOSVer | |
if ($EnableBinaryDifCheckBox.Checked -eq $true) | |
{ | |
Write-CMLogEntry -Value "$($Product): Enabling Binary Delta Replication" -Severity 1 | |
Set-CMPackage -Name "$BIOSUpdatePackage" -EnableBinaryDeltaReplication $true | |
} | |
Set-Location -Path $TempDirectory | |
# ================= Dell Flash 64 Upgrade Download ================== | |
$FlashUtilDir = $DriverRepositoryRoot + "\Flash64Utility\" | |
$Flash64BitDownload = (Invoke-WebRequest -Uri $Dell64BIOSUtil).links | Where-Object { $_.OuterText -eq "Here" } | |
$Flash64BitZip = $($FlashUtilDir + $(($Flash64BitDownload).href | Split-Path -Leaf)) | |
if ((Test-Path -Path $FlashUtilDir) -eq $false) | |
{ | |
New-Item -ItemType Directory -Path $FlashUtilDir | Out-Null | |
Write-CMLogEntry -Value "Info: Creating Directory - $FlashUtilDir" -Severity 1 -SkipGuiLog $True | |
Write-CMLogEntry -Value "Info: Downloading Dell Flash64 EXE From $($Flash64BitDownload.href) Using BITS" -Severity 1 -SkipGuiLog $True | |
if ($UseProxyServerCheckbox.Checked -eq $true) | |
{ | |
Start-BitsTransfer ($Flash64BitDownload.href) -Destination "$($Flash64BitZip)" -RetryTimeout 90 -RetryInterval 180 -ProxyList $ProxyServer -ProxyList $ProxyServer -ProxyAuthentication NTLM -ProxyCredential $ProxyCred -ProxyUsage SystemDefault | |
} | |
else | |
{ | |
Start-BitsTransfer ($Flash64BitDownload.href) -Destination "$($Flash64BitZip)" -RetryTimeout 90 -RetryInterval 180 | |
} | |
# Unzip Flash64 Exe | |
Add-Type -assembly "system.io.compression.filesystem" | |
[io.compression.zipfile]::ExtractToDirectory("$($Flash64BitZip)", "$($FlashUtilDir)") | |
Write-CMLogEntry -Value "Info: Unzipping Dell Flash64 EXE" -Severity 1 -SkipGuiLog $True | |
} | |
$Flash64BitExe = Get-ChildItem -Path "$($FlashUtilDir)" -Filter *.exe -File | |
Get-ChildItem -Path "$($FlashUtilDir)" -Filter *.EXE -File | Copy-Item -Destination "$($BIOSUpdateRoot)" | |
Write-CMLogEntry -Value "Info: Copying Dell Flash64Bit EXE To $BIOSUpdateRoot" -Severity 1 -SkipGuiLog $True | |
# =============== Distrubute Content ================= | |
Set-Location -Path ($SiteCode + ":") | |
$SCCMPackage = Get-CMPackage -Name $BIOSUpdatePackage | Where-Object { $_.Version -eq $BIOSVer } | |
DistributeContent -Product $Product -Package $SCCMPackage.PackageID -ImportInto $ImportInto | |
Write-CMLogEntry -Value "$($Product): BIOS Update Package $($SCCMPackage.PackageID) Created & Distributing" -Severity 1 | |
Set-Location -Path $TempDirectory | |
} | |
else | |
{ | |
Write-CMLogEntry -Value "$($Product): BIOS package already exists" -Severity 1 | |
} | |
} | |
} | |
if ($Make -eq "Lenovo") | |
{ | |
# ================= Lenovo BIOS Upgrade Download ================== | |
Write-CMLogEntry -Value "Info: Retrieving BIOS Download URL For $Make Client Model: $($Model)" -Severity 1 | |
Set-Location -Path $TempDirectory | |
Write-CMLogEntry -Value "Info: Attempting to find download URL using LenovoBiosFinder function" -Severity 1 -SkipGuiLog $true | |
$BIOSDownload = LenovoBiosFinder -Model $Model -OS $WindowsVersion | |
if ($BIOSDownload -ne $null) | |
{ | |
# Download Lenovo BIOS Details XML | |
if ($ProxyCheck.StatusDescription -eq "OK") | |
{ | |
Start-BitsTransfer -Source $($BIOSDownload.Location) -Destination $TempDirectory -RetryInterval 60 -RetryTimeout 180 -ProxyList $ProxyServer -ProxyAuthentication NTLM -ProxyCredential $ProxyCred -ProxyUsage SystemDefault -Priority Foreground | |
} | |
else | |
{ | |
Start-BitsTransfer -Source $($BIOSDownload.Location) -Destination $TempDirectory -RetryInterval 60 -RetryTimeout 180 | |
} | |
$LenovoBIOSDetails = (Select-Xml -Path ($TempDirectory + "\" + ($BIOSDownload.Location | Split-Path -leaf)) -XPath "/").Node.Package | |
$BIOSUpdatePackage = ("BIOS Update - " + "$Make" + " " + $Model + " ($global:LenovoModelType)") | |
Set-Location -Path ($SiteCode + ":") | |
$BIOSModelPackage = Get-CMPackage | Where-Object { $_.Name -match $BIOSUpdatePackage } | Sort-Object SourceDate -Descending | select -First 1 | |
Set-Location -Path $TempDirectory | |
if (($BIOSModelPackage.Version -ne $BIOSVer) -or ($LenovoBIOSDetails.Name -ne $null)) | |
{ | |
$BIOSFile = ($LenovoBIOSDetails.ExtractCommand).Split(" ")[0] | |
Write-CMLogEntry -Value "Info: Found exe file link: $BIOSFile" -Severity 1 | |
$BIOSVer = $LenovoBIOSDetails.version | |
Write-CMLogEntry -Value "Info: BIOS version is $BIOSVer" -Severity 1 | |
$BIOSUpdateRoot = ($DriverRepositoryRoot + $Model + "\BIOS\" + $BIOSVer + "\") | |
Write-CMLogEntry -Value "Info: BIOS update directory set to $BIOSUpdateRoot" -Severity 1 | |
# Check for destination directory, create if required and download the BIOS upgrade file | |
if ((Test-Path -Path "$($BIOSUpdateRoot + '\' + $BIOSFile)") -eq $false) | |
{ | |
New-Item -Path $BIOSUpdateRoot -ItemType Directory | |
$BIOSFileDownload = ($BIOSDownload.Location | Split-Path -Parent) + "/$BIOSFile" | |
# Correct slash direction issues | |
$BIOSFileDownload = $BIOSFileDownload.Replace("\", "/") | |
Write-CMLogEntry -Value "Info: Downloading BIOS update file from $BIOSFileDownload" -Severity 1 | |
if ($UseProxyServerCheckbox.Checked -eq $true) | |
{ | |
Start-BitsTransfer $BIOSFileDownload -Destination "$($BIOSUpdateRoot + $BIOSFile)" -RetryTimeout 90 -RetryInterval 180 -ProxyList $ProxyServer -ProxyList $ProxyServer -ProxyAuthentication NTLM -ProxyCredential $ProxyCred -ProxyUsage SystemDefault | |
} | |
else | |
{ | |
Start-BitsTransfer $BIOSFileDownload -Destination "$($BIOSUpdateRoot + $BIOSFile)" -RetryTimeout 90 -RetryInterval 180 | |
} | |
# =============== Extract BIOS Files ================= | |
$BIOSExtractSwitches = ((($LenovoBIOSDetails.ExtractCommand).TrimStart("$BIOSFile")).Trim()).Replace("%PACKAGEPATH%", $BIOSUpdateRoot) | |
Write-CMLogEntry -Value "Info: BIOS Switches = $BIOSExtractSwitches" -Severity 1 | |
Start-Process -FilePath $($BIOSUpdateRoot + $BIOSFile) -ArgumentList $BIOSExtractSwitches -Wait | |
if ((Get-ChildItem -Path $BIOSUpdateRoot).count -eq "1") | |
{ | |
# Cater for BIOS extract issues with UNC paths | |
$BIOSExtractSwitches = ((($LenovoBIOSDetails.ExtractCommand).TrimStart("$BIOSFile")).Trim()).Replace("%PACKAGEPATH%", ($TempDirectory + "\$Model\$BIOS\$BIOSVer")) | |
Start-Process -FilePath $("$BIOSUpdateRoot" + $BIOSFile) -ArgumentList $BIOSExtractSwitches -Wait | |
Write-CMLogEntry -Value "Info: Copying extracted files to $BIOSUpdateRoot" -Severity 1 | |
Get-ChildItem -Path ($TempDirectory + "\$Model\$BIOS\$BIOSVer") | Copy-Item -Destination $BIOSUpdateRoot | |
} | |
Write-CMLogEntry -Value "Info: Removing source BIOS exe file" -Severity 1 -SkipGuiLog $true | |
Get-ChildItem -Path "$BIOSUpdateRoot" -Filter "*.exe" | Where-Object { $_.Name -eq $BIOSFile } | Remove-Item | |
If ($ImportInto -notmatch "Download") | |
{ | |
# =============== Create Package ================= | |
Set-Location -Path ($SiteCode + ":") | |
Write-CMLogEntry -Value "$($Product): Creating BIOS Package" -Severity 1 | |
New-CMPackage -Name "$BIOSUpdatePackage" -Path "$BIOSUpdateRoot" -Description "$Make $Model BIOS Updates" -Manufacturer "$Make" -Language English -version $LenovoBIOSDetails.Version | |
if ($EnableBinaryDifCheckBox.Checked -eq $true) | |
{ | |
Write-CMLogEntry -Value "$($Product): Enabling Binary Delta Replication" -Severity 1 | |
Set-CMPackage -Name "$BIOSUpdatePackage" -EnableBinaryDeltaReplication $true | |
} | |
# =============== Distrubute Content ================= | |
Set-Location -Path ($SiteCode + ":") | |
$SCCMPackage = Get-CMPackage -Name $BIOSUpdatePackage | Where-Object { $_.Version -eq $BIOSVer } | |
DistributeContent -Product $Product -Package $SCCMPackage.PackageID -ImportInto "Standard" | |
Write-CMLogEntry -Value "$($Product): BIOS Update Package $($SCCMPackage.PackageID) Created & Distributing" -Severity 1 | |
} | |
Set-Location -Path $TempDirectory | |
} | |
else | |
{ | |
Write-CMLogEntry -Value "Info: BIOS package already exists" -Severity 2 | |
} | |
} | |
} | |
else | |
{ | |
Write-CMLogEntry -Value "Error: Unable to find BIOS link" -Severity 2 | |
} | |
Set-Location -Path $TempDirectory | |
} | |
} | |
Write-CMLogEntry -Value "======== $Model BIOS PROCESSING FINISHED ========" -Severity 1 | |
} | |
if (($DownloadType -ne "BIOS") -and ($ImportInto -ne "MDT")) | |
{ | |
Write-CMLogEntry -Value "======== $PRODUCT $Model DRIVER PROCESSING STARTED ========" -Severity 1 | |
# =============== ConfigMgr Driver Cab Download ================= | |
Write-CMLogEntry -Value "$($Product): Retrieving ConfigMgr Driver Pack Site For $Make $Model" -Severity 1 | |
Write-CMLogEntry -Value "$($Product): URL Found: $ModelURL" -Severity 1 | |
if (($ModelURL -ne $Null) -and ($ModelURL -ne "badLink")) | |
{ | |
# Cater for HP / Model Issue | |
$Model = $Model -replace '/', '-' | |
$Model = $Model.Trim() | |
Set-Location -Path $TempDirectory | |
# Check for destination directory, create if required and download the driver cab | |
if ((Test-Path -Path $("$DriverRepositoryRoot" + "$Model" + "\Driver Cab\" + "$DriverCab")) -eq $false) | |
{ | |
Write-CMLogEntry -Value "$($Product): Creating $Model download folder" -Severity 1 | |
if ((Test-Path -Path $("$DriverRepositoryRoot" + "$Model" + "\Driver Cab")) -eq $false) | |
{ | |
Write-CMLogEntry -Value "$($Product): Creating $("$DriverRepositoryRoot" + "$Model" + "\Driver Cab") folder " -Severity 1 | |
New-Item -ItemType Directory -Path $("$DriverRepositoryRoot" + "$Model" + "\Driver Cab") | |
} | |
Write-CMLogEntry -Value "$($Product): Downloading $DriverCab driver cab file" -Severity 1 | |
Write-CMLogEntry -Value "$($Product): Downloading from URL: $DriverDownload" -Severity 1 | |
Start-Job -Name "$Model-DriverDownload" -ScriptBlock $DriverDownloadJob -ArgumentList ($DriverRepositoryRoot, $Model, $DriverCab, $DriverDownload, $ProxyServer, $ProxyCred) | |
sleep -Seconds 5 | |
$BitsJob = Get-BitsTransfer | Where-Object { $_.DisplayName -match "$Model-DriverDownload" } | |
while (($BitsJob).JobState -eq "Connecting") | |
{ | |
Write-CMLogEntry -Value "$($Product): Establishing Connection to $DriverDownload" -Severity 1 | |
sleep -seconds 30 | |
} | |
while (($BitsJob).JobState -eq "Transferring") | |
{ | |
$PercentComplete = [int](($BitsJob.BytesTransferred * 100)/$BitsJob.BytesTotal); | |
Write-CMLogEntry -Value "$($Product): Downloaded $([int]((($BitsJob).BytesTransferred)/ 1MB)) MB of $([int]((($BitsJob).BytesTotal)/ 1MB)) MB ($PercentComplete%). Next update in 30 seconds." -Severity 1 | |
sleep -seconds 30 | |
} | |
Get-BitsTransfer | Where-Object { $_.DisplayName -eq "$Model-DriverDownload" } | Complete-BitsTransfer | |
Write-CMLogEntry -Value "$($Product): Driver Revision: $DriverRevision" -Severity 1 | |
} | |
else | |
{ | |
Write-CMLogEntry -Value "$($Product): Skipping $DriverCab... Driver pack already downloaded." -Severity 1 | |
} | |
# Cater for HP / Model Issue | |
$Model = $Model -replace '/', '-' | |
if (((Test-Path -Path "$($DriverRepositoryRoot + "$Model" + '\Driver Cab\' + $DriverCab)") -eq $true) -and ($DriverCab -ne $null)) | |
{ | |
Write-CMLogEntry -Value "$($Product): $DriverCab File Exists - Processing Driver Package" -Severity 1 -SkipGuiLog $true | |
# =============== Create Driver Package + Import Drivers ================= | |
if ((Test-Path -Path "$DriverExtractDest") -eq $false) | |
{ | |
New-Item -ItemType Directory -Path "$($DriverExtractDest)" | |
} | |
if ((Get-ChildItem -Path "$DriverExtractDest" -Recurse -Filter *.inf -File).Count -eq 0) | |
{ | |
Write-CMLogEntry -Value "==================== $PRODUCT DRIVER EXTRACT ====================" -Severity 1 | |
Write-CMLogEntry -Value "$($Product): Expanding Driver CAB Source File: $DriverCab" -Severity 1 | |
Write-CMLogEntry -Value "$($Product): Driver CAB Destination Directory: $DriverExtractDest" -Severity 1 | |
if ($Make -eq "Dell") | |
{ | |
Write-CMLogEntry -Value "$($Product): Extracting $Make Drivers to $DriverExtractDest" -Severity 1 | |
Expand "$DriverSourceCab" -F:* "$DriverExtractDest" | |
} | |
if ($Make -eq "HP") | |
{ | |
# Driver Silent Extract Switches | |
$HPTemp = $TempDirectory + "\" + $Model + "\Win" + $WindowsVersion + $Architecture | |
$HPTemp = $HPTemp -replace '/', '-' | |
# HP Work Around For Long Dir | |
if ((($HPTemp).Split("-").Count) -gt "1") | |
{ | |
$HPTemp = ($HPTemp).Split("-")[0] | |
} | |
Write-CMLogEntry -Value "$($Product): Extracting $Make Drivers to $HPTemp" -Severity 1 | |
$HPSilentSwitches = "-PDF -F" + "$HPTemp" + " -S -E" | |
Write-CMLogEntry -Value "$($Product): Using $Make Silent Switches: $HPSilentSwitches" -Severity 1 -SkipGuiLog $true | |
Start-Process -FilePath "$($DriverRepositoryRoot + $Model + '\Driver Cab\' + $DriverCab)" -ArgumentList $HPSilentSwitches -Verb RunAs | |
$DriverProcess = ($DriverCab).Substring(0, $DriverCab.length - 4) | |
# Wait for HP SoftPaq Process To Finish | |
While ((Get-Process).name -contains $DriverProcess) | |
{ | |
Write-CMLogEntry -Value "$($Product): Waiting For Extract Process (Process: $DriverProcess) To Complete.. Next Check In 30 Seconds" -Severity 1 | |
sleep -Seconds 30 | |
} | |
# Move HP Extracted Drivers To UNC Share | |
$HPExtract = Get-ChildItem -Path $HPTemp -Directory | |
# Loop through the HP extracted driver folders to find the extracted folders and reduce directory path | |
while ($HPExtract.Count -eq 1) | |
{ | |
$HPExtract = Get-ChildItem -Path $HPExtract.FullName -Directory | |
} | |
# Set HP extracted folder | |
$HPExtract = $HPExtract.FullName | Split-Path -Parent | Select -First 1 | |
Write-CMLogEntry -Value "$($Product): HP Driver Source Directory Set To $HPExtract" -Severity 1 | |
if ((Test-Path -Path "$HPExtract") -eq $true) | |
{ | |
Start-Job -Name "$Model-Driver-Move" -ScriptBlock $MoveHPDrivers -ArgumentList ($HPExtract, $DriverExtractDest) | |
while ((Get-Job -Name "$Model-Driver-Move").State -eq "Running") | |
{ | |
Write-CMLogEntry -Value "$($Product): Moving $Make $Model $OperatingSystem $Architecture Driver.. Next Check In 30 Seconds" -Severity 1 | |
sleep -seconds 30 | |
} | |
} | |
else | |
{ | |
Write-CMLogEntry -Value "ERROR: Issues occured during the $Make $Model extract process" -Severity 3 | |
} | |
} | |
if ($Make -eq "Lenovo") | |
{ | |
# Driver Silent Extract Switches | |
$LenovoSilentSwitches = "/VERYSILENT /DIR=" + '"' + $DriverExtractDest + '"' + ' /Extract="Yes"' | |
Write-CMLogEntry -Value "$($Product): Using $Make Silent Switches: $LenovoSilentSwitches" -Severity 1 -SkipGuiLog $true | |
Write-CMLogEntry -Value "$($Product): Extracting $Make Drivers to $DriverExtractDest" -Severity 1 | |
Start-Process -FilePath "$($DriverRepositoryRoot + $Model + '\Driver Cab\' + $DriverCab)" -ArgumentList $LenovoSilentSwitches -Verb RunAs | |
$DriverProcess = ($DriverCab).Substring(0, $DriverCab.length - 4) | |
# Wait for Lenovo Driver Process To Finish | |
While ((Get-Process).name -contains $DriverProcess) | |
{ | |
Write-CMLogEntry -Value "$($Product): Waiting For Extract Process (Process: $DriverProcess) To Complete.. Next Check In 60 Seconds" -Severity 1 | |
sleep -seconds 30 | |
} | |
} | |
if ($Make -eq "Acer") | |
{ | |
# Driver Silent Extract Switches | |
$AcerSilentSwitches = "x " + '"' + $($DriverRepositoryRoot + $Model + '\Driver Cab\' + $DriverCab) + '"' + " -O" + '"' + $DriverExtractDest + '"' | |
Write-CMLogEntry -Value "$($Product): Using $Make Silent Switches: $AcerSilentSwitches" -Severity 1 -SkipGuiLog $true | |
Write-CMLogEntry -Value "$($Product): Extracting $Make Drivers to $DriverExtractDest" -Severity 1 | |
$DriverProcess = Start-Process 'C:\Program Files\7-Zip\7z.exe' -ArgumentList $AcerSilentSwitches -PassThru -NoNewWindow | |
# Wait for Acer Driver Process To Finish | |
While ((Get-Process).ID -eq $DriverProcess.ID) | |
{ | |
Write-CMLogEntry -Value "$($Product): Waiting For Extract Process (Process ID: $($DriverProcess.ID)) To Complete.. Next Check In 60 Seconds" -Severity 1 | |
sleep -seconds 30 | |
} | |
} | |
if ($Make -eq "Microsoft") | |
{ | |
# Driver Silent Extract Switches | |
$MicrosoftSilentSwitches = "/a" + '"' + $($DriverRepositoryRoot + $Model + "\Driver Cab\" + $DriverCab) + '"' + '/QN TARGETDIR="' + $DriverExtractDest + '"' | |
Write-CMLogEntry -Value "$($Product): Extracting $Make Drivers to $DriverExtractDest" -Severity 1 | |
$DriverProcess = Start-Process msiexec.exe -ArgumentList $MicrosoftSilentSwitches -PassThru | |
# Wait for Microsoft Driver Process To Finish | |
While ((Get-Process).ID -eq $DriverProcess.ID) | |
{ | |
Write-CMLogEntry -Value "$($Product): Waiting For Extract Process (Process ID: $($DriverProcess.ID)) To Complete.. Next Check In 60 Seconds" -Severity 1 | |
sleep -seconds 30 | |
} | |
} | |
} | |
else | |
{ | |
Write-CMLogEntry -Value "Skipping.. Drivers already extracted." -Severity 1 | |
} | |
if ($ImportInto -ne "Download Only") | |
{ | |
Write-CMLogEntry -Value "$($Product): Checking For Extracted Drivers" -Severity 1 -SkipGuiLog $true | |
if ($ImportInto -like "*Driver*") | |
{ | |
if ((Get-ChildItem -Recurse -Path "$DriverExtractDest" -Filter *.inf -File).count -ne 0) | |
{ | |
Write-CMLogEntry -Value "$($Product): Driver Count In Path $DriverExtractDest - $((Get-ChildItem -Recurse -Path "$DriverExtractDest" -Filter *.inf -File).count) " -Severity 1 -SkipGuiLog $true | |
Write-CMLogEntry -Value "==================== $PRODUCT DRIVER IMPORT ====================" -Severity 1 | |
if ($OSBuild -eq $null) | |
{ | |
$CMDriverPackage = ("$Make " + $Model + " - " + $OperatingSystem + " " + $Architecture) | |
} | |
else | |
{ | |
$CMDriverPackage = ("$Make " + $Model + " - " + $OperatingSystem + " " + $OSBuild + " " + $Architecture) | |
} | |
Set-Location -Path ($SiteCode + ":") | |
if ((Get-CMDriverPackage -Name $CMDriverPackage | Where-Object { $_.Version -eq $DriverRevision }) -eq $null) | |
{ | |
if ((Test-Path -Path "$DriverPackageDest") -eq $false) | |
{ | |
New-Item -ItemType Directory -Path "$DriverPackageDest" | |
} | |
Set-Location -Path ($SiteCode + ":") | |
Write-CMLogEntry -Value "$($Product): Creating Driver Package $CMDriverPackage" -Severity 1 | |
Write-CMLogEntry -Value "$($Product): Searching For Driver INF Files In $DriverExtractDest" -Severity 1 | |
Set-Location -Path $TempDirectory | |
$DriverINFFiles = Get-ChildItem -Path "$DriverExtractDest" -Recurse -Filter "*.inf" -File | Where-Object { $_.FullName -like "*$Architecture*" } | |
if ($DriverINFFiles.Count -ne $null) | |
{ | |
Set-Location -Path ($SiteCode + ":") | |
if (Get-CMCategory -CategoryType DriverCategories -name $DriverCategoryName) | |
{ | |
Write-CMLogEntry -Value "$($Product): Category already exists" -Severity 1 | |
$DriverCategory = Get-CMCategory -CategoryType DriverCategories -name $DriverCategoryName | |
} | |
else | |
{ | |
Write-CMLogEntry -Value "$($Product): Creating Category $DriverCategoryName" -Severity 1 | |
$DriverCategory = New-CMCategory -CategoryType DriverCategories -name $DriverCategoryName | |
} | |
Write-CMLogEntry -Value "$($Product): Creating Driver Package for $Make $Model (Version $DriverRevision)" -Severity 1 | |
New-CMDriverPackage -Name $CMDriverPackage -path "$DriverPackageDest" | |
Write-CMLogEntry -Value "$($Product): New CMDriverPacakge Name: $CMDriverPackage | Path $DriverPackageDest" -Severity 1 -SkipGuiLog $true | |
Set-CMDriverPackage -Name $CMDriverPackage -Version $DriverRevision | |
# Check For Driver Package | |
$SCCMDriverPackage = Get-CMDriverPackage -Name $CMDriverPackage | Where-Object { $_.Version -eq $DriverRevision } | |
Write-CMLogEntry -Value "$($Product): Checking Driver Package Created Successfully" -Severity 1 -SkipGuiLog $true | |
if ($SCCMDriverPackage.PackageID -ne $null) | |
{ | |
# Import Driver Loop | |
$DriverNo = 1 | |
foreach ($DriverINF in $DriverINFFiles) | |
{ | |
$DriverInfo = Import-CMDriver -UncFileLocation "$($DriverINF.FullName)" -ImportDuplicateDriverOption AppendCategory -EnableAndAllowInstall $True -AdministrativeCategory $DriverCategory | Select-Object * | |
Add-CMDriverToDriverPackage -DriverID $DriverInfo.CI_ID -DriverPackageName "$($CMDriverPackage)" | |
Write-CMLogEntry -Value "$($Product): Importing Driver INF $DriverNo Of $($DriverINFFiles.count): $($DriverINF.FullName | Split-Path -Leaf)" -Severity 1 | |
$DriverNo++ | |
} | |
Write-CMLogEntry -Value "$($Product): Driver Package $($SCCMDriverPackage.PackageID) Created Succesfully" -Severity 1 | |
# =============== Distrubute Content ================= | |
Write-CMLogEntry -Value "$($Product): Distributing $($SCCMDriverPackage.PackageID)" -Severity 1 -SkipGuiLog $true | |
DistributeContent -Product $Product -Package $SCCMDriverPackage.PackageID -ImportInto $ImportInto | |
} | |
else | |
{ | |
Write-CMLogEntry -Value "Error: Errors Occurred While Creating Driver Package" -Severity 3 | |
} | |
Set-Location -Path $TempDirectory | |
} | |
else | |
{ | |
Write-CMLogEntry -Value "$($Product): Extract Folder Empty.. Skipping Driver Import / Package Creation" -Severity 2 | |
} | |
} | |
else | |
{ | |
Write-CMLogEntry -Value "$($Product): Driver Package Already Exists.. Skipping" -Severity 1 | |
Set-Location -Path $TempDirectory | |
} | |
} | |
else | |
{ | |
Write-CMLogEntry -Value "======== DRIVER EXTRACT ISSUE DETECTED ========" -Severity 3 | |
Write-CMLogEntry -Value "$($Product): Issues occurred while reading extracted drivers" -Severity 3 | |
Write-CMLogEntry -Value "$($Product): Driver count in path $DriverExtractDest - $((Get-ChildItem -Recurse -Path "$DriverExtractDest" -Filter *.inf -File).count) " -Severity 1 -SkipGuiLog $true | |
} | |
} | |
Write-CMLogEntry -Value "$($Product): Checking For Extracted Drivers" -Severity 1 -SkipGuiLog $true | |
if ($ImportInto -like "*Standard*") | |
{ | |
Write-CMLogEntry -Value "$($Product): Driver Count In Path $DriverExtractDest - $((Get-ChildItem -Recurse -Path "$DriverExtractDest" -Filter *.inf -File).count) " -Severity 1 -SkipGuiLog $true | |
if ((Get-ChildItem -Recurse -Path "$DriverExtractDest" -Filter *.inf -File).Count - $null) | |
{ | |
Write-CMLogEntry -Value "$($Product): Validated Drivers Exist In $DriverExtractDest - Processing Driver Packaging Steps " -Severity 1 -SkipGuiLog $true | |
Write-CMLogEntry -Value "==================== $PRODUCT DRIVER PACKAGE ====================" -Severity 1 | |
if ($OSBuild -eq $null) | |
{ | |
$CMPackage = ("Drivers - " + "$Make " + $Model + " - " + $OperatingSystem + " " + $Architecture) | |
} | |
else | |
{ | |
$CMPackage = ("Drivers - " + "$Make " + $Model + " - " + $OperatingSystem + " " + $OSBuild + " " + $Architecture) | |
} | |
if ($Make -eq "Lenovo") | |
{ | |
$CMPackage = $CMPackage + " ($global:LenovoModelType)" | |
} | |
Set-Location -Path ($SiteCode + ":") | |
if ((Get-CMPackage -Name $CMPackage | Where-Object { $_.Version -eq $DriverRevision }) -eq $null) | |
{ | |
Set-Location -Path $TempDirectory | |
if ((Test-Path -Path "$DriverPackageDest") -eq $false) | |
{ | |
New-Item -ItemType Directory -Path "$DriverPackageDest" | |
} | |
Set-Location -Path ($SiteCode + ":") | |
Write-CMLogEntry -Value "$($Product): Creating Package for $Make $Model (Version $DriverRevision)" -Severity 1 | |
# Work around for HP WMI when using the ConfigMgr Web Service | |
if ($Make -eq "HP") | |
{ | |
$Manufacturer = "Hewlett-Packard" | |
} | |
else | |
{ | |
$Manufacturer = $Make | |
} | |
# Create Driver Package | |
New-CMPackage -Name "$CMPackage" -path "$DriverPackageDest" -Manufacturer $Manufacturer -Description "$Make $Model Windows $WindowsVersion $Architecture Drivers" -Version $DriverRevision | |
if ($EnableBinaryDifCheckBox.Checked -eq $true) | |
{ | |
Write-CMLogEntry -Value "$($Product): Enabling Binary Delta Replication" -Severity 1 | |
Set-CMPackage -Name "$CMPackage" -EnableBinaryDeltaReplication $true | |
} | |
$MifVersion = $OperatingSystem + " " + $Architecture | |
Set-CMPackage -Name "$CMPackage" -MifName $Model -MifVersion $MifVersion | |
# Move Extracted Drivers To Driver Package Directory | |
Write-CMLogEntry -Value "$($Product): Source Directory $DriverExtractDest" -Severity 1 | |
Write-CMLogEntry -Value "$($Product): Destination Directory $DriverPackageDest" -Severity 1 | |
Set-Location -Path $TempDirectory | |
# Copy Drivers To Package Location | |
Start-Job -Name "$Model-Driver-Package" -ScriptBlock $PackageDrivers -ArgumentList ($Make, $DriverExtractDest, $Architecture, $DriverPackageDest) | |
while ((Get-Job -Name "$Model-Driver-Package").State -eq "Running") | |
{ | |
Write-CMLogEntry -Value "$($Product): Copying $Make $Model $OperatingSystem $Architecture Drivers.. Next Check In 30 Seconds" -Severity 1 | |
sleep -seconds 30 | |
} | |
if ((Get-Job -Name "$Model-Driver-Package").State -eq "Completed") | |
{ | |
# Check For Driver Package | |
Set-Location -Path ($SiteCode + ":") | |
$SCCMPackage = Get-CMPackage -Name $CMPackage | Where-Object { $_.Version -eq $DriverRevision } | |
if ($SCCMPackage.PackageID -ne $null) | |
{ | |
Write-CMLogEntry -Value "$($Product): Driver Package $($SCCMPackage.PackageID) Created Succesfully" -Severity 1 | |
# =============== Distrubute Content ================= | |
DistributeContent -Product $Product -Package $SCCMPackage.PackageID -ImportInto $ImportInto | |
} | |
else | |
{ | |
Write-CMLogEntry -Value "Error: Errors Occurred While Creating Package" -Severity 3 | |
} | |
} | |
else | |
{ | |
Write-CMLogEntry -Value "Error: Errors Occurred While Copying Drivers" -Severity 3 | |
} | |
Get-Job -Name "$Model-Driver-Package" | Remove-Job | |
Set-Location -Path $TempDirectory | |
} | |
else | |
{ | |
Write-CMLogEntry -Value "$($Product): Driver Package Already Exists.. Skipping" -Severity 2 | |
Set-Location -Path $TempDirectory | |
} | |
} | |
else | |
{ | |
Write-CMLogEntry -Value "======== DRIVER EXTRACT ISSUE DETECTED ========" -Severity 3 | |
Write-CMLogEntry -Value "$($Product): Issues occurred while reading extracted drivers" -Severity 3 | |
Write-CMLogEntry -Value "$($Product): Driver Count In Path $DriverExtractDest - $((Get-ChildItem -Recurse -Path "$DriverExtractDest" -Filter *.inf -File).count) " -Severity 1 -SkipGuiLog $true | |
} | |
} | |
} | |
} | |
else | |
{ | |
Write-CMLogEntry -Value "$($Product): $DriverCab File Download Failed" -Severity 3 | |
} | |
} | |
else | |
{ | |
Write-CMLogEntry -Value "$($Product): Operating system driver package download path not found.. Skipping $Model" -Severity 3 | |
} | |
Write-CMLogEntry -Value "======== $PRODUCT $MODEL DRIVER PROCESSING FINISHED ========" -Severity 1 | |
} | |
Set-Location -Path $TempDirectory | |
if (($ImportInto -like "*Both*") -or ($ImportInto -eq "MDT")) | |
{ | |
Write-CMLogEntry -Value "======== $PRODUCT $MODEL DRIVER PROCESSING STARTED ========" -Severity 1 | |
Set-Location -Path $TempDirectory | |
# Import MDT Module | |
Write-CMLogEntry -Value "======== $Product Prerequisites ========" -Severity 1 -SkipGuiLog $true | |
Write-CMLogEntry -Value "$($Product): Importing MDT PowerShell Module" -Severity 1 -SkipGuiLog $true | |
$MDTPSLocation = "C:\Program Files\Microsoft Deployment Toolkit\bin\MicrosoftDeploymentToolkit.psd1" | |
if ((Test-Path -Path $MDTPSLocation) -eq $true) | |
{ | |
Import-Module "$MDTPSLocation" | |
$Product = "MDT" | |
# =================== MDT Driver Download ===================== | |
Write-CMLogEntry -Value "======== $Product Driver Download ========" -Severity 1 | |
Write-CMLogEntry -Value "$($Product): Starting $Product Driver Download Process" -Severity 1 | |
# =================== DEFINE VARIABLES ===================== | |
Write-CMLogEntry -Value "$($Product): Driver Package Base Location Set To $DriverRepositoryRoot" -Severity 1 | |
# Operating System Version | |
$OperatingSystem = ("Windows " + $WindowsVersion) | |
# =============== MDT Driver Cab Download ================= | |
# Cater for HP / Model Issue | |
$Model = $Model -replace '/', '-' | |
if (($ModelURL -ne $null) -and ($ModelURL -ne "badLink")) | |
{ | |
# Check for destination directory, create if required and download the driver cab | |
if ((Test-Path -Path ($DriverRepositoryRoot + $Model + "\Driver Cab\" + $DriverCab)) -eq $false) | |
{ | |
Write-CMLogEntry -Value "$($Product): Creating $Model download folder" -Severity 1 | |
if ((Test-Path -Path ($DriverRepositoryRoot + $Model + "\Driver Cab")) -eq $false) | |
{ | |
New-Item -ItemType Directory -Path "$($DriverRepositoryRoot + $Model + '\Driver Cab')" | |
} | |
Write-CMLogEntry -Value "$($Product): Downloading $DriverCab driver cab file" -Severity 1 | |
Write-CMLogEntry -Value "$($Product): Downloading from URL: $DriverDownload" -Severity 1 | |
Start-Job -Name "$Model-DriverDownload" -ScriptBlock $DriverDownloadJob -ArgumentList ($DriverRepositoryRoot, $Model, $DriverCab, $DriverDownload, $ProxyServer, $ProxyCred) | |
sleep -Seconds 5 | |
$BitsJob = Get-BitsTransfer | Where-Object { $_.DisplayName -eq "$Model-DriverDownload" } | |
while (($BitsJob).JobState -eq "Connecting") | |
{ | |
Write-CMLogEntry -Value "$($Product): Establishing Connection to $DriverDownload." -Severity 1 | |
sleep -seconds 30 | |
} | |
while (($BitsJob).JobState -eq "Transferring") | |
{ | |
$PercentComplete = [int](($BitsJob.BytesTransferred * 100)/$BitsJob.BytesTotal); | |
Write-CMLogEntry -Value "$($Product): Downloaded $([int]((($BitsJob).BytesTransferred)/ 1MB)) MB of $([int]((($BitsJob).BytesTotal)/ 1MB)) MB ($PercentComplete%). Next update in 30 seconds" -Severity 1 | |
sleep -seconds 30 | |
} | |
Get-BitsTransfer | Where-Object { $_.DisplayName -eq "$Model-DriverDownload" } | Complete-BitsTransfer | |
Write-CMLogEntry -Value "$($Product): Driver Revision: $DriverRevision" -Severity 1 | |
} | |
else | |
{ | |
Write-CMLogEntry -Value "$($Product): Skipping $DriverCab... Driver pack already downloaded" -Severity 2 | |
} | |
# Check for destination directory, create if required and download the driver cab | |
if ((Test-Path -Path "$($DriverRepositoryRoot + $Model + '\Driver Cab\' + $DriverCab)") -eq $false) | |
{ | |
if ((Test-Path -Path "($DriverRepositoryRoot + $Model + '\Driver Cab\')") -eq $false) | |
{ | |
Write-CMLogEntry -Value "$($Product): Creating $Model Download Folder" -Severity 1 | |
New-Item -ItemType Directory -Path "$($DriverRepositoryRoot + $Model + '\Driver Cab')" | |
} | |
else | |
{ | |
# Remove previous driver cab revisions | |
Get-ChildItem -Path "$($DriverRepositoryRoot + $Model + '\Driver Cab\')" | Remove-Item | |
} | |
Write-CMLogEntry -Value "$($Product): Downloading $DriverCab Driver Cab File" -Severity 1 | |
Start-Job -Name "$Model-DriverDownload" -ScriptBlock $DriverDownloadJob -ArgumentList ($DriverRepositoryRoot, $Model, $DriverCab, $DriverDownload, $ProxyServer, $ProxyCred) | |
sleep -Seconds 5 | |
$BitsJob = Get-BitsTransfer | Where-Object { $_.DisplayName -eq "$Model-DriverDownload" } | |
while (($BitsJob).JobState -eq "Connecting") | |
{ | |
Write-CMLogEntry -Value "$($Product): Establishing Connection to $DriverDownload" -Severity 1 | |
sleep -seconds 30 | |
} | |
while (($BitsJob).JobState -eq "Transferring") | |
{ | |
$PercentComplete = [int](($BitsJob.BytesTransferred * 100)/$BitsJob.BytesTotal); | |
Write-CMLogEntry -Value "$($Product): Downloaded $([int]((($BitsJob).BytesTransferred)/ 1MB)) 1MB of $([int]((($BitsJob).BytesTotal)/ 1MB)) MB ($PercentComplete%). Next update in 30 seconds" -Severity 1 | |
sleep -seconds 30 | |
} | |
Get-BitsTransfer | Where-Object { $_.DisplayName -eq "$Model-DriverDownload" } | Complete-BitsTransfer | |
Write-CMLogEntry -Value "$($Product): Driver Revision: $DriverRevision" -Severity 1 | |
} | |
else | |
{ | |
Write-CMLogEntry -Value "$($Product): Skipping $DriverCab... Driver pack already extracted" -Severity 2 | |
} | |
if (((Test-Path -Path "$($DriverRepositoryRoot + $Model + '\Driver Cab\' + $DriverCab)") -eq $true) -and ($DriverCab -ne $null)) | |
{ | |
# =============== MDT Driver EXTRACT ==================== | |
if ((Test-Path -Path "$DriverExtractDest") -eq $false) | |
{ | |
# Extract Drivers From Driver | |
New-Item -ItemType Directory -Path "$DriverExtractDest" | |
} | |
if ((Get-ChildItem -Path "$DriverExtractDest" -Recurse -Filter *.inf -File).Count -eq 0) | |
{ | |
Write-CMLogEntry -Value "======== $PRODUCT DRIVER EXTRACT ========" -Severity 1 | |
Write-CMLogEntry -Value "$($Product): Expanding Driver CAB Source File: $DriverCab" -Severity 1 | |
Write-CMLogEntry -Value "$($Product): Driver CAB Destination Directory: $DriverExtractDest" -Severity 1 | |
if ($Make -eq "Dell") | |
{ | |
Write-CMLogEntry -Value "$($Product): Extracting $Make Drivers to $DriverExtractDest" -Severity 1 | |
Expand "$DriverSourceCab" -F:* "$DriverExtractDest" | |
} | |
if ($Make -eq "HP") | |
{ | |
# Driver Silent Extract Switches | |
$HPTemp = $TempDirectory + "\" + $Model + "\Win" + $WindowsVersion + $Architecture | |
$HPTemp = $HPTemp -replace '/', '-' | |
# HP Work Around For Long Dir | |
if ((($HPTemp).Split("-").Count) -gt "1") | |
{ | |
$HPTemp = ($HPTemp).Split("-")[0] | |
} | |
Write-CMLogEntry -Value "$($Product): Extracting HP Drivers to $HPTemp" -Severity 1 | |
$HPSilentSwitches = "-PDF -F" + $HPTemp + " -S -E" | |
Write-CMLogEntry -Value "$($Product): Using $Make Silent Switches: $HPSilentSwitches" -Severity 1 -SkipGuiLog $true | |
Write-CMLogEntry -Value "$($Product): Extracting $Make Drivers to $DriverExtractDest" -Severity 1 | |
Start-Process -FilePath "$($DriverRepositoryRoot + $Model + '\Driver Cab\' + $DriverCab)" -ArgumentList $HPSilentSwitches -Verb RunAs | |
$DriverProcess = ($DriverCab).Substring(0, $DriverCab.length - 4) | |
# Wait for HP SoftPaq Process To Finish | |
While ((Get-Process).name -contains $DriverProcess) | |
{ | |
Write-CMLogEntry -Value "$($Product): Waiting For Extract Process (Process: $DriverProcess) To Complete.. Next Check In 30 Seconds" -Severity 1 | |
sleep -Seconds 30 | |
} | |
# Move HP Extracted Drivers To UNC Share | |
$HPExtract = Get-ChildItem -Path $HPTemp | |
Start-Job -Name "$Model-Driver-Move" -ScriptBlock $MoveHPDrivers -ArgumentList ($HPExtract, $DriverExtractDest) | |
sleep -Seconds 2 | |
while ((Get-Job -Name "$Model-Driver-Move").State -eq "Running") | |
{ | |
Write-CMLogEntry -Value "$($Product): Moving $Make $Model $OperatingSystem $Architecture Driver.. Next Check In 30 Seconds" -Severity 1 | |
sleep -seconds 30 | |
} | |
} | |
if ($Make -eq "Lenovo") | |
{ | |
# Driver Silent Extract Switches | |
$LenovoSilentSwitches = "/VERYSILENT /DIR=" + "$($DriverExtractDest)" + '/Extract="Yes"' | |
Write-CMLogEntry -Value "$($Product): Using $Make Silent Switches: $LenovoSilentSwitches" -Severity 1 -SkipGuiLog $true | |
Write-CMLogEntry -Value "$($Product): Extracting $Make Drivers to $DriverExtractDest" -Severity 1 | |
Start-Process -FilePath $($DriverRepositoryRoot + $Model + "\Driver Cab\" + $DriverCab) -ArgumentList $LenovoSilentSwitches -Verb RunAs | |
$DriverProcess = ($DriverCab).Substring(0, $DriverCab.length - 4) | |
# Wait for Lenovo Driver Process To Finish | |
While ((Get-Process).name -contains $DriverProces) | |
{ | |
Write-CMLogEntry -Value "$($Product): Waiting For Extract Process (Process: $DriverProcess) To Complete.. Next Check In 60 Seconds" -Severity 1 | |
sleep -seconds 30 | |
} | |
} | |
if ($Make -eq "Acer") | |
{ | |
# Driver Silent Extract Switches | |
$AcerSilentSwitches = "x " + '"' + $($DriverRepositoryRoot + $Model + "\Driver Cab\" + $DriverCab) + '"' + " -O" + '"' + $DriverExtractDest + '"' | |
Write-CMLogEntry -Value "$($Product): Using $Make Silent Switches: $AcerSilentSwitches" -Severity 1 -SkipGuiLog $true | |
Write-CMLogEntry -Value "$($Product): Extracting $Make Drivers to $DriverExtractDest" -Severity 1 | |
$DriverProcess = Start-Process 'C:\Program Files\7-Zip\7z.exe' -ArgumentList $AcerSilentSwitches -PassThru -NoNewWindow | |
# Wait for Acer Driver Process To Finish | |
While ((Get-Process).ID -eq $DriverProcess.ID) | |
{ | |
Write-CMLogEntry -Value "$($Product): Waiting For Extract Process (Process ID: $($DriverProcess.ID)) To Complete.. Next Check In 60 Seconds" -Severity 1 | |
sleep -seconds 30 | |
} | |
} | |
if ($Make -eq "Microsoft") | |
{ | |
# Driver Silent Extract Switches | |
$MicrosoftSilentSwitches = "/a" + '"' + $($DriverRepositoryRoot + $Model + "\Driver Cab\" + $DriverCab) + '"' + '/QN TARGETDIR="' + $DriverExtractDest + '"' | |
Write-CMLogEntry -Value "$($Product): Using $Make Silent Switches: $MicrosoftSilentSwitches" -Severity 1 -SkipGuiLog $true | |
Write-CMLogEntry -Value "$($Product): Extracting $Make Drivers to $DriverExtractDest" -Severity 1 | |
$DriverProcess = Start-Process msiexec.exe -ArgumentList $MicrosoftSilentSwitches -PassThru | |
# Wait for Microsoft Driver Process To Finish | |
While ((Get-Process).ID -eq $MicrosoftProcess.ID) | |
{ | |
Write-CMLogEntry -Value "$($Product): Waiting For Extract Process (Process ID: $($DriverProcess.ID)) To Complete.. Next Check In 60 Seconds" -Severity 1 | |
sleep -seconds 30 | |
} | |
} | |
} | |
# =============== MDT Driver Import ==================== | |
Write-CMLogEntry -Value "======== $PRODUCT Driver Import ========" -Severity 1 | |
Write-CMLogEntry -Value "$($Product): Starting MDT Driver Import Process" -Severity 1 | |
# Detect First MDT PSDrive | |
Write-CMLogEntry -Value "$($Product): Detecting MDT PSDrive" -Severity 1 | |
if (!$PSDriveName) { $PSDriveName = (Get-MDTPersistentDrive)[0].name } | |
# Detect First MDT Deployment Share | |
Write-CMLogEntry -Value "$($Product): Detecting MDT Deployment Share" -Severity 1 | |
if (!$DeploymentShare) { $DeploymentShare = (Get-MDTPersistentDrive)[0].path } | |
$MDTDriverPath = $PSDriveName + ':\Out-of-Box Drivers' | |
$MDTSelectionProfilePath = $PSDriveName + ':\Selection Profiles' | |
# Connect to Deployment Share | |
Write-CMLogEntry -Value "$($Product): Connecting To MDT Share" -Severity 1 | |
if (!(Get-PSDrive -Name $PSDriveName -ErrorAction SilentlyContinue)) | |
{ | |
New-PSDrive -Name $PSDriveName -PSProvider MDTProvider -Root "$DeploymentShare" | |
Write-CMLogEntry -Value "$($Product): $PSDriveName connected to $DeploymentShare" -Severity 1 -SkipGuiLog $true | |
} | |
$DSDriverPath = $PSDriveName + ':\Out-of-Box Drivers' | |
$DSSelectionProfilePath = $PSDriveName + ':\Selection Profiles' | |
# Connect to Deployment Share | |
if ((Get-PSDrive -Name $PSDriveName -ErrorAction SilentlyContinue) -eq $false) | |
{ | |
New-PSDrive -Name $PSDriveName -PSProvider MDTProvider -Root "$DeploymentShare" | |
Write-CMLogEntry -Value "$($Product): $PSDriveName connected to $DeploymentShare" -Severity 1 -SkipGuiLog $true | |
} | |
# Cater for HP / Model Issue | |
$Model = $Model -replace '/', '-' | |
# =============== MDT Driver Import ==================== | |
if ($OSBuild -eq $null) | |
{ | |
$OperatingSystemDir = ($OperatingSystem + " " + $Architecture) | |
} | |
else | |
{ | |
$OperatingSystemDir = ($OperatingSystem + " " + $OSBuild + " " + $Architecture) | |
} | |
$DriverSource = $DriverRepositoryRoot + $Model + '\Driver Cab\' + $DriverCab | |
if ((Test-Path $MDTDriverPath\$OperatingSystemDir) -eq $false) | |
{ | |
New-Item -path $MDTDriverPath -enable "True" -Name $OperatingSystemDir -ItemType Directory | |
} | |
if ((Test-Path $MDTSelectionProfilePath"\Drivers - "$OperatingSystemDir) -eq $false) | |
{ | |
New-Item -path $MDTSelectionProfilePath -enable "True" -Name "Drivers - $OperatingSystemDir" -Definition "<SelectionProfile><Include path=`"Out-of-Box Drivers\$OS`" /></SelectionProfile>" -ReadOnly "False" | |
} | |
if ((Test-Path $MDTDriverPath\$OperatingSystemDir\$Make) -eq $false) | |
{ | |
New-Item -path $MDTDriverPath\$OperatingSystemDir -enable "True" -Name $Make -ItemType Directory | |
} | |
if ((Test-Path $MDTDriverPath\$OperatingSystemDir\$Make\$Model) -eq $false) | |
{ | |
New-Item -path $MDTDriverPath\$OperatingSystemDir\$Make -enable "True" -Name $Model -ItemType Directory | |
} | |
if ((Test-Path $MDTDriverPath\$OperatingSystemDir\$Make\$Model\$DriverRevision) -eq $false) | |
{ | |
New-Item -path $MDTDriverPath\$OperatingSystemDir\$Make\$Model -enable "True" -Name $DriverRevision -ItemType Directory | |
Write-CMLogEntry -Value "$($Product): Importing MDT driver pack for $Make $Model - Revision $DriverRevision" -Severity 1 | |
Write-CMLogEntry -Value "$($Product): MDT Driver Path = $MDTDriverPath\$OperatingSystemDir\$Make\$Model\$DriverRevision" -Severity 1 | |
Start-Job -Name "$Model-MDTImport" -ScriptBlock $MDTImportJob -ArgumentList ($PSDriveName, $MDTDriverPath, $Make, $Model, $DriverRevision, $OperatingSystemDir, $DriverExtractDest, $DeploymentShare, $Architecture) | |
while ((Get-Job -Name "$Model-MDTImport").State -eq "Running") | |
{ | |
Write-CMLogEntry -Value "$($Product): Waiting For Import Process To Finish For $Make $Model $OperatingSystem $Architecture.. Next Check In 60 Seconds" -Severity 1 | |
sleep -seconds 60 | |
} | |
} | |
else | |
{ | |
Write-CMLogEntry -Value "$($Product): Driver pack already exists.. Skipping" -Severity 2 | |
} | |
} | |
else | |
{ | |
Write-CMLogEntry -Value "$($Product): Error Downloading $DriverCab" -Severity 3 | |
} | |
} | |
} | |
else | |
{ | |
Write-CMLogEntry -Value "Error: MDT PowerShell Commandlets Not Found - Path Specified $MDTPSLocation" -Severity 3 | |
} | |
Write-CMLogEntry -Value "======== $PRODUCT $MODEL PROCESSING FINISHED ========" -Severity 1 | |
} | |
if ($RemoveLegacyDriverCheckbox.Checked -eq $true) | |
{ | |
Set-Location -Path ($SiteCode + ":") | |
Write-CMLogEntry -Value "======== Superseded Driver Package Option Processing ========" -Severity 1 | |
$ModelDriverPacks = Get-CMDriverPackage | Where-Object { $_.Name -like "*$Model*$WindowsVersion*$Architecture*" } | Sort-Object Version -Descending | |
if ($ModelDriverPacks.Count -gt "1") | |
{ | |
$LegacyDriverPack = $ModelDriverPacks | select -Last 1 | |
Write-CMLogEntry -Value "$($Product): Removing $($LegacyDriverPack.Name) / Package ID $($LegacyDriverPack.PackageID)" -Severity 1 | |
Remove-CMDriverPackage -id $LegacyDriverPack.PackageID -Force | |
} | |
$ModelPackages = Get-CMPackage | Where-Object { $_.Name -like "*$Model*$WindowsVersion*$Architecture*" } | Sort-Object Version -Descending | |
if ($ModelPackages.Count -gt "1") | |
{ | |
$LegacyPackage = $ModelPackages | select -Last 1 | |
Write-CMLogEntry -Value "$($Product): Removing $($LegacyPackage.Name) / Package ID $($LegacyPackage.PackageID)" -Severity 1 | |
Remove-CMPackage -id $LegacyPackage.PackageID -Force | |
} | |
Set-Location -Path $TempDirectory | |
} | |
$ProgressBar.Increment(1) | |
$ModelProgressOverlay.Increment(1) | |
$RemainingModels-- | |
Write-CMLogEntry -Value "Info: Remaining Models To Process: $RemainingModels" -Severity 1 -SkipGuiLog $True | |
} | |
} | |
$ProgressBar.Increment(1) | |
$ModelProgressOverlay.Increment(1) | |
if ($CleanUnusedCheckBox.Checked -eq $true) | |
{ | |
Set-Location -Path ($SiteCode + ":") | |
Write-CMLogEntry -Value "======== Clean Up Driver Option Processing ========" -Severity 1 | |
# Sleep to allow for driver package registration | |
sleep -Seconds 10 | |
# Get list of unused drivers | |
$DriverList = Get-CMDriverPackage | Get-CMDriver | Select -Property CI_ID | |
$UnusedDrivers = Get-CMDriver | Where-Object { $_.CI_ID -notin $DriverList.CI_ID } | |
Write-CMLogEntry -Value "$($Product): Found $($UnusedDrivers.Count) Unused Drivers" -Severity 1 | |
Write-CMLogEntry -Value "$($Product): Starting Driver Package Clean Up Process" -Severity 1 | |
foreach ($Driver in $UnusedDrivers) | |
{ | |
Write-CMLogEntry -Value "$($Product): Removing $($Driver.LocalizedDisplayName) from Category $($Driver.LocalizedCategoryInstanceNames)" -Severity 1 | |
Remove-CMDriver -ID $Driver.CI_ID -Force | |
} | |
Write-CMLogEntry -Value "$($Product): Driver Clean Up Process Completed" -Severity 1 | |
Set-Location -Path $TempDirectory | |
} | |
if ($RemoveDriverSourceCheckbox.Checked -eq $true) | |
{ | |
# Clean Up Driver Source Files | |
if ((($RepositoryTextBox.Text) -ne $null) -and ((Test-Path -Path ($RepositoryTextBox.text)) -eq $true)) | |
{ | |
Write-CMLogEntry -Value "$($Product): Removing Downloaded Driver Files From $($RepositoryTextBox.Text). Extracted Drivers Will Remain" -Severity 1 -SkipGuiLog $true | |
Get-ChildItem -Path $($RepositoryTextBox.Text) -Recurse -Directory | Where-Object { $_.FullName -match "Driver Cab" } | Get-ChildItem | Remove-Item -Force | |
} | |
} | |
Write-CMLogEntry -Value "======== Finished Processing ========" -Severity 1 | |
} | |
$ConnectSCCMButton_Click = { | |
$SiteServer = [string]$SiteServerInput.Text | |
$ProgressListBox.ForeColor = "Black" | |
Write-CMLogEntry -Value "======== Validating ConfigMgr Server Details $(Get-Date) ========" -Severity 1 | |
ConnectSCCM | |
} | |
$ClearSelectionButton_Click = { | |
#Reset Windows Form | |
$ProgressListBox.ForeColor = "Black" | |
$ProductListBox.Items.Clear() | |
$ProgressListBox.Items.Clear() | |
$SiteServerInput.Text = $null | |
$SiteServerInput.Enabled = $true | |
$SiteCodeText = $null | |
$PlatformComboBox.SelectedItem = $null | |
$PlatformComboBox.Enabled = $true | |
$DownloadComboBox.SelectedItem = $null | |
$DownloadComboBox.Enabled = $true | |
$OSComboBox.SelectedItem = $null | |
$OSComboBox.Enabled = $true | |
$ArchitectureComboxBox.SelectedItem = $null | |
$ArchitectureComboxBox.Enabled = $true | |
$RepositoryTextBox.Text = $null | |
$PackagePathTextBox.Text = $null | |
$PackagePathTextBox.Enabled = $true | |
$StartDownloadButton.Enabled = $false | |
$FullModelListBox.Items.Clear() | |
$DellCheckBox.Checked = $false | |
$HPCheckBox.Checked = $false | |
$LenovoCheckBox.Checked = $false | |
} | |
$AddToListButton_Click = { | |
foreach ($Item in $FullModelListBox.SelectedItems) | |
{ | |
$ProductListBox.Items.Add($Item) | |
} | |
} | |
$FindModelsButton_Click = { | |
$FullModelListBox.Items.Clear() | |
UpdateModeList $SiteServerInput.Text $SiteCodeText.Text | |
} | |
$UseProxyServerCheckbox_CheckedChanged = { | |
if ($UseProxyServerCheckbox.Checked -eq $true) | |
{ | |
$ProxyPswdInput.Enabled = $true | |
$ProxyUserInput.Enabled = $true | |
$ProxyServerInput.Enabled = $true | |
} | |
else | |
{ | |
$ProxyPswdInput.Enabled = $false | |
$ProxyUserInput.Enabled = $false | |
$ProxyServerInput.Enabled = $false | |
} | |
} | |
$DownloadComboBox_SelectedIndexChanged = { | |
if ($DownloadComboBox.Text -eq "BIOS") | |
{ | |
$PackagePathTextBox.Enabled = $false | |
#$OSComboBox.Enabled = $false | |
#$ArchitectureComboxBox.Enabled = $false | |
$LenovoCheckBox.Enabled = $true | |
$LenovoCheckBox.Checked = $false | |
$HPCheckBox.Enabled = $false | |
$HPCheckBox.Checked = $false | |
$AcerCheckBox.Enabled = $false | |
$AcerCheckBox.Checked = $false | |
$MicrosoftCheckBox.Enabled = $false | |
$MicrosoftCheckBox.Checked = $false | |
$DellCheckBox.Checked = $false | |
$CleanUnusedCheckBox.Enabled = $false | |
$RemoveLegacyDriverCheckbox.Enabled = $false | |
} | |
else | |
{ | |
if ($PlatformComboBox.SelectedItem -eq "Download Only") | |
{ | |
$OSComboBox.Enabled = $true | |
$ArchitectureComboxBox.Enabled = $true | |
$PackagePathTextBox.Enabled = $false | |
SCCMOptions -OptionsEnabled $false | |
} | |
else | |
{ | |
$PackagePathTextBox.Enabled = $true | |
$OSComboBox.Enabled = $true | |
$ArchitectureComboxBox.Enabled = $true | |
$PackagePathTextBox.Enabled = $true | |
SCCMOptions -OptionsEnabled $true | |
} | |
$LenovoCheckBox.Enabled = $true | |
$HPCheckBox.Enabled = $true | |
$AcerCheckBox.Enabled = $true | |
$MicrosoftCheckBox.Enabled = $true | |
$DellCheckBox.Checked = $false | |
} | |
} | |
$PlatformComboBox_SelectedIndexChanged = { | |
if ($PlatformComboBox.SelectedItem -eq "MDT") | |
{ | |
$DownloadComboBox.Text = "Drivers" | |
$DownloadComboBox.Enabled = $false | |
$PackagePathTextBox.Enabled = $false | |
$CleanUnusedCheckBox.Enabled = $false | |
$RemoveLegacyDriverCheckbox.Enabled = $false | |
SCCMOptions -OptionsEnabled $false | |
} | |
if ($PlatformComboBox.SelectedItem -match "Standard") | |
{ | |
$DownloadComboBox.Enabled = $true | |
$PackagePathTextBox.Enabled = $true | |
$CleanUnusedCheckBox.Enabled = $true | |
$RemoveLegacyDriverCheckbox.Enabled = $true | |
SCCMOptions -OptionsEnabled $true | |
} | |
if ($PlatformComboBox.SelectedItem -match "Driver") | |
{ | |
$DownloadComboBox.Enabled = $true | |
$PackagePathTextBox.Enabled = $true | |
$CleanUnusedCheckBox.Enabled = $true | |
$RemoveLegacyDriverCheckbox.Enabled = $true | |
SCCMOptions -OptionsEnabled $true | |
} | |
if ($PlatformComboBox.SelectedItem -eq "Download Only") | |
{ | |
$DownloadComboBox.Enabled = $true | |
$PackagePathTextBox.Enabled = $true | |
$PackagePathTextBox.Enabled = $false | |
SCCMOptions -OptionsEnabled $false | |
} | |
$StartDownloadButton.Enabled = $true | |
} | |
$RemoveItemsButton_Click = { | |
While ($ProductListBox.SelectedItems.Count -gt 0) | |
{ | |
$ProductListBox.Items.RemoveAt($ProductListBox.SelectedIndex) | |
} | |
} | |
$SCConfigMgrLink_LinkClicked = [System.Windows.Forms.LinkLabelLinkClickedEventHandler]{ | |
Start-Process "http://www.scconfigmgr.com/2017/03/01/driver-automation-tool/" | |
} | |
$OSComboBox_SelectedIndexChanged = { | |
if ($OSComboBox.SelectedItem -eq "Windows 10") | |
{ | |
$HPCheckBox.Enabled = $false | |
$HPCheckBox.Checked = $false | |
} | |
else | |
{ | |
$HPCheckBox.Enabled = $true | |
} | |
if ($OSComboBox.SelectedItem -like "Windows 10 1*") | |
{ | |
$DellCheckBox.Enabled = $false | |
$DellCheckBox.Checked = $false | |
$AcerCheckbox.Enabled = $false | |
$AcerCheckbox.Checked = $false | |
$LenovoCheckBox.Enabled = $false | |
$LenovoCheckBox.Checked = $false | |
$MicrosoftCheckBox.Enabled = $false | |
$MicrosoftCheckBox.Checked = $false | |
} | |
else | |
{ | |
$DellCheckBox.Enabled = $true | |
$AcerCheckbox.Enabled = $true | |
$LenovoCheckBox.Enabled = $true | |
$MicrosoftCheckBox.Enabled = $true | |
} | |
} | |
$MainForm_FormClosing = [System.Windows.Forms.FormClosingEventHandler]{ | |
Write-CMLogEntry -Value "======== Cleaning Up Temporary Files ========" -Severity 1 | |
Write-CMLogEntry -Value "Info: Removing Temp Folders & Source XML/CAB Files" -Severity 1 -SkipGuiLog $true | |
# Clean Up Temp Driver Folders | |
Get-ChildItem -Path $TempDirectory -Recurse -Directory | Remove-Item -Recurse | |
# Clean Up Temp XML & CAB Sources | |
Get-ChildItem -Path $TempDirectory -Recurse -Filter *.xml -File | Remove-Item | |
Get-ChildItem -Path $TempDirectory -Recurse -Filter *.cab -File | Remove-Item | |
} | |
$buttonBrowseFolder_Click = { | |
if ($RepositoryBrowseFolderDialogue.ShowDialog() -eq 'OK') | |
{ | |
$RepositoryTextBox.Text = $RepositoryBrowseFolderDialogue.SelectedPath | |
} | |
} | |
$RepositoryBrowseButton_Click2 = { | |
if ($RepositoryBrowseFolderDialogue.ShowDialog() -eq 'OK') | |
{ | |
$RepositoryTextBox.Text = $RepositoryBrowseFolderDialogue.SelectedPath | |
} | |
} | |
$PackageBrowseButton_Click2 = { | |
if ($PackageBrowseFolderDialogue.ShowDialog() -eq 'OK') | |
{ | |
$PackagePathTextBox.Text = $PackageBrowseFolderDialogue.SelectedPath | |
} | |
} | |
# --End User Generated Script-- | |
#---------------------------------------------- | |
#region Generated Events | |
#---------------------------------------------- | |
$Form_StateCorrection_Load= | |
{ | |
#Correct the initial state of the form to prevent the .Net maximized form issue | |
$MainForm.WindowState = $InitialFormWindowState | |
} | |
$Form_StoreValues_Closing= | |
{ | |
#Store the control values | |
$script:MainForm_ProductListBox = $ProductListBox.SelectedItems | |
$script:MainForm_DescriptionText = $DescriptionText.Text | |
$script:MainForm_PleaseNnoteText = $PleaseNnoteText.Text | |
$script:MainForm_ArchitectureComboxBox = $ArchitectureComboxBox.Text | |
$script:MainForm_ArchitectureComboxBox_SelectedItem = $ArchitectureComboxBox.SelectedItem | |
$script:MainForm_DownloadComboBox = $DownloadComboBox.Text | |
$script:MainForm_DownloadComboBox_SelectedItem = $DownloadComboBox.SelectedItem | |
$script:MainForm_PlatformComboBox = $PlatformComboBox.Text | |
$script:MainForm_PlatformComboBox_SelectedItem = $PlatformComboBox.SelectedItem | |
$script:MainForm_OSComboBox = $OSComboBox.Text | |
$script:MainForm_OSComboBox_SelectedItem = $OSComboBox.SelectedItem | |
$script:MainForm_MicrosoftCheckBox = $MicrosoftCheckBox.Checked | |
$script:MainForm_LenovoCheckBox = $LenovoCheckBox.Checked | |
$script:MainForm_HPCheckBox = $HPCheckBox.Checked | |
$script:MainForm_DellCheckBox = $DellCheckBox.Checked | |
$script:MainForm_FullModelListBox = $FullModelListBox.SelectedItems | |
$script:MainForm_AcerCheckbox = $AcerCheckbox.Checked | |
$script:MainForm_PackagePathTextBox = $PackagePathTextBox.Text | |
$script:MainForm_RepositoryTextBox = $RepositoryTextBox.Text | |
$script:MainForm_PleaseNoteStorageText = $PleaseNoteStorageText.Text | |
$script:MainForm_EnableBinaryDifCheckBox = $EnableBinaryDifCheckBox.Checked | |
$script:MainForm_DPGListBox = $DPGListBox.SelectedItems | |
$script:MainForm_DPListBox = $DPListBox.SelectedItems | |
$script:MainForm_RemoveDriverSourceCheckbox = $RemoveDriverSourceCheckbox.Checked | |
$script:MainForm_RemoveLegacyDriverCheckbox = $RemoveLegacyDriverCheckbox.Checked | |
$script:MainForm_CleanUnusedCheckBox = $CleanUnusedCheckBox.Checked | |
$script:MainForm_SiteCodeText = $SiteCodeText.Text | |
$script:MainForm_SiteServerInput = $SiteServerInput.Text | |
$script:MainForm_UseProxyServerCheckbox = $UseProxyServerCheckbox.Checked | |
$script:MainForm_ProxyPswdInput = $ProxyPswdInput.Text | |
$script:MainForm_ProxyUserInput = $ProxyUserInput.Text | |
$script:MainForm_ProxyServerInput = $ProxyServerInput.Text | |
$script:MainForm_ProgressListBox = $ProgressListBox.SelectedItems | |
} | |
$Form_Cleanup_FormClosed= | |
{ | |
#Remove all event handlers from the controls | |
try | |
{ | |
$RemoveItemsButton.remove_Click($RemoveItemsButton_Click) | |
$DownloadComboBox.remove_SelectedIndexChanged($DownloadComboBox_SelectedIndexChanged) | |
$PlatformComboBox.remove_SelectedIndexChanged($PlatformComboBox_SelectedIndexChanged) | |
$OSComboBox.remove_SelectedIndexChanged($OSComboBox_SelectedIndexChanged) | |
$FindModelsButton.remove_Click($FindModelsButton_Click) | |
$AddToListButton.remove_Click($AddToListButton_Click) | |
$PackageBrowseButton.remove_Click($PackageBrowseButton_Click2) | |
$RepositoryBrowseButton.remove_Click($RepositoryBrowseButton_Click2) | |
$SCConfigMgrLink.remove_LinkClicked($SCConfigMgrLink_LinkClicked) | |
$ConnectSCCMButton.remove_Click($ConnectSCCMButton_Click) | |
$UseProxyServerCheckbox.remove_CheckedChanged($UseProxyServerCheckbox_CheckedChanged) | |
$ClearSelectionButton.remove_Click($ClearSelectionButton_Click) | |
$StartDownloadButton.remove_Click($StartDownloadButton_Click) | |
$MainForm.remove_FormClosing($MainForm_FormClosing) | |
$MainForm.remove_Load($MainForm_Load) | |
$MainForm.remove_Load($Form_StateCorrection_Load) | |
$MainForm.remove_Closing($Form_StoreValues_Closing) | |
$MainForm.remove_FormClosed($Form_Cleanup_FormClosed) | |
} | |
catch { Out-Null <# Prevent PSScriptAnalyzer warning #> } | |
} | |
#endregion Generated Events | |
#---------------------------------------------- | |
#region Generated Form Code | |
#---------------------------------------------- | |
$MainForm.SuspendLayout() | |
$SelectionTabs.SuspendLayout() | |
$OSTab.SuspendLayout() | |
$ManufacturerTab.SuspendLayout() | |
$DriverStorageTab.SuspendLayout() | |
$DistributionTab.SuspendLayout() | |
$DGGroupBox.SuspendLayout() | |
$DPGroupBox.SuspendLayout() | |
$DriverCleanTab.SuspendLayout() | |
$SCCMDellTabControl.SuspendLayout() | |
$ConfigMgrTabPage1.SuspendLayout() | |
$ConfigMgrTabPage2.SuspendLayout() | |
# | |
# MainForm | |
# | |
$MainForm.Controls.Add($ProductListBox) | |
$MainForm.Controls.Add($SCConfigMgrLogo) | |
$MainForm.Controls.Add($DescriptionText) | |
$MainForm.Controls.Add($RemoveItemsButton) | |
$MainForm.Controls.Add($SelectionTabs) | |
$MainForm.Controls.Add($SCConfigMgrLink) | |
$MainForm.Controls.Add($SCCMDellTabControl) | |
$MainForm.Controls.Add($ClearSelectionButton) | |
$MainForm.Controls.Add($ModelProgressOverlay) | |
$MainForm.Controls.Add($ProgressBar) | |
$MainForm.Controls.Add($ProgressListBox) | |
$MainForm.Controls.Add($AutomationLabel) | |
$MainForm.Controls.Add($StartDownloadButton) | |
$MainForm.Controls.Add($SelectedLabel) | |
$MainForm.Controls.Add($LoggingLabel) | |
$MainForm.Controls.Add($ModelProgressLabel) | |
$MainForm.Controls.Add($labelThisScriptIsUsedAtYo) | |
$MainForm.AutoScaleDimensions = '9, 17' | |
$MainForm.AutoScaleMode = 'Font' | |
$MainForm.BackColor = 'White' | |
$MainForm.ClientSize = '985, 661' | |
$MainForm.Font = 'Microsoft Sans Serif, 8.25pt, style=Bold' | |
$MainForm.FormBorderStyle = 'FixedSingle' | |
#region Binary Data | |
$MainForm.Icon = [System.Convert]::FromBase64String(' | |
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 | |
mZf/zMjH/9PPzv/V0dD/2dXU/93Z2P7h3dz65eLh+eXh4P/X0dDYzsjHMc3HxgDb19YAAAAAAAAA | |
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABaS0oAPiwrAEg2NTY/LCvVU0JA/5mPjP+2sKv/pJyY | |
/1pLSf9mV1X/samn/8O/vf/EwL7/yMTD/8rGxf+3sK//loyK9H9zccyHfHqvubKwn9/b2s/f29qr | |
3dnYDN7a2QAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAwry7AEc1NABMOzoiQjAvyFFAP/+U | |
iYb/qqKe/6CXk/9cTUv/aFlY/62lof+3saz/uLOu/7y3s/+wqaf/eW5s/1BAPv9aSkn+dGdl/X9z | |
cfh3a2nWf3NxgNPPzpXZ1dRd2tbVANfU0wAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABTQ0IAV0dG | |
CkY1NKFMOjn/hnp4/52UkP+bko7/aFpX/19PTv+imJX/q6Of/62mof+wqqX/mI+L/11NS/9iUlH/ | |
mY+M/7mzsP/Dvrz/xsLB/8bBwP+3sa/yraalftHNzHTQzMsVz8vKAAAAAAAAAAAAAAAAAAAAAAAA | |
AAAAbF5dADsoJwBNOzpeSDY193NlY/+Rh4P/koiE/3hsaf9VREP/j4WC/5+Wkv+hmJT/pZyY/4yB | |
fv9aSkn/e25s/6ykoP+0rqr/t7Gs/7q1r/68trL/vrm2/8K9vP/Cvbzjwr28cMS/vTrBvLsA//// | |
AAAAAAAAAAAAAAAAAAAAAABVREMAVkZFGUo4N8xeTkz/hXp2/4Z7d/+DeHT/WEhG/3ZpZv+Uiob/ | |
lIqH/5iPi/+Ifnr/X1BN/4J2dP+mnZn/qKCc662lobWPipOqf3uKqaahn5q5s63FubOv+by2s/+8 | |
trOusaqoTcjDwQHIw8AAAAAAAAAAAAAAAAAAdmhnAEMwLgBRQD9pUD49/XRoZf96b2v/fXJu/2pc | |
Wf9dTUv/h3x4/4l+ev+Mgn7/h315/2RYVP99cW7/mpGO8Z2VkZuknJg12c+6BhERTS4YGFypIiRz | |
u0BAdWaxq6R4s62o8bWvqummn5tom5GPCKeenAAAAAAAAAAAAAAAAABgUU8AYVNRDVA/Pb5fT07/ | |
cWZi/29kYP9wZWH/WUpI/3BjYP9+c2//f3Rw/4J3c/9tYV3/dGhl/5GHg9mTioZUnpaTBpmQjABE | |
RHkAVVr/AF1gyxI4O858LTDB5D5BuGarpJ2Jraah/6WdmYmBdnQLjoSBAAAAAAAwMHgANDR7AFxF | |
JABZSkg6U0NB8GhbV/9kWFP/ZlpV/2NXUv9bTEn/dGll/3JnY/92a2f/cmdj/25hXv+IfXrLi4F9 | |
NHhtaACUiocAAAAAAAAAAAAAAAAAOTzWAEVHzgUjJ86cKCzc4WFesWKhmJLqp5+bmI2EgwKXjosA | |
AAAAACsrfwAlJnsIDA1wZUM4T5VaS0j/YVVO/1pNRf9dUUr/Wk1I/2JVUv9rYFv/aF1Y/2xhXf9t | |
YV3/gHVx0YuBfTCOhIAAjoeDAAAAAAAAAAAAAAAAAAAAAAAAAAAAGhykAB8goT0fIszzKy7WqZCG | |
hceflpKur6mlA6mingAAAAAAERFzABMUdCoEBG3kNi9e+2pcWP9fU0z/TkE5/1RHP/9XS0b/ZllV | |
/19TTP9gVE3/Z1tWwHdpZquQhYJAjX99AHJoYwAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAlJYwA | |
ISB6Eh4ftc8hJNrid2+JwZaMh7Sfl5MFn5eTAF5eowAAAGoACgpxYgwMdv5MRGj/lYuH/722s/9v | |
ZF7/TT84/1hMR/9iVlH/VEc//1hLQ/diVk5OlomJB4R4dQKIfXoAAAAAAAAAAAAAAAAAAAAAAAAA | |
AAAAAAAAAAAAAD4+mQAlI0sFHR6lsR0f1vdiWo/QkIV9qp6WkgOdlJAASEiYAAAAAAAGBnGYGxuI | |
/1RMa/+lnZn/39va/9POzP+YkIz/YlZS/1pNR/9JOzP/UEI71WBUTRlfVEwAAAAAAAAAAAAAAAAA | |
AAAAAAAAAAAAAAAAAAAAAAAAAAD///8AAABxACgogh8bHJqwHB7R/VlRkOOKfnWSdGZjAKefnAAr | |
K4gAKyuHCgUFc74oKJ7/WE5q/6qjn//Szs3/1dLR/83Ix/RwZWH0f3Rw/2JVT/9OQDmodGpkA21h | |
WwAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAERElgBycpkBFxd/iyAhl+ocHc7+W1OK | |
94R5bmt9c28Ao5uYACAghAAdHYIWBgZ31DAxsv9bUm3/p5+b/8fDwv/KxsX/ycTD5nJnY9qrpKL/ | |
zMfF/66npHjOycgAraajAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAIiKCABkZeBUZ | |
GYXOIiOh/xoaxf9cUnrwgHVmOXZsZwAAAAAAGBiBABUVfxwJCnzeMDLD+lxTde2elZD/vrm2/8C7 | |
uf/Ev77qfnNwt5mQjv/QzMv/08/OYNHNzAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA | |
AGRjowAEBXAAExN2TxwckfceH6z/Hhy2/2RYa8CBdl8PcWdiAAAAAAAaGoQAFhaAHAsMgN0qLcz4 | |
VE2G0ZGHgP+0rqn/trCs/7u1sfiZkY2UhXt468G8u//GwsFhxcG/AAAAAAAAAAAAAAAAAAAAAAAA | |
AAAAAAAAAAAAAAAAAAAAJSV9ABwcbgoZGYGtKSqn/zI0zv84NbTfaFpaOkMuVwB5cGsAAAAAACEh | |
iwAbG4YTCwyD0CQoy/9DQau9gndw86qinv+tpqH/sKql/7CqpaF4bGieqqOg/7+5tne7trIAw726 | |
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAFBQlAAAAF4AEA9rVissofUzNbn/Q0bk/0tEm5P/tgAB | |
c2NYAAAAAAAAAAAALy+TADAwjwYLC4KyICLB/ywv1MFzZ2jImpGN/6Sbl/+nn5v/q6Of4pKIhFKQ | |
hoLIr6mkqMXAvAS3sq0AAAAAAAAAAAAAAAAAAAAAAAAAAABYWJQACgplAA8PZCcfH4XRNTjA/zk7 | |
yf9HRsjwZFhxPV9UeQD///8AAAAAAAAAAABgYK0AAABwAAwMgXsaG7T/ICPf6FROkIuHfHXvmZCM | |
/52UkP+hmJT/pJuXo4d9eTedlZGWraWhJqqjngDMx8UAAAAAAAAAAAAAAAAATU2JAAwMYQAPD18Z | |
GBhzszY4vv8xM7v/P0DU/19XmKbXyYsJtKqhAAAAAAAAAAAAAAAAAAAAAAANDYUAEBCBMxITougc | |
Htj/IyXXpXVqboeLgXz4k4mF/5aNif+akI36nJOPg52VkSCooJwVnJOQANHOygAiGBcAVUE+AD8t | |
LAhRPzk6RjlIWxkZbq40Nrf+LzHB/zk8yf9EP6bOgHNxKGdaagD///8AAAAAAAAAAAAAAAAAAAAA | |
ACcnkgAzMngDDw+SkRUXxf8aHNn1KCnQcYN3cXOKf3vmjYJ+/5CGgv+Uiob5lYuIwoF1c31lVlVS | |
VENCRlA/PlJXRkR4YVFPtFpOWe08N3H8NTe7/i0vyP81OL3/NzSv3Ec6WjwAAGgAwLSRAAAAAAAA | |
AAAAAAAAAAAAAAAAAAAAAAAAAA8PiQATE4UfDxCrxBUX0P8YGtbrIiTXaYB4hkKJfnajiX5564uA | |
fP6OhH//kIaB/42CfvyIfHj4g3d1+3VsdP9YU3b/PDyV/zM2zf8oK8b/MzW3/zQyruE3K1xKAAD/ | |
AFpDEgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAKimIAAoLowATFJQuEhO6xBMVz/8WGNP2 | |
JCbPuTo7qnlcV3p2b2dvm3ZtcLt3bnPPcGh02mJddvRHRXn/NTWQ/y8xvP8nK9X/JCe5/zM2ufc2 | |
ONWbNCprNW08AAFQOA0AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAANDNxABIT | |
yAAaG6QeFhjEkRMUz+sSFND/GRrN/iEjwfEmJ7DiKSqi4Cssn+gqK6bzKSu3/Scpzf8hJNf/HiDD | |
/ygqrP80N8DhMjbfai0x6wktMeYAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA | |
AAAAAAAAAAAAAAAAAAAAACssxAA3OLoEHyDNNxgZy5kSFM3aERPQ8xIU0vsVF9T9FxnU/Roc0f8Z | |
Gsf/Ghu0/yQlp/8wMbLsMzXOni0w5DAfJPgBKS3nAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA | |
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAMTEfQD//ygAT096Fjg4lE80NaeRKiuq | |
tycoqcssLafeMDGk8i4vpuUwMbPDMTPKhSwu3zcfIfEGJSfrAAAAAAAAAAAAAAAAAAAAAAAAAAAA | |
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAJqaDABy | |
c9UAfH2WBWNkrx5MTbI9Pj+1Ujg5vlY0NspJLzHbLikr8BAQEv8BHB7/AAAAAAAAAAAAAAAAAAAA | |
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAD//gP///gAf//gAD//wAAf/4AA | |
D/8AAAf+AAAH/AAAA/wAAAP4AAAB+AAAAfAADgHwAD8BwAB/gcAA/4HAAP+BwAP/g4AD/wOAB/8D | |
gAf/A4AH/geAB/4HgAP8D8AD+A/AA8AfwAAAP+AAAH/wAAB/+AAB//wAA///AA///4A//ygAAAAw | |
AAAAYAAAAAEAIAAAAAAAACQAACMuAAAjLgAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA | |
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA | |
AAAAAAAAAAAAAAAAAMvHxwAAAAAAZVhWBUs6OBREMzEkPSwpKz0rKCpEMzEfRzc1CEAwLQD///8A | |
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA | |
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA | |
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAH1xbwDHwb4ATj07Ej4sKkE4JiN7MiAdrC8cGc0wHRrhMR4b | |
5jEfHOAzIR7WNyUikEo6OBY4JyQA////AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA | |
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA | |
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABbTUoAbmJeAkU0MiU7KCZ4NSIgyDAd | |
GvMyHx3/RDMw/11NS/NXRkSrVENBgk8/PIlHNjSsPi0qxzooJZIzIB5WMyEeNDsqKBCZj48AYFJQ | |
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA | |
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAa1tcAAAAAABI | |
NjUdPSopgDckIt0yHx3+PCoo/2VWVP+ckpH/yMLB/9LMy/SSiIatNyUipi0aGNwuGxj0OCUj/EQy | |
MP5KOTf8SDc17kAuLMQ1IyBzKBYTHG9QTAASBQMAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA | |
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA | |
AAAAAAAAAABRQD8AXk9OBkIwL1Q6JybONiIh/j0qKP9rXVv/q6Kh/9DLyv/W0tH/q6Oh/2BRT/82 | |
JCH/Py0r/2tcWv+ckZD/vre2/9DKyf/X0dD/1M7N/8S8u/+hl5X9dmhmzVBAPlAIAAADKRgWAAAA | |
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA | |
AAAAAAAAAAAAAAAAAAAAAAAAAAAA6OToAEEwLgBQQD8SQC4tiDonJvE4JCP/VkZF/5ySkf/GwcH/ | |
zsrJ/7+6uf96bWz/Oykn/z8sKv97bWv/ubKx/9fT0v/f29r/4Nzb/+Hd3P/j397/5uLh/+nl5P/s | |
6Of/4t3c/7mxsO6Kf31uOyspBWBSUAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA | |
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAACvp6cAOygmAE4+PB5ALi2qOygn | |
/D0rKv9yZGL/tK2q/8O+vP/Dv77/qqOi/1xNTP83IyL/YFBP/6yjov/Py8r/0s/O/9PPzv/V0dD/ | |
19PS/9nV1P/c2Nf/3trZ/+Dc2//i3t3/5eHg/+jk4//X0dDyvLS0Z21hXwGxqagAAAAAAAAAAAAA | |
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAGtd | |
XABGNDMATz49IUIwLrg8KSj/RDEw/4R4df+3sKz/ubSv/7y2sv+dlJH/Tz89/z0qKf98b27/vbe2 | |
/8jEw//IxMP/ysbF/8zIx//Oysn/0c3M/9XR0P/X09L+2dXU79vX1t7f29rZ4d3c5eHd3Pnj397/ | |
39va5dvW1jva1dQA4t7dAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA | |
AAAAAAAAAAAAAAAAAAAA////AEs6OQBRQUAaQzIwtD4rKv9HNTT/in98/7Grpv+wqqX/s62o/5eO | |
iv9MOzr/QzEv/4t/ff+9t7T/v7q3/8C7uf/Cvbz/xL++/8bCwf/KxsX/xsHA/6qjof+EeXf8YlRS | |
1U08OrlNPTufbmBee722tWrg3Nuo3trZ9t/b2q7e2tkN3trZAAAAAAAAAAAAAAAAAAAAAAAAAAAA | |
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAVERDAFhIRw5GNDOgQC4t/0Y1NP+I | |
fHn/q6Kf/6mhnf+spaD/l46K/08/Pf9FMzL/jYJ//7exrP+2saz/ubOu/7q1sP+8t7P/v7q3/7+6 | |
uP+gmJf/Z1lX/z8tK/84JSP/RjQy/1dHRf9fUE7/WUlH9kk4NcJJODZZ08/NXdrX1tva1tVq29fW | |
ANrW1QAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABkVlUA | |
joOCAkk4N3pDMTD7RDMy/35xb/+jmpb/oZiU/6Sbl/+akY3/WUlH/0MyMf+Genj/sKml/66oo/+w | |
qqX/sqyn/7Suqf+4sq3/r6ik/3pta/9FNDP/QS8u/2dYV/+XjYv/ta6t/8K9vP/HwsH/xsHA/7ex | |
sP+UiojvbmFfbs3Ix03W0tG21dHQHtXR0AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA | |
AAAAAAAAAAAAAAAAAIyCgQA+LCsAUD8+RkY0M+tDMTD/b2Bf/5uSjv+Yj4v/mpGO/5qRjf9oWlj/ | |
QzEw/3dqaP+poJz/p5+b/6mhnf+ro5//raah/7CppP+fl5L/Y1RS/0MxMP9fT07/mpCO/7q0sP+/ | |
urf/v7q4/8C8uv/Cvrz/xMC//8fEwv/KxsX/ubOy8qKamV7QzMtq0MzKaM7KyQDRzcwAAAAAAAAA | |
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAFdHRQBcTEsWSjg3wUUzMv9dTUz/k4iF | |
/5GHg/+SiIT/lYuI/3pua/9HNTT/Y1RS/5+Vkv+flpL/oZiU/6Oalv+lnZn/qKCc/5aMiP9cTEr/ | |
Szk4/3pta/+tpaH/ta+q/7Wvqv+2sKz/ubOu/7u1sf+9t7P/vrm2/8C7uf/Cvrz/xcC//8K+vNrC | |
vbtHxsLAh8zIxw7MyMcAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAcmZlAAAA | |
AABQPj11SDY1/U49PP+FeHb/i4F9/4uAfP+Og3//h3x4/1VFQ/9RPz7/j4SB/5iPi/+Yj4v/mpGN | |
/52UkP+gl5P/kYeD/11NS/9SQUD/iHt5/6ykoP+spKD/raWh/66oo/+xq6b6tq+p8Lexq++3saz5 | |
uLOu/7q1sf+9t7T/v7m3/8C8uv/BvbuSt7GvZ8C7uTS/urgAAAAAAAAAAAAAAAAAAAAAAAAAAAAA | |
AAAAAAAAAAAAAAAAAAAAVkVEAFpKSSNMOzrYSTc2/25gXv+HfHn/gndz/4V6dv+HfHj/a1xa/0o4 | |
N/92aGb/lIqG/5CGgv+SiIX/lIqH/5eNiv+PhYH/YlRR/1ZGRP+Kfnz/pZ2Z/6Oalv+mnZn3qaGc | |
yq6moYiGgo9+VVNzk2hlfXGemZ1fubSuf7awq8q3saz7ubOu/7u1sf+9t7TlsauoZa+oplCdlZMA | |
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAB/c3IAAAAAAFNCQHtLOTj/V0ZF/4F1cv96 | |
b2v/fHFt/390cP96bmr/VENB/1pJSP+MgH3/iX56/4uAfP+Ngn7/j4WB/42Df/9qXlr/V0pG/4V5 | |
dv+dlJH/m5KO+Z+Wkrqkm5dUqqKfEwAAKQAkJF0cDAxKqg8PTugSEk7DFBREZnp2fSW2sKp2s62o | |
7LWvqv+3saz/tK6pmJ6Vk1jHwb8Ez8rIAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAABfT00A | |
YVFQGVA/PtBNOzr/cGFf/3dtaf9zaGT/dWpm/3htaf9nWVb/Tz08/3VnZf+Fenf/gndz/4V6dv+H | |
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 | |
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA | |
AAAAAAAAAAAAAAAAAAAAAAD///+A//8AAP///AB//wAA///gAA//AAD//8AAA/8AAP//AAAA/wAA | |
//4AAAB/AAD//AAAAD8AAP/4AAAAPwAA//AAAAAfAAD/4AAAAB8AAP/AAAAADwAA/8AAAAAPAAD/ | |
gAAAAAcAAP+AAAAABwAA/wAAAAAHAAD/AAAAgAMAAP4AAAPAAwAA/gAAD/ADAAD8AAAf+AMAAPAA | |
AD/4BwAA8AAAf/wHAADwAAD//AcAAOAAAf/8BwAA4AAH//4HAADgAA//+AcAAOAAD//4BwAAwAAP | |
//gHAADAAA//+AcAAMAAH//wDwAAwAAf//APAADAAB//8A8AAMAAH//gHwAAwAAP/8A/AADAAA// | |
wD8AAOAAD/+AfwAA4AAH/wB/AADgAAf4AP8AAPAAB8AA/wAA8AAAAAH/AAD4AAAAA/8AAPwAAAAH | |
/wAA/gAAAA//AAD/AAAAP/8AAP+AAAB//wAA/+AAAf//AAD/4AAH//8AAP/4AB///wAA//8B//// | |
AAAoAAAA4gAAAL4BAAABACAAAAAAAHgTAwAjLgAAIy4AAAAAAAAAAAAA////AP///wD///8A//// | |
AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A | |
////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD/ | |
//8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP// | |
/wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A//// | |
AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A | |
////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD/ | |
//8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP// | |
/wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A//// | |
AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A | |
////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD/ | |
//8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP// | |
/wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A//// | |
AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A | |
////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD/ | |
//8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP// | |
/wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A//// | |
AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A | |
////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD/ | |
//8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP// | |
/wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A//// | |
AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A | |
////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD/ | |
//8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP// | |
/wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A//// | |
AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A | |
////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD/ | |
//8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP// | |
/wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A//// | |
AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A | |
////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD/ | |
//8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP// | |
/wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A//// | |
AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A | |
////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD/ | |
//8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP// | |
/wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A//// | |
AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A | |
////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD/ | |
//8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP// | |
/wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A//// | |
AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A | |
////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD/ | |
//8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP// | |
/wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A//// | |
AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A | |
////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD/ | |
//8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP// | |
/wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A//// | |
AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A | |
////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD/ | |
//8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP// | |
/wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A//// | |
AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A | |
////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD/ | |
//8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP// | |
/wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A//// | |
AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A | |
////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD/ | |
//8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP// | |
/wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A//// | |
AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A | |
////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD/ | |
//8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP// | |
/wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A////AP///wD///8A//// | |
AP///wD///8A39zcAN/c3ADf3NwA39zcAN/c3ADf3NwA39zcAN/c3ADf3NwA39zcAN/c3ADf3NwA | |
39zcAN/c3ADf3NwA39zcAN/c3ADf3NwA39zcAN/c3ADf3NwA39zcAN/c3ADf3NwA39zcAN/c3ADf | |
3NwA39zcAN/c3ADf3NwA39zcAN/c3ADf3NwA39zcAN/c3ADf3NwA39zcAN/c3ADf3NwA39zcAN/c | |
3ADf3NwA39zcAN/c3ADf3NwA39zcAN/c3ADd2toAzcnJAL+6uQC2sK8AtK6tALy1tQDGwcAA3NjY | |
ALGpqQCflpYAzcnIAKObmgCup6YAjIGBAMO+vQCup6YAqqKhAKujogCtpqUAs6yrAKefngCimZkA | |
npaVAKeengCjm5oAlIqJAJSKigCelZQAmZCPAIl+fQCxqqoApJybAJ6VlACZkZAAo5uaAKykowCl | |
nZwAgHR0AJ6WlACspKQAlIuKAJmQjwCck5IAnpWUAK+npwCup6YAqaGgAKegnwCupqcAj4WDAI+E | |
gwCgl5YArKSkAKaengCdlJMAqaGhAK+oqACSiIgArKSkAJOKiAC7tbUAg3l3ALy1tACGe3oAwry9 | |
D5qQjx9uYF8snZSUSY+FhF9wY2JvWUlIe0w7OoNALyyHUUE/jHFlYqltYF6iRjUyiUIyL4dPPzyB | |
X1FQd3pvbWmdlJRZlYyLPXxxbyW7tbQXo5ycAZuTkgDJxMQAq6OjAMfCwgCyrKsAoJiXAMzIxwDA | |
uroAopqZAMjCwgCqo6IAmZCQAJ6WlgCPhoUAi4B/AKmhoQChmZcAqKCgA |