Identify What Block UI Thread

I am working on a fairly large real-time WPF .NET application. The application works perfectly and, as expected, with the exception of one big problem - updating the user interface is slow.

This application is heavily event driven, all events occur in all cases - through these events the user interface is updated.

One or more of these events block the display of the user interface. When all work is completed, the user interface will display the expected results.

Is there a way to determine which event handler is causing the bottleneck?

Any help would be appreciated.

+4
source share
4 answers

I fully support the suggestion of colitis to use a profiler.

Alternatively, if the lock takes more than a second, you can click the Pause button in Visual Studio. The toolbar has a drop-down list in which you can select "Main theme". He then moves on to a method that currently blocks the user interface.

+6
source
public class UIBlockDetector { static Timer _timer; public UIBlockDetector(int maxFreezeTimeInMilliseconds = 200) { var sw = new Stopwatch(); new DispatcherTimer(TimeSpan.FromMilliseconds(10), DispatcherPriority.Send, (sender, args) => { lock (sw) { sw.Restart(); } }, Application.Current.Dispatcher); _timer = new Timer(state => { lock (sw) { if (sw.ElapsedMilliseconds > maxFreezeTimeInMilliseconds) { // Debugger.Break() or set breakpoint here; // Goto Visual Studio --> Debug --> Windows --> Theads // and checkup where the MainThread is. } } }, null, TimeSpan.FromMilliseconds(0), TimeSpan.FromMilliseconds(10)); } } 

Just a new class in the MainWindow constructor. When the breakpoint hits, you can go to Visual Studio -> Debug -> Windows -> Threads and check what operation blocked your UI-Thread!

+9
source

Do you have access to the code profiler? This is the thing they are good at. I recommend getting one if no answer.

In addition to using the profiler. You can do a poor person profiling by putting synchronization instructions at the beginning and end of the code blocks that you suspect. You can even use breakpoints and time with a wall clock. Is there a problem when you click something? If so, start there. Is this a recurring problem without user interaction? Start with timers.

As for the actual solution to the problem ... If the intruder handler does not do something that can be done more efficiently, consider using a multi-threaded approach. The new task library for .NET 4.0 is truly amazing in this regard.

+5
source

As a first-order approximation, I find it useful to break the debugger (with the pause button in the IDE) and look at the stack. Do this several times and you will see if there is a template. Are you always in the same function? Are you doing something expensive in response to an event? Do you get more events that you expect? It is low-tech, but can be very effective.

+1
source

All Articles