Friday, August 28, 2020

Object and array inlining

Fixed Array inlining if all objects of a parent class reference arrays with the same fixed length, then the field access for the array fields can be eliminated because their offset is known. In addition, subsequent access can also be optimized by eliminating the array bounds check. There are two additional instructions required over object field access. The first one checks the index against the length and the second one branches to an out of line code block that throws an exception. Instead of three loads - only one load is necessary with the two eliminations.

Variable array inlining: The objects of a parent class reference arrays with different but fixed lengths. The parent can have only one variable array inlining child because the inlining offset of a subsequent child cannot be known with the variable length of the first. In this case the two memory loads are necessary.

Dynamic array inlining: When an array field is assigned multiple times, one more check needs to be included for the field access because it is not safe to eliminate it. However, unlike object field, it is possible to detect if an array field has been changed at runtime.

The above section describes the types of array inlining for a single array and it is also possible to inline the parent array when one is nested within the other. The parent contains references to children arrays but when inlined the access to the child element is at an offset at start + zero-based-index x size + offset –of-field because the children are contiguous.

The array access bytecodes require a global data flow. The bytecodes are executed using an operand stack. Only constants are used with bytecodes which includes numbers of local variables, numeric constants and even field names. The bytecodes for loading and storing fields include a symbolic reference to the accessed field and the containing class This helps to determine which fields of the classes are changed at runtime.

The bytecodes that load and store elements of reference arrays have no static operands which makes it difficult to know whether elements of modified array have been inlined or not. If a field is modified after it has been initialized, the object inlining system knows that the field is not inlineable. The putField bytecode contains the type which determines which objects are being modified. The aastore bytecode is not typed therefore the same bytecodes are emitted for methods that contain typed and non-typed array parameters which prohibits the inlining of array elements. 

Only a global data flow analysis can determine all the contexts in which the methods are called and then determining whether the type in the parameter is the same as the candidate for inlining. Reflection and lazy loading might complicate this but the majority of the usages is suitable to global data flow. Special cases of arrays as inlining parents could be handled without a global analysis.


No comments:

Post a Comment