Search in sources :

Example 1 with H2ConnectionException

use of org.apache.hc.core5.http2.H2ConnectionException in project httpcomponents-core by apache.

the class AbstractH2StreamMultiplexer method applyLocalSettings.

private void applyLocalSettings() throws H2ConnectionException {
    hPackDecoder.setMaxTableSize(localConfig.getHeaderTableSize());
    hPackDecoder.setMaxListSize(localConfig.getMaxHeaderListSize());
    final int delta = localConfig.getInitialWindowSize() - initInputWinSize;
    initInputWinSize = localConfig.getInitialWindowSize();
    if (delta != 0 && !streamMap.isEmpty()) {
        for (final Iterator<Map.Entry<Integer, H2Stream>> it = streamMap.entrySet().iterator(); it.hasNext(); ) {
            final Map.Entry<Integer, H2Stream> entry = it.next();
            final H2Stream stream = entry.getValue();
            try {
                updateInputWindow(stream.getId(), stream.getInputWindow(), delta);
            } catch (final ArithmeticException ex) {
                throw new H2ConnectionException(H2Error.FLOW_CONTROL_ERROR, ex.getMessage());
            }
        }
    }
    lowMark = initInputWinSize / 2;
}
Also used : AtomicInteger(java.util.concurrent.atomic.AtomicInteger) H2ConnectionException(org.apache.hc.core5.http2.H2ConnectionException) Map(java.util.Map) ConcurrentHashMap(java.util.concurrent.ConcurrentHashMap)

Example 2 with H2ConnectionException

use of org.apache.hc.core5.http2.H2ConnectionException in project httpcomponents-core by apache.

the class ClientH2StreamMultiplexer method createLocallyInitiatedStream.

@Override
H2StreamHandler createLocallyInitiatedStream(final ExecutableCommand command, final H2StreamChannel channel, final HttpProcessor httpProcessor, final BasicHttpConnectionMetrics connMetrics) throws IOException {
    if (command instanceof RequestExecutionCommand) {
        final RequestExecutionCommand executionCommand = (RequestExecutionCommand) command;
        final AsyncClientExchangeHandler exchangeHandler = executionCommand.getExchangeHandler();
        final HandlerFactory<AsyncPushConsumer> pushHandlerFactory = executionCommand.getPushHandlerFactory();
        final HttpCoreContext context = HttpCoreContext.adapt(executionCommand.getContext());
        context.setAttribute(HttpCoreContext.SSL_SESSION, getSSLSession());
        context.setAttribute(HttpCoreContext.CONNECTION_ENDPOINT, getEndpointDetails());
        return new ClientH2StreamHandler(channel, httpProcessor, connMetrics, exchangeHandler, pushHandlerFactory != null ? pushHandlerFactory : this.pushHandlerFactory, context);
    }
    throw new H2ConnectionException(H2Error.INTERNAL_ERROR, "Unexpected executable command");
}
Also used : AsyncPushConsumer(org.apache.hc.core5.http.nio.AsyncPushConsumer) AsyncClientExchangeHandler(org.apache.hc.core5.http.nio.AsyncClientExchangeHandler) HttpCoreContext(org.apache.hc.core5.http.protocol.HttpCoreContext) H2ConnectionException(org.apache.hc.core5.http2.H2ConnectionException) RequestExecutionCommand(org.apache.hc.core5.http.nio.command.RequestExecutionCommand)

Example 3 with H2ConnectionException

use of org.apache.hc.core5.http2.H2ConnectionException in project httpcomponents-core by apache.

the class FrameInputBuffer method read.

/**
 * Attempts to read a complete frame from the given source buffer and the underlying data
 * channel. The source buffer is consumed first. More data can be read from the channel
 * if required.
 *
 * @param src the source buffer or {@code null} if not available.
 * @param channel the underlying data channel.
 *
 * @return a complete frame or {@code null} a complete frame cannot be read.
 *
 * @since 5.1
 */
