Multithreading – Programs Not Multi-Core Friendly

concurrencymultithreading

You see this phrase or similar kicked around from time to time, generally referring to a program that claims they were not designed to take full advantage of multi-core processors. This is common especially with video game programming. (of course a lot of programs have no concurrency and do not need it, such as basic scripts, etc).

How can this be? A lot of programs (especially games) inherently use concurrency, and since the OS is in charge of task scheduling on the CPU, then are these programs not inherently taking advantage of the multiple cores available? What would it mean in this context to "take advantage of multiple cores"? Are these developers actually forbidding OS task scheduling and forcing affinity or their own scheduling? (Sounds like a major stability issue).

I'm a Java programmer, so maybe I have not had to deal with this due to abstractions or whatnot.

Best Answer

Good concurrency requires a lot more than throwing a few threads in an application and hoping for the best. There's a range in how concurrent a program can be going from embarrassingly parallel to pure sequential. Any given program can use Amdahl's law to express how scalable a problem or algorithm is. A couple qualifications for a embarrassingly parallel application would be:

  • No shared state, every function only depends on the parameters passed in
  • No access to physical devices (graphic cards, hard drives, etc)

There are other qualifications, but with just these two we can understand why games in particular are not as easy as you might think to take advantage of multiple cores. For one, the model of the world that will be rendered has to be shared as different functions calculate physics, movement, apply artificial intelligence etc. Second, each frame of this game model has to be rendered on screen with a graphics card.

To be fair, many game makers use game engines that are produced by third parties. It took a while, but these third party game engines are now much more parallel than they used to be.

There are bigger architectural challenges in dealing with effective concurrency

Concurrency can take many forms, from running tasks in the background to a full architectural support for concurrency. Some languages give you very powerful concurrency features such as ERLANG, but it requires you to think very differently about how you construct your application.

Not every program really needs the complexity of full multicore support. One such example is tax software, or any form driven application. When most of your time is spent waiting on the user to do something, the complexity of multithreaded applications are just not that useful.

Some applications lend themselves to a more embarrassingly parallel solution, such as web applications. In this case, the platform starts out embarrassingly parallel and it's up to you not have to impose thread contention.

The bottom line:

Not all applications are really hurt by not taking advantage of multiple threads (and thus, cores). For the ones that are hurt by that, sometimes the computations are not friendly to parallel processing or the overhead to coordinate it would make the application more fragile. Unfortunately, parallel processing is still not as easy as it should be to do well.