I recently stumbled onto a somewhat major issue during OSD that is the result of a fundamental (bad) assumption made by many including Windows itself and Internet Explorer. That assumption is that at some point during the deployment of Windows (Windows 7 in this case), an Administrator will log on to the system. This may be during the actual deployment process or maybe right after it is done. Why is this assumption important? Because both Windows setup and Internet Explorer put items in the Windows RunOnce key (HKLM\Software\Microsoft\Windows\CurrentVersion\RunOnce) to be run the first time a user logs on. The things that Windows and IE setup put there require elevated permissions however.

Why is this assumption bad? Because the whole point of OSD in ConfigMgr is to be completely hands-off and that the first (and maybe only) user to ever log onto a system has no elevated permissions. Thus, things in RunOnce never run because task sequences in ConfigMgr run in the local SYSTEM context and never actually log into the system via the GINA.

I don’t know all the ramifications of this but it recently manifested itself at a client where we were adding IE 9 to a Windows 7 SP1 deployment. We used the IEAK to create an MSI and tested it manually with the desired results. The problem came in when we tried to add that MSI to either a Build and Capture Task Sequence or a Deployment Task Sequence. The install finished fine, but neither the Start Menu nor Taskbar icon for IE existed anymore. We could manually browse to iexplore.exe and launch it that way proving that the install was fine and of course it was listed in the Updates list under Programs and Features.

After some investigation and a TechNet forum thread pointing the way, I realized what was going on. As Michael Niehaus accurately pointed out also, this isn’t really a new issue but I’ve never seen a negative impact like this one before either. Upon examining the RunOnce key, both before and after IE 9 installation but before a reboot, I discovered no less than six other items listed that were from the base Windows 7 image we had recaptured using a Build and Capture Task Sequence. So, the conclusion is that this is not just an IE problem and it’s not just a Build and Capture issue. So even if you aren’t adding IE and even if you are using LiteTouch to create your image, it’s still possible for things to end up in the RunOnce key that never get executed.

So what’s the solution? In limited testing, the following VBScript seems to do the trick:

Const HKLM = &H80000002

Const REG_SZ = 1
Const REG_EXPAND_SZ = 2
Const REG_BINARY = 3
Const REG_DWORD = 4
Const REG_MULTI_SZ = 7
 
computer = "."

Set shell = CreateObject("WScript.Shell")
 
Set registry = GetObject("winmgmts:\\" & computer & "\root\default:StdRegProv")
 
keyPath = "SOFTWARE\Microsoft\Windows\CurrentVersion\RunOnce"
registry.EnumValues HKLM, keyPath, valueNames, valueTypes

If Not IsNull(valueNames) Then

    For i = 0 To UBound(valueNames)
        text = valueNames(i)  
        valueName = valueNames(i)
   
        Select Case valueTypes(i)
       
            Case REG_SZ
                registry.GetStringValue HKLM, keyPath, valueName, value
                WScript.Echo text & ": "  & value
               
                returnCode = shell.Run(value, 1, True)
               
                If returnCode = 0 Then
                    registry.DeleteValue HKLM, keyPath, valueName
                End If
               
            End Select
   
    Next
End If

What does it do? It simply enumerates each value under the RunOnce key, executes the command-line, and if a success code of 0 is returned from executing the command-line it deletes the value from RunOnce.

Based upon my findings, you should run this in all ConfigMgr OSD task sequences somewhere after the Setup Windows and ConfigMgr task preferably also after any included application installs and after a reboot. If there’s nothing in RunOnce, it’s a no-op.