Quantcast
Channel: packageology
Viewing all 67 articles
Browse latest View live

Fix for MSI packages created with App-V 5.0 SP1

$
0
0

So, having just started a project where I get to use App-V 5 outside of the lab environment, this of many posts I plan to make regarding v5, hopefully some of you may find it useful!

The MSI packages created by the 5.0 SP1 sequencer refuse to install on the client, showing the following in the MSI log:

Error: could not load custom action class Microsoft.AppV.MsiTemplate.CustomActions.CustomActions from assembly: AppVMsiPackageTemplate

Using InstEd, I generated a transform between a 5.0 and similar 5.0 SP1 package. I then stripped out all of the application-specific entries to be left with just a couple of changes to the binary table. These hold the custom action dlls responsible for the error above.

To use this, just append the following to your msiexec command line:

msiexec /i package.msi /qb TRANSFORMS=AppV5_MSI_Fix.mst

Using InstEd/Orca or similar, you can also save a transformed version if you don’t want to mess about with command lines.

Use this at your own risk! Whilst everything appears to work fine so far, this is unsupported by Microsoft. I suspect that all the dlls are doing is running Powershell commands to import the package, and as far as I know these haven’t changed, so you should be ok.

Click here to download the MST.


Launching reg / bat / cmd / vbs files in App-V 5

$
0
0

App-V 5 behaves a little differently to App-V 4 when it comes to launching files with different file extensions.  For instance, if you have a shortcut pointing to a PDF file, in App-V 4 this could prove a problem if Adobe Reader was already running since it would pass the command onto the already running instance asking it to open a file in the virtual environment that it could not see.  This is no longer a problem in App-V 5 since the shortcut points directly to a PDF file under C:\ProgramData which Adobe can open since the location is always visible.

I had the pleasure of sequencing an application recently that had start menu shortcuts to .reg files to configure the application in different ways.  When launching these .reg files, the registry settings were applied locally, outside of the virtual environment, which were then hidden from the application due to the main keys being set to override.  The solution to this was to point the shortcuts to C:\Windows\Regedit.exe <Path to reg file> instead.  But then I had to do a couple of tests to satisfy my curiosity to see what would happen with batch files and vbscripts!

I created a .bat, .cmd and .vbs file that each created a registry key under HKCU and added them to a sequence.  A point of note is that the vbscript uses the RegRead method, since the WMI method will always write outside of the bubble anyway due to the WMI Windows service being run outside of App-V.

Test.bat:

reg add HKCU\Software\Test /v Test.bat /d Success /f

Test.cmd:

reg add HKCU\Software\Test /v Test.cmd /d Success /f

Test.vbs:

Set wshShell = CreateObject("WScript.Shell")
wshShell.RegWrite "HKCU\Software\Test\Test.vbs", "Success", "REG_SZ"

The result was that the .bat and .cmd wrote the registry keys outside of the virtual environment, whereas the .vbs file wrote the registry entry inside the virtual environment as desired.

To workaround this you can change the shortcut to run cmd.exe /c <Path to batch file>.  I don’t know why .vbs behaves differently and we don’t have to resort to using wscript.exe <Path to script file>, but nobody ever said that any of this would make any sense!

App-V and Legacy NTFS Junctions

$
0
0

I was having problems recently sequencing an application named SolarWinds Toolset; it appeared to be ignoring the data stored under C:\ProgramData captured during sequencing and instead reading/writing files to this location outside of the virtual environment.

A bit of Procmon analysis showed that the application was trying to read from C:\ProgramData\Application Data. On Windows Vista and 7, this is not an actual folder but an NTFS junction; a reparse point so that (badly written) legacy apps designed for Windows XP can be redirected to write to the correct location. NTFS junctions are similar to file/folder shortcuts that you may see on your desktop, but they are put in place all over Windows 7 to aid application compatibility after Microsoft changed the folder structure since Vista. You can easily view just how many of these there are on your system by running the following command:

dir /s /al c:\

Applications are supposed to query Windows APIs to determine exactly where the per-user and per-machine app data locations are. But often developers use alternate methods, such as %ALLUSERSPROFILE%\Application Data and %USERPROFILE%\Application Data. On XP these folders would equate to C:\Documents and Settings\All Users\Application Data and C:\Documents and Settings\USERNAME\Application Data. After changing the folder structure since Vista, NTFS junctions are used to redirect attempt to write to these location to the correct place.

For example, say an application tries to write to: %ALLUSERSPROFILE%\Application Data on Windows 7, which actually would prefer you to store per-machine appdata to C:\ProgramData. To achieve this, %ALLUSERSPROFILE% is set to C:\ProgramData, and in there is an NTFS junction shortcut Application Data, which also points to C:\ProgramData. All of this redirection goes on transparently behind the scenes and it all works wonderfully.

Except if you try to run this application inside App-V!

You can try the following test for yourself on either App-V 4 or 5. Here is a simple batch file that tries to read and write to these junction points:

@echo off

echo Program data:
type "%ALLUSERSPROFILE%\Application Data\Test\config.txt"

echo User data:
type "%USERPROFILE%\Application Data\Test\config.txt"

echo.
echo Updating data files...
echo.

IF NOT EXIST "%ALLUSERSPROFILE%\Application Data\Test\config.txt" (
md "%ALLUSERSPROFILE%\Application Data\Test"
echo This file stores program data >"%ALLUSERSPROFILE%\Application Data\Test\config.txt" )

IF NOT EXIST "%USERPROFILE%\Application Data\Test\config.txt" (
md "%USERPROFILE%\Application Data\Test"
echo This file stores user data >"%USERPROFILE%\Application Data\Test\config.txt" )

echo Program data:
type "%ALLUSERSPROFILE%\Application Data\Test\config.txt"

echo User data:
type "%USERPROFILE%\Application Data\Test\config.txt"

pause

This simply does the following:

  1. Tries to read 2 config files using the %ALLUSERSPROFILE%\Application Data and %USERPROFILE%\Application Data locations.
  2. If they do not exist they are created.
  3. Then it tries to read the config files again.

This mimics simple application behaviour where it will try to read its config files and create default ones if none exist.  Running this locally, we see this on the first run as expected:

firstrun

Then on each successive run the script can find the files both times:

secondrun

Now, you can sequence this batch file and create a shortcut to it.  On App-V 5, you will also have to craft your shortcut to run cmd.exe /c <path to batch file>, since shortcuts directly to batch files run outside of the virtual environment by default (see here for a previous post detailing this).  You can launch the app as many times as you like during sequencing and the same result as above will be displayed.  However, on first launch on the App-V client, the result from the first window will be displayed; the script cannot find the files in the requested location.  It then creates them and can read them again, but it appears that this redirection has pointed to the folders outside of the virtual environment and the files are created on the local file system instead.

I believe the reason for this is as follows. App-V only virtualises subfolders under the common VFS folders that are created or written to during sequencing. So if your app creates %APPDATA%\Test during sequencing, it will be captured and virtualised, and all reads and writes to this location will be redirected to the user’s PKG file in App-V 4, or the user locations under their profile in App-V 5. However, if in later use on the client the application tries to create a folder %APPDATA%\Test2, App-V will allow these file operations to take place on the local file system since that folder was not captured during sequencing. Since the subfolder Application Data was not captured during sequencing as the location does not really exist, App-V does not attempt to virtualise or redirect access to this location.

Hopefully this will not affect too many applications since most should be using the ‘proper’ methods for determing the folder locations.  But the potential undesired impacts of this are:

  • If you configure an application during sequencing, it may not be able to find the configuration on client launch.  This could either cause the application to crash, or for it to recreate default settings files.
  • If you have two conflicting applications, such as two different version of the same product, they could both be trying to write to the same location with unintended results.
  • For multi-user systems or terminal servers, one user can change the application configuration which will also affect other users.

I have found a workaround  for this problem, which could help resolve these issues if they are affecting you.  On your sequencer, before monitoring, delete any of the affected NTFS junctions (you will need to enable the viewing of hidden and system files in Explorer) and recreate them as real folders.  Then in the example above, the sequence would actually capture the folder C:\Programdata\Application Data\Test, and this would then read and write correctly on the client.

This fix didn’t work for the application I was working on originally since it contained many components, some of which use the proper methods for determining the folder locations, and some which didn’t – resulting in the data being split across two locations, which it did not like.  Microsoft’s Application Compatibility Toolkit may be a solution in these dire cases where you need to force the application to redirect to an alternate location!

Fixing File Permissions in App-V 5

$
0
0

Back in App-V 4, there was a very useful checkbox labelled ‘Enforce Security Descriptors’, which was checked by default. App-V 4 would capture all of the ACL’s containing user permissions and store them within the sequence. By default, it would enforce these and prevent a standard user (or an admin user running without elevation) from writing to locations as C:\ProgramData, C:\Program Files and C:\Windows in the same way as a regular application. Since unticking this box would effectively make App-V ignore all of these permissions and allow users to write to these locations, it quickly became part many people’s standards and templates to leave it unchecked. The benefits are that you spend less time debugging permission based issues for poorly written apps that try to write to these folders, and there are no drawbacks since all changes are redirected to the user’s PKG file, leaving the system unharmed.

Now we have App-V 5 and things work rather differently. ACL’s are not captured at all, and the ‘Enforce Security Descriptors’ checkbox is gone. Instead, the App-V client uses the same permissions that are applied to the folders outside of the virtual environment. For example, if users cannot write to C:\Program Files normally, they will not be able to write to any VFS (Virtual File System) folders here inside App-V either. The only exception is your Primary Virtual Application Directory chosen during sequencing time, which is fully writeable (although somebody has alerted me that perhaps it’s not, so more investigation is needed here).  Also by the way, the registry is fully open to standard users when inside the virtual environment and does not suffer form the same restriction as the file system.

At the moment we have been given absolutely no way given to us by Microsoft how to fix this problem. With App-V 4 or even MSI, permissions could be applied to certain files and folders to allow them to work without requiring full admin rights on the machine. Apparently Microsoft believe that most applications now adhere to their guidelines and do not try to write to such locations, and also that nobody is still using legacy apps these days. Just like they believed that nobody used the Start Menu or that everybody with an XBox had a stable internet connection! Hopefully they will backtrack on this one too with a bit of pressure!

