jdk/src/solaris/native/sun/nio/ch/SctpChannelImpl.c

Print this page
rev 5686 : 7201071: InetSocketAddress serialization issue
Reviewed-by: alanb, michaelm, skoivu


  50 
  51 struct controlData {
  52     int assocId;
  53     unsigned short streamNumber;
  54     jboolean unordered;
  55     unsigned int ppid;
  56 };
  57 
  58 static jclass    smi_class;    /* sun.nio.ch.SctpMessageInfoImpl            */
  59 static jmethodID smi_ctrID;    /* sun.nio.ch.SctpMessageInfoImpl.<init>     */
  60 static jfieldID  src_valueID;  /* sun.nio.ch.SctpResultContainer.value      */
  61 static jfieldID  src_typeID;   /* sun.nio.ch.SctpResultContainer.type       */
  62 static jclass    ssf_class;    /* sun.nio.ch.SctpSendFailed                 */
  63 static jmethodID ssf_ctrID;    /* sun.nio.ch.SctpSendFailed.<init>          */
  64 static jclass    sac_class;    /* sun.nio.ch.SctpAssociationChanged         */
  65 static jmethodID sac_ctrID;    /* sun.nio.ch.SctpAssociationChanged.<init>  */
  66 static jclass    spc_class;    /* sun.nio.ch.SctpPeerAddressChanged         */
  67 static jmethodID spc_ctrID;    /* sun.nio.ch.SctpPeerAddressChanged.<init>  */
  68 static jclass    ss_class;     /* sun.nio.ch.SctpShutdown                   */
  69 static jmethodID ss_ctrID;     /* sun.nio.ch.SctpShutdown.<init>            */
  70 static jfieldID  isa_addrID;   /* java.net.InetSocketAddress.addr           */
  71 static jfieldID  isa_portID;   /* java.net.InetSocketAddress.port           */
  72 
  73 /* defined in SctpNet.c */
  74 jobject SockAddrToInetSocketAddress(JNIEnv* env, struct sockaddr* addr);
  75 
  76 /* use SocketChannelImpl's checkConnect implementation */
  77 extern jint Java_sun_nio_ch_SocketChannelImpl_checkConnect(JNIEnv* env,
  78     jobject this, jobject fdo, jboolean block, jboolean ready);
  79 
  80 /*
  81  * Class:     sun_nio_ch_SctpChannelImpl
  82  * Method:    initIDs
  83  * Signature: ()V
  84  */
  85 JNIEXPORT void JNICALL Java_sun_nio_ch_SctpChannelImpl_initIDs
  86   (JNIEnv *env, jclass klass) {
  87     jclass cls;
  88 
  89     /* SctpMessageInfoImpl */
  90     cls = (*env)->FindClass(env, MESSAGE_IMPL_CLASS);
  91     CHECK_NULL(cls);


 119     CHECK_NULL(sac_class);
 120     sac_ctrID = (*env)->GetMethodID(env, cls, "<init>", "(IIII)V");
 121     CHECK_NULL(sac_ctrID);
 122 
 123     /* SctpPeerAddrChange */
 124     cls = (*env)->FindClass(env, PEER_CHANGE_CLASS);
 125     CHECK_NULL(cls);
 126     spc_class = (*env)->NewGlobalRef(env, cls);
 127     CHECK_NULL(spc_class);
 128     spc_ctrID = (*env)->GetMethodID(env, cls, "<init>",
 129             "(ILjava/net/SocketAddress;I)V");
 130     CHECK_NULL(spc_ctrID);
 131 
 132     /* sun.nio.ch.SctpShutdown */
 133     cls = (*env)->FindClass(env, SHUTDOWN_CLASS);
 134     CHECK_NULL(cls);
 135     ss_class = (*env)->NewGlobalRef(env, cls);
 136     CHECK_NULL(ss_class);
 137     ss_ctrID = (*env)->GetMethodID(env, cls, "<init>", "(I)V");
 138     CHECK_NULL(ss_ctrID);
 139 
 140     /* InetSocketAddress */
 141     cls = (*env)->FindClass(env, "java/net/InetSocketAddress");
 142     CHECK_NULL(cls);
 143     isa_addrID = (*env)->GetFieldID(env, cls, "addr", "Ljava/net/InetAddress;");
 144     CHECK_NULL(isa_addrID);
 145     isa_portID = (*env)->GetFieldID(env, cls, "port", "I");
 146 }
 147 
 148 void getControlData
 149   (struct msghdr* msg, struct controlData* cdata) {
 150     struct cmsghdr* cmsg;
 151 
 152     for (cmsg = CMSG_FIRSTHDR(msg); cmsg != NULL; cmsg = CMSG_NXTHDR(msg, cmsg)) {
 153         if (cmsg->cmsg_level == IPPROTO_SCTP && cmsg->cmsg_type == SCTP_SNDRCV) {
 154             struct sctp_sndrcvinfo *sri;
 155 
 156             sri = (struct sctp_sndrcvinfo *) CMSG_DATA(cmsg);
 157             cdata->assocId = sri->sinfo_assoc_id;
 158             cdata->streamNumber = sri->sinfo_stream;
 159             cdata->unordered = (sri->sinfo_flags & SCTP_UNORDERED) ? JNI_TRUE :
 160                 JNI_FALSE;
 161             cdata->ppid = ntohl(sri->sinfo_ppid);
 162 
 163             return;
 164         }
 165     }


 490                    set in the result container. */
 491                 return 0;
 492             }
 493 
 494             // set iov back to addr, and reset msg_controllen
 495             iov->iov_base = addr;
 496             iov->iov_len = length;
 497             msg->msg_control = cbuf;
 498             msg->msg_controllen = sizeof(cbuf);
 499         }
 500     } while (msg->msg_flags & MSG_NOTIFICATION);
 501 
 502     handleMessage(env, resultContainerObj, msg, rv,
 503             (msg->msg_flags & MSG_EOR), (struct sockaddr*)&sa);
 504     return rv;
 505 }
 506 
 507 /*
 508  * Class:     sun_nio_ch_SctpChannelImpl
 509  * Method:    send0
 510  * Signature: (IJILjava/net/SocketAddress;IIZI)I
 511  */
 512 JNIEXPORT jint JNICALL Java_sun_nio_ch_SctpChannelImpl_send0
 513   (JNIEnv *env, jclass klass, jint fd, jlong address, jint length,
 514    jobject saTarget, jint assocId, jint streamNumber, jboolean unordered,
 515    jint ppid) {
 516     SOCKADDR sa;
 517     int sa_len = sizeof(sa);
 518     ssize_t rv = 0;
 519     jlong *addr = jlong_to_ptr(address);
 520     struct iovec iov[1];
 521     struct msghdr msg[1];
 522     int cbuf_size = CMSG_SPACE(sizeof (struct sctp_sndrcvinfo));
 523     char cbuf[CMSG_SPACE(sizeof (struct sctp_sndrcvinfo))];
 524     struct controlData cdata[1];
 525 
 526     /* SctpChannel:
 527      *    saTarget may contain the preferred address or NULL to use primary,
 528      *    assocId will always be -1
 529      * SctpMultiChannell:
 530      *    Setup new association, saTarget will contain address, assocId = -1
 531      *    Association already existing, assocId != -1, saTarget = preferred addr
 532      */
 533     if (saTarget != NULL /*&& assocId <= 0*/) {
 534 
 535         jobject targetAddress = (*env)->GetObjectField(env, saTarget, isa_addrID);
 536         jint targetPort = (*env)->GetIntField(env, saTarget, isa_portID);
 537 
 538         if (NET_InetAddressToSockaddr(env, targetAddress, targetPort,
 539                                       (struct sockaddr *)&sa,
 540                                       &sa_len, JNI_TRUE) != 0) {
 541             return IOS_THROWN;
 542         }
 543     } else {
 544         memset(&sa, '\x0', sa_len);
 545         sa_len = 0;
 546     }
 547 
 548     /* Set up the msghdr structure for sending */
 549     memset(msg, 0, sizeof (*msg));
 550     memset(cbuf, 0, cbuf_size);
 551     msg->msg_name = &sa;
 552     msg->msg_namelen = sa_len;
 553     iov->iov_base = addr;
 554     iov->iov_len = length;
 555     msg->msg_iov = iov;
 556     msg->msg_iovlen = 1;
 557     msg->msg_control = cbuf;




  50 
  51 struct controlData {
  52     int assocId;
  53     unsigned short streamNumber;
  54     jboolean unordered;
  55     unsigned int ppid;
  56 };
  57 
  58 static jclass    smi_class;    /* sun.nio.ch.SctpMessageInfoImpl            */
  59 static jmethodID smi_ctrID;    /* sun.nio.ch.SctpMessageInfoImpl.<init>     */
  60 static jfieldID  src_valueID;  /* sun.nio.ch.SctpResultContainer.value      */
  61 static jfieldID  src_typeID;   /* sun.nio.ch.SctpResultContainer.type       */
  62 static jclass    ssf_class;    /* sun.nio.ch.SctpSendFailed                 */
  63 static jmethodID ssf_ctrID;    /* sun.nio.ch.SctpSendFailed.<init>          */
  64 static jclass    sac_class;    /* sun.nio.ch.SctpAssociationChanged         */
  65 static jmethodID sac_ctrID;    /* sun.nio.ch.SctpAssociationChanged.<init>  */
  66 static jclass    spc_class;    /* sun.nio.ch.SctpPeerAddressChanged         */
  67 static jmethodID spc_ctrID;    /* sun.nio.ch.SctpPeerAddressChanged.<init>  */
  68 static jclass    ss_class;     /* sun.nio.ch.SctpShutdown                   */
  69 static jmethodID ss_ctrID;     /* sun.nio.ch.SctpShutdown.<init>            */


  70 
  71 /* defined in SctpNet.c */
  72 jobject SockAddrToInetSocketAddress(JNIEnv* env, struct sockaddr* addr);
  73 
  74 /* use SocketChannelImpl's checkConnect implementation */
  75 extern jint Java_sun_nio_ch_SocketChannelImpl_checkConnect(JNIEnv* env,
  76     jobject this, jobject fdo, jboolean block, jboolean ready);
  77 
  78 /*
  79  * Class:     sun_nio_ch_SctpChannelImpl
  80  * Method:    initIDs
  81  * Signature: ()V
  82  */
  83 JNIEXPORT void JNICALL Java_sun_nio_ch_SctpChannelImpl_initIDs
  84   (JNIEnv *env, jclass klass) {
  85     jclass cls;
  86 
  87     /* SctpMessageInfoImpl */
  88     cls = (*env)->FindClass(env, MESSAGE_IMPL_CLASS);
  89     CHECK_NULL(cls);


 117     CHECK_NULL(sac_class);
 118     sac_ctrID = (*env)->GetMethodID(env, cls, "<init>", "(IIII)V");
 119     CHECK_NULL(sac_ctrID);
 120 
 121     /* SctpPeerAddrChange */
 122     cls = (*env)->FindClass(env, PEER_CHANGE_CLASS);
 123     CHECK_NULL(cls);
 124     spc_class = (*env)->NewGlobalRef(env, cls);
 125     CHECK_NULL(spc_class);
 126     spc_ctrID = (*env)->GetMethodID(env, cls, "<init>",
 127             "(ILjava/net/SocketAddress;I)V");
 128     CHECK_NULL(spc_ctrID);
 129 
 130     /* sun.nio.ch.SctpShutdown */
 131     cls = (*env)->FindClass(env, SHUTDOWN_CLASS);
 132     CHECK_NULL(cls);
 133     ss_class = (*env)->NewGlobalRef(env, cls);
 134     CHECK_NULL(ss_class);
 135     ss_ctrID = (*env)->GetMethodID(env, cls, "<init>", "(I)V");
 136     CHECK_NULL(ss_ctrID);







 137 }
 138 
 139 void getControlData
 140   (struct msghdr* msg, struct controlData* cdata) {
 141     struct cmsghdr* cmsg;
 142 
 143     for (cmsg = CMSG_FIRSTHDR(msg); cmsg != NULL; cmsg = CMSG_NXTHDR(msg, cmsg)) {
 144         if (cmsg->cmsg_level == IPPROTO_SCTP && cmsg->cmsg_type == SCTP_SNDRCV) {
 145             struct sctp_sndrcvinfo *sri;
 146 
 147             sri = (struct sctp_sndrcvinfo *) CMSG_DATA(cmsg);
 148             cdata->assocId = sri->sinfo_assoc_id;
 149             cdata->streamNumber = sri->sinfo_stream;
 150             cdata->unordered = (sri->sinfo_flags & SCTP_UNORDERED) ? JNI_TRUE :
 151                 JNI_FALSE;
 152             cdata->ppid = ntohl(sri->sinfo_ppid);
 153 
 154             return;
 155         }
 156     }


 481                    set in the result container. */
 482                 return 0;
 483             }
 484 
 485             // set iov back to addr, and reset msg_controllen
 486             iov->iov_base = addr;
 487             iov->iov_len = length;
 488             msg->msg_control = cbuf;
 489             msg->msg_controllen = sizeof(cbuf);
 490         }
 491     } while (msg->msg_flags & MSG_NOTIFICATION);
 492 
 493     handleMessage(env, resultContainerObj, msg, rv,
 494             (msg->msg_flags & MSG_EOR), (struct sockaddr*)&sa);
 495     return rv;
 496 }
 497 
 498 /*
 499  * Class:     sun_nio_ch_SctpChannelImpl
 500  * Method:    send0
 501  * Signature: (IJILjava/net/InetAddress;IIIZI)I
 502  */
 503 JNIEXPORT jint JNICALL Java_sun_nio_ch_SctpChannelImpl_send0
 504   (JNIEnv *env, jclass klass, jint fd, jlong address, jint length,
 505    jobject targetAddress, jint targetPort, jint assocId, jint streamNumber,
 506    jboolean unordered, jint ppid) {
 507     SOCKADDR sa;
 508     int sa_len = sizeof(sa);
 509     ssize_t rv = 0;
 510     jlong *addr = jlong_to_ptr(address);
 511     struct iovec iov[1];
 512     struct msghdr msg[1];
 513     int cbuf_size = CMSG_SPACE(sizeof (struct sctp_sndrcvinfo));
 514     char cbuf[CMSG_SPACE(sizeof (struct sctp_sndrcvinfo))];
 515     struct controlData cdata[1];
 516 
 517     /* SctpChannel:
 518      *    targetAddress may contain the preferred address or NULL to use primary,
 519      *    assocId will always be -1
 520      * SctpMultiChannell:
 521      *    Setup new association, targetAddress will contain address, assocId = -1
 522      *    Association already existing, assocId != -1, targetAddress = preferred addr
 523      */
 524     if (targetAddress != NULL /*&& assocId <= 0*/) {




 525         if (NET_InetAddressToSockaddr(env, targetAddress, targetPort,
 526                                       (struct sockaddr *)&sa,
 527                                       &sa_len, JNI_TRUE) != 0) {
 528             return IOS_THROWN;
 529         }
 530     } else {
 531         memset(&sa, '\x0', sa_len);
 532         sa_len = 0;
 533     }
 534 
 535     /* Set up the msghdr structure for sending */
 536     memset(msg, 0, sizeof (*msg));
 537     memset(cbuf, 0, cbuf_size);
 538     msg->msg_name = &sa;
 539     msg->msg_namelen = sa_len;
 540     iov->iov_base = addr;
 541     iov->iov_len = length;
 542     msg->msg_iov = iov;
 543     msg->msg_iovlen = 1;
 544     msg->msg_control = cbuf;