Back to index

php5  5.3.10
Defines | Functions | Variables
xp_socket.c File Reference
#include "php.h"
#include "ext/standard/file.h"
#include "streams/php_streams_int.h"
#include "php_network.h"

Go to the source code of this file.

Defines

#define MSG_DONTWAIT   0
#define MSG_PEEK   0

Functions

static int php_tcp_sockop_set_option (php_stream *stream, int option, int value, void *ptrparam TSRMLS_DC)
static size_t php_sockop_write (php_stream *stream, const char *buf, size_t count TSRMLS_DC)
static void php_sock_stream_wait_for_data (php_stream *stream, php_netstream_data_t *sock TSRMLS_DC)
static size_t php_sockop_read (php_stream *stream, char *buf, size_t count TSRMLS_DC)
static int php_sockop_close (php_stream *stream, int close_handle TSRMLS_DC)
static int php_sockop_flush (php_stream *stream TSRMLS_DC)
static int php_sockop_stat (php_stream *stream, php_stream_statbuf *ssb TSRMLS_DC)
static int sock_sendto (php_netstream_data_t *sock, char *buf, size_t buflen, int flags, struct sockaddr *addr, socklen_t addrlen TSRMLS_DC)
static int sock_recvfrom (php_netstream_data_t *sock, char *buf, size_t buflen, int flags, char **textaddr, long *textaddrlen, struct sockaddr **addr, socklen_t *addrlen TSRMLS_DC)
static int php_sockop_set_option (php_stream *stream, int option, int value, void *ptrparam TSRMLS_DC)
static int php_sockop_cast (php_stream *stream, int castas, void **ret TSRMLS_DC)
static char * parse_ip_address_ex (const char *str, int str_len, int *portno, int get_err, char **err TSRMLS_DC)
static char * parse_ip_address (php_stream_xport_param *xparam, int *portno TSRMLS_DC)
static int php_tcp_sockop_bind (php_stream *stream, php_netstream_data_t *sock, php_stream_xport_param *xparam TSRMLS_DC)
static int php_tcp_sockop_connect (php_stream *stream, php_netstream_data_t *sock, php_stream_xport_param *xparam TSRMLS_DC)
static int php_tcp_sockop_accept (php_stream *stream, php_netstream_data_t *sock, php_stream_xport_param *xparam STREAMS_DC TSRMLS_DC)
PHPAPI php_stream * php_stream_generic_socket_factory (const char *proto, long protolen, char *resourcename, long resourcenamelen, const char *persistent_id, int options, int flags, struct timeval *timeout, php_stream_context *context STREAMS_DC TSRMLS_DC)

Variables

php_stream_ops php_stream_generic_socket_ops
PHPAPI php_stream_ops php_stream_socket_ops
php_stream_ops php_stream_udp_socket_ops

Define Documentation

#define MSG_DONTWAIT   0

Definition at line 35 of file xp_socket.c.

#define MSG_PEEK   0

Definition at line 39 of file xp_socket.c.


Function Documentation

static char* parse_ip_address ( php_stream_xport_param xparam,
int *portno  TSRMLS_DC 
) [inline, static]

Definition at line 564 of file xp_socket.c.

{
       return parse_ip_address_ex(xparam->inputs.name, xparam->inputs.namelen, portno, xparam->want_errortext, &xparam->outputs.error_text TSRMLS_CC);
}

Here is the call graph for this function:

Here is the caller graph for this function:

static char* parse_ip_address_ex ( const char *  str,
int  str_len,
int portno,
int  get_err,
char **err  TSRMLS_DC 
) [inline, static]

Definition at line 525 of file xp_socket.c.

{
       char *colon;
       char *host = NULL;

#ifdef HAVE_IPV6
       char *p;

       if (*(str) == '[' && str_len > 1) {
              /* IPV6 notation to specify raw address with port (i.e. [fe80::1]:80) */
              p = memchr(str + 1, ']', str_len - 2);
              if (!p || *(p + 1) != ':') {
                     if (get_err) {
                            spprintf(err, 0, "Failed to parse IPv6 address \"%s\"", str);
                     }
                     return NULL;
              }
              *portno = atoi(p + 2);
              return estrndup(str + 1, p - str - 1);
       }
#endif
       if (str_len) {
              colon = memchr(str, ':', str_len - 1);
       } else {
              colon = NULL;
       }
       if (colon) {
              *portno = atoi(colon + 1);
              host = estrndup(str, colon - str);
       } else {
              if (get_err) {
                     spprintf(err, 0, "Failed to parse address \"%s\"", str);
              }
              return NULL;
       }

       return host;
}

