Anon
Anon

Reputation: 1431

.net: threading debug

What are some of the techniques available to debug multi threading issues in .net environment.

Upvotes: 2

Views: 281

Answers (2)

David Castell
David Castell

Reputation: 21

One source of multithreading bugs comes from failing to lock data that is used from multiple threads. Stress testing your app is a one technique to reveal some of these issues. The more threads that are contending with higher frequency for data the greater the chance of spotting a problem.

Spotting that your data has been corrupted by unprotected access can be tricky. Your app might limp on for some while before showing symptoms of being sick. Assertions can help with this. They give you an improved chance of spotting corruption very soon after it occurred.

The other main type of multithreading bug is the deadlock. One technique you can use to see if your app is flirting with deadlocks is to use lock level checking. Lock level checking does not wait to spot a deadlock. It alerts you at runtime that there is the possibility of a deadlock.

Lock level checking works like this: Suppose you have 3 locks - A, B and C. You give them levels 1, 2 and 3 respectively. If a thread always claims a lower level lock before a higher level lock then you'll never get into a situation where one thread can claim A then B whilst the other claims B then A. To implement lock level checking, give each of your lock objects a level. Use thread local storage so that a thread knows what lock level it last claimed. In fact have a stack object in thread local storage, so that when a lock is released you know the level of the previous lock. Some apps claim locks that they already own. That is safe. To allow for that in the thread lock checker you'll need to scan the stack of locks to see if it has already been claimed.

All this lock level checking does impose a performance penalty. So it is likely to be appropriate just for a debug or special build.

Upvotes: 0

Juliet
Juliet

Reputation: 81516

Debugging and unit-testing multithreaded code is notoriously difficult, and I don't believe there are any tried and true solutions to debugging multiple threads.

However, you can make it easier to write multithreaded code by taking a few notes from functional programming languages:

Use immutable data structures:

its very easy to write multithreaded code in F#, Haskell, Erlang, OCaml, etc because data structures and values in these languages are immutable, meaning that you can't modify a variable once it has been assigned. Essentially, this means every variable is declared constant, and there are no methods like List.Add or Dictionary.Add which mutate the collection.

Immuability means that nothing can be mutated after its been declared, therefore you never have to worry about one thread mutating shared state used by another thread. Since that's the case, you don't have to use locks or mutexes in your code, and you've eliminated a whole class of threading errors related to race conditions and dead locks.

Rely on message passing to share data between process Read these blog post:

Erlang is a remarkable language, specifically because its concurrency model is scalable up to 1000s and 1000s of computer. Rather than giving threads access to shared state, it relies on message passing to send information from one thread to another.

Rely on channels to syncronize threads Here is a nice video on the Newsqueak language: http://video.google.com/videoplay?docid=810232012617965344

It describes Newsqueak's interesting approach to concurrency. It uses objects called "channels" to pipe data from one thread to another. Its easy to find C# implementations of channels.

Remember, you can learn a lot about solving problems in .NET by studying how the same problems are solved in other languages.

Upvotes: 2

Related Questions