Hi all,
I am new to php source code hacking, but got into it for a particular
reason: I need sub-second SOAP request timeouts.
To qualify the reasoning behind this sub-second timeout requirement a
bit further, let me explain what it is used for: We are implementing a
system that changes webcontent based on a remote SOAP service (i.e.
customer database) and we want to never wait more than - say - 250ms
for this to complete. Currently the best I can do is 1 sec connection
timeout (in SoapClient() using the connection_timeout parameter) and 1
sec socket-read timeout (using ini_set() on the default_socket_timeout
parameter). Assuming the remote SOAP server is down or slow, every
pagerender with the SOAP request in it would get delayed by at least 1
sec, which is unacceptable in our case.
BTW, comparing the PHP situation with other SOAP implementations, we
have typically millisecond timeouts available:
- Java (apachesoap): milliseconds
- Java (axis): milliseconds
- .NET: milliseconds
- perl (SOAP::Lite): seconds
Currently all socket/connection timeouts in PHP are implemented with
second resolution. This is an unnecessary limitation in my view and I
would love for this to be changed in mainstream PHP. I believe the
effort to do so is minimal and has no impact to the users.
The timeout numbers are usually used to populate a "tv" struct - in the
current PHP code only the tv.tv_sec is typically set. So the change
would simply be to promote default_socket_timeout (and similar
variables) to a float and use the fractional part to properly populate
tv.tv_usec with a microsecond number.
In fact I found locations where the default_socket_timeout parameter is
assumed to be a float (ext/standard/fsock.c - line 66).
Also this simple code shows the local default_socket_context to accept a
float parameter:
<?php
ini_set("default_socket_timeout",0.5);
phpinfo();
?>
while ext/standard/file.h - line 113 stores it as a long.
So a quick review of how this parameter is used throughout the code
might be a-good-thing (TM) anyhow.
An example implementation of the new, float resulution timeout use for
the SoapClient/SoapServer is a few lines in ext/soap/soap.c and
ext/soap/php_http.c as follows:
soap.c
if (zend_hash_find(ht, "connection_timeout",
sizeof("connection
Z_TYPE_PP(tmp) == IS_DOUBLE && Z_DVAL_PP(tmp) > 0.0) {
add_property_double(this_ptr,
"_connection_timeout", Z_
}
php_http.c
if (zend_hash_find(Z_OBJPROP_P(this_ptr), "_connection_timeout",
sizeof
Z_TYPE_PP(tmp) == IS_DOUBLE && Z_DVAL_PP(tmp) > 0.0) {
tv.tv_sec = floor(Z_DVAL_PP(tmp));
tv.tv_usec = (1000000.0*(Z_DVAL_PP(tmp)-floor(Z_DVAL_PP(tmp))));
timeout = &tv;
}
Similarly changes in the main PHP code could look something like this
(assuming the var is a float):
main/streams/transport.c
default_timeout.tv_sec = floor(FG(default_socket_timeout));
default_timeout.tv_usec = (1000000.0 *
(FG(default_socket_timeout)-floor(FG(default_socket_timeout))) );
The files that need to be changed are limited.
grep -c default_socket_timeout ind . -name "*.[ch]" | grep -v :0
gives
./ext/imap/php_imap.c:4
./ext/standard/file.c:1
./ext/standard/file.h:1
./ext/standard/fsock.c:1
./ext/standard/streamsfuncs.c:2
./ext/openssl/xp_ssl.c:2
./main/streams/transports.c:2
./main/streams/xp_socket.c:3
./main/network.c:2
grep -c default_socket_timeout ind . -name "*.[ch]" | grep -v :0
gives
./ext/ftp/ftp.c:2
./ext/curl/streams.c:1
./ext/soap/php_http.c:1
./ext/session/session.c:3
./ext/sockets/sockets.c:5
./ext/standard/uniqid.c:1
./ext/standard/lcg.c:1
./ext/standard/fsock.c:1
./ext/standard/streamsfuncs.c:4
./ext/openssl/xp_ssl.c:2
./main/streams/xp_socket.c:2
./main/network.c:2
Best regards
Andreas
--
PHP Internals - PHP Runtime Development Mailing List
To unsubscribe, visit: http://www.php.net/unsub.php