Summary
We fuzzed CUDD 4.0.0-rc2 / dddmp with AFL++ as part of a university course project. AFL++ generated 16.2M crashes which we de-duplicated and then investigated the 147 strongest candidates.
All 6 of the AFL++ bugs share the same root cause: a malformed DDDMP input causes CUDD to crash rather than return an error. While DDDMP performs some input validation, this validation is insufficient to prevent these crashes.
All reproducer files, triage scripts, and ASAN output are available at:
https://github.com/Boolean-Fuzzers/CUDD-Fuzzing (triage/ directory)
Bug 1 - DddmpCuddDdArrayLoad: Invalid Pointer Read
A malformed DDDMP input causes DddmpCuddDdArrayLoad to read from an invalid pointer, resulting in a SIGSEGV.
AddressSanitizer:DEADLYSIGNAL
=================================================================
==485721==ERROR: AddressSanitizer: SEGV on unknown address 0x501f07240b60 (pc 0x5dc6c1c71f76 bp 0x5dc6c2628e20 sp 0x7ffe10f57910 T0)
==485721==The signal is caused by a READ memory access.
#0 0x5dc6c1c71f76 in DddmpCuddDdArrayLoad dddmpLoad.c:1079:11
#1 0x5dc6c1c6fd6f in Dddmp_cuddBddArrayLoad dddmpLoad.c:211:14
#2 0x5dc6c1c6fd6f in Dddmp_cuddBddLoad dddmpLoad.c:99:12
#3 0x5dc6c1bdeb9d in main regular_main.c:35:17
#4 0x72ba6ee2a1c9 in __libc_start_call_main csu/../sysdeps/nptl/libc_start_call_main.h:58:16
#5 0x72ba6ee2a28a in __libc_start_main csu/../csu/libc-start.c:360:3
#6 0x5dc6c1b054e4 in _start (regular_harness_asan+0x2d4e4) (BuildId: ba886f0afc7a6bfc914c350c1b492698f7a276ab)
AddressSanitizer can not provide additional info.
SUMMARY: AddressSanitizer: SEGV dddmpLoad.c:1079:11 in DddmpCuddDdArrayLoad
==485721==ABORTING
Bug 2 - Dddmp_cuddHeaderLoad / strlen: Invalid Pointer Read
A malformed DDDMP file causes strlen() inside Dddmp_cuddHeaderLoad to read from an invalid pointer, resulting in a SIGSEGV.
AddressSanitizer:DEADLYSIGNAL
=================================================================
==485803==ERROR: AddressSanitizer: SEGV on unknown address 0x000200001102 (pc 0x750af079b95c bp 0x7ffdd4c1e400 sp 0x7ffdd4c1dbb8 T0)
==485803==The signal is caused by a READ memory access.
#0 0x750af079b95c in __strlen_evex string/../sysdeps/x86_64/multiarch/strlen-evex-base.S:81
#1 0x5f1a57d00b87 in strlen (regular_harness_asan+0x44b87) (BuildId: ba886f0afc7a6bfc914c350c1b492698f7a276ab)
#2 0x5f1a57e57a92 in Dddmp_cuddHeaderLoad dddmpLoad.c:446:32
#3 0x5f1a57dc2aba in validate_dddmp_header regular_main.c:121:18
#4 0x5f1a57dc2aba in main regular_main.c:19:25
#5 0x750af062a1c9 in __libc_start_call_main csu/../sysdeps/nptl/libc_start_call_main.h:58:16
#6 0x750af062a28a in __libc_start_main csu/../csu/libc-start.c:360:3
#7 0x5f1a57ce94e4 in _start (regular_harness_asan+0x2d4e4) (BuildId: ba886f0afc7a6bfc914c350c1b492698f7a276ab)
AddressSanitizer can not provide additional info.
SUMMARY: AddressSanitizer: SEGV string/../sysdeps/x86_64/multiarch/strlen-evex-base.S:81 in __strlen_evex
==485803==ABORTING
Bug 3 - DddmpBddReadHeader / scanf: Invalid High Value Pointer Dereference
A malformed DDDMP file causes scanf() inside DddmpBddReadHeader to read from a high-value invalid pointer, resulting in a SIGSEGV. ASAN noted this was caused by a dereference of a high value address.
AddressSanitizer:DEADLYSIGNAL
=================================================================
==485892==ERROR: AddressSanitizer: SEGV on unknown address (pc 0x73f24c46b8c5 bp 0x7ffe29e63580 sp 0x7ffe29e62ea0 T0)
==485892==The signal is caused by a READ memory access.
==485892==Hint: this fault was caused by a dereference of a high value address (see register values below). Disassemble the provided pc to learn which register was used.
#0 0x73f24c46b8c5 in __vfscanf_internal stdio-common/vfscanf-internal.c:345:3
#1 0x59203f113a3d in __isoc99_fscanf (regular_harness_asan+0x51a3d) (BuildId: ba886f0afc7a6bfc914c350c1b492698f7a276ab)
#2 0x59203f25e414 in DddmpBddReadHeader dddmpLoad.c:1266:10
#3 0x59203f25d7fd in Dddmp_cuddHeaderLoad dddmpLoad.c:403:9
#4 0x59203f1c8aba in validate_dddmp_header regular_main.c:121:18
#5 0x59203f1c8aba in main regular_main.c:19:25
#6 0x73f24c42a1c9 in __libc_start_call_main csu/../sysdeps/nptl/libc_start_call_main.h:58:16
#7 0x73f24c42a28a in __libc_start_main csu/../csu/libc-start.c:360:3
#8 0x59203f0ef4e4 in _start (regular_harness_asan+0x2d4e4) (BuildId: ba886f0afc7a6bfc914c350c1b492698f7a276ab)
AddressSanitizer can not provide additional info.
SUMMARY: AddressSanitizer: SEGV stdio-common/vfscanf-internal.c:345:3 in __vfscanf_internal
==485892==ABORTING
Bug 4 - Dddmp_cuddBddArrayLoad / cuddBddAndRecur: Invalid High Value Pointer Dereference
A malformed DDDMP file causes a SIGBUS inside cuddBddAndRecur triggered by a high-value address dereference during BDD reconstruction. This crash reaches into the core CUDD library from the DDDMP loading path.
AddressSanitizer:DEADLYSIGNAL
=================================================================
==485974==ERROR: AddressSanitizer: BUS on unknown address (pc 0x620f06158bf1 bp 0xbebebebebebebebe sp 0x7ffe91cb0bd0 T0)
==485974==The signal is caused by a READ memory access.
==485974==Hint: this fault was caused by a dereference of a high value address (see register values below). Disassemble the provided pc to learn which register was used.
#0 0x620f06158bf1 in cuddBddAndRecur cuddBddIte.c:1009:31
#1 0x620f06156ddc in cuddBddIteRecur cuddBddIte.c:743:12
#2 0x620f06156b14 in Cudd_bddIte cuddBddIte.c:114:8
#3 0x620f061e4095 in DddmpCuddDdArrayLoad dddmpLoad.c:1082:21
#4 0x620f061e1d6f in Dddmp_cuddBddArrayLoad dddmpLoad.c:211:14
#5 0x620f061e1d6f in Dddmp_cuddBddLoad dddmpLoad.c:99:12
#6 0x620f06150b9d in main regular_main.c:35:17
#7 0x7f29a5e2a1c9 in __libc_start_call_main csu/../sysdeps/nptl/libc_start_call_main.h:58:16
#8 0x7f29a5e2a28a in __libc_start_main csu/../csu/libc-start.c:360:3
#9 0x620f060774e4 in _start (regular_harness_asan+0x2d4e4) (BuildId: ba886f0afc7a6bfc914c350c1b492698f7a276ab)
AddressSanitizer can not provide additional info.
SUMMARY: AddressSanitizer: BUS cuddBddIte.c:1009:31 in cuddBddAndRecur
==485974==ABORTING
Bug 5 - DddmpCuddDdArrayLoad / cuddBddXorRecur: Invalid Pointer Read
A malformed DDDMP file causes cuddBddXorRecur to read from an invalid pointer during XOR BDD reconstruction, resulting in a SIGSEGV.
AddressSanitizer:DEADLYSIGNAL
=================================================================
==486074==ERROR: AddressSanitizer: SEGV on unknown address 0x50420000004c (pc 0x59705f3bec0c bp 0x000000000001 sp 0x7ffc40b9f900 T0)
==486074==The signal is caused by a READ memory access.
#0 0x59705f3bec0c in cuddBddXorRecur cuddBddIte.c:1142:12
#1 0x59705f3bbb14 in Cudd_bddIte cuddBddIte.c:114:8
#2 0x59705f449095 in DddmpCuddDdArrayLoad dddmpLoad.c:1082:21
#3 0x59705f446d6f in Dddmp_cuddBddArrayLoad dddmpLoad.c:211:14
#4 0x59705f446d6f in Dddmp_cuddBddLoad dddmpLoad.c:99:12
#5 0x59705f3b5b9d in main regular_main.c:35:17
#6 0x7999bd62a1c9 in __libc_start_call_main csu/../sysdeps/nptl/libc_start_call_main.h:58:16
#7 0x7999bd62a28a in __libc_start_main csu/../csu/libc-start.c:360:3
#8 0x59705f2dc4e4 in _start (regular_harness_asan+0x2d4e4) (BuildId: ba886f0afc7a6bfc914c350c1b492698f7a276ab)
AddressSanitizer can not provide additional info.
SUMMARY: AddressSanitizer: SEGV cuddBddIte.c:1142:12 in cuddBddXorRecur
==486074==ABORTING
Bug 6 - DddmpStrArrayFree: Invalid Pointer Write
A malformed DDDMP file causes DddmpStrArrayFree to attempt to write to the zero page.
AddressSanitizer:DEADLYSIGNAL
=================================================================
==486280==ERROR: AddressSanitizer: SEGV on unknown address 0x0000000000ae (pc 0x5a5ad8a9d8e6 bp 0x000000000000 sp 0x7ffd9cd93d30 T0)
==486280==The signal is caused by a WRITE memory access.
==486280==Hint: address points to the zero page.
#0 0x5a5ad8a9d8e6 in __asan::Allocator::Deallocate(void*, unsigned long, unsigned long, __sanitizer::BufferedStackTrace*, __asan::AllocType) (regular_harness_asan+0x2f8e6) (BuildId: ba886f0afc7a6bfc914c350c1b492698f7a276ab)
#1 0x5a5ad8b360ff in free (regular_harness_asan+0xc80ff) (BuildId: ba886f0afc7a6bfc914c350c1b492698f7a276ab)
#2 0x5a5ad8c0ddff in DddmpStrArrayFree src/dddmpUtil.c:303:5
#3 0x5a5ad8c0b3f2 in DddmpFreeHeader src/dddmpLoad.c:1474:3
#4 0x5a5ad8c09fad in Dddmp_cuddHeaderLoad src/dddmpLoad.c:521:3
#5 0x5a5ad8b74aba in validate_dddmp_header regular_main.c:121:18
#6 0x5a5ad8b74aba in main regular_main.c:19:25
#7 0x7e171f42a1c9 in __libc_start_call_main csu/../sysdeps/nptl/libc_start_call_main.h:58:16
#8 0x7e171f42a28a in __libc_start_main csu/../csu/libc-start.c:360:3
#9 0x5a5ad8a9b4e4 in _start (regular_harness_asan+0x2d4e4) (BuildId: ba886f0afc7a6bfc914c350c1b492698f7a276ab)
AddressSanitizer can not provide additional info.
SUMMARY: AddressSanitizer: SEGV (regular_harness_asan+0x2f8e6) (BuildId: ba886f0afc7a6bfc914c350c1b492698f7a276ab) in __asan::Allocator::Deallocate(void*, unsigned long, unsigned long, __sanitizer::BufferedStackTrace*, __asan::AllocType)
==486280==ABORTING
Summary
We fuzzed CUDD 4.0.0-rc2 / dddmp with AFL++ as part of a university course project. AFL++ generated 16.2M crashes which we de-duplicated and then investigated the 147 strongest candidates.
All 6 of the AFL++ bugs share the same root cause: a malformed DDDMP input causes CUDD to crash rather than return an error. While DDDMP performs some input validation, this validation is insufficient to prevent these crashes.
All reproducer files, triage scripts, and ASAN output are available at:
https://github.com/Boolean-Fuzzers/CUDD-Fuzzing (triage/ directory)
Bug 1 -
DddmpCuddDdArrayLoad: Invalid Pointer ReadA malformed DDDMP input causes
DddmpCuddDdArrayLoadto read from an invalid pointer, resulting in a SIGSEGV.Bug 2 -
Dddmp_cuddHeaderLoad/strlen: Invalid Pointer ReadA malformed DDDMP file causes
strlen()insideDddmp_cuddHeaderLoadto read from an invalid pointer, resulting in a SIGSEGV.Bug 3 -
DddmpBddReadHeader/scanf: Invalid High Value Pointer DereferenceA malformed DDDMP file causes
scanf()insideDddmpBddReadHeaderto read from a high-value invalid pointer, resulting in a SIGSEGV. ASAN noted this was caused by a dereference of a high value address.Bug 4 -
Dddmp_cuddBddArrayLoad/cuddBddAndRecur: Invalid High Value Pointer DereferenceA malformed DDDMP file causes a SIGBUS inside
cuddBddAndRecurtriggered by a high-value address dereference during BDD reconstruction. This crash reaches into the core CUDD library from the DDDMP loading path.Bug 5 -
DddmpCuddDdArrayLoad/cuddBddXorRecur: Invalid Pointer ReadA malformed DDDMP file causes
cuddBddXorRecurto read from an invalid pointer during XOR BDD reconstruction, resulting in a SIGSEGV.Bug 6 -
DddmpStrArrayFree: Invalid Pointer WriteA malformed DDDMP file causes
DddmpStrArrayFreeto attempt to write to the zero page.