[php-src] master: poll: fetch method ptr directly (#22816)
Gina Peter Banyard via GitHub <[email protected]> Mon, 20 Jul 2026 13:32:32 +0000
| Newsgroups | gmane.comp.php.cvs.general |
|---|---|
| Message-ID | <[email protected]> |
Author: Gina Peter Banyard (Girgias)
Committer: GitHub (web-flow)
Pusher: Girgias
Date: 2026-07-20T14:32:29+01:00
Commit: https://github.com/php/php-src/commit/55183b9d127bb8eba2d5e4b13e0c1536ff371d30
Raw diff: https://github.com/php/php-src/commit/55183b9d127bb8eba2d5e4b13e0c1536ff371d30.diff
poll: fetch method ptr directly (#22816)
Rather than going through a whole callability check via call_user_function() we can grab the known method pointer and call it directly.
This removes some allocations
Changed paths:
M main/poll/poll_handle.c
Diff:
diff --git a/main/poll/poll_handle.c b/main/poll/poll_handle.c
index 0c0628ac49dc..228d44e1e420 100644
--- a/main/poll/poll_handle.c
+++ b/main/poll/poll_handle.c
@@ -19,26 +19,22 @@
static php_socket_t php_poll_handle_default_get_fd(php_poll_handle_object *handle)
{
zval retval;
- zval obj;
- zval func_name;
- ZVAL_OBJ(&obj, &handle->std);
-
- /* Prepare function name as zval */
- ZVAL_STRING(&func_name, "getFileDescriptor");
+ /* Grab getFileDescriptor() method pointer which is stored in lowercase in the function table */
+ zend_function *method = zend_hash_str_find_ptr_lc(&handle->std.ce->function_table, ZEND_STRL("getfiledescriptor"));
+ ZEND_ASSERT(method && "no default method???");
/* Call getFileDescriptor() method */
- if (EXPECTED(call_user_function(NULL, &obj, &func_name, &retval, 0, NULL) == SUCCESS)) {
- if (Z_TYPE(retval) == IS_LONG) {
- php_socket_t fd = Z_LVAL(retval) < 0 ? SOCK_ERR : (php_socket_t) Z_LVAL(retval);
- zval_ptr_dtor(&retval);
- zval_ptr_dtor(&func_name); /* Clean up function name */
- return fd;
- }
- zval_ptr_dtor(&retval);
+ zend_call_known_function(method, &handle->std, handle->std.ce, &retval, 0, NULL, NULL);
+
+ /* No need to deref the return value as the class is final and thus the method cannot be changed to return by-ref */
+ if (EXPECTED(Z_TYPE(retval) == IS_LONG)) {
+ php_socket_t fd = Z_LVAL(retval) < 0 ? SOCK_ERR : (php_socket_t) Z_LVAL(retval);
+ /* No need to clean the retval as we know it is an integer, and thus it's just on the stack */
+ return fd;
}
- zval_ptr_dtor(&func_name); /* Clean up function name */
+ zval_ptr_dtor(&retval);
return SOCK_ERR; /* Invalid socket */
}