php.net |  support |  documentation |  report a bug |  advanced search |  search howto |  statistics |  random bug |  login
Bug #80121 Null pointer deref if CurlHandle directly instantiated
Submitted: 2020-09-18 10:15 UTC Modified: 2020-10-01 15:02 UTC
From: rekter0 at the3000 dot org Assigned:
Status: Closed Package: cURL related
PHP Version: 8.0.0beta4 OS: *
Private report: No CVE-ID: None
 [2020-09-18 10:15 UTC] rekter0 at the3000 dot org
Description:
------------
NullPointer dereference in _php_curl_verify_handlers

./configure --with-curl 


built with ASAN
	php-src-php-8.0.0beta4-asan$ ./sapi/cli/php -r '$a=new ($ch = curl_init("http://AAAAA"));'
	ASAN:DEADLYSIGNAL
	=================================================================
	==27740==ERROR: AddressSanitizer: SEGV on unknown address 0x000000000020 (pc 0x0000005f54cd bp 0x000000000000 sp 0x7ffebd8eeb50 T0)
	==27740==The signal is caused by a READ memory access.
	==27740==Hint: address points to the zero page.
	    #0 0x5f54cc in _php_curl_verify_handlers /php-src-php-8.0.0beta4/ext/curl/interface.c:148
	    #1 0x5f5797 in curl_free_obj /php-src-php-8.0.0beta4/ext/curl/interface.c:3311
	    #2 0xa5c9d6 in zend_objects_store_del /php-src-php-8.0.0beta4/Zend/zend_objects_API.c:193
	    #3 0x9af3fa in zval_ptr_dtor_nogc /php-src-php-8.0.0beta4-asan/Zend/zend_variables.h:35:3
	    #4 0x9af3fa in ZEND_HANDLE_EXCEPTION_SPEC_HANDLER /php-src-php-8.0.0beta4-asan/Zend/zend_vm_execute.h:3157
	    #5 0x80f1e3 in execute_ex /php-src-php-8.0.0beta4-asan/Zend/zend_vm_execute.h:55130:7
	    #6 0x80fcf6 in zend_execute /php-src-php-8.0.0beta4-asan/Zend/zend_vm_execute.h:59926:2
	    #7 0x7d492f in zend_eval_stringl /php-src-php-8.0.0beta4/Zend/zend_execute_API.c:1195
	    #8 0x7d4af8 in zend_eval_stringl_ex /php-src-php-8.0.0beta4/Zend/zend_execute_API.c:1236
	    #9 0xa64032 in do_cli /php-src-php-8.0.0beta4/sapi/cli/php_cli.c:979
	    #10 0x457c0a in main /php-src-php-8.0.0beta4/sapi/cli/php_cli.c:1336
	    #11 0x7fc1fd730b96 in __libc_start_main /build/glibc-2ORdQG/glibc-2.27/csu/../csu/libc-start.c:310
	    #12 0x4582f9 in _start (/php-src-php-8.0.0beta4-asan/sapi/cli/php+0x4582f9)

	AddressSanitizer can not provide additional info.
	SUMMARY: AddressSanitizer: SEGV /php-src-php-8.0.0beta4/ext/curl/interface.c:148 in _php_curl_verify_handlers
	==27740==ABORTING


