If your app depends on a particular set of environment variables, it could sometimes be a real pain to debug.

Case in point: The .NET profiling API depends on two environment variables to push the unmanaged profiling DLL into a process.  I covered this in my December 2001 column. When the CLR startup code executes, it checks for these environment variables, and if set correctly, loads the profiling DLL,

Debugging a profiler implementation (like my DNProfiler.dll) was a real pain. I couldn't just launch the managed app under the IDE. Why not? Because the IDE didn't use to give you any control over the environment passed to the debuggee. The target app's environment was an inherited copy of the IDE's environment.

You might be thinking “Big deal. Just set the environment variables you need at a command prompt before launching the IDE.”  There's a catch: VS.NET itself uses the CLR.  Having my profiling environment variables set before launching the IDE would cause the profiling DLL to load up and affect the IDE. Not at all what I wanted.

To debug in this scenario, I had the following steps:

  • Compile an INT 3 into my profiling DLL's startup code.
  • Start the IDE and a separate command prompt with the profiling environment variables set
  • Run my .NET app from this prompt
  • When my INT 3 got hit, the Just In Time debugging dialog comes up in response to the exception
  • Select the “debug in the IDE“ option, which caused my IDE to attach to my process

What a royal PITA!!!

In Whidbey, there's much more control over the target's environment. You can specify environment variables to be passed to the debuggee. You have two choices:

  • Pass your data as the complete environment to the child
  • Merge your environment variables with the environment that the IDE would normally pass on

This makes debugging my profiler DLL much simpler. In the Debugging options, I simply specify the additional profiling environment vars and select the “Merge Environment” option.