1 #include int pthread_create(pthread_t *tid, const pthread_attr_t *attr, void * (*start)(void *), void *args); P-threads: create tid: space used to return.

Slides:



Advertisements
Similar presentations
CS Lecture 4 Programming with Posix Threads and Java Threads George Mason University Fall 2009.
Advertisements

Threads Programming Thread creation Synchronization.
Multi-core Programming Programming with Posix Threads.
PTHREADS These notes are from LLNL Pthreads Tutorial
Computer Architecture II 1 Computer architecture II Programming: POSIX Threads OpenMP.
POSIX Threads Nezer J. Zaidenberg. References  Advanced programming for the UNIX environment (2nd edition. This material does not exist in first edition)
Fork Fork is used to create a child process. Most network servers under Unix are written this way Concurrent server: parent accepts the connection, forks.
8-1 JMH Associates © 2004, All rights reserved Windows Application Development Chapter 10 - Supplement Introduction to Pthreads for Application Portability.
Lecture 18 Threaded Programming CPE 401 / 601 Computer Network Systems slides are modified from Dave Hollinger.
Unix Synchronization * Mutexes * Semaphores - named - unnamed.
Threads© Dr. Ayman Abdel-Hamid, CS4254 Spring CS4254 Computer Network Architecture and Programming Dr. Ayman A. Abdel-Hamid Computer Science Department.
POSIX Threads HUJI Spring 2007.
Pthread II. Outline Join Mutex Variables Condition Variables.
Netprog Threads Programming1 Threads Programming Refs: Chapter 23.
Pthread (continue) General pthread program structure –Encapsulate parallel parts (can be almost the whole program) in functions. –Use function arguments.
Introduction to Pthreads. Pthreads Pthreads is a POSIX standard for describing a thread model, it specifies the API and the semantics of the calls. Model.
04/10/25Parallel and Distributed Programming1 Shared-memory Parallel Programming Taura Lab M1 Yuuki Horita.
Multi-threaded Programming with POSIX Threads CSE331 Operating Systems Design.
POSIX Threads Nezer J. Zaidenberg. References  Advanced programming for the UNIX environment (2nd edition chapter This material does not exist.
Threads and Thread Control Thread Concepts Pthread Creation and Termination Pthread synchronization Threads and Signals.
Copyright ©: University of Illinois CS 241 Staff1 Synchronization and Semaphores.
CS345 Operating Systems Threads Assignment 3. Process vs. Thread process: an address space with 1 or more threads executing within that address space,
What is a thread? process: an address space with 1 or more threads executing within that address space, and the required system resources for those threads.
Copyright ©: Nahrstedt, Angrave, Abdelzaher1 Semaphore and Mutex Operations.
Programming with POSIX* Threads Intel Software College.
ECE 297 Concurrent Servers Process, fork & threads ECE 297.
Pthreads: A shared memory programming model
Threads CSCE Thread Motivation Processes are expensive to create. Context switch between processes is expensive Communication between processes.
CSC Advanced Unix Programming, Fall, 2008 Monday, November 24 POSIX threads (pthreads)
S -1 Posix Threads. S -2 Thread Concepts Threads are "lightweight processes" –10 to 100 times faster than fork() Threads share: –process instructions,
Threads and Locking Ioctl operations. Threads Lightweight processes What’s wrong with processes? –fork() is expensive – 10 to 100 times slower –Inter.
Threads Chapter 26. Threads Light-weight processes Each process can have multiple threads of concurrent control. What’s wrong with processes? fork() is.
1 Pthread Programming CIS450 Winter 2003 Professor Jinhua Guo.
Thread API Xiaohua Lu Office : CS 3310 Tel. : Office hours: 11-12,3-5 T,TR.
POSIX Synchronization Introduction to Operating Systems: Discussion Module 5.
POSIX Threads HUJI Spring 2011.
IT 325 Operating systems Chapter6.  Threads can greatly simplify writing elegant and efficient programs.  However, there are problems when multiple.
Pthreads.
Lecture 15 Semaphore & Bugs. Concurrency Threads Locks Condition Variables Fixing atomicity violations and order violations.
2.3 interprocess communcation (IPC) (especially via shared memory & controlling access to it)
CS252: Systems Programming Ninghui Li Based on Slides by Prof. Gustavo Rodriguez-Rivera Topic 11: Thread-safe Data Structures, Semaphores.
Pthreads #include pthread_t tid ; //thread id. pthread_attr_t attr ; void *sleeping(void *); /* thread routine */ main() { int time = 2 ; pthread_create(&tid,
U NIVERSITY OF M ASSACHUSETTS A MHERST Department of Computer Science Software Systems Advanced Synchronization Emery Berger and Mark Corner University.
CS252: Systems Programming Ninghui Li Based on Slides by Prof. Gustavo Rodriguez-Rivera Topic 12: Thread-safe Data Structures, Semaphores.
Chapter 6 P-Threads. Names The naming convention for a method/function/operation is: – pthread_thing_operation(..) – Where thing is the object used (such.
CS252: Systems Programming Ninghui Li Based on Slides by Prof. Gustavo Rodriguez-Rivera Topic 13: Condition Variable, Read/Write Lock, and Deadlock.
PThread Synchronization. Thread Mechanisms Birrell identifies four mechanisms commonly used in threading systems –Thread creation –Mutual exclusion (mutex)
Thread S04, Recitation, Section A Thread Memory Model Thread Interfaces (System Calls) Thread Safety (Pitfalls of Using Thread) Racing Semaphore.
Thread Basic Thread operations include thread creation, termination, synchronization, data management Threads in the same process share:  Process address.
Working with Pthreads. Operations on Threads int pthread_create (pthread_t *thread, const pthread_attr_t *attr, void * (*routine)(void*), void* arg) Creates.
pThread synchronization
回到第一頁 What are threads n Threads are often called "lightweight processes” n In the UNIX environment a thread: u Exists within a process and uses the process.
Case Study: Pthread Synchronization Dr. Yingwu Zhu.
Synchronization and Semaphores
CS 537 – Introduction to Operating Systems
סמפורים.
Threads Threads.
Netprog: Threads Programming
Copyright ©: Nahrstedt, Angrave, Abdelzaher
Pthreads void *sleeping(void *); /* thread routine */
PTHREADS These notes are from LLNL Pthreads Tutorial
Lecture 14: Pthreads Mutex and Condition Variables
BOOM! count is [ ], should be
Pthread Prof. Ikjun Yeom TA – Mugyo
Synchronization Primitives – Semaphore and Mutex
Lecture 14: Pthreads Mutex and Condition Variables
Synchronization.
Lecture 20: Synchronization
Lecture 12 CV and Semaphores
POSIX Threads(pthreads)
Presentation transcript:

1 #include int pthread_create(pthread_t *tid, const pthread_attr_t *attr, void * (*start)(void *), void *args); P-threads: create tid: space used to return the thread id attr: thread attributes -- NULL start: a pointer to a function that takes a single argument of type void * and returns a value of type void * args: a value to be passed as the argument to start Return value: 0 means OK, non-zero indicates an error

2 #include int pthread_join(pthread_t tid, void **status); int pthread_detach(pthread_t tid); P-threads: join&detach pthread_join: wait for thread tid to finish status: will be set to point to the space where the return value from the start function will be stored pthread_detach: thread cannot be joined. System will reclaim resources on thread_exit.

3 void *printme(void *){ printf("Hello world\n"); return NULL;} // could use pthread_exit(NULL) here main(){ pthread_t tid; void *status; if (pthread_create(&tid, NULL, printme, NULL) != 0) { perror("pthread_create”); exit(1); } if (pthread_join(tid, &status) != 0) { perror("pthread_join"); exit(1); } P-threads: example Warning: tid is shared! What happens if you put a call to create in a loop?

4 void *printme(void *arg) { int me = *((int *)arg); printf(“Hello from %d\n”, me); return NULL; } int main(){ int i, j, vals[4]; pthread_t tids[4]; void *retval; for (i = 0; i < 4; i++) { vals[i] = i; pthread_create(tids+i, NULL, printme, (void *) ( vals+i)); } for (j = 0; j < 4; j++) { printf("Trying to join with tid %d\n", i); pthread_join(tids[j], (void **) &retval); printf("Joined with tid %d\n", j); } P-threads: multiple threads

5 int main(){ int i, vals[4]; pthread_t tids[4]; for (i = 0; i < 4; i++) { vals[i] = i; pthread_create(tids+i, NULL, printme, (void *) (vals+i)); } return 0; } P-threads: exit Returning from a start function is equivalent to calling thread_exit Returning from main is equivalent to calling exit!

6 struct harg { int newfd; struct sockaddr_in; }; void *handler(void *arg) { struct harg *harg = (struct harg *)arg; pthread_detach(pthread_self());... } int main() { pthread_t tid1; int sockfd = openServer(atoi(argv[1])); int addrsize = sizeof(struct sockaddr_in); while (1) { struct harg *arg = (struct harg *)malloc(sizeof(*arg)); arg->newfd = accept(sockfd, (struct sockaddr *) &arg->addr, &addrsize); pthread_t tid; pthread_create(&tid, NULL, handler, (void *)arg); } Pthreads: Servicing multiple clients

7 #define LEN 100 #define NUM_PARTS 4 #define PART_LEN LEN/NUM_PARTS void *sumPart(void *args) { int start = *((int *) args); int end = start + PART_LEN; int i; int mySum = 0; for (i = start; i <end; i++) { mySum += x[i]; } sum = sum + mySum; thread_exit(0); } P-threads: race condition example

8 int main() { int i, *arg, rv; pthread_t tids[NUM_PARTS]; initialize(x, 1); // initialize x[0..SIZE-1] to 1 for (i = 0; i < NUM_PARTS; i++) { arg = (int *) malloc(sizeof(*arg)); *arg = i*PART_LEN; pthread_create(tids+i, NULL, sumPart, (void *)arg); } for (i = 0; i < NUM_PARTS; i++) { pthread_join(tids[i], (void **) &rv); } printf(“sum: %d\n”, sum); } P-threads: race condition example

9 pthread_mutex_t mutex_lock; pthread_mutex_init(pthread_mutex_t *mutex, pthread_mutexattr_t attr); pthread_mutex_lock(pthread_mutex_t *mutex); pthread_mutex_trylock(pthread_mutex_t *mutex); pthread_mutex_unlock(pthread_mutex_t *mutex); P-threads:mutex locks pthread_mutex_init: initialize a mutex, use NULL for attrs. pthread_mutex_lock: attempt to lock a mutex, will block if the mutex is currently locked. pthread_ mutex_trylock: attempt to lock a mutex, returns with a busy error code if the lock is currently locked. pthread_mutex_unlock: release a mutex. returns an error (non-zero value) if the mutex is not held by the calling thread

10 pthread_mutex_t sumLock; int main() { int i, *arg; pthread_t tids[4]; void *retval; initialize(x); pthread_mutex_init(&sumLock, NULL); for (i = 0; i < NUM_PARTS; i++) { arg = (int *) malloc(sizeof(*arg)); *arg = i*PART_LEN; pthread_create(tids+i, NULL, sumPart, (void *)arg); } for (i = 0; i < NUM_PARTS; i++) { pthread_join(tids[i], (void **)&retval); } pthread_mutex_destroy(&sumLock); printf(“sum: %d\n”, sum); } P-threads: race condition example

11 void *sumPart(void *args) { int start = *((int) args); int end = start + PART_LEN; int i; int mySum = 0; for (i = start; i <end; i++) { mySum += x[i]; } mutex_lock(&sumLock); sum = sum + mySum; mutex_unlock(&sumLock); thread_exit(0); } P-threads: race condition example Is there another way to solve this (particular) problem?

12 void *sumPart(void *args) { int start = ((int) args); int end = start + PART_LEN; int i; int mySum = 0; for (i = start; i <end; i++) { mySum += x[i]; } // reuse arg space for return value *((int *) args) = mySum; thread_exit((void *)args); } P-threads: race condition example

13 int main() { int i,*arg; pthread_t tids[NUM_PARTS]; initialize(x, 1); // initialize x[0..SIZE-1] to 1 for (i = 0; i < NUM_PARTS; i++) { arg = (int *)malloc(sizeof(*arg)); *arg = i*PART_LEN; pthread_create(tids+i, NULL, sumPart, (void*)arg); } for (i = 0; i < NUM_PARTS; i++) { int *localSum; pthread_join(tids[i], (void **) &localSum); sum = sum + localSum; } printf(“sum: %d\n”, sum); } P-threads: race condition example

14 void *addOne(void *arg) { int *x = (int *) arg; *x = *x + 1; return NULL; } int main() { pthread_t tid1, tid2; int y = 7; void *rv; pthread_create(&tid1, NULL, addOne, (void *) &y); pthread_create(&tid2, NULL, addOne, (void *) &y); pthread_join(&tid1, (void **) &rv); pthread_join(&tid2, (void **) &rv); printf(“y: %d\n”, y); } Pthreads: stack sharing example

15 void *useStatic(void *arg) { static int z = 0; z = z + 1; return (void *) &z; } int main() { pthread_t tid1, tid2; int *prv1, *prv2; pthread_create(&tid1, NULL, useStatic, NULL); pthread_create(&tid2, NULL, useStatic, NULL); pthread_join(tid1, (void **) &prv1); pthread_join(tid2, (void **) &prv2); printf(“rv1: %d\trv2: %d\n”, prv1, prv2); } Pthreads: functions with state Real world example: gethostbyname

16 pthread_mutex_t zlock; void *useStatic(void *arg) { static int z = 0; z = z + 1; return (void *) &z; } void *safeUseStatic(void *arg) { int *rv = (int *) malloc(sizeof(int)); int *tmp; pthread_mutex_lock(&zlock); tmp = useStatic(arg); *rv = *tmp; pthread_mutex_unlock(&zlock); return rv; } int main() { pthread_mutex_init(&zlock, NULL); // create threads to call safeUseStatic... } Pthreads: lock and copy

17 int z; void initZ(int x) { z = x; } void *useGlobal(void *arg) { z = z + 1; return (void *)z; } int main() { pthread_t tid1, tid2; int rv1, rv2; initZ(7); /* create threads... */ pthread_join(tid1, (void **) &rv1); pthread_join(tid2, (void **) &rv1); printf(“rv1: %d\trv2: %d\n”, rv1, rv2); } Pthreads: functions with state Real world example: rand

18 void *useState(void *arg) { int z = *(int *)arg; z = z + 1; *arg = z; return (void *)z; } int main() { pthread_t tid1, tid2; int rv1, rv2; int z1 = 7, z2 = 7; // initialize the state pthread_create(&tid1, NULL, useGlobal, (void *)&z1); pthread_create(&tid1, NULL, useGlobal, (void *)&z2); pthread_join(&tid1, (void *) &rv1); pthread_join(&tid2, (void *) &rv2); printf(“rv1: %d\trv2: %d\n”, rv1, rv2); } Pthreads: state arguments Real world example: rand_r

19 PThreads: Deadlock pthread_mutex_t A, B; void *lockAB(void *arg) { pthread_mutex_lock(&A); pthread_mutex_lock(&B);....do work... pthread_mutex_unlock(&B); pthread_mutex_unlock(&A); } void *lockBA(void *arg) { pthread_mutex_lock(&B); pthread_mutex_lock(&A);....do other work... pthread_mutex_unlock(&A); pthread_mutex_unlock(&B); }

20 Pthreads: Deadlock continued int main() { pthread_t tid1, tid; pthread_mutex_init(&A, NULL); pthread_mutex_init(&B, NULL); pthread_create(&tid1, NULL, lockAB, NULL); pthread_create(&tid2, NULL, lockBA, NULL); pthread_exit(0); } Solution: (1) define an ordering on the locks (2) acquire locks in order (3) release locks in reverse order

21 PThreads: Semaphores #include int sem_init(sem_t *sem, int pshared, unsigned int value); int sem_wait(sem_t *sem); int sem_post(sem_t *sem); int sem_destroy(sem_t *sem); sem_init: initialize a semaphore. pshared should be zero. value is the initial value for the semaphore sem_wait: wait for the value to be > 0, then decrement and then continue sem_post: increment semaphore (will wake up a waiting thread) sem_destroy: free the semaphore

22 Pthreads: Semaphore example struct job { struct job *next; // other fields related to the job } *queue; pthread_mutex_t q_lock; sem_t q_cnt; void initJQ() { pthread_mutex_init(&q_lock, NULL); sem_init(&q_cnt, 0, 0); queue = NULL; }

23 Pthreads: Semaphore example void process_jobs(void *arg) { while (1) { sem_wait(&q_cnt); pthread_mutex_lock(&q_lock);... take job off queue... pthread_mutex_unlock(&q_lock);... process job... }

24 Pthreads: Semaphore example void enqueue_job() { pthread_mutex_lock(&queue);... add job to the queue... sem_post(&q_cnt); pthread_mutex_unlock(&queue); }

25 int myTurn = 0; int numThreads = 4; pthread_mutex_t lock; void *myTurnFn(void *args) { int myID = *((int *)args); while (1) { pthread_mutex_lock(lock); /* get lock */ while((myTurn % numThreads) != myID) { pthread_mutex_unlock(lock); /* give it up! */ pthread_mutex_lock(t->lock); /* get it again */ } /* do some work */ pthread_mutex_unlock(lock); /* give it up! */ } Condition variables: my turn example -- dumb

26 int pthread_cond_init(pthread_cond_t *cond, pthread_cond_attr_t *cond_attr); int pthread_cond_wait(pthread_cond_t *cond, pthread_mutex_t *mutex); int pthread_cond_signal(pthread_cond_t *cond); int pthread_cond_broadcast(pthread_cond_t *cond); Pthreads:condition variables A thread t: (1) grabs a lock (2a) tests to see if a condition holds, if so t proceeds (3a) signals when done. (2b) if not, goes to sleep, implicitly releasing the lock, (3b) re-awakes holding the lock when signaled by another thread.

27 int myTurn = 0; int numThreads = 4; pthread_mutex_t lock; // initialize to unlocked pthread_cond_t cv; // initialize to unavailable void *myTurnFn(void *args) { int myID = *((int *)args); while (1) { pthread_mutex_lock(&lock); while((myTurn % numThreads) != myID) { pthread_cond_wait(&cv, &lock); } /* do some work */ pthread_cond_broadcast(&cv); pthread_mutex_unlock(&lock); /*order matters! */ } Pthreads:my turn w/ CV

28 typedef struct { pthread_mutex_t *lock; pthread_cond_t *cv; int *ndone; int nthreads; int id; } TStruct; void *barrier(void *arg) { TStruct *ts = (TStruct *)arg; int i; printf("Thread %d -- waiting for barrier\n", ts->id); pthread_mutex_lock(ts->lock); *ts->ndone = *ts->ndone + 1; if (*ts->ndone nthreads) pthread_cond_wait(ts->cv, ts->lock); else for (i = 1; i < NTHREADS; i++) pthread_cond_signal(ts->cv); pthread_mutex_unlock(ts->lock); printf("Thread %d -- after barrier\n", ts->id); }