ECE231 Project 3

Intra-Process Communication Benchmarking

Due 2/21/02

In this project, you will build two programs that communicate among their threads in different ways. Both programs will create a specified number of producer and consumer thread pairs. Each producer will send a specified number of message of a specified size to the consumer. The consumer thread will accept these messages and print them (at first, anyway).

The first program will use POSIX semaphores to synchronize the producer and consumer over a shared buffer (each pair will share a buffer, but only a single producer will write to each buffer and only a single consumer will read from it). The Sun Threads document has a more complex version of this program, so you should be able to derive yours easily.

The other program will use POSIX message queues to send messages from each producer to its matching consumer. Each pair will share message queue. A nice introduction to POSIX Message Queues can be found here. Use the man command on the Suns to get more detail on each of the calls. Remember that for both named semaphores and named message queues, the name must start with a "/" character. POSIX Message Queues are only available on the Suns, not Linux or FreeBSD. If you are a glutton for punishment, you may use System V message queues at your own peril.

Both of your programs should take the following command line parameters in the specified order:

I suggest you put ASCII text in your buffer and modify it slightly for each message. For example, I used an sprintf as follows:

sprintf(buffer, "Message %d from Producer %d", i, pairNumber);

Though you only modify a small portion of your buffer each time, make sure you send/copy the entire number of bytes specified in the message size. Also remember that you need private buffers as well as the shared buffer in the semaphore program. You cannot access the shared buffer at random, but need to work/print from a private buffer and copy that buffer to/from the shared one as appropriate. Remember that your programs must be safe and must not corrupt the buffers.

While you are making sure your program works, have the consumer print the string at the start of each message it receives. Once you are certain that your program works and no messages are being lost or corrupted, comment out the per-message print statements (to reduce overhead) and recompile your programs with the -O flag (to turn on compiler optimization).

Then, benchmark each program to check how long it takes to perform its work. Benchmark for 1 producer/consumer pair every combination of message sizes (100, 1000, 10000, 100000, 1000000 bytes) and message counts (100, 1000, 10000, 100000) except for the largest case (100000 messages of 1000000 bytes, which would take too long). An example spreadsheet of these measurements is below (your numbers will be different!).

You may use the time command to determine the total user and system CPU time used or you can use system calls to do so. Do not measure wall clock time, as it will vary according to the load on the machine. Once you know the time, computer the throughput for each case. If you can use Excel or a similar program, try to graph the results as a surface plot, as shown below. If you cannot do that, draw a plot for each message count, where the x axis is the message size (in log scale) and the y axis is the throughput. Make sure your graphs are appropriately labeled.

Then, for the following two combinations of message size and message count, measure the time and calculate the throughput for each producer/consumer thread pair count from 1 to 10.

Based on all these measurements, answer (and explain why) each of the following questions:

  1. Which approach has the highest overall throughput?
  2. Do the highest throughput values for each approach correspond to the same message size/count combination?
  3. Which approach is more efficient in terms of the operations to send and receive (as opposed to the transfer itself)?
  4. Which approach transfers more messages per unit time?
  5. What happens to the aggregate throughput as we increase the number of thread pairs?

Turn in the following items:

  1. Email the source code for your two programs to prasad@dream.eng.uci.edu with the subject: ECE231_Project3 student_id
  2. Also email a sample run (typescript) of each of your programs with the print statements working for the case of 3 pairs, 5 messages of 100 bytes each.
  3. A printout of your throughput graphs for both communication mechanisms
  4. A printout of the throughput values for the varied producer/consumer pairs counts, as specified above.
  5. Answers to the questions (1-5) listed above.