public int appendFragmentedMessage( final long defaultVersionFlagsType, final long defaultSessionId, final DirectBuffer srcBuffer, final int srcOffset, final int length, final int maxPayloadLength) { final int numMaxPayloads = length / maxPayloadLength; final int remainingPayload = length % maxPayloadLength; final int lastFrameLength = (remainingPayload > 0) ? align(remainingPayload + HEADER_LENGTH, FRAME_ALIGNMENT) : 0; final int requiredLength = (numMaxPayloads * (maxPayloadLength + HEADER_LENGTH)) + lastFrameLength; int termOffset = metaDataBuffer.getAndAddInt(TERM_TAIL_COUNTER_OFFSET, requiredLength); final UnsafeBuffer termBuffer = this.termBuffer; final int capacity = termBuffer.capacity(); int resultingOffset = termOffset + requiredLength; if (resultingOffset > (capacity - HEADER_LENGTH)) { resultingOffset = handleEndOfLogCondition( termBuffer, termOffset, defaultVersionFlagsType, defaultSessionId, capacity); } else { byte flags = BEGIN_FRAG_FLAG; int remaining = length; do { final int bytesToWrite = Math.min(remaining, maxPayloadLength); final int frameLength = bytesToWrite + HEADER_LENGTH; final int alignedLength = align(frameLength, FRAME_ALIGNMENT); applyDefaultHeader( termBuffer, termOffset, frameLength, defaultVersionFlagsType, defaultSessionId); termBuffer.putBytes( termOffset + HEADER_LENGTH, srcBuffer, srcOffset + (length - remaining), bytesToWrite); if (remaining <= maxPayloadLength) { flags |= END_FRAG_FLAG; } frameFlags(termBuffer, termOffset, flags); frameLengthOrdered(termBuffer, termOffset, frameLength); flags = 0; termOffset += alignedLength; remaining -= bytesToWrite; } while (remaining > 0); } return resultingOffset; }
/** * Get the current tail value in a volatile memory ordering fashion. If raw tail is greater than * term capacity then capacity will be returned. * * @return the current tail value. */ public int tailVolatile() { return Math.min(metaDataBuffer.getIntVolatile(TERM_TAIL_COUNTER_OFFSET), termBuffer.capacity()); }