Name Date Size #Lines LOC

..30-Aug-2022-

corpus/H30-Aug-2022-

dict/H17-Jan-2024-

Makefile.fragH A D10-Jan-20241.8 KiB3422

README.mdH A D16-Apr-20243.7 KiB9874

config.m4H A D30-Aug-20222.5 KiB7765

fuzzer-execute-common.hH A D30-Aug-20225.1 KiB167110

fuzzer-execute.cH A D30-Aug-20221.5 KiB3714

fuzzer-exif.cH A D30-Aug-20222.1 KiB7338

fuzzer-function-jit.cH A D20-Nov-20232.6 KiB7040

fuzzer-json.cH A D30-Aug-20221.9 KiB6332

fuzzer-mbregex.cH A D30-Aug-20222.2 KiB7944

fuzzer-mbstring.cH A D28-Nov-20235.4 KiB14184

fuzzer-parser.cH A D30-Aug-20221.9 KiB5121

fuzzer-sapi.cH A D22-Jan-20248.7 KiB326220

fuzzer-sapi.hH A D30-Aug-20221.5 KiB279

fuzzer-tracing-jit.cH A D14-Nov-20233 KiB8250

fuzzer-unserialize.cH A D30-Aug-20221.9 KiB6835

fuzzer-unserializehash.cH A D30-Aug-20222.3 KiB8350

fuzzer.hH A D30-Aug-20221 KiB192

generate_all.phpH A D30-Aug-2022671 2219

generate_corpus_util.phpH A D30-Aug-2022966 2622

generate_execute_corpus.phpH A D30-Aug-2022379 1814

generate_mbstring_dict.phpH A D30-Aug-2022267 1310

generate_parser_corpus.phpH A D30-Aug-2022716 2520

generate_unserialize_dict.phpH A D30-Aug-2022213 107

generate_unserializehash_corpus.phpH A D30-Aug-2022436 1714

json.dictH A D30-Aug-2022416 5345

README.md

1Fuzzing SAPI for PHP
2--------------------
3
4The following `./configure` options can be used to enable the fuzzing SAPI, as well as all available fuzzers. If you don't build the exif/json/mbstring extensions, fuzzers for these extensions will not be built.
5
6```sh
7CC=clang CXX=clang++ \
8./configure \
9    --disable-all \
10    --enable-fuzzer \
11    --with-pic \
12    --enable-debug-assertions \
13    --enable-address-sanitizer \
14    --enable-exif \
15    --enable-mbstring
16```
17
18The `--with-pic` option is required to avoid a linking failure. The `--enable-debug-assertions` option can be used to enable debug assertions despite the use of a release build.
19
20You can combine fuzzing with `--enable-address-sanitizer`, `--enable-undefined-sanitizer` or `--enable-memory-sanitizer`. The first two options can also be used together.
21
22You will need a recent version of clang that supports the `-fsanitize=fuzzer-no-link` option.
23
24When running `make` it creates these binaries in `sapi/fuzzer/`:
25
26* `php-fuzz-parser`: Fuzzing language parser and compiler
27* `php-fuzz-unserialize`: Fuzzing unserialize() function
28* `php-fuzz-unserializehash`: Fuzzing unserialize() for HashContext objects
29* `php-fuzz-json`: Fuzzing JSON parser
30* `php-fuzz-exif`: Fuzzing `exif_read_data()` function (requires --enable-exif)
31* `php-fuzz-mbstring`: Fuzzing `mb_convert_encoding()` (requires `--enable-mbstring`)
32* `php-fuzz-mbregex`: Fuzzing `mb_ereg[i]()` (requires --enable-mbstring)
33* `php-fuzz-execute`: Fuzzing the executor
34* `php-fuzz-function-jit`: Fuzzing the function JIT (requires --enable-opcache)
35* `php-fuzz-tracing-jit`: Fuzzing the tracing JIT (requires --enable-opcache)
36
37Some fuzzers have a seed corpus in `sapi/fuzzer/corpus`. You can use it as follows:
38
39```sh
40cp -r sapi/fuzzer/corpus/exif ./my-exif-corpus
41sapi/fuzzer/php-fuzz-exif ./my-exif-corpus
42```
43
44For the unserialize fuzzer, a dictionary of internal classes should be generated first:
45
46```sh
47sapi/cli/php sapi/fuzzer/generate_unserialize_dict.php
48cp -r sapi/fuzzer/corpus/unserialize ./my-unserialize-corpus
49sapi/fuzzer/php-fuzz-unserialize -dict=$PWD/sapi/fuzzer/dict/unserialize ./my-unserialize-corpus
50```
51
52For the unserializehash fuzzer, generate a corpus of initial hash serializations:
53
54```sh
55sapi/cli/php sapi/fuzzer/generate_unserializehash_corpus.php
56cp -r sapi/fuzzer/corpus/unserializehash ./my-unserialize-corpus
57sapi/fuzzer/php-fuzz-unserializehash ./my-unserialize-corpus
58```
59
60For the parser fuzzer, a corpus may be generated from Zend test files:
61
62```sh
63sapi/cli/php sapi/fuzzer/generate_parser_corpus.php
64mkdir ./my-parser-corpus
65sapi/fuzzer/php-fuzz-parser -merge=1 ./my-parser-corpus sapi/fuzzer/corpus/parser
66sapi/fuzzer/php-fuzz-parser -only_ascii=1 ./my-parser-corpus
67```
68
69For the execute, function-jit and tracing-jit fuzzers, a corpus may be generated from any set of test files:
70
71```sh
72sapi/cli/php sapi/fuzzer/generate_execute_corpus.php ./execute-corpus Zend/tests ext/opcache/tests/jit
73sapi/fuzzer/php-fuzzer-function-jit ./execute-corpus
74```
75
76For the mbstring fuzzer, a dictionary of encodings should be generated first:
77
78```sh
79sapi/cli/php sapi/fuzzer/generate_mbstring_dict.php
80sapi/fuzzer/php-fuzz-mbstring -dict=$PWD/sapi/fuzzer/dict/mbstring ./my-mbstring-corpus
81```
82
83For the mbregex fuzzer, you may want to build the libonig dependency with instrumentation. At this time, libonig is not clean under ubsan, so only the fuzzer and address sanitizers may be used.
84
85```sh
86git clone https://github.com/kkos/oniguruma.git
87pushd oniguruma
88autoreconf -vfi
89./configure CC=clang CFLAGS="-fsanitize=fuzzer-no-link,address -O2 -g"
90make
91popd
92
93export ONIG_CFLAGS="-I$PWD/oniguruma/src"
94export ONIG_LIBS="-L$PWD/oniguruma/src/.libs -l:libonig.a"
95```
96
97This will link an instrumented libonig statically into the PHP binary.
98