Here is the call graph for this function:

Here is the caller graph for this function:

static void php_sock_stream_wait_for_data ( php_stream *  stream,
php_netstream_data_t *sock  TSRMLS_DC 
) [static]

Definition at line 114 of file xp_socket.c.

{
       int retval;
       struct timeval *ptimeout;

       if (sock->socket == -1) {
              return;
       }
       
       sock->timeout_event = 0;

       if (sock->timeout.tv_sec == -1)
              ptimeout = NULL;
       else
              ptimeout = &sock->timeout;

       while(1) {
              retval = php_pollfd_for(sock->socket, PHP_POLLREADABLE, ptimeout);

              if (retval == 0)
                     sock->timeout_event = 1;

              if (retval >= 0)
                     break;

              if (php_socket_errno() != EINTR)
                     break;
       }
}

Here is the call graph for this function:

Here is the caller graph for this function:

static int php_sockop_cast ( php_stream *  stream,
int  castas,
void **ret  TSRMLS_DC 
) [static]

Definition at line 416 of file xp_socket.c.

{
       php_netstream_data_t *sock = (php_netstream_data_t*)stream->abstract;

       switch(castas)       {
              case PHP_STREAM_AS_STDIO:
                     if (ret)      {
                            *(FILE**)ret = fdopen(sock->socket, stream->mode);
                            if (*ret)
                                   return SUCCESS;
                            return FAILURE;
                     }
                     return SUCCESS;
              case PHP_STREAM_AS_FD_FOR_SELECT:
              case PHP_STREAM_AS_FD:
              case PHP_STREAM_AS_SOCKETD:
                     if (ret)
                            *(int*)ret = sock->socket;
                     return SUCCESS;
              default:
                     return FAILURE;
       }
}
static int php_sockop_close ( php_stream *  stream,
int close_handle  TSRMLS_DC 
) [static]

Definition at line 175 of file xp_socket.c.

{
       php_netstream_data_t *sock = (php_netstream_data_t*)stream->abstract;
#ifdef PHP_WIN32
       int n;
#endif

       if (close_handle) {

#ifdef PHP_WIN32
              if (sock->socket == -1)
                     sock->socket = SOCK_ERR;
#endif
              if (sock->socket != SOCK_ERR) {
#ifdef PHP_WIN32
                     /* prevent more data from coming in */
                     shutdown(sock->socket, SHUT_RD);

                     /* try to make sure that the OS sends all data before we close the connection.
                      * Essentially, we are waiting for the socket to become writeable, which means
                      * that all pending data has been sent.
                      * We use a small timeout which should encourage the OS to send the data,
                      * but at the same time avoid hanging indefintely.
                      * */
                     do {
                            n = php_pollfd_for_ms(sock->socket, POLLOUT, 500);
                     } while (n == -1 && php_socket_errno() == EINTR);
#endif
                     closesocket(sock->socket);
                     sock->socket = SOCK_ERR;
              }

       }

       pefree(sock, php_stream_is_persistent(stream));
       
       return 0;
}

Here is the call graph for this function:

static int php_sockop_flush ( php_stream *stream  TSRMLS_DC) [static]

Definition at line 214 of file xp_socket.c.

{
#if 0
       php_netstream_data_t *sock = (php_netstream_data_t*)stream->abstract;
       return fsync(sock->socket);
#endif
       return 0;
}
static size_t php_sockop_read ( php_stream *  stream,
char *  buf,
size_t count  TSRMLS_DC 
) [static]

Definition at line 144 of file xp_socket.c.

{
       php_netstream_data_t *sock = (php_netstream_data_t*)stream->abstract;
       int nr_bytes = 0;

       if (sock->socket == -1) {
              return 0;
       }

       if (sock->is_blocked) {
              php_sock_stream_wait_for_data(stream, sock TSRMLS_CC);
              if (sock->timeout_event)
                     return 0;
       }

       nr_bytes = recv(sock->socket, buf, count, (sock->is_blocked && sock->timeout.tv_sec != -1) ? MSG_DONTWAIT : 0);

       stream->eof = (nr_bytes == 0 || (nr_bytes == -1 && php_socket_errno() != EWOULDBLOCK));

       if (nr_bytes > 0) {
              php_stream_notify_progress_increment(stream->context, nr_bytes, 0);
       }

       if (nr_bytes < 0) {
              nr_bytes = 0;
       }

       return nr_bytes;
}

