[kaffe] patch for unix-jthread hang

jrandom jrandom at i2p.net
Thu Aug 5 21:45:19 PDT 2004


-----BEGIN PGP SIGNED MESSAGE-----
Hash: SHA1

Hi y'all,

Here's a small patch for a bug in unix-jthreads that i've been
running into for a while.  Basically if there aren't any ready
threads when reschedule() is called, control will enter handleIO(),
which in turn will block on poll/select indefinitely until data
is available.  The problem with this is that it doesn't take into
account threads that are on the alarm queue - I saw this scenario
occur when my JVM would hang for several minutes in handleIO, only
to have a whole truckload of things fire up when I open a new socket.

The OS I've tested this on uses poll, so I've only gone down the
#if USE_POLL branch, but I modified the #else logic according to what
I think should do the trick.  My C is /very/ rusty though, so please
double check this :)

muchas gracias,
=jr

-----BEGIN PGP SIGNATURE-----
Version: PGP 8.1

iQA/AwUBQRML7BpxS9rYd+OGEQKHDACgjn7NEUa880Sp8LWiE1rB6K9pLoEAmQFj
uKUyt291Av68KWArnOjdeNCH
=X9sE
-----END PGP SIGNATURE-----
-------------- next part --------------
Index: jthread.c
===================================================================
RCS file: /cvs/kaffe/kaffe/kaffe/kaffevm/systems/unix-jthreads/jthread.c,v
retrieving revision 1.117
diff -u -r1.117 jthread.c
--- jthread.c   2 Aug 2004 10:45:04 -0000       1.117
+++ jthread.c   6 Aug 2004 04:28:37 -0000
@@ -2144,10 +2144,39 @@
                FD_SET(sigPipe[0], &rd);
 #endif
        }
+
+       /*
+        * find out if we have any threads waiting (and if so, when the first
+        * one will expire).  we use this to prevent indefinite waits in the
+        * poll / select
+        *
+        */
+       jlong firstAlarm = -1;
+       if (alarmList != 0) {
+               // sorted
+               firstAlarm = JTHREADQ(alarmList)->time;
+       }
+
+       jlong maxWait = (canSleep ? -1 : 0);
+       if ( (firstAlarm != -1) && (canSleep) ) {
+               jlong curTime = currentTime();
+               if (curTime >= firstAlarm) {
+                       maxWait = 0;
+               } else {
+                       maxWait = firstAlarm - curTime;
+               }
+               DBG(JTHREADDETAIL, dprintf("handleIO(sleep=%d) maxWait=%d\n", canSleep, maxWait); )
+       }
+
 #if USE_POLL
-       r = poll(pollarray, nfd, canSleep ? -1 : 0);
+       r = poll(pollarray, nfd, maxWait);
 #else
-       r = select(maxFd+1, &rd, &wr, 0, canSleep ? 0 : &zero);
+       if (maxWait <= 0) {
+               r = select(maxFd+1, &rd, &wr, 0, &zero);
+       } else {
+               struct timeval maxWaitVal = { maxWait/1000, maxWait % 1000 };
+               r = select(maxFd+1, &rd, &wr, 0, &maxWaitVal);
+       }
 #endif
        /* Reset wouldlosewakeup here */
        wouldlosewakeup = 0;



More information about the kaffe mailing list