|
|
@@ -0,0 +1,73 @@
|
|
|
+ ; Copyright (C) 2019 Intel Corporation. All rights reserved.
|
|
|
+ ; SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
|
|
|
+
|
|
|
+ AREA |.text|, CODE, READONLY, ALIGN=2
|
|
|
+
|
|
|
+ EXPORT invokeNative
|
|
|
+
|
|
|
+; ------------------------ direct call path ------------------------
|
|
|
+
|
|
|
+call_func
|
|
|
+ mov x20, x30 ; save x30(lr)
|
|
|
+ blr x19
|
|
|
+ mov sp, x22 ; restore sp saved before function call
|
|
|
+
|
|
|
+return_label
|
|
|
+ mov x30, x20 ; restore x30(lr)
|
|
|
+ ldp x19, x20, [sp, #0x20]
|
|
|
+ ldp x21, x22, [sp, #0x10]
|
|
|
+ ldp x23, x24, [sp, #0x0]
|
|
|
+ add sp, sp, #0x30
|
|
|
+ ret
|
|
|
+
|
|
|
+; ------------------------ stack-args path ------------------------
|
|
|
+
|
|
|
+handle_stack
|
|
|
+ ; Reserve aligned stack space for stack arguments and copy them
|
|
|
+ mov x23, sp
|
|
|
+ bic sp, x23, #15 ; Ensure 16-byte alignment
|
|
|
+ lsl x23, x21, #3 ; x23 = nstacks * 8
|
|
|
+ add x23, x23, #15
|
|
|
+ bic x23, x23, #15
|
|
|
+ sub sp, sp, x23
|
|
|
+ mov x23, sp
|
|
|
+
|
|
|
+copy_loop
|
|
|
+ cmp x21, #0
|
|
|
+ b.eq call_func ; when done, branch back to call path
|
|
|
+ ldr x24, [x20], #8
|
|
|
+ str x24, [x23], #8
|
|
|
+ sub x21, x21, #1
|
|
|
+ b copy_loop
|
|
|
+
|
|
|
+; ------------------------ function entry ------------------------
|
|
|
+
|
|
|
+invokeNative
|
|
|
+ sub sp, sp, #0x30
|
|
|
+ stp x19, x20, [sp, #0x20] ; save the registers
|
|
|
+ stp x21, x22, [sp, #0x10]
|
|
|
+ stp x23, x24, [sp, #0x0]
|
|
|
+
|
|
|
+ mov x19, x0 ; x19 = function ptr
|
|
|
+ mov x20, x1 ; x20 = argv
|
|
|
+ mov x21, x2 ; x21 = nstacks
|
|
|
+ mov x22, sp ; save the sp before call function
|
|
|
+
|
|
|
+ ; Fill in floating-point registers
|
|
|
+ ; v0 = argv[0], v1 = argv[1], v2 = argv[2], v3 = argv[3]
|
|
|
+ ld1 {v0.2D, v1.2D, v2.2D, v3.2D}, [x20], #64
|
|
|
+ ; v4 = argv[4], v5 = argv[5], v6 = argv[6], v7 = argv[7]
|
|
|
+ ld1 {v4.2D, v5.2D, v6.2D, v7.2D}, [x20], #64
|
|
|
+
|
|
|
+ ; Fill integer registers
|
|
|
+ ldp x0, x1, [x20], #16 ; x0 = argv[8] = exec_env, x1 = argv[9]
|
|
|
+ ldp x2, x3, [x20], #16
|
|
|
+ ldp x4, x5, [x20], #16
|
|
|
+ ldp x6, x7, [x20], #16
|
|
|
+
|
|
|
+ ; Now x20 points to stack args
|
|
|
+ cmp x21, #0
|
|
|
+ b.ne handle_stack ; (backward) there are stack args
|
|
|
+ b call_func ; (backward) no stack args
|
|
|
+
|
|
|
+ END
|