The Dawning of the Age of Multithreading

Dr. Dobb's Journal September 1998

By Jeff Cromwell

Jeff is a programmer for Levi, Ray, and Shoup, and can be contacted at jcromwell@primary.net.

Multithreading Programming
Techniques in Win32: The
Complete Guide to Threads

Jim Beveridge and R. Wiener
Addison-Wesley, 1997
368 pp., $39.95
ISBN 0-201-44234-5

Object-Oriented
Multithreading Using C++

Cameron and Tracy Hughes
John Wiley & Sons, 1997
512 pp., $49.99
ISBN 0-471-18012-2

Multithreading
Programming Techniques

Shashi Prasad
McGraw-Hill, 1997
400 pp., $49.95
ISBN 0-0791-2250-7

It can finally be said that we are at the dawn of multithreaded client/server development. We live at a time in which it is necessary to build high-performance servers, develop sophisticated extensions for Internet/intranet servers, utilize the power of multiprocessor systems, construct high-performance OLE and COM objects, and enhance overall application responsiveness. In the coming years, there will be the need for high-performance video servers and complex real-time animation and simulation systems -- many under the auspices of virtual reality. As with any dawn, some of us have overslept.

The definition of a multithreading program, according to Beveridge and Wiener's Multithreading Programming Techniques in Win32, is one that allows tasks to be divided into components, where each task can operate independently from others. Although most programmers get chills at the mention of this topic, we must remember that even Visual Basic can create multithreaded server applications. The ability to build multithreaded applications is one of the most important skills you can add to your repertoire. Why? Simple economics. Threads are cheaper than processes in terms of initialization, termination, and efficiency. For example, consider a web server that can receive thousands of hits per day. It would be far more expensive to initialize and terminate each request as a separate process. What is needed is something more lightweight -- threads. Although UNIX, Windows NT, and web servers like Internet Information Server have inherent thread processes, an increasing number of client/server applications need to take advantage of the multithreading technology. To implement such a technology, developers need a reliable source of information.

Multithreading in Win32

Most of my time nowadays is spent developing Windows-based client/server applications in a variety of languages. Recently, I had to develop a multithreaded server in C++, and one of my reference sources was Multithreading Programming Techniques in Win32: The Complete Guide to Threads, by Jim Beveridge and R. Wiener. I selected this book because it received laudatory reviews on the Internet and because the authors wrote the book around a FAQ-style layout. Beveridge and Wiener ask and answer 56 questions, on topics from "How does a context switch work?" to "Why should I be careful of starting threads in DllMain()?" Each of these questions are answered and developed in three basic sections: "Threads in Action," "Multithreading Tools and Tricks," and "Multithreading in Real-World Applications." Although the last section on real-world examples is a bit terse, the first two are very helpful and easy to digest. For pedagogical purposes, the inclusion of a real-world web-server application would have been helpful. In any event, I was able to proceed through the chapters quickly and adopt some of the practices in my work.

In addition, Beveridge and Wiener do an excellent job of communicating multithreading fundamentals to a diverse audience. For example, they elaborate on several useful tips, including:

Another basic tip that all multithreading programmers must know is that you do not make each window of a MDI application its own thread. Beveridge and Wiener give a detailed discussion on why you should not do this. An accompanying CD-ROM includes all the code and sample applications in the book.

Object-Oriented Multithreading

One of the most striking features of Object-Oriented Multithreading Using C++, by Cameron and Tracy Hughes, is the heavy use of objects -- not only with respect to multithreading, but also by way of diagrams, tables, and figures. The authors should be commended for their ability and diligence in mapping code to diagrams. This lets you take larger steps up the learning curve. Besides their organizational ability, the authors provide a practical guidance on topics such as:

The strength of Object-Oriented Multithreading Using C++ is in its examination of the use of multithreading techniques and principles for objects and class libraries. The book assumes little experience with multithreading, but requires familiarity with C++ and object-oriented programming. The focal point on the object-oriented nature of multithreading is based on the chapters "Threading Object-Oriented Architectures," "Class Hierarchies and C++ Components for Threading," and "Class Behavior and Threading."

The authors provide an excellent treatment of threading object-oriented architectures. For example, they have identified three essential candidates for multithreading: client/server, event-driver programming (GUI), and blackboards. The authors then proceed to give several design examples for each type of architectures, which are extremely useful to novices and seasoned veterans of architectural design. The chapter on class hierarchies and C++ components is excellent and provides helpful examples that take advantage of templates that demonstrate an anatomy of a multithreaded class. Their final chapter on class behavior demonstrates the need to understand how domain, interface, utility, and other support objects will behave in a multithreaded environment.

Overall, Object-Oriented Multithreading Using C++ requires a considerable investment of time but promises a high rate of return. The authors include a disk with all the source code from the book along with a variety of multithreaded components ready to build into your own applications or class library.

Other Operating Systems

While most of my work has been in the Windows environment, no review on multithreading would be complete without some discussion on other operating systems. A multithreaded programmer must have the ability to move from one platform to another with ease. For an examination of how to implement threads on a variety of different platforms, Multithreading Programming Techniques, by Shashi Prasad, is an excellent resource.

This book covers five different thread implementations on operating systems such as UNIX, Mach, Windows NT, and OS/2. The thread implementations used are of the POSIX and Win32-OS/2 variety. Multithreading Programming Techniques is organized in such a way that if you are interested only in the POSIX- and UNIX-based threads, you only need to read those chapters.

Prasad provides a helpful introduction to multithreading and discusses several pitfalls to thread programming, including:

Prasad addresses each one of these pitfalls with respect to each implementation. All code in the book is C, since the operating system Prasad developed has a C-based API for thread programming.

One of the first lessons I learned in this book is that UNIX supports threads. Operating systems such as AIX, Solaris, Digital UNIX, and SVR4/MP now offer a multithreaded kernel. At a more abstract level, there are small differences between platforms. For effective thread implementation, for example, you must understand thread-synchronization issues such as mutexes and semaphores, along with data handling for threads and overall thread management. While Prasad provides detailed treatment of these topics, he leaves it up to you to compare and contrast the OSs to effectively implement the architectures in real-world examples. The book is accompanied by a disk that provides the source code in C to many of the examples. In addition, Prasad has also included source code for Mthread -- a portable, thread abstraction layer for the different thread implementations developed in the book.

Wrapping it Up

Multithreading is a difficult subject and you must spend considerable time in designing, coding, and running examples. If you are looking for code to use in your applications, you will not find it in Prasad's book. However, you will find three excellent books that will teach you the fundamentals of thread-based programming. If this is not an option (Steve McConnell says that the average programmer reads less than one book a year), I would start off with Beveridge and Wiener's book for your transition into thread programming. The Prasad book is ideal for those who are not in a development phase and do not have to port a threaded application to another operating system. The Hughes book is excellent for those who are well versed in the use of object-oriented technology and like to be challenged in the construction and implementation of threadsafe objects.

Although all three books are helpful for developing a grasp of the concepts, it is always helpful to read the code from real-world multithreaded applications. I was able to track down several examples of multithreaded servers that expounded on several of the techniques described in the books examined here. In addition to this intellectual investment, developing multithreaded applications requires a deep understanding of system processes. If you aspire to be ready for this new dawn, you can prepare by tinkering under the hood of Windows and UNIX-based platforms.

DDJ


Copyright © 1998, Dr. Dobb's Journal