GSoC'21 Final Report
Project: Syzkaller improvements
Student: Simran Kathpalia
Github: simran-kathpalia
Project Description
Goal: To enhance the existing state of syzkaller support in FreeBSD.
To achieve this, the project was divided into subtasks:-
- Adding syscalls and device drivers to syzkaller.
- Automating the generation of syscalls and ioctl calls.
- Fuzzing FreeBSD’s Linux compatibility layer.
- Improving fuzzing for subsystems(USB traffic).
- Patching syzkaller reported bugs.
Syscall descriptions
- I looked into the syscall support of NetBSD and extracted the syscalls which were missing from FreeBSD. These could be easily added to FreeBSD with slight tweaking.
Next, I looked into coverage of FreeBSD syscalls and got a list of missing syscalls.
- Some of the major groups of syscalls added to syzkaller are:
I could increase the syscall coverage of syscalls added under FreeBSD to syzkaller by 9 percent.
Device drivers
Added a bunch of device drivers:-
- Manually
- Checked each man page and corresponding header and C files in FreeBSD source, to get all the ioctl calls for a selected device driver. Next, I got the associated structures, unions, and flags to the ioctl call. Followed the documentation which describes rules for writing syscall descriptions. Compiled all the ioctl calls for the device driver into a file.
- The ioctl calls added:
bpf(4) along with necessary path change.
- Automated
An existing tool(sys2syz) which is used to extract descriptions for NetBSD, was modified to also support FreeBSD. It extracts the ioctl calls and their arguments from header files, compiles the kernel to get the type and macros, and then converts into the format supported by syzkaller. The tool will soon be integrated with the original repository.
- The ioctls tested in FreeBSD and then added to syzkaller:
Linuxlator fuzzing
Linuxulator fuzzing is basically fuzzing the linux binary compatibility layer (mechanism to run unmodified Linux binaries under FreeBSD). It is similar to how 32 bit FreeBSD binaries run on 64 bit FreeBSD kernel. Currently, in syzkaller, there are three tuples that define the whole target OS. These are TARGETOS, TARGETARCH, TARGETVMARCH. To fuzz the 32 bit compatibility layer, we pass arguments as TARGETOS=FreeBSD, TARGETARCH=i386, and TARGETVMARCH=amd64.
To fuzz the Linux compatibility layer, the idea is to add a 4th tuple to define the target which now makes the whole target OS as TARGETOS, TARGETVMOS, TARGETARCH, TARGETVMARCH. Using this we can fuzz 64 bit Linux layer (linux, freebsd, amd64, amd64) or even 32 bit Linux layer (linux, freebsd, i386, amd64).
With the help of my mentor, I split up the original TARGETOS into TARGETOS or TARGETVMOS, making it target the right kernel interface. The syz-manager fuzzes the FreeBSD itself but it has to target the Linux layer inside. I inspected quite a few occurrences of TARGETOS and subsequently made changes. There is still some amount of testing to be done but is near completion.
Here is the updated work: Latest fork
Bugs reported
There are quite a few bugs reported by syzkaller as a result of adding the description for syscalls and device drivers. Some are already patched some are yet to be patched.
From sigtimedwait(2):-
https://syzkaller.appspot.com/bug?id=d04fa6fedd4529fae5ab99771ccc402d72602618
https://syzkaller.appspot.com/bug?id=b12f0c4dc1e73c25636e4c4d4787209d155cca0a
From crypto(4):-
https://syzkaller.appspot.com/bug?extid=007341439ae295cee74f
https://syzkaller.appspot.com/bug?id=0c6b2567feb1563105cd95da2a03a1122bd37890
https://syzkaller.appspot.com/bug?id=53246f1d9a11588c630ff9e2676551ee0a2757a4
https://syzkaller.appspot.com/bug?id=9c74fee9d6ceabfff73819e94328a18723217cf9
https://syzkaller.appspot.com/bug?id=284ea5a644f5ff5750cc2fd2f10fb0c387e9c032
https://syzkaller.appspot.com/bug?id=6b67987da83c93586bb6a3f1a69875ec96bb1086
https://syzkaller.appspot.com/bug?id=2d87c3da8c5be955513e6949a11904d660a1a189
https://syzkaller.appspot.com/bug?id=6a2c83effe3aa29e49b545afbe0a8c89a1c67f9b
From aio(4):- https://syzkaller.appspot.com/bug?id=014369febb828b519ce5094bcec5a2c46bd991ad
From md(4):- https://syzkaller.appspot.com/bug?id=287c28a7c9cc6a0be01eed27d6e61c14a5d305ad
Additional patches:-
https://cgit.freebsd.org/src/commit/?id=9246b3090cbc82c54350391601b9acef2aa9a625
https://cgit.freebsd.org/src/commit/?id=70dd5eebc025badb7b835dfee3915d8b5f1e7468
Patching of kernel bugs
I worked on two kernel bugs reported by syzkaller which were found with KMSAN (Kernel Memory SANitizer) enabled. They were both based on the usage of uninitialized memory. I could build the kernel with KMSAN enabled and reproduce the bug. With the help of kgdb and basic debugging, I could detect the point of the trigger of the panic. I was able to patch one of the bugs and had a basic understanding of the other one. One was located in the crypto device driver which was triggering a panic because of an uninitialized value being passed to another variable. This was due to a missing check for MAC (digest) in case mac was not provided by userspace. Here’s the patch I added. The other was located in get_socketop() where one of the socket options was not initialized properly and thus triggering a panic. This was found and patched by another developer.
Work Left
The main objective of the project was to increase FreeBSD’s coverage and all the work has been done in this direction. However, there is still a task left which is one of many ways to increase the coverage. One of the tasks was to look into external USB fuzzing which has not been addressed yet. But I plan to look into it.
Future
GSoC was a tremendous learning experience for me, wherein I worked on a fuzzer and understood the logic behind it. I dealt with a lot of syscalls and device drivers and their applications and working. I also got to learn about kernel bugs and how to debug them. Overall, it was an immensely steep learning curve, concentrated in the last few months.
I plan on staying in touch with my mentors and finishing up the rest of the project. And if possible, work on patching more kernel related bugs. My mentor has been very helpful and supportive, which makes me more excited about working with him in the future.