JVM EPollArrayWrapper

EPollArrayWrapper

 

EPollArrayWrapper类在jdk\src\solaris\classes\sun\nio\ch目录下。用于linux平台下,操作一个本地epoll_event结构数组。主要封装了epoll的相关函数调用。

 

EPollArrayWrapper

普通方法

initInterrupt

putEventOps

putData

putDescriptor

getEventOps

getDescriptor

setInterest

add

release

closeEPollFD

poll

updateRegistrations

interrupt

interruptedIndex

interrupted

clearInterrupted

EPollArrayWrapper

EPollArrayWrapper通过Native方法与JVM交互。Native实现在jdk\src\solaris\native\sun\nio\ch目录下,对应EPollArrayWrapper.c。

 

 

EPollArrayWrapper

Native方法

epollCreate

epollCtl

epollWait

sizeofEPollEvent

offsetofData

fdLimit

interrupt

init

EPollArrayWrapper

初始化init

执行一些初始化操作:

通过dlsym方式将

epoll_create_func指向epoll_create

epoll_ctl_func指向epoll_ctl

epoll_wait_func指向epoll_wait

 

 

 

 

EPollArrayWrapper

源代码如下:

JNIEXPORT void JNICALL

Java_sun_nio_ch_EPollArrayWrapper_init(JNIEnv *env, jclass this)

{

    epoll_create_func = (epoll_create_t) dlsym(RTLD_DEFAULT, "epoll_create");

    epoll_ctl_func    = (epoll_ctl_t)    dlsym(RTLD_DEFAULT, "epoll_ctl");

    epoll_wait_func   = (epoll_wait_t)   dlsym(RTLD_DEFAULT, "epoll_wait");

 

    if ((epoll_create_func == NULL) || (epoll_ctl_func == NULL) ||

        (epoll_wait_func == NULL)) {

        JNU_ThrowInternalError(env, "unable to get address of epoll functions, pre-2.6 kernel?");

    }

}

 

 

 

 

EPollArrayWrapper

创建epoll epollCreate

 

源代码如下:

JNIEXPORT jint JNICALL

Java_sun_nio_ch_EPollArrayWrapper_epollCreate(JNIEnv *env, jobject this)

{

    /*

     * epoll_create expects a size as a hint to the kernel about how to

     * dimension internal structures. We can't predict the size in advance.

     */

    int epfd = (*epoll_create_func)(256);

    if (epfd < 0) {

       JNU_ThrowIOExceptionWithLastError(env, "epoll_create failed");

    }

    return epfd;

}

 

 

 

EPollArrayWrapper

获取文件句柄上限 fdLimit

用于获取打开的文件句柄上限,这里是socket句柄。这个限制实际上可以通过ulimit 进行查看和设置。可以通过ulimit –a查看open files                      (-n),也可以通过ulimit –n直接查看。

 

 

 

 

 

EPollArrayWrapper

源代码如下:

JNIEXPORT jint JNICALL

Java_sun_nio_ch_EPollArrayWrapper_fdLimit(JNIEnv *env, jclass this)

{

    struct rlimit rlp;

    if (getrlimit(RLIMIT_NOFILE, &rlp) < 0) {

        JNU_ThrowIOExceptionWithLastError(env, "getrlimit failed");

    }

    return (jint)rlp.rlim_max;

}

 

 

 

 

 

 

EPollArrayWrapper

epoll_event结构大小

源代码如下:

JNIEXPORT jint JNICALL

Java_sun_nio_ch_EPollArrayWrapper_sizeofEPollEvent(JNIEnv* env, jclass this)

{

    return sizeof(struct epoll_event);

}

 

 

 

 

 

EPollArrayWrapper

用户数据data字段在epoll_event结构中的偏移量 offsetofData

JNIEXPORT jint JNICALL

Java_sun_nio_ch_EPollArrayWrapper_offsetofData(JNIEnv* env, jclass this)

{

    return offsetof(struct epoll_event, data);

}

 

 

 

 

EPollArrayWrapper

在epfd 上执行操作 epollCtl

源代码如下:

JNIEXPORT void JNICALL

Java_sun_nio_ch_EPollArrayWrapper_epollCtl(JNIEnv *env, jobject this, jint epfd,

                                           jint opcode, jint fd, jint events)

{

    struct epoll_event event;

    int res;

 

    event.events = events;

    event.data.fd = fd;

 

    RESTARTABLE((*epoll_ctl_func)(epfd, (int)opcode, (int)fd, &event), res);

 

    /*

     * A channel may be registered with several Selectors. When each Selector

     * is polled a EPOLL_CTL_DEL op will be inserted into its pending update

     * list to remove the file descriptor from epoll. The "last" Selector will

     * close the file descriptor which automatically unregisters it from each

     * epoll descriptor. To avoid costly synchronization between Selectors we

     * allow pending updates to be processed, ignoring errors. The errors are

     * harmless as the last update for the file descriptor is guaranteed to

     * be EPOLL_CTL_DEL.

     */

    if (res < 0 && errno != EBADF && errno != ENOENT && errno != EPERM) {

        JNU_ThrowIOExceptionWithLastError(env, "epoll_ctl failed");

    }

}

 

 

 

EPollArrayWrapper

epoll_wait

源代码如下:

JNIEXPORT jint JNICALL

Java_sun_nio_ch_EPollArrayWrapper_epollWait(JNIEnv *env, jobject this,

                                            jlong address, jint numfds,

                                            jlong timeout, jint epfd)

{

    struct epoll_event *events = jlong_to_ptr(address);

    int res;

 

    if (timeout <= 0) {           /* Indefinite or no wait */

        RESTARTABLE((*epoll_wait_func)(epfd, events, numfds, timeout), res);

    } else {                      /* Bounded wait; bounded restarts */

        res = iepoll(epfd, events, numfds, timeout);

    }

 

    if (res < 0) {

        JNU_ThrowIOExceptionWithLastError(env, "epoll_wait failed");

    }

    return res;

}

 

 

 

 

EPollArrayWrapper

中断操作 interrupt

源代码如下:

JNIEXPORT void JNICALL

Java_sun_nio_ch_EPollArrayWrapper_interrupt(JNIEnv *env, jobject this, jint fd)

{

    int fakebuf[1];

    fakebuf[0] = 1;

    if (write(fd, fakebuf, 1) < 0) {

        JNU_ThrowIOExceptionWithLastError(env,"write to interrupt fd failed");

    }

}

 

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值