Here is the call graph for this function:

static int php_sockop_set_option ( php_stream *  stream,
int  option,
int  value,
void *ptrparam  TSRMLS_DC 
) [static]

Definition at line 268 of file xp_socket.c.

{
       int oldmode, flags;
       php_netstream_data_t *sock = (php_netstream_data_t*)stream->abstract;
       php_stream_xport_param *xparam;
       
       switch(option) {
              case PHP_STREAM_OPTION_CHECK_LIVENESS:
                     {
                            struct timeval tv;
                            char buf;
                            int alive = 1;

                            if (value == -1) {
                                   if (sock->timeout.tv_sec == -1) {
                                          tv.tv_sec = FG(default_socket_timeout);
                                          tv.tv_usec = 0;
                                   } else {
                                          tv = sock->timeout;
                                   }
                            } else {
                                   tv.tv_sec = value;
                                   tv.tv_usec = 0;
                            }

                            if (sock->socket == -1) {
                                   alive = 0;
                            } else if (php_pollfd_for(sock->socket, PHP_POLLREADABLE|POLLPRI, &tv) > 0) {
                                   if (0 >= recv(sock->socket, &buf, sizeof(buf), MSG_PEEK) && php_socket_errno() != EWOULDBLOCK) {
                                          alive = 0;
                                   }
                            }
                            return alive ? PHP_STREAM_OPTION_RETURN_OK : PHP_STREAM_OPTION_RETURN_ERR;
                     }
                     
              case PHP_STREAM_OPTION_BLOCKING:
                     oldmode = sock->is_blocked;
                     if (SUCCESS == php_set_sock_blocking(sock->socket, value TSRMLS_CC)) {
                            sock->is_blocked = value;
                            return oldmode;
                     }
                     return PHP_STREAM_OPTION_RETURN_ERR;

              case PHP_STREAM_OPTION_READ_TIMEOUT:
                     sock->timeout = *(struct timeval*)ptrparam;
                     sock->timeout_event = 0;
                     return PHP_STREAM_OPTION_RETURN_OK;

              case PHP_STREAM_OPTION_META_DATA_API:
                     add_assoc_bool((zval *)ptrparam, "timed_out", sock->timeout_event);
                     add_assoc_bool((zval *)ptrparam, "blocked", sock->is_blocked);
                     add_assoc_bool((zval *)ptrparam, "eof", stream->eof);
                     return PHP_STREAM_OPTION_RETURN_OK;
              
              case PHP_STREAM_OPTION_XPORT_API:
                     xparam = (php_stream_xport_param *)ptrparam;

                     switch (xparam->op) {
                            case STREAM_XPORT_OP_LISTEN:
                                   xparam->outputs.returncode = (listen(sock->socket, xparam->inputs.backlog) == 0) ?  0: -1;
                                   return PHP_STREAM_OPTION_RETURN_OK;

                            case STREAM_XPORT_OP_GET_NAME:
                                   xparam->outputs.returncode = php_network_get_sock_name(sock->socket,
                                                 xparam->want_textaddr ? &xparam->outputs.textaddr : NULL,
                                                 xparam->want_textaddr ? &xparam->outputs.textaddrlen : NULL,
                                                 xparam->want_addr ? &xparam->outputs.addr : NULL,
                                                 xparam->want_addr ? &xparam->outputs.addrlen : NULL
                                                 TSRMLS_CC);
                                   return PHP_STREAM_OPTION_RETURN_OK;

                            case STREAM_XPORT_OP_GET_PEER_NAME:
                                   xparam->outputs.returncode = php_network_get_peer_name(sock->socket,
                                                 xparam->want_textaddr ? &xparam->outputs.textaddr : NULL,
                                                 xparam->want_textaddr ? &xparam->outputs.textaddrlen : NULL,
                                                 xparam->want_addr ? &xparam->outputs.addr : NULL,
                                                 xparam->want_addr ? &xparam->outputs.addrlen : NULL
                                                 TSRMLS_CC);
                                   return PHP_STREAM_OPTION_RETURN_OK;

                            case STREAM_XPORT_OP_SEND:
                                   flags = 0;
                                   if ((xparam->inputs.flags & STREAM_OOB) == STREAM_OOB) {
                                          flags |= MSG_OOB;
                                   }
                                   xparam->outputs.returncode = sock_sendto(sock,
                                                 xparam->inputs.buf, xparam->inputs.buflen,
                                                 flags,
                                                 xparam->inputs.addr,
                                                 xparam->inputs.addrlen TSRMLS_CC);
                                   if (xparam->outputs.returncode == -1) {
                                          char *err = php_socket_strerror(php_socket_errno(), NULL, 0);
                                          php_error_docref(NULL TSRMLS_CC, E_WARNING,
                                                 "%s\n", err);
                                          efree(err);
                                   }
                                   return PHP_STREAM_OPTION_RETURN_OK;

                            case STREAM_XPORT_OP_RECV:
                                   flags = 0;
                                   if ((xparam->inputs.flags & STREAM_OOB) == STREAM_OOB) {
                                          flags |= MSG_OOB;
                                   }
                                   if ((xparam->inputs.flags & STREAM_PEEK) == STREAM_PEEK) {
                                          flags |= MSG_PEEK;
                                   }
                                   xparam->outputs.returncode = sock_recvfrom(sock,
                                                 xparam->inputs.buf, xparam->inputs.buflen,
                                                 flags,
                                                 xparam->want_textaddr ? &xparam->outputs.textaddr : NULL,
                                                 xparam->want_textaddr ? &xparam->outputs.textaddrlen : NULL,
                                                 xparam->want_addr ? &xparam->outputs.addr : NULL,
                                                 xparam->want_addr ? &xparam->outputs.addrlen : NULL
                                                 TSRMLS_CC);
                                   return PHP_STREAM_OPTION_RETURN_OK;


#ifdef HAVE_SHUTDOWN
# ifndef SHUT_RD
#  define SHUT_RD 0
# endif
# ifndef SHUT_WR
#  define SHUT_WR 1
# endif
# ifndef SHUT_RDWR
#  define SHUT_RDWR 2
# endif
                            case STREAM_XPORT_OP_SHUTDOWN: {
                                   static const int shutdown_how[] = {SHUT_RD, SHUT_WR, SHUT_RDWR};

                                   xparam->outputs.returncode = shutdown(sock->socket, shutdown_how[xparam->how]);
                                   return PHP_STREAM_OPTION_RETURN_OK;
                            }
#endif
                            
                            case PHP_STREAM_OPTION_WRITE_BUFFER:
                                   php_stream_set_chunk_size(stream, (ptrparam ? *(size_t *)ptrparam : PHP_SOCK_CHUNK_SIZE));
                                   return PHP_STREAM_OPTION_RETURN_OK;

                            default:
                                   return PHP_STREAM_OPTION_RETURN_NOTIMPL;
                     }

              default:
                     return PHP_STREAM_OPTION_RETURN_NOTIMPL;
       }
}

