On Tue, Jul 24, 2001 at 08:34:44AM -0700, Chris Vandomelen wrote : 
> > > The new version (renamed, cleaned up) is fairly new, so it should be fine
> > > to do that.
> >
> > While we're at it, wouldn't it be more intuitiv to modify the
> > socket_fd_*() calls to accept the fd_set resource as first
> > parameter and the fd to add or remove as second parameter ?
> >
> 
> No problem with that request. I'll still get them confused though. :)
> 
> > For socket_fd_set() I'ld also vote to let the second parameter be
> > a single socket or an array of sockets (when you're dealing with
> > many connection you're likely holding them in an array than in
> > separate vars); same for socket_fd_clear(). Maybe, but I haven't
> > thought more about it, it would make sense for _isset() [after
> > writing this sentence I think not :) ].
> 
> *_set() and *_clear() it makes sense to accept an array for. *_isset(),
> OTOH, it doesn't. "Oh, I want to know if any of the fds 5, 6, 7, or 8 are
> set"... somehow that doesn't seem quite kosher. :)

I've come up with a patch based on the ideas and suggestion that
came up in this thread:

- Let the fd_set resource keep track of the highest socket; nuked
  _select() first parameter and determine it ourself
- Swapped _set(), _clear() and _isset() parameters and
  recognize plain sockets as well as array of sockets

The patch is against current CVS and only compiled unter linux
(debian unstable) so far.

Please everyone interested test and verify it and let me know
what you think. Due my lack of karma I can't commit it anyway,
feel free to do so if you find it appropriate.

- Markus

-- 
Markus Fischer,  http://guru.josefine.at/~mfischer/
EMail:         [EMAIL PROTECTED]
PGP Public  Key: http://guru.josefine.at/~mfischer/C2272BD0.asc
PGP Fingerprint: D3B0 DD4F E12B F911 3CE1  C2B5 D674 B445 C227 2BD0
? .php_sockets.h.swp
? .sockets.c.swp
Index: php_sockets.h
===================================================================
RCS file: /repository/php4/ext/sockets/php_sockets.h,v
retrieving revision 1.10
diff -u -r1.10 php_sockets.h
--- php_sockets.h       21 May 2001 19:36:22 -0000      1.10
+++ php_sockets.h       24 Jul 2001 17:59:52 -0000
@@ -82,6 +82,11 @@
        unsigned int count;
 } php_iovec_t;
 
