Laboratory work in TDDI04 Introduction to Pintos Assignments 00, 0, 1, 2 Motivation

advertisement
Laboratory work in TDDI04
Introduction to Pintos
Assignments 00, 0, 1, 2
Viacheslav Izosimov
2008-01-17
viaiz@ida.liu.se
Motivation
• Operating systems are nearly
everywhere
• Crucial piece of software
• Perform concurrent
tasks
• Synchronization
• C is the main
language for real
operating systems!
Motivation
• Nearly the first experience
with a relatively large piece of
software
• Direct jump from 1000 to
1000000 can be too difficult!
1000000-5000000 LOC
5000-10000 LOC
up to 1000 LOC
Your programs so far.
Pintos.
Outline
•
•
•
•
•
•
General questions
Introduction to Pintos
General description of labs
Lab rules
General algorithm for completing the labs
Lab 0
– Setting up the program environment
– Debugging of Pintos
• Lab 1
– Synchronization
– Bounded buffer
• Lab 2 (selected parts)
– System calls
– Memory issues
Real systems.
General questions
Quiz:
Labs:
Groups of five students
Sign up and take your quiz today!
Groups of two students
Sign up as soon as possible!
(deadline 2008-01-24)
Answer on the questions
until the next lesson!
Work jointly!
No cheating!
Lab lessons:
Mandatory – participation list…
5
You are not allowed to work
alone!
General questions
Quiz example
Your names!
Q1: Give an example of
Pintos recipe (2p)
A question
Your answer here!!!
Obtained points: all questions should
be answered, at least 70% of them
correctly
One copy for each group!
Sign up on the table during
the break. Once 5 students
have signed up, you can
take the quiz.
6
Introduction to Pintos
• Shift from Nachos (1990s) to Pintos (2004)
–
–
–
–
Pintos is the most up-to-date “toy operating” system
Can boot as a real operating system
Code is not as “messy” as in Nachos
Pure C implementation
Pintos
Install on Sun machines during Lab #0
Extend during Lab #1, #2, and #3
Introduction to Pintos
•
•
•
•
Runs on x86 machine
QEMU – a computer system emulator is used
UNIX environment
C implementation
(both Kernel
and user programs)
• Not complete…
• Your task!
Introduction to Pintos
User programs
User memory
User stack
Threads
Scheduler
Lab 1
Kernel stack
Synchronization
User-exception handler
primitives
Memory management
Interrupt handler
Timer
File system
General Description of Labs
• Lab 00: “Introduction to C Programming”
– Checks your ability to complete the labs
• Lab 0: “Introduction and installation”
– Introductory lab, where you need to setup your program
environment and try out debugging
• Lab 1: “Synchronization primitives”
– First “real” lab
– First introduction to threads
– Synchronization mechanisms
General Description of Labs
• Lab 2: “System calls”
–
–
–
–
System calls
Single user program
Memory issues
Console
• Lab 3: “Execution, termination and
synchronization of user programs”
–
–
–
–
–
Handling program arguments
Execution of several user programs
Termination of a user program
Synchronization of shared data structures
Wait system call
General Description of Labs
• Lab 4: “File system”
– Synchronization of read-write operations
But before…
Lab Rules
1. Every member of the group participate
equally and every member should be able to
answer questions related to labs
2. Before doing the lab answer on “preparatory
questions” on the lab page and in the
corresponding quiz
3. Understand first, then implement
4. Try to find ”bugs” yourself at first
5. No copying of source code from any sources,
no cheating
6. Pass assignments on time!
Lab Rules
Pass assignments on time to get bonus!
•
•
•
•
•
•
Lab 00, 0 – today!
Lab 1 – 30th of January (+1 point)
Lab 2 – 13th of February (+1 point)
Lab 3 – 5th of March (+1 point)
Lab 4 – 7th of April (+1 point)
•
If got 4 points, +1 extra point! 20% of the exam!
•
FINAL DEADLINE – 21st of May (no points)
General Algorithm to Complete the Labs
1. Answer on all preparatory questions. Note that many questions
are replicated in Quizzes! So, solving quizzes will help!
2. Understand what you are supposed to do (read
instructions carefully)
3. Discuss all the issues with your lab partner to make sure
that he/she also understands (That’s you future help!)
4. Understand the source code, which you are supposed to
understand
5. Begin implementation!
6. Document carefully what you are doing (put date, name
and short description around each new piece of code)
7. Work hard… and not only during lab hours, they are
mostly for asking questions from lab assistants
Lab 00
• You will need to debug a small program “debugthis.c”
with DDD after compiling it with GCC (not CC!)
• Create a linked list
• Learn how to browse the source code
• If you are not able to complete the lab, then you should
focus on C before you proceed further or even consider to
take the course next year. No formal pass/fail or other
regulations though…
Lab 0
• Set up the program environment (don’t forget!)
• module initadd
~TDDI04/labs2008/modules/pintos
• module add ~TDDI04/labs2008/modules/pintos
• Check if you have correct version of GCC and GDB
module list
• GCC should be 3.4.x and you will know if GDB
version is correct after completing Lab 00
• Copy Pintos to your directory
• gzip -cd ~TDDI04/labs2008/pintos_ida.tar.gz |
tar xvf -
Lab 0
• You will have the following structure of directories
• pintos/src
–
–
–
–
–
–
–
–
–
–
•
devices
examples
filesys
lib
misc
tests
threads
userprog
utils
vm
Lab 0
•Compile and build Pintos
• cd pintos/src/threads
• gmake
•Test if Pintos works
• cd build
• pintos --qemu -- run alarm-multiple
Lab 0
•Debugging (from build)
pintos --qemu --gdb
•
•
-- run testname
ddd --gdb --debugger pintos-gdb kernel.o&
–Note that only breakpoints can be inserted and only “Continue”
command of DDD works since Pintos is already running. Other
commands would terminate Pintos!
•Other commands:
•pintos --qemu --gdb --dport=port_number -- run testname
•Port number is 1234 + k, where k is your group number in WebReg
•ddd --gdb --debugger pintos-gdb kernel.o&
• target remote localhost:port_number
Lab 1
• First introduction to threads
• Synchronization mechanisms
– Semaphores
– Locks
– Conditions
Example with Threads
A system contains several threads running in parallel
Thread is a “basic unit of CPU utilization”
§Thread ID
§A program counter
§A register set
§A stack
Thread 1
Thread 2
Thread execution sequence
22
Example with Threads
void SimpleThread(void * which)
{
int num;
for (num = 0; num < 5; num++) {
printf("*** thread %d looped %d times\n", (int)which, num);
thread_yield();
Entering SimpleTest
}
*** thread 0 looped 0 times
}
void SimpleThreadTest(void)
{
char *t_name = "forked thread";
printf("Entering SimpleTest");
*** thread 1 looped 0 times
*** thread 0 looped 1 times
*** thread 1 looped 1 times
…
thread_create(t_name, PRI_MIN, SimpleThread, (void *)1);
}
SimpleThread((void *)0);
23
Critical Section Problem
• Critical Section: A set of instructions, operating on
shared data or resources, that should be executed
by a single process without interruption
– Atomicity of execution
– Mutual exclusion: At most one process should
be allowed to operate inside at any time
– Consistency: inconsistent intermediate states of
shared data not visible to other processes outside
• General structure, with structured control flow:
– Entry of critical section C
– … critical section C: operation on shared data
24
– Exit of critical section C
Semaphores
• Semaphore S:
– shared integer variable
– two atomic operations to modify S:
P() and V()
Example: At most five passengers in the car
• P (S):
•
while S <= 0 do Sleep(currentThread)
•
S--;
• // Critical section
• V (S):
•
WakeUp (sleepingThread)
25
•
S++;
Semaphores
• // P(S)
• void sema_down (struct semaphore *sema) {
•
enum intr_level old_level;
•
…
•
old_level = intr_disable ();
•
while (sema->value == 0) {
•
list_push_back (&sema->waiters, &thread_current ()->elem);
•
thread_block ();
•
}
•
sema->value--;
•
intr_set_level (old_level);
26
• }
Semaphores
• // V(S)
• void sema_up (struct semaphore *sema) {
•
enum intr_level old_level;
•
…
•
old_level = intr_disable ();
•
if (!list_empty (&sema->waiters))
•
thread_unblock (list_entry (list_pop_front (&sema->waiters),
struct thread, elem));
•
sema->value++;
Good for handling simple
•
intr_set_level (old_level);
• }
synchronization
problems
27
Locks
• Binary semaphore (e.g. “taken” or “not taken”)
• Only the owner can release the lock
• Advantage: No other thread can enter the
critical section!
• Essential for security, for example, access to
the shared data, arrays, lists, and etc.
• Problem: deadlock situations
28
Conditions
•
•
•
•
•
Queuing mechanism on top of Locks
Helps to manage the Locks
Prevents deadlock situations
Locks are often used together with Conditions
Locks/Conditions are good for handling
complex synchronization problems
• Attention: never use a Condition with an
empty Lock!
29
Example
Lab 1::Part B
30
Lab 1
• Your task is to write the code for
BoundedBuffer data structure
• In a bounded buffer you must handle two
conditions: the case of an empty buffer and a
full buffer
• Provide two alternative implementations:
– with Semaphores
– with Locks/Conditions
31
Lab 1
• Understand the source code in
– threads/synch.[h|c]
– threads/synchlist.[h|c]
– threads/boundedbuffer.[h|c]
– contains a skeleton of Bounded Buffer.
– src/tests/threads/threadtest.c
– tests your Bounded Buffer
implementations
Lab 1::BoundedBuffer
• An array with a fixed number of available
positions to store data in
• Used for communication between threads
–A thread produces data and puts it in the buffer
–A thread consumes data by reading data from buffer
Lab 1::BoundedBuffer
• How does it work?
• Look at it as a circular buffer
• Treat the buffer as an array and three indexes,
in, out, and count
Synchronization!
Lab 1::BoundedBuffer
• What happens if a consumer tries to read data
from an empty buffer?
• What happens if a producer tries to put data in a
full buffer?
• Note! The buffer is a shared resource
Lab 1::BoundedBuffer
• Using of BoundedBuffer (from threadtest.c)
• struct BoundedBuffer bounded_buffer[2];
• bb_write(&bounded_buffer[buf],(int) p);
• struct Data *data = (struct Data*)
bb_read(&bounded_buffer[buf]);
Lab 1::Test
• To test your implementation use threadtest.c.
• Prints 50 messages that are sent from a set of producers to
a set of consumers through the BoundedBuffer that you
have implemented
• Do not modify this program!
• You can run Pintos from threads/build directory as
• pintos --qemu -- run threadtest
• Run Pintos several times to test your implementation to
see if you do not get into a deadlock and if all the
messages appear correctly
Lab 2
•
•
•
•
System calls
Single user program
Memory issues
Console
Lab 2 :: Systems Calls At High Level
• System calls:
– communication between the user program and the
kernel
– functions, called from the user program and
performed by the kernel
– computers often use interrupts to accomplish that
switch from user code to system code
Lab 2:: Systems Calls At High Level
user_program.c
bool flag;
flag = create(“file.txt”, 1000);
Calling
Return result back
corresponding
to the user program
function in
pintos/src/lib/user/syscall.c
System
call
wrapper
the wrapper
bool create (const char *file, unsigned initial_size) {
return syscall2 (SYS_CREATE, file, initial_size);
}
Calling
corresponding
exception in Pintos kernel
pintos/src/userprog/syscall.c
the kernel
Return result back
to the wrapper
User exception handler
// Your code here!
Lab 2::What to Implement?
• You will need to implement:
– create - creates a file.
– open - opens a file.
– close - closes a file.
– read - reads from a file or the console (the keyboard).
– write - writes to a file or the console (the monitor).
– halt - halts the processor.
– exit - Terminates a program and deallocates resources
occupied by the program, for example, closes all files
opened by the program.
Lab 2::Useful Files
• You have to have a look at:
– pintos/src/lib/user/syscall[.h|.c] – the wrapper…
– userprog/syscall[.h|.c] – Your implementation of system
calls!!!
– threads/interrupt.[h|c] – important structures!!!
– lib/syscall-nr.h – system call constants
–filesys/filesys.[h|c] Pintos file system implementation…
– examples/lab2test.c – the “official” test program for this lab
– filesys/file.[h|c] – useful functions for operations with files.
Things which you don’t find in “filesys”, you find here
–userprog/process.c Look up what is here and tell me…
Lab 2::How Do I Start? (1)
• STEP 1
• Understand what the user program is
• Look into “examples” directory and a couple of
the user programs, especially “halt.c”
• Look into Makefile in this directory to understand
how the user programs are compiled
• Compile the user programs by “gmake”
• STEP 2
• Prepare Pintos disk
• Copy one or two user programs to the disk
Lab 2::How Do I Start? (2)
• STEP 2 (Continuation) Dealing with Pintos disk
• In “userprog/build”: pintos-mkdisk fs.dsk 2
– This will create a file fs.dsk with a 2MB simulated disk in
the directory.
• Format: pintos --qemu -- -f -q.
• Copy user programs:
pintos --qemu -p programname -- -q
with new name
pintos --qemu -p programname -a newname -- -q
Lab 2::How Do I Start? (3)
• STEP 2 (Continuation) Dealing with Pintos disk
• Example:
• pintos --qemu -p ../../examples/halt
-a severe_student_program -- -q
• To copy a file from the disk:
pintos --qemu -g programname -- -q
• or
pintos --qemu -g programname -a newname -- -q
* -p = put, -g = get
• To run: pintos
• Example:
--qemu -- run programname
• pintos --qemu -- run severe_student_program
Lab 2::How Do I Start? (4)
• STEP 3
• into userprog/process.c, find setup_stack()
– *esp = PHYS_BASE;
– change to *esp = PHYS_BASE - 12;
• STEP 4
• Make sure that you understand the problems which may
arise if you access (in the kernel) data stored in the user
memory using the pointers provided by the user program
as system call arguments.
• (First, make sure that you understand what this sentence
means…)
Lab 2::Shutdown Example
•
•
•
•
•
•
halt.c
#include "userprog/syscall.h“
#include <stdio.h>
#include <syscall.h>
#include <syscall-nr.h>
int
#include "threads/interrupt.h“
"threads/thread.h“
main (void){ #include
static void syscall_handler (struct intr_frame *);
voidsyscall_init (void) {
halt ();
intr_register_int (0x30, 3, INTR_ON,
}
syscall_handler, "syscall");
userprog/syscall.c
}
static void
syscall_handler (struct intr_frame *f UNUSE
printf ("system call!\n");
thread_exit ();
}
system call!
48
Lab 2::Shutdown Example
•
•
•
•
•
•
#include "userprog/syscall.h“
halt.c
#include <stdio.h>
#include <syscall-nr.h>
#include <syscall.h>
#include "threads/interrupt.h“
int
#include "threads/thread.h“
static void syscall_handler (struct intr_frame *);
main (void){
voidsyscall_init (void) {
intr_register_int (0x30, 3, INTR_ON,
halt ();
syscall_handler, "syscall");
}
}
static void
syscall_handler (struct intr_frame *f UNUSED)
userprog/syscall.c printf ("system call!\n");
get a name of the system callthread_exit ();
! f->esp – stack pointer
SYS_HALT from the stack}
use power_off()
Lab 2::Useful Files for Shutdown
• You have to have a look at:
– pintos/src/lib/user/syscall[.h|.c] – the wrapper…
– userprog/syscall[.h|.c] – Your implementation of system
calls!!!
– threads/interrupt.[h|c] – important structures!!!
– lib/syscall-nr.h – system call constants
–filesys/filesys.[h|c] Pintos file system implementation…
– examples/lab2test.c – the “official” test program for this lab
– filesys/file.[h|c] – useful functions for operations with files.
Things which you don’t find in “filesys”, you find here
–userprog/process.c Look up what is here and tell me…
Pintos Stack (1)
51
W
hy
”?
4
“
Pintos Stack (2)
f->esp
f->esp + 4
f->esp + 8
f->esp + 12
…
52
Lab 2::Create Example
• bool create (const char *file, unsigned
initial_size)
• Example: create(“file.txt”, 1000);
How to get them?
Answer: f->esp
Hint:
… note that, in order to get
How to return a value?
a string, you will need get a void pointer
Answer: f->eax
from esp and then get a char pointer to which
points that void pointer. The char pointer will point to the first
element of the string …
f->esp
54
Lab 2::Create Example
• To implement the system calls, which operate
with files, look at “filesys/filesys.[h|c]” and
“filesys/file.[h|c]”.
• Everything is already done there for you! Just
call the functions…
So simple? Not yet…
Memory issues!!!
All the pointers on the variables,
which you get from the user program,
must be validated!
Problem 1: If the pointer above PHYS_BASE,
It points to Kernel memory! UNSAFE!
57
Memory Issues in Pintos
Kernel VM
Physical Memory
Kernel process
PHYS_BASE
User process
Page directory
If no entry?
a)Kill user
b) Handle page fault
Lab 2::Memory Issues in Pintos
Kernel VM
Physical Memory
Kernel process
PHYS_BASE
Check if the pointer is below
User process
Page directory
Check if the pointer is in the page directory
If no entry?
a)Kill user
b) Handle page fault
Conclusions
•
•
•
•
•
Introduction to Pintos and labs in general
Labs 00, 0, and 1
Lab 2 (selected parts)
TO DO: Prepare Quiz until the next lesson
Deadline for Lab #1 is 30th of January
60
Download