/[classpath]/classpath/native/jni/java-nio/java_nio.c
ViewVC logotype

Diff of /classpath/native/jni/java-nio/java_nio.c

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 1.1 by mkoch, Wed Jul 2 09:16:52 2003 UTC revision 1.2 by rupp, Wed Jul 23 07:53:15 2003 UTC
# Line 35  this exception to your version of the li Line 35  this exception to your version of the li
35  obligated to do so.  If you do not wish to do so, delete this  obligated to do so.  If you do not wish to do so, delete this
36  exception statement from your version. */  exception statement from your version. */
37    
38  #include <stdio.h>  /* do not move; needed here because of some macro definitions */
39  #include <stdlib.h>  #include <config.h>
 #include <string.h>  
 #include <errno.h>  
 #include <fcntl.h>  
 #include <unistd.h>  
 #include <sys/stat.h>  
40    
41    #ifdef HAVE_MMAP
42  #include <sys/mman.h>  #include <sys/mman.h>
43  #include <sys/types.h>  #endif
 #include <sys/socket.h>  
 #include <netinet/in.h>  
 #include <netinet/tcp.h>  
 #include <netinet/in.h>  
44    
45  #include <jni.h>  #include <jni.h>
46  #include <jcl.h>  #include <jcl.h>
47    
48    #include "target_native.h"
49    #ifndef WITHOUT_NETWORK
50      #include "target_native_network.h"
51    #endif /* WITHOUT_NETWORK */
52    
53  #include "gnu_java_nio_FileChannelImpl.h"  #include "gnu_java_nio_FileChannelImpl.h"
54    
55  #include "javaio.h"  #include "javaio.h"
56    
   
57  #define NIO_DEBUG(X) /* no debug */  #define NIO_DEBUG(X) /* no debug */
58  //#define NIO_DEBUG(X) X  //#define NIO_DEBUG(X) X
59    
   
   
60  /***************************************  /***************************************
61   *   *
62   *  File Channel implementation   *  File Channel implementation
# Line 222  u_int64_t nio_mmap_file(jint fd, Line 217  u_int64_t nio_mmap_file(jint fd,
217                          jint size,                          jint size,
218                          jint jflags)                          jint jflags)
219  {  {
220    #ifdef HAVE_MMAP
221    u_int64_t ret = 0;    u_int64_t ret = 0;
222    void *address;    void *address;
223        
# Line 251  u_int64_t nio_mmap_file(jint fd, Line 247  u_int64_t nio_mmap_file(jint fd,
247    *(void **) &ret = address;    *(void **) &ret = address;
248    
249    return ret;    return ret;
250    #else /* not HAVE_MMAP */
251      return(TARGET_NATIVE_MATH_INT_INT64_CONST_0);
252    #endif /* not HAVE_MMAP */
253  }  }
254    
255    
# Line 258  void nio_msync(int fd, Line 257  void nio_msync(int fd,
257                 jlong jaddress,                 jlong jaddress,
258                 int size)                 int size)
259  {  {
260    #ifdef HAVE_MMAP
261    int res;    int res;
262    char *address = *(void **) &jaddress;    char *address = *(void **) &jaddress;
263    
# Line 269  void nio_msync(int fd, Line 269  void nio_msync(int fd,
269      {      {
270        perror("synchronize with file failed");        perror("synchronize with file failed");
271      }      }
272    #else /* not HAVE_MMAP */
273    #endif /* not HAVE_MMAP */
274  }  }
275    
276  void nio_unmmap_file(int fd,  void nio_unmmap_file(int fd,
277                       jlong jaddress,                       jlong jaddress,
278                       int size)                       int size)
279  {  {
280    #ifdef HAVE_MMAP
281    int res = 0;    int res = 0;
282    char *address = *(void **) &jaddress;    char *address = *(void **) &jaddress;
283    
# Line 287  void nio_unmmap_file(int fd, Line 290  void nio_unmmap_file(int fd,
290      {      {
291        perror("un-mapping file failed");        perror("un-mapping file failed");
292      }      }
293    #else /* not HAVE_MMAP */
294    #endif /* not HAVE_MMAP */
295  }  }
296    
297    
# Line 330  void Java_gnu_java_nio_FileChannelImpl_n Line 335  void Java_gnu_java_nio_FileChannelImpl_n
335   * It's a copy to avoid a link error in orp.   * It's a copy to avoid a link error in orp.
336   */   */
337    
 #define IO_EXCEPTION "java/io/IOException"  
   
