in java/fury-core/src/main/java/org/apache/fury/builder/ObjectCodecBuilder.java [684:768]
private List<Expression> deserializeCompressedPrimitives(
Expression bean, Expression buffer, List<List<Descriptor>> primitiveGroups) {
List<Expression> expressions = new ArrayList<>();
int numPrimitiveFields = getNumPrimitiveFields(primitiveGroups);
for (List<Descriptor> group : primitiveGroups) {
// After this check, following read can be totally unsafe without checks.
// checkReadableBytes first, `fillBuffer` may create a new heap buffer.
ReplaceStub checkReadableBytesStub = new ReplaceStub();
expressions.add(checkReadableBytesStub);
Expression heapBuffer =
new Invoke(buffer, "getHeapMemory", "heapBuffer", PRIMITIVE_BYTE_ARRAY_TYPE);
expressions.add(heapBuffer);
ListExpression groupExpressions = new ListExpression();
Expression readerAddr =
new Invoke(buffer, "getUnsafeReaderAddress", "readerAddr", PRIMITIVE_LONG_TYPE);
int acc = 0;
boolean compressStarted = false;
for (Descriptor descriptor : group) {
TypeRef<?> type = descriptor.getTypeRef();
Class<?> clz = getRawType(type);
Preconditions.checkArgument(isPrimitive(clz));
Expression fieldValue;
if (clz == byte.class) {
fieldValue = unsafeGet(heapBuffer, getReaderAddress(readerAddr, acc));
acc += 1;
} else if (clz == boolean.class) {
fieldValue = unsafeGetBoolean(heapBuffer, getReaderAddress(readerAddr, acc));
acc += 1;
} else if (clz == char.class) {
fieldValue = unsafeGetChar(heapBuffer, getReaderAddress(readerAddr, acc));
acc += 2;
} else if (clz == short.class) {
fieldValue = unsafeGetShort(heapBuffer, getReaderAddress(readerAddr, acc));
acc += 2;
} else if (clz == float.class) {
fieldValue = unsafeGetFloat(heapBuffer, getReaderAddress(readerAddr, acc));
acc += 4;
} else if (clz == double.class) {
fieldValue = unsafeGetDouble(heapBuffer, getReaderAddress(readerAddr, acc));
acc += 8;
} else if (clz == int.class) {
if (!fury.compressInt()) {
fieldValue = unsafeGetInt(heapBuffer, getReaderAddress(readerAddr, acc));
acc += 4;
} else {
if (!compressStarted) {
compressStarted = true;
addIncReaderIndexExpr(groupExpressions, buffer, acc);
}
fieldValue = readVarInt32(buffer);
}
} else if (clz == long.class) {
if (!fury.compressLong()) {
fieldValue = unsafeGetLong(heapBuffer, getReaderAddress(readerAddr, acc));
acc += 8;
} else {
if (!compressStarted) {
compressStarted = true;
addIncReaderIndexExpr(groupExpressions, buffer, acc);
}
fieldValue = LongSerializer.readInt64(buffer, fury.longEncoding());
}
} else {
throw new IllegalStateException("impossible");
}
// `bean` will be replaced by `Reference` to cut-off expr dependency.
groupExpressions.add(setFieldValue(bean, descriptor, fieldValue));
}
if (acc != 0) {
checkReadableBytesStub.setTargetObject(
new Invoke(buffer, "checkReadableBytes", Literal.ofInt(acc)));
}
if (!compressStarted) {
addIncReaderIndexExpr(groupExpressions, buffer, acc);
}
if (numPrimitiveFields < 4 || isRecord) {
expressions.add(groupExpressions);
} else {
expressions.add(
objectCodecOptimizer.invokeGenerated(
ofHashSet(bean, buffer, heapBuffer), groupExpressions, "readFields"));
}
}
return expressions;
}