Commit 56bd75634f9 for php
commit 56bd75634f931745f35bbbde52aa92e319557ca1
Author: lacatoire <la.catoire@gmail.com>
Date: Sun Aug 16 19:29:18 2026 +0200
ext/ldap: fix crash in ldap_exop_sync() when $response_data is omitted
ldap_exop_sync() always takes the synchronous branch of php_ldap_exop(),
which assigns $response_data unconditionally. When the argument is not
passed, retdata is NULL and ZEND_TRY_ASSIGN_REF_STRINGL()/
ZEND_TRY_ASSIGN_REF_EMPTY_STRING() dereference it, so any successful
ldap_exop_sync($ldap, $oid) call segfaults. Guard the assignment the way
the $response_oid one already is.
Closes GH-23339.
diff --git a/NEWS b/NEWS
index 798f849854c..433aa7d0297 100644
--- a/NEWS
+++ b/NEWS
@@ -111,6 +111,9 @@ PHP NEWS
properties after running out of memory while escaping a property name.
(adapik)
+- LDAP:
+ . Fix crash in ldap_exop_sync() when $response_data is omitted. (lacatoire)
+
- MBString:
. Fixed bug GH-23958 (truncated encoding names resolving to full names). (Kamil Tekiela)
. Fixed out-of-bounds read in php_mb_rfc1867_getword() on a multibyte lead
diff --git a/ext/ldap/ldap.c b/ext/ldap/ldap.c
index 2b3cb0e8a70..4c9466749ea 100644
--- a/ext/ldap/ldap.c
+++ b/ext/ldap/ldap.c
@@ -4129,10 +4129,12 @@ static void php_ldap_exop(INTERNAL_FUNCTION_PARAMETERS, bool force_sync) {
}
if (lretdata) {
- ZEND_TRY_ASSIGN_REF_STRINGL(retdata, lretdata->bv_val, lretdata->bv_len);
+ if (retdata) {
+ ZEND_TRY_ASSIGN_REF_STRINGL(retdata, lretdata->bv_val, lretdata->bv_len);
+ }
ldap_memfree(lretdata->bv_val);
ldap_memfree(lretdata);
- } else {
+ } else if (retdata) {
ZEND_TRY_ASSIGN_REF_EMPTY_STRING(retdata);
}
diff --git a/ext/ldap/tests/ldap_exop_sync_without_response_data.phpt b/ext/ldap/tests/ldap_exop_sync_without_response_data.phpt
new file mode 100644
index 00000000000..111900c6a05
--- /dev/null
+++ b/ext/ldap/tests/ldap_exop_sync_without_response_data.phpt
@@ -0,0 +1,22 @@
+--TEST--
+ldap_exop_sync() - without the response_data argument
+--EXTENSIONS--
+ldap
+--SKIPIF--
+<?php require_once('skipifbindfailure.inc'); ?>
+--FILE--
+<?php
+require "connect.inc";
+
+$link = ldap_connect_and_bind($uri, $user, $passwd, $protocol_version);
+
+var_dump(
+ ldap_exop_sync($link, LDAP_EXOP_WHO_AM_I),
+ ldap_exop_sync($link, LDAP_EXOP_WHO_AM_I, null, null, $retdata),
+ $retdata
+);
+?>
+--EXPECTF--
+bool(true)
+bool(true)
+string(%d) "dn:%s"