When you start multiple threads on a multi core processor, are they guaranteed to be processed by different cores?

26

6

I have a Pentium core i5 processor, which has 4 cores. If I do this in a C# console program

var t1 = new Thread(Thread1);
var t2 = new Thread(Thread2);
t1.Start();
t2.Start();

are t1 and t2 threads guaranteed to run on separate cores?

developer747

Posted 2013-06-07T18:31:46.303

Reputation: 385

1

Assuming that the C# runtime uses equivalent native system calls to spawn another thread (and is thus truly parallel; this is not the case for everything, like CPython's infamous Global Interpreter Lock), this would depend solely on the operating system's process/task scheduler. In general though, code is truly thread safe if you assume that t1 and t2 are executed at different times in an arbitrary order (e.g. it's possible t2 starts before t1 in some models).

– Breakthrough – 2013-06-07T20:45:02.040

2I didn't know that there were Pentium i5 processors. Maybe you meant Core i5? Picky. I know :D – JosephGarrone – 2013-06-08T01:59:54.713

Answers

19

You cannot guarantee in .Net that two Threads run on two separate cores. In fact, you also cannot guarantee that one Thread will run on only one core(!).

This is because managed threads are not the same as OS threads - a single managed Thread may use multiple OS threads to support it. In C#, you only ever deal directly with managed Threads (at least, without resorting to p/invoke to call the WinAPI threading functions, which you should never do).

However, the .Net and Windows thread schedulers are very good at what they do - they wouldn't run two threads on a single core while a second core sits completely idle. So, in general, you don't need to worry about it.

BlueRaja - Danny Pflughoeft

Posted 2013-06-07T18:31:46.303

Reputation: 7 183

In practice, .Net Threads are OS threads. But that's not why there is no guarantee that a single thread will always execute on the same core. – svick – 2013-06-07T21:44:15.790

2@svick: In practice, on x86, that is true. However, the standard explicitly states that you cannot rely on this behavior, so it could change in the future. In fact, it is not true on other versions of the .Net CLR, like XBox 360's. – BlueRaja - Danny Pflughoeft – 2013-06-08T18:39:36.337

@BlueRaja - The question is specific about what version of the CLR we are talking about. You can guarantee something will exists on two seperate cores by using async threads because it would mean they would happen async from one another. The current example code is a sync call technically. Of course the operating system decides what cores would be used. – Ramhound – 2013-08-06T16:45:37.083

@Ramhound "You can guarantee something will exists on two seperate cores by using async threads" - that is false. The async keyword (which is what I assume you are talking about, as "async threads" is redundant) is just syntactical sugar for using a BackgroundWorker thread, which is like any other .Net thread - you can't guarantee whether it will run on a separate core or not. – BlueRaja - Danny Pflughoeft – 2013-08-06T17:56:13.077

@BlueRaja - If two async threads were started they would both run at the same time provided there were 2 CPU cores. If there was only one then the operating system would schedule when each thread would get priority and run and your typical single threaded thrashing situation would happen. This was how I was taught how a CPU handels multi-threads. – Ramhound – 2013-08-06T18:04:33.937

@Ramhound: Your understanding is close, but flawed. Even if the computer has two cores, the OS won't necessarily schedule both threads to separate cores (eg. it might currently be using one of the cores for something much higher priority). In that case, both threads would be scheduled to the same core, and the usual context-switching would occur (which would have to occur anyways; a normal PC has dozens of processes running at once!). Also, it's not called 'thrashing' - that is something completely different.

– BlueRaja - Danny Pflughoeft – 2013-08-06T18:10:51.433

@BlueRaja - You are indeed right Thrashing is something else, the specific term I am looking for, currently escapes me. I suppose two async threads could be given the same core, finding it hard to find the words, to describe exactly what I am thinking of so I will just drop it. – Ramhound – 2013-08-06T18:32:36.407

16

No, the OS and CPU will decide what to run and when. in the simple example you have shown, to the exclusion of other tasks, yes those would most likely run in parallel on separate cores, but there is rarely a guarantee that that will be the case.

You can use the thread affinity to attempt to take some control over the allocation of a core to a given thread.

Also consider scheduling priorities to stack the deck in terms of which threads should be entirely parallel, and which can wait.

Frank Thomas

Posted 2013-06-07T18:31:46.303

Reputation: 29 039

1I also want to add, that with virtualization technologies there is another layer between your program and the hardware. What the OS presents to the application might not be physically accurate. – Keltari – 2013-06-07T19:07:12.300

1Those are WinAPI functions for OS threads, not for managed threads. They should never be called from C#, as they could severely interfere with the .Net thread scheduler. – BlueRaja - Danny Pflughoeft – 2013-06-07T20:31:36.650