Introduction to Asynchronous Programming Fall 2014

Similar documents
3.1 Introduction. Computers perform operations concurrently

Process Concepts. CSC400 - Operating Systems. 3. Process Concepts. J. Sumey

PROCESSES AND THREADS THREADING MODELS. CS124 Operating Systems Winter , Lecture 8

SMD149 - Operating Systems

Course: Operating Systems Instructor: M Umair. M Umair

Threads SPL/2010 SPL/20 1

CS 351 Week 15. Course Review

Processes and Non-Preemptive Scheduling. Otto J. Anshus

Inter-Process Communication

Operating System Structure

CHAPTER 3 - PROCESS CONCEPT

BENCHMARKING LIBEVENT AGAINST LIBEV


Part V. Process Management. Sadeghi, Cubaleska RUB Course Operating System Security Memory Management and Protection

CS 43: Computer Networks. 07: Concurrency and Non-blocking I/O Sep 17, 2018

Agenda. Threads. Single and Multi-threaded Processes. What is Thread. CSCI 444/544 Operating Systems Fall 2008

Asynchronous Events on Linux

For use by students enrolled in #71251 CSE430 Fall 2012 at Arizona State University. Do not use if not enrolled.

Threads Chapter 5 1 Chapter 5

W4118 Operating Systems. Junfeng Yang

Chapter 3: Process Concept

Chapter 3: Process Concept

Computer Systems Assignment 2: Fork and Threads Package

Overview. Administrative. * HW 2 Grades. * HW 3 Due. Topics: * What are Threads? * Motivating Example : Async. Read() * POSIX Threads

Today s Topics. u Thread implementation. l Non-preemptive versus preemptive threads. l Kernel vs. user threads

Chapter 3: Process Concept

Operating System. Chapter 4. Threads. Lynn Choi School of Electrical Engineering

Assignment 2 Group 5 Simon Gerber Systems Group Dept. Computer Science ETH Zurich - Switzerland

CS 326: Operating Systems. Process Execution. Lecture 5

CS510 Operating System Foundations. Jonathan Walpole

CS510 Operating System Foundations. Jonathan Walpole

! How is a thread different from a process? ! Why are threads useful? ! How can POSIX threads be useful?

Operating Systems: Internals and Design Principles. Chapter 4 Threads Seventh Edition By William Stallings

ECE 550D Fundamentals of Computer Systems and Engineering. Fall 2017

CSE 43: Computer Networks Structure, Threading, and Blocking. Kevin Webb Swarthmore College September 14, 2017

PROCESS CONCEPTS. Process Concept Relationship to a Program What is a Process? Process Lifecycle Process Management Inter-Process Communication 2.

CS 4300 Computer Graphics

THE CPU SPENDS ALMOST ALL of its time fetching instructions from memory

Distributed Systems CSCI-B 534/ENGR E-510. Spring 2019 Instructor: Prateek Sharma

CSE 451 Midterm 1. Name:

CS 3305 Intro to Threads. Lecture 6

Chapter 3: Processes. Operating System Concepts 9 th Edition

What s An OS? Cyclic Executive. Interrupts. Advantages Simple implementation Low overhead Very predictable

Guido van Rossum 9th LASER summer school, Sept. 2012

CSC 2405: Computer Systems II

Exception-Less System Calls for Event-Driven Servers

!! How is a thread different from a process? !! Why are threads useful? !! How can POSIX threads be useful?

Chapter 13: I/O Systems

Frequently asked questions from the previous class survey

CS 5523 Operating Systems: Midterm II - reivew Instructor: Dr. Tongping Liu Department Computer Science The University of Texas at San Antonio

A Scalable Event Dispatching Library for Linux Network Servers

Motivation. Threads. Multithreaded Server Architecture. Thread of execution. Chapter 4

3. Process Management in xv6

* What are the different states for a task in an OS?

Execution Architecture

Outline. Threads. Single and Multithreaded Processes. Benefits of Threads. Eike Ritter 1. Modified: October 16, 2012

Twisted is the first library we ll be working with that does not come with the Python Standard Library.

CPS221 Lecture: Threads

Roadmap. Tevfik Ko!ar. CSC Operating Systems Fall Lecture - III Processes. Louisiana State University. Processes. September 1 st, 2009

