/*
 *  Licensed to the Apache Software Foundation (ASF) under one or more
 *  contributor license agreements.  See the NOTICE file distributed with
 *  this work for additional information regarding copyright ownership.
 *  The ASF licenses this file to You under the Apache License, Version 2.0
 *  (the "License"); you may not use this file except in compliance with
 *  the License.  You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 *  Unless required by applicable law or agreed to in writing, software
 *  distributed under the License is distributed on an "AS IS" BASIS,
 *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 *  See the License for the specific language governing permissions and
 *  limitations under the License.
 */
package org.apache.coyote.ajp;

import java.io.IOException;
import java.nio.ByteBuffer;
import java.nio.channels.CompletionHandler;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.TimeUnit;
import java.util.concurrent.TimeoutException;

import org.apache.juli.logging.Log;
import org.apache.juli.logging.LogFactory;
import org.apache.tomcat.util.net.Nio2Channel;
import org.apache.tomcat.util.net.Nio2Endpoint;
import org.apache.tomcat.util.net.SocketStatus;
import org.apache.tomcat.util.net.SocketWrapper;

/**
 * Processes AJP requests using NIO2.
 */
public class AjpNio2Processor extends AbstractAjpProcessor<Nio2Channel> {

    private static final Log log = LogFactory.getLog(AjpNio2Processor.class);
    @Override
    protected Log getLog() {
        return log;
    }

    /**
     * The completion handler used for asynchronous write operations
     */
    protected CompletionHandler<Integer, SocketWrapper<Nio2Channel>> writeCompletionHandler;

    /**
     * Flipped flag for read buffer.
     */
    protected boolean flipped = false;

    /**
     * Write pending flag.
     */
    protected volatile boolean writePending = false;

    public AjpNio2Processor(int packetSize, Nio2Endpoint endpoint0) {
        super(packetSize, endpoint0);
        response.setOutputBuffer(new SocketOutputBuffer());
        this.writeCompletionHandler = new CompletionHandler<Integer, SocketWrapper<Nio2Channel>>() {
            @Override
            public void completed(Integer nBytes, SocketWrapper<Nio2Channel> attachment) {
                boolean notify = false;
                synchronized (writeCompletionHandler) {
                    if (nBytes.intValue() < 0) {
                        failed(new IOException(sm.getString("ajpprocessor.failedsend")), attachment);
                        return;
                    }
                    writePending = false;
                    if (!Nio2Endpoint.isInline()) {
                        notify = true;
                    }
                }
                if (notify) {
                    endpoint.processSocket(attachment, SocketStatus.OPEN_WRITE, false);
                }
            }
            @Override
            public void failed(Throwable exc, SocketWrapper<Nio2Channel> attachment) {
                attachment.setError(true);
                writePending = false;
                endpoint.processSocket(attachment, SocketStatus.DISCONNECT, true);
            }
        };
    }

    @Override
    public void recycle(boolean socketClosing) {
        super.recycle(socketClosing);
        writePending = false;
        flipped = false;
    }

    @Override
    protected void registerForEvent(boolean read, boolean write) {
        // Nothing to do here, the appropriate operations should
        // already be pending
    }

    @Override
    protected void resetTimeouts() {
        // The NIO connector uses the timeout configured on the wrapper in the
        // poller. Therefore, it needs to be reset once asycn processing has
        // finished.
        if (!getErrorState().isError() && socketWrapper != null &&
                asyncStateMachine.isAsyncDispatching()) {
            long soTimeout = endpoint.getSoTimeout();

            //reset the timeout
            if (keepAliveTimeout > 0) {
                socketWrapper.setTimeout(keepAliveTimeout);
            } else {
                socketWrapper.setTimeout(soTimeout);
            }
        }

    }


    @Override
    protected void setupSocket(SocketWrapper<Nio2Channel> socketWrapper)
            throws IOException {
        // NO-OP
    }


