Search in sources :

Example 1 with ChannelEndPoint

use of org.eclipse.jetty.io.ChannelEndPoint in project jetty.project by eclipse.

the class ThreadStarvationTest method testDefaultServletSuccess.

@Test
@Slow
public void testDefaultServletSuccess() throws Exception {
    int maxThreads = 10;
    QueuedThreadPool threadPool = new QueuedThreadPool(maxThreads, maxThreads);
    threadPool.setDetailedDump(true);
    _server = new Server(threadPool);
    // Prepare a big file to download.
    File directory = MavenTestingUtils.getTargetTestingDir();
    Files.createDirectories(directory.toPath());
    String resourceName = "resource.bin";
    Path resourcePath = Paths.get(directory.getPath(), resourceName);
    try (OutputStream output = Files.newOutputStream(resourcePath, StandardOpenOption.CREATE, StandardOpenOption.WRITE)) {
        byte[] chunk = new byte[1024];
        Arrays.fill(chunk, (byte) 'X');
        chunk[chunk.length - 2] = '\r';
        chunk[chunk.length - 1] = '\n';
        for (int i = 0; i < 256 * 1024; ++i) output.write(chunk);
    }
    final CountDownLatch writePending = new CountDownLatch(1);
    ServerConnector connector = new ServerConnector(_server, 0, 1) {

        @Override
        protected ChannelEndPoint newEndPoint(SocketChannel channel, ManagedSelector selectSet, SelectionKey key) throws IOException {
            return new SocketChannelEndPoint(channel, selectSet, key, getScheduler()) {

                @Override
                protected void onIncompleteFlush() {
                    super.onIncompleteFlush();
                    writePending.countDown();
                }
            };
        }
    };
    connector.setIdleTimeout(Long.MAX_VALUE);
    _server.addConnector(connector);
    ServletContextHandler context = new ServletContextHandler(_server, "/");
    context.setResourceBase(directory.toURI().toString());
    context.addServlet(DefaultServlet.class, "/*").setAsyncSupported(false);
    _server.setHandler(context);
    _server.start();
    List<Socket> sockets = new ArrayList<>();
    for (int i = 0; i < maxThreads * 2; ++i) {
        Socket socket = new Socket("localhost", connector.getLocalPort());
        sockets.add(socket);
        OutputStream output = socket.getOutputStream();
        String request = "" + "GET /" + resourceName + " HTTP/1.1\r\n" + "Host: localhost\r\n" + "\r\n";
        output.write(request.getBytes(StandardCharsets.UTF_8));
        output.flush();
        Thread.sleep(100);
    }
    // Wait for a the servlet to block.
    Assert.assertTrue(writePending.await(5, TimeUnit.SECONDS));
    long expected = Files.size(resourcePath);
    byte[] buffer = new byte[48 * 1024];
    List<Exchanger<Long>> totals = new ArrayList<>();
    for (Socket socket : sockets) {
        final Exchanger<Long> x = new Exchanger<>();
        totals.add(x);
        final InputStream input = socket.getInputStream();
        new Thread() {

            @Override
            public void run() {
                long total = 0;
                try {
                    // look for CRLFCRLF
                    StringBuilder header = new StringBuilder();
                    int state = 0;
                    while (state < 4 && header.length() < 2048) {
                        int ch = input.read();
                        if (ch < 0)
                            break;
                        header.append((char) ch);
                        switch(state) {
                            case 0:
                                if (ch == '\r')
                                    state = 1;
                                break;
                            case 1:
                                if (ch == '\n')
                                    state = 2;
                                else
                                    state = 0;
                                break;
                            case 2:
                                if (ch == '\r')
                                    state = 3;
                                else
                                    state = 0;
                                break;
                            case 3:
                                if (ch == '\n')
                                    state = 4;
                                else
                                    state = 0;
                                break;
                        }
                    }
                    while (total < expected) {
                        int read = input.read(buffer);
                        if (read < 0)
                            break;
                        total += read;
                    }
                } catch (IOException e) {
                    e.printStackTrace();
                } finally {
                    try {
                        x.exchange(total);
                    } catch (InterruptedException e) {
                        e.printStackTrace();
                    }
                }
            }
        }.start();
    }
    for (Exchanger<Long> x : totals) {
        Long total = x.exchange(-1L, 10000, TimeUnit.SECONDS);
        Assert.assertEquals(expected, total.longValue());
    }
    // We could read everything, good.
    for (Socket socket : sockets) socket.close();
}
Also used : ManagedSelector(org.eclipse.jetty.io.ManagedSelector) SocketChannel(java.nio.channels.SocketChannel) Server(org.eclipse.jetty.server.Server) Exchanger(java.util.concurrent.Exchanger) OutputStream(java.io.OutputStream) ArrayList(java.util.ArrayList) ServerConnector(org.eclipse.jetty.server.ServerConnector) QueuedThreadPool(org.eclipse.jetty.util.thread.QueuedThreadPool) DefaultServlet(org.eclipse.jetty.servlet.DefaultServlet) Path(java.nio.file.Path) SelectionKey(java.nio.channels.SelectionKey) InputStream(java.io.InputStream) IOException(java.io.IOException) CountDownLatch(java.util.concurrent.CountDownLatch) ChannelEndPoint(org.eclipse.jetty.io.ChannelEndPoint) SocketChannelEndPoint(org.eclipse.jetty.io.SocketChannelEndPoint) ServletContextHandler(org.eclipse.jetty.servlet.ServletContextHandler) File(java.io.File) SocketChannelEndPoint(org.eclipse.jetty.io.SocketChannelEndPoint) Socket(java.net.Socket) Test(org.junit.Test) Slow(org.eclipse.jetty.toolchain.test.annotation.Slow)

