in protonj2/src/main/java/org/apache/qpid/protonj2/engine/impl/ProtonFrameDecodingHandler.java [341:397]
public void parse(EngineHandlerContext context, ProtonBuffer input) {
int dataOffset = (input.readByte() << 2) & 0x3FF;
int frameSize = length + FRAME_SIZE_BYTES;
validateDataOffset(dataOffset, frameSize);
int type = input.readByte() & 0xFF;
short channel = input.readShort();
// Skip over the extended header if present (i.e offset > 8)
if (dataOffset != 8) {
input.advanceReadOffset(dataOffset - 8);
}
final int frameBodySize = frameSize - dataOffset;
ProtonBuffer payload = null;
Object val = null;
if (frameBodySize > 0) {
int startReadIndex = input.getReadOffset();
val = decoder.readObject(input, decoderState);
// Copy the payload portion of the incoming bytes for now as the incoming may be
// from a wrapped pooled buffer and for now we have no way of retaining or otherwise
// ensuring that the buffer remains ours. Since we might want to store received
// data at a client level and decode later we could end up losing the data to reuse
// if it was pooled.
if (input.isReadable()) {
int payloadSize = frameBodySize - (input.getReadOffset() - startReadIndex);
if (payloadSize > 0) {
// Payload is now only a view of the bytes from the input that comprise it.
payload = input.copy(input.getReadOffset(), payloadSize, true);
input.advanceReadOffset(payloadSize);
}
}
} else {
transitionToFrameSizeParsingStage();
context.fireRead(EmptyEnvelope.INSTANCE);
return;
}
if (type == AMQP_FRAME_TYPE) {
Performative performative = (Performative) val;
IncomingAMQPEnvelope frame = framePool.take(performative, channel, payload);
transitionToFrameSizeParsingStage();
context.fireRead(frame);
} else if (type == SASL_FRAME_TYPE) {
SaslPerformative performative = (SaslPerformative) val;
SASLEnvelope saslFrame = new SASLEnvelope(performative);
transitionToFrameSizeParsingStage();
// Ensure we process transition from SASL to AMQP header state
handleRead(context, saslFrame);
} else {
throw new FrameDecodingException(String.format("unknown frame type: %d", type));
}
}