318 }
319 return portUnreachableSupported;
320 }
321
322 /*
323 * This function "purges" all outstanding ICMP port unreachable packets
324 * outstanding on a socket and returns JNI_TRUE if any ICMP messages
325 * have been purged. The rational for purging is to emulate normal BSD
326 * behaviour whereby receiving a "connection reset" status resets the
327 * socket.
328 */
329 static jboolean purgeOutstandingICMP(JNIEnv *env, jobject this, jint fd)
330 {
331 jboolean got_icmp = JNI_FALSE;
332 char buf[1];
333 fd_set tbl;
334 struct timeval t = { 0, 0 };
335 struct sockaddr_in rmtaddr;
336 int addrlen = sizeof(rmtaddr);
337
338 /*
339 * A no-op if this OS doesn't support it.
340 */
341 if (!supportPortUnreachable()) {
342 return JNI_FALSE;
343 }
344
345 /*
346 * Peek at the queue to see if there is an ICMP port unreachable. If there
347 * is then receive it.
348 */
349 FD_ZERO(&tbl);
350 FD_SET(fd, &tbl);
351 while(1) {
352 if (select(/*ignored*/fd+1, &tbl, 0, 0, &t) <= 0) {
353 break;
354 }
355 if (recvfrom(fd, buf, 1, MSG_PEEK,
356 (struct sockaddr *)&rmtaddr, &addrlen) != JVM_IO_ERR) {
357 break;
414 ia4_clazz = (*env)->NewGlobalRef(env, ia4_clazz);
415 CHECK_NULL(ia4_clazz);
416 ia4_ctor = (*env)->GetMethodID(env, ia4_clazz, "<init>", "()V");
417 CHECK_NULL(ia4_ctor);
418
419
420 InitializeCriticalSection(&sizeCheckLock);
421 }
422
423 JNIEXPORT void JNICALL
424 Java_java_net_TwoStacksPlainDatagramSocketImpl_bind0(JNIEnv *env, jobject this,
425 jint port, jobject addressObj,
426 jboolean exclBind) {
427 jobject fdObj = (*env)->GetObjectField(env, this, pdsi_fdID);
428 jobject fd1Obj = (*env)->GetObjectField(env, this, pdsi_fd1ID);
429
430 int fd, fd1, family;
431 int ipv6_supported = ipv6_available();
432
433 SOCKETADDRESS lcladdr;
434 int lcladdrlen;
435 int address;
436
437 family = getInetAddress_family(env, addressObj);
438 if (family == IPv6 && !ipv6_supported) {
439 JNU_ThrowByName(env, JNU_JAVANETPKG "SocketException",
440 "Protocol family not supported");
441 return;
442 }
443
444 if (IS_NULL(fdObj) || (ipv6_supported && IS_NULL(fd1Obj))) {
445 JNU_ThrowByName(env, JNU_JAVANETPKG "SocketException", "socket closed");
446 return;
447 } else {
448 fd = (*env)->GetIntField(env, fdObj, IO_fd_fdID);
449 if (ipv6_supported) {
450 fd1 = (*env)->GetIntField(env, fd1Obj, IO_fd_fdID);
451 }
452 }
453 if (IS_NULL(addressObj)) {
454 JNU_ThrowNullPointerException(env, "argument address");
455 return;
456 } else {
600 /* The object's field */
601 jobject fdObj;
602 /* The fdObj'fd */
603 jint fd, len;
604 SOCKETADDRESS addr;
605
606 if (family == IPv4) {
607 fdObj = (*env)->GetObjectField(env, this, pdsi_fdID);
608 len = sizeof (struct sockaddr_in);
609 } else {
610 fdObj = (*env)->GetObjectField(env, this, pdsi_fd1ID);
611 len = sizeof (struct SOCKADDR_IN6);
612 }
613
614 if (IS_NULL(fdObj)) {
615 /* disconnect doesn't throw any exceptions */
616 return;
617 }
618 fd = (*env)->GetIntField(env, fdObj, IO_fd_fdID);
619
620 memset(&addr, 0, len);
621 connect(fd, (struct sockaddr *)&addr, len);
622
623 /*
624 * use SIO_UDP_CONNRESET
625 * to disable ICMP port unreachable handling here.
626 */
627 if (xp_or_later) {
628 DWORD x1, x2; /* ignored result codes */
629 int t = FALSE;
630 WSAIoctl(fd,SIO_UDP_CONNRESET,&t,sizeof(t),&x1,sizeof(x1),&x2,0,0);
631 }
632 }
633
634 /*
635 * Class: java_net_TwoStacksPlainDatagramSocketImpl
636 * Method: send
637 * Signature: (Ljava/net/DatagramPacket;)V
638 */
639 JNIEXPORT void JNICALL
640 Java_java_net_TwoStacksPlainDatagramSocketImpl_send(JNIEnv *env, jobject this,
641 jobject packet) {
642
643 char BUF[MAX_BUFFER_LEN];
644 char *fullPacket;
645 jobject fdObj;
646 jint fd;
647
648 jobject iaObj;
649 jint address;
650 jint family;
651
652 jint packetBufferOffset, packetBufferLen, packetPort;
653 jbyteArray packetBuffer;
654 jboolean connected;
655
656 SOCKETADDRESS rmtaddr;
657 SOCKETADDRESS *addrp = &rmtaddr;
658 int addrlen;
659
660
661 if (IS_NULL(packet)) {
662 JNU_ThrowNullPointerException(env, "null packet");
663 return;
664 }
665
666 iaObj = (*env)->GetObjectField(env, packet, dp_addressID);
667
668 packetPort = (*env)->GetIntField(env, packet, dp_portID);
669 packetBufferOffset = (*env)->GetIntField(env, packet, dp_offsetID);
670 packetBuffer = (jbyteArray)(*env)->GetObjectField(env, packet, dp_bufID);
671 connected = (*env)->GetBooleanField(env, this, pdsi_connected);
672
673 if (IS_NULL(iaObj) || IS_NULL(packetBuffer)) {
674 JNU_ThrowNullPointerException(env, "null address || null buffer");
675 return;
676 }
677
678 family = getInetAddress_family(env, iaObj);
679 if (family == IPv4) {
1427 /* check to see if it's because the buffer was too small */
1428 if (errorCode == WSAEMSGSIZE) {
1429 /* it is because the buffer is too small. It's UDP, it's
1430 * unreliable, it's all good. discard the rest of the
1431 * data..
1432 */
1433 n = packetBufferLen;
1434 } else {
1435 /* failure */
1436 (*env)->SetIntField(env, packet, dp_lengthID, 0);
1437 }
1438 }
1439 if (n == -1) {
1440 JNU_ThrowByName(env, JNU_JAVANETPKG "SocketException", "socket closed");
1441 } else if (n == -2) {
1442 JNU_ThrowByName(env, JNU_JAVAIOPKG "InterruptedIOException",
1443 "operation interrupted");
1444 } else if (n < 0) {
1445 NET_ThrowCurrent(env, "Datagram receive failed");
1446 } else {
1447 int port;
1448 jobject packetAddress;
1449
1450 /*
1451 * Check if there is an InetAddress already associated with this
1452 * packet. If so we check if it is the same source address. We
1453 * can't update any existing InetAddress because it is immutable
1454 */
1455 packetAddress = (*env)->GetObjectField(env, packet, dp_addressID);
1456
1457 if (packetAddress != NULL) {
1458 if (!NET_SockaddrEqualsInetAddress(env, (struct sockaddr *)&remote_addr, packetAddress)) {
1459 /* force a new InetAddress to be created */
1460 packetAddress = NULL;
1461 }
1462 }
1463 if (packetAddress == NULL) {
1464 packetAddress = NET_SockaddrToInetAddress(env, (struct sockaddr *)&remote_addr, &port);
1465 /* stuff the new Inetaddress in the packet */
1466 (*env)->SetObjectField(env, packet, dp_addressID, packetAddress);
1467 } else {
1805 if (setsockopt(fd, IPPROTO_IP, IP_MULTICAST_IF,
1806 (const char*)&in, sizeof(in)) < 0) {
1807 NET_ThrowByNameWithLastError(env, JNU_JAVANETPKG "SocketException",
1808 "Error setting socket option");
1809 }
1810 return;
1811 }
1812 }
1813 }
1814
1815 /*
1816 * Class: java_net_TwoStacksPlainDatagramSocketImpl
1817 * Method: socketNativeSetOption
1818 * Signature: (ILjava/lang/Object;)V
1819 */
1820 JNIEXPORT void JNICALL
1821 Java_java_net_TwoStacksPlainDatagramSocketImpl_socketNativeSetOption(JNIEnv *env,jobject this,
1822 jint opt,jobject value) {
1823
1824 int fd=-1, fd1=-1;
1825 int levelv4, levelv6, optnamev4, optnamev6, optlen;
1826 union {
1827 int i;
1828 char c;
1829 } optval;
1830 int ipv6_supported = ipv6_available();
1831 fd = getFD(env, this);
1832
1833 if (ipv6_supported) {
1834 fd1 = getFD1(env, this);
1835 }
1836 if (fd < 0 && fd1 < 0) {
1837 JNU_ThrowByName(env, JNU_JAVANETPKG "SocketException", "socket closed");
1838 return;
1839 }
1840
1841 if ((opt == java_net_SocketOptions_IP_MULTICAST_IF) ||
1842 (opt == java_net_SocketOptions_IP_MULTICAST_IF2)) {
1843
1844 setMulticastInterface(env, this, fd, fd1, opt, value);
1845 return;
1846 }
1847
1848 /*
1849 * Map the Java level socket option to the platform specific
2176 }
2177 return NULL;
2178 }
2179
2180
2181 /*
2182 * Returns relevant info as a jint.
2183 *
2184 * Class: java_net_TwoStacksPlainDatagramSocketImpl
2185 * Method: socketGetOption
2186 * Signature: (I)Ljava/lang/Object;
2187 */
2188 JNIEXPORT jobject JNICALL
2189 Java_java_net_TwoStacksPlainDatagramSocketImpl_socketGetOption(JNIEnv *env, jobject this,
2190 jint opt) {
2191
2192 int fd=-1, fd1=-1;
2193 int level, optname, optlen;
2194 union {
2195 int i;
2196 } optval;
2197 int ipv6_supported = ipv6_available();
2198
2199 fd = getFD(env, this);
2200 if (ipv6_supported) {
2201 fd1 = getFD1(env, this);
2202 }
2203
2204 if (fd < 0 && fd1 < 0) {
2205 JNU_ThrowByName(env, JNU_JAVANETPKG "SocketException",
2206 "Socket closed");
2207 return NULL;
2208 }
2209
2210 /*
2211 * Handle IP_MULTICAST_IF separately
2212 */
2213 if (opt == java_net_SocketOptions_IP_MULTICAST_IF ||
2214 opt == java_net_SocketOptions_IP_MULTICAST_IF2) {
2215 return getMulticastInterface(env, this, fd, fd1, opt);
2216 }
2427
2428 return (jbyte)result;
2429 }
2430
2431 /* join/leave the named group on the named interface, or if no interface specified
2432 * then the interface set with setInterfac(), or the default interface otherwise */
2433
2434 static void mcast_join_leave(JNIEnv *env, jobject this,
2435 jobject iaObj, jobject niObj,
2436 jboolean join)
2437 {
2438 jobject fdObj = (*env)->GetObjectField(env, this, pdsi_fdID);
2439 jobject fd1Obj = (*env)->GetObjectField(env, this, pdsi_fd1ID);
2440 jint fd = -1, fd1 = -1;
2441
2442 SOCKETADDRESS name;
2443 struct ip_mreq mname;
2444 struct ipv6_mreq mname6;
2445
2446 struct in_addr in;
2447 DWORD ifindex;
2448
2449 int len, family;
2450 int ipv6_supported = ipv6_available();
2451 int cmd ;
2452
2453 if (IS_NULL(fdObj) && IS_NULL(fd1Obj)) {
2454 JNU_ThrowByName(env, JNU_JAVANETPKG "SocketException",
2455 "Socket closed");
2456 return;
2457 }
2458 if (!IS_NULL(fdObj)) {
2459 fd = (*env)->GetIntField(env, fdObj, IO_fd_fdID);
2460 }
2461 if (ipv6_supported && !IS_NULL(fd1Obj)) {
2462 fd1 = (*env)->GetIntField(env, fd1Obj, IO_fd_fdID);
2463 }
2464
2465 if (IS_NULL(iaObj)) {
2466 JNU_ThrowNullPointerException(env, "address");
2467 return;
2468 }
2469
2470 if (NET_InetAddressToSockaddr(env, iaObj, 0, (struct sockaddr *)&name, &len, JNI_FALSE) != 0) {
2471 return;
2472 }
|
318 }
319 return portUnreachableSupported;
320 }
321
322 /*
323 * This function "purges" all outstanding ICMP port unreachable packets
324 * outstanding on a socket and returns JNI_TRUE if any ICMP messages
325 * have been purged. The rational for purging is to emulate normal BSD
326 * behaviour whereby receiving a "connection reset" status resets the
327 * socket.
328 */
329 static jboolean purgeOutstandingICMP(JNIEnv *env, jobject this, jint fd)
330 {
331 jboolean got_icmp = JNI_FALSE;
332 char buf[1];
333 fd_set tbl;
334 struct timeval t = { 0, 0 };
335 struct sockaddr_in rmtaddr;
336 int addrlen = sizeof(rmtaddr);
337
338 memset((char *)&rmtaddr, 0, sizeof(rmtaddr));
339
340 /*
341 * A no-op if this OS doesn't support it.
342 */
343 if (!supportPortUnreachable()) {
344 return JNI_FALSE;
345 }
346
347 /*
348 * Peek at the queue to see if there is an ICMP port unreachable. If there
349 * is then receive it.
350 */
351 FD_ZERO(&tbl);
352 FD_SET(fd, &tbl);
353 while(1) {
354 if (select(/*ignored*/fd+1, &tbl, 0, 0, &t) <= 0) {
355 break;
356 }
357 if (recvfrom(fd, buf, 1, MSG_PEEK,
358 (struct sockaddr *)&rmtaddr, &addrlen) != JVM_IO_ERR) {
359 break;
416 ia4_clazz = (*env)->NewGlobalRef(env, ia4_clazz);
417 CHECK_NULL(ia4_clazz);
418 ia4_ctor = (*env)->GetMethodID(env, ia4_clazz, "<init>", "()V");
419 CHECK_NULL(ia4_ctor);
420
421
422 InitializeCriticalSection(&sizeCheckLock);
423 }
424
425 JNIEXPORT void JNICALL
426 Java_java_net_TwoStacksPlainDatagramSocketImpl_bind0(JNIEnv *env, jobject this,
427 jint port, jobject addressObj,
428 jboolean exclBind) {
429 jobject fdObj = (*env)->GetObjectField(env, this, pdsi_fdID);
430 jobject fd1Obj = (*env)->GetObjectField(env, this, pdsi_fd1ID);
431
432 int fd, fd1, family;
433 int ipv6_supported = ipv6_available();
434
435 SOCKETADDRESS lcladdr;
436 int lcladdrlen = sizeof(lcladdr);
437 int address;
438
439 memset((char *)&lcladdr, 0, sizeof(lcladdr));
440
441 family = getInetAddress_family(env, addressObj);
442 if (family == IPv6 && !ipv6_supported) {
443 JNU_ThrowByName(env, JNU_JAVANETPKG "SocketException",
444 "Protocol family not supported");
445 return;
446 }
447
448 if (IS_NULL(fdObj) || (ipv6_supported && IS_NULL(fd1Obj))) {
449 JNU_ThrowByName(env, JNU_JAVANETPKG "SocketException", "socket closed");
450 return;
451 } else {
452 fd = (*env)->GetIntField(env, fdObj, IO_fd_fdID);
453 if (ipv6_supported) {
454 fd1 = (*env)->GetIntField(env, fd1Obj, IO_fd_fdID);
455 }
456 }
457 if (IS_NULL(addressObj)) {
458 JNU_ThrowNullPointerException(env, "argument address");
459 return;
460 } else {
604 /* The object's field */
605 jobject fdObj;
606 /* The fdObj'fd */
607 jint fd, len;
608 SOCKETADDRESS addr;
609
610 if (family == IPv4) {
611 fdObj = (*env)->GetObjectField(env, this, pdsi_fdID);
612 len = sizeof (struct sockaddr_in);
613 } else {
614 fdObj = (*env)->GetObjectField(env, this, pdsi_fd1ID);
615 len = sizeof (struct SOCKADDR_IN6);
616 }
617
618 if (IS_NULL(fdObj)) {
619 /* disconnect doesn't throw any exceptions */
620 return;
621 }
622 fd = (*env)->GetIntField(env, fdObj, IO_fd_fdID);
623
624 memset((char *)&addr, 0, len);
625 connect(fd, (struct sockaddr *)&addr, len);
626
627 /*
628 * use SIO_UDP_CONNRESET
629 * to disable ICMP port unreachable handling here.
630 */
631 if (xp_or_later) {
632 DWORD x1 = 0, x2 = 0; /* ignored result codes */
633 int t = FALSE;
634 WSAIoctl(fd,SIO_UDP_CONNRESET,&t,sizeof(t),&x1,sizeof(x1),&x2,0,0);
635 }
636 }
637
638 /*
639 * Class: java_net_TwoStacksPlainDatagramSocketImpl
640 * Method: send
641 * Signature: (Ljava/net/DatagramPacket;)V
642 */
643 JNIEXPORT void JNICALL
644 Java_java_net_TwoStacksPlainDatagramSocketImpl_send(JNIEnv *env, jobject this,
645 jobject packet) {
646
647 char BUF[MAX_BUFFER_LEN];
648 char *fullPacket;
649 jobject fdObj;
650 jint fd;
651
652 jobject iaObj;
653 jint address;
654 jint family;
655
656 jint packetBufferOffset, packetBufferLen, packetPort;
657 jbyteArray packetBuffer;
658 jboolean connected;
659
660 SOCKETADDRESS rmtaddr;
661 SOCKETADDRESS *addrp = &rmtaddr;
662 int addrlen = 0;
663
664 memset((char *)&rmtaddr, 0, sizeof(rmtaddr));
665
666 if (IS_NULL(packet)) {
667 JNU_ThrowNullPointerException(env, "null packet");
668 return;
669 }
670
671 iaObj = (*env)->GetObjectField(env, packet, dp_addressID);
672
673 packetPort = (*env)->GetIntField(env, packet, dp_portID);
674 packetBufferOffset = (*env)->GetIntField(env, packet, dp_offsetID);
675 packetBuffer = (jbyteArray)(*env)->GetObjectField(env, packet, dp_bufID);
676 connected = (*env)->GetBooleanField(env, this, pdsi_connected);
677
678 if (IS_NULL(iaObj) || IS_NULL(packetBuffer)) {
679 JNU_ThrowNullPointerException(env, "null address || null buffer");
680 return;
681 }
682
683 family = getInetAddress_family(env, iaObj);
684 if (family == IPv4) {
1432 /* check to see if it's because the buffer was too small */
1433 if (errorCode == WSAEMSGSIZE) {
1434 /* it is because the buffer is too small. It's UDP, it's
1435 * unreliable, it's all good. discard the rest of the
1436 * data..
1437 */
1438 n = packetBufferLen;
1439 } else {
1440 /* failure */
1441 (*env)->SetIntField(env, packet, dp_lengthID, 0);
1442 }
1443 }
1444 if (n == -1) {
1445 JNU_ThrowByName(env, JNU_JAVANETPKG "SocketException", "socket closed");
1446 } else if (n == -2) {
1447 JNU_ThrowByName(env, JNU_JAVAIOPKG "InterruptedIOException",
1448 "operation interrupted");
1449 } else if (n < 0) {
1450 NET_ThrowCurrent(env, "Datagram receive failed");
1451 } else {
1452 int port = 0;
1453 jobject packetAddress;
1454
1455 /*
1456 * Check if there is an InetAddress already associated with this
1457 * packet. If so we check if it is the same source address. We
1458 * can't update any existing InetAddress because it is immutable
1459 */
1460 packetAddress = (*env)->GetObjectField(env, packet, dp_addressID);
1461
1462 if (packetAddress != NULL) {
1463 if (!NET_SockaddrEqualsInetAddress(env, (struct sockaddr *)&remote_addr, packetAddress)) {
1464 /* force a new InetAddress to be created */
1465 packetAddress = NULL;
1466 }
1467 }
1468 if (packetAddress == NULL) {
1469 packetAddress = NET_SockaddrToInetAddress(env, (struct sockaddr *)&remote_addr, &port);
1470 /* stuff the new Inetaddress in the packet */
1471 (*env)->SetObjectField(env, packet, dp_addressID, packetAddress);
1472 } else {
1810 if (setsockopt(fd, IPPROTO_IP, IP_MULTICAST_IF,
1811 (const char*)&in, sizeof(in)) < 0) {
1812 NET_ThrowByNameWithLastError(env, JNU_JAVANETPKG "SocketException",
1813 "Error setting socket option");
1814 }
1815 return;
1816 }
1817 }
1818 }
1819
1820 /*
1821 * Class: java_net_TwoStacksPlainDatagramSocketImpl
1822 * Method: socketNativeSetOption
1823 * Signature: (ILjava/lang/Object;)V
1824 */
1825 JNIEXPORT void JNICALL
1826 Java_java_net_TwoStacksPlainDatagramSocketImpl_socketNativeSetOption(JNIEnv *env,jobject this,
1827 jint opt,jobject value) {
1828
1829 int fd=-1, fd1=-1;
1830 int levelv4 = 0, levelv6 = 0, optnamev4 = 0, optnamev6 = 0, optlen = 0;
1831 union {
1832 int i;
1833 char c;
1834 } optval = { 0 };
1835 int ipv6_supported = ipv6_available();
1836 fd = getFD(env, this);
1837
1838 if (ipv6_supported) {
1839 fd1 = getFD1(env, this);
1840 }
1841 if (fd < 0 && fd1 < 0) {
1842 JNU_ThrowByName(env, JNU_JAVANETPKG "SocketException", "socket closed");
1843 return;
1844 }
1845
1846 if ((opt == java_net_SocketOptions_IP_MULTICAST_IF) ||
1847 (opt == java_net_SocketOptions_IP_MULTICAST_IF2)) {
1848
1849 setMulticastInterface(env, this, fd, fd1, opt, value);
1850 return;
1851 }
1852
1853 /*
1854 * Map the Java level socket option to the platform specific
2181 }
2182 return NULL;
2183 }
2184
2185
2186 /*
2187 * Returns relevant info as a jint.
2188 *
2189 * Class: java_net_TwoStacksPlainDatagramSocketImpl
2190 * Method: socketGetOption
2191 * Signature: (I)Ljava/lang/Object;
2192 */
2193 JNIEXPORT jobject JNICALL
2194 Java_java_net_TwoStacksPlainDatagramSocketImpl_socketGetOption(JNIEnv *env, jobject this,
2195 jint opt) {
2196
2197 int fd=-1, fd1=-1;
2198 int level, optname, optlen;
2199 union {
2200 int i;
2201 } optval = {0};
2202 int ipv6_supported = ipv6_available();
2203
2204 fd = getFD(env, this);
2205 if (ipv6_supported) {
2206 fd1 = getFD1(env, this);
2207 }
2208
2209 if (fd < 0 && fd1 < 0) {
2210 JNU_ThrowByName(env, JNU_JAVANETPKG "SocketException",
2211 "Socket closed");
2212 return NULL;
2213 }
2214
2215 /*
2216 * Handle IP_MULTICAST_IF separately
2217 */
2218 if (opt == java_net_SocketOptions_IP_MULTICAST_IF ||
2219 opt == java_net_SocketOptions_IP_MULTICAST_IF2) {
2220 return getMulticastInterface(env, this, fd, fd1, opt);
2221 }
2432
2433 return (jbyte)result;
2434 }
2435
2436 /* join/leave the named group on the named interface, or if no interface specified
2437 * then the interface set with setInterfac(), or the default interface otherwise */
2438
2439 static void mcast_join_leave(JNIEnv *env, jobject this,
2440 jobject iaObj, jobject niObj,
2441 jboolean join)
2442 {
2443 jobject fdObj = (*env)->GetObjectField(env, this, pdsi_fdID);
2444 jobject fd1Obj = (*env)->GetObjectField(env, this, pdsi_fd1ID);
2445 jint fd = -1, fd1 = -1;
2446
2447 SOCKETADDRESS name;
2448 struct ip_mreq mname;
2449 struct ipv6_mreq mname6;
2450
2451 struct in_addr in;
2452 DWORD ifindex = 0;
2453
2454 int len, family;
2455 int ipv6_supported = ipv6_available();
2456 int cmd ;
2457
2458 memset((char *)&in, 0, sizeof(in));
2459 memset((char *)&name, 0, sizeof(name));
2460
2461 if (IS_NULL(fdObj) && IS_NULL(fd1Obj)) {
2462 JNU_ThrowByName(env, JNU_JAVANETPKG "SocketException",
2463 "Socket closed");
2464 return;
2465 }
2466 if (!IS_NULL(fdObj)) {
2467 fd = (*env)->GetIntField(env, fdObj, IO_fd_fdID);
2468 }
2469 if (ipv6_supported && !IS_NULL(fd1Obj)) {
2470 fd1 = (*env)->GetIntField(env, fd1Obj, IO_fd_fdID);
2471 }
2472
2473 if (IS_NULL(iaObj)) {
2474 JNU_ThrowNullPointerException(env, "address");
2475 return;
2476 }
2477
2478 if (NET_InetAddressToSockaddr(env, iaObj, 0, (struct sockaddr *)&name, &len, JNI_FALSE) != 0) {
2479 return;
2480 }
|