Hi again,

Am Montag, den 04.12.2006, 11:19 -0800 schrieb David Daney:
> Andrew Haley wrote:
> > Roman Kennke writes:
> >  > > While testing eclipse I sometimes saw interrupted reads occur. 
> > VMChannel
> >  > > already had a mechanism for checking the interrupted status of a thread
> >  > > when a system call returned early. But this wasn't used for the read()
> >  > > and write() methods. This patch adds the logic. And makes my eclipse
> >  > > happy again :)
> >  > 
> >  > I am seeing a (possibly) related issue still:
> >  > 
> >  > java.net.SocketException: Interrupted system call
> > 
> > If connect(2) returns EINTR, you should retry:
> > 
> > CPNIO_EXPORT int
> > cpnio_connect (int fd, const struct sockaddr *addr, socklen_t addrlen)
> > {
> >   int retcode;
> >   do
> >     {
> >       retcode = connect (fd, addr, addrlen);
> >     }
> >   while (retcode == EINTR);
> >   return retcode;
> > }
> 
> Except that you should probably also check if the thread was interrupted 
> as the original patch does for read and write.

I did it like that and it solved all my problems :-)

Mark: Include that in 0.93?

2006-12-04  Roman Kennke  <[EMAIL PROTECTED]>

        * native/jni/java-nio/gnu_java_nio_VMChannel.c
        (Java_gnu_java_nio_VMChannel_connect): Retry on EINTR.

/Roman

Index: native/jni/java-nio/gnu_java_nio_VMChannel.c
===================================================================
RCS file: /cvsroot/classpath/classpath/native/jni/java-nio/gnu_java_nio_VMChannel.c,v
retrieving revision 1.11
diff -u -1 -5 -r1.11 gnu_java_nio_VMChannel.c
--- native/jni/java-nio/gnu_java_nio_VMChannel.c	4 Dec 2006 01:32:18 -0000	1.11
+++ native/jni/java-nio/gnu_java_nio_VMChannel.c	4 Dec 2006 20:12:06 -0000
@@ -1024,30 +1024,31 @@
 /*
  * Class:     gnu_java_nio_VMChannel
  * Method:    connect
  * Signature: (I[BI)Z
  */
 JNIEXPORT jboolean JNICALL
 Java_gnu_java_nio_VMChannel_connect (JNIEnv *env, jclass clazz __attribute__((unused)),
                                      jint fd, jbyteArray addr, jint port, jint timeout)
 {
 #ifdef HAVE_CONNECT
   struct sockaddr_in sockaddr;
   struct timeval timeo;
   int origflags = 0, flags;
   jbyte *addr_elems;
   int ret;
+  int tmpErrno;
 
   if ((*env)->GetArrayLength (env, addr) != 4)
     {
       JCL_ThrowException (env, SOCKET_EXCEPTION,
                           "expecting 4-byte address");
       return JNI_FALSE;
     }
 
   if (timeout > 0)
     {
       timeo.tv_sec = timeout / 1000;
       timeo.tv_usec = (timeout % 1000) * 1000;
       origflags = fcntl (fd, F_GETFL, 0);
       if (origflags == -1)
         {
@@ -1062,32 +1063,38 @@
             {
               JCL_ThrowException (env, SOCKET_EXCEPTION, strerror (errno));
               return JNI_FALSE;
             }
         }
     }
 
   addr_elems = (*env)->GetByteArrayElements (env, addr, NULL);
 
   memset (&sockaddr, 0, sizeof (struct sockaddr_in));
   sockaddr.sin_family = AF_INET;
   sockaddr.sin_port = htons (port);
   sockaddr.sin_addr.s_addr = *((uint32_t *) addr_elems);
 
 
-  ret = cpnio_connect (fd, (struct sockaddr *) &sockaddr,
-                       sizeof (struct sockaddr_in));
+  do
+    {
+      ret = cpnio_connect (fd, (struct sockaddr *) &sockaddr,
+                           sizeof (struct sockaddr_in));
+      tmpErrno = errno;
+    }
+  while (ret == -1 && errno == EINTR && ! JCL_thread_interrupted(env));
+  errno = tmpErrno;
 
   (*env)->ReleaseByteArrayElements (env, addr, addr_elems, JNI_ABORT);
 
   /* If a timeout was specified, select on the file descriptor with
      the timeout. */
   if (timeout > 0 && ret == -1)
     {
       /* Reset the non-blocking flag, if needed. */
       if (!(origflags & O_NONBLOCK))
         {
           if (fcntl (fd, F_SETFL, origflags) == -1)
             {
               /* oops */
               JCL_ThrowException (env, SOCKET_EXCEPTION, strerror (errno));
               return JNI_FALSE;

Reply via email to