Here is the call graph for this function:

Here is the caller graph for this function:

static int php_sockop_stat ( php_stream *  stream,
php_stream_statbuf *ssb  TSRMLS_DC 
) [static]

Definition at line 223 of file xp_socket.c.

{
       php_netstream_data_t *sock = (php_netstream_data_t*)stream->abstract;
#if ZEND_WIN32
       return 0;
#else
       return fstat(sock->socket, &ssb->sb);
#endif
}
static size_t php_sockop_write ( php_stream *  stream,
const char *  buf,
size_t count  TSRMLS_DC 
) [static]

Definition at line 54 of file xp_socket.c.

{
       php_netstream_data_t *sock = (php_netstream_data_t*)stream->abstract;
       int didwrite;
       struct timeval *ptimeout;

       if (sock->socket == -1) {
              return 0;
       }

       if (sock->timeout.tv_sec == -1)
              ptimeout = NULL;
       else
              ptimeout = &sock->timeout;

retry:
       didwrite = send(sock->socket, buf, count, (sock->is_blocked && ptimeout) ? MSG_DONTWAIT : 0);

       if (didwrite <= 0) {
              long err = php_socket_errno();
              char *estr;

              if (sock->is_blocked && err == EWOULDBLOCK) {
                     int retval;

                     sock->timeout_event = 0;

                     do {
                            retval = php_pollfd_for(sock->socket, POLLOUT, ptimeout);

                            if (retval == 0) {
                                   sock->timeout_event = 1;
                                   break;
                            }

                            if (retval > 0) {
                                   /* writable now; retry */
                                   goto retry;
                            }

                            err = php_socket_errno();
                     } while (err == EINTR);
              }
              estr = php_socket_strerror(err, NULL, 0);
              php_error_docref(NULL TSRMLS_CC, E_NOTICE, "send of %ld bytes failed with errno=%ld %s",
                            (long)count, err, estr);
              efree(estr);
       }

       if (didwrite > 0) {
              php_stream_notify_progress_increment(stream->context, didwrite, 0);
       }

       if (didwrite < 0) {
              didwrite = 0;
       }

       return didwrite;
}