Example 2 with ChannelEndPoint

use of org.eclipse.jetty.io.ChannelEndPoint in project jetty.project by eclipse.

the class SslBytesServerTest method init.

@Before
public void init() throws Exception {
    threadPool = Executors.newCachedThreadPool();
    server = new Server();
    File keyStore = MavenTestingUtils.getTestResourceFile("keystore.jks");
    sslContextFactory = new SslContextFactory();
    sslContextFactory.setKeyStorePath(keyStore.getAbsolutePath());
    sslContextFactory.setKeyStorePassword("storepwd");
    HttpConnectionFactory httpFactory = new HttpConnectionFactory() {

        @Override
        public Connection newConnection(Connector connector, EndPoint endPoint) {
            return configure(new HttpConnection(getHttpConfiguration(), connector, endPoint, getHttpCompliance(), isRecordHttpComplianceViolations()) {

                @Override
                protected HttpParser newHttpParser(HttpCompliance compliance) {
                    return new HttpParser(newRequestHandler(), getHttpConfiguration().getRequestHeaderSize(), compliance) {

                        @Override
                        public boolean parseNext(ByteBuffer buffer) {
                            httpParses.incrementAndGet();
                            return super.parseNext(buffer);
                        }
                    };
                }

                @Override
                protected boolean onReadTimeout() {
                    final Runnable idleHook = SslBytesServerTest.this.idleHook;
                    if (idleHook != null)
                        idleHook.run();
                    return super.onReadTimeout();
                }
            }, connector, endPoint);
        }
    };
    httpFactory.getHttpConfiguration().addCustomizer(new SecureRequestCustomizer());
    SslConnectionFactory sslFactory = new SslConnectionFactory(sslContextFactory, httpFactory.getProtocol()) {

        @Override
        protected SslConnection newSslConnection(Connector connector, EndPoint endPoint, SSLEngine engine) {
            return new SslConnection(connector.getByteBufferPool(), connector.getExecutor(), endPoint, engine) {

                @Override
                protected DecryptedEndPoint newDecryptedEndPoint() {
                    return new DecryptedEndPoint() {

                        @Override
                        public int fill(ByteBuffer buffer) throws IOException {
                            sslFills.incrementAndGet();
                            return super.fill(buffer);
                        }

                        @Override
                        public boolean flush(ByteBuffer... appOuts) throws IOException {
                            sslFlushes.incrementAndGet();
                            return super.flush(appOuts);
                        }
                    };
                }
            };
        }
    };
    ServerConnector connector = new ServerConnector(server, null, null, null, 1, 1, sslFactory, httpFactory) {

        @Override
        protected ChannelEndPoint newEndPoint(SocketChannel channel, ManagedSelector selectSet, SelectionKey key) throws IOException {
            ChannelEndPoint endp = super.newEndPoint(channel, selectSet, key);
            serverEndPoint.set(endp);
            return endp;
        }
    };
    connector.setIdleTimeout(idleTimeout);
    connector.setPort(0);
    server.addConnector(connector);
    server.setHandler(new AbstractHandler() {

        @Override
        public void handle(String target, Request request, HttpServletRequest httpRequest, HttpServletResponse httpResponse) throws IOException, ServletException {
            try {
                request.setHandled(true);
                String contentLength = request.getHeader("Content-Length");
                if (contentLength != null) {
                    int length = Integer.parseInt(contentLength);
                    ServletInputStream input = httpRequest.getInputStream();
                    ServletOutputStream output = httpResponse.getOutputStream();
                    byte[] buffer = new byte[32 * 1024];
                    while (length > 0) {
                        int read = input.read(buffer);
                        if (read < 0)
                            throw new EOFException();
                        length -= read;
                        if (target.startsWith("/echo"))
                            output.write(buffer, 0, read);
                    }
                }
            } catch (IOException x) {
                if (!(target.endsWith("suppress_exception")))
                    throw x;
            }
        }
    });
    server.start();
    serverPort = connector.getLocalPort();
    sslContext = sslContextFactory.getSslContext();
    proxy = new SimpleProxy(threadPool, "localhost", serverPort);
    proxy.start();
    logger.info("proxy:{} <==> server:{}", proxy.getPort(), serverPort);
}
Also used : ManagedSelector(org.eclipse.jetty.io.ManagedSelector) ServerConnector(org.eclipse.jetty.server.ServerConnector) Connector(org.eclipse.jetty.server.Connector) SocketChannel(java.nio.channels.SocketChannel) Server(org.eclipse.jetty.server.Server) HttpConnection(org.eclipse.jetty.server.HttpConnection) ChannelEndPoint(org.eclipse.jetty.io.ChannelEndPoint) ServletOutputStream(javax.servlet.ServletOutputStream) SSLEngine(javax.net.ssl.SSLEngine) EndPoint(org.eclipse.jetty.io.EndPoint) ChannelEndPoint(org.eclipse.jetty.io.ChannelEndPoint) SslConnectionFactory(org.eclipse.jetty.server.SslConnectionFactory) AbstractHandler(org.eclipse.jetty.server.handler.AbstractHandler) ServerConnector(org.eclipse.jetty.server.ServerConnector) HttpServletRequest(javax.servlet.http.HttpServletRequest) ServletException(javax.servlet.ServletException) SslContextFactory(org.eclipse.jetty.util.ssl.SslContextFactory) ServletInputStream(javax.servlet.ServletInputStream) EOFException(java.io.EOFException) HttpParser(org.eclipse.jetty.http.HttpParser) SelectionKey(java.nio.channels.SelectionKey) SecureRequestCustomizer(org.eclipse.jetty.server.SecureRequestCustomizer) HttpConnectionFactory(org.eclipse.jetty.server.HttpConnectionFactory) Request(org.eclipse.jetty.server.Request) HttpServletRequest(javax.servlet.http.HttpServletRequest) HttpServletResponse(javax.servlet.http.HttpServletResponse) IOException(java.io.IOException) ByteBuffer(java.nio.ByteBuffer) HttpCompliance(org.eclipse.jetty.http.HttpCompliance) SslConnection(org.eclipse.jetty.io.ssl.SslConnection) File(java.io.File) Before(org.junit.Before)

