CS 162 Operating Systems and Systems Programming Lecture

  • Slides: 57
Download presentation
CS 162 Operating Systems and Systems Programming Lecture 3 Concurrency and Thread Dispatching September

CS 162 Operating Systems and Systems Programming Lecture 3 Concurrency and Thread Dispatching September 11, 2013 Anthony D. Joseph and John Canny http: //inst. eecs. berkeley. edu/~cs 162

Goals for Today • • Review: Processes and Threads Thread Dispatching Cooperating Threads Concurrency

Goals for Today • • Review: Processes and Threads Thread Dispatching Cooperating Threads Concurrency examples Note: Some slides and/or pictures in the following are adapted from slides © 2005 Silberschatz, Galvin, and Gagne. Slides courtesy of Anthony D. Joseph, John Kubiatowicz, AJ Shankar, George Necula, Alex Aiken, Eric Brewer, Ras Bodik, Ion Stoica, Doug Tygar, and David Wagner. 9/11/13 Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 2

Why Processes & Threads? Goals: • Multiprogramming: Run multiple applications concurrently • Protection: Don’t

Why Processes & Threads? Goals: • Multiprogramming: Run multiple applications concurrently • Protection: Don’t want a bad application to crash system! Solution: Process: unit of execution and allocation • Virtual Machine abstraction: give process illusion it owns machine (i. e. , CPU, Memory, and IO device multiplexing) Challenge: • Process creation & switching expensive • Need concurrency within same app (e. g. , web server) Solution: Thread: Decouple allocation and execution • Run multiple threads within same process 9/11/13 Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 3

