class HttpParser {

    public boolean parseNext(ByteBuffer buffer) {
        if (DEBUG)
            LOG.debug("parseNext s={} {}", state, BufferUtils.toDetailString(buffer));
        try {
            // Start a request/response
            if (state == State.START) {
                version = null;
                method = null;
                methodString = null;
                endOfContent = EndOfContent.UNKNOWN_CONTENT;
                header = null;
                if (quickStart(buffer))
                    return true;
            }

            // Request/response line
            if (state.ordinal() >= State.START.ordinal() && state.ordinal() < State.HEADER.ordinal()) {
                if (parseLine(buffer))
                    return true;
            }

            // parse headers
            if (state == State.HEADER) {
                if (parseFields(buffer))
                    return true;
            }

            // parse content
            if (state.ordinal() >= State.CONTENT.ordinal() && state.ordinal() < State.TRAILER.ordinal()) {
                // Handle HEAD response
                if (responseStatus > 0 && headResponse) {
                    setState(State.END);
                    return handleContentMessage();
                } else {
                    if (parseContent(buffer))
                        return true;
                }
            }

            // parse headers
            if (state == State.TRAILER) {
                if (parseFields(buffer))
                    return true;
            }

            // handle end states
            if (state == State.END) {
                // eat white space
                while (buffer.remaining() > 0 && buffer.get(buffer.position()) <= HttpTokens.SPACE)
                    buffer.get();
            } else if (isClose() || isClosed()) {
                BufferUtils.clear(buffer);
            }

            // Handle EOF
            if (eof && !buffer.hasRemaining()) {
                switch (state) {
                    case CLOSED:
                        break;

                    case START:
                        setState(State.CLOSED);
                        handler.earlyEOF();
                        break;

                    case END:
                    case CLOSE:
                        setState(State.CLOSED);
                        break;

                    case EOF_CONTENT:
                    case TRAILER:
                        if (fieldState == FieldState.FIELD) {
                            // Be forgiving of missing last CRLF
                            setState(State.CLOSED);
                            return handleContentMessage();
                        }
                        setState(State.CLOSED);
                        handler.earlyEOF();
                        break;

                    case CONTENT:
                    case CHUNKED_CONTENT:
                    case CHUNK_SIZE:
                    case CHUNK_PARAMS:
                    case CHUNK:
                        setState(State.CLOSED);
                        handler.earlyEOF();
                        break;

                    default:
                        if (DEBUG)
                            LOG.debug("{} EOF in {}", this, state);
                        setState(State.CLOSED);
                        handler.badMessage(new BadMessageException(HttpStatus.BAD_REQUEST_400));
                        break;
                }
            }
        } catch (BadMessageException x) {
            BufferUtils.clear(buffer);
            badMessage(x);
        } catch (Throwable x) {
            BufferUtils.clear(buffer);
            badMessage(new BadMessageException(HttpStatus.BAD_REQUEST_400, requestHandler != null ? "Bad Request" : "Bad Response", x));
        }
        return false;
    }

    public  HttpParser(RequestHandler handler);
    public  HttpParser(ResponseHandler handler);
    public  HttpParser(RequestHandler handler, int maxHeaderBytes);
    public  HttpParser(ResponseHandler handler, int maxHeaderBytes);
    @Deprecated public  HttpParser(RequestHandler handler, int maxHeaderBytes, boolean strict);
    @Deprecated public  HttpParser(ResponseHandler handler, int maxHeaderBytes, boolean strict);
    public  HttpParser(RequestHandler handler, HttpCompliance compliance);
    public  HttpParser(RequestHandler handler, int maxHeaderBytes, HttpCompliance compliance);
    public  HttpParser(ResponseHandler handler, int maxHeaderBytes, HttpCompliance compliance);
    private  HttpParser(RequestHandler requestHandler, ResponseHandler responseHandler, int maxHeaderBytes, HttpCompliance compliance);

}