Example 3 with ChannelEndPoint

use of org.eclipse.jetty.io.ChannelEndPoint in project jetty.project by eclipse.

the class ThreadStarvationTest method testFailureStarvation.

@Test
public void testFailureStarvation() throws Exception {
    try (StacklessLogging stackless = new StacklessLogging(HttpChannel.class)) {
        int acceptors = 0;
        int selectors = 1;
        int maxThreads = 10;
        final int barried = maxThreads - acceptors - selectors * 2;
        final CyclicBarrier barrier = new CyclicBarrier(barried);
        QueuedThreadPool threadPool = new QueuedThreadPool(maxThreads, maxThreads);
        threadPool.setDetailedDump(true);
        _server = new Server(threadPool);
        ServerConnector connector = new ServerConnector(_server, acceptors, selectors) {

            @Override
            protected ChannelEndPoint newEndPoint(SocketChannel channel, ManagedSelector selectSet, SelectionKey key) throws IOException {
                return new SocketChannelEndPoint(channel, selectSet, key, getScheduler()) {

                    @Override
                    public boolean flush(ByteBuffer... buffers) throws IOException {
                        super.flush(buffers[0]);
                        throw new IOException("TEST FAILURE");
                    }
                };
            }
        };
        connector.setIdleTimeout(Long.MAX_VALUE);
        _server.addConnector(connector);
        final AtomicInteger count = new AtomicInteger(0);
        _server.setHandler(new AbstractHandler() {

            @Override
            public void handle(String target, Request baseRequest, HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException {
                int c = count.getAndIncrement();
                try {
                    if (c < barried) {
                        barrier.await(10, TimeUnit.SECONDS);
                    }
                } catch (InterruptedException | BrokenBarrierException | TimeoutException e) {
                    throw new ServletException(e);
                }
                baseRequest.setHandled(true);
                response.setStatus(200);
                response.setContentLength(13);
                response.getWriter().print("Hello World!\n");
                response.getWriter().flush();
            }
        });
        _server.start();
        List<Socket> sockets = new ArrayList<>();
        for (int i = 0; i < maxThreads * 2; ++i) {
            Socket socket = new Socket("localhost", connector.getLocalPort());
            sockets.add(socket);
            OutputStream output = socket.getOutputStream();
            String request = "" + "GET / HTTP/1.1\r\n" + "Host: localhost\r\n" + //                    "Connection: close\r\n" +
            "\r\n";
            output.write(request.getBytes(StandardCharsets.UTF_8));
            output.flush();
        }
        byte[] buffer = new byte[48 * 1024];
        List<Exchanger<Integer>> totals = new ArrayList<>();
        for (Socket socket : sockets) {
            final Exchanger<Integer> x = new Exchanger<>();
            totals.add(x);
            final InputStream input = socket.getInputStream();
            new Thread() {

                @Override
                public void run() {
                    int read = 0;
                    try {
                        // look for CRLFCRLF
                        StringBuilder header = new StringBuilder();
                        int state = 0;
                        while (state < 4 && header.length() < 2048) {
                            int ch = input.read();
                            if (ch < 0)
                                break;
                            header.append((char) ch);
                            switch(state) {
                                case 0:
                                    if (ch == '\r')
                                        state = 1;
                                    break;
                                case 1:
                                    if (ch == '\n')
                                        state = 2;
                                    else
                                        state = 0;
                                    break;
                                case 2:
                                    if (ch == '\r')
                                        state = 3;
                                    else
                                        state = 0;
                                    break;
                                case 3:
                                    if (ch == '\n')
                                        state = 4;
                                    else
                                        state = 0;
                                    break;
                            }
                        }
                        read = input.read(buffer);
                    } catch (IOException e) {
                    // e.printStackTrace();
                    } finally {
                        try {
                            x.exchange(read);
                        } catch (InterruptedException e) {
                            e.printStackTrace();
                        }
                    }
                }
            }.start();
        }
        for (Exchanger<Integer> x : totals) {
            Integer read = x.exchange(-1, 10, TimeUnit.SECONDS);
            Assert.assertEquals(-1, read.intValue());
        }
        // We could read everything, good.
        for (Socket socket : sockets) socket.close();
        _server.stop();
    }
}
Also used : ManagedSelector(org.eclipse.jetty.io.ManagedSelector) SocketChannel(java.nio.channels.SocketChannel) Server(org.eclipse.jetty.server.Server) Exchanger(java.util.concurrent.Exchanger) OutputStream(java.io.OutputStream) ArrayList(java.util.ArrayList) AbstractHandler(org.eclipse.jetty.server.handler.AbstractHandler) ServerConnector(org.eclipse.jetty.server.ServerConnector) HttpServletRequest(javax.servlet.http.HttpServletRequest) ServletException(javax.servlet.ServletException) QueuedThreadPool(org.eclipse.jetty.util.thread.QueuedThreadPool) SelectionKey(java.nio.channels.SelectionKey) InputStream(java.io.InputStream) Request(org.eclipse.jetty.server.Request) HttpServletRequest(javax.servlet.http.HttpServletRequest) HttpServletResponse(javax.servlet.http.HttpServletResponse) IOException(java.io.IOException) ByteBuffer(java.nio.ByteBuffer) ChannelEndPoint(org.eclipse.jetty.io.ChannelEndPoint) SocketChannelEndPoint(org.eclipse.jetty.io.SocketChannelEndPoint) CyclicBarrier(java.util.concurrent.CyclicBarrier) AtomicInteger(java.util.concurrent.atomic.AtomicInteger) AtomicInteger(java.util.concurrent.atomic.AtomicInteger) StacklessLogging(org.eclipse.jetty.util.log.StacklessLogging) SocketChannelEndPoint(org.eclipse.jetty.io.SocketChannelEndPoint) Socket(java.net.Socket) Test(org.junit.Test)

Aggregations

IOException (java.io.IOException)3 SelectionKey (java.nio.channels.SelectionKey)3 SocketChannel (java.nio.channels.SocketChannel)3 ChannelEndPoint (org.eclipse.jetty.io.ChannelEndPoint)3 ManagedSelector (org.eclipse.jetty.io.ManagedSelector)3 Server (org.eclipse.jetty.server.Server)3 ServerConnector (org.eclipse.jetty.server.ServerConnector)3 File (java.io.File)2 InputStream (java.io.InputStream)2 OutputStream (java.io.OutputStream)2 Socket (java.net.Socket)2 ByteBuffer (java.nio.ByteBuffer)2 ArrayList (java.util.ArrayList)2 Exchanger (java.util.concurrent.Exchanger)2 ServletException (javax.servlet.ServletException)2 HttpServletRequest (javax.servlet.http.HttpServletRequest)2 HttpServletResponse (javax.servlet.http.HttpServletResponse)2 SocketChannelEndPoint (org.eclipse.jetty.io.SocketChannelEndPoint)2 Request (org.eclipse.jetty.server.Request)2 AbstractHandler (org.eclipse.jetty.server.handler.AbstractHandler)2