Eroxl's Notes
09 - I-O, Asynchrony and Threads (CPSC 213 Practice)

Problem 1

For each of the following, state whether the CPU, IO controller, or both determines when it occurs. (i.e., initiates it)

Programmed IO (PIO)

  • [x] (a) CPU
  • [ ] (b) IO Controller

Select all possible options that apply.

Direct Memory Access (DMA)

  • [x] (a) IO Controller
  • [ ] (b) CPU

Select all possible options that apply.

Interrupts

  • [ ] (a) CPU
  • [x] (b) IO Controller

Select all possible options that apply.

Polling

  • [ ] (a) IO Controller
  • [x] (b) CPU

Select all possible options that apply.

Problem 2

Which of the following (if any) prints the sum of the first 256 bytes of disk block 1234? Assume that the arguments to async_read are correctly set, that it performs the PIOs to request the block data be transferred into buf, and that it enqueues sufficient information so that the interrupt service routine can call the specified event handler (if this is necessary).

A:

char buf\[256\];
void ps(){
   async\_read(1234, buf, 256);
   int s\=0;
   for (int i\=0; i<256; i++)
      s += buf\[i\];
   print("%d\\n", s);
}

B:

int getsum(char\* buf) {
   int s\=0;
   for(int i\=0; i<256; i++)
      s += buf\[i\];
   return s;
}

char buf\[256\];
void ps(){
   int s \= async\_read(1234, buf, 256, getsum);
   print("%d\\n", s);
}
  • [ ] A.
  • [ ] B.
  • [ ] A and B.
  • [x] None of them.

Problem 3

Which of the following statements best describes this code that is attempting to print the value of a disk block. Note that syntax of queue has changed slightly from the assignment to simplify it.

void interrupt\_service\_routine(){
   int\* result;
   void (\*callback)(int\*);
   queue\_dequeue(&result, &callback);
   callback(result);
}

void printInt(int\* i){
   printf("%d\\n", \*i);
 }

void read(int blockno){
   int\* result \= malloc(sizeof(int));
   queue\_enqueue(result, printInt);
   disk\_read(result, blockno);
   free(result);
}
  • [ ] It makes incorrect use of function pointers.
  • [ ] It has a memory leak bug.
  • [ ] It is correct.
  • [x] It has a dangling pointer bug.
  • [ ] It has an error : it might print before the read has completed.
  • [ ] It has an error: it never calls interrupt_service_routine.

Problem 4

Which of the following best describes what happens to a thread when it calls the following functions? Answer each subquestion separately (i.e., previous subquestions have no effect on subsequent ones).

uthread_create(proc, arg)

  • [x] It creates the thread and marks the thread as nascent with the specified procedure.
  • [ ] It creates the thread but has to call the thread to make it start running.
  • [ ] It initializes the thread, but does not schedule the thread.
  • [ ] It creates the thread and blocks itself to start the thread to run the specified procedure.
  • [ ] It creates the thread and yields to the thread to make it run.

uthread_block

  • [ ] If there are threads waiting to run, it stops running, otherwise it continues to run.
  • [ ] It stops the CPU on which it is running and waits for it to be ready to restart.
  • [ ] It stops the CPU on which it is running.
  • [x] The thread that was running stops running, and if there are threads waiting to run, they start running instead.

uthread_unblock

  • [ ] It starts running the unblocked thread immediately.
  • [x] It makes the unblocked thread runnable but does not necessarily run it immediately.
  • [ ] It stops the current thread to start running the unblocked thread.
  • [ ] It restarts the CPU.

uthread_join(t)

  • [ ] t switches to a different CPU core and starts executing there.
  • [ ] Thread t blocks until the current thread finishes.
  • [ ] If t has completed, it is freed immediately, otherwise t is tagged to be freed once it completes.
  • [x] If t has completed, it is freed immediately, otherwise the current thread blocks until t finishes.
  • [ ] It yields to thread t and then continues running.
  • [ ] t is preempted and forced to yield to another thread.
  • [ ] t is freed immediately, and will not be able to execute anymore.

uthread_yield

  • [ ] It stops and the CPU on which it is running waits for it to be ready to restart.
  • [ ] It stops the CPU on which it is running.
  • [ ] The thread that was running stops running, and if there are threads waiting to run, they start running instead.
  • [x] If there are threads waiting to run, it stops running and the CPU it was running on runs another thread, otherwise it continues to run.

uthread_detach(t)

  • [ ] t is blocked until some thread calls uthread_join(t).
  • [ ] t is freed immediately, and will not be able to execute anymore.
  • [ ] t is preempted and forced to yield to another thread.
  • [x] If t has completed, it is freed immediately, otherwise t is tagged to be freed once it completes.
  • [ ] If t has completed, it is freed immediately, otherwise the current thread blocks until t finishes.e
  • [ ] t switches to a different CPU core and starts executing there.

Problem 4

Which of the following statements best describes the comparison between these two blocks of code? Assume that foo's runtime is known, and that the code will not be interrupted or otherwise disrupted from outside the program.

A:

thread\_t t0 \= uthread\_create(foo, NULL);
thread\_t t1 \= uthread\_create(foo, NULL);
thread\_t t2 \= uthread\_create(foo, NULL);
uthread\_join(t0);
uthread\_join(t1);
uthread\_join(t2);
thread\_t t3 \= uthread\_create(foo, NULL);
uthread\_join(t3);

B:

thread\_t t0 \= uthread\_create(foo, NULL);
uthread\_join(t0);
thread\_t t1 \= uthread\_create(foo, NULL);
uthread\_join(t1);
thread\_t t2 \= uthread\_create(foo, NULL);
uthread\_join(t2);
thread\_t t3 \= uthread\_create(foo, NULL);
uthread\_join(t3);
  • [ ] B will always complete sooner than A.
  • [ ] A will always complete sooner than B.
  • [ ] They will always complete in roughly the same time.
  • [ ] B will always complete sooner than A or in roughly the same time as A, depending on characteristics of the system on which they execute.
  • [x] A will always complete sooner than B or in roughly the same time as B, depending on characteristics of the system on which they execute.
  • [ ] None of them.