Skip to content

Commit 10b5d4b

Browse files
committed
Merge branch 'PHP-8.2' into PHP-8.3
* PHP-8.2: NEWS entries for LDAP bug fixes ext/ldap: Fix GH-16136 (Memory leak in php_ldap_do_modify()) ext/ldap: Fix GH-16132 (Freeing pointer not allocated by ZMM)
2 parents a551b99 + f8b925b commit 10b5d4b

File tree

5 files changed

+99
-11
lines changed

5 files changed

+99
-11
lines changed

NEWS

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -23,6 +23,10 @@ PHP NEWS
2323
ldap_modify_batch()). (Girgias)
2424
. Fixed bug GH-16101 (Segfault in ldap_list(), ldap_read(), and ldap_search()
2525
when LDAPs array is not a list). (Girgias)
26+
. Fix GH-16132 (php_ldap_do_modify() attempts to free pointer not allocated
27+
by ZMM.). (Girgias)
28+
. Fix GH-16136 (Memory leak in php_ldap_do_modify() when entry is not a
29+
proper dictionary). (Girgias)
2630

2731
- OpenSSL:
2832
. Fixed stub for openssl_csr_new. (Jakub Zelenka)

ext/ldap/ldap.c

Lines changed: 9 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -2224,17 +2224,11 @@ static void php_ldap_do_modify(INTERNAL_FUNCTION_PARAMETERS, int oper, int ext)
22242224
ldap_mods[i]->mod_type = estrndup(ZSTR_VAL(attribute), ZSTR_LEN(attribute));
22252225
} else {
22262226
php_error_docref(NULL, E_WARNING, "Unknown attribute in the data");
2227-
/* Free allocated memory */
2228-
while (i >= 0) {
2229-
if (ldap_mods[i]->mod_type) {
2230-
efree(ldap_mods[i]->mod_type);
2231-
}
2232-
efree(ldap_mods[i]);
2233-
i--;
2234-
}
2235-
efree(num_berval);
2236-
efree(ldap_mods);
2237-
RETURN_FALSE;
2227+
RETVAL_FALSE;
2228+
num_berval[i] = 0;
2229+
num_attribs = i + 1;
2230+
ldap_mods[i]->mod_bvalues = NULL;
2231+
goto cleanup;
22382232
}
22392233

22402234
value = zend_hash_get_current_data(Z_ARRVAL_P(entry));
@@ -2255,6 +2249,8 @@ static void php_ldap_do_modify(INTERNAL_FUNCTION_PARAMETERS, int oper, int ext)
22552249
convert_to_string(value);
22562250
if (EG(exception)) {
22572251
RETVAL_FALSE;
2252+
num_berval[i] = 0;
2253+
num_attribs = i + 1;
22582254
goto cleanup;
22592255
}
22602256
ldap_mods[i]->mod_bvalues[0] = (struct berval *) emalloc (sizeof(struct berval));
@@ -2271,6 +2267,8 @@ static void php_ldap_do_modify(INTERNAL_FUNCTION_PARAMETERS, int oper, int ext)
22712267
}
22722268
convert_to_string(ivalue);
22732269
if (EG(exception)) {
2270+
num_berval[i] = j;
2271+
num_attribs = i + 1;
22742272
RETVAL_FALSE;
22752273
goto cleanup;
22762274
}

ext/ldap/tests/gh16132-1.phpt

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
--TEST--
2+
Bug GH-16132: Attempting to free pointer not allocated by ZMM
3+
--EXTENSIONS--
4+
ldap
5+
--FILE--
6+
<?php
7+
8+
/* ldap_add(_ext)(), ldap_mod_replace(_ext)(), ldap_mod_add(_ext)(), and ldap_mod_del(_ext)() share an underlying C function */
9+
/* We are assuming 3333 is not connectable */
10+
$ldap = ldap_connect('ldap://127.0.0.1:3333');
11+
$valid_dn = "cn=userA,something";
12+
13+
$dict_key_value_not_string = [
14+
'attribute1' => new stdClass(),
15+
'attribute2' => [
16+
'value1',
17+
'value2',
18+
],
19+
];
20+
try {
21+
var_dump(ldap_add($ldap, $valid_dn, $dict_key_value_not_string));
22+
} catch (Throwable $e) {
23+
echo $e::class, ': ', $e->getMessage(), PHP_EOL;
24+
}
25+
26+
?>
27+
--EXPECT--
28+
Error: Object of class stdClass could not be converted to string

ext/ldap/tests/gh16132-2.phpt

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
--TEST--
2+
Bug GH-16132: Attempting to free pointer not allocated by ZMM
3+
--EXTENSIONS--
4+
ldap
5+
--FILE--
6+
<?php
7+
8+
/* ldap_add(_ext)(), ldap_mod_replace(_ext)(), ldap_mod_add(_ext)(), and ldap_mod_del(_ext)() share an underlying C function */
9+
/* We are assuming 3333 is not connectable */
10+
$ldap = ldap_connect('ldap://127.0.0.1:3333');
11+
$valid_dn = "cn=userA,something";
12+
13+
$dict_key_multi_value_not_list_of_strings2 = [
14+
'attribute1' => 'value',
15+
'attribute2' => [
16+
'value1',
17+
new stdClass(),
18+
],
19+
];
20+
try {
21+
var_dump(ldap_add($ldap, $valid_dn, $dict_key_multi_value_not_list_of_strings2));
22+
} catch (Throwable $e) {
23+
echo $e::class, ': ', $e->getMessage(), PHP_EOL;
24+
}
25+
26+
?>
27+
--EXPECT--
28+
Error: Object of class stdClass could not be converted to string

ext/ldap/tests/gh16136.phpt

Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,30 @@
1+
--TEST--
2+
Bug GH-16136: Memory leak in php_ldap_do_modify() when entry is not a proper dictionary
3+
--EXTENSIONS--
4+
ldap
5+
--FILE--
6+
<?php
7+
8+
/* ldap_add(_ext)(), ldap_mod_replace(_ext)(), ldap_mod_add(_ext)(), and ldap_mod_del(_ext)() share an underlying C function */
9+
/* We are assuming 3333 is not connectable */
10+
$ldap = ldap_connect('ldap://127.0.0.1:3333');
11+
$valid_dn = "cn=userA,something";
12+
13+
$not_dict_of_attributes = [
14+
'attribute1' => 'value',
15+
'not_key_entry',
16+
'attribute3' => [
17+
'value1',
18+
'value2',
19+
],
20+
];
21+
try {
22+
var_dump(ldap_add($ldap, $valid_dn, $not_dict_of_attributes));
23+
} catch (Throwable $e) {
24+
echo $e::class, ': ', $e->getMessage(), PHP_EOL;
25+
}
26+
27+
?>
28+
--EXPECTF--
29+
Warning: ldap_add(): Unknown attribute in the data in %s on line %d
30+
bool(false)

0 commit comments

Comments
 (0)