Introduction to Embedded Systems. Lab Logistics

Lecture 21 Concurrent Programming

CS 333 Introduction to Operating Systems. Class 3 Threads & Concurrency. Jonathan Walpole Computer Science Portland State University

Processes. Process Concept

CS 153 Design of Operating Systems Winter 2016

CS 475. Process = Address space + one thread of control Concurrent program = multiple threads of control

Yi Shi Fall 2017 Xi an Jiaotong University

Project 1: Snowcast Due: 11:59 PM, Sep 22, 2016

Chapter 4: Threads. Overview Multithreading Models Thread Libraries Threading Issues Operating System Examples Windows XP Threads Linux Threads

LINUX OPERATING SYSTEM Submitted in partial fulfillment of the requirement for the award of degree of Bachelor of Technology in Computer Science

CSE 153 Design of Operating Systems Fall 2018

CSCE Introduction to Computer Systems Spring 2019

2 Processes. 2 Processes. 2 Processes. 2.1 The Process Model. 2.1 The Process Model PROCESSES OPERATING SYSTEMS

CS 333 Introduction to Operating Systems. Class 3 Threads & Concurrency. Jonathan Walpole Computer Science Portland State University

Operating Systems Overview. Chapter 2

Questions answered in this lecture: CS 537 Lecture 19 Threads and Cooperation. What s in a process? Organizing a Process

Today: VM wrap-up Select (if time) Course wrap-up Final Evaluations

Lecture 7: Process & Thread Introduction

Threads. Computer Systems. 5/12/2009 cse threads Perkins, DW Johnson and University of Washington 1

Concurrency COMS W4115. Prof. Stephen A. Edwards Spring 2002 Columbia University Department of Computer Science

Implementing Coroutines. Faking Coroutines in Java

Processes. Johan Montelius KTH

CISC2200 Threads Spring 2015

CS 5460/6460 Operating Systems

Threads. Raju Pandey Department of Computer Sciences University of California, Davis Spring 2011

CS 5523: Operating Systems

Learning from Bad Examples. CSCI 5828: Foundations of Software Engineering Lecture 25 11/18/2014

SE350: Operating Systems. Lecture 3: Concurrency

A process. the stack

Chapter 4: Threads. Operating System Concepts. Silberschatz, Galvin and Gagne

Chapter 4: Threads. Operating System Concepts 9 th Edition

Chapter 3: Processes. Operating System Concepts 8th Edition

Lecture 2: February 6

hardware interrupts software interrupts

THREADS AND CONCURRENCY

Chapter 3: Processes

628 Lecture Notes Week 4

Disciplina Sistemas de Computação

CSE 410: Systems Programming

CS-537: Midterm Exam (Spring 2001)

Lecture 4: Memory Management & The Programming Interface

Transcription:

CS168 Computer Networks Fonseca Introduction to Asynchronous Programming Fall 2014 Contents 1 Introduction 1 2 The Models 1 3 The Motivation 3 4 Event-Driven Programming 4 5 select() to the rescue 5 1 Introduction In this document we introduce an asynchronous model for concurrent programming. For certain applications, an asynchronous model may yield performance benefits over traditional multithreading. Much of the material presented in this document is taken from Dave Peticola s excellent introduction to Twisted 1, a Python framework for asynchronous programming. 2 The Models We will start by reviewing two (hopefully) familiar models in order to contrast them with the asynchronous model. By way of illustration we will imagine a program that consists of three conceptually distinct tasks which must be performed to complete the program. Note that I am using task in the non-technical sense of something that needs to be done. The first model we will look at is the single-threaded synchronous model, as shown in Figure 1. This is the simplest style of programming. Each task is performed one at a time, with one finishing completely before another is started. And if the tasks are always performed in a definite order, the implementation of a later task can assume that all earlier tasks have finished without errors, with all their output available for use a definite simplification in logic. We can contrast the single-threaded synchronous model with the multi-threaded synchronous model illustrated in Figure 2. In this model, each task is performed in a separate thread of control. The threads are managed by the operating system and may, on a system with multiple processors or multiple cores, run truly concurrently, or may be interleaved together on a single processor. The point is, in the threaded model the details of execution are handled by the OS and the programmer simply thinks in terms 1 http://krondo.com/?page_id=1327