built without ASAN

	php-src-php-8.0.0beta4$ ./sapi/cli/php -r '$a=new ($ch = curl_init("http://AAAAA"));'
	Segmentation fault (core dumped)


	gef➤  r -r '$a=new ($ch = curl_init("http://AAAAA"));'
	Starting program: /php-src-php-8.0.0beta4/sapi/cli/php -r '$a=new ($ch = curl_init("http://AAAAA"));'
	[Thread debugging using libthread_db enabled]
	Using host libthread_db library "/lib/x86_64-linux-gnu/libthread_db.so.1".

	Program received signal SIGSEGV, Segmentation fault.
	[ Legend: Modified register | Code | Heap | Stack | String ]
	────────────────────────────────────────────────────────────────────────────────────────── registers ────
	$rax   : 0x0               
	$rbx   : 0x00007fffee891300  →  0x0000000000000000
	$rcx   : 0x00007fffee852000  →  0x0000000000000000
	$rdx   : 0x0000555556556960  →  0x0000000000000148
	$rsp   : 0x00007fffffffc5c0  →  0x00007fffee891448  →  0x0000030800000001
	$rbp   : 0x0               
	$rsi   : 0x0               
	$rdi   : 0x00007fffee891300  →  0x0000000000000000
	$rip   : 0x000055555570d79d  →  <_php_curl_verify_handlers+13> cmp BYTE PTR [rax+0x20], 0x0
	$r8    : 0x00005555565b2c10  →  0x000001d600000001
	$r9    : 0x00005555566171f0  →  0x0000000000000001
	$r10   : 0x00007fffee800000  →  0x00007fffee800040  →  0x0000000000000000
	$r11   : 0x100000          
	$r12   : 0x00007fffee891300  →  0x0000000000000000
	$r13   : 0x0               
	$r14   : 0x00007fffee812020  →  0x0000555556570518  →  0x00005555559426bb  →  <execute_ex+5723> call 0x55555593dd90 <ZEND_HANDLE_EXCEPTION_SPEC_HANDLER>
	$r15   : 0x0000555556570518  →  0x00005555559426bb  →  <execute_ex+5723> call 0x55555593dd90 <ZEND_HANDLE_EXCEPTION_SPEC_HANDLER>
	$eflags: [ZERO carry PARITY adjust sign trap INTERRUPT direction overflow RESUME virtualx86 identification]
	$cs: 0x0033 $ss: 0x002b $ds: 0x0000 $es: 0x0000 $fs: 0x0000 $gs: 0x0000 
	────────────────────────────────────────────────────────────────────────────────────────────── stack ────
	0x00007fffffffc5c0│+0x0000: 0x00007fffee891448  →  0x0000030800000001	 ← $rsp
	0x00007fffffffc5c8│+0x0008: 0x0000000000000002
	0x00007fffffffc5d0│+0x0010: 0x00007fffee891300  →  0x0000000000000000
	0x00007fffffffc5d8│+0x0018: 0x000055555570da68  →  <curl_free_obj+24> mov rdi, QWORD PTR [rbx-0x148]
	0x00007fffffffc5e0│+0x0020: 0x00007fffee891448  →  0x0000030800000001
	0x00007fffffffc5e8│+0x0028: 0x0000000000000002
	0x00007fffffffc5f0│+0x0030: 0x0000000000000002
	0x00007fffffffc5f8│+0x0038: 0x00005555559687b7  →  <zend_objects_store_del+87> mov rdx, QWORD PTR [rbx+0x18]
	──────────────────────────────────────────────────────────────────────────────────────── code:x86:64 ────
	   0x55555570d795 <_php_curl_verify_handlers+5> push   rbx
	   0x55555570d796 <_php_curl_verify_handlers+6> mov    rax, QWORD PTR [rdi+0x8]
	   0x55555570d79a <_php_curl_verify_handlers+10> mov    rbx, rdi
	 → 0x55555570d79d <_php_curl_verify_handlers+13> cmp    BYTE PTR [rax+0x20], 0x0
	   0x55555570d7a1 <_php_curl_verify_handlers+17> jne    0x55555570d858 <_php_curl_verify_handlers+200>
	   0x55555570d7a7 <_php_curl_verify_handlers+23> mov    rdx, QWORD PTR [rax+0x10]
	   0x55555570d7ab <_php_curl_verify_handlers+27> test   rdx, rdx
	   0x55555570d7ae <_php_curl_verify_handlers+30> je     0x55555570d7ba <_php_curl_verify_handlers+42>
	   0x55555570d7b0 <_php_curl_verify_handlers+32> cmp    BYTE PTR [rdx+0x50], 0x0
	────────────────────────────────────────────────────────────────── source:/php[...].c+153 ────
	    148	 {
	    149	 	php_stream *stream;
	    150	 
	    151	 	ZEND_ASSERT(ch && ch->handlers);
	    152	 
	 →  153	 	if (!Z_ISUNDEF(ch->handlers->std_err)) {
	    154	 		stream = (php_stream *)zend_fetch_resource2_ex(&ch->handlers->std_err, NULL, php_file_le_stream(), php_file_le_pstream());
	    155	 		if (stream == NULL) {
	    156	 			if (reporterror) {
	    157	 				php_error_docref(NULL, E_WARNING, "CURLOPT_STDERR resource has gone away, resetting to stderr");
	    158	 			}
	──────────────────────────────────────────────────────────────────────────────────────────── threads ────
	[#0] Id 1, Name: "php", stopped, reason: SIGSEGV
	────────────────────────────────────────────────────────────────────────────────────────────── trace ────
	[#0] 0x55555570d79d → _php_curl_verify_handlers(ch=0x7fffee891300, reporterror=0x0)
	[#1] 0x55555570da68 → curl_free_obj(object=0x7fffee891448)
	[#2] 0x5555559687b7 → zend_objects_store_del(object=0x7fffee891448)
	[#3] 0x55555593df0a → zval_ptr_dtor_nogc(zval_ptr=<optimized out>)
	[#4] 0x55555593df0a → ZEND_HANDLE_EXCEPTION_SPEC_HANDLER()
	[#5] 0x5555559426c0 → execute_ex(ex=0x7fffee891300)
	[#6] 0x555555949a1f → zend_execute(op_array=<optimized out>, return_value=0x7fffffffc750)
	[#7] 0x5555558cf9b0 → zend_eval_stringl(str=0x5555565a50f0 "$a=new ($ch = curl_init(\"http://AAAAA\"));", str_len=<optimized out>, retval_ptr=0x0, string_name=0x55555610cc55 "Command line code")
	[#8] 0x5555558cfb79 → zend_eval_stringl_ex(str=<optimized out>, str_len=<optimized out>, retval_ptr=<optimized out>, string_name=<optimized out>, handle_exceptions=<optimized out>)
	[#9] 0x55555596fd93 → do_cli(argc=0x3, argv=0x5555565a5070)
	─────────────────────────────────────────────────────────────────────────────────────────────────────────
	_php_curl_verify_handlers (ch=0x7fffee891300, reporterror=0x0) at /php-src-php-8.0.0beta4/ext/curl/interface.c:153
	153		if (!Z_ISUNDEF(ch->handlers->std_err)) {


tested against different php8 releases

Test script:
---------------
<?php
$a = new ($ch = curl_init('foo/bar'));



Patches

Pull Requests

History

AllCommentsChangesGit/SVN commitsRelated reports
 [2020-09-18 12:03 UTC] cmb@php.net
-Status: Open +Status: Verified -Type: Security +Type: Bug
 [2020-09-18 12:03 UTC] cmb@php.net
Thanks for reporting, I can confirm the issue.  A debug build of
0582c40907649f2e86f3b75617e814427da1ce3f fails an assertion:

php_curl.dll!_php_curl_verify_handlers(php_curl * ch, int reporterror) Line 151 (c:\php-sdk\phpdev\vs16\x64\php-src\ext\curl\interface.c:151)
php_curl.dll!curl_free_obj(_zend_object * object) Line 3324 (c:\php-sdk\phpdev\vs16\x64\php-src\ext\curl\interface.c:3324)
php8_debug.dll!zend_objects_store_del(_zend_object * object) Line 195 (c:\php-sdk\phpdev\vs16\x64\php-src\Zend\zend_objects_API.c:195)
php8_debug.dll!rc_dtor_func(_zend_refcounted * p) Line 58 (c:\php-sdk\phpdev\vs16\x64\php-src\Zend\zend_variables.c:58)
php8_debug.dll!zval_ptr_dtor_nogc(_zval_struct * zval_ptr) Line 37 (c:\php-sdk\phpdev\vs16\x64\php-src\Zend\zend_variables.h:37)
php8_debug.dll!ZEND_HANDLE_EXCEPTION_SPEC_HANDLER(_zend_execute_data * execute_data) Line 2962 (c:\php-sdk\phpdev\vs16\x64\php-src\Zend\zend_vm_execute.h:2962)
php8_debug.dll!execute_ex(_zend_execute_data * ex) Line 54258 (c:\php-sdk\phpdev\vs16\x64\php-src\Zend\zend_vm_execute.h:54258)
php8_debug.dll!zend_execute(_zend_op_array * op_array, _zval_struct * return_value) Line 58788 (c:\php-sdk\phpdev\vs16\x64\php-src\Zend\zend_vm_execute.h:58788)
php8_debug.dll!zend_execute_scripts(int type, _zval_struct * retval, int file_count, ...) Line 1681 (c:\php-sdk\phpdev\vs16\x64\php-src\Zend\zend.c:1681)
php8_debug.dll!php_execute_script(_zend_file_handle * primary_file) Line 2492 (c:\php-sdk\phpdev\vs16\x64\php-src\main\main.c:2492)
php.exe!do_cli(int argc, char * * argv) Line 951 (c:\php-sdk\phpdev\vs16\x64\php-src\sapi\cli\php_cli.c:951)
php.exe!main(int argc, char * * argv) Line 1336 (c:\php-sdk\phpdev\vs16\x64\php-src\sapi\cli\php_cli.c:1336)
php.exe!invoke_main() Line 79 (d:\agent\_work\9\s\src\vctools\crt\vcstartup\src\startup\exe_common.inl:79)

However, this does not affect any PHP 7 version, and since PHP 8
has not yet reached GA, this is not a security issue.
 [2020-09-18 17:07 UTC] stas@php.net
To be clear, it wouldn't be a security issue even if it did affect PHP 7.
 [2020-10-01 14:55 UTC] nikic@php.net
Reduced test case:

<?php
new CurlHandle;
 [2020-10-01 15:02 UTC] nikic@php.net
-Summary: NullPointer dereference +Summary: Null pointer deref if CurlHandle directly instantiated
 [2020-10-01 15:06 UTC] nikic@php.net
Automatic comment on behalf of nikita.ppv@gmail.com
Revision: http://git.php.net/?p=php-src.git;a=commit;h=d96219c185e68c82beb994db2c93bd26f47ce16a
Log: Fixed bug #80121
 [2020-10-01 15:06 UTC] nikic@php.net
-Status: Verified +Status: Closed
 
PHP Copyright © 2001-2024 The PHP Group
All rights reserved.
Last updated: Thu Nov 21 10:01:29 2024 UTC