• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1## Headerparser
2
3headerparser is a tool that assists in writing device system call descriptions for syzkaller.
4
5In order to make syzkaller smarter when it comes to fuzzing a device node, you can provide it with
6information about the ioctl argument struct types it expects.
7
8However, in certain cases the number of argument struct types might be high, increasing the amount of manual
9effort that goes into writing the description files for the struct types.
10
11In order to ease the effort of writing ioctl argument type description files, headerlib does a best-effort job at generating them for you. You will still need to manually select the appropriate syzkaller data type from the list of types [here](https://github.com/google/syzkaller/blob/master/docs/syscall_descriptions_syntax.md).
12
13## Dependencies
14Headerlib uses pycparser. You can install pycparser using pip.
15
16```shell
17$ pip install pycparser
18```
19
20## Using headerparser
21```shell
22$ python headerparser.py --filenames=./test_headers/th_b.h
23B {
24          B1     len|fileoff|flags|intN     #(unsigned long)
25          B2     len|fileoff|flags|intN     #(unsigned long)
26}
27struct_containing_union {
28          something          len|fileoff|flags|int32                   #(int)
29          a_union.a_char     ptr[in|out, string]|ptr[in, filename]     #(char*)
30          a_union.B_ptr      ptr|buffer|array                          #(struct B*)
31}
32```
33
34You can copy paste the content underneath the `Structure Metadata` over to your syzkaller device description.
35
36## Something breaks
37Let us try parsing `test_headers/th_a.h` header file to generate argument structs.
38
39```shell
40$ python headerparser.py --filenames=./test_headers/th_a.h
41ERROR:root:HeaderFilePreprocessorException: /tmp/tmpW8xzty/source.o:36:2: before: some_type
42
43$ python headerparser.py --filenames=./test_headers/th_a.h --debug
44DEBUG:GlobalHierarchy:load_header_files : ['./test_headers/th_a.h']
45DEBUG:HeaderFilePreprocessor:HeaderFilePreprocessor._mktempfiles: sourcefile=/tmp/tmpbBQYhR/source.cobjectfile=/tmp/tmpbBQYhR/source.o
46DEBUG:HeaderFilePreprocessor:HeaderFilePreprocessor.execute: cp ./test_headers/th_a.h /tmp/tmpbBQYhR
47DEBUG:HeaderFilePreprocessor:HeaderFilePreprocessor.execute: gcc -I. -E -P -c /tmp/tmpbBQYhR/source.c > /tmp/tmpbBQYhR/source.o
48ERROR:root:HeaderFilePreprocessorException: /tmp/tmpbBQYhR/source.o:36:2: before: some_type
49```
50
51From the error message, we can see that the error occurs as pycparser is not aware of the type `some_type`. We can resolve this by making pycparser aware of the unknown type. In order to do this, we supply headerparser with a include file that contains C declarations and includes that can fix the parse error.
52
53```shell
54$ cat > include_file
55typedef int some_type;
56$ python headerparser.py --filenames=./test_headers/th_a.h --include=./include_file
57A {
58          B_item              ptr|buffer|array                          #(struct B*)
59          char_ptr            ptr[in|out, string]|ptr[in, filename]     #(char*)
60          an_unsigned_int     len|fileoff|int32                         #(unsigned int)
61          a_bool              _Bool                                     #(_Bool)
62          another_bool        _Bool                                     #(_Bool)
63          var                 some_type                                 #(some_type)
64}
65```
66