I found a Technet forum post discussing the problem and how to work around it, but none of the suggestions work. Any permission changes to where the application files are stored under C:\ProgramData\AppV are ignored inside the virtual environment. You also cannot change the permissions from inside the bubble as a standard user (I didn’t try as an admin).

After investigation, I discovered that the ACLs for these folders are not simply inherited at runtime, they are copied and stored in the user profile, where they can be changed. App-V 5 splits the user’s sandbox for each application between two locations – folders that typically roam, such as %APPDATA%, get stored under C:\Users\USERNAME\AppData\Roaming\AppV. Any changes to non-roaming locations, such as Program Files are written to the local appdata folder under C:\Users\USERNAME\AppData\Local. It is under here that the App-V client creates all of the common restricted VFS folders that we are interested in, and it does this when the virtual environment for a particular application is launched for the first time. The folder are also emptied and the default permissions re-applied when the application is repaired.

LocalAppDataVFS

Example default permissions:

permissionsbefore

If you change the permissions on those folders to grant the Users group modify permissions, standard users can then write to those locations in the virtual environment. In fact you will have even more freedom than you did in App-V 4 since you can now create entirely new subfolders under Program Files, whereas in App-V 4 you could only write to subfolders that were created during sequencing!

One important thing to note is that you will only see the folders above that are part of your sequence.  If you need write access to a particular VFS folder, you need to ensure that folder is in the VFS within your sequence in the first place, as simply adding it to this local appdata location as an afterthought via a script for example does not work.

There are a few points to be aware of before trying to solve this with a script to modify the permissions:

  • The owner of each subfolder is set to the Administrators group and the Users group does not have full control; so standard users cannot adjust the permissions directly.
  • They can however delete and recreate the folders, and the new folders will then inherit full write permissions.
  • The folders do not exist at add / publish time to it’s not possible to change them with a script running as local system. It may be possible to add them from scratch, but since a repair resets the folders, it’s better to solve this with a script run within StartVirtualEnvironment.
  • However when the virtual environment initialises, it creates these folders and applies those permissions to the VE before running any StartVirtualEnvironment scripts. Once the VE is running, changes to the permissions from the outside take no effect until the VE is shutdown and restarted. Therefore an application will not see any of the changes applied until it is launched a second time.

I have put together a script (designed to be run outside of the VE at StartVirtualEnvironment) that does the following:

  • Checks to see if one of the VFS subfolders (APPV_ROOTS) has write access. The -guid switch is used to provide the package GUID.
  • If it does, assume script has already run or is not required, and quit.
  • If access is denied, the entire GUID subfolder is renamed, copied back to it’s original name, then the old copy deleted.
  • If the -warn switch is supplied, a popup box appears to warn the user that the permissions have been set, suggesting that they close and restart the application.
  • If the -error switch is supplied the behaviour is similar to the above with a different message, and the script exits with an error code, which can be trapped by setting RollbackOnError=True in the xml where you define the script. Use this if the application will not work at all without the permissions being in place to prevent it launching the first time around. Unfortunately the App-V client displays some further nasty error messages when a script returns an error, I don’t know if it’s possible to suppress these yet.
  • The -name switch can be used to supply a friendly package name to show on the message box popups. If the user launched lots of apps at once or put them in their startup folder, they might not know where the error is coming from otherwise.

 

Click here to download the script.

 

' VFSCACLS.vbs v1.0.2 (23/06/13)
' Written by Dan Gough © 2013 Aceapp Solutions

Option Explicit
On Error Resume Next

Dim objShell, objFSO, args, i, bWarnOnChange, bErrorOnChange, PackageGUID, PackageName, VFSPath, objTempFile

bWarnOnChange = False
bErrorOnChange = False

Set args = Wscript.Arguments
If args.Count = 0 Then
	WScript.Echo "USAGE:" & vbCrLf & vbCrLf & "VFSCACLS.vbs -guid <PackageGUID> [-name <ApplicationName>] [-warn] [-error]" & vbCrLf & vbCrLf & _
	"-guid : Package GUID." & vbCrLf & vbCrLf &_
	"-name : Text to show on title bar of any popup message boxes displayed when using -warn or -error." & vbCrLf & vbCrLf &_
	"-warn : Shows a warning message to the user that they may need to restart the application if changes have been made." & vbCrLf & vbCrLf &_
	"-error : As above but also exits with an error code of 1 so that this can trigger a script rollback and prevent the app from being launched."
Else
	For i = 0 To args.Count - 1
  		If LCase(args(i)) = "-warn" Or LCase(args(i)) = "/warn" Then bWarnOnChange = True
  		If LCase(args(i)) = "-error" Or LCase(args(i)) = "/error" Then bErrorOnChange = True 
  		If LCase(args(i)) = "-guid" Or LCase(args(i)) = "/guid" Then 
  			If i < args.Count -1 Then
  				If Len(args(i+1)) = 36 Then PackageGUID = args(i+1)
  			End If
  		End If
  		If LCase(args(i)) = "-name" Or LCase(args(i)) = "/name" Then 
  			If i < args.Count -1 Then PackageName = args(i+1)
  		End If
	Next
End If

If PackageGUID = Empty Then
	WScript.Echo "ERROR: No package GUID specified or invalid value."
	WScript.Quit(1)
End If

Set objShell = WScript.CreateObject("WScript.Shell")
Set objFSO = WScript.CreateObject("Scripting.FileSystemObject")

VFSPath = objShell.RegRead("HKCU\Software\Microsoft\Windows\CurrentVersion\Explorer\Shell Folders\Local AppData") & "\Microsoft\AppV\Client\VFS\" & PackageGUID
If Err.Number <> 0 Then
	WScript.Echo "ERROR: Unable to read registry key HKCU\Software\Microsoft\Windows\CurrentVersion\Explorer\Shell Folders\Local AppData"
	WScript.Quit(2)
End If

If Not objFSO.FolderExists (VFSPath) Then
	WScript.Echo "ERROR: Unable to locate folder VFSPath"
	WScript.Quit(3)
End If

Set objTempFile = objFSO.CreateTextFile(VFSPath & "\APPV_ROOTS\_VFSCACLCS_TempFile.txt", True)
If Err.Number <> 0 Then
	objFSO.MoveFolder VFSPath, VFSPath & "_old"
	objFSO.CopyFolder VFSPath & "_old", VFSPath
	objFSO.DeleteFolder VFSPath & "_old", True
	If bWarnOnChange Then
		MsgBox "Folder permissions have been updated.  It is recommended that you close and restart the application.", 48, PackageName
	End If
	If bErrorOnChange Then
		MsgBox "Folder permissions have been updated.  Please ignore any errors that may follow and launch the application again.", 64, PackageName
		WScript.Quit(4)
	End If
Else
	objTempFile.Close
	objFSO.DeleteFile VFSPath & "\APPV_ROOTS\_VFSCACLCS_TempFile.txt", True
End If

You can add this script to the default Scripts directory from the Package Files tab of the sequencer.  Then add the following to DeploymentConfig.xml:

<UserScripts>
	<StartVirtualEnvironment RunInVirtualEnvironment="false">
	<Path>wscript.exe</Path>
	<Arguments>VFSCACLS.vbs -guid XXX -name "My App" -warn</Arguments>
	<Wait RollbackOnError="false"/>
	</StartVirtualEnvironment>
</UserScripts>

The only mandatory parameter is -guid, which you can find from the very top of the xml file.  If you want to make the script error on first launch to prevent the app from loading until the permissions are ready, simply change -warn to -error and set RollbackOnError to true.

After running this, all folder permissions inherit from the user’s local appdata folder, which give System, Administrators and the owner (but not the Users group) write access:

permissionsafter

So please share this around and comment below if you’ve found it useful or have any issues or ideas for improvements. It would be nice to be able to suppress App-V error messages from a failing script and automatically re-launch the application for the user but that presents further challenges!

 

User Environment Variables in App-V 5 Scripts

$
0
0

One problem with scripting in App-V 5 is that when you run a script as the user, the process does not inherit the user’s environment variables.  If you try to reference %APPDATA% or %USERPROFILE% for example, they will all point to the locations belonging to the local system account.

Tim Mangan goes into more detail about this here and also has a free tool, which among other things sets an environment variable %EFFECTIVEUSERNAME% that you can use to help you reference user-related locations within your scripts.

Whilst useful, it doesn’t fully solve the problem.  Say there are policies in place to redirect the documents folder for VDI desktops but not laptops for example; you would not be able to rely upon the user name alone to locate the folder.

Using VBScript as an example, there are three common methods for retrieving known folders:

 

1. WScript.Shell.ExpandEnvironmentStrings:

Set objShell = CreateObject("WScript.Shell")
MsgBox objShell.ExpandEnvironmentStrings("%APPDATA%")

This will obviously not work since as already mentioned, the environment variables inherited by the script process are that of the local system account and you’ll just get ‘C:\Windows\system32\config\systemprofile\AppData\Roaming’.

2. WScript.Shell.SpecialFolders:

Set objShell = CreateObject("WScript.Shell")
MsgBox objShell.SpecialFolders("MyDocuments")

This method can only return a limited number of folders anyway, but for some reason it returns a blank value when run as a script in App-V 5.

3. Shell.Application.Namespace:

Const ssfLOCALAPPDATA = &H1C
Set objShellApp = CreateObject("Shell.Application")
MsgBox objShellApp.NameSpace(ssfLOCALAPPDATA).Self.Path

This is the most flexible method with the widest list of supported folders.  It works outside of the virtual environment even when run as the local system account, but for some reason when run inside App-V as a StartVirtualEnvironment script, Shell.Application.Namespace returns a null object.

 

The trick I used in the script in my previous post is to read the user’s local appdata folder location from the registry:

Path = objShell.RegRead("HKCU\Software\Microsoft\Windows\CurrentVersion\Explorer\Shell Folders\Local AppData")