Figure 1: The single-threaded synchronous model Figure 2: The threaded model of independent instruction streams which may run simultaneously. Although the diagram is simple, in practice threaded programs can be quite complex because of the need for threads to coordinate with one another. Thread communication and coordination is an advanced programming topic and can be difficult to get right. Some programs implement parallelism using multiple processes instead of multiple threads. Although the programming details are different, conceptually it is the same model as in Figure 2. Now we can introduce the asynchronous model 2, depicted in Figure 3: In this model, the tasks are interleaved with one another, but in a single thread of control. This is simpler than the threaded case because the programmer always knows that when one task is executing, another task is not. Although in a single-processor system a threaded program will also execute in an interleaved pattern, a programmer using threads should still think in terms of Figure 2, not Figure 3, lest the program work incorrectly when moved to a multi-processor system. But a single-threaded asynchronous system will always execute with interleaving, even on a multi-processor system. There is another difference between the asynchronous and threaded models. In a threaded system the decision to suspend one thread and execute another is largely outside of the programmer s control. Rather, it is under the control of the operating system, and the programmer must assume that a thread may be suspended and replaced with another at almost any time. In contrast, under the asynchronous model a task will continue to run until it explicitly relinquishes control to other 2 The multi-threaded synchronous model is also referred to as preemptive multitasking, with the asynchronous model called cooperative multitasking. 2

Figure 3: The asynchronous model tasks. 3 The Motivation We ve seen that the asynchronous model is in some ways simpler than the threaded one because there is a single instruction stream and tasks explicitly relinquish control instead of being suspended arbitrarily. But the asynchronous model clearly introduces its own complexities. The programmer must organize each task as a sequence of smaller steps that execute intermittently. If one task uses the output of another, the dependent task must be written to accept its input as a series of bits and pieces instead of all together. Since there is no actual parallelism, it appears from our diagrams that an asynchronous program will take just as long to execute as a synchronous one. But there is a condition under which an asynchronous system can outperform a synchronous one, sometimes dramatically so. This condition holds when tasks are forced to wait, or block, as illustrated in Figure 4: Figure 4: Blocking in a synchronous program 3

In the figure, the gray sections represent periods of time when a particular task is waiting (blocking) and thus cannot make any progress. Why would a task be blocked? A frequent reason is that it is waiting to perform I/O, to transfer data to or from an external device. A typical CPU can handle data transfer rates that are orders of magnitude faster than a disk or a network link is capable of sustaining. Thus, a synchronous program that is doing lots of I/O will spend much of its time blocked while a disk or network catches up. Such a synchronous program is also called a blocking program for that reason. Notice that Figure 4, a blocking program, looks a bit like Figure 3, an asynchronous program. This is not a coincidence. The fundamental idea behind the asynchronous model is that an asynchronous program, when faced with a task that would normally block in a synchronous program, will instead execute some other task that can still make progress. So an asynchronous program only blocks when no task can make progress (which is why an asynchronous program is often called a non-blocking program). Each switch from one task to another corresponds to the first task either finishing, or coming to a point where it would have to block. With a large number of potentially blocking tasks, an asynchronous program can outperform a synchronous one by spending less overall time waiting, while devoting a roughly equal amount of time to real work on the individual tasks. Compared to the synchronous model, the asynchronous model performs best when: There are a large number of tasks so there is likely always at least one task that can make progress. The tasks perform lots of I/O, causing a synchronous program to waste lots of time blocking when other tasks could be running. The tasks are largely independent from one another so there is little need for inter-task communication (and thus for one task to wait upon another). These conditions almost perfectly characterize a typical busy network server (like a web server) in a client-server environment. Each task represents one client request with I/O in the form of receiving the request and sending the reply. A network server implementation is a prime candidate for the asynchronous model, which is why Twisted and Node.js, among other asynchronous server libraries, have grown so much in popularity in recent years. You may be asking: Why not just use more threads? If one thread is blocking on an I/O operation, another thread can make progress, right? However, as the number of threads increases, your server may start to experience performance problems. With each new thread, there is some memory overhead associated with the creation and maintenance of thread state. Another performance gain from the asynchronous model is that it avoids context switching every time the OS transfers control over from one thread to another it has to save all the relevant registers, memory map, stack pointers, FPU context etc. so that the other thread can resume execution where it left off. The overhead of doing this can be quite significant. (For more on this, we suggest taking CSCI1670). 4 Event-Driven Programming We ve seen that asynchronous programming allows us to spend less time waiting while utilizing only a single thread. But how exactly do we reap that benefit? Consider a program that blocks waiting to read input from stdin: 4