Here is the call graph for this function:

PHPAPI php_stream* php_stream_generic_socket_factory ( const char *  proto,
long  protolen,
char *  resourcename,
long  resourcenamelen,
const char *  persistent_id,
int  options,
int  flags,
struct timeval *  timeout,
php_stream_context *context STREAMS_DC  TSRMLS_DC 
)

Definition at line 778 of file xp_socket.c.

{
       php_stream *stream = NULL;
       php_netstream_data_t *sock;
       php_stream_ops *ops;

       /* which type of socket ? */
       if (strncmp(proto, "tcp", protolen) == 0) {
              ops = &php_stream_socket_ops;
       } else if (strncmp(proto, "udp", protolen) == 0) {
              ops = &php_stream_udp_socket_ops;
       }
#ifdef AF_UNIX
       else if (strncmp(proto, "unix", protolen) == 0) {
              ops = &php_stream_unix_socket_ops;
       } else if (strncmp(proto, "udg", protolen) == 0) {
              ops = &php_stream_unixdg_socket_ops;
       }
#endif
       else {
              /* should never happen */
              return NULL;
       }
       
       sock = pemalloc(sizeof(php_netstream_data_t), persistent_id ? 1 : 0);
       memset(sock, 0, sizeof(php_netstream_data_t));

       sock->is_blocked = 1;
       sock->timeout.tv_sec = FG(default_socket_timeout);
       sock->timeout.tv_usec = 0;

       /* we don't know the socket until we have determined if we are binding or
        * connecting */
       sock->socket = -1;
       
       stream = php_stream_alloc_rel(ops, sock, persistent_id, "r+");

       if (stream == NULL)  {
              pefree(sock, persistent_id ? 1 : 0);
              return NULL;
       }

       if (flags == 0) {
              return stream;
       }

       return stream;
}
static int php_tcp_sockop_accept ( php_stream *  stream,
php_netstream_data_t *  sock,
php_stream_xport_param *xparam STREAMS_DC  TSRMLS_DC 
) [inline, static]

Definition at line 704 of file xp_socket.c.

{
       int clisock;

       xparam->outputs.client = NULL;

       clisock = php_network_accept_incoming(sock->socket,
                     xparam->want_textaddr ? &xparam->outputs.textaddr : NULL,
                     xparam->want_textaddr ? &xparam->outputs.textaddrlen : NULL,
                     xparam->want_addr ? &xparam->outputs.addr : NULL,
                     xparam->want_addr ? &xparam->outputs.addrlen : NULL,
                     xparam->inputs.timeout,
                     xparam->want_errortext ? &xparam->outputs.error_text : NULL,
                     &xparam->outputs.error_code
                     TSRMLS_CC);

       if (clisock >= 0) {
              php_netstream_data_t *clisockdata;

              clisockdata = emalloc(sizeof(*clisockdata));

              if (clisockdata == NULL) {
                     close(clisock);
                     /* technically a fatal error */
              } else {
                     memcpy(clisockdata, sock, sizeof(*clisockdata));
                     clisockdata->socket = clisock;

                     xparam->outputs.client = php_stream_alloc_rel(stream->ops, clisockdata, NULL, "r+");
                     if (xparam->outputs.client) {
                            xparam->outputs.client->context = stream->context;
                            if (stream->context) {
                                   zend_list_addref(stream->context->rsrc_id);
                            }
                     }
              }
       }
       
       return xparam->outputs.client == NULL ? -1 : 0;
}

