Skip to content

Commit c7a322c

Browse files
committed
ext/sockets: follow-up on GH-17300 to check hints value ranges.
close GH-17326
1 parent 0a69e14 commit c7a322c

File tree

4 files changed

+71
-2
lines changed

4 files changed

+71
-2
lines changed

NEWS

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -90,6 +90,8 @@ PHP NEWS
9090
(David Carlier)
9191
. socket_addrinfo_lookup throws an exception on invalid hints value types.
9292
(David Carlier)
93+
. socket_addrinfo_lookup throws an exception if any of the hints value
94+
overflows. (David Carlier)
9395

9496
- Standard:
9597
. Fixed crypt() tests on musl when using --with-external-libcrypt

UPGRADING

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -128,7 +128,8 @@ PHP 8.5 UPGRADE NOTES
128128
. socket_create_listen, socket_bind and socket_sendto throw a
129129
ValueError if the port is lower than 0 or greater than 65535.
130130
. socket_addrinfo_lookup throw a TypeError if any of the hints
131-
values cannot be cast to a int.
131+
values cannot be cast to a int and can throw a ValueError if
132+
any of these values overflow.
132133

133134
- Zlib:
134135
. The "use_include_path" argument for the

ext/sockets/sockets.c

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2583,6 +2583,12 @@ PHP_FUNCTION(socket_addrinfo_lookup)
25832583

25842584
memset(&hints, 0, sizeof(hints));
25852585

2586+
#if defined(PHP_WIN32)
2587+
# if !defined(AF_MAX)
2588+
# define AF_MAX (AF_BTH + 1)
2589+
# endif
2590+
#endif
2591+
25862592
if (zhints && !HT_IS_PACKED(Z_ARRVAL_P(zhints))) {
25872593
ZEND_HASH_MAP_FOREACH_STR_KEY_VAL(Z_ARRVAL_P(zhints), key, hint) {
25882594
if (key) {
@@ -2593,27 +2599,43 @@ PHP_FUNCTION(socket_addrinfo_lookup)
25932599
zend_argument_type_error(3, "\"ai_flags\" key must be of type int, %s given", zend_zval_type_name(hint));
25942600
RETURN_THROWS();
25952601
}
2602+
if (val < 0 || val > INT_MAX) {
2603+
zend_argument_value_error(3, "\"ai_flags\" key must be between 0 and %d", INT_MAX);
2604+
RETURN_THROWS();
2605+
}
25962606
hints.ai_flags = (int)val;
25972607
} else if (zend_string_equals_literal(key, "ai_socktype")) {
25982608
zend_long val = zval_try_get_long(hint, &failed);
25992609
if (failed) {
26002610
zend_argument_type_error(3, "\"ai_socktype\" key must be of type int, %s given", zend_zval_type_name(hint));
26012611
RETURN_THROWS();
26022612
}
2613+
if (val < 0 || val > INT_MAX) {
2614+
zend_argument_value_error(3, "\"ai_socktype\" key must be between 0 and %d", INT_MAX);
2615+
RETURN_THROWS();
2616+
}
26032617
hints.ai_socktype = (int)val;
26042618
} else if (zend_string_equals_literal(key, "ai_protocol")) {
26052619
zend_long val = zval_try_get_long(hint, &failed);
26062620
if (failed) {
26072621
zend_argument_type_error(3, "\"ai_protocol\" key must be of type int, %s given", zend_zval_type_name(hint));
26082622
RETURN_THROWS();
26092623
}
2624+
if (val < 0 || val > INT_MAX) {
2625+
zend_argument_value_error(3, "\"ai_protocol\" key must be between 0 and %d", INT_MAX);
2626+
RETURN_THROWS();
2627+
}
26102628
hints.ai_protocol = (int)val;
26112629
} else if (zend_string_equals_literal(key, "ai_family")) {
26122630
zend_long val = zval_try_get_long(hint, &failed);
26132631
if (failed) {
26142632
zend_argument_type_error(3, "\"ai_family\" key must be of type int, %s given", zend_zval_type_name(hint));
26152633
RETURN_THROWS();
26162634
}
2635+
if (val < 0 || val >= AF_MAX) {
2636+
zend_argument_value_error(3, "\"ai_family\" key must be between 0 and %d", AF_MAX - 1);
2637+
RETURN_THROWS();
2638+
}
26172639
hints.ai_family = (int)val;
26182640
} else {
26192641
zend_argument_value_error(3, "must only contain array keys \"ai_flags\", \"ai_socktype\", "

ext/sockets/tests/socket_getaddrinfo_error.phpt

Lines changed: 45 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -44,9 +44,53 @@ try {
4444
} catch (\TypeError $e) {
4545
echo $e->getMessage() . PHP_EOL;
4646
}
47+
try {
48+
socket_addrinfo_lookup('127.0.0.1', 2000, array(
49+
'ai_family' => PHP_INT_MAX,
50+
'ai_socktype' => SOCK_DGRAM,
51+
'ai_flags' => 0,
52+
'ai_protocol' => 0,
53+
));
54+
} catch (\ValueError $e) {
55+
echo $e->getMessage() . PHP_EOL;
56+
}
57+
try {
58+
socket_addrinfo_lookup('127.0.0.1', 2000, array(
59+
'ai_family' => AF_INET,
60+
'ai_socktype' => -1,
61+
'ai_flags' => 0,
62+
'ai_protocol' => 0,
63+
));
64+
} catch (\ValueError $e) {
65+
echo $e->getMessage() . PHP_EOL;
66+
}
67+
try {
68+
socket_addrinfo_lookup('127.0.0.1', 2000, array(
69+
'ai_family' => AF_INET,
70+
'ai_socktype' => SOCK_DGRAM,
71+
'ai_flags' => -256,
72+
'ai_protocol' => 0,
73+
));
74+
} catch (\ValueError $e) {
75+
echo $e->getMessage() . PHP_EOL;
76+
}
77+
try {
78+
socket_addrinfo_lookup('127.0.0.1', 2000, array(
79+
'ai_family' => AF_INET,
80+
'ai_socktype' => SOCK_DGRAM,
81+
'ai_flags' => 0,
82+
'ai_protocol' => PHP_INT_MIN,
83+
));
84+
} catch (\ValueError $e) {
85+
echo $e->getMessage() . PHP_EOL;
86+
}
4787
?>
48-
--EXPECT--
88+
--EXPECTF--
4989
socket_addrinfo_lookup(): Argument #3 ($hints) "ai_family" key must be of type int, stdClass given
5090
socket_addrinfo_lookup(): Argument #3 ($hints) "ai_socktype" key must be of type int, stdClass given
5191
socket_addrinfo_lookup(): Argument #3 ($hints) "ai_flags" key must be of type int, stdClass given
5292
socket_addrinfo_lookup(): Argument #3 ($hints) "ai_protocol" key must be of type int, stdClass given
93+
socket_addrinfo_lookup(): Argument #3 ($hints) "ai_family" key must be between 0 and %d
94+
socket_addrinfo_lookup(): Argument #3 ($hints) "ai_socktype" key must be between 0 and %d
95+
socket_addrinfo_lookup(): Argument #3 ($hints) "ai_flags" key must be between 0 and %d
96+
socket_addrinfo_lookup(): Argument #3 ($hints) "ai_protocol" key must be between 0 and %d

0 commit comments

Comments
 (0)