I am going through some code right now that is not mine. In the code there is a thread with the following code:
while (true)
{
Thread.sleep(int.MaxValue);
}
It also catches InterruptedException and goes right back into the loop, so the loop can't even be interrupted.
Does anyone know why this thread would exist, what the purpose is?
EDIT: The full code, for a little bit more context:
using IKVM.Attributes;
using java.lang;
using System;
using System.Runtime.CompilerServices;
namespace applicationNamespace
{
internal sealed class DedicatedServerSleepThread : Thread
{
internal DedicatedServer theDecitatedServer;
[MethodImpl(MethodImplOptions.NoInlining)]
internal DedicatedServerSleepThread(DedicatedServer dedicatedServer)
{
this.theDecitatedServer = dedicatedServer;
base.setDaemon(true);
this.start();
}
[MethodImpl(MethodImplOptions.NoInlining)]
public override void run()
{
while (true)
{
try
{
while (true)
{
System.Threading.Thread.Sleep(int.MaxValue);
}
}
catch (System.Threading.ThreadInterruptedException)
{
}
}
}
static DedicatedServerSleepThread()
{
}
}
}
Note that the earlier code uses some non-standard libraries, so the lowercase sleep was valid. Specifically it was using ikvm libraries (which are based on java standard libraries, and used to cross-compile java programs to .net)
This was a java server program that I cross-compiled to .net bytecode and then decompiled. I wasn't sure if anyone had ever seen a thread dedicated to sleeping for any reason, and if so what the reason was. ta.speot.is for giving a really good answer.
Let's ignore the code you posted, since it won't compile, and just focus on whether a thread that sleeps forever serves any purpose.
There's three reasons I can think of for a thread whose job is to sleep, none of them are particularly legitimate.
To Do Nothing
The thread might exist to do nothing meaningful, forever. If someone tasked you with the job of creating a thread that should not do anything meaningful, ever, you might come up with that code.
To Keep The CLR/Process Alive
If it's a foreground thread, the thread will keep the process and CLR alive, even if the main thread completes. From MSDN:
A managed thread is either a background thread or a foreground thread. Background threads are identical to foreground threads with one exception: a background thread does not keep the managed execution environment running. Once all foreground threads have been stopped in a managed process (where the .exe file is a managed assembly), the system stops all background threads and shuts down.
To Cool Down
It's possible that by tying up a thread with sleep, other threads which can do meaningful work are not started as frequently (e.g. if they're being scheduled inside a threadpool or other environment). From The Daily WTF:
Due to a bunch of data-crunching speedups, the cpu's no longer have a chance to throttle down. The heat built up in the server, a fan controller fried and the cpu's cooked. As an alternative to purchasing redundant cooling, they made me slow the application down to previous performance levels with strategically placed sleeps.
The code, as written (except with Sleep capitalized), will only serve the purpose of making a thread that does nothing, and uses up some extra memory (for the thread's stack data).
It's possible that the thread was intended to perform some other function, but it's likely something that should have been handled in another manner.
From what you have shown us it just creates a thread and makes it sleep forever. Without more context we can't tell you anything else
Related
For a given task T, and blocks of code (wrapped in methods here) m1, m2 and m3,
is there a way to force any one of them - say m2 - to run uninterruptedly, i.e., that the thread running this program, upon reaching its time slice limit, if in the middle of execution of m2, do not leave the processor until m2 finishes, only then making room for a new thread ?
Is this possible ?
Example:
class Program
{
static void Main(string[] args)
{
Task task = new Task(() =>
{
m1();
//I want to assure m2 runs uninterruptedly, i.e., that the running thread does not stop while executing m2
m2();
m3();
});
}
private static void m1()
{
//whatever1...
}
private static void m2()
{
//whatever2...
}
private static void m3()
{
//whatever3...
}
}
Answering everybody's "why did you come up with this?", it popped up while trying to find a solution to this problem. What I thought: I need to guarantee that my switches from and to the main window handle is not interrupted/preempted.
Whether this is a plausible solution for my real problem or not - I thought the question was worth asking.
No. You are running your code on preemptive OS so there is nothing in your power to prevent preemption.
What is your real problem? Try to describe the actual problem you have, why did you come up with this requirement, and then perhaps one can offer advice to your actual problem..
After update
Remember this simple rule of thumb for multi-threaded programming: threads are almost never the right answer, event driven programming almost always is. Unless you have CPU intensive computation than can scale-up on distinct data sets, there is seldom a need to add threads. Spawning a new thread (or Task) simply to wait for IO (navigate to URL...) is an anti-pattern. Unfortunately 99.999% of multi-threaded programming examples simply use threads to simplify the control flow.
With that in mind, consider using an event driven model, for example EventFiringWebDriver. You will only have one thread, you main thread, and react in it to your web driver events (URLs downloaded, tabs opened, etc etc).
This is one of those situations where the correct answer depends on why you are trying to do what you are asking. Doing this right is much harder than it sounds.
In the general case, yes. There are ways that you can make that happen. However, I assume from the context that you are wondering if you can make that happen on a stock Windows OS. The short answer is no. Windows has a preemptively multi-tasking kernel, and there is a nothing a user process can do to prevent it from interrupting the thread when the time slice ends.
However, that's not the whole story. You can set your thread's priority to "REALTIME", which will keep it from being preempted by any other thread. The scheduler will still preempt you, but because no one else has a higher priority it will come right back to you. This document explains how to do that.
Note that this is know to be a bad idea. If not properly managed it will take over the whole machine and bring it to a screaming halt.
For most users, it is suggested to use the Multimedia Class Scheduling Service
If you really need real time services for your software (that is, being able to run something with hard guarantees about quality of service) you might look at real time extensions for Windows or Linux, or one of the fully real time systems like vxWorks or QNX.
Not without switching to a embedded version of windows that supports Real-Time Extensions. And even then you would need to switch from C# to a native language to be able to use those scheduling features.
The best you can do is change the thread's priority during the execution of m2 to make it less likely that it will get scheduled away. However if you are going to do that you should not use Task.Run and instead use a actual Thread object, you should not change priorities on a ThreadPool thread (which is what Task.Run uses).
I have a C# Winforms application that talks to a USB device through a vendor library. I run this interface with a background thread. During the vendor constructor, the entire Winforms application GUI is frozen. One core of the CPU is at 100%, but the other cores are idle. How do I determine what calls the vendor is making to block the GUI?
I run the background thread like this -
public HardwareInterfaceClass() {
var hardwareThread = new Thread(HardwareInterfaceThread);
hardwareThread.IsBackground = true;
hardwareThread.Name = "USB Interface Communication";
hardwareThread.Start();
return
}
private void HardwareInterfaceThread() {
var usbInterface = new USBInterfaceHardware(0); // Takes 5 seconds and blocks GUI
...
}
There is nothing at all in the code you posted that would block the UI thread. So there are two possibilities:
There is something in the library code you are calling that is blocking the UI thread.
The UI thread is not really blocked.
It's impossible to know for sure which is correct, though the first option would be very unusual, especially if you hadn't actually passed anything to the library code that would even tell it where your UI thread is (but not impossible…it could have logic internally that seeks out your UI thread and somehow messes with it).
If the second option is correct, then the UI could seem to be blocked, but simply not getting enough CPU. The fact that your other CPU cores are idle suggests this isn't the problem, but given how remote the first possibility is, it's worth at least considering.
If your background thread is taking CPU time away from the UI thread, then you can fix that by setting hardwareThread.Priority = ThreadPriority.BelowNormal;. Indeed, this is a good idea to do for any thread that spins consuming 100% of a core's CPU time.
There is, of course, a third possibility: in your own code, you have somehow caused the UI thread to be blocked while this background thread is working. But without a concise, complete code example it would be impossible to explain where that is. We can only look at the code you posted, and that code doesn't block the UI anywhere.
I have some common code that i seem to use often when it comes to some of our in house applications.
public State SomeState { get; set; }
Thread thread = new Thread(ThreadProc)
thread.Start();
void ThreadProc() {
while(isTrue){
//Changes SomeState after ping
//Can take up to 5 seconds to complete if service is unavailable
PingServiceTocheckState();
UpdateUI();
Thread.Sleep(200);
}
}
void UpdateUI() {
if (InvokeRequired)
{
Invoke(new MethodInvoker(UpdateUI));
return;
}
if(SomeState == State.Up){
//set these UI values (txt.Text = ...)
}
......
}
And the constant action may be updating Ui on a windows form or constantly reading from a network stream.
I feel this is probably outdated when compared to TPL and Async.
Am I correct to feel it can be better managed using Async/TPL?
And if so, could someone give me an example of how i would accomplish the above using these new ideas?
*Note: I currently use async occasionally and I am trying to make it more prevalent in my coding, but I am a little lost on the best method for creating a longrunning "background thread" using async.
Edit:
I have updated my example with a little more detail relating to my current project. I have code similar to this in a UserControl. I then have a windows form which adds ~50 of these controls dynamically. Without the Thread the form basically hangs, with the thread everything runs smooth. I just figured that rather than managing the thread myself async/TPL would manage the tasks (Ping and Update) more efficiently than myself.
The TPL is well suited to tasks that are short in duration - as you are basically using up workers from a pool. If your operation is continuous, a dedicated thread is entirely appropriate. If, however, the PerformAction is actually blocking waiting on data coming into a queue, and only actually has anything to do very briefly and occasionally, then yes: the TPL may come back into play. But then there is a question of sequential vs concurrent programming: at the moment, in that scenario, you will be processing things sequentially. The TPL makes no such guarantees, and is intended to process things concurrently. It is of course possible to write code that uses the TPL (or just the regualar ThreadPool) to process a sequential queue, but it is a bit more complicated, and there are edge-cases and thread-races around the "is there a current worker? do I need to start one? is it me?" questions.
Thread, TPL, Async stand on shoulders of the same OS kernel objects and artifacts. They are just different classes that provide different functionality to you.
None of them provides you with true low level control over threading, but, for example TPL, if can, splits your task among different cores of your CPU, and finds in general best possible way of paralleling your task on multi-core modern processors, so tends to be faster and more lightweight.
So TPL is a suggested library for multi threading handling in your app, if you have and can use most updated .NET framework.
MSDN on migrating legacy multithreaded applications (from this page on exception handling in threads):
In general, the change will expose previously unrecognized programming problems so that they can be fixed. In some cases, however, programmers might have taken advantage of the runtime backstop, for example to terminate threads. Depending on the situation, they should consider one of the following migration strategies:
Restructure the code so the thread exits gracefully when a signal is received.
Use the Thread.Abort method to abort the thread.
If a thread must to be stopped so that process termination can proceed, make the thread a background thread so that it is automatically terminated on process exit.
In all cases, the strategy should follow the design guidelines for exceptions. See Design Guidelines for Exceptions.
This suggests that using Thread.Abort is an appropriate way to terminate a thread. Has something changed while I wasn't looking? The last I'd heard was this could cause unexpected behaviours so shouldn't be used.
Thread.Abort is a lot safer than it used to be for the following reasons.
The runtime will defer aborts while execution is in unmanaged code.
The abort will allow finally blocks to execute.
However, there is still a problem with exactly when the ThreadAbortException gets injected. Consider this code.
public class Example
{
private DateTime value = DateTime.MinValue;
public void DoSomething()
{
try
{
value = DateTime.UtcNow;
}
finally
{
}
}
}
If this code were running on a 32-bit platform the value variable could be corrupted if Thread.Abort was called and the ThreadAbortException were injected in the middle of the write to value. Since DateTime is 8 bytes the write has to take place using more than one instruction.
It is possible to guard against this by placing critical code in a finally block and by using Constrained Execution Regions, but it would be incredibly difficult to get right for all but the simplest types your define. And even then you cannot just put everything in a finally block.
Generally speaking, Thread.Abort will kill threads, leaving the data they were processing at the time in an unknown state. The state being unknown, it's usually not safe to deal with that data anymore. However, when you're trying to terminate a process, you are not expecting to deal with that thread's data anymore, so why not abort it?
Well, the problem with Thread.Abort() is that will abort the thread possibly in the middle of work. That might cause your state to be corrupted. That's why is advisable to use a volatile bool flag to control the thread, and let the thread finish its task gracefully, but based on that flag.
For more details, I recall this blog post.
I have this simple code:
public void Run()
{
var invokerThread = new Thread(new ThreadStart(RunOnBackground));
invokerThread.Start();
}
private void RunOnBackground()
{
Trace.WriteLine("hi");
...
}
Unfortunately when running this code (from third party process) the thread doesn't really run.
Either in process explorer and in VS debugger I see that the thread is created and its state is "Running".
The main thread's apartment is STA and I've tried both STA and MTA on internal thread.
When I add to the Run() method at the end invokerThread.Join(); then the thread does run. But then again it doesn't really help.
What am I missing?
Edit: Here is some more information regarding the code hosting -
Run() method is called via COM interop from a process which is also managed executable assembly (the reason COM interop is used is because all other components in the system are native).
The method RunOnBackground() includes some more code after the tracing and generally its execution lasts between 10 - 20 seconds, including starting another process and waiting for its termination. Also I have some other areas in the code where I write some debug information to the Trace. While debugging the code, Run() runs as usual and after invokerThread.Start(); invokerThread's state is "Running" (though breakpoints inside the RunOnBackground() method don't stop).
When I add invokerThread.Join() at the end of the Run() method the debugger goes to RunOnBackground() after the Join().
There's some crucial information missing about what RunOnBackground() really does. This is otherwise a good match for what happens when you use apartment threaded COM objects on a worker thread. COM automatically marshals any method call on such an object from the worker thread to the STA thread on which it was created.
That can only work well when the STA thread observes STA threading requirements. It must pump a message loop and cannot block. Breaking those rules makes deadlock very likely, the worker thread call cannot complete until the STA thread dispatches the marshaled call. A sure sign that this is what is going on is seeing Thread.Join() solve the problem. It pumps a message loop internally in the CLR when it is called on an STA thread.
To diagnose this, you'll need Debug + Windows + Threads to see what that worker thread is blocking on. If my guess is right, it will be buried deep inside of the COM plumbing code, waiting for the marshaled call to complete. You can only see this by enabling unmanaged code debugging and setting up the Microsoft Symbol Server so you get debugging symbols for the plumbing code and get a reliable stack trace.
Fixing this is going to be difficult. You cannot magically flip a switch and make code run on a thread when it has explicitly stated that it doesn't support multi-threading. It is imperative that you create the instance of the COM object on the same thread that calls its methods. And that thread has to be an STA thread. Check this sample code for the approach. If you don't control the creation of the COM object then you're stuck.
I may say something stupid, but here is what I saw in MSDN Threads.
Look at the examples section at the end.
The output of the example is interesting, you can see there that the Thread created and started only starts executing when the main thread does a Sleep(0) or a Thread.Join().
It seems to be what exactly happens to you, doesn't it ?
Maybe try with a Sleep(0) on your main thread to really launch your working Thread.
Another workaround would be to use the BackGroundWorker.
As its name says it, it works on the Background and is really easy to use. It may be of much use to you.