Phil Stracchino wrote:
Frank Sweetser wrote:

On Mon, Dec 05, 2005 at 11:07:14PM +0100, Kern Sibbald wrote:


Yes, as I mentioned in a previous email. You are using encrypted comm. The current way it is programmed, this is exactly what will happen because it runs in non-blocking read mode. That is a point that I forgot to look into before the 1.38.0 release ...


Ah, I see, I didn't realize you meant this was expected.  Any chance this will
change in a future rev?


You're not using a select() on the socket...?

The code assumes that select() does not modify the timeout parameter. FreeBSD, which I was using for testing, does not. However, SuSv3 states that "the select() function may modify the object pointed to by the timeout argument"

Linux's select() man page:
   (ii) The select function may update the timeout parameter
        to indicate how much time was left.

This is why Frank is seeing the daemons spin with a timeout of 0:
    2103  select(6, [5], NULL, [5], {0, 0}) = 0 (Timeout)

After the first call to select() times out, the timeval will be set to { 0 ,0 }.

Frank, I've attached a patch against 1.38.2 -- I'd be most appreciative if you could test it and verify that it solves your problem.

-landonf
--- src/lib/tls.c.orig	Sun Sep 18 02:56:20 2005
+++ src/lib/tls.c	Mon Dec  5 18:50:29 2005
@@ -466,8 +466,6 @@
 
    /* Zero the fdset, we'll set our fd prior to each invocation of select() */
    FD_ZERO(&fdset);
-   tv.tv_sec = 10;
-   tv.tv_usec = 0;
    fdmax = bsock->fd + 1;
 
    /* Ensure that socket is non-blocking */
@@ -497,12 +495,18 @@
            case SSL_ERROR_WANT_READ:
               /* If we timeout of a select, this will be unset */
               FD_SET((unsigned) bsock->fd, &fdset);
+              /* Set our timeout */
+              tv.tv_sec = 10;
+              tv.tv_usec = 0;
               /* Block until we can read */
               select(fdmax, &fdset, NULL, &fdset, &tv);
               break;
            case SSL_ERROR_WANT_WRITE:
               /* If we timeout of a select, this will be unset */
               FD_SET((unsigned) bsock->fd, &fdset);
+              /* Set our timeout */
+              tv.tv_sec = 10;
+              tv.tv_usec = 0;
               /* Block until we can write */
               select(fdmax, NULL, &fdset, &fdset, &tv);
               break;

Reply via email to