338  static  static
339  int socket_channel_get_net_addr(JNIEnv *env, jobject addr)  int socket_channel_get_net_addr(JNIEnv *env, jobject addr)
340  {  {
341    #ifndef WITHOUT_NETWORK
342    jclass cls = 0;    jclass cls = 0;
343    jmethodID mid;    jmethodID mid;
344    jarray arr = 0;    jarray arr = 0;
# Line 346  int socket_channel_get_net_addr(JNIEnv * Line 350  int socket_channel_get_net_addr(JNIEnv *
350    /* Call the getAddress method on the object to retrieve the IP address */    /* Call the getAddress method on the object to retrieve the IP address */
351    cls = (*env)->GetObjectClass(env, addr);    cls = (*env)->GetObjectClass(env, addr);
352    if (cls == NULL)    if (cls == NULL)
353      return 0;      return(0);
354    
355    mid = (*env)->GetMethodID(env, cls, "getAddress", "()[B");    mid = (*env)->GetMethodID(env, cls, "getAddress", "()[B");
356    if (mid == NULL)    if (mid == NULL)
357      return 0;      return(0);
358    
359    DBG("socket_channel_get_net_addr(): Got getAddress method\n");    DBG("socket_channel_get_net_addr(): Got getAddress method\n");
360    
361    arr = (*env)->CallObjectMethod(env, addr, mid);    arr = (*env)->CallObjectMethod(env, addr, mid);
362    if (arr == NULL)    if (arr == NULL)
363      return 0;      return(0);
364    
365    DBG("socket_channel_get_net_addr(): Got the address\n");    DBG("socket_channel_get_net_addr(): Got the address\n");
366    
# Line 364  int socket_channel_get_net_addr(JNIEnv * Line 368  int socket_channel_get_net_addr(JNIEnv *
368    len = (*env)->GetArrayLength(env, arr);    len = (*env)->GetArrayLength(env, arr);
369    if (len != 4)    if (len != 4)
370      {      {
371        JCL_ThrowException(env, IO_EXCEPTION, "Internal Error");        JCL_ThrowException(env, "java/io/IOException", "Internal Error: invalid byte array length");
372        return 0;        return(0);
373      }      }
374    DBG("socket_channel_get_net_addr(): Length ok\n");    DBG("socket_channel_get_net_addr(): Length ok\n");
375    
376    octets = (*env)->GetByteArrayElements(env, arr, 0);      octets = (*env)->GetByteArrayElements(env, arr, 0);  
377    if (octets == NULL)    if (octets == NULL)
378      return 0;      return(0);
379    
380    DBG("socket_channel_get_net_addr(): Grabbed bytes\n");    DBG("socket_channel_get_net_addr(): Grabbed bytes\n");
381    
382    netaddr = (((unsigned char)octets[0]) << 24) +    TARGET_NATIVE_NETWORK_IPADDRESS_BYTES_TO_INT(octets[0],
383              (((unsigned char)octets[1]) << 16) +                                                 octets[1],
384              (((unsigned char)octets[2]) << 8) +                                                 octets[2],
385              ((unsigned char)octets[3]);                                                 octets[3],
386                                                   netaddr
387    netaddr = htonl(netaddr);                                                );
388    
389    (*env)->ReleaseByteArrayElements(env, arr, octets, 0);    (*env)->ReleaseByteArrayElements(env, arr, octets, 0);
390    DBG("socket_channel_get_net_addr(): Done getting addr\n");    DBG("socket_channel_get_net_addr(): Done getting addr\n");
391    
392    return netaddr;    return netaddr;
393    #else /* not WITHOUT_NETWORK */
394      return(0);
395    #endif /* not WITHOUT_NETWORK */
396  }  }
397    
398  int Java_gnu_java_nio_SocketChannelImpl_SocketCreate(JNIEnv *env,jclass c)  int Java_gnu_java_nio_SocketChannelImpl_SocketCreate(JNIEnv *env,jclass c)
399  {  {
400    int val = 1;  #ifndef WITHOUT_NETWORK
401      int fd;
402    int result;    int result;
403        
404    result = socket(AF_INET, SOCK_STREAM, 0 /* IPPROTO_TCP */ );    TARGET_NATIVE_NETWORK_SOCKET_OPEN_STREAM(fd, result);
405        if (result != TARGET_NATIVE_OK)
406    //  fprintf(stderr, "socket created: %d\n", result);      {
407          return(0);
408        }
409    
410    if (result < 0) return result;    TARGET_NATIVE_NETWORK_SOCKET_SET_OPTION_REUSE_ADDRESS(fd, 1, result);
411        if (result != TARGET_NATIVE_OK)
412    setsockopt(result, SOL_SOCKET, SO_REUSEADDR, &val, sizeof(int));      {
413    setsockopt(result, 6 /* TCP */ , TCP_NODELAY, &val, sizeof(int));        TARGET_NATIVE_NETWORK_SOCKET_CLOSE(fd,result);
414          return(0);
415        }
416      TARGET_NATIVE_NETWORK_SOCKET_SET_OPTION_TCP_NODELAY(fd, 1, result);
417      if (result != TARGET_NATIVE_OK)
418        {
419          TARGET_NATIVE_NETWORK_SOCKET_CLOSE(fd, result);
420          return(0);
421        }
422    
423    return result;    return(fd);
424    #else /* not WITHOUT_NETWORK */
425      return(-1);
426    #endif /* not WITHOUT_NETWORK */
427  }  }
428    
429  int Java_gnu_java_nio_SocketChannelImpl_SocketConnect(JNIEnv *env,jclass c,int fd, jobject InetAddress, int port)  int Java_gnu_java_nio_SocketChannelImpl_SocketConnect(JNIEnv *env,jclass c,int fd, jobject InetAddress, int port)
430  {  {
431    #ifndef WITHOUT_NETWORK
432      int inet_addr;
433    int result;    int result;
434    struct sockaddr_in server;    int local_address;
435    int inet_addr =  socket_channel_get_net_addr(env, InetAddress);    int local_port;
436    
437    server.sin_family = PF_INET;    inet_addr = socket_channel_get_net_addr(env, InetAddress);
438    server.sin_addr.s_addr = inet_addr;  
439    server.sin_port = htons(port);    /* connect */
440      do
441    do {      {
442      result = connect(fd, (struct sockaddr *) &server, sizeof(server));        TARGET_NATIVE_NETWORK_SOCKET_CONNECT(fd, inet_addr, inet_addr, result);
443    } while (result == -1 && errno == EINTR);      } while ((result != TARGET_NATIVE_OK) &&
444                   (TARGET_NATIVE_LAST_ERROR() == TARGET_NATIVE_ERROR_INTERRUPT_FUNCTION_CALL)
445    if (result >= 0) {              );
446      socklen_t len = sizeof(server);    if (result != TARGET_NATIVE_OK)
447      if (getsockname(fd, (struct sockaddr *) &server, &len) < 0) {      {
448          return(-1);
449        }
450    
451      /* get local address info */
452      TARGET_NATIVE_NETWORK_SOCKET_GET_LOCAL_INFO(fd, local_address, local_port, result);
453      if (result != TARGET_NATIVE_OK)
454        {
455    //??? NYI
456        perror("getsockname: ");        perror("getsockname: ");
457        return -1;        return(-1);
458      }      }
459      result = ntohs(server.sin_port);  
460    }    return(local_port);
461      #else /* not WITHOUT_NETWORK */
462    return result;    return(-1);
463    #endif /* not WITHOUT_NETWORK */
464  }  }
465    
466  int Java_gnu_java_nio_SocketChannelImpl_SocketBind(JNIEnv *env,jclass c,int fd, jobject InetAddress, int port)  int Java_gnu_java_nio_SocketChannelImpl_SocketBind(JNIEnv *env,jclass c,int fd, jobject InetAddress, int port)
467  {  {
468    struct sockaddr_in server;  #ifndef WITHOUT_NETWORK
469    int inet_addr =  socket_channel_get_net_addr(env, InetAddress);    int inet_addr;
470      int result;
471      int local_address;
472      int local_port;
473    
474    server.sin_family = AF_INET;    inet_addr =  socket_channel_get_net_addr(env, InetAddress);
475    server.sin_addr.s_addr = inet_addr;  
476    server.sin_port = htons(port);    TARGET_NATIVE_NETWORK_SOCKET_BIND(fd, inet_addr, port, result);
477      if (result != TARGET_NATIVE_OK)
478    if (bind(fd, (struct sockaddr *) &server, sizeof(server)) < 0) {      {
479      fprintf(stderr, "Error binding fd %d port %d\n", fd, port);  //??? NYI
480      perror("BIND");        perror("BIND");
     return -1;  
   }  
   if (port == 0) {  
     socklen_t len = sizeof(server);  
     /* Find the port number and return it; */  
     if (getsockname(fd, (struct sockaddr *) &server, &len) < 0) {  
       perror("getsockname: ");  
481        return -1;        return -1;
482      }      }
483      return ntohs(server.sin_port);    if (port == 0)
484    }      {
485    return port;        /* get local address info */
486          TARGET_NATIVE_NETWORK_SOCKET_GET_LOCAL_INFO(fd, local_address, local_port, result);
487          if (result != TARGET_NATIVE_OK)
488            {
489    //??? NYI
490              perror("getsockname: ");
491              return -1;
492            }
493        }
494      else
495        {
496          local_port = port;
497        }
498    
499      return(local_port);
500    #else /* not WITHOUT_NETWORK */
501    #endif /* not WITHOUT_NETWORK */
502  }  }
503    
504  int Java_gnu_java_nio_SocketChannelImpl_SocketListen(JNIEnv *env,jclass c,int fd, int backlog)  int Java_gnu_java_nio_SocketChannelImpl_SocketListen(JNIEnv *env,jclass c,int fd, int backlog)
505  {  {
506    int res;  #ifndef WITHOUT_NETWORK
507      int result;
508    
509    res = listen(fd, backlog);    TARGET_NATIVE_NETWORK_SOCKET_LISTEN(fd, backlog, result);
510      if (result != TARGET_NATIVE_OK)
511      {
512        return(-1);
513      }
514    
515    return res;    return(0);
516    #else /* not WITHOUT_NETWORK */
517      return(-1);
518    #endif /* not WITHOUT_NETWORK */
519  }  }
520    
521  int Java_gnu_java_nio_SocketChannelImpl_SocketAvailable(JNIEnv *env,jclass c,int fd)  int Java_gnu_java_nio_SocketChannelImpl_SocketAvailable(JNIEnv *env,jclass c,int fd)
522  {  {
523      unsigned long curr = lseek(fd, 0, SEEK_CUR);  #ifndef WITHOUT_NETWORK
524      struct stat stat_buf;    int bytes_available;
525      int result;
526    
527      if (fstat(fd, &stat_buf) < 0) {    TARGET_NATIVE_NETWORK_SOCKET_RECEIVE_AVAILABLE(fd, bytes_available, result);
528          return 0;    if (result!=TARGET_NATIVE_OK)
529      }    {
530      return stat_buf.st_size - curr;      return(0);
531      }
532    
533      return(bytes_available);
534    #else /* not WITHOUT_NETWORK */
535      return(0);
536    #endif /* not WITHOUT_NETWORK */
537  }  }
538    
539  int Java_gnu_java_nio_SocketChannelImpl_SocketClose(JNIEnv *env,jclass c,int fd)  int Java_gnu_java_nio_SocketChannelImpl_SocketClose(JNIEnv *env,jclass c,int fd)
540  {  {
541      if (fd >= 0) {  #ifndef WITHOUT_NETWORK
542          return close(fd);    int result;
     }  
     return 0;  
543    
544      if (fd >= 0) {
545        TARGET_NATIVE_NETWORK_SOCKET_CLOSE(fd, result);
546      }
547    
548      return(0);
549    #else /* not WITHOUT_NETWORK */
550      return(0);
551    #endif /* not WITHOUT_NETWORK */
552  }  }
553    
554  int Java_gnu_java_nio_SocketChannelImpl_SocketRead(JNIEnv *env,jclass c,int fd, jarray buf, int off, int len)  int Java_gnu_java_nio_SocketChannelImpl_SocketRead(JNIEnv *env,jclass c,int fd, jarray buf, int off, int len)
555  {  {
556    int result;  #ifndef WITHOUT_NETWORK
557    jbyte *p;    jbyte *buffer;
558    p = (*env)->GetByteArrayElements(env, buf, 0);    int   bytes_received;
     
   result = read(fd, p + off, len);  
559    
560    (*env)->ReleaseByteArrayElements(env, buf, p, 0);    buffer = (*env)->GetByteArrayElements(env, buf, 0);
561      assert(buffer != NULL);
562    
563    //  fprintf(stderr, "p=%s\n", p+off);    TARGET_NATIVE_NETWORK_SOCKET_RECEIVE(fd, buffer + off, len, bytes_received);
564    
565    return result;    (*env)->ReleaseByteArrayElements(env, buf, buffer, 0);
566    
567      return(bytes_received);
568    #else /* not WITHOUT_NETWORK */
569      return(0);
570    #endif /* not WITHOUT_NETWORK */
571  }  }
572    
573  int Java_gnu_java_nio_SocketChannelImpl_SocketWrite(JNIEnv *env,jclass c,int fd, jarray buf, int off, int len)  int Java_gnu_java_nio_SocketChannelImpl_SocketWrite(JNIEnv *env,jclass c,int fd, jarray buf, int off, int len)
574  {  {
575    int result;  #ifndef WITHOUT_NETWORK
576    jbyte *p;    jbyte *buffer;
577    p = (*env)->GetByteArrayElements(env, buf, 0);    int   bytes_sent;
578      
579    result = write(fd, p + off, len);    buffer = (*env)->GetByteArrayElements(env, buf, 0);
580    
581    (*env)->ReleaseByteArrayElements(env, buf, p, 0);    TARGET_NATIVE_NETWORK_SOCKET_SEND(fd, buffer + off, len, bytes_sent);
582    
583      (*env)->ReleaseByteArrayElements(env, buf, buffer, 0);
584    
585    return result;    return(bytes_sent);
586    #else /* not WITHOUT_NETWORK */
587      return(0);
588    #endif /* not WITHOUT_NETWORK */
589  }  }

Legend:
Removed from v.1.1  
changed lines
  Added in v.1.2

savannah-hackers-public@gnu.org
ViewVC Help
Powered by ViewVC 1.1.26