Operating Systems - Computer Sciencepxk/416/notes/content/04r-assignment-3.… · Assignment 2 –...
Transcript of Operating Systems - Computer Sciencepxk/416/notes/content/04r-assignment-3.… · Assignment 2 –...
Operating Systems
Week 3 Recitation:
Assignment 1 & 2 Review, Assignment 3 Discussion
Paul Krzyzanowski
Rutgers University
Spring 2015
1 February 14, 2015 © 2015 Paul Krzyzanowski
Assignment 1 – Question 1
• UEFI can parse a file system and load a multi-block file that contains
a bootloader.
• The BIOS could only read individual disk blocks. It does not know
anything about the structure of the file system.
– It reads a single disk disk block
– That one disk block contains
• partition map that identifies different areas of the disk (logical disks)
• a boot loader that reads N consecutive blocks from a specific partition
February 14, 2015 © 2015 Paul Krzyzanowski 3
Why does UEFI (the Unified Extensible Firmware Interface) not need to load a
first-stage boot loader from the Master Boot Record (MBR) and why did the
BIOS need to do so?
Assignment 1 – Question 2
• The design of the kernel is simpler
• Adding new services does not require modifying the kernel
• Better controls over security: drivers and other services don't wield supreme
power
There is also a downside: performance often suffers since many system calls
have to go to the kernel, be relayed to a user-level kernel process, back to the
kernel, and then back to the user.
February 14, 2015 © 2015 Paul Krzyzanowski 4
(a) What is the main advantage of the microkernel approach to system design?
(b) How do user programs and system services interact in a microkernel
architecture?
• Via interprocess communication mechanisms, such as messages.
Assignment 1 – Question 3 a-b
The code became about 33% bigger.
February 14, 2015 © 2015 Paul Krzyzanowski 5
a. By approximately how much did the size of the UNIX system increase when it
was rewritten in C in 1973?
b. What is a path name?
A sequence of directory names separated by slashes (/) and ending with a file
name.
Example: /usr/share/mysql/charsets/Index.xml
Assignment 1 – Question 3 c-d
1. File and device I/O are as similar as possible.
2. File and device names have the same syntax and meaning.
3. Special files (devices) are subject to the same protection mechanism as regular files.
February 14, 2015 © 2015 Paul Krzyzanowski 6
c. What are three advantages to treating devices as files within the file system?
d. What is the purpose of a set-user-ID bit in a file's permissions?
It allows privileged programs to access files that may be inaccessible to other
users.
Assignment 2 – Question 1
• Mechanism and policy must be separate to ensure that systems are
easy to modify.
• No two system installations are the same, so each installation may
want to tune the operating system to suit its needs.
• With mechanism and policy separate, the policy may be changed at
will while the mechanism stays unchanged.
• This arrangement provides a more flexible system.
February 14, 2015 © 2015 Paul Krzyzanowski 9
Why is the separation of mechanism and policy desirable?
Assignment 2 – Question 2
• When a process terminates, it moves to the zombie state and
remains in that state until the parent calls wait().
• At that time, the process ID as well as its entry in the process table
are both released – the exit state is returned with the return from wait
and is no longer retained by the kernel.
• However, if a parent does not invoke wait()
– the child process remains a zombie as long as the parent remains alive
– Once the parent process terminates, the init process becomes the new parent of the
zombie
– Periodically, the init process calls wait() which ultimately releases the Process ID
and entry in the process table of the zombie process.
February 14, 2015 © 2015 Paul Krzyzanowski 10
Explain the role of the init process on UNIX and Linux systems in regard to
process termination.
Assignment 2 – Question 3
8 processes.
1st fork: creates a child process – we have 2 processes
2nd fork: each process creates a child ⇒ 2 more processes ⇒ 4 total
3rd fork: each of 4 processes creates a child ⇒ 8 total
February 14, 2015 © 2015 Paul Krzyzanowski 11
Including the initial parent process, how many processes are created by the
following program? #include <unistd.h>
#include <stdio.h>
int
main(int argc, char **argv)
{
fork();
fork();
fork();
/* ... */
}
Assignment 2 – Question 4 a-b
In the past, Linux used a software interrupt (trap) – int 0x80 – to do the
mode switch.
February 14, 2015 © 2015 Paul Krzyzanowski 12
a. What mechanism did Linux used to use for invoking system calls (creating
the mode switch) on the x86 Intel architecture?
b. What mechanism is used to invoke system calls since the 2.6 kernel?
• On Intel architectures, the Linux kernel no longer uses the trap
mechanism but the SYSENTER/SYSEXIT instructions
Assignment 2 – Question 4 c
Performance. SYSENTER was much faster on Pentium 4 and later
processors.
More detail:
• INT accepts a parameter that identifies the entry in the interrupt vector table, which resides in
memory.
• When processing the int instruction, the processor has to read data from the interrupt vector table
– For example int 0x80 causes the function pointed to by the 128th (128 decimal == 0x80) entry in
the interrupt vector table to be executed.
• SYSENTER does not require consulting a table to take the jump
– The kernel registers the sysentry function handler by storing the address of the function into the
CPU Model Specific Register SYSENTER_EIP_MSR (0x175) when it starts up
– Whenever the sysenter instruction is executed, the CPU can get the target address directly from
a register
[ This is a simplification: there are two additional registers that may need to be set for sysenter ]
February 14, 2015 © 2015 Paul Krzyzanowski 13
c. Why was the system call mechanism changed?
Assignment 2 – Question 5
No.
A multithreaded system comprising of multiple user-level threads
cannot make use of the different processors in a multiprocessor system
simultaneously.
The operating system sees only a single process and will not schedule
the different threads of the process on separate processors.
Consequently, there is no performance benefit associated with
executing multiple user-level threads on a multiprocessor system.
February 14, 2015 © 2015 Paul Krzyzanowski 14
Can a multithreaded solution using multiple user-level threads achieve better
performance on a multiprocessor system than on a single- processor system?
Explain.
Assignment 3
• Download and build the xv6 operating system
• Run it under an x86 CPU emulator
• Add a new system call:
int trace(int)
– Turn system call tracing on/off
• trace(1): turn tracing on. Each system call from that process only will be
printed to the console
• trace(0): turn tracing off. System calls will no longer be printed to the
console
– Return total number of system calls for the process
• trace returns the total number of system calls called by the process so far
February 14, 2015 © 2015 Paul Krzyzanowski 16
Example output
• When tracing is on, each system call will result in one line
of text printed to the console
• Each line contains
– The process ID
– Command name
– System call number
– System call name
February 14, 2015 © 2015 Paul Krzyzanowski 17
...
pid: 2 [sh] syscall(5=read)
pid: 2 [sh] syscall(5=read)
pid: 2 [sh] syscall(1=fork)
pid: 2 [sh] syscall(3=wait)
pid: 3 [sh] syscall(12=sbrk)
pid: 3 [sh] syscall(7=exec)
pid: 3 [try] syscall(20=mkdir)
pid: 3 [try] syscall(15=open)
pid: 3 [try] syscall(16=write)
pid: 3 [try] syscall(21=close)
pid: 3 [try] syscall(2=exit)
pid: 2 [sh] syscall(16=write)
pid: 2 [sh] syscall(16=write)
...
Sample Output
What is xv6?
• UNIX v6
– Old version of UNIX from Bell Labs before networking was added to the OS
– Simple – not a lot of features
– Nicely documented source
– BUT: written in an obsolete version of C and with PDP-11 specific code
• xv6
– A rewrite of Unix v6 in ANSI C (standard C) for multicore Intel x86 processors
– Designed at MIT as a tiny OS suitable for teaching
– Same basic internal design as UNIX v6
• Kernel, processes, files & directories, memory protection, …
• Why not Linux?
– xv6 is a super-simple bare-bones OS – about 7K lines of code
– Linux: >20K lines of code
– with a lot of complexity due to features & optimizations
February 14, 2015 © 2015 Paul Krzyzanowski 18
What do you need to do?
• Follow the instructions in the homework posting!
• You need:
– QEMU: open source machine emulator
– git: to download the xv6 code
– A Linux system to run it on
• Search the web for instructions on cross compiling on OS X or Windows
if you don’t want to use Linux
• Instructions are provided to install VirtualBox (a virtual machine) and
Ubuntu Linux – that will ensure you have an environment that works on
your machine
• Rutgers iLab machines already have git; I’ll check about QEMU
• You will run xv6 on a machine emulator
– You won’t have to boot it natively and you can set breakpoints
February 14, 2015 © 2015 Paul Krzyzanowski 19
Install xv6
• Download the source from MIT git clone git://pdos.csail.mit.edu/xv6/xv6.git
• This will create a directory called xv6
– 98 files – no subdirectories or a separation between user program
files and kernel files
• Running make qemu will
– Compile everything (user + kernel)
– Start QEMU emulator
– Run the OS, which will start init, which will start the shell process
– The shell will give you a command prompt
February 14, 2015 © 2015 Paul Krzyzanowski 20
Several options for compiling & running xv6
• make qemu
– Build everything
– Start QEMU with the VGA console in a new window and the serial
console in your terminal
– Exit by closing the VGA window or ctrl-a x in your terminal
• make qemu-nox
– Build everything
– Run only the serial console
– Exit by pressing ctrl-a x
• make qemu-gdb and make qemu-nox-gdb
– Same as above but waits for a gdb (debugger) connection
February 14, 2015 © 2015 Paul Krzyzanowski 21
I use this since I ssh
to my Linux systems
Exiting QEMU
• This assignment is easy
– You’re unlikely to write code that will cause the kernel to die
– You won’t need to do register-level debugging or setting
breakpoints
• To switch between the console (running xv6) and the
QEMU emulator command prompt
– Type ctrl-a c
– Then you can type QEMU commands, such as
• info registers – to show CPU registers
• x/10i $eip – show the next 10 instructions at the current instruction
pointer
• system-reset – reset & reboot the system
• quit – exit the emulator (quit xv6)
– Type ctrl-a c again to get back to the console (unless you ran quit)
February 14, 2015 © 2015 Paul Krzyzanowski 22
Make sure xv6 is working!
• xv6 supports a hierarchical file system but boots up with only a tiny
number of files, all at the root level
• The only commands that come with the source are:
February 14, 2015 © 2015 Paul Krzyzanowski 23
cat print files to the standard output mkdir Create a directory
echo print command arguments rm Remove a file
forktest test process creation sh The shell
grep search for a string in a file stressfs Bunch of writes & reads
init The first process – starts the shell usertests Tests all system calls
kill Send a signal to a process wc Counts pages, lines, chars
ln Create a link to a file zombie Create a zombie process
ls List files
How to add a system call
• syscall.c – process system calls
– syscall(void) – entry function for all system calls
• This is the kernel function that is called for every system call
• System call number is in the eax register
• Check the range and call the corresponding function in the syscalls[]
table of functions
– Follow the example of other system calls to add your new one.
• sysproc.c – implements process-related system calls
– The functions here are called from syscall().
– You can add your new function in this file.
February 14, 2015 © 2015 Paul Krzyzanowski 24
How to add a system call
• usys.S – macros for assembler code for each sys call
– This simply places the system call number into the eax register and
invokes the system call.
– You need to add an entry to your system call here
• syscall.h – definitions of system call numbers
– You need to define a unique number for your system call
• user.h – user definition of system calls
– You need to define the user’s interface for your call here
February 14, 2015 © 2015 Paul Krzyzanowski 25
System call tracing
• You need to:
– Keep track of whether system call tracing is on or off for a process
– Count total number of system calls used by the process (irrespective of
whether tracing is on or off)
– Print a line to the console if tracing is on
• Storing per-process data
– xv6 stores its process control blocks in a process table (not a list)
struct proc
– You will need to extend this table to store the info you need
– Find where the entry is initialized to clear the values
• Printing a message to the console
– Use cprintf – just like printf!
cprintf(“Hello, I’m number %d\n”, num)
– Look at the proc struct – getting the program name is easy. You’re on your
own for printing the system call name
February 14, 2015 © 2015 Paul Krzyzanowski 26
Hints
• The assignment is easy – just a few lines of code
• You have 21 other system calls to use as a guide
• Write a test program
– Call a number of different system calls
– Turn tracing on/off
– Print system call counts
– Fork a child process to make sure it does not trace calls even if the
parent does
• There’s a detailed description of xv6 online:
http://pdos.csail.mit.edu/6.828/2014/xv6/book-rev8.pdf
short link: http://tinyurl.com/xv6-os
February 14, 2015 © 2015 Paul Krzyzanowski 27