Qemu code fault automatic discovery with symbolic search Paul Marinescu, Cristian Cadar, Chunjie Zhu, Philippe Gabriel
Goals of this presentation Introduction of KLEE (symbolic execution tool) Qemu fault/patch retrospective Understand how Qemu-dm works Qemu code check by symbolic execution Work on the way
Introduction of KLEE (symbolic execution tool) - 1 https://github.com/klee/klee klee_make_symbolic(&a, sizeof (a), “a”) klee_make_symbolic(&b, sizeof (b), “b”) int foo(int x, int y) { int ret = 0; if (x + y < 15) { if (y != 10) ret = 1; else ret = 2; } else { if (y != 10) ret = 3; else ret = 4; } return ret; } foo(a, b);
Introduction of KLEE (symbolic execution tool) - 2 https://github.com/klee/klee See real execution paths explored by KLEE test000001.ktest test000002.ktest test000003.ktest test000004.ktest (int32 overflow) args : ['test.o'] args : ['test.o'] args : ['test.o'] args : ['test.o'] num objects: 2 num objects: 2 num objects: 2 num objects: 2 object 0: name: b'a' object 0: name: b'a' object 0: name: b'a' object 0: name: b'a' object 0: size: 4 object 0: size: 4 object 0: size: 4 object 0: size: 4 object 0: data: object 0: data: 0 object 0: data: object 0: data: 2147483635 object 1: name: b'b' 2110308033 2147483640 object 1: name: b'b' object 1: size: 4 object 1: name: b'b' object 1: name: b'b' object 1: size: 4 object 1: data: 0 object 1: size: 4 object 1: size: 4 object 1: data: 10 object 1: data: object 1: data: 10 37170385
Introduction of KLEE (symbolic execution tool) - 3 https://github.com/klee/klee How does KLEE work compile target program to LLVM bitcode core engine plays the role of a virtual machine for LLVM bitcode symbolic execution traverses as many possible code paths in a given time budget (dead loop?) 1. depth-first search/breadth-first search/non-uniform-random search 2. query-cost-optimization/code-coverage-optimization requests constraint solver to give a solution once run into code branch special case handling 1. constraint solver does not support symbolic-sized objects, e.g. malloc(size) external environment modeling (e.g. file system access) one test case is generated once a code path reaches its end or encounters an error replay the test case after klee code check is completed
Introduction of KLEE (symbolic execution tool) - 4 https://github.com/klee/klee Successful story ( see http://llvm.org/pubs/2008-12-OSDI-KLEE.pdf )
Qemu fault/patch retrospective - 1 Qemu buffer overflow CVE-2015-4106, does not restrict PCI config space write access for PCI pass-through CVE-2015-3456, floppy disk controller issue CVE-2015-2752, XEN_DOMCTL_memory_mapping hypercall issue others Postmortem idea to spot any potential vulnerability automatically?
Qemu fault/patch retrospective - 2 Solutions fuzz testing a) treat Qemu as a black box b) generate random input to Qemu, easy to implement c) a very hard time reaching some code paths (e.g. int32 x == 764387, 1/2^32 chance to hit the branch without any guidance) d) not reproducible symbolic execution a) have internal state representation of Qemu b) generate stable test case to reproduce any code fault c) higher code coverage d) difficult to adopt
Understand how Qemu-dm works - 1
Understand how Qemu-dm works - 2 guest os <-> xen hypervisor xen-hypervisor <-> qemu process (qemu calls libxc to map the shared memory into its own virtual guest os issues “IN AL, 0x10” memory address space at startsup) VM exit traps guest os into hypervisor qemu event loop polls ioreq from queue hypervisor packages an ioreq and fills it into qemu gets an ioreq and parse it (0x10, read, ioreq queue (shared memory between memory to store 0x10 data) hypervisor and qemu), notifies qemu to handle qemu calls xen_platform ioport read function this request and waits the io instruction done (hypervisor schedules other task to execute on (xen_platform registers ioport 0x10) CPU, but does not block forever) qemu writes the data into the memory block qemu gives response, hypervisor reads the data (ioreq contains a memory point which is used to out, and then copies it to guest os registers in store the data) VMCS (See x86 VT-x spec) qemu notifies hypervisor that job is done
Qemu code check by symbolic search Rebuild Qemu in LLVM bitcode (libxc dependencies?) Minimal Qemu image necessary load/startup instructions ioport in/out instructions Run check klee core engine loads Qemu LLVM bitcode and the minimal image klee generates input and traverses Qemu program state space klee records the input sequence (change on klee?) watchdog monitor, restart if klee terminates when it runs into Qemu code fault code coverage report? Alternative option start Qemu from an actual instruction trace and treat various instruction arguments as symbolic input, see if some input causes errors
Work on the way Rebuild Qemu remove dependency stub libxc? klee libxc modeling? achievement boot toy OS using klee and do some initial symbolic checks KLEE symbolic variable input -> instruction input? restart after crash, next crash at the same location? (using klee seeds) others We are still on the way ...
Q & A Thanks. Questions?
Recommend
More recommend