Build Problems with a Very Large Visual Studio Deployment Project

So I have been tackling a build problem with some humongous deployment builds in Visual Studio.  In reality, VS Deployment Projects are not ideal for even slightly sophisticated MSI installers; but we've gone far enough down this path that we can't make the switch at the moment.  So please choose something with more control like the Microsoft-sponsored open-source project WiX or a well-established, paid product like InstallShield.

So the error I kept getting was "Not enough storage is available to complete this operation" and it would list some file (not the same every time).  It appears the error means the build process ran out of virtual memory or something.  So I found something interesting about default limit of 2 GB for any Windows process and how to raise that limit.  That process is discussed in this post:  http://murrayon.net/2007/12/building-monster-vs-2005-or-2008.html

Well, it has worked on one guy's laptop this whole time and it only worked for about 2 days on my machine (then it started getting an error that said "Unrecoverable build error" and was accompanied with a "Send Error Report" dialog).  I also tried the fix on like 3 other machines without any success at all (in fact many of the machines become highly unstable with the 3GB Windows boot switch).  So for 6 months, I couldn't figure out why it would work on that one machine and none of the others.  Well, just recently that guy's laptop joined the domain and started using a domain user account (I have no clue why he wasn't from the beginning, but I digress).  His machine didn't become unstable, but it did quit building our monster deployment build.  We thought we were up a creek with no box to build the MSI installer and a deadline fast approaching.  We got it working on his laptop by going back to a local user account.

Well, that got me thinking about how we could get another PC to be able to do the darn build.  I tried the build on my PC with just a local user account, but that didn't work because I don't currently have the other fix named above.  So I created a virtual machine (in case things got unstable again) and didn't add it to the domain, just to be safe.  I did the fix named above, and am now able to successfully build this MSI install consistently under a local user account without getting the "Not enough storage is available" error message.  The details of this adventure are discussed in this post:  http://murrayon.net/2007/12/build-error-when-building-very-large-vs.html

Maybe in a few months we'll move this installer build process to WiX and avoid the inflexibility we are running into with Visual Studio Deployment Projects.

View Full Article

Display Name in Add/Remove Programs, MSI-Installed Products, and Compressed GUIDs

I was trying to rename a product's display name found in its ARP (Add/Remove Programs) entry.  There is a registry key that lists just about every product installed on your machine:

HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall

Most (if not all) MSI-installed products have an entry under this key that is the ProductCode GUID.  Every product under this key seems to have a DisplayName value, some of which you can modify and it will show the change in ARP.  However, it appeared any product installed via MSI did not work this way.  So I went registry hunting for any other entries the MSI installers might create.  I found the following location:

HKEY_LOCAL_MACHINE\SOFTWARE\Classes\Installer

This key has many helpful sub-keys (including Assemblies, Components, Features, Patches, Products, and UpgradeCodes); the Products sub-key is the most important to me at the moment.  Under this sub-key there are many entries (not as many as the first location I mentioned; these appear to MSI only products) that appear to be GUIDs without hyphens and braces.  However, the key that represented the product I was interested in didn't match the ProductCode I had.  But in one of the values, there was a PackageCode that was indeed the correct package GUID (different than ProductCode) and the ProductName matched as well.  Turns out for MSI-installed products I could change this ProductName value and it would make the change to its ARP entry.

But I was puzzled how I would know which entry to pick for any given product under this Products sub-key.  I ended up coming across this blog post that explained what these different GUIDs are (called Compressed GUIDs); focus on the "UPDATE" section by John Walker:

http://www.hanselman.com/blog/BATCHFILEVOODOODeterm.....UsingUpgradeCode.aspx

And then John Walker's update mentions this link that explains how to convert back and forth between regular and Compressed GUIDs:

http://www.appdeploy.com/messageboards/tm.asp?m=11996&mpage=1&#12037

Basically you break up the GUID into groupings and reverse them.  See below:

  • Original GUID:  {abcdefgh-ijkl-mnop-qrst-uvwxyz123456}
  • Groupings:  abcdefgh ijkl mnop qr st uv wx yz 12 34 56
  • Reversed Groupings:  hgfedcba lkji ponm rq ts vu xw zy 21 43 65
  • Compressed GUID:  hgfedcbalkjiponmrqtsvuxwzy214365

Don't know why Microsoft chose to butcher up GUIDs like this, but it's nice to know.

View Full Article

Finding Microsoft Office's Install Location

One of my co-workers, in trying to find the install location of Microsoft Word, found a cool little registry tree.  Here is the key:

HKEY_LOCAL_MACHINE\SOFTWARE\Classes\Applications

Underneath this key, there are keys named Winword.exe, EXCEL.EXE, Outlook.EXE, MSACCESS.EXE, POWERPNT.EXE, explorer.exe, iexplore.exe, AcroRD32.exe, iTunes.exe, javaw.exe, and so on.  It appears many of the big companies use this area to put information about how to do certain commands for a product from a shell (like open, edit, print, etc.).

My next post will be about another section under SOFTWARE\Classes that I discovered.

View Full Article

Launching MSIExec.exe From C#

I ran into a problem with trying to spawn off a process to launch an MSIExec.exe command from C#.  I wanted to launch the process and then wait for it to finish before proceeding; however,  it was always returned immediately before the install or uninstall was really finished.  I confirmed this behavior with this blog entry:  http://blogs.msdn.com/heaths/archive/2005/11/15/493236.aspx

The author suggests "start /wait" which works from the command line or a batch file.  I did verify it works launching a batch file or two from C#, but I preferred to keep in C# as much as possible.  Also, I was trying to accomplish a silent background process running the MSIExec commands.  However, C# can't just start a process calling "start," which is an internal command to the Command Prompt I guess.

Someone reminded me on a message board that you can start a process using CMD.exe, calling "start" like this:

ProcessStartInfo startInfo = new ProcessStartInfo(
    "cmd.exe",
    string.Format("/c start /MIN /wait msiexec.exe /x {0} /quiet", guid));
startInfo.WindowStyle = ProcessWindowStyle.Hidden;

Process process = Process.Start(startInfo);
process.WaitForExit();

It works like a charm.  I don't think you even need the "/MIN" flag for "start" anyway.

View Full Article