+typedef struct php_fd_set {
+       fd_set set;
+       int max_fd;
+} php_fd_set_t;
+
 typedef struct {
 #ifdef PHP_WIN32
        SOCKET socket;
Index: sockets.c
===================================================================
RCS file: /repository/php4/ext/sockets/sockets.c,v
retrieving revision 1.56
diff -u -r1.56 sockets.c
--- sockets.c   16 Jul 2001 04:31:13 -0000      1.56
+++ sockets.c   24 Jul 2001 18:00:01 -0000
@@ -178,8 +178,8 @@
 
 static void destroy_fd_sets(zend_rsrc_list_entry *rsrc)
 {
-       fd_set *set = (fd_set *) rsrc->ptr;
-       efree(set);
+       php_fd_set_t *the_set = (php_fd_set_t *) rsrc->ptr;
+       efree(the_set);
 }
 
 static void destroy_iovec(zend_rsrc_list_entry *rsrc)
@@ -397,13 +397,14 @@
    Allocates a new file descriptor set */
 PHP_FUNCTION(socket_fd_alloc)
 {
-       fd_set *set;
+       php_fd_set_t *the_set;
 
-       set = emalloc(sizeof *set);
+       the_set = emalloc(sizeof(php_fd_set_t));
        
-       FD_ZERO(set);
+       FD_ZERO(&(the_set->set));
+       the_set->max_fd = -1;
        
-       ZEND_REGISTER_RESOURCE(return_value, set, le_destroy);
+       ZEND_REGISTER_RESOURCE(return_value, the_set, le_destroy);
 }
 /* }}} */
 
@@ -412,75 +413,97 @@
 PHP_FUNCTION(socket_fd_free)
 {
        zval **arg1;
-       fd_set *the_set;
+       php_fd_set_t *the_set;
        
        if (ZEND_NUM_ARGS() != 1 || zend_get_parameters_ex(1, &arg1) == FAILURE) {
                WRONG_PARAM_COUNT;
        }
        
-       ZEND_FETCH_RESOURCE(the_set, fd_set *, arg1, -1, le_destroy_name, le_destroy);
+       ZEND_FETCH_RESOURCE(the_set, php_fd_set_t *, arg1, -1, le_destroy_name, 
+le_destroy);
        
        zend_list_delete(Z_RESVAL_PP(arg1));
        RETURN_TRUE;
 }
 /* }}} */
 
-/* {{{ proto bool socket_fd_set(resource socket, resource set)
+/* {{{ proto bool socket_fd_set(resource set, mixed socket)
    Adds a file descriptor to a set */
 PHP_FUNCTION(socket_fd_set)
 {
-       zval **arg1, **arg2;
-       fd_set *the_set;
+       zval **arg1, **arg_socket, **arg_socket_entry;
+       php_fd_set_t *the_set;
        php_socket *php_sock;
 
-       if (ZEND_NUM_ARGS() != 2 || zend_get_parameters_ex(2, &arg1, &arg2) == 
FAILURE) {
+       if (ZEND_NUM_ARGS() != 2 || zend_get_parameters_ex(2, &arg1, &arg_socket) == 
+FAILURE) {
                WRONG_PARAM_COUNT;
        }
 
-       ZEND_FETCH_RESOURCE(php_sock, php_socket*, arg1, -1, le_socket_name, 
le_socket);
-       ZEND_FETCH_RESOURCE(the_set, fd_set*, arg2, -1, le_destroy_name, le_destroy);
+       ZEND_FETCH_RESOURCE(the_set, php_fd_set_t*, arg1, -1, le_destroy_name, 
+le_destroy);
+       if( Z_TYPE_PP( arg_socket) == IS_ARRAY) {
+               zend_hash_internal_pointer_reset( Z_ARRVAL_PP( arg_socket));
+               while( zend_hash_get_current_data( Z_ARRVAL_PP( arg_socket), 
+(void**)&arg_socket_entry) == SUCCESS) {
+                       ZEND_FETCH_RESOURCE( php_sock, php_socket*, arg_socket_entry, 
+-1, le_socket_name, le_socket);
+                       FD_SET(php_sock->socket, &(the_set->set));
+                       if( php_sock->socket > the_set->max_fd)
+                               the_set->max_fd = php_sock->socket;
+                       zend_hash_move_forward( Z_ARRVAL_PP( arg_socket));
+               }
+       } else {
+               ZEND_FETCH_RESOURCE(php_sock, php_socket*, arg_socket, -1, 
+le_socket_name, le_socket);
+               FD_SET(php_sock->socket, &(the_set->set));
+               if( php_sock->socket > the_set->max_fd)
+                       the_set->max_fd = php_sock->socket;
+       }
 
-       FD_SET(php_sock->socket, the_set);
        RETURN_TRUE;
 }
 /* }}} */
 
-/* {{{ proto bool socket_fd_clear(resource socket, resource set)
+/* {{{ proto bool socket_fd_clear(resource set, mixed socket)
    Clears a file descriptor from a set */
 PHP_FUNCTION(socket_fd_clear)
 {
-       zval **arg1, **arg2;
-       fd_set *the_set;
+       zval **arg1, **arg_socket, **arg_socket_entry;
+       php_fd_set_t *the_set;
        php_socket *php_sock;
 
-       if (ZEND_NUM_ARGS() != 2 || zend_get_parameters_ex(2, &arg1, &arg2) == 
FAILURE) {
+       if (ZEND_NUM_ARGS() != 2 || zend_get_parameters_ex(2, &arg1, &arg_socket) == 
+FAILURE) {
                WRONG_PARAM_COUNT;
        }
 
-       ZEND_FETCH_RESOURCE(php_sock, php_socket*, arg1, -1, le_socket_name, 
le_socket);
-       ZEND_FETCH_RESOURCE(the_set, fd_set *, arg2, -1, le_destroy_name, le_destroy);
+       ZEND_FETCH_RESOURCE(the_set, php_fd_set_t *, arg1, -1, le_destroy_name, 
+le_destroy);
+       if( Z_TYPE_PP( arg_socket) == IS_ARRAY) {
+               zend_hash_internal_pointer_reset( Z_ARRVAL_PP( arg_socket));
+               while( zend_hash_get_current_data( Z_ARRVAL_PP( arg_socket), 
+(void**)&arg_socket_entry) == SUCCESS) {
+                       ZEND_FETCH_RESOURCE( php_sock, php_socket*, arg_socket_entry, 
+-1, le_socket_name, le_socket);
+                       FD_CLR(php_sock->socket, &(the_set->set));
+                       zend_hash_move_forward( Z_ARRVAL_PP( arg_socket));
+               }
+       } else {
+               ZEND_FETCH_RESOURCE(php_sock, php_socket*, arg_socket, -1, 
+le_socket_name, le_socket);
+               FD_CLR(php_sock->socket, &(the_set->set));
+       }
 
-       FD_CLR(php_sock->socket, the_set);
        RETURN_TRUE;
 }
 /* }}} */
 
-/* {{{ proto bool socket_fd_isset(resource socket, resource set)
+/* {{{ proto bool socket_fd_isset(resource set, resource socket)
    Checks to see if a file descriptor is set within the file descrirptor set */
 PHP_FUNCTION(socket_fd_isset)
 {
        zval **arg1, **arg2;
-       fd_set *the_set;
+       php_fd_set_t *the_set;
        php_socket *php_sock;
 
        if (ZEND_NUM_ARGS() != 2 || zend_get_parameters_ex(2, &arg1, &arg2) == 
FAILURE) {
                WRONG_PARAM_COUNT;
        }
 
-       ZEND_FETCH_RESOURCE(php_sock, php_socket*, arg1, -1, le_socket_name, 
le_socket);
-       ZEND_FETCH_RESOURCE(the_set, fd_set *, arg2, -1, le_destroy_name, le_destroy);
+       ZEND_FETCH_RESOURCE(the_set, php_fd_set_t *, arg1, -1, le_destroy_name, 
+le_destroy);
+       ZEND_FETCH_RESOURCE(php_sock, php_socket*, arg2, -1, le_socket_name, 
+le_socket);
 
-       if (FD_ISSET(php_sock->socket, the_set)) {
+       if (FD_ISSET(php_sock->socket, &(the_set->set))) {
                RETURN_TRUE;
        }
 
@@ -493,15 +516,16 @@
 PHP_FUNCTION(socket_fd_zero)
 {
        zval **arg1;
-       fd_set *the_set;
+       php_fd_set_t *the_set;
 
        if (ZEND_NUM_ARGS() != 1 || zend_get_parameters_ex(1, &arg1) == FAILURE) {
                WRONG_PARAM_COUNT;
        }
 
-       ZEND_FETCH_RESOURCE(the_set, fd_set *, arg1, -1, le_destroy_name, le_destroy);
+       ZEND_FETCH_RESOURCE(the_set, php_fd_set_t *, arg1, -1, le_destroy_name, 
+le_destroy);
 
-       FD_ZERO(the_set);
+       FD_ZERO(&(the_set->set));
+       the_set->max_fd = -1;
 
        RETURN_TRUE;
 }
@@ -511,24 +535,32 @@
    Runs the select() system call on the sets mentioned with a timeout specified by 
tv_sec and tv_usec */
 PHP_FUNCTION(socket_select)
 {
-       zval **arg1, **arg2, **arg3, **arg4, **arg5, **arg6;
+       zval **arg1, **arg2, **arg3, **arg4, **arg5;
        struct timeval tv;
-       fd_set *rfds, *wfds, *xfds;
+       php_fd_set_t *rfds, *wfds, *xfds;
+       int highest = -1;
 
-       if (zend_get_parameters_ex(6, &arg1, &arg2, &arg3, &arg4, &arg5, &arg6) == 
FAILURE) {
+       if (zend_get_parameters_ex(5, &arg1, &arg2, &arg3, &arg4, &arg5) == FAILURE) {
                WRONG_PARAM_COUNT;
        }
        
-       convert_to_long_ex(arg1);
+       ZEND_FETCH_RESOURCE(rfds, php_fd_set_t *, arg1, -1, le_destroy_name, 
+le_destroy);
+       ZEND_FETCH_RESOURCE(wfds, php_fd_set_t *, arg2, -1, le_destroy_name, 
+le_destroy);
+       ZEND_FETCH_RESOURCE(xfds, php_fd_set_t *, arg3, -1, le_destroy_name, 
+le_destroy);
+       convert_to_long_ex(arg4);
        convert_to_long_ex(arg5);
-       convert_to_long_ex(arg6);
-       ZEND_FETCH_RESOURCE(rfds, fd_set *, arg2, -1, le_destroy_name, le_destroy);
-       ZEND_FETCH_RESOURCE(wfds, fd_set *, arg3, -1, le_destroy_name, le_destroy);
-       ZEND_FETCH_RESOURCE(xfds, fd_set *, arg4, -1, le_destroy_name, le_destroy);
-       tv.tv_sec  = Z_LVAL_PP(arg5);
-       tv.tv_usec = Z_LVAL_PP(arg6);
+       tv.tv_sec  = Z_LVAL_PP(arg4);
+       tv.tv_usec = Z_LVAL_PP(arg5);
+
+       if( rfds->max_fd > highest)
+               highest = rfds->max_fd;
+       if( wfds->max_fd > highest)
+               highest = wfds->max_fd;
+       if( xfds->max_fd > highest)
+               highest = xfds->max_fd;
+       highest++;
 
-       RETURN_LONG(select(Z_LVAL_PP(arg1), rfds, wfds, xfds, &tv));
+       RETURN_LONG(select(highest, &(rfds->set), &(wfds->set), &(xfds->set), &tv));
 }
 /* }}} */
 

-- 
PHP Development Mailing List <http://www.php.net/>
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]
To contact the list administrators, e-mail: [EMAIL PROTECTED]

Reply via email to