[Kernel, courtesy IowaFarmer.com CornCam]

Readable Kernel Systems, Winter 2005

Project Descriptions

Verifiable Kernel

The security and reliability of any system depends at root on the security and reliability of its kernel. If the kernel fails to implement correct memory protection, for example, then any process might leak information or crash unexpectedly, because of memory corruption caused by other processes. Many of us have probably "proved" that a piece of code performs some function, safely -- that this function will return 4, for example:

int f(void) {
   return 2 + 2;

But that proof is contingent on a set of assumptions about the compiler and the hardware -- and, especially relevant for this class, the operating system.

The verifiable kernel project aims to build a kernel whose behavior is in some way verified. That is, a theorem prover has proven that the kernel code has some useful property -- that no process can inappropriately manipulate other processes' memory, for example. The goal is to reduce the set of assumptions on which a program's verification must depend. It's not necessary to eliminate all assumptions, however.

You might attack this project by picking some property you want to prove; developing a list of assumptions that imply the property holds; and then gradually change the kernel, and develop any necessary verification technology, so that more and more of the assumptions are verified. Take memory safety in an x86 OS, for example. The property might be:

A private page of memory owned by process P cannot be modified by processes other than P.

("Private" means that P has not explicitly granted page access to other processes through shared memory.) Here's a sample set of assumptions:

  1. The kernel itself manipulates memory safely (it contains no buffer-overrun or use-after-free bugs or the like).
  2. Memory page reference counts are correctly maintained.
  3. Whenever the kernel transfers control to a user process, the TLB is clean (it contains no old mappings).
  4. All user processes run at privilege level 3 (unprivileged).
  5. User processes can't modify page tables directly.
  6. User processes can't modify kernel code.
  7. User processes use sys_page_alloc to allocate memory pages.
  8. sys_page_alloc allocates fresh pages, to which no other process has access.
  9. ...

You see how we're going here. The project of the term would be to gradually pick off these assumptions, one by one, and prove them. For example, you could prove that sys_page_alloc allocates fresh pages, using a theorem prover. This might in turn require changing the kernel to help the theorem prover: adding an assert at the right place, for example.

This project requires a multi-function team, with some verification experts (or wannabe experts) and some kernel people.

Component Kernel

Most kernels are relatively monolithic, with deeply interlocked subsystems. Although they often have aspects of object-oriented systems, with devices and protocols and file system interfaces implemented as "objects" full of "virtual functions" (function pointers), each individual device, protocol, or file system uses many interfaces in the surrounding code. The interactions between different components are so complex that it's hard to really understand what's going on.

The goal of the component kernel project is to simplify a kernel subsystem by dividing it into fine-grained, modular components. These components should be smaller and simpler to understand than the high-level "objects" in today's kernels. The connections between components should probably be based on the flow of some data type, like memory pages, system calls, or disk blocks. To understand the functionality of the subsystem, you should be able to look just at the names of the components and how they're connected.

To get a feeling for how well this can work, check out the Click modular router, which did this for packet forwarding (routers and stuff).

Fault-resistant kernel


Profile-driven kernel optimizations


DDoS-free kernel


Kernel interpreter


Back to Readable Kernel Systems, Winter 2005