I know the Shell Folders key deprecated, but it works and it’s unlikely that anybody would have redirected the local appdata folder in this case.  The ‘User Shell Folders’ key is no good to us here either since the value for Local AppData reads ‘%USERPROFILE%\AppData\Local’, and %USERPROFILE% is set to that of the System account when we are running a script.

A possibly more reliable method (which I may well update my script to use) is to read the environment variables directly from HKCU\Volatile Environment in the registry.  Under here you will typically be able to read:

  • %APPDATA%
  • %HOMEDRIVE%
  • %HOMEPATH%
  • %LOCALAPPDATA%
  • %LOGONSERVER%
  • %USERDOMAIN%
  • %USERDOMAIN_ROAMING%
  • %USERNAME%
  • %USERPROFILE%

Not all the user environment variables are stored here; %TEMP%, %TMP%, and any manually created variables will be stored under HKCU\Environment.

Note that for the %TEMP% variable, the registry key will usually read %USERPROFILE%\AppData\Local\Temp. I advise that you still grab it from here then manually replace the %USERPROFILE% portion with the value pulled from HKCU\Volatile Environment, since the temp folder will not always be directly under the local appdata folder, particularly on a terminal server.

Another option that should work is to loop through all of these registry keys in turn and set the environment variables as you normally would, then use them as normal!

App-V 5 and UAC File Virtualisation

$
0
0

In App-V 5 we no longer have PKG files, and changes made by the user are stored hidden away in various folders and registry keys instead.  Check out Thamim Karim’s articles here, here and here for a full explanation of how these locations work.  But essentially, file changes are stored here:

  • %APPDATA%\Microsoft\AppV\Client\VFS  (for roaming appdata)
  • %LOCALAPPDATA%\Microsoft\AppV\Client\VFS  (for everything else)

Whilst registry changes are stored here:

  • HKCU\Software\Microsoft\AppV\Client\Packages\<PackageGUID>\REGISTRY

However, this is not always the case.  If you are running an app under the following conditions:

  • You have UAC enabled
  • You are not running the app as administrator
  • The app is 32-bit
  • The app has no embedded or external manifest to tell it which execution level to use (i.e. asInvoker, highestAvailable, requireAdministrator) – typically all applications prior to Vista, and even some still being made today

Then the app will automatically redirect failed writes to certain system areas such as C:\Program Files and HKLM\Software to the following locations via a process known as UAC file virtualisation (not to be confused with App-V virtualisation):

  • %LOCALAPPDATA%\VirtualStore
  • HKCU\Software\Classes\VirtualStore

Now, consider that you are sequencing such an application and you have UAC enabled.  Instead of launching the application from the sequencer interface, which is running elevated, you run it via its shortcut and configure the application.  If it is a badly written legacy app that tries to write to these system areas, Windows silently redirects the write operations to the locations shown above.  Files will be excluded from the resulting sequence if you are using the default sequencer configuration to exclude %LOCALAPPDATA%, and registry will be captured under the VirtualStore key:

ExclusionWarning

CapturedVirtualRegistry

When you run the application on the client, any files or registry keys written here will not be visible.  It seems the UAC virtualisation system only looks in those two locations on the local system and ignores anything in the virtual environment.

Now, in another scenario, ignoring what happens during sequencing – what happens when you try to write to these locations when running inside the App-V client?  For the registry, same as usual – users have full permissions to write to HKCU and HKLM.  However, I noticed that HKLM writes get stored under Classes, something not mentioned in the articles linked to earlier:

  • HKLM: HKCU\Software\Classes\AppV\Client\Packages\<PackageGUID>\REGISTRY\MACHINE
  • HKCU: HKCU\Software\Microsoft\AppV\Client\Packages\<PackageGUID>\REGISTRY\USER\<USERSID>

Standard users will not be able to write to Program Files without resorting to the method I published recently.  The difference is that if the app satisfies the UAC virtualisation criteria, writes will be redirected to the VirtualStore folder, outside of the virtual environment:

LocalVirtStoreFile

I consider these bugs, resulting in the following issues:

  • The sequencer may not capture all desired files and registry
  • When launched, different packages could have conflicting files in the VirtualStore
  • When repairing the virtual app, any files in the VirtualStore will not be removed

If you have an application that is suffering from this problem, the workaround is to put a manifest next to the executable configured to use a suitable execution level:

  • requireAdministrator - use this if your intended users have admin rights and you want to pop up a UAC prompt.
  • asInvoker - this will not produce a UAC prompt – users will be able to write to HKLM since App-V allows this, but if you want the app to write to protected file system areas you will have to use my pre-launch script method to apply permissions to the VFS.

For example, for an app named Test.exe, put this in a text file named Test.exe.manifest in the same folder:

<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
    <assembly xmlns="urn:schemas-microsoft-com:asm.v1" manifestVersion="1.0">
    <trustInfo xmlns="urn:schemas-microsoft-com:asm.v3">
        <security>
            <requestedPrivileges>
                <requestedExecutionLevel level="asInvoker" uiAccess="false"/>
            </requestedPrivileges>
        </security>
    </trustInfo>
</assembly>

 
These tests were of course done using App-V 5. I haven’t tried the same scenarios on App-V 4, but it’s possible the same problems exist there also!

Overriding Group Policy Settings With App-V

$
0
0

There are certain situations where it is desirable to override group policy settings in an App-V package, for example:

  • Relaxing security settings to enable Data URI support in Internet Explorer in the virtual environment
  • Increasing security to restrict a virtualised legacy Java version so that only specific websites can access it

The last statement made by Microsoft on this subject was that it is not supported, and as of App-V 4.5, the client will ignore any policy registry keys in the package:

http://blogs.technet.com/b/appv/archive/2009/04/23/some-insight-into-how-softgrid-and-app-v-4-5-handle-group-policies.aspx

I’m not sure if Microsoft changed their stance on this at some point, but in my testing with App-V 4.6 SP3, any registry keys stored under HKLM\Software\Policies work just fine and are read and used by the virtual application. However, in a DSC linking scenario, any policies from the child packages are ignored similar to the way described in the link above; only policy keys in the parent package are used.

With App-V 5.0, all policies are ignored by default. Any attempt to read or write to HKLM\Software\Polices, HKCU\Software\Policies, or even HKCU\Software\Microsoft\Windows\CurrentVersion\Internet Settings, will get redirected to the native registry. Thankfully this is all configurable however! Please note that this is a global setting that will affect all virtual applications on the client, so care must be taken to avoid capturing policy settings in other packages unintentionally.

Here is the registry key in question, along with its default contents:

[HKEY_LOCAL_MACHINE \SOFTWARE\Microsoft\AppV\Subsystem\VirtualRegistry]
PassThroughPaths = REG_MULTI_SZ :
HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\WINEVT
HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\services\eventlog\Application
HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\WMI\Autologger
HKEY_CURRENT_USER\SOFTWARE\Microsoft\Windows\CurrentVersion\Internet Settings
HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Perflib
HKEY_LOCAL_MACHINE\SOFTWARE\Policies
HKEY_CURRENT_USER\SOFTWARE\Policies

Delete the value HKEY_LOCAL_MACHINE\SOFTWARE\Policies to allow the policy keys captured in the package to work. It appears that policies in HKLM override any equivalent policies placed in HKCU, so I advise just erasing this value and ensuring any policy values required in your sequences are stored under HKLM also. With connection groups, the policies can be placed in any of the packages, although the final result may be affected by the package load order and the merge/override status of the registry keys.

I recommend you that all keys are set to merge unless you absolutely want to override all content from a policy area in the native registry. For example, if HKLM\SOFTWARE\Polices\Microsoft\Windows\CurrentVersion\Internet Settings is captured and set to override, it may mask setting such as the proxy configuration, resulting in the browser not functioning correctly.

Sequencing Java – The Definitive Guide Part 1(Introduction and recipe)

$
0
0

Java is a necessary evil in today’s enterprise desktop. It is required by various business critical applications, yet it is the number one target for malware, made worse by the fact that people don’t always apply the latest security updates because they have an application that depends on an older version (or more commonly, are simply not bothering to regularly test their applications with each new release hoping that nobody notices!).

A great solution to this is to use App-V to virtualise older Java versions then link them to the applications (or browser shortcuts) that depends on them. Then the locally installed Java version can be kept up to date, or even removed entirely. There are a few problems that I have commonly seen with this:

  1. The solution does not always work as intended. Mostly the browser opens in the virtual environment with the desired version of Java, but sometimes it can ignore that and open the locally installed version. Sometimes the browser can hang or crash. Also to make it more complicated, these issues seem to affect some users and not others.
  2. App-V 5.0 SP2 now virtualises ActiveX control and Browser Helper Objects and presents them to the local Internet Explorer. Unfortunately this causes issues when we are virtualising legacy plugins and do not want the native browser to see them!
  3. Once the browser has been opened in the virtual environment with a legacy Java version attached, there is nothing to stop the user continuing to use the browser window to go about their daily business, where they are an open target for malware.
  4. There is no automatic redirection taking place, so the users have to remember which links they can get away with simply typing in and which ones they have to dig around in the start menu for. ThinApp has a solution for automatically redirecting URLs to specific packages, and there are third party solutions to the problem such as Browsium Ion, but nothing available to solve the problem for App-V.

This post is about solving the first problem by showing the results of my testing and sharing what has now become my standard recipe for sequencing Java.

The two main causes of the complications described in the first point above are:

  • If Internet Explorer is already running outside the virtual environment, attempting to open a new page can sometimes pass the request to the already running process rather than creating a new Internet Explorer process inside the bubble.
  • Insufficient isolation causing Internet Explorer to see multiple versions of Java, and in some cases attempt to load the latest rather than the desired legacy version.

Ensuring IE Gets Loaded Within The Virtual Environment

This one is pretty simple, and was originally shown to me by Colin Bragg (unfortunately the original blog post seems to have vanished). Add the -noframemerging parameter to the Internet Explorer command line, e.g:

C:\Program Files (x86)\Internet Explorer\iexplore.exe -noframemerging http://javatester.org/version.html

