Why the debugger will not hit your breakpoints?

I am reviving my blog after several months. The reason I have been away is because I was learning IIS. But of course I have been doing other things on ASP.net. One of the things that I have been focusing on is looking into managed and unmanaged debugging with memory dumps. I want to start with some problems that you may encounter in certain environments when debugging.

So you have written you first ASP.net application and you want to debug the code. You set a breakpoint in Visuak Studio and you start with debugging (F5). You notice that the page executes perfectly, but your debugger didn't hit the breakpoint you set. What would be your first thoughts about that?

Here are some of the things you may check right away:

1. The program did not execute the code path where the breakpoint is present. This is easy to figure by setting a breakpoint at a place that you know for sure would execute such as Page_Init or Page_Load in an ASP.net webform

2. Ensure that debugging is enabled.

I have seen very few folks being confused about this part. For most development using Visual Studio, the project properties define whether debugging is turned on or not. This is a little different for ASP.net applications though. For ASP.net web applications, debugging can be enabled or disabled through the application's web.config file. You will be familiar with this attribute
 
 <compilation debug="true" />

This was always present when you create a new web application in Visual Studio .net 2003 and Visual Studio .net 2002, but not in VS 2005. So if you attempt to run a web application from within VS by hitting F5 key or selecting "Start with debugging" you will get a prompt asking you whether you want to turn on debugging before proceeding or run without debugging. The former is the default. When you select that, it simply adds this to your web.config file and proceeds.

There are also other things that happen under the hood when you enable debugging. The ASP.net compiler generates PDB (Program debug database) files within the Temporary ASP.net files folder. These are essential for debugging. If they are not being created, then breakpoints will not be hit.

Note that these are basic things that you should check before further investigation. Interestingly there is another setting in machine.config that controls generation of PDB files and this is specific to ASP.net 2.0.

            <deployment  retail = "false" [true|false]  />

When retail is set to true, ASP.NET disables certain configuration settings such as trace output, custom errors, and debug capabilities. When you have this attribute configured to true, you will ofcourse see the PDB files being created but you will also notice that Visual Studio deletes them after compilation. That behavior is by design and you can catch this by using File Monitor utility from sysinternals.

This attribute is a new feature of ASP.net 2.0 that allows system administrators to ensure that when developers put their applications onto production servers, debugging/tracing/custom errors are overridden even if they are configured in the application's web.config. Enabling debugging in a production environment is a very bad thing. If you want to know why and the specific details, then please read this article by Rahul Soni who is a Technical Lead and a splendid resource with ASP.net and IIS technologies at Microsoft:

https://aspalliance.com/1341

You can read more about the deployment setting here: https://msdn2.microsoft.com/en-us/library/dbcc2c62-3159-4a62-9f1e-8cfe3b8b09dc.aspx

Also note that debugging using Visual Studio in a production site must be avoided. When you set a breakpoint you have essentially paused the execution of your application loaded in the appdomain of the worker process. Some developers prefer to generate and keep PDB symbols of their application when they publish their site for offline debugging if a problem occurs. When you attempt to debug a  website published using “Publish Website” option in VS 2005 using CLR Debugger and put a breakpoint on the source code file, you may get a message “The breakpoint will not be currently hit. No symbols have been loaded for this document”.

This behavior is by design. The first step in publishing is to precompile the Web site. Precompilation for publishing is somewhat different from precompiling in place. Precompilation performs essentially the same compilation process that normally occurs when a page is compiled dynamically upon being requested in a browser. The precompiler produces assemblies from the pages, including both the markup and the code. It also compiles files in the App_Code, App_GlobalResources, App_LocalResources, and App_Themes folders. This precompiled output doesn’t have the symbols needed for debugging the application. But there is a workaround to this. Note that there is no option in VS 2005 to do this so don't bother surfing through all the menu options to try and find it. The workaround is to use aspnet_compiler with the -v and -d parameter. -d will generate the symbols for you.

3. Are you debugging on Windows XP 64-bit or a clean install of Windows Server 2003 with IIS? If so, read on...

With IIS 6 there is a property called Web Garden in Application Pools property within IIS Manager. By default this value is 1, but this is a configurable attribute. When you increase this value, then the system will spawn multiple worker processes for serving your application and requests will be routed in a round robin fashion to each worker processes. So in such a situation, you will notice that the debugger may sometimes hit the breakpoint and sometimes it will not. The reason being that the debugger will attach to one of these processes and if the request is being served by another worker process which is part of the same application Pool, the debugger will never know about it and therefore not break in.

Some Internet Explorer third party add-ons are also known to cause debugging failures.

Hope this posting was helpful. Please feel free to send me your comments.