void monitor_stdin(void) { char input[500]; while(1) { memset(input, 0, 500); scanf("%s", &input); printf("you typed %s\n", input); } } scanf() blocks until data is available on the stdin file descriptor. This means that the thread executing this function is not able to perform any other work until scanf() returns. Most asynchronous programming libraries get around this problem in the following way: Rather than block on scanf(), continue executing the next line of code. Provide a chunk of code to run when scanf() actually finds data available on stdin. This callback block of code will execute when scanf() would have returned in the synchronous case 3. If you ve used AJAX before, this pattern will sound familiar. It s the same pattern employed by many GUI frameworks When the button is clicked, call this function, but don t just continually wait for the button to be clicked because that would block us from doing any other work. If you experiment with Twisted or Node.js, you ll again see this pattern providing a callback to be performed when some event occurs in the future. libevent is an asynchronous event notification library. While we won t be using it explicitly in this course, it serves as the foundation for many asynchronous programming frameworks. The libevent API provides a mechanism to execute a callback function when a specific event occurs on a file descriptor or after a timeout has been reached. Currently, libevent supports /dev/poll, kqueue, select, poll, and epoll, all of which are different I/O event notification mechanisms. libevent provides a higher level abstraction around these mechanisms, choosing the best one based on the OS. In this course, we ll be using select() and epoll() directly, but libevent may be useful for future indulgences in asynchronous programming. 5 select() to the rescue One traditional way to write network servers is to have the main server block on accept(), waiting for a connection. Once a connection comes in, the server fork()s or spawns a new thread, and the 3 Providing these callback functions (sometimes called event handlers ) can introduce some complexity to the programming logic. The programmer is responsible for maintaining state between when a blocking operation begins and when the callback is invoked. In the synchronous model, this state is automatically maintained on the stack. In the asynchronous model, the programmer must ensure the data is available for later use when the future event occurs. Luckily many languages provide closures to deal with this transparently, which you can read up on if you re curious. Debugging is also a bit more complicated in an asynchronous environment. If you ve registered an event handler and then set a breakpoint inside of the callback code, the stack will always show something to the extent of event loop called event handler. You need extra support to see where the handler was actually registered, i.e. what code caused the callback to be invoked. 5

child process/thread handles the connection while the main server is able to service new incoming requests. With select(), instead of having a process/thread for each client, there is usually only one thread that multiplexes all requests, servicing each client as much as it can. So one main advantage of using select() is that your server will only require a single process/thread to handle all requests. Thus, your server will not need shared memory or synchronization primitives for different tasks to communicate. select() works by blocking until something happens on a file descriptor (which can represent an actual file, a pipe, or a network socket). What s something? Data coming in, being able to write to the file descriptor, or a timeout you tell select() what you want to be woken up by. Most select()-based servers are structured around a event loop consisting of the following: Fill up a fd set structure with the file descriptors you want to know when data comes in on. Fill up a fd set structure with the file descriptors you want to know when you can write on. Call select() and block until something happens. Once select() returns, check to see if any of your file descriptors was the reason you woke up. If so, service that file descriptor in whatever particular way your server needs to. Repeat this process forever. To get a comprehensive overview of select() with sample code, read sections 7.1 and 7.2 of Beej s guide at: http://beej.us/guide/bgnet/output/html/multipage/advanced.html. This should be one of your primary resources as you re implementing non-blocking I/O for the Snowcast server. If you have any questions about how to use select(), or about asynchronous programming in general, be sure to contact the TAs or stop by their office hours. Please let us know if you find any mistakes, inconsistencies, or confusing language in this or any other CS168 document by filling out the anonymous feedback form: http://cs.brown.edu/courses/cs168/f14/feedback.html. 6