You’ll use two sets of tools in this class: QEMU, a machine emulator for running your kernel; and a compiler toolchain, including assembler, linker, C compiler, and debugger, for compiling and testing your kernel.
You have two options to install your development environment. Please take care of this as soon as the semester starts as it can take some time to get familiar with the environment. There is technically a third option whereby you install all software and dependencies manually on Linux or Mac, but this is not officially supported.
We recommend the use of Docker Desktop, if your personal machine:
is reasonably new (maybe 4 years),
is reasonably up to date,
has adequate free disk space (ten gigabytes should do it).
Follow the installation instructions.
While Docker Desktop should work fine on most machines, it is possible that you may run into errors. Do not ask course staff to help you debug issues; instead, please use Option 2
which will rely on Duke VCM.
We have reserved a set of virtual machines (VMs) on Duke VCM. You first need to figure out how to ssh into the VM; if you are unfamiliar with this, please see the Duke VCM SSH Guide.
To run Docker, you will have to either add yourself to the docker group, or prefix commands with sudo
so that the commands run as root. Otherwise, if you don’t do this, you will see permission denied errors.
I recommend adjusting groups, since it is a simple, one-time process. Please run the following commands (you’ll have to enter your Duke NetID password when prompted):
$ sudo adduser $(whoami) docker
$ newgrp docker
Now, if you run the groups
command, you should see docker listed.
Docker constructs the environment for building and running course projects. Under the hood, Docker launches a container that runs alongside the host operating system, managing all dependencies and software requirements. We provide a standard Docker image on Dockerhub, which supports a RISC-V environment for the labs. The container runs bash with user student. The password of the user is also student.
Each lab will rely on the same base repo that contains all of the necessary files (e.g., xv6, grading scripts). Please clone the base repo in your host system (i.e., your personal machine or Duke VCM) before you start. Follow the git instructions to learn how to clone the base repo. Once you have the base repo cloned, you can start a new Docker container by running:
The following commands specify default architecture tags (amd64 or arm64) for given host operating systems. However, it is possible that your own personal system deviates from this. Typically, arm64 should only be used if you have a M1/M2 MacBook; otherwise, use amd64.
On Mac (Intel):
$ cd <PathToBaseRepo>
$ docker run -it --rm -v $PWD:/home/student/labs mlentz/os-env:amd64
On Mac (M1/M2):
$ cd <PathToBaseRepo>
$ docker run -it --rm -v $PWD:/home/student/labs mlentz/os-env:arm64
On Linux (i.e., VCM):
$ cd <PathToBaseRepo>
$ docker run -it --rm --user 0:0 -v $PWD:/home/student/labs mlentz/os-env:amd64
On Windows Powershell:
$ cd <PathToBaseRepo>
$ docker run -it --rm -v ${PWD}:/home/student/labs mlentz/os-env:amd64
On Windows Cmd:
$ cd <PathToBaseRepo>
$ docker run -it --rm -v "%cd%":/home/student/labs mlentz/os-env:amd64
This command also maps the xv6 repository directory into /home/student/labs
inside your container. If successful, you should see the following output from the container:
To run a command as administrator (user "root"), use "sudo <command>".
See "man sudo_root" for details.
student@a8ff1cc22700:~/labs$
The shell prompt (student@a8ff1cc22700:~/labs$
) consists of the username (student
), hostname (a8ff1cc22700
), and current working directory (/home/student/labs
or ~/labs
). The hostname is the same as the container ID, so it may differ from the above example.
All of the kernel-oriented labs rely on the xv6 teaching OS. The Docker container will support building and running xv6 wit QEMU. To do this, run the following commands:
student@a8ff1cc22700:~/labs$ make
...
student@a8ff1cc22700:~/labs$ make qemu
...
xv6 kernel is booting
hart 2 starting
hart 1 starting
init: starting sh
$
At this point, you are now in a shell hosted by the xv6 OS. You can run any available user-space programs (e.g., ls).
To exit from xv6 and return to the Docker container, type ctrl-a followed by x.
Now you are free to start working on your lab. The lab repo in your host system is mounted into the docker container, so you can open the repo with any editor of your choice on your host system (e.g., VSCode, vim, emacs). All the modifications will be reflected in the Docker container automatically.
If you are using a VCM machine, you can use VSCode and the Remote-SSH plugin to connect to you VCM machine.
If you are using VCM and followed the above, this is what the setup process looks like end-to-end (including some key management commands for accessing Gitlab):
ml579@vcm-34842:~$ sudo adduser $(whoami) docker
[sudo] password for ml579:
Adding user `ml579' to group `docker' ...
Adding user ml579 to group docker
Done.
ml579@vcm-34842:~$ newgrp docker
ml579@vcm-34842:~$ groups
docker ml579
ml579@vcm-34842:~$ ssh-keygen -t rsa -b 4096
...
ml579@vcm-34842:~$ cat ~/.ssh/id_rsa.pub
...
<NOTE: The output from the cat command should be used to add an SSH key to your Gitlab account.>
ml579@vcm-34842:~$ git clone git@gitlab.oit.duke.edu:os-course/xv6.git
Cloning into 'xv6'...
The authenticity of host 'gitlab.oit.duke.edu (152.3.101.106)' can't be established.
ED25519 key fingerprint is SHA256:xQqapKwMlcb/u8ZGJAwnMHrLB4YOH5HjebWd7Ep4sCs.
This key is not known by any other names
Are you sure you want to continue connecting (yes/no/[fingerprint])? yes
Warning: Permanently added 'gitlab.oit.duke.edu' (ED25519) to the list of known hosts.
remote: Enumerating objects: 7669, done.
remote: Counting objects: 100% (9/9), done.
remote: Compressing objects: 100% (9/9), done.
remote: Total 7669 (delta 3), reused 0 (delta 0), pack-reused 7660
Receiving objects: 100% (7669/7669), 16.96 MiB | 50.62 MiB/s, done.
Resolving deltas: 100% (3929/3929), done.
ml579@vcm-34842:~$ cd xv6/
ml579@vcm-34842:~$ docker run -it --rm --user 0:0 -v $PWD:/home/student/labs mlentz/os-env:amd64
root@09415f6351a7:~/labs# make
...
root@09415f6351a7:~/labs# make qemu
...
xv6 kernel is booting
hart 1 starting
hart 2 starting
init: starting sh
$ ls
. 1 1 1024
.. 1 1 1024
README 2 2 2226
xargstest.sh 2 3 93
...