RFR: 8313406: nep_invoker_blob can be simplified more
Jorn Vernee
jvernee at openjdk.org
Wed Aug 2 14:23:56 UTC 2023
On Wed, 2 Aug 2023 12:35:50 GMT, Yasumasa Suenaga <ysuenaga at openjdk.org> wrote:
> I guess you suggested that ArgumentShuffle in HotSpot moves into DowncallLinker, right?
No, ArgumentShuffle should stay inside HotSpot. We can not do all the shuffling on the Java side. We can only eliminate some of the register moves that are needed by re-ordering the arguments on the Java side.
For instance, if you look at the comment in `assembler_x86.hpp`, where we define `j_rarg*` Register constants, you'll see this:
// |-------------------------------------------------------|
// | c_rarg0 c_rarg1 c_rarg2 c_rarg3 c_rarg4 c_rarg5 |
// |-------------------------------------------------------|
// | rcx rdx r8 r9 rdi* rsi* | windows (* not a c_rarg)
// | rdi rsi rdx rcx r8 r9 | solaris/linux
// |-------------------------------------------------------|
// | j_rarg5 j_rarg0 j_rarg1 j_rarg2 j_rarg3 j_rarg4 |
// |-------------------------------------------------------|
i.e. all the registers in the Java calling convention are 'off by one' compared to the native calling convention. This makes sense for JNI since we need to prepend the JNIEnv* to the start of the argument list, but it doesn't make sense for Panama.
Let's say we have a native function taking five `long`s. On Linux/x64 the VMStorage[] for the arguments (the one we use when creating the NativeEntryPoint inside DowncallLinker) would be:
[rdi, rsi, rdx, rcx, r8, r9]
i.e. the first argument we pass on the Java side gets moved (by the downcall stub) into `rdi`, the second into `rsi`, etc. This doesn't match the incoming registers of the Java calling convention, where the first argument is passed passing in `rsi`, the second is passed in `rdx`, etc. (i.e. off-by-one).
We can simply re-arrange the entries in the `VMStorage[]` to match the order of registers in the Java calling convention:
[rsi, rdx, rcx, r8, r9, rdi]
i.e. the argument that should go into `rdi` is passed in the fifth position instead. Since now the registers for each argument match the Java calling convention, the downcall stub doesn't need to do any shuffling! (I'm being very hand-wavey here. Figuring out how to correctly do the re-ordering is the hard part of this).
Ok, but now the arguments we pass to the downcall stub are going to go in the wrong registers as well :( So, to compensate for that, we have to also re-order the incoming argument values on the Java side so that each argument will correspond to it's original register again. To do that, we just need to pass the first argument in the fifth position as well, and shift arguments 1-4 forward by one spot.
Make sense?
-------------
PR Comment: https://git.openjdk.org/jdk/pull/15089#issuecomment-1662302891
More information about the hotspot-compiler-dev
mailing list