2015-10-12 08:16:57 +00:00
|
|
|
# syzkaller - linux syscall fuzzer
|
|
|
|
|
2015-10-12 15:15:57 +00:00
|
|
|
`syzkaller` is a distributed, unsupervised, coverage-guided Linux syscall fuzzer.
|
|
|
|
It is meant to be used with [KASAN](https://www.kernel.org/doc/Documentation/kasan.txt) (`CONFIG_KASAN=y`),
|
|
|
|
[KTSAN](https://github.com/google/ktsan) (`CONFIG_KTSAN=y`),
|
2015-10-12 08:16:57 +00:00
|
|
|
or [KUBSAN] (http://developerblog.redhat.com/2014/10/16/gcc-undefined-behavior-sanitizer-ubsan/) ([patch](https://lkml.org/lkml/2014/10/20/181)).
|
|
|
|
|
2015-12-09 14:16:40 +00:00
|
|
|
Project mailing list: [syzkaller@googlegroups.com](https://groups.google.com/forum/#!forum/syzkaller).
|
2015-10-12 08:16:57 +00:00
|
|
|
|
2015-10-12 09:36:48 +00:00
|
|
|
List of [found bugs](https://github.com/google/syzkaller/wiki/Found-Bugs).
|
|
|
|
|
2015-10-12 08:16:57 +00:00
|
|
|
This is work-in-progress, some things may not work yet.
|
|
|
|
|
|
|
|
## Usage
|
|
|
|
|
2015-11-19 13:38:37 +00:00
|
|
|
Various components are needed to build and run syzkaller.
|
|
|
|
|
|
|
|
- C compiler with coverage support
|
|
|
|
- Linux kernel with coverage additions
|
|
|
|
- QEMU and disk image
|
|
|
|
- The syzkaller components
|
|
|
|
|
|
|
|
Setting each of these up is discussed in the following sections.
|
|
|
|
|
|
|
|
### C Compiler
|
|
|
|
|
|
|
|
Syzkaller is a coverage-guided fuzzer and so needs the kernel to be built with coverage support.
|
2015-12-04 18:32:35 +00:00
|
|
|
Therefore, a recent upstream version of GCC is needed. Coverage support is submitted to gcc in
|
|
|
|
revision 231296. Sync past it and build fresh gcc.
|
2015-11-19 13:38:37 +00:00
|
|
|
|
|
|
|
### Linux Kernel
|
|
|
|
|
|
|
|
As well as adding coverage support to the C compiler, the Linux kernel itself needs to be modified
|
|
|
|
to:
|
2015-12-21 12:37:04 +00:00
|
|
|
- add support in the build system for the coverage options (under `CONFIG_KCOV`)
|
|
|
|
- add extra instrumentation on system call entry/exit (for a `CONFIG_KCOV` build)
|
2015-11-19 13:38:37 +00:00
|
|
|
- add code to track and report per-task coverage information.
|
|
|
|
|
2015-12-04 18:32:35 +00:00
|
|
|
This is all implemented in [this coverage patch](https://github.com/dvyukov/linux/commits/kcov);
|
2015-12-17 15:20:12 +00:00
|
|
|
once the patch is applied, the kernel should be configured with `CONFIG_KCOV` plus `CONFIG_KASAN`
|
2015-11-19 13:38:37 +00:00
|
|
|
or `CONFIG_KTSAN`.
|
|
|
|
|
|
|
|
### QEMU Setup
|
|
|
|
|
|
|
|
Syzkaller runs its fuzzer processes inside QEMU virtual machines, so a working QEMU system is needed
|
|
|
|
– see [QEMU docs](http://wiki.qemu.org/Manual) for details.
|
|
|
|
|
|
|
|
In particular:
|
|
|
|
|
|
|
|
- The fuzzing processes communicate with the outside world, so the VM image needs to include
|
|
|
|
networking support.
|
|
|
|
- The program files for the fuzzer processes are transmitted into the VM using SSH, so the VM image
|
|
|
|
needs a running SSH server.
|
|
|
|
- The VM's SSH configuration should be set up to allow root access for the identity that is
|
2015-12-21 12:37:04 +00:00
|
|
|
included in the `syz-manager`'s configuration. In other words, you should be able to do `ssh -i
|
2015-11-19 13:38:37 +00:00
|
|
|
$SSHID -p $PORT root@localhost` without being prompted for a password (where `SSHID` is the SSH
|
2015-12-21 12:37:04 +00:00
|
|
|
identification file and `PORT` is the port that are specified in the `syz-manager` configuration
|
2015-11-19 13:38:37 +00:00
|
|
|
file).
|
2015-12-16 09:47:38 +00:00
|
|
|
- The kernel exports coverage information via a debugfs entry, so the VM image needs to mount
|
|
|
|
the debugfs filesystem at `/sys/kernel/debug`.
|
2015-11-19 13:38:37 +00:00
|
|
|
|
2016-01-07 12:16:20 +00:00
|
|
|
[create-image.sh](tools/create-image.sh) script can be used to create a suitable Linux image.
|
|
|
|
|
2015-11-19 13:38:37 +00:00
|
|
|
TODO: Describe how to support other types of VM other than QEMU.
|
|
|
|
|
|
|
|
### Syzkaller
|
|
|
|
|
|
|
|
The syzkaller tools are written in [Go](https://golang.org), so a Go compiler (>= 1.4) is needed
|
|
|
|
to build them. Build with `make`, which generates compiled binaries in the `bin/` folder.
|
|
|
|
|
|
|
|
## Configuration
|
|
|
|
|
2015-12-21 12:37:04 +00:00
|
|
|
The operation of the syzkaller `syz-manager` process is governed by a configuration file, passed at
|
2015-11-19 13:38:37 +00:00
|
|
|
invocation time with the `-config` option. This configuration can be based on the
|
2015-12-17 15:21:46 +00:00
|
|
|
[syz-manager/example.cfg](syz-manager/example.cfg); the file is in JSON format with the
|
2015-11-19 13:38:37 +00:00
|
|
|
following keys in its top-level object:
|
|
|
|
|
2015-12-21 12:37:04 +00:00
|
|
|
- `http`: URL that will display information about the running `syz-manager` process.
|
|
|
|
- `workdir`: Location of a working directory for the `syz-manager` process. Outputs here include:
|
2015-12-23 18:33:12 +00:00
|
|
|
- `<workdir>/instance-x`: per VM instance temporary files
|
2015-11-19 13:38:37 +00:00
|
|
|
- `<workdir>/crashes/crashN-T`: crash output files
|
2015-12-17 15:20:12 +00:00
|
|
|
- `<workdir>/corpus/*`: corpus with interesting programs
|
2015-12-23 18:33:12 +00:00
|
|
|
- `syzkaller`: Location of the `syzkaller` checkout.
|
2015-11-19 13:38:37 +00:00
|
|
|
- `vmlinux`: Location of the `vmlinux` file that corresponds to the kernel being tested.
|
2015-12-23 18:33:12 +00:00
|
|
|
- `type`: Type of virtual machine to use, e.g. `qemu` or `kvm`.
|
2015-11-19 13:38:37 +00:00
|
|
|
- `count`: Number of VMs to run in parallel.
|
2015-12-04 18:32:35 +00:00
|
|
|
- `procs`: Number of parallel test processes in each VM (4 or 8 would be a reasonable number).
|
|
|
|
- `leak`: Detect memory leaks with kmemleak (very slow).
|
2015-12-23 18:33:12 +00:00
|
|
|
- `kernel`: Location of the `bzImage` file for the kernel to be tested; this is passed as the
|
|
|
|
`-kernel` option to `qemu-system-x86_64`.
|
|
|
|
- `cmdline`: Additional command line options for the booting kernel, for example `root=/dev/sda1`.
|
|
|
|
- `image`: Location of the disk image file for the QEMU instance; a copy of this file is passed as the
|
|
|
|
`-hda` option to `qemu-system-x86_64`.
|
|
|
|
- `sshkey`: Location (on the host machine) of an SSH identity to use for communicating with
|
|
|
|
the virtual machine.
|
|
|
|
- `cpu`: Number of CPUs to simulate in the VM (*not currently used*).
|
|
|
|
- `mem`: Amount of memory (in MiB) for the VM; this is passed as the `-m` option to `qemu-system-x86_64`.
|
2015-11-23 16:01:47 +00:00
|
|
|
- `enable_syscalls`: List of syscalls to test (optional).
|
|
|
|
- `disable_syscalls`: List of system calls that should be treated as disabled (optional).
|
2015-12-04 18:32:35 +00:00
|
|
|
- `suppressions`: List of regexps for known bugs.
|
2015-11-19 13:38:37 +00:00
|
|
|
|
|
|
|
|
|
|
|
## Running syzkaller
|
|
|
|
|
2015-12-21 12:37:04 +00:00
|
|
|
Start the `syz-manager` process as:
|
2015-10-12 15:15:57 +00:00
|
|
|
```
|
2015-12-17 15:20:12 +00:00
|
|
|
./bin/syz-manager -config my.cfg
|
2015-10-12 15:15:57 +00:00
|
|
|
```
|
2015-10-12 08:16:57 +00:00
|
|
|
|
2015-11-19 13:38:37 +00:00
|
|
|
The `-config` command line option gives the location of the configuration file
|
|
|
|
[described above](configuration).
|
|
|
|
|
2015-12-17 15:20:12 +00:00
|
|
|
The `syz-manager` process will wind up qemu virtual machines and start fuzzing in them.
|
|
|
|
It also reports some statistics on the HTTP address.
|
2015-11-19 13:38:37 +00:00
|
|
|
|
2015-10-12 08:16:57 +00:00
|
|
|
|
|
|
|
## Process Structure
|
|
|
|
|
2015-11-19 13:38:37 +00:00
|
|
|
The process structure for the syzkaller system is shown in the following diagram; red labels
|
|
|
|
indicate corresponding configuration options.
|
|
|
|
|
|
|
|
![Process structure for syzkaller](structure.png?raw=true)
|
|
|
|
|
2015-12-17 15:20:12 +00:00
|
|
|
The `syz-manager` process starts, monitors and restarts several VM instances (support for
|
|
|
|
physical machines is not implemented yet), and starts a `syz-fuzzer` process inside of the VMs.
|
|
|
|
It is responsible for persistent corpus and crash storage. As opposed to `syz-fuzzer` processes,
|
|
|
|
it runs on a host with stable kernel which does not experience white-noise fuzzer load.
|
2015-10-12 08:16:57 +00:00
|
|
|
|
2015-12-17 15:20:12 +00:00
|
|
|
The `syz-fuzzer` process runs inside of presumably unstable VMs (or physical machines under test).
|
|
|
|
The `syz-fuzzer` guides fuzzing process itself (input generation, mutation, minimization, etc)
|
|
|
|
and sends inputs that trigger new coverage back to the `syz-manager` process via RPC.
|
|
|
|
It also starts transient `syz-executor` processes.
|
2015-10-12 08:16:57 +00:00
|
|
|
|
2015-12-17 15:20:12 +00:00
|
|
|
Each `syz-executor` process executes a single input (a sequence of syscalls).
|
|
|
|
It accepts the program to execute from the `syz-fuzzer` process and sends results back.
|
2015-10-12 08:16:57 +00:00
|
|
|
It is designed to be as simple as possible (to not interfere with fuzzing process),
|
|
|
|
written in C++, compiled as static binary and uses shared memory for communication.
|
|
|
|
|
|
|
|
## Syscall description
|
|
|
|
|
|
|
|
syzkaller uses declarative description of syscalls to generate, mutate, minimize,
|
|
|
|
serialize and deserialize programs (sequences of syscalls). Below you can see
|
|
|
|
(hopefully self-explanatory) excerpt from the description:
|
|
|
|
|
|
|
|
```
|
|
|
|
open(file filename, flags flags[open_flags], mode flags[open_mode]) fd
|
|
|
|
read(fd fd, buf buffer[out], count len[buf]) len[buf]
|
|
|
|
close(fd fd)
|
|
|
|
open_mode = S_IRUSR, S_IWUSR, S_IXUSR, S_IRGRP, S_IWGRP, S_IXGRP, S_IROTH, S_IWOTH, S_IXOTH
|
|
|
|
```
|
|
|
|
|
2015-12-17 15:21:46 +00:00
|
|
|
The description is contained in [sys/sys.txt](sys/sys.txt) file.
|
2015-10-12 08:16:57 +00:00
|
|
|
|
|
|
|
This is not an official Google product.
|