import depuis ancien GitHub

This commit is contained in:
David Wuibaille
2025-10-31 08:38:13 +01:00
parent 6f3aeedc93
commit 6a2f2de58e
745 changed files with 178444 additions and 0 deletions

View File

@@ -0,0 +1,718 @@
#cs ----------------------------------------------------------------------------
AutoIt Version: 3.2.12.1
Author: Jan Buelens, Landesk Software (idea stolen from Sergio Ribeiro)
Script Function:
CopyDrivers. This script copies machine dependent drivers to a provisioning / OSD client machine.
A mapping table (CopyDrivers.ini) is used to map the WMI machine model to a driver source folder.
A GUI is included to build CopyDrivers.ini
Version: 1.5.1
#ce ----------------------------------------------------------------------------
#include <GUIConstantsEx.au3>
#include <WindowsConstants.au3>
#include <EditConstants.au3>
#include <StaticConstants.au3>
Dim $iniFilename = ""
Dim $Manufacturer = ""
Dim $Model = ""
Dim $Version = ""
Dim $subfolder = ""
Dim $SourceFolder = ""
Dim $TargetFolder = ""
Dim $sysprep = "C:\sysprep\sysprep.inf"
Dim $bVerbose = False
Dim $bRunOnce = True
Dim $bCmdLines = True
; ===========================================================================================
; Validate command line parameters and verify that copydrivers.ini exists
; ===========================================================================================
If $CmdLine[0] = 0 Then DoGui() ; no command line parameters - do gui
If $CmdLine[0] > 0 And ($CmdLine[1] = "/?" Or $CmdLine[1] = "-?" Or $CmdLine[1] = "help") Then
Usage()
EndIf
For $n = 1 to $CmdLine[0]
if $CmdLine[$n] = "/s" Or $CmdLine[$n] = "-s" Then
if $n >= $CmdLine[0] Then Usage()
$SourceFolder = $CmdLine[$n + 1]
$n = $n + 1
ElseIf $CmdLine[$n] = "/d" Or $CmdLine[$n] = "-d" Then
if $n >= $CmdLine[0] Then Usage()
$TargetFolder = $CmdLine[$n + 1]
$n = $n + 1
ElseIf $CmdLine[$n] = "/c" Or $CmdLine[$n] = "-c" Then
; if no other command line parameters are required, use /c to copy drivers rather than launch GUI
ElseIf $CmdLine[$n] = "/v" Or $CmdLine[$n] = "-v" Then
$bVerbose = True;
;If there is a reason for not doing the cmdlines and GuiRunOnce stuff, uncomment these lines
; ElseIf $CmdLine[$n] = "/cmdlines" Or $CmdLine[$n] = "-cmdlines" Then
; $bCmdLines = False
; ElseIf $CmdLine[$n] = "/RunOnce" Or $CmdLine[$n] = "-RunOnce" Then
; $bRunOnce = False
Else
Usage()
EndIf
Next
$iniFilename = @ScriptDir & "\copydrivers.ini" ; @ScriptDir is folder in which this script (or compiled program) resides
If not FileExists($iniFilename) Then ErrorExit("File not found: " & $iniFilename, 2)
; If no source and target folders were defined on the command line, take them from the [Config] section of copydrivers.ini
If $SourceFolder = "" Then $SourceFolder = IniRead($iniFilename, "Config", "DriversSource", "")
If $TargetFolder = "" Then $TargetFolder = IniRead($iniFilename, "Config", "DriversTarget", "")
If $SourceFolder = "" Then ErrorExit("No Drivers Source Folder defined", 3)
If $TargetFolder = "" Then ErrorExit("No Drivers Target Folder defined", 4)
; MsgBox(0, "CopyDrivers", "source: " & $SourceFolder & @CRLF & "target: " & $TargetFolder);
; ===========================================================================================
; Read Manufacturer, Model and Version from WMI. We only use Model.
; ===========================================================================================
ReadWmi($Manufacturer, $Model, $Version)
; ===========================================================================================
; Find a match for WMI Model in [Models] section of copydrivers.ini
; ===========================================================================================
;IniReadSection returns a 2 dimensional array of keywords and values; $ini[n][0] is key # n, $ini[n][1] is value # n; $ini[0][0] is the number of elements
$ini = IniReadSection($iniFilename, "Models")
if @error OR $ini[0][0] = 0 Then ErrorExit("There is no [Models] section in " & $iniFilename, 5)
; Take WMI Model and find match in ini file
For $n = 1 to $ini[0][0]
if $ini[$n][0] = $Model Then
$subfolder = $ini[$n][1]
ExitLoop
EndIf
Next
if $subfolder = "" Then ErrorExit("No match found for Model """ & $Model & """ in " &$iniFilename, 6)
If $bVerbose Then MsgBox(0, "CopyDrivers","Manufacturer: " & $Manufacturer & @CRLF & "Model: " & $Model & @CRLF & "Version: " & $Version & @CRLF & "subfolder: " & $subfolder)
; ===========================================================================================
; Copy the driver files
; ===========================================================================================
$src = $SourceFolder & "\" & $subfolder
If Not IsFolder($src) Then ErrorExit("Source folder not found: " & $src, 7)
DirCreate($TargetFolder)
If Not IsFolder($TargetFolder) Then ErrorExit("Unable to create target folder: " & $TargetFolder, 8)
If Not DirCopy($src, $TargetFolder, 1) Then ErrorExit("Unable to copy folder: " & $TargetFolder, 9) ; 1 on DirCopy means overwrite existing files
; ===========================================================================================
; Handle RunOnce and CmdLines
; ===========================================================================================
if $bRunOnce Then DoRunOnce()
if $bCmdLines Then DoCmdLines()
; ===========================================================================================
; Done
; ===========================================================================================
; ===========================================================================================
Func DoCmdLines()
; Run at deployment time if the $bCmdLines is true. If there is a cmdlines.txt file in the drivers folder that we just copied, set up
; sysprep.inf such that it will be processed at mini-setup time. If sysprep.inf already refers to a cmdlines.txt file, merge it. The cmdlines.txt file must be
; in the format as described in the sysprep documentation. Example:
;
; [cmdlines]
; "c:\drivers\setup\driver1\setup.exe"
;
; This program also has a GUI that allows cmdlines.txt to be edited in a convenient way, without the user being aware of the format or the location of the file.
; ===========================================================================================
Dim $MyBase = $TargetFolder
Dim $MyCmdLines = $MyBase & "\cmdlines.txt"
Dim $oemFolder = ""
Dim $OemCmdLines = ""
if not FileExists($MyCmdLines) Then Return
if not FileExists($sysprep) Then ErrorExit("File not found: " & $sysprep, 2)
$InstallFilesPath = Iniread($sysprep, "unattended", "InstallFilesPath", "")
if $InstallFilesPath = "" Then
; no InstallFilesPath in sysprep.inf - create one
$InstallFilesPath = $MyBase
IniWrite($sysprep, "unattended", "InstallFilesPath", $InstallFilesPath)
EndIf
$oemFolder = $InstallFilesPath & "\$oem$"
$OemCmdLines = $oemFolder & "\cmdlines.txt"
if not FileExists($OemCmdLines) Then
; no $oem$\cmdlines.txt exist - just copy ours
$success = FileCopy($MyCmdLines, $OemCmdLines, 8) ; 8 = create folders
if $success = 0 Then ErrorExit("Copy " & $MyCmdLines & " to " & $OemCmdLines & " failed", 3)
Exit 0
EndIf
; A $oem$\cmdlines.txt already exists - append ours
$file1 = FileOpen($MyCmdLines, 0) ; 0 = read
if $file1 = -1 Then ErrorExit("Error opening " & $MyCmdLines, 5)
$file2 = FileOpen($OemCmdLines, 1) ; 1 = append
if $file2 = -1 Then ErrorExit("Error opening " & $OemCmdLines, 4)
While 1
$line = FileReadLine($file1)
If @error Then ExitLoop
If StringStripWS($line,8) <> "[commands]" Then ; StringStripWS($line,8) strips all white space
FileWriteLine($file2, $line)
EndIf
Wend
FileClose($file1)
FileClose($file2)
EndFunc
; ===========================================================================================
Func DoRunOnce()
; Run at deployment time if the $bRunonce is true. If there is a file called GuiRunOnce.ini in the drivers
; folder that we just copied, merge its GuiRunOnce section with the sysprep.inf GuiRunOnce section. The GuiRunOnce.ini file must be
; in the format as described in the sysprep documentation. Example:
;
; [GuiRunOnce]
; Command0="c:\drivers\driver1\setup.exe"
; Command1="c:\drivers\driver2\setup.exe"
;
; This program also has a GUI that allows GuiRunOnce.ini to be edited in a convenient way, without the user to be aware of the format or the location of the file.
; ===========================================================================================
Dim $MyRunOnce = $TargetFolder & "\GuiRunOnce.ini"
if not FileExists($MyRunOnce) Then Return
if not FileExists($sysprep) Then ErrorExit("File not found: " & $sysprep, 2)
Dim $section1[1][1]
$section1[0][0] = 0
$section1 = IniReadSection($sysprep, "GuiRunOnce")
if @error Then
Dim $section1[1][1]
$section1[0][0] = 0
EndIf
$section2 = IniReadSection($MyRunOnce, "GuiRunOnce")
if @error Then Return
if $section2[0][0] = 0 Then Return
$count = $section1[0][0]
For $i = 1 To $section2[0][0]
$count = $count + 1
ReDim $section1[$count + 1][2]
$section1[$count][0] = $section2[$i][0]
$section1[$count][1] = $section2[$i][1]
Next
$section1[0][0] = $count
For $i = 1 To $section1[0][0]
$section1[$count][0] = "Command" & ($i - 1)
Next
IniWriteSection($sysprep, "GuiRunOnce", $section1)
EndFunc
; ===========================================================================================
; Set the 3 WMI attributes mentioned. We only use the Model, but feel free to organise things differently
Func ReadWmi(ByRef $Manufacturer, ByRef $Model, ByRef $Version)
; ===========================================================================================
$objWMIService = ObjGet("winmgmts:{impersonationLevel=impersonate}!\\.\root\cimv2")
If $objWMIService = 0 Then ErrorExit("Failed to connect to WMI", 10)
$colRows = $objWMIService.ExecQuery("SELECT * FROM Win32_ComputerSystem")
For $row In $colRows
$Manufacturer = StringStripWS($Row.Manufacturer, 3)
$Model = StringStripWS($Row.Model, 3)
Next
$colRows = $objWMIService.ExecQuery("SELECT * FROM Win32_ComputerSystemProduct")
For $row In $colRows
$Version = StringStripWS($Row.Version, 3)
Next
Return True
EndFunc
; ===========================================================================================
Func Usage()
; ===========================================================================================
Msgbox ("0", "CopyDrivers V1.5.1", _
"This program copies machine specific drivers from a source folder on a" _
& @CRLF & "server to a destination folder on the local machine." & @CRLF _
& @CRLF & "Usage: CopyDrivers [/s <sourcedir>] [/d <destdir>] [/cmdlines] [/RunOnce] [/c] [/v]" _
& @CRLF & "where <sourcedir> is the base path for machine specfic driver folders" _
& @CRLF & " <destdir> is the target folder on the local machine." _
& @CRLF & " /v: verbose" _
& @CRLF & " /c: copy" & @CRLF _
& @CRLF & "CopyDrivers requires a list that associates machine types with driver folders." _
& @CRLF & "This list is to be supplied in the [Models] section of copydrivers.ini, which" _
& @CRLF & "associates WMI model names with specific subfolders of <sourcedir>." & @CRLF _
& @CRLF & "When invoked without command line switches, CopyDrivers opens a GUI that allows" _
& @CRLF & "copydrivers.ini to be edited. Use /c to do the copying rather than show the GUI." _
)
Exit 1
EndFunc
; ===========================================================================================
; The remainder of the file is just GUI stuff. It does nothing that you can't do by simply editing the CopyDrivers.ini file
; ===========================================================================================
; ===========================================================================================
; Main GUI function called when program is invoked with no command line parameters
Func DoGui()
; ===========================================================================================
$iniFilename = @ScriptDir & "\copydrivers.ini" ; @ScriptDir is folder in which this script (or compiled program) resides
$SourceFolder = IniRead($iniFilename, "Config", "DriversSource", "")
$TargetFolder = IniRead($iniFilename, "Config", "DriversTarget", "")
#Region ### START Koda GUI section ### Form=z:\install\autoit\koda_1.7.0.1\forms\myform1.kxf
$Form_Main = GUICreate("CopyDrivers", 452, 322)
$BtnOK = GUICtrlCreateButton("OK", 16, 280, 97, 25, 0)
$EditSource = GUICtrlCreateInput("", 13, 32, 305, 21)
GUICtrlSetState(-1, $GUI_DISABLE)
$BtnConfig = GUICtrlCreateButton("Edit", 335, 32, 57, 21, 0)
$ListView1 = GUICtrlCreateListView("WMI Model|Subfolder", 13, 120, 305, 145)
GUICtrlSendMsg(-1, 0x101E, 0, 150)
GUICtrlSendMsg(-1, 0x101E, 1, 150)
; GUICtrlSetTip(-1, "abc")
$BtnAdd = GUICtrlCreateButton("Add", 335, 126, 57, 21, 0)
$BtnEdit = GUICtrlCreateButton("Edit", 335, 157, 57, 21, 0)
$BtnDelete = GUICtrlCreateButton("Delete", 335, 190, 57, 21, 0)
GUICtrlCreateLabel("Drivers source folder", 16, 14, 101, 17)
$BtnCancel = GUICtrlCreateButton("Cancel", 133, 281, 97, 25, 0)
$EditTarget = GUICtrlCreateInput("", 13, 79, 305, 21)
GUICtrlSetState(-1, $GUI_DISABLE)
GUICtrlCreateLabel("Drivers target folder", 16, 61, 96, 17)
GUISetState(@SW_SHOW)
#EndRegion ### END Koda GUI section ###
GUICtrlSetData($EditSource, $SourceFolder)
GUICtrlSetData($EditTarget, $TargetFolder)
;IniReadSection returns a 2 dimensional array of keywords and values; $ini[n][0] is key # n, $ini[n][1] is value # n; $ini[0][0] is the number of elements
$items = 0
$count = 0
$ini = IniReadSection($iniFilename, "Models")
if not @error Then
$items = $ini[0][0]
EndIf
$count1 = $items
if ($items = 0) Then $count1 = 1
Dim $item [$count1] [4] ; we'll store the model in item[n][0], the folder in item[n][1], the listview controlid in item[n][2] and the state (0 = deleted, 1 = active) in item[n][3]
if $items = 0 Then
; if the section was empty or non-existing, we create one dummy item to avoid run-time errors
$item[0][0] = ""
$item[0][1] = ""
$item[0][2] = 0
$item[0][3] = 0
EndIf
For $n = 1 to $items
$item[$n-1][0] = $ini[$n][0]
$item[$n-1][1] = $ini[$n][1]
$item[$n-1][2] = GUICtrlCreateListViewItem($ini[$n][0] & "|" & $ini[$n][1], $ListView1)
$item[$n-1][3] = 1
$count = $count + 1
Next
While 1
$nMsg = GUIGetMsg()
Switch $nMsg
Case $GUI_EVENT_CLOSE
Exit
Case $BtnOK
IniWrite($iniFilename, "Config", "DriversSource", $SourceFolder)
IniWrite($iniFilename, "Config", "DriversTarget", $TargetFolder)
Dim $ini[$count][2]
$i = 0
for $n = 0 to UBound($item) - 1
if $item[$n][3] = 1 Then
$ini[$i][0] = $item[$n][0]
$ini[$i][1] = $item[$n][1]
$i = $i + 1
EndIf
Next
IniWriteSection($iniFilename, "Models", $ini, 0)
Exit
Case $BtnCancel
Exit
Case $BtnConfig
$newSource = $SourceFolder
$newTarget = $TargetFolder
if EditConfig($newSource, $newTarget) Then
$SourceFolder = $newSource
$TargetFolder = $newTarget
GUICtrlSetData($EditSource, $SourceFolder)
GUICtrlSetData($EditTarget, $TargetFolder)
EndIf
Case $BtnDelete
$id = GUICtrlRead($ListView1)
for $n = 0 to UBound($item) - 1
if $item[$n][2] = $id And $item[$n][3] = 1 Then
GUICtrlDelete($id)
$item[$n][3] = 0
$count = $count - 1
EndIf
Next
Case $BtnAdd
Dim $newModel = ""
Dim $newFolder = ""
If AddModel($newModel, $newFolder, 0) Then
$n = UBound($item);
ReDim $item[$n+1][4]
$item[$n][0] = $newModel
$item[$n][1] = $newFolder
$item[$n][2] = GUICtrlCreateListViewItem($newModel & "|" & $newFolder, $ListView1)
$item[$n][3] = 1
$count = $count + 1
EndIf
Case $BtnEdit
$id = GUICtrlRead($ListView1)
for $n = 0 to UBound($item) - 1
if $item[$n][2] = $id And $item[$n][3] = 1 Then
ExitLoop
EndIf
Next
if $n >= UBound($item) Then ContinueLoop
Dim $newModel = $item[$n][0]
Dim $newFolder = $item[$n][1]
If AddModel($newModel, $newFolder, 1) Then
$item[$n][0] = $newModel
$item[$n][1] = $newFolder
GUICtrlSetData($id, $newModel & "|" & $newFolder)
EndIf
EndSwitch
WEnd
EndFunc
; ===========================================================================================
; GUI function called when the Add or Edit button is pressed.
Func AddModel(ByRef $model, ByRef $folder, $flag) ; flag = 0: Add flag = 1: Edit
; ===========================================================================================
$title = "Add Model"
if $flag = 1 Then $title = "Edit Model"
#Region ### START Koda GUI section ### Form=Z:\install\AutoIt\koda_1.7.0.1\Forms\Form_AddItem.kxf
$Form_AddModel = GUICreate($title, 429, 413)
GUICtrlCreateGroup("", 8, 1, 297, 137)
$InputModel = GUICtrlCreateInput("", 16, 40, 209, 21)
$InputFolder = GUICtrlCreateInput("", 16, 97, 209, 21, BitOR($ES_AUTOHSCROLL,$ES_READONLY) )
GUICtrlCreateLabel("Model", 16, 16, 33, 17)
GUICtrlCreateLabel("Subfolder", 17, 73, 49, 17)
$Btn_WMI = GUICtrlCreateButton("WMI", 236, 40, 57, 21, 0)
$BtnBrowse = GUICtrlCreateButton("..", 236, 97, 57, 21, 0)
$CmdLines = GUICtrlCreateEdit("", 16, 192, 385, 81, BitOR($ES_AUTOVSCROLL,$ES_AUTOHSCROLL,$ES_WANTRETURN,$WS_HSCROLL,$WS_VSCROLL,$WS_BORDER), $ES_MULTILINE)
$ButtonOK = GUICtrlCreateButton("&OK", 321, 11, 75, 25, 0)
$ButtonCancel = GUICtrlCreateButton("&Cancel", 322, 43, 75, 25, 0)
$RunOnce = GUICtrlCreateEdit("", 16, 304, 385, 81, BitOR($ES_AUTOVSCROLL,$ES_AUTOHSCROLL,$ES_WANTRETURN,$WS_HSCROLL,$WS_VSCROLL,$WS_BORDER), $ES_MULTILINE)
GUICtrlCreateGroup("Command lines for drivers that require a setup program", 8, 152, 409, 249)
GUICtrlCreateLabel("Before reboot (cmdlines.txt)", 16, 174, 132, 17)
GUICtrlCreateLabel("After reboot (GuiRunonce section of sysprep.inf)", 16, 287, 230, 17)
GUISetState(@SW_SHOW)
#EndRegion ### END Koda GUI section ###
GUICtrlSetData($InputModel, $model)
GUICtrlSetData($InputFolder, $folder)
; If the model specific folder exists, read the cmdlines.txt and GuiRunOnce.txt files from it and display their contents in the $cmdlines and $RunOnce edit boxes.
; If the model specific folder does not exist, disable the edit boxes
$RunOnceText = ""
$CmdLinesText = ""
$ModelFolder = $SourceFolder & "\" & $folder
if $SourceFolder = "" or $folder = "" Then $ModelFolder = "---dummy---"
if IsFolder($ModelFolder) Then
$CmdLinesText = ReadCmdLines($ModelFolder)
GUICtrlSetData($CmdLines, $CmdLinesText)
$RunOnceText = ReadRunOnce($ModelFolder)
GUICtrlSetData($RunOnce, $RunOnceText)
Else
GUICtrlSetState($CmdLines, $GUI_DISABLE)
GUICtrlSetState($RunOnce, $GUI_DISABLE)
EndIf
While 1
$nMsg = GUIGetMsg()
Switch $nMsg
Case $GUI_EVENT_CLOSE
Return False
Case $ButtonCancel
GUIDelete($Form_AddModel)
Return False
Case $BtnBrowse
$flag = 1
if IsWinPE() Then $flag = 0
$old = $SourceFolder + "\" + GUICtrlRead($InputFolder)
$new = FileSelectFolder("Select Folder", $SourceFolder, $flag, $ModelFolder) ; $flag = 1 : Show Create Folder Button (does not work in WinPE)
if $new <> "" Then
$new = StringMid($new, StringLen($SourceFolder) + 2)
GUICtrlSetData($InputFolder, $new)
EndIf
$ModelFolder = $SourceFolder & "\" & $new
if $SourceFolder = "" or $new = "" Then $ModelFolder = "---dummy---"
if IsFolder($ModelFolder) Then
; User selected a new model specific folder - and the folder exists. Read the cmdlines.txt and GuiRunOnce.txt files from it and display their contents in the
; $cmdlines and $RunOnce edit boxes.
GUICtrlSetState($CmdLines, $GUI_ENABLE)
GUICtrlSetState($RunOnce, $GUI_ENABLE)
$CmdLinesText = ReadCmdLines($ModelFolder)
$RunOnceText = ReadRunOnce($ModelFolder)
Else
; User selected a new model specific folder - and the folder does not exist. Disable the $cmdlines and $RunOnce edit boxes.
GUICtrlSetState($CmdLines, $GUI_DISABLE)
GUICtrlSetState($RunOnce, $GUI_DISABLE)
$CmdLinesText = ""
$RunOnceText = ""
EndIf
GUICtrlSetData($CmdLines, $CmdLinesText)
GUICtrlSetData($RunOnce, $RunOnceText)
Case $Btn_WMI
ReadWmi($Manufacturer, $Model, $Version)
GUICtrlSetData($InputModel, $Model)
Case $ButtonOK
$model = StringStripWS(GUICtrlRead($InputModel),3)
$folder = StringStripWS(GUICtrlRead($InputFolder),3)
If $model = "" Then
MsgBox(0, "CopyDrivers", "A model is required")
ElseIf $folder = "" Then
MsgBox(0, "CopyDrivers", "A folder is required")
Else
$newCmdLinesText = GUICtrlRead($CmdLines)
$newRunOnceText = GUICtrlRead($RunOnce)
GUIDelete($Form_AddModel)
if IsFolder($ModelFolder) Then
if $newCmdLinesText <> $CmdLinesText Then SaveCmdLines($ModelFolder, $newCmdLinesText)
if $newRunOnceText <> $RunOnceText Then SaveRunOnce ($ModelFolder, $newRunOnceText)
EndIf
return True
EndIf
EndSwitch
WEnd
EndFunc
; ===========================================================================================
; GUI function to edit the SOurce Folder and target folder settings
Func EditConfig(ByRef $source, ByRef $target)
; ===========================================================================================
#Region ### START Koda GUI section ### Form=Z:\install\AutoIt\koda_1.7.0.1\Forms\Form_Config.kxf
$Form_Config = GUICreate("Edit Config", 316, 197)
; GUISetIcon("D:\003.ico")
GUICtrlCreateGroup("", 8, 1, 297, 153)
$EditSource = GUICtrlCreateInput("", 16, 38, 217, 21)
$EditTarget = GUICtrlCreateInput("", 16, 110, 217, 21)
GUICtrlCreateLabel("Drivers Source Folder (Specify UNC path)", 16, 16, 200, 17)
GUICtrlCreateLabel("DriversTarget Folder", 16, 87, 100, 17)
$BtnBrowse = GUICtrlCreateButton("..", 244, 38, 57, 21, 0)
GUICtrlCreateGroup("", -99, -99, 1, 1)
$BtnOK = GUICtrlCreateButton("&OK", 65, 163, 75, 25, 0)
$BtnCancel = GUICtrlCreateButton("&Cancel", 162, 163, 75, 25, 0)
GUISetState(@SW_SHOW)
#EndRegion ### END Koda GUI section ###
GUICtrlSetData($EditSource, $source)
GUICtrlSetData($EditTarget, $target)
While 1
$nMsg = GUIGetMsg()
Switch $nMsg
Case $GUI_EVENT_CLOSE
Return False
Case $BtnCancel
GUIDelete($Form_Config)
Return False
Case $BtnOK
$source = StringStripWS(GUICtrlRead($EditSource),3)
$target = StringStripWS(GUICtrlRead($EditTarget),3)
if $source = "" Then
MsgBox(0, "CopyDrivers", "A source folder is required")
Else
GUIDelete($Form_Config)
Return True
EndIf
Case $BtnBrowse
$new = FileSelectFolder("Select Source Folder", "", 0, $source)
$new = StringStripWS($new,3)
GUICtrlSetData($EditSource, $new)
if $new <> "" Then $source = $new
EndSwitch
WEnd
EndFunc
; ===========================================================================================
; Used by GUI to read cmdlines.txt from specified folder. The data is returned in a format ready to be fed into a GUI edit box
; (lines separated by CR-LF). The header line ([Commands]) is not included in the data.
Func ReadCmdLines($folder)
; ===========================================================================================
$retstring = ""
$filename = $folder & "\cmdlines.txt"
$lineno = 0
$file = FileOpen($filename, 0) ; 0 = read
if $file = -1 Then return ""
While 1
$line = FileReadLine($file)
If @error Then ExitLoop
If StringStripWS($line,8) = "[commands]" Then ContinueLoop ; StringStripWS($line,8) strips all white space
$line = StringStripWS($line, 3) ; 3 = strip leading & trailing while space
if $line = "" Then ContinueLoop
if StringLeft($line, 1) = '"' And StringRight($line, 1) = '"' Then
$line = StringTrimLeft($line, 1)
$line = StringTrimRight($line, 1)
EndIf
$line = StringStripWS($line, 3) ; 3 = strip leading & trailing while space
if $line = "" Then ContinueLoop
if $lineno > 0 Then $retstring = $retstring & @CRLF
$lineno = $lineno + 1
$retstring = $retstring & $line
Wend
FileClose($file)
return $retstring
EndFunc
; ===========================================================================================
; Used by GUI to read GuiRunOnce.ini from specified folder. The data is returned in a format ready to be fed into a GUI edit box
; (lines separated by CR-LF). The header line ([GuiRunOnce]) is not included in the data, nor are the CommandN= prefixes.
Func ReadRunOnce($folder)
; ===========================================================================================
$retstring = ""
$filename = $folder & "\GuiRunOnce.ini"
$lineno = 0
$lines = IniReadSection($filename, "GuiRunOnce")
if @error Then return ""
for $i = 1 to $lines[0][0]
$line = $lines[$i][1]
if $line = "" Then ContinueLoop
if StringLeft($line, 1) = '"' And StringRight($line, 1) = '"' Then
$line = StringTrimLeft($line, 1)
$line = StringTrimRight($line, 1)
EndIf
$line = StringStripWS($line, 3) ; 3 = strip leading & trailing while space
if $line = "" Then ContinueLoop
if $lineno > 0 Then $retstring = $retstring & @CRLF
$lineno = $lineno + 1
$retstring = $retstring & $line
Next
return $retstring
EndFunc
; ===========================================================================================
; Used by GUI to save cmdlines.txt in specified folder. The input data ($text) is the raw data as read from the GUI edit control. The header line ([Commands]) is not expected to
; be included in the input data.
Func SaveCmdLines($folder, $text)
; ===========================================================================================
$filename = $folder & "\cmdlines.txt"
if not IsFolder($folder) Then DirCReate($folder)
$file = FileOpen($filename, 2) ; 2 = create
$text = StringReplace($text, @LF, "")
$lineno = 0
$lines = StringSplit($text, @CR)
for $i = 1 to $lines[0]
$line = StringReplace($lines[$i], @LF, "")
$line = StringStripWS($line, 3) ; 3 = strip leading & trailing while space
if $line = "" Then ContinueLoop
if StringLeft($line, 1) = '"' And StringRight($line, 1) = '"' Then
$line = StringTrimLeft($line, 1)
$line = StringTrimRight($line, 1)
EndIf
$line = '"' & $line & '"'
if $lineno = 0 Then FileWriteLine($file, "[Commands]")
$lineno = $lineno + 1
FileWriteLine($file, $line)
Next
FileClose($file)
if $lineno = 0 Then FileDelete($filename)
EndFunc
; ===========================================================================================
; Used by GUI to save GuiRunOnce.ini in specified folder. The input data ($text) is the raw data as read from the GUI edit control. The header line ([GuiRunOnce]) is not expected to
; be included in the input data, nor are the "CommandN=" prefixes.
Func SaveRunOnce($folder, $text)
; ===========================================================================================
$filename = $folder & "\GuiRunOnce.ini"
if not IsFolder($folder) Then DirCReate($folder)
$file = FileOpen($filename, 2) ; 2 = create
$text = StringReplace($text, @LF, "")
$lineno = 0
$lines = StringSplit($text, @CR)
for $i = 1 to $lines[0]
$line = StringReplace($lines[$i], @LF, "")
$line = StringStripWS($line, 3) ; 3 = strip leading & trailing while space
if $line = "" Then ContinueLoop
if StringLeft($line, 1) = '"' And StringRight($line, 1) = '"' Then
$line = StringTrimLeft($line, 1)
$line = StringTrimRight($line, 1)
EndIf
$line = 'Command' & $lineno & '="' & $line & '"'
if $lineno = 0 Then FileWriteLine($file, "[GuiRunOnce]")
$lineno = $lineno + 1
FileWriteLine($file, $line)
Next
FileClose($file)
if $lineno = 0 Then FileDelete($filename)
EndFunc
; ===========================================================================================
; Return true if $s is a folder
Func IsFolder($s)
; ===========================================================================================
If Not FileExists($s) Or Not StringInStr(FileGetAttrib($s), "D") Then Return False
Return True
EndFunc
; ===========================================================================================
; Return true uf running under WinPE
Func IsWinPE()
; ===========================================================================================
If EnvGet("SystemDrive") = "X:" Then Return True
Return False
EndFunc
; ===========================================================================================
Func ErrorExit($msg, $exitcode)
; ===========================================================================================
MsgBox(0x40010, "CopyDrivers", $msg, 10) ; 10 is timeout, i.e. the msgbox closes after 10 seconds
Exit $exitcode
EndFunc

Binary file not shown.

Binary file not shown.

Binary file not shown.

File diff suppressed because it is too large Load Diff

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

View File

@@ -0,0 +1,385 @@
#Region ;**** Directives created by AutoIt3Wrapper_GUI ****
#AutoIt3Wrapper_Res_Comment=This program injects a mass storage driver previously captured by CaptureMsd
#AutoIt3Wrapper_Res_Description=InjectMsd
#AutoIt3Wrapper_Res_Fileversion=1.1
#AutoIt3Wrapper_Res_LegalCopyright=Copyright LANDesk Software
#EndRegion ;**** Directives created by AutoIt3Wrapper_GUI ****
#cs ----------------------------------------------------------------------------
InjectMsd Version 1.0.1 08 Dec 2008
AutoIt Version: 3.2.12.1
Author: Jan Buelens, Landesk Software
Script Function:
Inject a mass storage driver into a freshly restored image. Context: we are still running under WinPE. The target machine has just been restored
from an image. We are about to reboot the target into mini-setup. But before the target reboots, we need to inject the correct mass storage sriver into
it.
This script expects a path as a command line parameter. Within that path, there should be following:
-1- A .inf and a .sys file, to be copied to c:\Windows\inf and c:\Windows\System32\drivers respectively
-2- A subfolder called "windows", to be copied recursively to c:\windows. This subfolder contains any additional files to be injected, e.g. DLLs.
There is a redundancy here (the .sys and .inf could just as well be in this subfolder), but item -1- above is still believed to be convenient.
-3- One or more .reg files. These were probably exported from a working machine using the same mass storage driver. Typically, two .reg files
will be needed. One to describe the "service" under HKLM\CurrentControlSet\Services. A second one to describe the driver's subkey under
HKLM\CurrentControlSet\Control\CriticalDeviceDatabase.
The script imports these .reg files into the target system's registry.
The path passed as a command line parameter must have write access because -1- the program will make a temp copy of the .reg files it finds, -2- the
program will create a log file called injectmsd.log.
If something goes wrong, the script returns a non-zero exit code. There will also be a message box that goes away after 10 seconds.
Change history:
V1.0.1 (08 Dec 08). In addition to HKLM\Software and HKLM\System, a .reg file can now also write to the target's HKEY_USERS\.Default.
v1.1 (07 July 09). The msd folder is no longer required as a command line parameter if a copydrivers.ini file (with a DriversTarget parameter in it)
is present in the folder from which this program is running. If copydrivers.ini has the "typical" DriversTarget path of c:\drivers, InjectMsd will
default to c:\drivers\msd. Non-existence of this folder will not be considered an error (exit code 0). If an msdfolder is specified on the command
line, however, it is required to exist.
The log file is in a different place than before (c:\drivers if that's what's in copydrivers.ini/DriversTarget).
#ce ----------------------------------------------------------------------------
#Include <File.au3>
$progname = "InjectMsd V1.1"
Dim $logfilename = "" ; log file (from /log command line parameter)
Dim $log = -1
Dim $MsdFolder = ""
; ===========================================================================================
; Validate command line parameters. There should be one command line parameter = base folder
; ===========================================================================================
For $n = 1 to $CmdLine[0]
$s = ""
$c = StringLeft($CmdLine[$n],1)
if $n = 1 And $c <> "/" And $c <> "-" Then
$MsdFolder = $CmdLine[1]
ElseIf ValParam($CmdLine[$n], "log", $s) Then
$logfilename = $s
Else
Usage()
EndIf
Next
LogOpen($logfilename)
if $MsdFolder = "" Then
; If no folder was specified on the command line, see if there is a copydrivers.ini with a DriversTarget parameter and default to msd subfolder off it.
; Example: if DriversTarget has its typical value of c:\drivers, default to c:\drivers\msd. If that folder does not exist, don't complain - this may be
; a normal case of a machine type that does not require an msd folder
$iniFilename = PathConcat(@ScriptDir, "copydrivers.ini") ; @ScriptDir is folder in which this script (or compiled program) resides
LogIniSection($iniFilename, "Config")
if FileExists($iniFilename) Then
$DriverPath = IniRead($iniFilename, "Config", "DriversTarget", "") ; normally c:\drivers
if $DriverPath <> "" Then
$MsdFolder = PathConcat($DriverPath, "msd")
if not IsFolder($MsdFolder) Then
LogMessage("Default msd folder (" & $MsdFolder & ") does not exist. No work to do - exiting")
Exit 0
EndIf
EndIf
EndIf
EndIf
if $MsdFolder = "" Then
; No msd folder was specified on the command line and we couldn't take a default from copydrivers.ini. Complain.
Usage()
EndIf
; If we defaulted the msdfolder based on DriversTarget in copydrivers.ini, we have already exited with a zero return code if the folder doesn't exist.
; But if an msdfolder was specified on the command line and it doesn't exist, we still complain.
if not IsFolder($MsdFolder) Then ErrorExit("Folder " & $MsdFolder & " does not exist.", 2)
; ===========================================================================================
; If there is a subfolder called windows, copy it to c:\Windows
; ===========================================================================================
CopyWindows() ; Copy Windows subfolder if any to C:\Windows
; ===========================================================================================
; Find .inf and .sys files and copy to C:\Windows\Inf and c:\windows\system32\drivers respectively. This
; is strictly speaking redundant since same can be achieved using CopyWindows. But is probably convenient.
; ===========================================================================================
$search = FileFindFirstFile(PathConcat($MsdFolder, "*.inf"))
While 1
$file = FileFindNextFile($search)
If @error Then ExitLoop
LogMessage("Copying " & $file & " to c:\windows\inf\")
FileCopy(PathConcat($MsdFolder, $file), "c:\windows\inf\", 1) ; 1 = overwrite
If @error Then LogMessage("Copy of " & $file & " failed")
WEnd
FileClose($search) ; Close the search handle
$search = FileFindFirstFile(PathConcat($MsdFolder, "*.sys"))
While 1
$file = FileFindNextFile($search)
If @error Then ExitLoop
LogMessage("Copying " & $file & " to c:\windows\system32\drivers\")
FileCopy(PathConcat($MsdFolder, $file), "c:\windows\system32\drivers\", 1) ; 1 = overwrite
If @error Then LogMessage("Copy of " & $file & " failed")
WEnd
FileClose($search) ; Close the search handle
; ===========================================================================================
; Find .reg files. For each .reg file, call ProcessReg.
; ===========================================================================================
$search = FileFindFirstFile(PathConcat($MsdFolder, "*.reg"))
While 1
$file = FileFindNextFile($search)
If @error Then ExitLoop
LogMessage("Processing " & $file)
ProcessReg(PathConcat($MsdFolder, $file))
WEnd
FileClose($search) ; Close the search handle
; ===========================================================================================
; Done
; ===========================================================================================
; ===========================================================================================
; If the folder that we got as a command line parameter has a subfolder called "windows", then xcopy it to C:\Windows
Func CopyWindows()
; ===========================================================================================
Local $SourceFolder = PathConcat($MsdFolder, "Windows")
Local $TargetFolder = "C:\Windows"
if Not IsFolder($SourceFolder) Then Return False
LogMessage("Copying " & $MsdFolder & "\Windows to c:\windows")
DirCreate($TargetFolder)
If Not IsFolder($TargetFolder) Then ErrorExit("Unable to create target folder: " & $TargetFolder, 6)
If Not DirCopy($SourceFolder, $TargetFolder, 1) Then ErrorExit("Unable to copy folder: " & $TargetFolder, 7) ; 1 means overwrite existing files
Return True
EndFunc
; ===========================================================================================
; Import a .reg file into the target's registry. Make a temp copy of the .reg file (called .reg1), with modified registry key names. We need to modify
; the registry key names because e.g. HKLM\System refers to the WinPE registry. We change HKLM\System to HKLM\System1 and HKLM\Software to HKLM\Software1.
; We also need to change CurrentControlSet to ControlSet001 because CurrentControlSet is an alias that only exists in the running system, not in the target's
; System hive on disk.
; We then use the REG LOAD command to mount the target system's HKLM\System registry hive as HKLM\System1 and HKLM\Software as HKLM\Software1. After that,
; we can use the REG IMPORT command to import the modified .reg file into the target's registry.
Func ProcessReg($file)
; ===========================================================================================
$tempfile = $file & "1"
LogMessage("Making temp copy of " & $file & ", the copy is called " & $tempfile)
FileCopy($file, $tempfile, 1) ; 1 = overwrite
if @error then ErrorExit("Unable to create " & $tempfile, 8)
if not FileExists($tempfile) then ErrorExit("Unable to create " & $tempfile, 9)
LogMessage("Editing " & $tempfile & ", replacing registry root key names")
$count1 = _ReplaceStringInFile($tempfile, "HKEY_LOCAL_MACHINE\System", "HKEY_LOCAL_MACHINE\System1")
$count2 = _ReplaceStringInFile($tempfile, "System1\CurrentControlSet", "System1\ControlSet001")
$count3 = _ReplaceStringInFile($tempfile, "HKEY_LOCAL_MACHINE\Software", "HKEY_LOCAL_MACHINE\Software1")
$count4 = _ReplaceStringInFile($tempfile, "HKEY_USERS\.DEFAULT", "HKEY_LOCAL_MACHINE\Default1")
if $count1 > 0 Then
if not FileExists("c:\windows\system32\config\system") Then ErrorExit("File not found: c:\windows\system32\config\system", 10)
RunCommand("reg load HKLM\System1 c:\windows\system32\config\system")
if not HasSubKey("HKLM\System1") Then ErrorExit("Something went wrong loading target's HKLM\System", 11)
EndIf
if $count3 > 0 Then
if not FileExists("c:\windows\system32\config\software") Then ErrorExit("File not found: c:\windows\system32\config\software", 12)
RunCommand("reg load HKLM\Software1 c:\windows\system32\config\software")
if not HasSubKey("HKLM\Software1") Then ErrorExit("Something went wrong loading target's HKLM\Software", 13)
EndIf
if $count4 > 0 Then
if not FileExists("c:\windows\system32\config\default") Then ErrorExit("File not found: c:\windows\system32\config\default", 12)
RunCommand("reg load HKLM\Default1 c:\windows\system32\config\default")
if not HasSubKey("HKLM\Default1") Then ErrorExit("Something went wrong loading target's HKEY_USERS\.DEFAULT", 13)
EndIf
RunCommand("reg import " & $tempfile)
if $count1 > 0 Then RunCommand("reg unload HKLM\System1")
if $count3 > 0 Then RunCommand("reg unload HKLM\Software1")
if $count4 > 0 Then RunCommand("reg unload HKLM\Default1")
EndFunc
; ===========================================================================================
; Return true if $s has a registry subkey
Func HasSubKey($s)
; ===========================================================================================
SetError(0)
Dim $subkey = ""
$subkey = RegEnumKey($s, 1)
if @error Then Return False
If $subkey = "" Then Return False
Return True
EndFunc
; ===========================================================================================
; Run specified command and include stdout and stderr output in our log file
Func RunCommand($cmd)
; ===========================================================================================
LogMessage("Running this command line: " & $cmd)
FileClose($log)
$command = "cmd /c " & $cmd & " >>" & $logfilename & " 2>&1"
RunWait($command)
$log = FileOpen($logfilename, 1) ; 1 = write, append mode
EndFunc
; ===========================================================================================
Func Usage()
; ===========================================================================================
Msgbox ("0", $progname, _
"This program injects a Mass Storage Driver previously captured with the" _
& @CRLF & "CaptureMsd program." & @CRLF _
& @CRLF & "Usage: InjectMsd [msdfolder] [parameters]" & @CRLF _
& @CRLF & "Msdfolder is the path where the driver files captured by CaptureMsd" _
& @CRLF & "are stored (typically a .sys, .inf and .reg). The msdfolder parameter" _
& @CRLF & "is optional if a copydrivers.ini file with appropriate parameters is" _
& @CRLF & "present in the folder from which InjectMsd is running." & @CRLF _
& @CRLF & "Parameters:" _
& @CRLF & "/log=<logfile> : log file" _
)
Exit 1
EndFunc
; ===========================================================================================
; Concatenate a filename ($s) with a base path
Func PathConcat($base, $s)
; ===========================================================================================
$base = StringStripWS($base,3)
$s = StringStripWS($s,3)
if StringRight($base,1) <> "\" Then $base &= "\"
if StringLeft($s,1) = "\" Then $s = StringTrimLeft($s,1)
Return $base & $s
EndFunc
; ===========================================================================================
; Return true if $s is a folder
Func IsFolder($s)
; ===========================================================================================
If Not FileExists($s) Or Not StringInStr(FileGetAttrib($s), "D") Then Return False
Return True
EndFunc
; ===========================================================================================
; Return true if $s is a network path. Must be full path.
Func IsRemote($s)
; ===========================================================================================
If StringLeft($s, 2) = "\\" Then Return True
Local $drive = StringLeft($s, 3)
if DriveGetType($drive) = "Network" Then Return True
Return False
EndFunc
; ===========================================================================================
Func LogCmdLine()
; ===========================================================================================
Local $n
LogMessage($progname & ", command line parameter(s): " & $CmdLine[0])
For $n = 1 to $CmdLine[0]
LogMessage(" " & $CmdLine[$n])
Next
EndFunc
; ===========================================================================================
Func LogMessage($msg)
; ===========================================================================================
FileWriteLine($log, $msg)
EndFunc
; ===========================================================================================
Func LogIniSection($inifilename, $inisection, $msg = Default)
; ===========================================================================================
Local $i
if $msg = Default Then
LogMessage($inifilename & ",section [" & $inisection & "]:")
Else
LogMessage($msg)
EndIf
Local $section = IniReadSection($inifilename, $inisection)
if @error Then
if not FileExists($inifilename) Then
LogMessage(" File does not exist: " & $inifilename)
Return
EndIf
LogMessage(" " & $inifilename & " includes no [" & $inisection & "] section")
Return
EndIf
For $i = 1 to $section[0][0]
LogMessage(" " & $section[$i][0] & " = " & $section[$i][1])
Next
EndFunc
; ===========================================================================================
Func LogOpen(ByRef $logfilename)
; ===========================================================================================
Local $scriptName = StringTrimRight(@ScriptName, 4)
While 1
If $logfilename <> "" Then
; log filename specified on command line
$log = FileOpen($logfilename, 10) ; 10 = 2 (write, create) + 8 (create path)
ExitLoop
EndIf
; No /log command line parameter. If there is a copydrivers.ini file with a DriversTarget parameter (typically c:\drivers), create the log in there
Local $iniFilename = PathConcat(@ScriptDir, "copydrivers.ini")
Local $DriverPath = IniRead($iniFilename, "Config", "DriversTarget", "")
if $DriverPath <> "" Then
$DriverPath = StringStripWS($DriverPath, 3)
if StringRight($DriverPath, 1) <> "\" Then $DriverPath &= "\"
$logfilename = $DriverPath & $scriptName & ".log"
$log = FileOpen($logfilename, 10) ; 10 = 2 (write, create) + 8 (create path)
if $log <> -1 Then ExitLoop
EndIf
; No /log command parameter and no copydrivers.ini. If running from a local path, create log in folder of running program
If Not IsRemote(@ScriptFullPath) Then
$logfilename = StringTrimRight(@ScriptFullPath, 3) & "log"
$log = FileOpen($logfilename, 2)
if $log <> -1 Then ExitLoop
EndIf
; failed to create log
$log = -1
$logfilename = ""
return
Wend
LogCmdLine()
EndFunc
; ===========================================================================================
Func ErrorExit($msg, $exitcode)
; ===========================================================================================
LogMessage($msg)
FileClose($log)
MsgBox(0x40010, $progname, $msg, 10) ; 10 is timeout, i.e. the msgbox closes after 10 seconds
Exit $exitcode
EndFunc
; ===========================================================================================
; parse command line parameter such as /keyw=something. Examples:
; ValParam("/path=c:\temp", "path", $value) sets $value to "c:\temp" and returns True
; ValParam("-path=c:\temp", "path", $value) sets $value to "c:\temp" and returns True
; ValParam("/path=c:\temp", "dir", $value) sets $value to "" and returns False
Func ValParam($param, $keyword, ByRef $value)
; ===========================================================================================
$value = ""
Local $p1 = "/" & $keyword & "="
Local $p2 = "-" & $keyword & "="
Local $len = StringLen($p1)
if StringLen($param) < ($len + 1) Then Return False
Local $t = StringLeft($param, $len)
if ($t <> $p1) And ($t <> $p2) Then Return False
$value = StringMid($param, $len + 1) ; 1 based
Return True
EndFunc

Binary file not shown.

View File

@@ -0,0 +1,3 @@
X:\ldclient\sdclient.exe /f /o /p=http://%coreIP%/landesk/files/prefmap.exe /dest=x:\ldclient\prefmap.exe /attemptpref
X:\ldclient\prefmap.exe /drv=I: /shr=%share% /usr=%usr% /pwd=%pwd%

View File

@@ -0,0 +1,88 @@
#cs ----------------------------------------------------------------------------
AutoIt Version: 3.2.10.0
Author: Jan Buelens, LANDesk Software
Script Function:
This script may help in an OSD or Provisioning context to make environment variables useful. The author knows of no other way
whereby one provisioning action can use an environment variable set by another provisioning action. Even using setx to set a system
environment variable doesn't do the trick.
This script gets around the issue by reading the system environment variables from the registry before launching the specified
command line. The child process will see all the system environment variables.
#ce ----------------------------------------------------------------------------
$progname = "RunEnv V1.0"
If $CmdLine[0] = 0 Then Usage()
If $CmdLine[0] > 0 And ($CmdLine[1] = "/?" Or $CmdLine[1] = "-?" Or $CmdLine[1] = "help") Then
Usage()
EndIf
$CommandLine = ""
For $n = 1 to $CmdLine[0]
$str = $CmdLine[$n]
; $str = StringReplace($str, '"', '""')
if StringInStr($str, " ") > 0 And StringLeft($str,1) <> '"' Then
$str = '"' & $str & '"'
EndIf
if $CommandLine <> "" Then
$CommandLine = $CommandLine & " "
EndIf
$CommandLine = $CommandLine & $str
Next
$base = "HKLM\System\CurrentControlSet\Control\Session Manager\Environment"
for $n = 1 to 9999
$valname = RegEnumVal($base, $n)
if @error Then ExitLoop
$val = RegRead($base, $valname)
$env = EnvGet($valname)
if $env = "" Then
; This environment variable doesn't exist - set it. We only set variables that do not exist in the currrent environment. We don't override
; variables that exist. This would violate the rule whereby user environmrent variables take priority over system environment variables.
EnvSet($valname, $val)
EndIf
Next
; Msgbox ("0", "RunEnv V1.0", "Command Line: ==" & $CommandLine & "==")
AutoItSetOption ( "ExpandEnvStrings", 1) ; This tells AutoIt to expand Env Vars
$ExitCode = RunWait($CommandLine)
if @error Then ErrorExit("Failed to run command: " & $CommandLine, 2)
; ErrorExit("Exit Code: " & $ExitCode, $ExitCode)
Exit $ExitCode
; ===========================================================================================
Func Usage()
; ===========================================================================================
Msgbox ("0", $progname, _
"This program runs the specified command line, after refreshing the system" _
& @CRLF & "environment variables." & @CRLF _
& @CRLF & "In a normal windows environment, when a new system environment variable is" _
& @CRLF & "created (e.g. with setx), running processes will not see the new environment" _
& @CRLF & "variable, but future processes launched by the windows shell will." & @CRLF _
& @CRLF & "Under WinPE, the new environment variable seems to remain invisible even to" _
& @CRLF & "future processes. If this is a problem, use RunEnv. A process launched by" _
& @CRLF & "RunEnv will see all environment variables. To use RunEnv, just prefix the" _
& @CRLF & "normal command line with RunEnv." _
)
Exit 1
EndFunc
; ===========================================================================================
Func ErrorExit($msg, $exitcode)
; ===========================================================================================
MsgBox(0x40010, $progname, $msg, 10) ; 10 is timeout, i.e. the msgbox closes after 10 seconds
Exit $exitcode
EndFunc

Binary file not shown.

View File

@@ -0,0 +1,298 @@
#Region ;**** Directives created by AutoIt3Wrapper_GUI ****
#AutoIt3Wrapper_Res_Comment=This program connects a drive letter to the preferred server for Windows or WinPE.
#AutoIt3Wrapper_Res_Fileversion=3.0.0.1
#AutoIt3Wrapper_Res_LegalCopyright=LANdesk Software
#EndRegion ;**** Directives created by AutoIt3Wrapper_GUI ****
#cs ----------------------------------------------------------------------------
AutoIt Version: 3.3.0.0
Author: Jan Buelens, LANDesk Software
Script Function:
Map a drive to the preferred server.
Change History:
V1.0 01 July 2009. Original version. Based on earlier C++ program.
V2.0 020 Jan 2010. Chnaged for LDMS 9.0. PreferredServer.dat file lives in different place and has different format.
V3.0 06 June 2011. Made work in Windows XP (32-bit) and Windows 7 (32 and 64-bit).
#ce ----------------------------------------------------------------------------
; Script Start - Add your code below here
Const $progname = "prefmap V3.0"
Dim $share = ""
Dim $drvletter = ""
Dim $user = ""
Dim $pwd = ""
Dim $varname = ""
Dim $bVerbose = False
Dim $bSilent = False
$logfilename = "" ; log file (from /log command line parameter)
$log = -1
Dim $PrefServerFile8 = ""
Dim $PrefServerFile9 = ""
Dim $CoreServer = ""
Dim $LDMSPath = ""
If IsWinPE() Then
$PrefServerFile8 = "x:\LANDesk\ManagementSuite\sdmcache\preferredserver.dat" ; LDMS WinPE 8.x
$PrefServerFile9 = "x:\ldclient\preferredservers.dat" ; LDMS WinPE 9.0
$CoreServer = RegRead("HKEY_LOCAL_MACHINE\SOFTWARE\Intel\LANDesk\EventLog", "CoreServer")
Else
If StringInStr(@OSArch, "86") Then
$CoreServer = RegRead("HKEY_LOCAL_MACHINE\Software\Intel\LANDesk\EventLog", "CoreServer")
$PrefServerFile9 = "c:\program files\landesk\ldclient\sdmcache\preferredservers." & $CoreServer & ".dat"
$LDMSPath = "c:\program files\landesk\ldclient\"
ElseIf StringInStr(@OSArch, "64") Then
$CoreServer = RegRead("HKEY_LOCAL_MACHINE\Software\Wow6432Node\Intel\LANDesk\EventLog", "CoreServer")
$PrefServerFile9 = "c:\program files (x86)\landesk\ldclient\sdmcache\preferredservers." & $CoreServer & ".dat"
$LDMSPath = "c:\program files (x86)\landesk\ldclient\"
EndIf
EndIf
Dim $PrefServerFile = ""
; ===========================================================================================
; Validate command line parameters
; ===========================================================================================
For $n = 1 to $CmdLine[0]
$s = ""
If ValParam($CmdLine[$n], "shr", $s) Then
$share = $s
ElseIf ValParam($CmdLine[$n], "drv", $s) Then
$drvletter = $s
ElseIf ValParam($CmdLine[$n], "usr", $s) Then
$user = $s
ElseIf ValParam($CmdLine[$n], "pwd", $s) Then
$pwd = $s
ElseIf ValParam($CmdLine[$n], "var", $s) Then
$varname = $s
ElseIf ValParam($CmdLine[$n], "log", $s) Then
$logfilename = $s
ElseIf $CmdLine[$n] = "/v" Or $CmdLine[$n] = "-v" Then
$bVerbose = True;
Else
Usage()
EndIf
Next
if $logfilename = "" Then $logfilename = StringTrimRight(@ScriptFullPath, 3) & "log"
$log = FileOpen($logfilename, 2)
if $varname = "" Then
; No variable name (/var) is specified. The other 3 parameters (/drv, /shr, /usr) must be present
if $share = "" then Usage()
if $user = "" then Usage()
if $drvletter = "" then Usage()
EndIf
If $share <> "" Or $user <> "" Or $drvletter <> "" Then
; if one of (/drv, /shr, /usr) is present, all 3 must be present
if $share = "" then Usage()
if $user = "" then Usage()
if $drvletter = "" then Usage()
; validate format of /drv
if StringLen($drvletter) > 2 Then Usage()
if StringLen($drvletter) = 1 Then $drvletter &= ":"
if StringRight($drvletter, 1) <> ":" Then Usage()
$drvletter = StringUpper($drvletter)
if $drvletter < "A:" Or $drvletter > "Z:" Then Usage()
EndIf
;If Not IsWinPE() Then ErrorExit("This program must be run under WinPE", 2)
If not GetPrefServerFile() Then
; ===================================================================================
; Use sdclient to download a small dummy file from the core server. As a side effect,
; a preferredserver.dat file is left in x:\LANDesk\ManagementSuite\sdmcache.
; Whether the download is successful does not matter
; ===================================================================================
;$CoreServer = RegRead("HKEY_LOCAL_MACHINE\SOFTWARE\Intel\LANDesk\LDWM", "CoreServer")
if $bVerbose Then MsgBox(0, $progname, "core server: " & $CoreServer, 5)
If IsWinPE() Then
$SdclientCommandLine = "X:\ldclient\sdclient.exe /f /o /dest=x:\ldclient\win_prov_files.xml /p=http://" & $CoreServer & "/ldlogon/provisioning/win_prov_files.xml"
if $bVerbose Then MsgBox(0, $progname, "command line: " & $SdclientCommandLine, 10)
LogMessage("Dummy download from core server so sdclient/lddwnld.dll gets hold of preferredserver(s).dat")
LogMessage("command line: " & $SdclientCommandLine)
RunWait($SdclientCommandLine, "x:\ldclient")
Else
$SdclientCommandLine = $LDMSPath & "sdclient.exe /f /o /p=http://" & $CoreServer & "/ldlogon/provisioning/win_prov_files.xml /requirepref"
if $bVerbose Then MsgBox(0, $progname, "command line: " & $SdclientCommandLine, 10)
LogMessage("Dummy download from core server so sdclient/lddwnld.dll gets hold of preferredserver(s).dat")
LogMessage("command line: " & $SdclientCommandLine)
RunWait($SdclientCommandLine, $LDMSPath)
EndIf
EndIf
If not GetPrefServerFile() Then ErrorExit("preferredserver(s).dat not found", 3)
LogMessage("preferredserver.dat found at " & $PrefServerFile)
$line = FileReadLine($PrefServerFile)
if $line = "" Then ErrorExit("PreferredServer(s).dat file is empty", 4)
LogMessage("preferredserver(s).dat file contents: " & $line)
; ===================================================================================
; Found preferredserver.dat. It is a text file with no CR-LF. If there are multiple preferred servers,
; they are separated by a semicolon. The preferred server list may or may not be prefixed with a time stamp
; and a question mark.
; Expected formats for LDMS 8.8:
; SERVER1
; SERVER1;SERVER2
; Expected formats for LDMS 8.8:
; 12349439485?SERVER1
; 12349439485?SERVER1;SERVER2
; ===================================================================================
$serverlist = ""
$array = StringSplit($line,"?")
If $array[0] = 1 Then
; there was no question mark
$serverlist = $line
ElseIf $array[0] = 2 Then
; there was 1 question mark - take the substring after the question mark
$serverlist = $array[2]
Else
ErrorExit("preferredserver.dat, invalid format", 41)
EndIf
$array = StringSplit($serverlist,";")
$servername = $array[1]
; ===================================================================================
; When using local user names, we may need something like <machinename>\<username>.
; If the username we got from the command line includes a substring "$server$", replace
; with server name from preferredserver.dat
; ===================================================================================
$user = StringReplace($user, "$server$", $servername)
if $bVerbose Then MsgBox(0, $progname, "preferred server: " & $servername, 5)
LogMessage("preferred server: " & $servername)
if $share <> "" Then
$unc = "\\" & $servername & "\" & $share
if $bVerbose Then MsgBox(0, $progname, "connecting " & $drvletter & " to " & $unc & " as " & $user, 5)
LogMessage("connecting " & $drvletter & " to " & $unc & " as " & $user)
$ret = DriveMapAdd($drvletter, $unc, 0, $user, $pwd)
if $ret = 0 Then
$errmsg = "DriveMapAdd(" & $drvletter & ", " & $unc & ", " & $user & ", <pwd>) failed. "
if @error = 1 Then $errmsg &= "Win32 error code " & @extended
if @error = 2 Then $errmsg &= "Access Denied"
if @error = 3 Then $errmsg &= "Drive letter already assigned"
if @error = 4 Then $errmsg &= "Invalid drive letter"
if @error = 5 Then $errmsg &= "UNC path not found"
if @error = 6 Then $errmsg &= "Invalid password"
ErrorExit($errmsg, 5)
EndIf
if $bVerbose Then MsgBox(0, $progname, "connection successful", 5)
LogMessage("connection successful")
EndIf
if $varname <> "" Then
$base = "HKLM\System\CurrentControlSet\Control\Session Manager\Environment"
RegWrite($base, $varname, "REG_SZ", $servername)
if @error Then ErrorExit("RegWrite, error " & @error, 6)
LogMessage("Environment variable set")
EndIf
FileClose($log)
; ===========================================================================================
; The location of the preferredserver.dat file is different between LDMS 8.8 and 9.0. This function looks in the
; two possible places and sets a global variable ($PrefServerFile) to the correct path. If the file is found in
; neither place, the return value is false.
Func GetPrefServerFile()
; ===========================================================================================
$PrefServerFile = ""
If FileExists($PrefServerFile8) Then
$PrefServerFile = $PrefServerFile8
Return True
EndIf
If FileExists($PrefServerFile9) Then
$PrefServerFile = $PrefServerFile9
Return True
EndIf
Return False
EndFunc
; ===========================================================================================
; Return true if running under WinPE
Func IsWinPE()
; ===========================================================================================
If EnvGet("SystemDrive") = "X:" Then Return True
Return False
EndFunc
; ===========================================================================================
Func ErrorExit($msg, $exitcode)
; ===========================================================================================
LogMessage($msg)
FileClose($log)
if not $bSilent Then MsgBox(0x40010, $progname, $msg, 10) ; 10 is timeout, i.e. the msgbox closes after 10 seconds
Exit $exitcode
EndFunc
; ===========================================================================================
; parse command line parameter such as /keyw=something. Examples:
; ValParam("/path=c:\temp", "path", $value) sets $value to "c:\temp" and returns True
; ValParam("-path=c:\temp", "path", $value) sets $value to "c:\temp" and returns True
; ValParam("/path=c:\temp", "dir", $value) sets $value to "" and returns False
Func ValParam($param, $keyword, ByRef $value)
; ===========================================================================================
$value = ""
Local $p1 = "/" & $keyword & "="
Local $p2 = "-" & $keyword & "="
Local $len = StringLen($p1)
if StringLen($param) < ($len + 1) Then Return False
Local $t = StringLeft($param, $len)
if ($t <> $p1) And ($t <> $p2) Then Return False
$value = StringMid($param, $len + 1) ; 1 based
Return True
EndFunc
; ===========================================================================================
Func LogMessage($msg)
; ===========================================================================================
FileWriteLine($log, $msg)
EndFunc
; ===========================================================================================
Func Usage()
; ===========================================================================================
Msgbox (0, $progname & " by Jan Buelens", _
"This program maps a drive to the preferred server." & @CRLF _
& @CRLF & "Usage:" _
& @CRLF & " /shr= share" _
& @CRLF & " /drv= drive letter" _
& @CRLF & " /usr= user name" _
& @CRLF & " /pwd= password" _
& @CRLF & " /var= environment variable" _
& @CRLF & " /v verbose" & @CRLF _
& @CRLF & "Use this program only under WinPE." _
& @CRLF & "If there are multiple preferred servers, the first one will be used." _
& @CRLF & "If you are using a local machine account to connect, you may want to" _
& @CRLF & "include a $server$ substring in the user name. The program will replace" _
& @CRLF & "it with the preferred server name." _
& @CRLF & "" _
& @CRLF & "If a /var parameter is specified, a system environment variable will" _
& @CRLF & "set to the preferred server name. You probably need the RunEnv tool to" _
& @CRLF & "use the environment variable. If you only want prefmap to set an" _
& @CRLF & "environment variable, without mapping a drive, use the /var parameter" _
& @CRLF & "only." _
& @CRLF & "" _
)
Exit 1
EndFunc

Binary file not shown.