public RawFrame read(final ByteBuffer src, final ReadableByteChannel channel) throws IOException {
    for (; ; ) {
        if (src != null) {
            if (buffer.hasRemaining()) {
                buffer.compact();
            } else {
                buffer.clear();
            }
            final int remaining = buffer.remaining();
            if (remaining >= src.remaining()) {
                buffer.put(src);
            } else {
                final int limit = src.limit();
                src.limit(remaining);
                buffer.put(src);
                src.limit(limit);
            }
            buffer.flip();
        }
        switch(state) {
            case HEAD_EXPECTED:
                if (buffer.remaining() >= FrameConsts.HEAD_LEN) {
                    final int lengthAndType = buffer.getInt();
                    payloadLen = lengthAndType >> 8;
                    if (payloadLen > maxFramePayloadSize) {
                        throw new H2ConnectionException(H2Error.FRAME_SIZE_ERROR, "Frame size exceeds maximum");
                    }
                    type = lengthAndType & 0xff;
                    flags = buffer.get();
                    streamId = Math.abs(buffer.getInt());
                    state = State.PAYLOAD_EXPECTED;
                } else {
                    break;
                }
            case PAYLOAD_EXPECTED:
                if (buffer.remaining() >= payloadLen) {
                    if ((flags & FrameFlag.PADDED.getValue()) > 0) {
                        if (payloadLen == 0) {
                            throw new H2ConnectionException(H2Error.PROTOCOL_ERROR, "Inconsistent padding");
                        }
                        buffer.mark();
                        final int padding = buffer.get();
                        if (payloadLen < padding + 1) {
                            throw new H2ConnectionException(H2Error.PROTOCOL_ERROR, "Inconsistent padding");
                        }
                        buffer.reset();
                    }
                    final ByteBuffer payload = payloadLen > 0 ? ByteBuffer.wrap(bytes, buffer.position(), payloadLen) : null;
                    buffer.position(buffer.position() + payloadLen);
                    state = State.HEAD_EXPECTED;
                    metrics.incrementFramesTransferred();
                    return new RawFrame(type, flags, streamId, payload);
                }
        }
        if (buffer.hasRemaining()) {
            buffer.compact();
        } else {
            buffer.clear();
        }
        final int bytesRead = channel.read(buffer);
        buffer.flip();
        if (bytesRead > 0) {
            metrics.incrementBytesTransferred(bytesRead);
        }
        if (bytesRead == 0) {
            break;
        } else if (bytesRead < 0) {
            if (state != State.HEAD_EXPECTED || buffer.hasRemaining()) {
                throw new H2CorruptFrameException("Corrupt or incomplete HTTP2 frame");
            } else {
                throw new ConnectionClosedException();
            }
        }
    }
    return null;
}
Also used : H2CorruptFrameException(org.apache.hc.core5.http2.H2CorruptFrameException) H2ConnectionException(org.apache.hc.core5.http2.H2ConnectionException) RawFrame(org.apache.hc.core5.http2.frame.RawFrame) ConnectionClosedException(org.apache.hc.core5.http.ConnectionClosedException) ByteBuffer(java.nio.ByteBuffer)

Example 4 with H2ConnectionException

use of org.apache.hc.core5.http2.H2ConnectionException in project httpcomponents-core by apache.

the class AbstractH2StreamMultiplexer method consumeSettingsFrame.

private void consumeSettingsFrame(final ByteBuffer payload) throws HttpException, IOException {
    final H2Config.Builder configBuilder = H2Config.initial();
    while (payload.hasRemaining()) {
        final int code = payload.getShort();
        final int value = payload.getInt();
        final H2Param param = H2Param.valueOf(code);
        if (param != null) {
            switch(param) {
                case HEADER_TABLE_SIZE:
                    try {
                        configBuilder.setHeaderTableSize(value);
                    } catch (final IllegalArgumentException ex) {
                        throw new H2ConnectionException(H2Error.PROTOCOL_ERROR, ex.getMessage());
                    }
                    break;
                case MAX_CONCURRENT_STREAMS:
                    try {
                        configBuilder.setMaxConcurrentStreams(value);
                    } catch (final IllegalArgumentException ex) {
                        throw new H2ConnectionException(H2Error.PROTOCOL_ERROR, ex.getMessage());
                    }
                    break;
                case ENABLE_PUSH:
                    configBuilder.setPushEnabled(value == 1);
                    break;
                case INITIAL_WINDOW_SIZE:
                    try {
                        configBuilder.setInitialWindowSize(value);
                    } catch (final IllegalArgumentException ex) {
                        throw new H2ConnectionException(H2Error.PROTOCOL_ERROR, ex.getMessage());
                    }
                    break;
                case MAX_FRAME_SIZE:
                    try {
                        configBuilder.setMaxFrameSize(value);
                    } catch (final IllegalArgumentException ex) {
                        throw new H2ConnectionException(H2Error.PROTOCOL_ERROR, ex.getMessage());
                    }
                    break;
                case MAX_HEADER_LIST_SIZE:
                    try {
                        configBuilder.setMaxHeaderListSize(value);
                    } catch (final IllegalArgumentException ex) {
                        throw new H2ConnectionException(H2Error.PROTOCOL_ERROR, ex.getMessage());
                    }
                    break;
            }
        }
    }
    applyRemoteSettings(configBuilder.build());
}
Also used : H2ConnectionException(org.apache.hc.core5.http2.H2ConnectionException) H2Param(org.apache.hc.core5.http2.config.H2Param) H2Config(org.apache.hc.core5.http2.config.H2Config)

