aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorDmitry Vyukov <dvyukov@google.com>2016-02-18 21:41:40 +0100
committerDmitry Vyukov <dvyukov@google.com>2016-02-18 21:41:40 +0100
commit87d7cc4d27a2ae64a48cbad48e21369448841e1f (patch)
tree8b3b0ebaf03c09ab4e73831428e339ae4be4b53c
parent68c7a49a96b970897db5f61dd618382b5fe18ec0 (diff)
parent548b4a94a3e936aab2f8a519bb0e54b9ab4dc476 (diff)
Merge pull request #21 from daviddrysdale/doc-update
Some doc & diagnostic updates
-rw-r--r--README.md53
-rw-r--r--structure.pngbin47084 -> 43259 bytes
-rw-r--r--syz-fuzzer/fuzzer.go5
-rw-r--r--syz-manager/cover.go6
-rw-r--r--syz-manager/manager.go4
5 files changed, 63 insertions, 5 deletions
diff --git a/README.md b/README.md
index dbcf7fa06..ad288b535 100644
--- a/README.md
+++ b/README.md
@@ -40,6 +40,9 @@ This is all implemented in [this coverage patch](https://github.com/dvyukov/linu
once the patch is applied, the kernel should be configured with `CONFIG_KCOV` plus `CONFIG_KASAN`
or `CONFIG_KTSAN`.
+(Note that if the kernel under test does not include support for all namespaces, the `dropprivs`
+configuration value should be set to `false`.)
+
### QEMU Setup
Syzkaller runs its fuzzer processes inside QEMU virtual machines, so a working QEMU system is needed
@@ -95,6 +98,9 @@ following keys in its top-level object:
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`.
+ - `dropprivs` : Whether the executor program should try to use namespaces to drop privileges
+ before executing (requires a kernel built with `CONFIG_NAMESPACES`, `CONFIG_UTS_NS`,
+ `CONFIG_USER_NS`, `CONFIG_PID_NS` and `CONFIG_NET_NS`).
- `enable_syscalls`: List of syscalls to test (optional).
- `disable_syscalls`: List of system calls that should be treated as disabled (optional).
- `suppressions`: List of regexps for known bugs.
@@ -151,4 +157,51 @@ open_mode = S_IRUSR, S_IWUSR, S_IXUSR, S_IRGRP, S_IWGRP, S_IXGRP, S_IROTH, S_IWO
The description is contained in [sys/sys.txt](sys/sys.txt) file.
+## Troubleshooting
+
+Here are some things to check if there are problems running syzkaller.
+
+ - Check that QEMU can successfully boot the virtual machine. For example,
+ if `IMAGE` is set to the VM's disk image (as per the `image` config value)
+ and `KERNEL` is set to the test kernel (as per the `kernel` config value)
+ then something like the following command should start the VM successfully:
+
+ ```qemu-system-x86_64 -hda $IMAGE -m 256 -net nic -net user,host=10.0.2.10,hostfwd=tcp::23505-:22 -enable-kvm -kernel $KERNEL -append root=/dev/sda```
+
+ - Check that inbound SSH to the running virtual machine works. For example, with
+ a VM running and with `SSHKEY` set to the SSH identity (as per the `sshkey` config value) the
+ following command should connect:
+
+ ```ssh -i $SSHKEY -p 23505 root@localhost```
+
+ - Check that the `CONFIG_KCOV` option is available inside the VM:
+ - `ls /sys/kernel/debug # Check debugfs mounted`
+ - `ls /sys/kernel/debug/kcov # Check kcov enabled`
+ - Build the test program from `Documentation/kcov.txt` and run it inside the VM.
+
+ - Check that debug information (from the `CONFIG_DEBUG_INFO` option) is available
+ - Pass the hex output from the kcov test program to `addrline -a -i -f -e $VMLINUX` (where
+ `VMLINUX` is the vmlinux file, as per the `vmlinux` config value), to confirm
+ that symbols for the kernel are available.
+
+ - Use the `-v N` command line option to increase the amount of logging output, from both
+ the `syz-manager` top-level program and the `syz-fuzzer` instances (which go to the
+ output files in the `crashes` subdirectory of the working directory). Higher values of
+ N give more output.
+
+ - If logging indicates problems with the executor program (e.g. `executor failure`),
+ try manually running a short sequence of system calls:
+ - Build additional tools with `make all-tools`
+ - Copy `syz-executor` and `syz-execprog` into a running VM.
+ - In the VM run `./syz-execprog -executor ./syz-executor -debug sampleprog` where
+ sampleprog is a simple system call script (e.g. just containing `getpid()`).
+ - For example, if this reports that `clone` has failed, this probably indicates
+ that the test kernel does not include support for all of the required namespaces.
+ In this case, running the `syz-execprog` test with the `-nobody=0` option fixes the problem,
+ so the main configuration needs to be updated to set `dropprivs` to `false`.
+
+
+## Disclaimer
+
This is not an official Google product.
+
diff --git a/structure.png b/structure.png
index 4ca456957..b08a63688 100644
--- a/structure.png
+++ b/structure.png
Binary files differ
diff --git a/syz-fuzzer/fuzzer.go b/syz-fuzzer/fuzzer.go
index 7942a6cab..87fd6b9cb 100644
--- a/syz-fuzzer/fuzzer.go
+++ b/syz-fuzzer/fuzzer.go
@@ -97,7 +97,7 @@ func main() {
fmt.Fprintf(os.Stderr, "-output flag must be one of none/stdout/dmesg/file\n")
os.Exit(1)
}
- logf(0, "started")
+ logf(0, "fuzzer started, log level %v", *flagV)
corpusCover = make([]cover.Cover, sys.CallCount)
maxCover = make([]cover.Cover, sys.CallCount)
@@ -496,11 +496,12 @@ retry:
panic(err)
}
try++
+ logf(4, "fuzzer detected executor failure='%v', retrying #%d\n", err, (try + 1))
debug.FreeOSMemory()
time.Sleep(time.Second)
goto retry
}
- logf(4, "result failed=%v hanged=%v:\n%v\n", failed, hanged, string(output))
+ logf(2, "result failed=%v hanged=%v:\n%v\n", failed, hanged, string(output))
cov := make([]cover.Cover, len(p.Calls))
for i, c := range rawCover {
cov[i] = cover.Cover(c)
diff --git a/syz-manager/cover.go b/syz-manager/cover.go
index bc99f3da8..efeb14795 100644
--- a/syz-manager/cover.go
+++ b/syz-manager/cover.go
@@ -29,7 +29,11 @@ func generateCoverHtml(w io.Writer, vmlinux string, cov []uint32) error {
return err
}
if len(info) == 0 {
- return fmt.Errorf("vmlinux does not have debug info (set CONFIG_DEBUG_INFO=y)")
+ if len(cov) == 0 {
+ return fmt.Errorf("No coverage data available")
+ } else {
+ return fmt.Errorf("'%s' does not have debug info (set CONFIG_DEBUG_INFO=y)", vmlinux)
+ }
}
var d templateData
diff --git a/syz-manager/manager.go b/syz-manager/manager.go
index ffb184936..075b3127a 100644
--- a/syz-manager/manager.go
+++ b/syz-manager/manager.go
@@ -207,8 +207,8 @@ func (mgr *Manager) runInstance(vmCfg *vm.Config, first bool) bool {
leak := first && mgr.cfg.Leak
// Run the fuzzer binary.
- outputC, errorC, err := inst.Run(time.Hour, fmt.Sprintf("%v -executor %v -name %v -manager %v -output=%v -procs %v -leak=%v -cover=%v -nobody=%v",
- fuzzerBin, executorBin, vmCfg.Name, fwdAddr, mgr.cfg.Output, mgr.cfg.Procs, leak, mgr.cfg.Cover, mgr.cfg.DropPrivs))
+ outputC, errorC, err := inst.Run(time.Hour, fmt.Sprintf("%v -executor %v -name %v -manager %v -output=%v -procs %v -leak=%v -cover=%v -nobody=%v -v %d",
+ fuzzerBin, executorBin, vmCfg.Name, fwdAddr, mgr.cfg.Output, mgr.cfg.Procs, leak, mgr.cfg.Cover, mgr.cfg.DropPrivs, *flagV))
if err != nil {
logf(0, "failed to run fuzzer: %v", err)
return false