>>> On 11/3/2008 at 5:27 PM, in message <[EMAIL PROTECTED]>,
Kostas Georgiou <[EMAIL PROTECTED]> wrote:
> On Mon, Nov 03, 2008 at 11:46:52PM +0000, Kostas Georgiou wrote:
>
>> On Mon, Nov 03, 2008 at 01:55:22PM -0700, Brad Nicholes wrote:
>> >
>> > If a timeout is set, then is the resulting XML output still good or did we
> lose something because of the timeout?
>>
>> No, it seems to be working fine. I am testing with:
>
> Actually I was wrong there was enough data in the socket buffers to
> confuse me. The xml output is truncated in the slow reader :(
>
Attached is a patch against trunk which implements a lingering close. I am not
sure if this will solve the problem but Apache does a similar thing to make
sure that both sides get a chance to complete the conversation before closing
the socket. Apply this patch, let it run for a while and let's see if this
solves the problem.
Brad
Index: gmond.c
===================================================================
--- gmond.c (revision 1883)
+++ gmond.c (working copy)
@@ -1498,6 +1498,76 @@
return apr_socket_send(client, "</HOST>\n", &len);
}
+/* we now proceed to read from the client until we get EOF, or until
+ * MAX_SECS_TO_LINGER has passed. the reasons for doing this are
+ * documented in a draft:
+ *
+ * http://www.ics.uci.edu/pub/ietf/http/draft-ietf-http-connection-00.txt
+ *
+ * in a nutshell -- if we don't make this effort we risk causing
+ * TCP RST packets to be sent which can tear down a connection before
+ * all the response data has been sent to the client.
+ */
+#define MAX_SECS_TO_LINGER 30
+#define SECONDS_TO_LINGER 2
+void lingering_close(apr_socket_t *csd)
+{
+ char dummybuf[512];
+ apr_size_t nbytes;
+ apr_time_t timeup = 0;
+
+ if (!csd) {
+ return;
+ }
+
+#ifdef NO_LINGCLOSE
+ ap_flush_conn(c); /* just close it */
+ apr_socket_close(csd);
+ return;
+#endif
+
+ /* Close the connection, being careful to send out whatever is still
+ * in our buffers. If possible, try to avoid a hard close until the
+ * client has ACKed our FIN and/or has stopped sending us data.
+ */
+
+ /* Shut down the socket for write, which will send a FIN
+ * to the peer.
+ */
+ if (apr_socket_shutdown(csd, APR_SHUTDOWN_WRITE) != APR_SUCCESS)
+ {
+ apr_socket_close(csd);
+ return;
+ }
+
+ /* Read available data from the client whilst it continues sending
+ * it, for a maximum time of MAX_SECS_TO_LINGER. If the client
+ * does not send any data within 2 seconds (a value pulled from
+ * Apache 1.3 which seems to work well), give up.
+ */
+ apr_socket_timeout_set(csd, apr_time_from_sec(SECONDS_TO_LINGER));
+ apr_socket_opt_set(csd, APR_INCOMPLETE_READ, 1);
+
+ /* The common path here is that the initial apr_socket_recv() call
+ * will return 0 bytes read; so that case must avoid the expensive
+ * apr_time_now() call and time arithmetic. */
+
+ do {
+ nbytes = sizeof(dummybuf);
+ if (apr_socket_recv(csd, dummybuf, &nbytes) || nbytes == 0)
+ break;
+
+ if (timeup == 0) {
+ /* First time through; calculate now + 30 seconds. */
+ timeup = apr_time_now() + apr_time_from_sec(MAX_SECS_TO_LINGER);
+ continue;
+ }
+ } while (apr_time_now() < timeup);
+
+ apr_socket_close(csd);
+ return;
+}
+
static void
process_tcp_accept_channel(const apr_pollfd_t *desc, apr_time_t now)
{
@@ -1584,8 +1654,9 @@
/* Close down the accepted socket */
close_accept_socket:
- apr_socket_shutdown(client, APR_SHUTDOWN_READ);
- apr_socket_close(client);
+ lingering_close(client);
+ //apr_socket_shutdown(client, APR_SHUTDOWN_READ);
+ //apr_socket_close(client);
apr_pool_destroy(client_context);
}
-------------------------------------------------------------------------
This SF.Net email is sponsored by the Moblin Your Move Developer's challenge
Build the coolest Linux based applications with Moblin SDK & win great prizes
Grand prize is a trip for two to an Open Source event anywhere in the world
http://moblin-contest.org/redirect.php?banner_id=100&url=/
_______________________________________________
Ganglia-general mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/ganglia-general