Example 5 with H2ConnectionException

use of org.apache.hc.core5.http2.H2ConnectionException in project httpcomponents-core by apache.

the class AbstractH2StreamMultiplexer method commitPushPromise.

private void commitPushPromise(final int streamId, final int promisedStreamId, final List<Header> headers) throws IOException {
    if (headers == null || headers.isEmpty()) {
        throw new H2ConnectionException(H2Error.INTERNAL_ERROR, "Message headers are missing");
    }
    if (streamListener != null) {
        streamListener.onHeaderOutput(this, streamId, headers);
    }
    final ByteArrayBuffer buf = new ByteArrayBuffer(512);
    buf.append((byte) (promisedStreamId >> 24));
    buf.append((byte) (promisedStreamId >> 16));
    buf.append((byte) (promisedStreamId >> 8));
    buf.append((byte) (promisedStreamId));
    hPackEncoder.encodeHeaders(buf, headers, localConfig.isCompressionEnabled());
    int off = 0;
    int remaining = buf.length();
    boolean continuation = false;
    while (remaining > 0) {
        final int chunk = Math.min(remoteConfig.getMaxFrameSize(), remaining);
        final ByteBuffer payload = ByteBuffer.wrap(buf.array(), off, chunk);
        remaining -= chunk;
        off += chunk;
        final boolean endHeaders = remaining == 0;
        final RawFrame frame;
        if (!continuation) {
            frame = frameFactory.createPushPromise(streamId, payload, endHeaders);
            continuation = true;
        } else {
            frame = frameFactory.createContinuation(streamId, payload, endHeaders);
        }
        commitFrameInternal(frame);
    }
}
Also used : H2ConnectionException(org.apache.hc.core5.http2.H2ConnectionException) RawFrame(org.apache.hc.core5.http2.frame.RawFrame) ByteBuffer(java.nio.ByteBuffer) ByteArrayBuffer(org.apache.hc.core5.util.ByteArrayBuffer)

Aggregations

H2ConnectionException (org.apache.hc.core5.http2.H2ConnectionException)12 ByteBuffer (java.nio.ByteBuffer)5 RawFrame (org.apache.hc.core5.http2.frame.RawFrame)5 Map (java.util.Map)4 ConcurrentHashMap (java.util.concurrent.ConcurrentHashMap)4 AtomicInteger (java.util.concurrent.atomic.AtomicInteger)4 ConnectionClosedException (org.apache.hc.core5.http.ConnectionClosedException)2 ProtocolException (org.apache.hc.core5.http.ProtocolException)2 H2StreamResetException (org.apache.hc.core5.http2.H2StreamResetException)2 AsyncPingHandler (org.apache.hc.core5.http2.nio.AsyncPingHandler)2 IOException (java.io.IOException)1 Iterator (java.util.Iterator)1 Header (org.apache.hc.core5.http.Header)1 HttpException (org.apache.hc.core5.http.HttpException)1 HttpStreamResetException (org.apache.hc.core5.http.HttpStreamResetException)1 AsyncClientExchangeHandler (org.apache.hc.core5.http.nio.AsyncClientExchangeHandler)1 AsyncPushConsumer (org.apache.hc.core5.http.nio.AsyncPushConsumer)1 ExecutableCommand (org.apache.hc.core5.http.nio.command.ExecutableCommand)1 RequestExecutionCommand (org.apache.hc.core5.http.nio.command.RequestExecutionCommand)1 ShutdownCommand (org.apache.hc.core5.http.nio.command.ShutdownCommand)1