Putting it together: Process (Unix) Process A(int tmp) { if (tmp<2) Memory Stack B();

Putting it together: Process (Unix) Process A(int tmp) { if (tmp<2) Memory Stack B(); printf(tmp); } B() { Sequential stream of instructions C(); } Resources I/O State (e. g. , file, socket contexts) C() { A(2); } A(1); CPU state (PC, SP, registers. . ) Stored in OS … 9/11/13 Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 4

Putting it together: Processes Process 1 Process 2 Process N Mem. IO state CPU

Putting it together: Processes Process 1 Process 2 Process N Mem. IO state CPU state … CPU state CPU sched. CPU (1 core) 9/11/13 IO state OS 1 process at a time Anthony D. Joseph and John Canny CS 162 • Switch overhead: high – CPU state: low – Memory/IO state: high • Process creation: high • Protection – CPU: yes – Memory/IO: yes • Sharing overhead: high (involves at least a context switch) ©UCB Fall 2013 Lec 3. 5

Putting it together: Threads Process 1 Process N threads … CP U stat e

Putting it together: Threads Process 1 Process N threads … CP U stat e threads Mem. IO state … CP U stat e CPU sched. CPU (1 core) 9/11/13 – CPU: yes – Memory/IO: No OS 1 thread at a time Anthony D. Joseph and John Canny • Switch overhead: low (only CPU state) • Thread creation: low • Protection CS 162 • Sharing overhead: low (thread switch overhead low) ©UCB Fall 2013 Lec 3. 6

Putting it together: Multi-Cores Process 1 Process N threads … CP U stat e

Putting it together: Multi-Cores Process 1 Process N threads … CP U stat e Mem. IO state … … CP U stat e CPU sched. – CPU: yes – Memory/IO: No OS 4 threads at a time core 1 9/11/13 Core 2 Core 3 Core 4 Anthony D. Joseph and John Canny • Switch overhead: low (only CPU state) • Thread creation: low • Protection CS 162 • Sharing overhead: low (thread switch overhead low) CPU ©UCB Fall 2013 Lec 3. 7

Putting it together: Hyper-Threading Process 1 Process N threads … CP U stat e

Putting it together: Hyper-Threading Process 1 Process N threads … CP U stat e Mem. IO state … … CP U stat e hardware-threads (hyperthreading) CP U stat e CPU sched. • Switch overhead between hardwarethreads: very-low (done in hardware) • Contention for ALUs/FPUs may hurt performance OS 8 threads at a time CPU core 1 9/11/13 core 2 core 3 core 4 Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 8

Process Control Block • The current state of process held in a process control

Process Control Block • The current state of process held in a process control block (PCB): (for a single-threaded process) Process Control Block 9/11/13 Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 9

CPU Switch From Process to Process • This is also called a “context switch”

CPU Switch From Process to Process • This is also called a “context switch” • Code executed in kernel above is overhead 9/11/13 – Overhead sets minimum practical switching time – Less overhead with SMT/Hyperthreading, but… contention for resources instead Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 10

The Numbers Context switch in Linux: 3 -4 secs (Current Intel i 7 &

The Numbers Context switch in Linux: 3 -4 secs (Current Intel i 7 & E 5). Some surprises: • Thread switching only slightly faster than process switching (100 ns). • But switching across cores about 2 x more expensive than within-core switching. • Context switch time increases sharply with the size of the working set*, and can increase 100 x or more. * The working set is the subset of memory used by the process in a time window. Moral: Context switching depends mostly on cache limits and the process or thread’s hunger for memory. 9/11/13 Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 11

The Numbers • Many process are multi-threaded, so thread context switches may be either

The Numbers • Many process are multi-threaded, so thread context switches may be either within-process or acrossprocesses. The latter involve changes in memory and I/O tables and are more like single-threaded process switches described earlier. 9/11/13 Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 12

# of addr spaces: Classification One Many One MS/DOS, early Macintosh Traditional UNIX Many

# of addr spaces: Classification One Many One MS/DOS, early Macintosh Traditional UNIX Many Embedded systems (Geoworks, Vx. Works, Java. OS, etc) Java. OS, Pilot(PC) Mach, OS/2, Linux Win NT to 8, Solaris, HP -UX, OS X # threads per AS: • Real operating systems have either – One or many address spaces – One or many threads per address space 9/11/13 Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 13

Thread State • State shared by all threads in process/addr space – Content of

Thread State • State shared by all threads in process/addr space – Content of memory (global variables, heap) – I/O state (file system, network connections, etc) • State “private” to each thread – Kept in TCB Thread Control Block – CPU registers (including, program counter) – Execution stack – what is this? • Execution Stack – Parameters, temporary variables – Return PCs are kept while called procedures are executing 9/11/13 Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 14

Review: Execution Stack Example addr. X: . . . A(int tmp) { if (tmp<2)

Review: Execution Stack Example addr. X: . . . A(int tmp) { if (tmp<2) B(); addr. Y: . . . printf(tmp); } B() { C(); addr. U: . . . } addr. V: } . . . addr. Z: 9/11/13 C() { A(2); A(1); exit; • Stack holds function arguments, return address • Permits recursive execution • Crucial to modern languages Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 15

Review: Execution Stack Example addr. X: . . . A(int tmp) { if (tmp<2)

Review: Execution Stack Example addr. X: . . . A(int tmp) { if (tmp<2) B(); addr. Y: . . . Stack Pointer A: tmp=1 ret=addr. Z Stack Growth printf(tmp); } B() { C(); addr. U: . . . } addr. V: } . . . addr. Z: 9/11/13 C() { A(2); A(1); exit; • Stack holds function arguments, return address • Permits recursive execution • Crucial to modern languages Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 16

Review: Execution Stack Example addr. X: . . . A(int tmp) { if (tmp<2)

Review: Execution Stack Example addr. X: . . . A(int tmp) { if (tmp<2) B(); addr. Y: . . . Stack Pointer A: tmp=1 ret=addr. Z Stack Growth printf(tmp); } B() { C(); addr. U: . . . } addr. V: } . . . addr. Z: 9/11/13 C() { A(2); A(1); exit; • Stack holds function arguments, return address • Permits recursive execution • Crucial to modern languages Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 17

Review: Execution Stack Example addr. X: . . . A(int tmp) { if (tmp<2)

Review: Execution Stack Example addr. X: . . . A(int tmp) { if (tmp<2) B(); addr. Y: . . . Stack Pointer A: tmp=1 ret=addr. Z Stack Growth printf(tmp); } B() { C(); addr. U: . . . } addr. V: } . . . addr. Z: 9/11/13 C() { A(2); A(1); exit; • Stack holds function arguments, return address • Permits recursive execution • Crucial to modern languages Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 18

Review: Execution Stack Example addr. X: . . . A(int tmp) { if (tmp<2)

Review: Execution Stack Example addr. X: . . . A(int tmp) { if (tmp<2) B(); addr. Y: . . . A: tmp=1 ret=addr. Z printf(tmp); Stack Pointer B: ret=addr. Y Stack Growth } B() { C(); addr. U: . . . } addr. V: } . . . addr. Z: 9/11/13 C() { A(2); A(1); exit; • Stack holds function arguments, return address • Permits recursive execution • Crucial to modern languages Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 19

Review: Execution Stack Example addr. X: . . . A(int tmp) { if (tmp<2)

Review: Execution Stack Example addr. X: . . . A(int tmp) { if (tmp<2) B(); addr. Y: . . . A: tmp=1 ret=addr. Z printf(tmp); Stack Pointer B: ret=addr. Y Stack Growth } B() { C(); addr. U: . . . } addr. V: } . . . addr. Z: 9/11/13 C() { A(2); A(1); exit; • Stack holds function arguments, return address • Permits recursive execution • Crucial to modern languages Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 20

Review: Execution Stack Example addr. X: . . . A(int tmp) { if (tmp<2)

Review: Execution Stack Example addr. X: . . . A(int tmp) { if (tmp<2) B: ret=addr. Y B(); addr. Y: . . . A: tmp=1 ret=addr. Z printf(tmp); } Stack Pointer B() { Stack Growth C(); addr. U: . . . } addr. V: } . . . addr. Z: 9/11/13 C() { A(2); A(1); exit; C: ret=addr. U • Stack holds function arguments, return address • Permits recursive execution • Crucial to modern languages Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 21

Review: Execution Stack Example addr. X: . . . A(int tmp) { if (tmp<2)

Review: Execution Stack Example addr. X: . . . A(int tmp) { if (tmp<2) B: ret=addr. Y B(); addr. Y: . . . A: tmp=1 ret=addr. Z printf(tmp); } Stack Pointer B() { Stack Growth C(); addr. U: . . . } addr. V: } . . . addr. Z: 9/11/13 C() { A(2); A(1); exit; C: ret=addr. U • Stack holds function arguments, return address • Permits recursive execution • Crucial to modern languages Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 22

Review: Execution Stack Example addr. X: . . . A(int tmp) { if (tmp<2)

Review: Execution Stack Example addr. X: . . . A(int tmp) { if (tmp<2) } B() { addr. U: . . . } addr. V: } addr. Z: 9/11/13 C: ret=addr. U printf(tmp); C(); . . . B: ret=addr. Y B(); addr. Y: . . . A: tmp=1 ret=addr. Z Stack Pointer A: tmp=2 ret=addr. V Stack Growth C() { A(2); A(1); exit; • Stack holds function arguments, return address • Permits recursive execution • Crucial to modern languages Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 23

Review: Execution Stack Example addr. X: . . . A(int tmp) { if (tmp<2)

Review: Execution Stack Example addr. X: . . . A(int tmp) { if (tmp<2) } B() { addr. U: . . . } addr. V: } addr. Z: 9/11/13 C: ret=addr. U printf(tmp); C(); . . . B: ret=addr. Y B(); addr. Y: . . . A: tmp=1 ret=addr. Z Stack Pointer A: tmp=2 ret=addr. V Stack Growth C() { A(2); A(1); exit; • Stack holds function arguments, return address • Permits recursive execution • Crucial to modern languages Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 24

Review: Execution Stack Example addr. X: . . . A(int tmp) { if (tmp<2)

Review: Execution Stack Example addr. X: . . . A(int tmp) { if (tmp<2) } B() { addr. U: . . . } addr. V: } addr. Z: 9/11/13 C: ret=addr. U printf(tmp); C(); . . . B: ret=addr. Y B(); addr. Y: . . . A: tmp=1 ret=addr. Z Stack Pointer A: tmp=2 ret=addr. V Stack Growth C() { Output: 2 A(2); A(1); exit; Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 25

Review: Execution Stack Example addr. X: . . . A(int tmp) { if (tmp<2)

Review: Execution Stack Example addr. X: . . . A(int tmp) { if (tmp<2) B: ret=addr. Y B(); addr. Y: . . . A: tmp=1 ret=addr. Z printf(tmp); } Stack Pointer B() { Stack Growth C(); addr. U: . . . } addr. V: } . . . addr. Z: 9/11/13 C: ret=addr. U C() { Output: 2 A(2); A(1); exit; Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 26

Review: Execution Stack Example addr. X: . . . A(int tmp) { if (tmp<2)

Review: Execution Stack Example addr. X: . . . A(int tmp) { if (tmp<2) B(); addr. Y: . . . A: tmp=1 ret=addr. Z printf(tmp); Stack Pointer B: ret=addr. Y Stack Growth } B() { C(); addr. U: . . . } addr. V: } . . . addr. Z: 9/11/13 C() { Output: 2 A(2); A(1); exit; Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 27

Review: Execution Stack Example addr. X: . . . A(int tmp) { if (tmp<2)

Review: Execution Stack Example addr. X: . . . A(int tmp) { if (tmp<2) B(); addr. Y: . . . Stack Pointer A: tmp=1 ret=addr. Z Stack Growth printf(tmp); } B() { C(); addr. U: . . . } addr. V: } . . . addr. Z: 9/11/13 C() { Output: 2 1 A(2); A(1); exit; Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 28

Review: Execution Stack Example addr. X: . . . A(int tmp) { if (tmp<2)

Review: Execution Stack Example addr. X: . . . A(int tmp) { if (tmp<2) B(); addr. Y: . . . printf(tmp); } B() { C(); addr. U: . . . } addr. V: } . . . addr. Z: 9/11/13 C() { Output: 2 1 A(2); A(1); exit; Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 29

Single-Threaded Example • Imagine the following C program: main() { Compute. PI(“pi. txt”); Print.

Single-Threaded Example • Imagine the following C program: main() { Compute. PI(“pi. txt”); Print. Class. List(“clist. text”); } • What is the behavior here? – Program would never print out class list – Why? Compute. PI would never finish 9/11/13 Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 30

Use of Threads • Version of program with Threads: main() { Create. Thread(Compute. PI(“pi.

Use of Threads • Version of program with Threads: main() { Create. Thread(Compute. PI(“pi. txt”)); Create. Thread(Print. Class. List(“clist. text”)); } • What does “Create. Thread” do? – Start independent thread running given procedure • What is the behavior here? – Now, you would actually see the class list – This should behave as if there are two separate CPUs CPU 1 CPU 2 Time 9/11/13 Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 31

Memory Footprint of Two-Thread Example • If we stopped this program and examined it

Memory Footprint of Two-Thread Example • If we stopped this program and examined it with a debugger, we would see – Two sets of CPU registers – Two sets of Stacks Stack 1 Stack 2 – How do we position stacks relative to each other? – What maximum size should we choose for the stacks? – What happens if threads violate this? – How might you catch violations? Heap Address Space • Questions: Global Data Code 9/11/13 Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 32

Per Thread State • Each Thread has a Thread Control Block (TCB) – Execution

Per Thread State • Each Thread has a Thread Control Block (TCB) – Execution State: CPU registers, program counter (PC), pointer to stack (SP) – Scheduling info: state, priority, CPU time – Various Pointers (for implementing scheduling queues) – Pointer to enclosing process (PCB) – Etc (add stuff as you find a need) • OS Keeps track of TCBs in protected memory – In Array, or Linked List, or … 9/11/13 Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 33

Multithreaded Processes • PCB points to multiple TCBs: • Switching threads within a block

Multithreaded Processes • PCB points to multiple TCBs: • Switching threads within a block is a simple thread switch • Switching threads across blocks requires changes to memory and I/O address tables. 9/11/13 Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 34

Lifecycle of a Thread (or Process) • As a thread executes, it changes state:

Lifecycle of a Thread (or Process) • As a thread executes, it changes state: – new: The thread is being created – ready: The thread is waiting to run – running: Instructions are being executed – waiting: Thread waiting for some event to occur – terminated: The thread has finished execution • “Active” threads are represented by their TCBs – TCBs organized into queues based on their state 9/11/13 Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 35

Ready Queues • Note because of the actual number of live threads in a

Ready Queues • Note because of the actual number of live threads in a typical OS, and the (much smaller) number of running threads, most threads will be in a “ready” state. • Thread not running TCB is in some scheduler queue 9/11/13 Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 36

Ready Queue And Various I/O Device Queues • Thread not running TCB is in

Ready Queue And Various I/O Device Queues • Thread not running TCB is in some scheduler queue – Separate queue for each device/signal/condition – Each queue can have a different scheduler policy Ready Queue Head SSD Unit 0 Head Tail Disk Unit 0 Head Disk Unit 2 Head Tail Ether Netwk 0 Head Tail 9/11/13 Tail Link Registers Other State TCB 9 Link Registers Other State TCB 6 Link Registers Other State TCB 2 Tail Link Registers Other State TCB 16 Link Registers Other State TCB 3 Link Registers Other State TCB 8 Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 37

Administrivia: Project Signup • Project Signup: Use “Group/Section Signup” Link – 4 -5 members

Administrivia: Project Signup • Project Signup: Use “Group/Section Signup” Link – 4 -5 members to a group, everyone must attend the same section » Use Piazza pinned teammate search thread (please close when done!) – Only submit once per group! Due Thu (9/12) by 11: 59 PM » Everyone in group must have logged into their cs 162 -xx accounts once before you register the group, Select at least 3 potential sections • New section assignments: Watch “Group/Section Assignment” Link – Attend new sections NEXT week Section Time Location TA 101 Tu 9: 00 A-10: 00 A 310 Soda Matt 102 Tu 10: 00 A-11: 00 A 75 Evans Matt 103 Tu 11: 00 A-12: 00 P 71 Evans George 104 Tu 3: 00 P-4: 00 P 24 Wheeler George 105 We 10: 00 A-11: 00 A 85 Evans Kevin 106 We 11: 00 A-12: 00 P 85 Evans Kevin 107 Tu 1: 00 P-2: 00 P 405 Soda Allen 108 Tu 2: 00 P-3: 00 P 405 Soda Allen 9/11/13 Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 38

5 min Break 9/11/13 Anthony D. Joseph and John Canny CS 162 ©UCB Fall

5 min Break 9/11/13 Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 39

Dispatch Loop • Conceptually, the dispatching loop of the operating system looks as follows:

Dispatch Loop • Conceptually, the dispatching loop of the operating system looks as follows: Loop { Run. Thread(); Choose. Next. Thread(); Save. State. Of. CPU(cur. TCB); Load. State. Of. CPU(new. TCB); } • This is an infinite loop – One could argue that this is all that the OS does 9/11/13 Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 40

Running a thread Consider first portion: Run. Thread() • How do I run a

Running a thread Consider first portion: Run. Thread() • How do I run a thread? – Load its state (registers, stack pointer) into CPU – Load environment (virtual memory space, etc) – Jump to the PC • How does the dispatcher get control back? – Internal events: thread returns control voluntarily – External events: thread gets preempted 9/11/13 Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 41

Yielding through Internal Events • Blocking on I/O – The act of requesting I/O

Yielding through Internal Events • Blocking on I/O – The act of requesting I/O implicitly yields the CPU • Waiting on a “signal” from other thread – Thread asks to wait and thus yields the CPU • Thread executes a yield() – Thread volunteers to give up CPU compute. PI() { while(TRUE) { Compute. Next. Digit(); yield(); } } – Note that yield() must be called by programmer frequently enough! 9/11/13 Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 42

Stack for Yielding a Thread Compute. PI User Stack yield Trap to OS kernel_yield

Stack for Yielding a Thread Compute. PI User Stack yield Trap to OS kernel_yield run_new_thread Kernel Stack switch • How do we run a new thread? run_new_thread() { new. Thread = Pick. New. Thread(); switch(cur. Thread, new. Thread); Thread. House. Keeping(); /* deallocates finished threads */ } • Finished thread not killed right away. Why? – Move them in “exit/terminated” state – Thread. House. Keeping() deallocates finished threads 9/11/13 Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 43

Stack for Yielding a Thread Compute. PI User Stack yield Trap to OS kernel_yield

Stack for Yielding a Thread Compute. PI User Stack yield Trap to OS kernel_yield run_new_thread Kernel Stack switch • How do we run a new thread? run_new_thread() { new. Thread = Pick. New. Thread(); switch(cur. Thread, new. Thread); Thread. House. Keeping(); /* deallocates finished threads */ } • How does dispatcher switch to a new thread? – Save anything next thread may trash: PC, regs, SP – Maintain isolation for each thread 9/11/13 Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 44

Review: Two Thread Yield Example • Consider the following code blocks: Thread T Thread

Review: Two Thread Yield Example • Consider the following code blocks: Thread T Thread S proc A() { B(); A A B(while) } proc B() { while(TRUE) { yield(); } } yield kernel_yield run_new_thread switch • Suppose we have two threads: – Threads S and T 9/11/13 Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 45

Detour: Interrupt Controller Priority Encoder Interrupt Mask Timer Network Software Interrupt Int. ID Interrupt

Detour: Interrupt Controller Priority Encoder Interrupt Mask Timer Network Software Interrupt Int. ID Interrupt Anthony D. Joseph and John Canny CS 162 Int Disable Control NMI • Interrupts invoked with interrupt lines from devices • Interrupt controller chooses interrupt request to honor – Mask enables/disables interrupts – Priority encoder picks highest enabled interrupt – Software Interrupt Set/Cleared by Software – Interrupt identity specified with ID line • CPU can disable all interrupts with internal flag • Non-maskable interrupt line (NMI) can’t be disabled 9/11/13 CPU ©UCB Fall 2013 Lec 3. 46

Review: Preemptive Multithreading • Use the timer interrupt to force scheduling decisions Some Routine

Review: Preemptive Multithreading • Use the timer interrupt to force scheduling decisions Some Routine Interrupt Timer. Interrupt run_new_thread User Stack Kernel Stack switch • Timer Interrupt routine: Timer. Interrupt() { Do. Periodic. House. Keeping(); run_new_thread(); } • This is often called preemptive multithreading, since threads are preempted for better scheduling – Solves problem of user who doesn’t insert yield(); 9/11/13 Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 47

Why allow cooperating threads? • People cooperate; computers help/enhance people’s lives, so computers must

Why allow cooperating threads? • People cooperate; computers help/enhance people’s lives, so computers must cooperate – By analogy, the non-reproducibility/non-determinism of people is a notable problem for “carefully laid plans” • Advantage 1: Share resources – One computer, many users – One bank balance, many ATMs » What if ATMs were only updated at night? – Embedded systems (robot control: coordinate arm & hand) • Advantage 2: Speedup – Overlap I/O and computation – Multiprocessors – chop up program into parallel pieces • Advantage 3: Modularity – Chop large problem up into simpler pieces 9/11/13 » To compile, for instance, gcc calls cpp | cc 1 | cc 2 | as | ld » Makes system easier to extend Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 48

Threaded Web Server • Multithreaded version: server. Loop() { connection = Accept. Con(); Thread.

Threaded Web Server • Multithreaded version: server. Loop() { connection = Accept. Con(); Thread. Create(Service. Web. Page(), connection); } • Advantages of threaded version: – Can share file caches kept in memory, results of CGI scripts, other things – Threads are much cheaper to create than processes, so this has a lower per-request overhead • What if too many requests come in at once? 9/11/13 Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 49

Thread Pools • Problem with previous version: Unbounded Threads – When web-site becomes too

Thread Pools • Problem with previous version: Unbounded Threads – When web-site becomes too popular – throughput sinks Master Thread queue • Instead, allocate a bounded “pool” of threads, representing the maximum level of multiprogramming Thread Pool master() { alloc. Threads(slave, queue); while(TRUE) { con=Accept. Con(); Enqueue(queue, con); wake. Up(queue); } } 9/11/13 Anthony D. Joseph and John Canny slave(queue) { while(TRUE) { con=Dequeue(queue); if (con==null) sleep. On(queue); else Service. Web. Page(con); } } Lec 3. 50 CS 162 ©UCB Fall 2013

ATM Bank Server • ATM server problem: – Service a set of requests –

ATM Bank Server • ATM server problem: – Service a set of requests – Do so without corrupting database – Don’t hand out too much money 9/11/13 Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 51

ATM bank server example • Suppose we wanted to implement a server process to

ATM bank server example • Suppose we wanted to implement a server process to handle requests from an ATM network: Bank. Server() { while (TRUE) { Receive. Request(&op, &acct. Id, &amount); Process. Request(op, acct. Id, amount); } } Process. Request(op, acct. Id, amount) { if (op == deposit) Deposit(acct. Id, amount); else if … } Deposit(acct. Id, amount) { acct = Get. Account(acct. Id); /* may use disk I/O */ acct->balance += amount; Store. Account(acct); /* Involves disk I/O */ } • How could we speed this up? – More than one request being processed at once – Multiple threads (multi-proc, or overlap comp and I/O) 9/11/13 Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 52

Can Threads Help? • One thread per request! • Requests proceeds to completion, blocking

Can Threads Help? • One thread per request! • Requests proceeds to completion, blocking as required: Deposit(acct. Id, amount) { acct = Get. Account(act. Id); /* May use disk I/O */ acct->balance += amount; Store. Account(acct); /* Involves disk I/O */ } • Unfortunately, shared state can get corrupted: Thread 1 load r 1, acct->balance add r 1, amount 1 store r 1, acct->balance 9/11/13 Anthony D. Joseph and John Canny Thread 2 load r 1, acct->balance add r 1, amount 2 store r 1, acct->balance CS 162 ©UCB Fall 2013 Lec 3. 53

Problem is at the lowest level • Most of the time, threads are working

Problem is at the lowest level • Most of the time, threads are working on separate data, so scheduling doesn’t matter: Thread A x = 1; Thread B y = 2; • However, What about (Initially, y = 12): Thread A x = 1; x = y+1; Thread B y = 2; y = y*2; – What are the possible values of x? Thread A x = 1; x = y+1; Thread B y = 2; y = y*2 x=13 9/11/13 Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 54

Problem is at the lowest level • Most of the time, threads are working

Problem is at the lowest level • Most of the time, threads are working on separate data, so scheduling doesn’t matter: Thread A x = 1; Thread B y = 2; • However, What about (Initially, y = 12): Thread A x = 1; x = y+1; Thread B y = 2; y = y*2; – What are the possible values of x? Thread A Thread B y = 2; y = y*2; x = 1; x = y+1; x=5 9/11/13 Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 55

Problem is at the lowest level • Most of the time, threads are working

Problem is at the lowest level • Most of the time, threads are working on separate data, so scheduling doesn’t matter: Thread A x = 1; Thread B y = 2; • However, What about (Initially, y = 12): Thread A x = 1; x = y+1; Thread B y = 2; y = y*2; – What are the possible values of x? Thread A Thread B y = 2; x = 1; x = y+1; y= y*2; x=3 9/11/13 Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 56

Summary • Concurrent threads are a very useful abstraction – Allow transparent overlapping of

Summary • Concurrent threads are a very useful abstraction – Allow transparent overlapping of computation and I/O – Allow use of parallel processing when available • Concurrent threads introduce problems when accessing shared data – Programs must be insensitive to arbitrary interleavings – Without careful design, shared variables can become completely inconsistent • Next lecture: deal with concurrency problems 9/11/13 Anthony D. Joseph and John Canny CS 162 ©UCB Fall 2013 Lec 3. 57