Skip to content

Commit 34866e9

Browse files
committed
Convert CLI server to new internal polling API
Similar to GH-22796.
1 parent de5a582 commit 34866e9

1 file changed

Lines changed: 37 additions & 107 deletions

File tree

sapi/cli/php_cli_server.c

Lines changed: 37 additions & 107 deletions
Original file line numberDiff line numberDiff line change
@@ -74,17 +74,14 @@
7474

7575
#include "php_getopt.h"
7676

77+
#include "php_poll.h"
7778
#ifndef PHP_WIN32
78-
# define php_select(m, r, w, e, t) select(m, r, w, e, t)
7979
# define SOCK_EINVAL EINVAL
8080
# define SOCK_EAGAIN EAGAIN
81-
# define SOCK_EINTR EINTR
8281
# define SOCK_EADDRINUSE EADDRINUSE
8382
#else
84-
# include "win32/select.h"
8583
# define SOCK_EINVAL WSAEINVAL
8684
# define SOCK_EAGAIN WSAEWOULDBLOCK
87-
# define SOCK_EINTR WSAEINTR
8885
# define SOCK_EADDRINUSE WSAEADDRINUSE
8986
#endif
9087

@@ -117,11 +114,9 @@ static zend_long php_cli_server_workers_max;
117114
static zend_string* cli_concat_persistent_zstr_with_char(zend_string *old_str, const char *at, size_t length);
118115

119116
typedef struct php_cli_server_poller {
120-
fd_set rfds, wfds;
121-
struct {
122-
fd_set rfds, wfds;
123-
} active;
124-
php_socket_t max_fd;
117+
php_poll_ctx *poll_ctx;
118+
php_poll_event *events;
119+
int count;
125120
} php_cli_server_poller;
126121