    @Override
    protected void setTimeout(SocketWrapper<Nio2Channel> socketWrapper,
            int timeout) throws IOException {
        socketWrapper.setTimeout(timeout);
    }


    @Override
    protected int output(byte[] src, int offset, int length, boolean block)
            throws IOException {

        if (socketWrapper == null || socketWrapper.getSocket() == null)
            return -1;

        ByteBuffer writeBuffer =
                socketWrapper.getSocket().getBufHandler().getWriteBuffer();
        int toWrite = Math.min(length, writeBuffer.capacity());

        int result = 0;
        if (block) {
            writeBuffer.clear();
            writeBuffer.put(src, offset, toWrite);
            writeBuffer.flip();
            try {
                result = socketWrapper.getSocket().write(writeBuffer)
                        .get(socketWrapper.getTimeout(), TimeUnit.MILLISECONDS).intValue();
            } catch (InterruptedException | ExecutionException
                    | TimeoutException e) {
                throw new IOException(sm.getString("ajpprocessor.failedsend"), e);
            }
        } else {
            synchronized (writeCompletionHandler) {
                if (!writePending) {
                    writeBuffer.clear();
                    writeBuffer.put(src, offset, toWrite);
                    writeBuffer.flip();
                    writePending = true;
                    Nio2Endpoint.startInline();
                    socketWrapper.getSocket().write(writeBuffer, socketWrapper.getTimeout(),
                            TimeUnit.MILLISECONDS, socketWrapper, writeCompletionHandler);
                    Nio2Endpoint.endInline();
                    result = toWrite;
                }
            }
        }
        return result;
    }


    @Override
    protected boolean read(byte[] buf, int pos, int n, boolean blockFirstRead)
        throws IOException {

        int read = 0;
        int res = 0;
        boolean block = blockFirstRead;

        while (read < n) {
            res = readSocket(buf, read + pos, n - read, block);
            if (res > 0) {
                read += res;
            } else if (res == 0 && !block) {
                return false;
            } else {
                throw new IOException(sm.getString("ajpprocessor.failedread"));
            }
            block = true;
        }
        return true;
    }


    private int readSocket(byte[] buf, int pos, int n, boolean block)
            throws IOException {
        int nRead = 0;
        ByteBuffer readBuffer =
                socketWrapper.getSocket().getBufHandler().getReadBuffer();

        if (block) {
            if (!flipped) {
                readBuffer.flip();
                flipped = true;
            }
            if (readBuffer.remaining() > 0) {
                nRead = Math.min(n, readBuffer.remaining());
                readBuffer.get(buf, pos, nRead);
                if (readBuffer.remaining() == 0) {
                    readBuffer.clear();
                    flipped = false;
                }
            } else {
                readBuffer.clear();
                flipped = false;
                if (n < readBuffer.capacity()) {
                    readBuffer.limit(n);
                }
                try {
                    nRead = socketWrapper.getSocket().read(readBuffer)
                            .get(socketWrapper.getTimeout(), TimeUnit.MILLISECONDS).intValue();
                } catch (InterruptedException | ExecutionException
                        | TimeoutException e) {
                    throw new IOException(sm.getString("ajpprocessor.failedread"), e);
                }
                if (nRead > 0) {
                    if (!flipped) {
                        readBuffer.flip();
                        flipped = true;
                    }
                    nRead = Math.min(n, readBuffer.remaining());
                    readBuffer.get(buf, pos, nRead);
                    if (readBuffer.remaining() == 0) {
                        readBuffer.clear();
                        flipped = false;
                    }
                }
            }
        } else {
            if (!flipped) {
                readBuffer.flip();
                flipped = true;
            }
            if (readBuffer.remaining() > 0) {
                nRead = Math.min(n, readBuffer.remaining());
                readBuffer.get(buf, pos, nRead);
                if (readBuffer.remaining() == 0) {
                    readBuffer.clear();
                    flipped = false;
                }
            } else {
                readBuffer.clear();
                flipped = false;
                readBuffer.limit(n);
            }
        }
        return nRead;
    }
}