This forces IE to open in a new process inside the virtual environment.

Ensuring IE Loads The Correct Java Version

Sometimes even when you employ the trick above to ensure IE is running inside the bubble, certain conditions can cause the browser to load the locally installed version instead of the virtualised one. This is down to the virtual instance not being sufficiently isolated so that it actually sees both versions of Java.

Here are a couple of blog posts that describe the issue each with different solutions:

http://stealthpuppy.com/juggling-sun-java-runtimes-in-app-v

http://blogs.technet.com/b/virtualworld/archive/2007/08/14/troubleshooting-softgrid-with-process-monitor.aspx

I performed some tests to first of all reproduce the problem reliably, then to see if the proposed solutions above fix the problem. To test this out, the Java test page at http://javatester.org/version.html was used. This uses the deprecated <applet> tag, and in all instances tested, the virtualised Java runtime was loaded rather than the locally installed version.

Then to test the results using the <object> tag, a customised html file was used using the Java class file from javatester.org:

http://javatester.org/JavaVersionDisplayApplet.class

<html>
  <head>
    <title>Java Tester - What Version of Java Are You Running?</title>
  </head>
  <body>
    <object classid="clsid:CAFEEFAC-0015-0000-FFFF-ABCDEFFEDCBA" width="500" height="150">
      <param name="code" value="http://javatester.org/JavaVersionDisplayApplet.class">
      <param name="image" value="verify_anim.gif">
      <param name="centerimage" value="true">
      <param name="java_version" value="1.5+">
    </object>
  </body>
</html>

With a locally installed Java 7 and virtualised Java 6, at first this worked in the same way, loading Java 6 in the bubble. However, after launching the local Java 7 just once, the results changed. On Windows XP, Java 7 was loaded in the virtual environment instead of v6, and on Windows 7, Internet Explorer stopped responding. The java_version attribute is the important one here, and it accepts the following input types:

  • Selecting a specific version:
    • <param name=”java_version” value=”1.5.0_11″>
  • Selecting the latest version from a particular family:
    • <param name=”java_version” value=”1.5*”>
  • Selecting the latest version available with a defined minimum version:
    • <param name=”java_version” value=”1.5+”>

The value of 1.5+ was making Internet Explorer attempt to load the locally installed v7 instead of the virtualised v6, which in some tests caused the browser to hang. If a value of 1.6* was specified, the virtualised Java 6 loaded correctly.

Bringing up the virtual copy of the Java Control Panel highlighted the problem further by showing two versions of the Java plugin active:

Multiple Java versions

I tried the isolation techniques in the posts above but unfortunately could not get them to work to fix the problem reproduced as above. I even wrote a script to generate a huge number of future proof CLSID values and combined the registry entries from every available version of Java into a mega-anti-JRE but it still did not help.

The solution for me was not to be found in the registry at all, but in the config file deployment.properties. The folder hosting this file was not in the VFS of my virtual package, so when Java was launched it was writing this file to the local file system, where it was being shared with the local Java install.  This is why everything worked fine until I launched the local Java, after which it always went after the latest version. This also explains why some users suffer from issues and some do not!

Important points of note about this file:

  • The file is located in a different place on different operating systems:
    • Windows XP: %APPDATA%\Sun\Java\Deployment
    • Windows 7: %USERPROFILE%\AppData\LocalLow\Sun\Java\Deployment
  • If you installed Java via the vendor exe, this extracts the MSI to the locations listed above. If you install via the extracted MSI, this folder structure is not created and therefore not captured.
  • If you launch Java via the browser, Java Web Start, or the Java Control Panel, it will re-create the folder structure and create a new deployment.config file.
  • The AppData\LocalLow location is excluded by default in App-V 4.6. It is not actually in the exclusion list, but removing the %CSIDL_LOCAL_APPDATA% exclusion (which equates to AppData\Local) also covers this folder.  Nothing needs to be changed in App-V 5 as Root\VFS\LocalAppDataLow is included by default. No changes are required on XP either, as %CSIDL_APPDATA% is also included by default.
  • You don’t necessarily need to capture the deployment.properties file (unless you want custom settings in there) as it gets recreated automatically. All you need is for the Sun folder to exist in the VFS to ensure that read/write operations are contained within the bubble rather than redirected to the local file system.
  • It should be possible therefore to create a universal package by sequencing on Windows 7 32-bit and creating dummy folders %APPDATA%\Sun and %USERPROFILE%\AppData\LocalLow\Sun whilst monitoring (because 64-bit packages cannot be used on a 32-bit OS and XP does not have the LocalLow folder).

System Config Files

As well as the deployment.properties file that gets created under the user profile, system administrators can also create a system-wide config file, the settings in which can override the user settings.  For example, you may have configured your virtualised Java to run in medium security mode to fix a problem with a certain website.  If an administrator has deployed a system config file to force Java to run in high security mode, this would override the package settings and break the application.  For this reason, I recommend that you either create your own system config file within your package, or just create a dummy folder set to override to hide the local one.

The default path for this config file is C:\Windows\Sun\Java\Deployment\deployment.properties. The location of this file can be changed by supplying an additional file C:\Windows\Sun\Java\Deployment\deployment.config (see recipe).

Another note about deployment.properties is that you may be tempted to create a barebones config file in the user profile containing just the settings you need. However, from my experimentation, I have found that there is a property named deployment.version (which does not match up with the actual Java version!), which if incorrectly set, causes the settings to be erased and replaced with defaults.  This is another reason I recommend putting all desired settings in a system wide config file.

Java 7 Security Features Issues

Java 7u10 introduced a new feature which causes the Java plugin to check if an updated version exists before it loads. Then in 7u17 they also added a built-in expiry date so the plugin can complain that it is out of date even if you block it from phoning home at the firewall! If your Java plugin believes it is out of date, this is what you will see first:

Java Update Prompt

Even if you check the box at the bottom, it only ignores the current release and will just pop up again when it detects another Java update has been released. I have seen posts describing ways to suppress this (such as this one) but I did not have any luck with any of them – the only method that worked for me was to set the registry keys that are created by the action of dismissing the dialog:

[HKEY_CURRENT_USER\Software\AppDataLow\Software\JavaSoft\DeploymentProperties]
"deployment.expiration.decision.10.45.2"="later"
"deployment.expiration.decision.suppression.10.45.2"="true"

The keys above relate to Java 7u45. Yes, this is yet another versioning system being used by Oracle for the same product, don’t ask my why it says 10.45!

Another point of note is that these keys get wiped out if you open and close the Java Control Panel, so do not launch it after setting them!

If you are running 7u21 or above, you will run into another hurdle if your applet is unsigned (such as the one used at Javatester.org):

Javatester with out of date JRE7

To get past this you need to lower the security level to medium by setting deployment.security.level=MEDIUM in your deployment.config file.  Alternatively, Java 7u51 offers a way to do this for specific URLs by adding them to a text file named exception.sites which is then placed in the Sun\Java\Deployment\Security folder.

We’re not done yet! The next popup you will see still prompts you to update before running the plugin:

Javatester with out of date JRE7 - medium security, updates requested - 7u21

There does not seem to be an easy way to suppress this one except for launching the plugin during sequencing and checking the boxes to not show again. This saves a file under the user’s Sun\Java\Deployment\cache folder, but the format of the folder structure does not offer an easy way to automate this.  At least as of Java 7u40, there is a deployment.properties setting you can configure to at least get rid of the update option, deployment.expiration.check.enabled=false, which then changes the dialog to this:

Javatester with out of date JRE7 - medium security, updates disabled 7u40

So, security settings in Java 7 are a bit of a mess!

Disabling Java Updates

There seems to be a lot of differing advice around regarding how to disable Java updates, so I decided to get to the bottom of it once and for all, here are my findings:

  • All of the Java MSI packages contain three properties related to automatic updates, AUTOUPDATECHECKJAVAUPDATE, and JU.
  • These properties only seem to affect versions v5u11 to v6u18, where setting any one of them to zero prevents a Run registry key being created which launches the Java update scheduler jusched.exe on startup. This isn’t majorly important as App-V ignores these keys, but I set all the properties to zero anyway.
  • Java v6u19 onwards separates the Java Update components into a separate MSI package, and both are installed by the main setup exe. If you extract the main MSI and only install that, then you do not have to worry about it.
  • The Java Control Panel will display an update tab with updates checked by default for v5u11 to v6u18, and also for v6u19 onwards if the update components are installed. This entire tab can be hidden by setting a registry key (see recipe).
  • If you’re going back that far, updates appear to be disabled by default for v5u10 and below.

Sequencing Recipe For Java Runtime

WARNING! – If sequencing using App-V 5.0 SP2 and plan on using global (i.e. per-machine) publishing, you should read this post first and consider creating the sequence using SP1 instead!

If Java is sequenced on a 32-bit machine it will work on 64-bit, but it will not be usable on 32-bit if sequenced on a 64-bit machine. I recommend using Windows 7 32-bit to create these packages if portability between 32/64-bit is desirable.

Pre-Sequencing Steps

Download The Source Media

The various versions of Java can be downloaded from the following locations:

Java 7 downloads: http://www.oracle.com/technetwork/java/javase/downloads/java-archive-downloads-javase7-521261.html

Java 6 downloads: http://www.oracle.com/technetwork/java/javase/downloads/java-archive-downloads-javase6-419409.html

Java 5 downloads: http://www.oracle.com/technetwork/java/javasebusiness/downloads/java-archive-downloads-javase5-419410.html

Java 4 downloads: http://www.oracle.com/technetwork/java/javasebusiness/downloads/java-archive-downloads-javase14-419411.html

Java 3 doesn’t seem to work on Windows 7 so is being ignored.

Extract The MSI Packages

To extract the MSI package (and Data1.cab file), simply launch the executable (no need to install it) then look for the files under the following locations:

  • %USERPROFILE%\AppData\LocalLow\Sun\Java (for versions 6 & 7 on Windows 7)
  • %APPDATA%\Sun\Java (for versions 6 & 7 on Windows XP)
  • %LOCALAPPDATA%\Sun\Java (for version 5)
  • %TEMP%\_isXXXX (for version 4)

