Excellent script, works every time.
-------------------
' Script to enumerate last applied hotfixes, and rollback
on error resume next
const forappending = 8
const forwriting=2
const forreading=1
Const dictKey = 1
Const dictItem = 2
' **********set to 0 to get out of testmode**********
testmode=0
' ***************************************************
Logpath="C:\hotfixundo.log"
Set fso = createObject("Scripting.FileSystemObject")
set windir=fso.GetSpecialFolder(0)
call stamplog("*************************************************************")
call stamplog("Starting process, windows directory is "&windir.path)
lastdate=""
' enumerate subfolders, check date.
For Each Subfolder in windir.SubFolders
if instr(lcase(subfolder.name),"$ntuninstall")<>0 then
if lastdate="" then
lastdate=subfolder.datecreated
end if
if datediff("d",lastdate,subfolder.datecreated)>1 then
lastdate=subfolder.datecreated
end if
end if
Next
call stamplog("Latest date found for uninstall folder is "&lastdate)
' loop again, creating a list of directories to be targeted.
set list = CreateObject("Scripting.Dictionary")
call stamplog ("Processing the following directories:")
For Each Subfolder in windir.SubFolders
if instr(lcase(subfolder.name),"$ntuninstall")<>0 then
if datediff("d",lastdate,subfolder.datecreated)<1 and datediff("d",lastdate,subfolder.datecreated)>=0 then
list.add subfolder.datecreated,subfolder.path
call stamplog2(subfolder.path)
end if
end if
Next
' sort dictionary
sortdictionary list,dictkey
' loop through list, shell out to run spuninst for each directory, last first
for each location in list
call stamplog("Launching "& list.item(location)&"\spuninst\spuninst.exe")
err.clear
if testmode=0 then
run list.item(location)&"\spuninst\spuninst.exe /quiet /passive /norestart"
else
call stamplog("***TESTMODE - Uninstall NOT run***")
end if
next
call stamplog("Finished at "&date&" "&time)
' Stamp line of text to specified logfile
sub stamplog(text)
Set objFSO = CreateObject("Scripting.FileSystemObject")
Set objTextFile = objFSO.OpenTextFile _
(logpath, Forappending, True)
objtextfile.writeline(text)
wscript.echo (text)
objTextFile.Close
end sub
sub stamplog2(text)
Set objFSO = CreateObject("Scripting.FileSystemObject")
Set objTextFile = objFSO.OpenTextFile _
(logpath, Forappending, True)
objtextfile.writeline(text)
'wscript.echo (text)
objTextFile.Close
end sub
' Run function
Function Run (ByVal cmd)
Dim sh: Set sh = CreateObject("WScript.Shell")
Dim wsx: Set wsx = Sh.Exec(cmd)
If wsx.ProcessID = 0 And wsx.Status = 1 Then
' (The Win98 version of VBScript does not detect WshShell.Exec errors)
Err.Raise vbObjectError,,"WshShell.Exec failed."
End If
Do
Dim Status: Status = wsx.Status
WScript.StdOut.Write wsx.StdOut.ReadAll()
WScript.StdErr.Write wsx.StdErr.ReadAll()
If Status <> 0 Then Exit Do
WScript.Sleep 10
Loop
Run = wsx.ExitCode
End Function
' Runs an internal command interpreter command.
Function RunCmd (ByVal cmd)
RunCmd = Run("%ComSpec% /c " & cmd)
End Function
' Sort function
Function SortDictionary(objDict,intSort)
' declare our variables
Dim strDict()
Dim objKey
Dim strKey,strItem
Dim X,Y,Z
' get the dictionary count
Z = objDict.Count
' we need more than one item to warrant sorting
If Z > 1 Then
' create an array to store dictionary information
ReDim strDict(Z,2)
X = 0
' populate the string array
For Each objKey In objDict
strDict(X,dictKey) = CStr(objKey)
strDict(X,dictItem) = CStr(objDict(objKey))
X = X + 1
Next
' perform a a shell sort of the string array
For X = 0 to (Z - 2)
For Y = X to (Z - 1)
If StrComp(strDict(X,intSort),strDict(Y,intSort),vbTextCompare) > 0 Then
strKey = strDict(X,dictKey)
strItem = strDict(X,dictItem)
strDict(X,dictKey) = strDict(Y,dictKey)
strDict(X,dictItem) = strDict(Y,dictItem)
strDict(Y,dictKey) = strKey
strDict(Y,dictItem) = strItem
End If
Next
Next
' erase the contents of the dictionary object
objDict.RemoveAll
' repopulate the dictionary with the sorted information
For x=(z-1) to 0 step -1
' For X = 0 to (Z - 1)
objDict.Add strDict(X,dictKey), strDict(X,dictItem)
Next
End If
End Function
-------------------
' Script to enumerate last applied hotfixes, and rollback
on error resume next
const forappending = 8
const forwriting=2
const forreading=1
Const dictKey = 1
Const dictItem = 2
' **********set to 0 to get out of testmode**********
testmode=0
' ***************************************************
Logpath="C:\hotfixundo.log"
Set fso = createObject("Scripting.FileSystemObject")
set windir=fso.GetSpecialFolder(0)
call stamplog("*************************************************************")
call stamplog("Starting process, windows directory is "&windir.path)
lastdate=""
' enumerate subfolders, check date.
For Each Subfolder in windir.SubFolders
if instr(lcase(subfolder.name),"$ntuninstall")<>0 then
if lastdate="" then
lastdate=subfolder.datecreated
end if
if datediff("d",lastdate,subfolder.datecreated)>1 then
lastdate=subfolder.datecreated
end if
end if
Next
call stamplog("Latest date found for uninstall folder is "&lastdate)
' loop again, creating a list of directories to be targeted.
set list = CreateObject("Scripting.Dictionary")
call stamplog ("Processing the following directories:")
For Each Subfolder in windir.SubFolders
if instr(lcase(subfolder.name),"$ntuninstall")<>0 then
if datediff("d",lastdate,subfolder.datecreated)<1 and datediff("d",lastdate,subfolder.datecreated)>=0 then
list.add subfolder.datecreated,subfolder.path
call stamplog2(subfolder.path)
end if
end if
Next
' sort dictionary
sortdictionary list,dictkey
' loop through list, shell out to run spuninst for each directory, last first
for each location in list
call stamplog("Launching "& list.item(location)&"\spuninst\spuninst.exe")
err.clear
if testmode=0 then
run list.item(location)&"\spuninst\spuninst.exe /quiet /passive /norestart"
else
call stamplog("***TESTMODE - Uninstall NOT run***")
end if
next
call stamplog("Finished at "&date&" "&time)
' Stamp line of text to specified logfile
sub stamplog(text)
Set objFSO = CreateObject("Scripting.FileSystemObject")
Set objTextFile = objFSO.OpenTextFile _
(logpath, Forappending, True)
objtextfile.writeline(text)
wscript.echo (text)
objTextFile.Close
end sub
sub stamplog2(text)
Set objFSO = CreateObject("Scripting.FileSystemObject")
Set objTextFile = objFSO.OpenTextFile _
(logpath, Forappending, True)
objtextfile.writeline(text)
'wscript.echo (text)
objTextFile.Close
end sub
' Run function
Function Run (ByVal cmd)
Dim sh: Set sh = CreateObject("WScript.Shell")
Dim wsx: Set wsx = Sh.Exec(cmd)
If wsx.ProcessID = 0 And wsx.Status = 1 Then
' (The Win98 version of VBScript does not detect WshShell.Exec errors)
Err.Raise vbObjectError,,"WshShell.Exec failed."
End If
Do
Dim Status: Status = wsx.Status
WScript.StdOut.Write wsx.StdOut.ReadAll()
WScript.StdErr.Write wsx.StdErr.ReadAll()
If Status <> 0 Then Exit Do
WScript.Sleep 10
Loop
Run = wsx.ExitCode
End Function
' Runs an internal command interpreter command.
Function RunCmd (ByVal cmd)
RunCmd = Run("%ComSpec% /c " & cmd)
End Function
' Sort function
Function SortDictionary(objDict,intSort)
' declare our variables
Dim strDict()
Dim objKey
Dim strKey,strItem
Dim X,Y,Z
' get the dictionary count
Z = objDict.Count
' we need more than one item to warrant sorting
If Z > 1 Then
' create an array to store dictionary information
ReDim strDict(Z,2)
X = 0
' populate the string array
For Each objKey In objDict
strDict(X,dictKey) = CStr(objKey)
strDict(X,dictItem) = CStr(objDict(objKey))
X = X + 1
Next
' perform a a shell sort of the string array
For X = 0 to (Z - 2)
For Y = X to (Z - 1)
If StrComp(strDict(X,intSort),strDict(Y,intSort),vbTextCompare) > 0 Then
strKey = strDict(X,dictKey)
strItem = strDict(X,dictItem)
strDict(X,dictKey) = strDict(Y,dictKey)
strDict(X,dictItem) = strDict(Y,dictItem)
strDict(Y,dictKey) = strKey
strDict(Y,dictItem) = strItem
End If
Next
Next
' erase the contents of the dictionary object
objDict.RemoveAll
' repopulate the dictionary with the sorted information
For x=(z-1) to 0 step -1
' For X = 0 to (Z - 1)
objDict.Add strDict(X,dictKey), strDict(X,dictItem)
Next
End If
End Function