Here is the call graph for this function:

Here is the caller graph for this function:

static int php_tcp_sockop_bind ( php_stream *  stream,
php_netstream_data_t *  sock,
php_stream_xport_param *xparam  TSRMLS_DC 
) [inline, static]

Definition at line 569 of file xp_socket.c.

{
       char *host = NULL;
       int portno, err;

#ifdef AF_UNIX
       if (stream->ops == &php_stream_unix_socket_ops || stream->ops == &php_stream_unixdg_socket_ops) {
              struct sockaddr_un unix_addr;

              sock->socket = socket(PF_UNIX, stream->ops == &php_stream_unix_socket_ops ? SOCK_STREAM : SOCK_DGRAM, 0);

              if (sock->socket == SOCK_ERR) {
                     if (xparam->want_errortext) {
                            spprintf(&xparam->outputs.error_text, 0, "Failed to create unix%s socket %s",
                                          stream->ops == &php_stream_unix_socket_ops ? "" : "datagram",
                                          strerror(errno));
                     }
                     return -1;
              }

              parse_unix_address(xparam, &unix_addr TSRMLS_CC);

              return bind(sock->socket, (struct sockaddr *)&unix_addr, sizeof(unix_addr));
       }
#endif

       host = parse_ip_address(xparam, &portno TSRMLS_CC);

       if (host == NULL) {
              return -1;
       }

       sock->socket = php_network_bind_socket_to_local_addr(host, portno,
                     stream->ops == &php_stream_udp_socket_ops ? SOCK_DGRAM : SOCK_STREAM,
                     xparam->want_errortext ? &xparam->outputs.error_text : NULL,
                     &err
                     TSRMLS_CC);
       
       if (host) {
              efree(host);
       }

       return sock->socket == -1 ? -1 : 0;
}

Here is the call graph for this function:

Here is the caller graph for this function:

static int php_tcp_sockop_connect ( php_stream *  stream,
php_netstream_data_t *  sock,
php_stream_xport_param *xparam  TSRMLS_DC 
) [inline, static]

Definition at line 615 of file xp_socket.c.

{
       char *host = NULL, *bindto = NULL;
       int portno, bindport = 0;
       int err = 0;
       int ret;
       zval **tmpzval = NULL;

#ifdef AF_UNIX
       if (stream->ops == &php_stream_unix_socket_ops || stream->ops == &php_stream_unixdg_socket_ops) {
              struct sockaddr_un unix_addr;

              sock->socket = socket(PF_UNIX, stream->ops == &php_stream_unix_socket_ops ? SOCK_STREAM : SOCK_DGRAM, 0);

              if (sock->socket == SOCK_ERR) {
                     if (xparam->want_errortext) {
                            spprintf(&xparam->outputs.error_text, 0, "Failed to create unix socket");
                     }
                     return -1;
              }

              parse_unix_address(xparam, &unix_addr TSRMLS_CC);

              ret = php_network_connect_socket(sock->socket,
                            (const struct sockaddr *)&unix_addr, (socklen_t) XtOffsetOf(struct sockaddr_un, sun_path) + xparam->inputs.namelen,
                            xparam->op == STREAM_XPORT_OP_CONNECT_ASYNC, xparam->inputs.timeout,
                            xparam->want_errortext ? &xparam->outputs.error_text : NULL,
                            &err);

              xparam->outputs.error_code = err;

              goto out;
       }
#endif

       host = parse_ip_address(xparam, &portno TSRMLS_CC);

       if (host == NULL) {
              return -1;
       }

       if (stream->context && php_stream_context_get_option(stream->context, "socket", "bindto", &tmpzval) == SUCCESS) {
              if (Z_TYPE_PP(tmpzval) != IS_STRING) {
                     if (xparam->want_errortext) {
                            spprintf(&xparam->outputs.error_text, 0, "local_addr context option is not a string.");
                     }
                     efree(host);
                     return -1;
              }
              bindto = parse_ip_address_ex(Z_STRVAL_PP(tmpzval), Z_STRLEN_PP(tmpzval), &bindport, xparam->want_errortext, &xparam->outputs.error_text TSRMLS_CC);
       }

       /* Note: the test here for php_stream_udp_socket_ops is important, because we
        * want the default to be TCP sockets so that the openssl extension can
        * re-use this code. */
       
       sock->socket = php_network_connect_socket_to_host(host, portno,
                     stream->ops == &php_stream_udp_socket_ops ? SOCK_DGRAM : SOCK_STREAM,
                     xparam->op == STREAM_XPORT_OP_CONNECT_ASYNC,
                     xparam->inputs.timeout,
                     xparam->want_errortext ? &xparam->outputs.error_text : NULL,
                     &err,
                     bindto,
                     bindport
                     TSRMLS_CC);
       
       ret = sock->socket == -1 ? -1 : 0;
       xparam->outputs.error_code = err;

       if (host) {
              efree(host);
       }
       if (bindto) {
              efree(bindto);
       }

#ifdef AF_UNIX
out:
#endif

       if (ret >= 0 && xparam->op == STREAM_XPORT_OP_CONNECT_ASYNC && err == EINPROGRESS) {
              /* indicates pending connection */
              return 1;
       }
       
       return ret;
}

