CISC2200 Threads Spring 2015 Process We learn the concept of process A program in execution A process owns some resources A process executes a program => execution state, PC, … We learn that bash creates processes to run user’s command We practice with process creation in assignment 2 Create a child process Parent process OS: Protection Protection: mechanism for controlling access of processes or users to resources (Files, memory segment, CPU and other) Systems generally first distinguish among users to determine who can do what 3 User identities (user IDs): a unique name and number User ID then associated with all files, processes of that user to determine access control Group identifier (group ID) allows set of users to be defined, then also associated with each process, file Hardware Support for protection Dual-mode allows OS to protect itself and other system components A mode bit provided by processor hardware Kernel mode for running kernel code User mode for running user code Privileged instructions only executable in kernel mode System call: changes mode to kernel, return from call resets it to user mode “ps” command: reports user time, system time 4 Single-threaded Processes 5 Multithreading Separate two characteristics of process Unit of dispatching => thread, lightweight process Unit of resource ownership => process, task Multi-threading: ability of OS to support multiple, concurrent paths of execution with a single process 6 Multithreading (cont’d) Process: unit of resource allocation/protection An address space for its image Protected access to resources Inter-process communication Thread: A thread execution state Saved context, Execution stack Access to memory/resource of its process, shared with other threads in the process 7 Why Multithreading ? Many applications require a set of related units of execution Web Server example: listening on port for client connection request serving a client: read client request, serve the file Can create multiple processes for them Mainly performance consideration. Threads are 8 Faster to create a new thread, terminate a thread Faster to switch between two threads within a process More efficient communication between threads (without invoking kernel) Thread Usage (1) Figure 2-7. A word processor with three threads. Tanenbaum, Modern Operating Systems 3 e, (c) 2008 Prentice-Hall, Inc. All rights reserved. 0-13-6006639 Thread Usage (2) Figure 2-8. A multithreaded Web server. Tanenbaum, Modern Operating Systems 3 e, (c) 2008 Prentice-Hall, Inc. All rights reserved. 0-13-6006639 Thread Usage (3) Figure 2-9. A rough outline of the code for Fig. 2-8. (a) Dispatcher thread. (b) Worker thread. Tanenbaum, Modern Operating Systems 3 e, (c) 2008 Prentice-Hall, Inc. All rights reserved. 0-13-6006639 Thread Usage (4) Figure 2-10. Three ways to construct a server. Tanenbaum, Modern Operating Systems 3 e, (c) 2008 Prentice-Hall, Inc. All rights reserved. 0-13-6006639 Benefits of Threads Responsiveness Resource Sharing Economy Scalability 10 Increase parallelism, allow application to take advantage of multiprocessor architecture Concurrent Execution Parallel Execution (Multicore System) 11 POSIX Threads (1) Figure 2-14. Some of the Pthreads function calls. Tanenbaum, Modern Operating Systems 3 e, (c) 2008 Prentice-Hall, Inc. All rights reserved. 0-13-6006639 Blocking I/O vs non-blocking I/O What we usually do to read/write from I/O is blocking I/O: read (src_fd, &buf, 1) cin >> op1 >> opcode >> op2; The calling process/thread blocks (enters into BLOCKED state) until reading operation completes…. Non-blocking I/O int flags = fcntl(fd, F_GETFL, 0); fcntl(fd, F_SETFL, flags | O_NONBLOCK); read (fd, …) will return failure if there is nothing to read Making blocking I/O after select, poll system call monitor multiple fds until one of them become ready — commonly used in server programs call read() on file descriptor that is ready to read (i.e., it won’t block the calling process)… 10 Blocking I/O int main() { char buf[100]; int ret; int count=0; ret = read (0,buf,100); if (ret>0){ write (1, "Read this:",9); write (1, buf, ret); } else write (2, “failed in read.”,15); } 17 0: file descriptor for standard input, by default, it’s linked to keyboard 1: file descriptor for standard output, by default, it’s linked to terminal 2: file descriptor for standard error, by default, it’s linked to terminal Same read(), write() system calls can be used to read/write from I/O device, files, sockets, … We usually use higher-level library calls, printf, scanf (in C), cin and cout (in C++) Non-blocking I/O int main() { char buf[100]; int ret; int count=0; get the current mode of file descriptor 0 (standard input), and set it to non-blocking int flags = fcntl (0, F_GETFL,0); fcntl (0, F_SETFL, flags | O_NONBLOCK); do { ret = read (0,buf,100); /* sleep (1); //put wait for 1 second before continue... count++; cout <<“Waited “ << count << “ seconds…\n”; */ } while (ret<=0); buf[ret]='\0'; cout <<"Input"<<buf<<"End of INput”<<endl; } 18 Solution: blocking I/O after select, poll select, pselect, synchronous I/O multiplexing int select(int nfds, fd_set *readfds, fd_set *writefds, fd_set *exceptfds, struct timeval *timeout); Timeout value fd_set: a set of file descriptors void FD_CLR(int fd, fd_set *set); int FD_ISSET(int fd, fd_set *set); void FD_SET(int fd, fd_set *set); void FD_ZERO(fd_set *set); allows a program to monitor multiple file descriptors Calling process waits (is blocked) until one or more of the file descriptors become "ready" for some class of I/O operation (e.g., input possible). A file descriptor is considered ready if it is possible to perform corresponding I/O operation (e.g., read(2)) without blocking. Timer expires Ex: in connect-four game or other game program, implement a limited time play (make a move within 10 seconds)… 19 User Threads vs Kernel Threads Support for threads: provided at user level or kernel level User thread: Thread management done by user-level threads library Kernel thread: threads supported and managed by the Kernel 12 Implementation of Threads: User-level Implemented by a user-level threads package Kernel only knows about processes Thread library runtime system schedule multiple threads within a process Pro: Lower overhead when switching between threads (no system call/trap involved) Con: blocking I/O made by one thread will block whole process Tanenbaum, Modern Operating Systems 3 e, (c) 2008 Prentice-Hall, Inc. All rights reserved. 0-13-6006639 Many-to-One, User-level threads Multiple user-level threads mapped to a single kernel thread/process; user-level thread library implements all threading functionalities Advantage: Thread switching requires no kernel mode (save time) Application specific scheduling Run on any OS Disadvantage: One thread blocking blocks all threads in process A multithread app. cannot take advantage of multiprocessor Examples: Solaris Green Threads. GNU Portable Threads 14 Thread library Implementation of Threads: Kernel Implemented by a kernel Kernel knows about threads, schedule threads Con: Overhead when switching between threads (system call/trap involved) Pro: blocking I/O made by one thread will NOT block whole process Question: Is Linux thread implemented in OS kernel, or by user-level threads library? package user-level kernel threads package Tanenbaum, Modern Operating Systems 3 e, (c) 2008 Prentice-Hall, Inc. All rights reserved. 0-13-6006639 One-to-One Each user-level thread maps to kernel thread Advantage? Disadvantage? Examples 15 Windows NT/XP/2000, Linux, Solaris 9 and later The Classical Thread Model (2) Figure 2-12. The first column lists some items shared by all threads in a process. The second one lists some items private to each thread. Tanenbaum, Modern Operating Systems 3 e, (c) 2008 Prentice-Hall, Inc. All rights reserved. 0-13-6006639 Hybrid Implementations Figure 2-17. Multiplexing user-level threads onto kernel-level threads. Tanenbaum, Modern Operating Systems 3 e, (c) 2008 Prentice-Hall, Inc. All rights reserved. 0-13-6006639 Many-to-Many Model User-level thread library: thread creation, scheduling, synchronization Multiple user level threads mapped to some (smaller of equal) number of kernel threads Programmer can adjust # of kernel threads Ex: 16 Solaris prior to version 9, Windows NT/2000 with the ThreadFiber package Thread library Thread Libraries Thread library provides programmer with API for creating and managing threads Two primary ways of implementation 18 User-level library: library entirely in user space Kernel-level library supported by the OS Pthreads A POSIX standard (IEEE 1003.1c) API for thread creation and synchronization API specifies behavior of the thread library, implementation is up to developer of the library May be provided either as user-level or kernel-level Common in UNIX operating systems (Solaris, Linux, Mac OS X) 19 #include <pthread.h> #include <stdio.h> int sum; /* this data is shared by the thread(s) */ void *runner(void *param); /* the thread */ int main(int argc, char *argv[]) { pthread_t tid; /* the thread identifier */ pthread_attr_t attr; /* set of attributes for the thread */ if (argc != 2) { fprintf(stderr,"usage: a.out <integer value>\n"); return -1; } if (atoi(argv[1]) < 0) { fprintf(stderr,"Argument %d must be non-negative\n",atoi(argv[1])); return -1; } pthread_attr_init(&attr); /* get the default attributes */ /* create the thread */ pthread_create(&tid,&attr,runner,argv[1]); pthread_join(tid,NULL); /* now wait for the thread to exit */ printf("sum = %d\n",sum); } /** * The thread will begin control in this function */ void *runner(void *param) { int i, upper = atoi(param); sum = 0; if (upper > 0) { for (i = 1; i <= upper; i++) sum += i; } pthread_exit(0); } 21 To compile: gcc –pthread main.c Java Threads Java threads are managed by the JVM Typically implemented using the threads model provided by underlying OS Java threads may be created by: 22 Extending Thread class Implementing the Runnable interface Threading Issues Complication due to shared resources: e.g., global variables, system info for the process … Semantics of fork() and exec() system calls Thread cancellation of target thread Asynchronous or deferred Signal handling Thread pools 23 Is swap thread-safe? int t; void swap(int *x, int *y) { t = *x; *x = *y; // hardware interrupt might invoke isr() here! *y = t; } Can swap function be called by multiple threads within a program? 34 Making Single-Threaded Code Multithreaded Figure 2-19. Conflicts between threads over the use of a global variable. Tanenbaum, Modern Operating Systems 3 e, (c) 2008 Prentice-Hall, Inc. All rights reserved. 0-13-6006639 Semantics of fork() and exec() Does fork() duplicate only the calling thread or all threads? Some Unix provides two version of fork(), one duplicate all threads and another duplicates only the thread making fork() calls exec() replace the entire process with the new program, including all threads 24 Thread Cancellation Terminating a thread (referred to as target thread) before it finishes Two general approaches: Asynchronous cancellation terminates target thread immediately Problematic if target thread is updating shared data, or has allocated some resource Deferred cancellation allows target thread to periodically check (at cancellation points) if it should be cancelled 25 Signal Handling Signals are used in UNIX systems to notify a process that a particular event has occurred • 1. 2. 3. Signal is generated by particular event: segmentation fault, division by error, ctrl-c, kill …. Signal is delivered to a process Signal is handled by the process A signal handler is used to process signals • • 26 Default signal handler, user-defined signal handler Signal Handling & multi-threading Deliver signal to all threads within the process, or just one particular thread ? Options: • • – – – – 27 Deliver signal to the thread to which the signal applies Deliver the signal to every thread in the process Deliver the signal to certain threads in the process Assign a specific thread to receive all signals for the process and process the signals Thread Pools Create a number of threads in a pool where they await work Advantages: 28 Usually slightly faster to service a request with an existing thread than create a new thread Allows the number of threads in the application(s) to be bound to the size of the pool Windows XP Threads Implements the one-to-one mapping, kernel-level Each thread contains A thread id Register set Separate user and kernel stacks Private data storage area The register set, stacks, and private storage area are known as the context of the threads The primary data structures of a thread include: 29 ETHREAD (executive thread block) KTHREAD (kernel thread block) TEB (thread environment block) Linux Threads Linux does not distinguish between processes and threads Linux refers to them as tasks rather than threads A flow of control within a program System call clone(): create a new task, with flags specify the level of sharing between parent and child task CLONE_FS: file system info is shared CLONE_VM: memory space is shared CLOSE_SIGHAND: signal handlers are shared CLONE_FILES: the set of open files is shared How to create a task with similar sharing of threads as described in this class ? How to create a task with similar sharing as process ? 30