* Your assessment is very important for improving the workof artificial intelligence, which forms the content of this project
Download Errors and Exception Handling
Plan 9 from Bell Labs wikipedia , lookup
Distributed operating system wikipedia , lookup
Burroughs MCP wikipedia , lookup
Security-focused operating system wikipedia , lookup
Unix security wikipedia , lookup
Linux kernel wikipedia , lookup
Spring (operating system) wikipedia , lookup
Errors and Exception Handling Tim Bisson Outline for Today Kernel Development Userspace C Debugging, error handling, and virtual machines Exception handling? C++ and Exception handling Kernel Development Implement abstract functionality to leverage physical devices Optimize physical resources (disk, memory, power) File Systems can optimize I/O access for mechanical nature of disks Debugging/developing OS functionality traditionally involved pressing the power-switch 100s of times per day Very time-consuming Kernel Debugging Printk - kernel-level printing Message classification KERN_DEBUG, KERN_CRIT, KERN_INFO, … printk(KERN_CRIT “Bug On\n"); Current process usually faults Drivers are usually the culprit, so process using that driver dies If your lucky, the system won’t panic Kernel Debugging KDB Serial Debugging Run on live system Two machines: test and development Communicate over gdb through serial port Many systems companies have some form of this infrastructure Core dumps Analyze stack trace off-line Kernel Development with Virtual Machines Virtual machines as test systems - when the break, they don’t panic the host system Speeds up kernel development Just reboot the virtual machines (like restarting an app) Booting is akin to application start-up Debugging is easier (run debugger on virtual machine) Useful for networking, fs, etc development Parallels, Xen UML Run Linux Kernel as a process in Linux Example using UML UML uses SIGSEGV to fault pages into the UML kernel handle SIGSEGV pass nostop noprint To ignore such signals when debugging a UML kernel Why get involved with opensource kernel development Contribute to an open source kernel project: Tons of cool projects to work on Linux, FreeBSD, NetBSD, DragonFlyBSD “Microsoft isn't evil, they just make really crappy operating systems.” - Linus Torvalds http://www.netbsd.org/contrib/projects.html http://wiki.dragonflybsd.org/index.cgi/ProjectsPage Looks really good on your resume… Apply to SoC ‘07 and get paid to work on an open-source kernel project for the summer Kernel Error Handling A difference between application and kernel programming is error handling Application segmentation faults are harmless Kernel faults can often be fatal for the whole system Drivers are typically responsible for OS failures Debugger can trace the error to source (gdb) They run in kernel address space Their quality is questionable Core OS subsystems have error handling too File System Error Handling Ext4 - new file system for Linux with many new features Extents allocation, preallocation, defragmentation, etc… Sets error code numbers: EIO, ENOMEM, ENOSPC Some error handlers Ext4_warning() Ext4-_error() Report failure conditions such as inconsistencies or read I/O failures Ext4_abort unrecoverable failures such as journal I/O or ENOMEM Unconditionally force file system into read-only mode or panic Ext4_decode_error() - errno values and return string File System Error Handling (2) ext4_warning() ext4_orphan_get() - error handling for bad orphan inodes ext4_handle_error() ext4_get_inode_block() - ensure selected block group < total block groups ext4_abort() ext4_journal_start_sb() - journalling aborted Goto Goto is also useful for aggregating error handling Free() is only called from one place int function() { int ret_val = -; char * data = (char * ) malloc (100); /* do some work */ if (error) { ret_val = error1; goto end; } /* do some more work */ if (error) { ret_val = error; goto end; } end: /* clean up*/ free (data); return ret_val; } Userland C and exception handling C doesn’t support exception handling It supports supports other functionality Assert Goto Signals Return/reason codes System Call/Library Errors When system call or library errors occur, the errno variable gets set Take a look at errno.h (“man errno”) for a list of possible numbers: EPERM Operation not permitted (POSIX.1) EIO Input/output error (POSIX.1) … Perror() Prints a message of describing last error that occurred Translates errors into human readable format Example Why does the program fail? #define SIZE 10 int main() { char buf[SIZE]; int ret, fd; Read(2) sets errno value to EBADF Perror(3) describes EBADF ret = read(fd,buf, SIZE); if (ret != SIZE) { perror("Read Error"); exit(1); } return 0; } bisson root # gcc this.c && a.out Read Error: Bad file descriptor Signal Handling The OS delivers an exception in the form of a software interrupt to an executing process process must handle event immediately Signals are defined by a number Processes may define signal handlers for a particular signals Function called when process receives that signal Asynchronous execution What good are signals for Report errors - invalid memory address reference Report asynchronous events Ctrl-c, ctrl-z, fg Alternative is event polling Example - srtgen A synthetic soft real-time application generator Use SIGINT (ctrl-c) to process current frame, dump stats, then exit atexit(3) - register a function to be called at normal process termination Int bool = 0; void sig_int (int s) { fprintf(stderr, “CTRL-C detected, aborting after this frame\n”); quit = 1; } void dumpstats() { /*prints application statistics*/ …. } int main (int argc, char **argv) { signal (SIGINT, sig_int); atexit(dumpstats); do { … }while(++numsamples < NUMSAMPLES && !quit); C++ and Exception Handling Try-Catch-Throw model Deals with synchronous and asynchronous errors Synchronous error example - divide by zero Put code that may generate an exception in a try block try { //code that might throw an exception } Throwing an Exception Indicates an exception occurred Specify one operand Exception object, if operand thrown is an object Exception caught by closest handler from try block in which exception thrown Control transferred to handler if (denominator == 0) throw DivideByZeroException(); Exception handler need not terminate program, but block where exception occurred is terminated Catching an Exception Exception handlers are the catch block Caught if argument type matches throw type If not, terminate (abort) called catch (DivideByZeroException ex) { cout << “Exception occurred: “ << ex.what() << endl; } Use catch(…) to catch all exceptions Simple Example int main () { char myarray[10]; try { for (int n=0; n<=10; n++) { if (n>9) throw "Out of range"; myarray[n]='z'; } } catch (char * str) { cout << "Exception: " << str << endl; } return 0; } Re-throwing an Exception Exception handler can handle some of the exception, then throw it to the calling function Uses throw; void throwException() { try { // Throw an exception and immediately catch it. cout << "Function throwException\n"; throw exception(); } catch( exception e ) { cout << "Exception handled in function throwException\n"; throw; // re-throw exception for further processing } cout << “This should not be print\n”; //control never gets here } void main( ) { try { throwException(); cout << “This should not be print\n”; //exception will be thrown } catch ( exception e ) { cout << "Exception handled in main" << endl; } cout << "Program control continues after catch in main" << endl; } Output: Function throwException Exception handled in function throwException Exception handled in main Program control continues after catch in main