Example : Mutex.C

Classes/Techniques Demonstrated :

Mutex.C

Mutex.c demonstrates a trivial example of delineating a section of code as a critical section through the use of the HPCxx_Mutex object. Unlike Java, the library cannot support synchronized methods or CC++ atomic members, but the simple Mutex object provides the basic capability using two functions, lock and unlock.

In this example, several threads are created. Each thread is given a pointer to a semaphore and a reference to an integer variable. Each thread sleeps for a few seconds and then attempts to obtain the lock for a critical section. When it is allowed to enter the critical section, the thread adds its ID to the integer variable and then releases the lock on the critical section. It then increments the semaphore and exits. Meanwhile, main, is blocked until every thread has incremented the semaphore. At that point, the cumulative total of the thread IDs is output and main waits for the threads to terminate before exiting.

#include <iostream.h>
#include <hpcxx_rts.h>

class MyThread : public HPCxx_Thread {
  HPCxx_CSem* sem;
  HPCxx_Mutex l;
  int& sharedVal;
  int myId;
  
public:
  MyThread(int id, HPCxx_CSem* _sem, int& sv):
    myId(id), sem(_sem), sharedVal(sv), HPCxx_Thread(){}

  void run() {

    sleep((unsigned)3);
    cout << "Thread " << myId << " waiting for my turn..." << endl << flush;

    l.lock(); 
    // begin critical section

    cout << "Thread " << myId << " has critical section!" << endl << flush;
    sharedVal += myId;

    // end critical section
    l.unlock();

    sem->incr();
    cout << "Thread " << myId << " added in my value (exiting)." 
         << endl << flush;
  } 
};


int main(int argc, char **argv)
{
  HPCxx_Group* g;
  hpcxx_init(argc, argv, g);

  int num_threads;
  cout << "enter number of threads: " ;  
  cin >> num_threads;

  HPCxx_CSem c(num_threads);
  MyThread* t[num_threads];
  int total = 0;

  //
  // Create and begin execution of threads
  //
  for(int i = 0; i < num_threads; i++) {
    t[i] = new MyThread(i, &c, total);
    t[i]->start();
  }

  // Block here until all num_threads have incremented semaphore
  c.wait();
  cout << " Total of thread IDs is : " << total << endl << flush;

  //
  // Wait for threads to finish
  //
  for(i = 0; i < num_threads; i++) {
    t[i]->join();
  }

  cout << "DONE" << endl << flush;
  return hpcxx_exit(g);
}

Benjamin Temko
Last modified: Thu Jun 25 11:09:16 EST 1998