source: CIVL/examples/pthread/condvar.cvl@ 50f834b

1.23 2.0 main test-branch
Last change on this file since 50f834b was 609ffd1, checked in by John Edenhofner <johneden@…>, 12 years ago

Added support for pthread join/exit interaction, new translations, updated documentation and other features

git-svn-id: svn://vsl.cis.udel.edu/civl/trunk@1080 fb995dde-84ed-4084-dfe6-e5aef3e2452c

  • Property mode set to 100644
File size: 4.2 KB
RevLine 
[8090425]1/*****************************************************************************
2* SOURCE: This is a translation of a Pthread program from the Lawrence Livermore
3* Computing Center POSIX Threads Programming Exercise at:
4* https://computing.llnl.gov/tutorials/pthreads/exercise.html
5* SUPERSOURCE: Adapted from example code in "Pthreads Programming", B. Nichols
6* et al. O'Reilly and Associates.
[bf81b8c]7* FILE: condvar.cvl
[38374b7]8* DESCRIPTION:
9* Example code for using Pthreads condition variables. The main thread
10* creates three threads. Two of those threads increment a "count" variable,
11* while the third thread watches the value of "count". When "count"
12* reaches a predefined limit, the waiting thread is signaled by one of the
13* incrementing threads. The waiting thread "awakens" and then modifies
14* count. The program continues until the incrementing threads reach
15* TCOUNT. The main program prints the final value of count.
[8090425]16* Command line execution:
17* civl verify -inputNUM_THREADS=3 -inputTCOUNT=10 -inputCOUNT_LIMIT=12 condvar.cvl
[38374b7]18******************************************************************************/
19#include "pthread.cvh"
20#include <civlc.h>
21#include <stdio.h>
22#include <stdlib.h>
23
[8090425]24$input int NUM_THREADS;
25$input int TCOUNT;
26$input int COUNT_LIMIT;
[38374b7]27
[bf81b8c]28int count = 0;
[38374b7]29pthread_mutex_t count_mutex;
30pthread_cond_t count_threshold_cv;
31
32void *inc_count(void *t)
33{
34 int i;
[6fe2cd9]35 long my_id = (long)*t; // Dereference rather than direct conv
[38374b7]36
37 for (i=0; i < TCOUNT; i++) {
38 pthread_mutex_lock(&count_mutex);
39 count++;
40
41 /*
42 Check the value of count and signal waiting thread when condition is
43 reached. Note that this occurs while mutex is locked.
44 */
45 if (count == COUNT_LIMIT) {
[6fe2cd9]46 printf("inc_count(): thread %d, count = %d Threshold reached. ", my_id, count);
[38374b7]47 pthread_cond_signal(&count_threshold_cv);
48 printf("Just sent signal.\n");
[609ffd1]49 }
[6fe2cd9]50 printf("inc_count(): thread %d, count = %d, unlocking mutex\n", my_id, count);
[38374b7]51 pthread_mutex_unlock(&count_mutex);
52
53 /* Do some work so threads can alternate on mutex lock */
[2beb8ff]54 //sleep(1);
[609ffd1]55 }
[6fe2cd9]56 pthread_exit(NULL, false, NULL, 0); //Different parameters
[38374b7]57}
58
59void *watch_count(void *t)
60{
[6fe2cd9]61 long my_id = (long)*t; // Dereference rather than direct conv
[38374b7]62
[bf81b8c]63 printf("Starting watch_count(): thread %d\n", my_id);
[38374b7]64
65 /*
66 Lock mutex and wait for signal. Note that the pthread_cond_wait routine
67 will automatically and atomically unlock mutex while it waits.
68 Also, note that if COUNT_LIMIT is reached before this routine is run by
69 the waiting thread, the loop will be skipped to prevent pthread_cond_wait
70 from never returning.
71 */
72 pthread_mutex_lock(&count_mutex);
73 while (count < COUNT_LIMIT) {
[bf81b8c]74 printf("watch_count(): thread %d Count= %d. Going into wait...\n", my_id,count);
[38374b7]75 pthread_cond_wait(&count_threshold_cv, &count_mutex);
[bf81b8c]76 printf("watch_count(): thread %d Condition signal received. Count= %d\n", my_id,count);
77 printf("watch_count(): thread %d Updating the value of count...\n", my_id,count);
[38374b7]78 count += 125;
[bf81b8c]79 printf("watch_count(): thread %d count now = %d.\n", my_id, count);
[38374b7]80 }
[bf81b8c]81 printf("watch_count(): thread %d Unlocking mutex.\n", my_id);
[38374b7]82 pthread_mutex_unlock(&count_mutex);
[6fe2cd9]83 pthread_exit(NULL, false, NULL, 0); //Different parameters
[38374b7]84}
85
[8090425]86int main(void)
[38374b7]87{
88 int i, rc;
89 long t1=1, t2=2, t3=3;
90 pthread_t threads[3];
91 pthread_attr_t attr;
92
93 /* Initialize mutex and condition variable objects */
94 pthread_mutex_init(&count_mutex, NULL);
[609ffd1]95 pthread_cond_init(&count_threshold_cv, NULL);
[38374b7]96
97 /* For portability, explicitly create threads in a joinable state */
98 pthread_attr_init(&attr);
99 pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_JOINABLE);
[bf81b8c]100 pthread_create(&threads[0], &attr, watch_count, (void *)&t1);
101 pthread_create(&threads[1], &attr, inc_count, (void *)&t2);
102 pthread_create(&threads[2], &attr, inc_count, (void *)&t3);
[38374b7]103
104 /* Wait for all threads to complete */
105 for (i = 0; i < NUM_THREADS; i++) {
106 pthread_join(threads[i], NULL);
107 }
[6fe2cd9]108 printf ("Main(): Waited and joined with %d threads. Final value of count = %d. Done.\n", NUM_THREADS, count);
[38374b7]109
110 /* Clean up and exit */
111 pthread_attr_destroy(&attr);
112 pthread_mutex_destroy(&count_mutex);
113 pthread_cond_destroy(&count_threshold_cv);
[6fe2cd9]114 pthread_exit(NULL, true, NULL, 0); //Different parameters
[bf81b8c]115 return 0;
[38374b7]116}
Note: See TracBrowser for help on using the repository browser.