Here is the call graph for this function:

Here is the caller graph for this function:

static int php_tcp_sockop_set_option ( php_stream *  stream,
int  option,
int  value,
void *ptrparam  TSRMLS_DC 
) [static]

Definition at line 746 of file xp_socket.c.

{
       php_netstream_data_t *sock = (php_netstream_data_t*)stream->abstract;
       php_stream_xport_param *xparam;

       switch(option) {
              case PHP_STREAM_OPTION_XPORT_API:
                     xparam = (php_stream_xport_param *)ptrparam;

                     switch(xparam->op) {
                            case STREAM_XPORT_OP_CONNECT:
                            case STREAM_XPORT_OP_CONNECT_ASYNC:
                                   xparam->outputs.returncode = php_tcp_sockop_connect(stream, sock, xparam TSRMLS_CC);
                                   return PHP_STREAM_OPTION_RETURN_OK;

                            case STREAM_XPORT_OP_BIND:
                                   xparam->outputs.returncode = php_tcp_sockop_bind(stream, sock, xparam TSRMLS_CC);
                                   return PHP_STREAM_OPTION_RETURN_OK;


                            case STREAM_XPORT_OP_ACCEPT:
                                   xparam->outputs.returncode = php_tcp_sockop_accept(stream, sock, xparam STREAMS_CC TSRMLS_CC);
                                   return PHP_STREAM_OPTION_RETURN_OK;
                            default:
                                   /* fall through */
                                   ;
                     }
       }
       return php_sockop_set_option(stream, option, value, ptrparam TSRMLS_CC);
}

Here is the call graph for this function:

static int sock_recvfrom ( php_netstream_data_t *  sock,
char *  buf,
size_t  buflen,
int  flags,
char **  textaddr,
long *  textaddrlen,
struct sockaddr **  addr,
socklen_t *addrlen  TSRMLS_DC 
) [inline, static]

Definition at line 245 of file xp_socket.c.

{
       php_sockaddr_storage sa;
       socklen_t sl = sizeof(sa);
       int ret;
       int want_addr = textaddr || addr;

       if (want_addr) {
              ret = recvfrom(sock->socket, buf, buflen, flags, (struct sockaddr*)&sa, &sl);
              ret = (ret == SOCK_CONN_ERR) ? -1 : ret;
              php_network_populate_name_from_sockaddr((struct sockaddr*)&sa, sl,
                     textaddr, textaddrlen, addr, addrlen TSRMLS_CC);
       } else {
              ret = recv(sock->socket, buf, buflen, flags);
              ret = (ret == SOCK_CONN_ERR) ? -1 : ret;
       }

       return ret;
}

Here is the call graph for this function:

Here is the caller graph for this function:

static int sock_sendto ( php_netstream_data_t *  sock,
char *  buf,
size_t  buflen,
int  flags,
struct sockaddr *  addr,
socklen_t addrlen  TSRMLS_DC 
) [inline, static]

Definition at line 233 of file xp_socket.c.

{
       int ret;
       if (addr) {
              ret = sendto(sock->socket, buf, buflen, flags, addr, addrlen);
              return (ret == SOCK_CONN_ERR) ? -1 : ret;
       }
       return ((ret = send(sock->socket, buf, buflen, flags)) == SOCK_CONN_ERR) ? -1 : ret;
}

Here is the caller graph for this function:


Variable Documentation