Network Security Internet Technology Development Database Servers Mobile Phone Android Software Apple Software Computer Software News IT Information

In addition to Weibo, there is also WeChat

Please pay attention

WeChat public account

Shulou

How to deal with deadlock in .NET Monitor Program

2025-01-16 Update From: SLTechnology News&Howtos shulou NAV: SLTechnology News&Howtos > Development >

Share

Shulou(Shulou.com)06/02 Report--

This article will explain in detail how to deal with deadlocks in .NET monitor programs. The editor thinks it is very practical, so I share it with you as a reference. I hope you can get something after reading this article.

The monitor program is mainly used to monitor the occurrence of deadlocks, but this kind of .NET monitor program can only be used in testing, if widely used, it is likely to cause performance degradation.

Every day on the way home, there is always a long way too dark to read. At such times, if I am interested, I will use my mobile phone to surf the Internet, but most of the time I still use it to think. I just remembered on the road that one of today's tasks is to make all methods in a type "completely mutually exclusive" to multithreading-- I don't know how to name it, I mean any two methods An or B in a class, before An exits. The other thread cannot access B (and certainly cannot access A). The easiest way would be to mark each method as:

[MethodImpl (MethodImplOptions.Synchronized)] public void SomeMethod () {...}

But this means that every time you enter a method, it will automatically lock (the type of the method), and locking such a public object (or even cross-AppDomain) is naturally not a good practice. It is better to declare a private variable and then lock it. But this means that every method needs to be included in lock, and I find it troublesome to try to use a common Lock method and pass in an Action object, so that the lock statement appears only once:

Private object m_mutex = new object (); private void Lock (Action action) {lock (this.m_mutex) action ();}

However, this means that the Lock method is used inside every exposed method, which is different from using lock (this.m_mutex) directly. Of course, there is a difference. To put it bluntly, using the Lock method means that "if one day I want to remove the" mutex "condition, I just need to modify one of the Lock methods-otherwise I need to modify all the public methods.

Of course, I don't think this theoretical "advantage" is enough to modify the code, so I'll continue to use the MethodImplOptions.Synchronized approach.

After thinking about the circle above that didn't bring much value, I recalled an article on the front page of the garden today about deadlocks. Deadlocks are easy to occur, for example, the probability that the following code causes a deadlock is almost 100%:

Var mutexA = new object (); var mutexB = new object (); ThreadPool.QueueUserWorkItem ((_) = > {lock (mutexA) {Console.WriteLine ("Mutex An acquired."); Thread.Sleep (1000); Console.WriteLine ("Trying to acquire mutex B."); lock (mutexB) {Console.WriteLine ("Mutex B acquired.") }); ThreadPool.QueueUserWorkItem ((_) = > {lock (mutexB) {Console.WriteLine ("Mutex B acquired."); Thread.Sleep (1000); Console.WriteLine ("Trying to acquire mutex A."); lock (mutexA) {Console.WriteLine ("Mutex An acquired.");})

In this case, the code in both inner lock cannot be executed because each thread is waiting for the other to release before continuing, and this inconsistent mutex locking order results in a deadlock. So in a nutshell, under what circumstances will deadlocks occur? In fact, it is: "if thread An is holding object an and requests to lock b, while thread B holds b and requests lock c, and thread C holds c and requests... lock a", no matter how long the loop is and how many threads are involved, once such a loop occurs, it enters a deadlock. In fact, I think any book about the operating system will talk about how to check deadlocks-and unlock them. Since the lock statement only allows us to wait quietly, we might as well provide an implementation ourselves to avoid a deadlock. For example:

Public static class Lock {public static void With (object mutex, Action action) {...} so the statement that originally used lock can now be: / / lock (mutex) / / {/... / /} Lock.With (mutex, () = > {...})

In the Lock.With method, in addition to calling the Monitor.Enter/Exit method to implement the real lock, we also need to determine whether the mutex can be obtained correctly before the Enter. It's just to see if at the same time another thread is holding the current mutex object and (through a "chain") is also waiting for other mutex objects that the current thread is holding. If this happens, Lock.With does not call Monitor.Enter, but instead throws an exception. This must be feasible, and the crux of the problem is how to design a data structure that is easy to use, superior performance, and thread safe.

This is the end of this article on "how to deal with deadlocks in .NET monitoring programs". I hope the above content can be helpful to you so that you can learn more knowledge. if you think the article is good, please share it for more people to see.

Welcome to subscribe "Shulou Technology Information " to get latest news, interesting things and hot topics in the IT industry, and controls the hottest and latest Internet news, technology news and IT industry trends.

Views: 0

*The comments in the above article only represent the author's personal views and do not represent the views and positions of this website. If you have more insights, please feel free to contribute and share.

Share To

Development

Wechat

© 2024 shulou.com SLNews company. All rights reserved.

12
Report