Alternatively, the download and extraction process can be automated using this method described by  Remko Weijnen:

http://www.cupfighter.net/index.php/2014/01/100-automation-of-java-updates/

I have modified this script and added a .cmd file wrapper so that you can drag’n'drop the Java exe installer onto the cmd file and extract the MSI automatically, although it only works on v6u19 and above. Download the script here!

It is possible to use the default provided exe to produce the virtual package, however:

  • Extra steps may need to be taken to disable updates.
  • Care must be taken not to install the Ask toolbar, which is bundled in some Java releases.
  • The source MSI that gets extracted during installation should be manually deleted to save space in the resulting sequence.

Modify The Exclusion List

The following path should be added to the exclusion list for all operating systems and App-V versions:

C:\Windows\Installer

I don’t recommend adding this to a standard template as sometimes icons are stored in here and excluding them can have detrimental effects, but it is safe to do so with the Java installers.

Then, if you are sequencing on Windows Vista/7 or above using App-V 4.6, you will need to remove the following exclusion:

%CSIDL_LOCAL_APPDATA%

Installation Location

In App-V 4.6, it should not make much difference whether Java is installed to the virtual mount drive or the VFS. However, all testing was done with Java installed to its default location in the VFS, as this should in theory provide extra isolation by masking the locally installed Java files since the root Java folder gets set to override.

In App-V 5, it is recommended to install Java to its default location, but set the PVAD (Primary Virtual Application Directory) in this case to a random folder e.g. C:\<PACKAGENAME>. This ensures the main Java folder is set to override as described above, but is also advised due to a strange issue that was sometimes seen when installing into the PVAD, where the root folder contained nothing but empty folders mirroring the same folder structure filled up in the VFS; the net result of this was a bunch of empty folders when viewed on the client.

Monitoring Steps

Installation

Install the extracted MSI. Example command line:

msiexec /i jre1.6.0_45.msi /qb AUTOUPDATECHECK=0 JAVAUPDATE=0 JU=0 ADDLOCAL=ALL

ADDLOCAL=ALL is optional but it enables extra non-default features in Java 4 & 5.

Configuration

Set the following registry key:

