A heap buffer overflow in cURL
So last week (Friday night to be exact) I had the bright idea to start fuzzing cURL. Because it was Friday night and I was feeling a bit lazy, I decided to take the easy way out and take a look at the
-K command line flag which tells cURL to read the specified
config file. And so I gave it a text file containing
Hello world! and let it run like so:
afl-fuzz -m none -d -i in -o out curl -q -K @@.
It didn't take long for AFL to start finding crashes:
Needless to say, the
unique crashes announced by AFL were mostly the same thing. ASAN identified this one as a heap-buffer-overflow (also known as a buffer read overrun or read outside of buffer):
==21754==ERROR: AddressSanitizer: heap-buffer-overflow on address 0x60200000dbb2 at pc 0x0000004fcd39 bp 0x7ffcd27dc250 sp 0x7ffcd27dc248 READ of size 1 at 0x60200000dbb2 thread T0 #0 0x4fcd38 in ourWriteOut /root/curl/src/tool_writeout.c:115:3 #1 0x4ec947 in operate_do /root/curl/src/tool_operate.c:1669:11 #2 0x4e053e in operate /root/curl/src/tool_operate.c:2024:20 #3 0x4de5a6 in main /root/curl/src/tool_main.c:252:14 #4 0x7fad0a96fb44 in __libc_start_main /build/glibc-qK83Be/glibc-2.19/csu/libc-start.c:287 #5 0x4c407c in _start (/root/curl/src/curl+0x4c407c) 0x60200000dbb2 is located 0 bytes to the right of 2-byte region [0x60200000dbb0,0x60200000dbb2) allocated by thread T0 here: #0 0x4a69fb in malloc (/root/curl/src/curl+0x4a69fb) #1 0x7fad0a9cf989 in __strdup /build/glibc-qK83Be/glibc-2.19/string/strdup.c:42 SUMMARY: AddressSanitizer: heap-buffer-overflow /root/curl/src/tool_writeout.c:115 ourWriteOut
While my command line was
curl -q -K test_case, an alternate way to trigger this would be
curl -q --write-out '%' http://foo.
One of the developers on the cURL mailing list says this about the flaw:
It's possible that the data past the end of the buffer could get displayed as part of the --write-out output (up to the first nul character, anyway), so theoretically, it could write out a password or secret key or something.
The git commit for the fix says:
If a % ended the statement, the string's trailing NUL would be skipped and memory past the end of the buffer would be accessed and potentially displayed as part of the --write-out output.
Nobody could conclusively say that this was exploitable, so it was patched in git and no CVE has been assigned yet. I'll release the minimized PoC generated by AFL after I talk to the Mitre folks and see if they're interested in assigning a CVE for this.