127122
typedef struct php_cli_server_request {
@@ -821,112 +816,48 @@ sapi_module_struct cli_server_sapi_module = {
821816

822817
static void php_cli_server_poller_ctor(php_cli_server_poller *poller) /* {{{ */
823818
{
824-
FD_ZERO(&poller->rfds);
825-
FD_ZERO(&poller->wfds);
826-
poller->max_fd = -1;
819+
uint32_t flags = PHP_POLL_FLAG_PERSISTENT | PHP_POLL_FLAG_RAW_EVENTS;
820+
php_poll_register_backends();
821+
poller->poll_ctx = php_poll_create(PHP_POLL_BACKEND_AUTO, flags);
822+
php_poll_init(poller->poll_ctx);
823+
poller->count = php_poll_get_suitable_max_events(poller->poll_ctx);
824+
poller->events = pecalloc(poller->count, sizeof(php_poll_event), 1);
827825
} /* }}} */
828826

829827
static void php_cli_server_poller_add(php_cli_server_poller *poller, int mode, php_socket_t fd) /* {{{ */
830828
{
831-
if (mode & POLLIN) {
832-
PHP_SAFE_FD_SET(fd, &poller->rfds);
833-
}
834-
if (mode & POLLOUT) {
835-
PHP_SAFE_FD_SET(fd, &poller->wfds);
836-
}
837-
if (fd > poller->max_fd) {
838-
poller->max_fd = fd;
839-
}
829+
php_poll_add(poller->poll_ctx, fd, mode, NULL);
840830
} /* }}} */
841831

842832
static void php_cli_server_poller_remove(php_cli_server_poller *poller, int mode, php_socket_t fd) /* {{{ */
843833
{
844-
if (mode & POLLIN) {
845-
PHP_SAFE_FD_CLR(fd, &poller->rfds);
846-
}
847-
if (mode & POLLOUT) {
848-
PHP_SAFE_FD_CLR(fd, &poller->wfds);
849-
}
850-
#ifndef PHP_WIN32
851-
if (fd == poller->max_fd) {
852-
while (fd > 0) {
853-
fd--;
854-
if (PHP_SAFE_FD_ISSET(fd, &poller->rfds) || PHP_SAFE_FD_ISSET(fd, &poller->wfds)) {
855-
break;
856-
}
857-
}
858-
poller->max_fd = fd;
859-
}
860-
#endif
834+
/* XXX: Should be modify if mode is different from what was added? */
835+
php_poll_remove(poller->poll_ctx, fd);
861836
} /* }}} */
862837

863838
static int php_cli_server_poller_poll(php_cli_server_poller *poller, struct timeval *tv) /* {{{ */
864839
{
865-
memmove(&poller->active.rfds, &poller->rfds, sizeof(poller->rfds));
866-
memmove(&poller->active.wfds, &poller->wfds, sizeof(poller->wfds));
867-
return php_select(poller->max_fd + 1, &poller->active.rfds, &poller->active.wfds, NULL, tv);
840+
struct timespec ts;
841+
TIMEVAL_TO_TIMESPEC(tv, &ts);
842+
return php_poll_wait(poller->poll_ctx, poller->events, poller->count, &ts);
868843
} /* }}} */
869844

870845
static zend_result php_cli_server_poller_iter_on_active(php_cli_server_poller *poller, void *opaque, zend_result(*callback)(void *, php_socket_t fd, int events)) /* {{{ */
871846
{
872847
zend_result retval = SUCCESS;
873-
#ifdef PHP_WIN32
874-
struct socket_entry {
875-
SOCKET fd;
876-
int events;
877-
} entries[FD_SETSIZE * 2];
878-
size_t i;
879-
struct socket_entry *n = entries, *m;
880-
881-
for (i = 0; i < poller->active.rfds.fd_count; i++) {
882-
n->events = POLLIN;
883-
n->fd = poller->active.rfds.fd_array[i];
884-
n++;
885-
}
886-
887-
m = n;
888-
for (i = 0; i < poller->active.wfds.fd_count; i++) {
889-
struct socket_entry *e;
890-
SOCKET fd = poller->active.wfds.fd_array[i];
891-
for (e = entries; e < m; e++) {
892-
if (e->fd == fd) {
893-
e->events |= POLLOUT;
848+
for (int i = 0; i < poller->count; i++) {
849+
int fd = poller->events[i].fd;
850+
if (poller->events[i].revents & PHP_POLL_READ) {
851+
if (SUCCESS != callback(opaque, fd, PHP_POLL_READ)) {
852+
retval = FAILURE;
894853
}
895854
}
896-
if (e == m) {
897-
assert(n < entries + FD_SETSIZE * 2);
898-
n->events = POLLOUT;
899-
n->fd = fd;
900-
n++;
901-
}
902-
}
903-
904-
{
905-
struct socket_entry *e = entries;
906-
for (; e < n; e++) {
907-
if (SUCCESS != callback(opaque, e->fd, e->events)) {
855+
if (poller->events[i].revents & PHP_POLL_WRITE) {
856+
if (SUCCESS != callback(opaque, fd, PHP_POLL_WRITE)) {
908857
retval = FAILURE;
909858
}
910859
}
911860
}
912-
913-
#else
914-
php_socket_t fd;
915-
const php_socket_t max_fd = poller->max_fd;
916-
917-
for (fd=0 ; fd<=max_fd ; fd++) {
918-
if (PHP_SAFE_FD_ISSET(fd, &poller->active.rfds)) {
919-
if (SUCCESS != callback(opaque, fd, POLLIN)) {
920-
retval = FAILURE;
921-
}
922-
}
923-
if (PHP_SAFE_FD_ISSET(fd, &poller->active.wfds)) {
924-
if (SUCCESS != callback(opaque, fd, POLLOUT)) {
925-
retval = FAILURE;
926-
}
927-
}
928-
}
929-
#endif
930861
return retval;
931862
} /* }}} */
932863

@@ -1901,7 +1832,7 @@ static size_t php_cli_server_client_send_through(php_cli_server_client *client,
19011832
if (nbytes_sent < 0) {
19021833
int err = php_socket_errno();
19031834
if (err == SOCK_EAGAIN) {
1904-
int nfds = php_pollfd_for(client->sock, POLLOUT, &tv);
1835+
int nfds = php_pollfd_for(client->sock, PHP_POLL_WRITE, &tv);
19051836
if (nfds > 0) {
19061837
continue;
19071838
} else {
@@ -2090,7 +2021,7 @@ static zend_result php_cli_server_send_error_page(php_cli_server *server, php_cl
20902021
}
20912022

20922023
php_cli_server_log_response(client, status, errstr ? errstr : "?");
2093-
php_cli_server_poller_add(&server->poller, POLLOUT, client->sock);
2024+
php_cli_server_poller_add(&server->poller, PHP_POLL_WRITE, client->sock);
20942025
if (errstr) {
20952026
pefree(errstr, 1);
20962027
}
@@ -2203,7 +2134,7 @@ static zend_result php_cli_server_begin_send_static(php_cli_server *server, php_
22032134
php_cli_server_buffer_append(&client->content_sender.buffer, chunk);
22042135
}
22052136
php_cli_server_log_response(client, 200, NULL);
2206-
php_cli_server_poller_add(&server->poller, POLLOUT, client->sock);
2137+
php_cli_server_poller_add(&server->poller, PHP_POLL_WRITE, client->sock);
22072138
return SUCCESS;
22082139
}
22092140
/* }}} */
@@ -2405,7 +2336,7 @@ static void php_cli_server_client_dtor_wrapper(zval *zv) /* {{{ */
24052336

24062337
shutdown(p->sock, SHUT_RDWR);
24072338
closesocket(p->sock);
2408-
php_cli_server_poller_remove(&p->server->poller, POLLIN | POLLOUT, p->sock);
2339+
php_cli_server_poller_remove(&p->server->poller, PHP_POLL_READ | PHP_POLL_WRITE, p->sock);
24092340
php_cli_server_client_dtor(p);
24102341
pefree(p, 1);
24112342
} /* }}} */
@@ -2575,7 +2506,7 @@ static zend_result php_cli_server_ctor(php_cli_server *server, const char *addr,
25752506

25762507
php_cli_server_poller_ctor(&server->poller);
25772508

2578-
php_cli_server_poller_add(&server->poller, POLLIN, server_sock);
2509+
php_cli_server_poller_add(&server->poller, PHP_POLL_READ, server_sock);
25792510

25802511
server->host = host;
25812512
server->port = port;
@@ -2641,10 +2572,10 @@ static zend_result php_cli_server_recv_event_read_request(php_cli_server *server
26412572
if (client->request.request_method == PHP_HTTP_NOT_IMPLEMENTED) {
26422573
return php_cli_server_send_error_page(server, client, 501);
26432574
}
2644-
php_cli_server_poller_remove(&server->poller, POLLIN, client->sock);
2575+
php_cli_server_poller_remove(&server->poller, PHP_POLL_READ, client->sock);
26452576
return php_cli_server_dispatch(server, client);
26462577
case 0:
2647-
php_cli_server_poller_add(&server->poller, POLLIN, client->sock);
2578+
php_cli_server_poller_add(&server->poller, PHP_POLL_READ, client->sock);
26482579
return SUCCESS;
26492580
default: ZEND_UNREACHABLE();
26502581
}
@@ -2724,14 +2655,14 @@ static zend_result php_cli_server_do_event_for_each_fd_callback(void *_params, p
27242655

27252656
zend_hash_index_update_ptr(&server->clients, client_sock, client);
27262657

2727-
php_cli_server_poller_add(&server->poller, POLLIN, client->sock);
2658+
php_cli_server_poller_add(&server->poller, PHP_POLL_READ, client->sock);
27282659
} else {
27292660
php_cli_server_client *client;
27302661
if (NULL != (client = zend_hash_index_find_ptr(&server->clients, fd))) {
2731-
if (event & POLLIN) {
2662+
if (event & PHP_POLL_READ) {
27322663
params->rhandler(server, client);
27332664
}
2734-
if (event & POLLOUT) {
2665+
if (event & PHP_POLL_WRITE) {
27352666
params->whandler(server, client);
27362667
}
27372668
}
@@ -2767,12 +2698,11 @@ static zend_result php_cli_server_do_event_loop(php_cli_server *server) /* {{{ *
27672698
} else if (n == 0) {
27682699
/* do nothing */
27692700
} else {
2770-
int err = php_socket_errno();
2771-
if (err != SOCK_EINTR) {
2701+
php_poll_error err = php_poll_get_error(server->poller.poll_ctx);
2702+
if (err != PHP_POLL_ERR_INTERRUPTED) {
27722703
if (php_cli_server_log_level >= PHP_CLI_SERVER_LOG_ERROR) {
2773-
char *errstr = php_socket_strerror(err, NULL, 0);
2774-
php_cli_server_logf(PHP_CLI_SERVER_LOG_ERROR, "%s", errstr);
2775-
efree(errstr);
2704+
const char *errstr = php_poll_error_string(err);
2705+
php_cli_server_logf(PHP_CLI_SERVER_LOG_ERROR, "Poll error: %s", errstr);
27762706
}
27772707
retval = FAILURE;
27782708
goto out;

0 commit comments

Comments
 (0)