[HKEY_LOCAL_MACHINE\SOFTWARE\Wow6432Node\JavaSoft\Java Update\Policy
(on 64-bit Windows)
[HKEY_LOCAL_MACHINE\SOFTWARE\JavaSoft\Java Update\Policy]
(on 32-bit Windows)

"EnableJavaUpdate"=dword:00000000

Next, set up your config files.  Create a folder %USERPROFILE%\AppData\LocalLow\Sun (Windows 7) or %APPDATA%\Sun (Windows XP) if it does not already exist. If sequencing on Windows 7 32-bit, creating both folders should result in a package that works on all platforms.

Create a file C:\Windows\Sun\Java\Deployment\deployment.config with the following contents:

deployment.system.config = file:\\C:\\WINDOWS\\Sun\\Java\\Deployment\\deployment.properties

Then create a file C:\Windows\Sun\Java\Deployment\deployment.properties. The contents of this will be optional depending on your Java version and desired settings, but here is an example:

deployment.expiration.check.enabled=false
(to prevent the upgrade button in the dialog when running unsigned Java code. Only applies to Java 7u40 and above.)
deployment.security.level=MEDIUM
(required to enable expired versions of from Java 7u21 to run unsigned code)
deployment.security.level.locked
(this forces the security level to override the setting in the user deployment.config and disables the slider in the Java Control Panel)

To suppress additional update prompts in Java 7u10 and above, set the following registry keys, replacing the 45 in the version field with your Java update version (e.g. 10.51.2 for Java 7u51):

[HKEY_CURRENT_USER\Software\AppDataLow\Software\JavaSoft\DeploymentProperties]
"deployment.expiration.decision.10.45.2"="later"
"deployment.expiration.decision.suppression.10.45.2"="true"

It is recommended to remove the file associations with .JAR and .JNLP files unless this package is going to be the main version of Java. If a local version of Java is installed we do not want this virtual package to override its file associations. To do this, delete the following registry keys:

[-HKEY_CLASSES_ROOT\jarfile\Shell]
[-HKEY_CLASSES_ROOT\JNLPFile\Shell]

An extra thing I like to add is a modification to the browser title bar as a visual indicator that the browser is using a different version of Java. Unfortunately the title bar is no longer displayed in IE9 onwards, however the text can still be seen when hovering the mouse over the icon on the taskbar.

[HKEY_CURRENT_USER\Software\Microsoft\Internet Explorer\Main]
"Window Title"="Internet Explorer with Java 6u45"

Some versions of Java create shortcuts which need to be deleted:

  • Java 4 – Delete Desktop\Java Web Start and Start Menu\Java Web Start shortcuts
  • Java 7 – Delete Start Menu\Java shortcuts

 
I’ve automated all of these steps in a batch file which you can download here.
 

Post-Monitoring Steps

Delete any captured applications and create a new application pointing to the Java Control Panel. The location for this in Java 6 x86 on a 64-bit machine is:

C:\Program Files (x86)\Java\jre6\bin\javacpl.exe

OSD settings

The control panel is in a similar path for versions 5, 6 and 7, although the 64-bit Java versions are located under C:\Program Files instead of C:\Program Files (x86).  For Java version 4, the control panel is named jpicpl32.exe (also it has no icon by default but one can be set manually).

Modify the properties as per your own naming standards. Bear in mind that for App-V 4.6, the name + version joined together needs to be unique for each application, as does the OSD filename. It is recommended to append x86 or x64 to the version number at this point to prevent naming conflicts as a result of virtualising both 32-bit and 64-bit variants of the same Java release.

A shortcut is added by default when adding a new application, so this should be removed by expanding Shortcuts, pressing Edit Locations, and unchecking the box for the Start Menu.

In App-V 5, the applications are added and shortcuts are modified in the very last tab of the final sequencing stage.  The sequencer has a bug that means shortcuts cannot be edited, but they can be removed by pressing the delete key.

If sequencing Java 7u10 or above and you have set the registry keys to suppress the update prompt, remember do not launch the Java Control Panel as it will erase those settings!

Click here to continue to Part 2!


Sequencing Java – The Definitive Guide Part 2(Problems with App-V 5.0 SP2)

$
0
0

In Part 1, I discussed the reasons for virtualising Java along with some of the common problems, with a recipe to ensure the virtual Java instance is suitable isolated from any local installations. This part discusses how the new App-V 5.0 SP2 functionality negatively impacts the usage of virtualised Java plugins in a typical enterprise environment.

As of SP2, App-V 5.0 handles Browser Helper Objects and ActiveX controls differently – if the package is published globally (i.e. per machine) rather than per user, these components are locally integrated so that the native Explorer and Internet Explorer processes can see them without having to launch these processes inside the virtual environment. On the one hand, this is great new functionality, meaning you can now virtualise your primary instances of Adobe Reader, Flash Player, etc. On the other hand, there is no obvious way of disabling this functionality on a per-package basis. One of the selling points of a virtualisation solution is that you can deploy applications without fear of messing up anything that is locally installed. By beginning to integrate components locally, App-V is beginning to cross over into the dark side! This new functionality works for the relatively simple ActiveX controls mentioned above, but for some reason it does not work with Java possibly due to its more complex launch process, where in addition to having multiple CLSIDs registered for the plugin, there is an additional Browser Helper Object ‘SSV Helper’. As far as I can gather, this is responsible for  stepping in to deliver the highest available plugin version unless a specific version is requested (hence the acronym Secure Static Versioning). However, after virtualising Java 6 and publishing globally to a machine that has Java 7 installed (which is a typical usage case), then the Browser Helper Object from v6 ends up overriding the locally installed version:

Java 6 SSV Helper Add-on

Ignoring App-V for a moment, if you install Java 6 on top of Java 7, you often see a UAC prompt upon the next launch of the Internet Explorer due to ssvagent.exe wanting to run (I assume it is trying to update settings to re-register Java 7 as the default plugin). Exactly the same thing happens when layering the virtualised Java 6 on top of the local Java 7. This is what is shown after attepting to launch the local Internet Explorer:

Java UAC Prompt

This is a really annoying one, because if the user does not have admin rights, that prompt will appear every time they open a new browser tab until an admin comes along and authorises it. In addition another new security prompt appears, but this one can be got rid of via the checkbox:

Internet Explorer Security Prompt

The proper solution to this would be to modify DeploymentConfig.xml to disable the subsystems related to ActiveX controls and Browser Helper Objects, but unfortunately I have not yet been able to figure out how to do this.  I’ve tried using the tag element names from the internal manifest and putting them in the config file, but it failed to import every time due to invalid XML. Either I am doing something wrong, or the new elements have not yet been added to the config.xml schema! The current workarounds for this are:

  • Ensure all Java packages are deployed per-user rather than per-machine / globally published. This way the problematic components will not be integrated locally. Bear in mind that if you are deploying via the MSI produced by the sequencer, that this publishes the app globally.
  • If this is not feasible then sequence the Java plugins using App-V 5.0 SP1. Bear in mind that the MSI packages produced by the SP1 sequencer do not install without one of these workarounds:
  • Reinstall the local Java version each time after publishing a virtual instance.
  • Alternatively, these new App-V 5.0 SP2 features can be switched off – but this is a last resort as it affects all packages on the system.  This setting disable Shell Extensions, Browser Helper Objects, and Active X controls, and must be set before publishing the application:

HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\AppV\Client\Virtualization "EnableDynamicVirtualization="=dword:00000000

  • Similar to above, there is another setting that controls which processes are able to integrate with these new dynamic virtualisation features. If you want to keep the shell extensions working in Explorer, and just disable the Internet Explorer stuff, you should be able to do this by removing iexplore.exe from the following multi-string value:

HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\AppV\Client\Virtualization "ProcessesUsingVirtualComponents"= REG_MULTI_SZ

If you’re feeling experimental, some additional (and brutal) workarounds I have thought up but not yet tested are:

  • Running a PublishPackage script to launch the command <Java Install Dir>\bin\ssvagent.exe -new -high. This should prevent the UAC prompt by running the command pre-emptively.
  • Running a script to temporarily switch the EnableDynamicVirtualization setting off then on again after importing the package.
  • Running a PublishPackage script to reinstall the local Java to overwrite any unwanted settings coming from the App-V package.
  • Replacing the manifest in the virtualised ssvagent.exe to change the requested execution level to asInvoker. This way it would not show a UAC prompt, and could either fail gracefully or horribly when it finds it’s unable to do what it wants to do.
  • Delete the SSV Browser Helper Object from the virtual package. The keys appear to be located under HKLM\SOFTWARE\Microsoft\Windows\Explorer\Browser Helper Objects. This should stop it being integrated locally, but the downside is that it will not be available within the virtual environment either, where it may be needed – in fact a virtualised Java 6 might even then start using the SSV Helper from a local Java 7 installation which could have unwanted effects.

Additional Issues Using App-V 5.0 SP2 Alongside 4.6.x

An additional issue has come about, regarding using App-V 5.0 SP2 & 4.6 on the same machine.  Basically, if you had any 4.6 sequences with shortcuts to Internet Explorer, installing 5.0 SP2 breaks them. This is due to the new dynamic virtualisation features, it appears that App-V 5.0 steps in where it isn’t wanted and Internet Explorer does not launch in the 4.6 virtual environment.  The original post in German from Sebastian Gernert can be found here, and a translated page here.

Click here to continue to Part 3!

Sequencing Java – The Definitive Guide Part 3 (Restricting access to insecure Java versions)

$
0
0

Back in Part 1, we established the reasons for virtualising Java along with best practices for doing so, and in Part 2, we went over how the new features of App-V 5.0 SP2 can cause problems with this solution.

The next step is to create either a DSC link or Connection Group between your application and the Java package. Typically the ‘application’ will be just an Internet Explorer shortcut pointing to specific URL.

There is a problem with this approach however. The user will typically not be aware of what is going on under the hood, they just know that for this website to work, they need to use this special start menu shortcut as it won’t work by just typing the URL into their browser. Once the browser has been launched in the virtual environment with an insecure Java version (aren’t they all?), there is nothing preventing the user from continuing to use the session for their day-to-day browsing, where they might be unlucky enough to suffer at the hand of one of many exploits in the wild. You can’t rely on the basic isolation that App-V provides as a security blanket either, as there are plenty of ways to break out of the sandbox.

This post describes a solution to lock down the virtualised instance of Java so that it can only be loaded by specific sites. There are a few different ways to pull this off, but the simplest solution I came up with was to configure the internet settings to put every site into Restricted Sites by default, then configure a domain whitelist to allow specific URLs to be assigned an alternate zone, such as Internet, Intranet, or Trusted Sites.

There are four locations in the registry that can store these settings, and they have a hierarchy as follows:

  1. HKLM\Software\Policies\Microsoft\Windows\CurrentVersion\Internet Settings
  2. HKCU\Software\Policies\Microsoft\Windows\CurrentVersion\Internet Settings
  3. HKCU\Software\Microsoft\Windows\CurrentVersion\Internet Settings
  4. HKLM\Software\Microsoft\Windows\CurrentVersion\Internet Settings

Since HKLM\Software\Policies overrides all of the other locations, this is where we should place our configuration settings. All of these locations are ignored by default in App-V 5, so the registry settings on the client need to be reconfigured for this to work. Also, in App-V these settings are ignored if placed in any DSC link child packages, so they must be placed in the main package.  See my previous post Overriding Group Policy Settings With App-V for further information about this.

There are four default zones configured in Internet Explorer and each is assigned a number:

  • 0 – My Computer
  • 1 – Local Intranet
  • 2 – Trusted Sites
  • 3 – Internet
  • 4 – Restricted Sites

To configure all URLs to default to Restricted Sites, the following registry keys can be set:

[HKEY_LOCAL_MACHINE\Software\Policies\Microsoft\Windows\CurrentVersion\Internet Settings\ZoneMap\ProtocolDefaults]
"http"=dword:00000004
"https"=dword:00000004
"ftp"=dword:00000004
"file"=dword:00000004
"shell"=dword:00000004

There may be other protocols you wish to lock down, but these are all the defaults.

This however does not seem to apply when HTML files are loaded from the local machine, so to optionally harden the My Computer zone to block the Java plugin, the following key can be set (see this page for further information):

[HKEY_LOCAL_MACHINE\Software\Policies\Microsoft\Windows\CurrentVersion\Internet Settings\Zones\0]
"1200"=dword:00000003
(disables all ActiveX controls loaded via the object tag)
"1C00"=dword:00000000 (disables loading of Java via the applet tag)

Then, to place the domain javatester.org in the Internet zone, where it will be able to load Java, the following registry key can be set:

[HKEY_LOCAL_MACHINE\Software\Policies\Microsoft\Windows\CurrentVersion\Internet Settings\ZoneMap\Domains\javatester.org]
"*"=dword:00000003

The asterisk denotes all protocols, and the number 3 equates to the Internet zone as described previously.

All of these internet settings registry keys should be marked as merge, except for the Domains key listed above, which should be set to override. This is because we don’t want to override the entire Internet Settings key since it might contain vital settings such as proxy configuration.  We do however want  full control of the contents of the Domains key since the domain policy applied to clients might already contain some entries to direct certain URLs to Trusted Sites for example.

Sequencing Recipe For IE Shortcuts

It is recommended to create these sequences on a 32-bit machine if possible to increase their portability. Although I recommend steering clear of App-V 5.0 SP2 for now for creating the Java packages, it is fine to use it for generating these shortcut packages.

Pre-Sequencing Steps

If sequencing on a clean machine, many of the registry keys under HKLM\Software\Policies will not exist, so creating them prior to sequencing will help ensure that they get marked as merge by default rather than override. Set the following registry keys:

[HKEY_LOCAL_MACHINE\Software\Policies\Microsoft\Windows\CurrentVersion\Internet Settings\ZoneMap\ProtocolDefaults]

[HKEY_LOCAL_MACHINE\Software\Policies\Microsoft\Windows\CurrentVersion\Internet Settings\Zones\0]

Monitoring Steps

Create The Shortcut

Create a shortcut to Internet Explorer. Unless the site has a specific requirement to use a 64-bit Java plugin with the 64-bit version of Internet Explorer, ensure to use the 32-bit version of Internet Explorer from Program Files (x86) on a 64-bit Windows machine.

Edit the shortcut target to add the -noframemerging parameter followed by your URL. This switch forces Internet Explorer to create a new process, rather than pass the request to an instance of the browser that could already be running outside of the bubble. For example, on 64-bit Windows:

“C:\Program Files (x86)\Internet Explorer\iexplore.exe” -noframemerging http://javatester.org

Or on 32-bit Windows:

“C:\Program Files\Internet Explorer\iexplore.exe”
-noframemerging http://javatester.org

Change the default icon if desired.  You can either change it to the IE page icon as shown below:

IE icons

Or, if your desired web site uses a favicon, e.g:

favicon

You can find this in %LOCALAPPDATA%\Microsoft\Windows\Temporary Internet Files:

temporary internet files

However, you cannot browse to this location from the Change Icon dialog box so just copy it to the %TEMP% folder first (so that it does not get picked up as a file during monitoring).

Do not launch Internet Explorer during the sequencing process.  It is not necessary to create feature blocks to optimise streaming as the package will be tiny in size and launching will only capture unnecessary registry settings.

Applying The Policy Settings

Apply the following registry keys, adjusting the domain name and the required zone number as necessary:

[HKEY_LOCAL_MACHINE\Software\Policies\Microsoft\Windows\CurrentVersion\Internet Settings\ZoneMap\Domains\javatester.org]
"*"=dword:00000003

[HKEY_LOCAL_MACHINE\Software\Policies\Microsoft\Windows\CurrentVersion\Internet Settings\ZoneMap\ProtocolDefaults]
"http"=dword:00000004
"https"=dword:00000004
"ftp"=dword:00000004
"file"=dword:00000004
"shell"=dword:00000004

[HKEY_LOCAL_MACHINE\Software\Policies\Microsoft\Windows\CurrentVersion\Internet Settings\Zones\0]
"1200"=dword:00000003
"1C00"=dword:00000000

Post-Monitoring Steps

Again, do not launch Internet Explorer during the customise / streaming phases.

Create a mandatory DSC link to the required Java package if using App-V 4.6.

Check the override/merge status of the HKLM\Software\Policies keys. These should be correct if the pre-sequencing step was followed and the application was sequenced on a clean machine with no group policies applied.  In general, it is recommended that all the policy keys are set to merge except for the Domains subkey.

 

You can download all of the required reg files and some pre-configured Internet Explorer shortcuts here.

 

Demonstration

To give these packages a spin, I created them with App-V 5, and created a connection group using Tim Mangan’s excellent App-V Manage tool:

App-V Manage Connection Group

Then by launching my specially crafted shortcut, Internet Explorer opens, loading my virtualised version of Java. Notice the site is in the Internet Zone:

IE - Internet Zone example

If I then try to use the same browser instance to navigate to a different website, notice that it automatically gets put into Restricted Sites and the Java plugin is unable to load:

IE - Restricted Sites example
 

App-V 5 PVAD / VFS Layering Bug

$
0
0

Whilst testing for various App-V 5 issues, I often make quick little test sequences with one or two files in them to help. When doing so I came across this problem.

Now, a recap for those that may not be aware:

  • When sequencing you select a Primary Virtual Application Directory, otherwise known as the PVAD.
  • When inside the virtual environment, a file browser dialog, or the DIR command of a CMD prompt will display the folders created in the VFS, but the PVAD will be hidden.
  • Although the PVAD may be hidden from view, it is still accessible by either typing the path into a file browser dialog, or with the CD command of a CMD prompt.

In some of the test sequences I made (which were made for the purpose of tracking down a totally different bug), I was unable to access the PVAD via the CD command. After comparing the ones that worked with the ones that didn’t, I spotted the difference – all the packages where the App-V client failed to mount the PVAD properly had files installed only to the root, with no files or folders captured in the VFS!

It would be rare to see this in the wild, but an application that satisfies the following criteria would be broken by this bug:

  • The application tries to read/write assets (such as a config file) to/from the original install path instead of looking at the working directory, exe directory, or using the tokenised path under %ALLUSERSPROFILE%\Microsoft\AppV\Client\Integration\XXX\XXX\Root. An app might behave this way if it is either hard-coded to do so or if it reads the location from a config file.
  • The application only puts files down in its root directory, with nothing going to System32, Common Files, etc.
  • The application uses a non Windows Installer setup, or the C:\Windows\Installer directory is excluded if using a Windows Installer package.
  • The application only creates shortcuts in the root of the Start Menu or Start Menu\Programs folders (.lnk shortcut files are ignored by the sequencer, but if a directory is created, that is picked up and placed into the VFS as an empty folder).

If an app satisfies all of those points, then it will not be able to access the original PVAD path where the app was installed to.

It is also possible to trigger this bug by cleaning away ‘unnecessary’ VFS entries. If you’re the sort that likes to ruthlessly clean their packages after capture, make sure you leave at least one file or empty folder in the VFS!

To demonstrate this, I found a simple app in my toolbox that satisfies some of these criteria, Nirsoft IconsExtract. This is uses a NSIS installer (which therefore leaves no files behind in C:\Windows\Installer) and puts all of its files in the root install folder. By default it creates its shortcuts in a ‘Nirsoft IconsExtract’ subfolder of the start menu, and this empty folder is the only thing that gets captured in the VFS (since the .lnk files are ignored):

IconsExtract (default shortcut) - package contents

When bringing up a debug CMD prompt in the virtual environment, I can successfully cd into my PVAD ‘C:\Program Files (x86)\NirSoft\IconsExtract’:

PVAD Visible

However, if I change the shortcut location on the installer to put the shortcut in the root of the start menu instead, no new files or folders are captured in the VFS other than the built-in Programs folder which seems not to count:

IconsExtract (root shortcut) - package contents

Then when I try the same thing in the CMD prompt, it is unable to find the PVAD:

PVAD Invisible

If I open the first package up for upgrade and clean away the seemingly unnecessary empty folder, I end up with the same problem as the second package, a broken PVAD.

This particular application works just fine even with the broken PVAD by the way, but it’s likely that somewhere out there is an application affected by this, so hopefully this helps somebody someday!

Applying Dynamic Config To App-V 5 MSI Packages

$
0
0

The App-V sequencer produces an MSI package by default as part of its output. This is a wrapper that runs the necessary commands to publish and remove the virtual application. I first assumed that these would usually just be used for test purposes since most places would deploy the App-V native infrastructure or use SCCM, but it turns out a few customers I am working with are using these in a live environment, particularly those using Windows Intune cloud based management software, which does not handle App-V packages natively.

A big limitation of these MSI packages however, is that they ignore the DeploymentConfig.xml files (the UserConfig.xml file is irrelevant since the MSI publishes the app globally to all users). This means that if you want to modify any package settings, or add some package scripts, then you need a separate process to import these custom configurations and re-publish the applications with Powershell commands. Most people I have encountered have opted to forget the App-V deployment and stick with a traditional MSI if such scripting is required, rather than face the hassle of managing this situation.

To solve this, I have created a generic MST transform that can be used when installing the MSI to automatically import the DeploymentConfig.xml file, and also optionally enable/disable package scripts.

To use this, you would install like so:

msiexec /i MyApp.msi /qn TRANSFORMS=ApplyDeploymentConfig.mst

There are a couple of optional properties supported too. In the example above, it will assume that the DeploymentConfig.xml matches the default naming convention. If you have a custom file name however, you can supply it via the DEPLOYMENTCONFIG property:

msiexec /i MyApp.msi /qn TRANSFORMS=ApplyDeploymentConfig.mst DEPLOYMENTCONFIG=”C:\MyApp Config.xml”

The full path needs to be supplied to the alternate config file. I can see that this would be a problem if you don’t know the install path (as would be the case with SCCM for example), so I will update this soon so that it also works if given just the filename.

Because you may typically supply a custom config file in order to use App-V scripting, you can also enable (or disable) package scripts with the ENABLEPACKAGESCRIPTS property:

To enable scripts:
msiexec /i MyApp.msi /qn TRANSFORMS=ApplyDeploymentConfig.mst ENABLEPACKAGESCRIPTS=1

Or to disable scripts:
msiexec /i MyApp.msi /qn TRANSFORMS=ApplyDeploymentConfig.mst ENABLEPACKAGESCRIPTS=0

If this property is not supplied then the settings will not be modified.

Click here to download the transform.

I have designed it to work with both 32-bit and 64-bit clients, but have only tested it on 64-bit. Leave comments below if you find any issues!

App-V 5.0 and TerminateChildProcesses

$
0
0

You know, I think somebody on the product team at Microsoft must have looked at the old 4.6 setting ‘TERMINATECHILDREN’ and thought:

“You know what, I think we ought to rename that. It sounds a little evil, especially in all caps like that. How about TerminateChildProcesses? Oh, and while we’re at it, let’s do what we can to stop it working like it used to. Save the children!”

I’ve found three bugs with the new TerminateChildProcesses functionality in App-V 5.0, although the first one might arguably be a ‘feature’…

Detection Of Lingering Child Processes

In App-V 4.6, if you launch your applications for ‘streaming optimisation’ phase, the sequencer hangs around to make sure that all child processes are closed before continuing. If you close your app but this is still hanging around due to lingering child processes, you press the Stop button to force it to close:

4.6 sequencer

App-V 5.0 works slightly differently in that it will just tell you if any child processes are found when you hit next to finish the streaming phase:

5.0 sequencer

However I have found that I rarely see the above message, and often have to force it to pop up by leaving my specific application open when I press next if I know I want the TerminateChildProcesses setting applied to that app.

And I have just figured out why!

In 4.6, the ‘configure’ phase (which runs prior to the ‘streaming optimisation’ phase shown above) spins up a mini virtual environment, like a cut-down App-V client. When you press next to complete the phase, this virtual environment is disposed of along with any processes that were created within it, including task manager and any explorer windows that were opened.

In 5.0, the application is executed as a regular native application. This makes sequencing much faster, however when you go past this phase, any lingering child processes are left running. Then, when you get to the ‘streaming optimisation’ phase, these problematic background processes are not detected as new processes, hence the dialog above will not appear!

If Microsoft are listening, my preferred fix for this would be to move the detection of lingering child processes to the initial configuration launch phase. Additionally, terminate all processes triggered since the start of monitoring before entering this phase, in case any are left running by the installer, or if the user launched the app via the start menu. The other added benefit of moving the detection to this earlier phase, is that it adds child process detection for those of us that don’t perform streaming optimisation (which will be more commonplace now that fault streaming has been said to be more efficient!).

For everyone else, there are a couple of things you can do to avoid this if it is important to you:

  1. Before the streaming optimisation phase, open the task manager, and kill any processes that look like they are related to your application. This is my recommendation for now, although it’s not idiot proof as you might close an unrelated process by mistake. I have an idea to write a script to do the job though, if I get around to it I will add it to this post.
  2. Alternatively, don’t launch your app from the installer, start menu, or configuration phase. Instead, configure your app in the streaming optimisation phase. I don’t really recommend this, as sometimes apps can create new  file associations or register other new entries in various subsystems on first launch, and these will be missed if you skip the configuration phase.

Internal Manifest vs DeploymentConfig.xml

The 5.0 sequencer correctly adds the required <TerminateChildProcess> tags to both the manifest file inside the .appv package, and the external DeploymentConfig.xml. In fact it will add multiple identical entries for the same app if you launch it and accept the dialog more than once (bug #2!).

<TerminateChildProcesses>
  <Application Path="[{ProgramFilesCommonX86}]\Adobe\Adobe Drive CS4\ConnectUI\Adobe Drive CS4.exe" />
</TerminateChildProcesses>

The main problem however, is that (in my testing at least) the App-V client totally ignores the setting in the internal manifest file and will only listen to it if DeploymentConfig.xml is imported.  I think these config files are only imported automatically if using SCCM 2012 integration, so for any other deployment method there will be an extra step required to import the config. If you are using the MSI package to deploy, help is at hand with this transform I created earlier.

 

User Scripts Broken In App-V 5.0 SP2 For Local Accounts

$
0
0

I received a comment on my post ‘Fixing File Permissions in App-V 5′ from someone that was unable to run the script since updating to SP2.  I did a bit of testing in my home lab and found it still worked fine, so put it down to user error and carried on with my day.

Until, that is, I got the very same error working on a client’s system.  I had a UserScript configured to run at StartVirtualEnvironment, but whenever it was launched I saw the following error:

Script error

MSVCR100 error

The error code 534 in hex (1332 decimal) can be looked up here:

ERROR_NONE_MAPPED
1332 (0×534)No mapping between account names and security IDs was done.

As well as the 534 error, I’m getting an MSVCR100.dll not found error. Disabling App-V scripts stops both of these error messages and the application loads correctly.  The second error is a curious one, since by default if you install only the App-V 5.0 SP2 client on a clean machine, you will only have the 64-bit MSVCR100.dll present in C:\Windows\System32.  For some reason, the 32-bit virtual application is being told to use this dll when it doesn’t exist under C:\Windows\SysWOW64. I think this second error is nothing to worry about, being just a curious side effect of the virtual environment not starting up correctly due to the first error.

So after a lengthy troubleshooting session examining the differences between the working and non-working systems, I came to the conclusion that user scripts are broken in App-V 5.0 SP2 for local accounts only. Log on with a domain account and everything is ok.  Whether or not the accounts have admin rights or not makes no difference. The RTM and SP1 releases are not affected by this issue.

Luckily pretty much all live implementations of App-V will be used with everybody logging on with domain accounts, so this isn’t a major issue.  Packagers however tend to sequence and test using local admin accounts, which is where I and others ran into the problem!

App-V and the Flexnet Licensing Service

$
0
0

If an application uses the Flexnet Licensing Service, it can be sequenced and will at first appear to work fine in App-V.  However, if you have more than one instance of this service on the machine you can run into problems:

  • A Flexnet service may fail to start if the process is already running, which can cause the application that tried to start it to hang or crash.
  • An application can talk to the wrong instance of the service, which can produce errors saying that the application is not licensed.
  • Alternatively, an application can throw an error if the Flexnet service it comminicates with is an older version than expected.

These errors can vary depending on which application is started first. The Flexnet service is typically started manually by the calling application, then stopped when that application is closed. Whilst it is open, all other Flexnet applications will use that instance of the service.

Here’s an example of the problem – I have virtualised Adobe Photoshop CS4 with its own embedded copy of the Flexnet service, and have installed Tableau Desktop 8.1 locally, which also installs the service. Both applications work independently, but if I start Photoshop first, then Tableau, problems occur. Tableau hangs on load whilst it is waiting for the service to start; it then gives up waiting and talks to it anyway, only to find that it is the incorrect version:

Tableau error

And if I try to start the local Flexnet service manually, I see this:

Error starting Flexnet service

Since these problems might not be picked up until its too late, when the apps are already published to users, I always recommend banning Flexnet from every single virtual package and instead deploy it locally as an MSI. There are both 32-bit and 64-bit versions of this service, and both should use the highest version available and be regularly updated whenever a newer version is discovered. It’s probably even worth installing them on your base sequencer image.

If you install these services on the sequencer before monitoring, the service will never be picked up in the package. Unless the application you are sequencing contains a newer version, in which case the executable will be updated – in which case you should stop, update the Flexnet MSI package, then start again.

The latest version I have found is 11.12.0.0, and I have built two MSI packages, one for 32-bit and one for 64-bit.  They are built with Installshield, each contains just the single licensing service executable and uses the MsiLockPermissionsEx table to grant the Users group rights to start and stop the service. Because of this it depends on Windows Installer 5.0, so will only work on Windows 7 / Server 2008 R2 an upwards. ISM files are provided if you want to rebuild them yourself. If you come across newer versions, let me know and I can rebuild them and share!

Click here to download the packages.


App-V 5.0 SP2 Hotfix 4 Released!

$
0
0

If you’re using App-V 5, you need this update! With this, users can have full write permissions to the VFS, and can also start applications on network shares without having to give the computer account access. Package branching is back too, so you can test application updates by giving them to users without touching the live package.

There’s plenty more good stuff in this update, check out Tim Mangan’s article for more info:

http://www.tmurgent.com/TMBlog/?p=2029

You can download the update here:

http://support.microsoft.com/kb/2956985

App-V User Group UK 2014

$
0
0

Banner

I have been a regular attendee to the European App-V User Group (appvug.com) for the last few years and have found it a great place to learn and share information about App-V, meet various bloggers and MVPs and network with fellow professionals – as well as being a fun day out of course!

It appears that there is plenty of demand over here in the UK for a similar event, so it is with great pleasure that I, along with Danny Clarke, Nathan Sperry, Thamim Karim and Nicke Källén present the first App-V User Group UK, sponsored by add3. It will be held on Friday 3rd October at Microsoft’s London office at Cardinal Place.

We are still finalising the agenda, so watch this space for further details. Expect a star studded roster of App-V bloggers and MVPs to be presenting! In the meantime, get over to appvuguk.eventbrite.com and register as soon as you can, as availability is limited.

Stay up to date by checking back here, or on Twitter with #APPVUGUK

App-V 5.0 SP2 Hotfix 5 Released

$
0
0

This update was actually released a few weeks ago but it’s not widely known about so I am spreading the word!

http://support.microsoft.com/kb/2963211/en-gb

This release has the following changes:

  • Connection groups can now support a mixture of per-user and globally published packages
  • Powershell cmdlets now support -UserSID parameter for running commands as another user from an administrator session
  • PackageStoreAccessControl (PSAC) has been deprecated

Also, this will contain all the changes from Hotfix 4, which if you haven’t installed yet, you really should! More info here.

Issue With App-V 5 and Java Mission Control

$
0
0

I recently encountered a strange error when trying to sequence the Java JDK. It has a shortcut named Mission Control, which produced the following error message when trying to launch on the client:

JDK Mission Control Error
Invalid Configuration Location – The configuration area at ‘C:\Users\testadmin\.eclipse\810663534\configuration’ is not writable. Please choose a writeable location using the ‘-configuration’ command line option.

This folder is present in the VFS and should be writeable. I tried various tricks such as enabling full VFS write permissions and setting the PVAD to this location, but to no avail. I first thought it might be something to do with the folder name starting with a dot – Windows doesn’t really like this, for instance it won’t let you create such a folder through Explorer. Busting out Procmon however showed that the application is trying to create and delete a .dll file in this folder to see if it’s writable; and this file extension is read-only in the VFS (see here for more info on which file types are blocked). Here is the Procmon trace:

JDK Mission Control - without local folder

Since this folder is in the VFS, I would not expect to see the first few PATH NOT FOUND entries, so perhaps there is something else going on here that’s forcing it to look at the real file system instead of the VFS. The app works however if I create the folder on the local file system:

JDK Mission Control - with local folder

So, the simplest solution to this is to not launch the Java Mission Control shortcut during sequencing! This way the folder never gets created or captured, and it will create the folder on the local file system automatically.

This issue is not just limited to the Java JDK. I have seen a forum post where the same issue affects Eclipse, and I also happened to run into the exact same issue on two other applications in the same week. The error message is identical, and they all appear to have some code based on a modified version of Eclipse.

 

How To (sometimes) Fix A Crashing Sequencer! ImgBurn Recipe

$
0
0

I’ve come across a couple of apps that just do not want to be sequenced, crashing the sequencer in various ways, or even producing a package with an invalid manifest that cannot be imported. The first one was ImgBurn, a freeware disc image burning tool, and the second was IBM iSeries Access for Windows. I will use ImgBurn to demonstrate the issue, the debugging, and the solution.

The Problem

So, download and sequence ImgBurn, then attempt to go through to the process where you launch the applications for streaming optimisation, and you will see ‘Exception of type Microsoft.ApplicationVirtualization.Packaging.EncoderTools.EncoderToolsException was thrown’:

ImgBurn - Streaming Error

Hmm, not good. If you press OK and try to launch again the sequencer will hang forever. So, revert and try again but skip the streaming phase to go straight to the final package editing phase and you instead get ‘Microsoft Application Virtualization Sequencer has stopped working’:

ImgBurn - Editing Sequence

Not much better. So, revert again and this time just hit the option to save the package immediately – this time you will save a package but with an ‘Invalid manifest detected’ error:

ImgBurn - Invalid Manifest Detected

Debugging

Now you at least have a package to play with – but it fails to import into the client. The error message is not of much use, it pretty much just tells us that the manifest is invalid like the sequencer already did:

ImgBurn - PoSh Import Error

The Event Log doesn’t show anything on the Sequencer or the Client. The hidden debug logs show nothing on the sequencer either, but there is one in particular you want to activate on the client – ManifestLibrary:

Event Viewer - Show Debug Log

 

Event Viewer - Enable ManifestLibrary Debug Log

After this, import the app again and you will see this in the event log:

ImgBurn - ManifestLibrary Error

According to this, there is a ProgId entry with a missing name. Rename the .appv file to .zip and examine the AppxManifest.xml file buried within. This is how a file association should look – notice that the file extension is associated with a ProgId, then the ProgId definition follows along with the shell commands. This is the same way the file extensions, ProgIds and commands are usually linked in the registry:

ImgBurn - Manifest ccd FTA

However, the definitions for .img and .iso appear different – there is no name listed for the ProgId:

ImgBurn - Manifest img FTA

Looking at regedit back on the sequencer with the app still installed, the .iso and .img extensions are pointing to the ProgId Windows.IsoFile. Also, rather than listing the commands under the ProgIds, ImgBurn takes the non-standard approach of listing the commands directly under the extensions:

ImgBurn - Registry iso

 

ImgBurn - Registry WindowsIsoFile

 

I am assuming that the sequencer has difficulties when commands are registered directly under the extension key, and that extension key links to an already existing ProgID. So lets fix that by linking the .img and .iso extensions to the already existing but seemingly unused ImgBurn.AssocFile.img and ImgBurn.AssocFile.iso ProgIds:

ImgBurn - Registry ImgBurnAssocFileIso

After making this link, the shell command exists twice (and gets picked up twice in the sequencer) so the duplicate commands listed directly under the extension keys should be deleted.

Solution

To remedy this, run the following reg file after installing whilst still monitoring:

Windows Registry Editor Version 5.00

[HKEY_CLASSES_ROOT\.img]
@=”ImgBurn.AssocFile.img”

[HKEY_CLASSES_ROOT\.iso]
@=”ImgBurn.AssocFile.iso”

[-HKEY_CLASSES_ROOT\.img\shell]
[-HKEY_CLASSES_ROOT\.iso\shell]

Then proceed as normal; the file type associations will be picked up as they should and the application can be launched successfully during the streaming phase, saved and deployed.

Fixing Other Apps

The solution for IBM iSeries was slightly different; the installer nests two ProgIds, BCH and WS, under a common PCOMW key. The file associations for .bch and .ws then refer to the ProgId in the format PCOMW\BCH and PCOMW\WS. The AppxManifest.xml schema does not allow backslashes in ProgId names, so this was causing the error, found by exactly the same troubleshooting steps listed for ImgBurn. The fix in this case was to move these ProgIds into their own keys PCOMW.BCH and PCOMW.WS and update the file extension keys to suit, essentially replacing the backslash with a dot.

I ran into other issues preventing my from sequencing iSeries however, but this method of troubleshooting was still useful and can hopefully apply to other apps out there – let me know via the comments below if you’ve found any others!

 

Viewing all 67 articles
Browse latest View live