Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/358.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 为什么是Tomcat';s非阻塞连接器是否使用阻塞插座?_Java_Tomcat_Nio - Fatal编程技术网

Java 为什么是Tomcat';s非阻塞连接器是否使用阻塞插座?

Java 为什么是Tomcat';s非阻塞连接器是否使用阻塞插座?,java,tomcat,nio,Java,Tomcat,Nio,我阅读了有关非阻塞I/O、java NIO和tomcat连接器的内容,查看了tomcat NIO连接器的代码,并且: 我没有NIO方面的经验,所以有人能解释一下,当套接字被配置为阻塞时,它是如何非阻塞的吗?看起来下面这行代码是在这次提交时引入的 据我所知,NioEndpoint正在使用blocking ServerSocketChannel来阻止和等待传入连接,只有在接受该连接后,它才会以非阻塞方式处理该传入套接字通道(请参阅setSocketOptions方法) 将ServerSocketCh

我阅读了有关非阻塞I/O、java NIO和tomcat连接器的内容,查看了tomcat NIO连接器的代码,并且:


我没有NIO方面的经验,所以有人能解释一下,当套接字被配置为阻塞时,它是如何非阻塞的吗?

看起来下面这行代码是在这次提交时引入的

据我所知,NioEndpoint正在使用blocking ServerSocketChannel来阻止和等待传入连接,只有在接受该连接后,它才会以非阻塞方式处理该传入套接字通道(请参阅setSocketOptions方法)

将ServerSocketChannel设置为非阻塞模式的替代方法将导致作者指出的繁忙读取,即线程将不断轮询传入连接,因为非阻塞模式下的accept()可能返回null

你可以找到一些有用的解释

附言。
我假设神秘的APR代表Apache便携式运行时。

从调用者的角度看是非阻塞的。API仍然需要使用阻塞(在工作线程中)或异步I/O来实际完成操作。否则,套接字将需要一个带有CPU浸泡的自旋锁


您需要查看实现的其余部分,以了解此映射是如何完成的。

阅读代码后:

正在侦听传入连接的
serverSock
对象被阻塞。与其新接受的连接关联的
套接字
通道对象是实现非阻塞I/O的对象

侦听传入连接的线程的
Acceptor类在其
run
方法中具有以下定义:

protected class Acceptor extends AbstractEndpoint.Acceptor {
        @Override
        public void run() {
            // Loop until we receive a shutdown command
            while (running) {
                // Loop if endpoint is paused
                while (paused && running) {
                   ...
                try {
                        ........
                    SocketChannel socket = null;
                    try {
                        // Accept the next incoming connection from the server
                        // socket
                        socket = serverSock.accept(); 

                    } catch (IOException ioe) {............}
                ...................
                // setSocketOptions() will add channel to the poller
                // if successful
                if (running && !paused) {
                    if (!setSocketOptions(socket)) {
                        countDownConnection();
                        closeSocket(socket);
                    }
                } ....
如您所见,是
setSocketOptions
方法处理新的
socket
,它具有以下代码:

protected boolean setSocketOptions(SocketChannel socket) {
        // Process the connection
        try {
            //disable blocking, APR style, we are gonna be polling it
            socket.configureBlocking(false);
            Socket sock = socket.socket();
            socketProperties.setProperties(sock); 
与用于在相应连接的端点中发送/接收数据的每个连接关联的
socket
通道对象是真正实现
非阻塞I/O
的对象


尽管人们总是可以将
serverSock
对象
accept
方法设置为非阻塞,但我认为使
select
(即accept)操作非阻塞是不切实际的,不会有任何实际用途,在任何实际环境中都不会有用。我想不出任何非阻塞接受操作有用的用例。这是给我的。

是否应该将其设置为
false
以使其成为非阻塞,这是您的问题,对吗?您似乎没有听说过java.nio.channels.Selector。您是对的-我没有听说过。注释仍然正确,因为仍然需要映射到一些底层操作系统操作,并且在*ix实现中可能映射到sockets API select()调用@ultrajohn为选择套接字上的阻塞设置提供了更精确的理由。正如我所建议的那样,NIO似乎在每个接受会话上都有一个线程。
protected boolean setSocketOptions(SocketChannel socket) {
        // Process the connection
        try {
            //disable blocking, APR style, we are gonna be polling it
            socket.configureBlocking(false);
            Socket sock = socket.socket();
            socketProperties.setProperties(sock);