diff options
| author | Mike Pall <mike> | 2011-04-16 23:28:51 +0200 |
|---|---|---|
| committer | Mike Pall <mike> | 2011-04-16 23:28:51 +0200 |
| commit | d636a3decdf8dc503e707fad8b0e2745c0cabd21 (patch) | |
| tree | d23c1122b288819eca73d2b54d1008275a7de7d6 /src | |
| parent | fc4021427964de06b6ba445172c7345a208a725d (diff) | |
| download | luajit-d636a3decdf8dc503e707fad8b0e2745c0cabd21.tar.gz luajit-d636a3decdf8dc503e707fad8b0e2745c0cabd21.tar.bz2 luajit-d636a3decdf8dc503e707fad8b0e2745c0cabd21.zip | |
ARM: Add partial support for FFI.
Diffstat (limited to 'src')
| -rw-r--r-- | src/buildvm_arm.dasc | 36 | ||||
| -rw-r--r-- | src/lj_arch.h | 2 | ||||
| -rw-r--r-- | src/lj_ccall.c | 41 | ||||
| -rw-r--r-- | src/lj_ccall.h | 12 |
4 files changed, 87 insertions, 4 deletions
diff --git a/src/buildvm_arm.dasc b/src/buildvm_arm.dasc index 3e3fb23c..c12b4da8 100644 --- a/src/buildvm_arm.dasc +++ b/src/buildvm_arm.dasc | |||
| @@ -1873,7 +1873,32 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 1873 | | | 1873 | | |
| 1874 | |->vm_ffi_call: | 1874 | |->vm_ffi_call: |
| 1875 | #if LJ_HASFFI | 1875 | #if LJ_HASFFI |
| 1876 | | NYI | 1876 | | .type CCSTATE, CCallState, r4 |
| 1877 | | push {CCSTATE, r5, r11, lr} | ||
| 1878 | | mov CCSTATE, CARG1 | ||
| 1879 | | ldr CARG1, CCSTATE:CARG1->spadj | ||
| 1880 | | ldrb CARG2, CCSTATE->nsp | ||
| 1881 | | add CARG3, CCSTATE, #offsetof(CCallState, stack) | ||
| 1882 | | mov r11, sp | ||
| 1883 | | sub sp, sp, CARG1 // Readjust stack. | ||
| 1884 | | subs CARG2, CARG2, #1 | ||
| 1885 | | ldr RB, CCSTATE->func | ||
| 1886 | | bmi >2 | ||
| 1887 | |1: // Copy stack slots. | ||
| 1888 | | ldr CARG4, [CARG3, CARG2, lsl #2] | ||
| 1889 | | str CARG4, [sp, CARG2, lsl #2] | ||
| 1890 | | subs CARG2, CARG2, #1 | ||
| 1891 | | bpl <1 | ||
| 1892 | |2: | ||
| 1893 | | ldr CARG1, CCSTATE->gpr[0] | ||
| 1894 | | ldr CARG2, CCSTATE->gpr[1] | ||
| 1895 | | ldr CARG3, CCSTATE->gpr[2] | ||
| 1896 | | ldr CARG4, CCSTATE->gpr[3] | ||
| 1897 | | blx RB | ||
| 1898 | | mov sp, r11 | ||
| 1899 | | str CRET1, CCSTATE->gpr[0] | ||
| 1900 | | str CRET2, CCSTATE->gpr[1] | ||
| 1901 | | pop {CCSTATE, r5, r11, pc} | ||
| 1877 | #endif | 1902 | #endif |
| 1878 | | | 1903 | | |
| 1879 | |//----------------------------------------------------------------------- | 1904 | |//----------------------------------------------------------------------- |
| @@ -2340,7 +2365,14 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 2340 | break; | 2365 | break; |
| 2341 | case BC_KCDATA: | 2366 | case BC_KCDATA: |
| 2342 | #if LJ_HASFFI | 2367 | #if LJ_HASFFI |
| 2343 | | NYI | 2368 | | // RA = dst*8, RC = cdata_const (~) |
| 2369 | | mvn RC, RC | ||
| 2370 | | ins_next1 | ||
| 2371 | | ldr CARG1, [KBASE, RC, lsl #2] | ||
| 2372 | | mvn CARG2, #~LJ_TCDATA | ||
| 2373 | | ins_next2 | ||
| 2374 | | strd CARG12, [BASE, RA] | ||
| 2375 | | ins_next3 | ||
| 2344 | #endif | 2376 | #endif |
| 2345 | break; | 2377 | break; |
| 2346 | case BC_KSHORT: | 2378 | case BC_KSHORT: |
diff --git a/src/lj_arch.h b/src/lj_arch.h index 5e866fe4..ca5b0df4 100644 --- a/src/lj_arch.h +++ b/src/lj_arch.h | |||
| @@ -137,7 +137,7 @@ | |||
| 137 | #define LJ_TARGET_MASKSHIFT 0 | 137 | #define LJ_TARGET_MASKSHIFT 0 |
| 138 | #define LJ_TARGET_MASKROT 1 | 138 | #define LJ_TARGET_MASKROT 1 |
| 139 | #define LJ_ARCH_DUALNUM 2 | 139 | #define LJ_ARCH_DUALNUM 2 |
| 140 | #define LJ_ARCH_NOFFI 1 | 140 | #define LJ_ARCH_NOFFI 1 /* NYI: comparisons, calls. */ |
| 141 | #define LJ_ARCH_NOJIT 1 | 141 | #define LJ_ARCH_NOJIT 1 |
| 142 | 142 | ||
| 143 | #elif LUAJIT_TARGET == LUAJIT_ARCH_PPC | 143 | #elif LUAJIT_TARGET == LUAJIT_ARCH_PPC |
diff --git a/src/lj_ccall.c b/src/lj_ccall.c index 85d8af9c..da7b4738 100644 --- a/src/lj_ccall.c +++ b/src/lj_ccall.c | |||
| @@ -164,6 +164,47 @@ | |||
| 164 | } \ | 164 | } \ |
| 165 | } | 165 | } |
| 166 | 166 | ||
| 167 | #elif LJ_TARGET_ARM | ||
| 168 | /* -- ARM calling conventions --------------------------------------------- */ | ||
| 169 | |||
| 170 | #define CCALL_HANDLE_STRUCTRET \ | ||
| 171 | /* Return structs of size <= 4 in a GPR. */ \ | ||
| 172 | cc->retref = !(sz <= 4); \ | ||
| 173 | if (cc->retref) cc->gpr[ngpr++] = (GPRArg)dp; | ||
| 174 | |||
| 175 | #define CCALL_HANDLE_COMPLEXRET \ | ||
| 176 | cc->retref = 1; /* Return all complex values by reference. */ \ | ||
| 177 | cc->gpr[ngpr++] = (GPRArg)dp; | ||
| 178 | |||
| 179 | #define CCALL_HANDLE_COMPLEXRET2 \ | ||
| 180 | UNUSED(dp); /* Nothing to do. */ | ||
| 181 | |||
| 182 | #define CCALL_HANDLE_STRUCTARG \ | ||
| 183 | /* Pass all structs by value in registers and/or on the stack. */ | ||
| 184 | |||
| 185 | #define CCALL_HANDLE_COMPLEXARG \ | ||
| 186 | /* Pass complex by value in 2 or 4 GPRs. */ | ||
| 187 | |||
| 188 | /* ARM has a softfp ABI. */ | ||
| 189 | #define CCALL_HANDLE_REGARG \ | ||
| 190 | if ((d->info & CTF_ALIGN) > CTALIGN_PTR) { \ | ||
| 191 | if (ngpr < maxgpr) \ | ||
| 192 | ngpr = (ngpr + 1u) & ~1u; /* Align to regpair. */ \ | ||
| 193 | else \ | ||
| 194 | nsp = (nsp + 1u) & ~1u; /* Align argument on stack. */ \ | ||
| 195 | } \ | ||
| 196 | if (ngpr < maxgpr) { \ | ||
| 197 | dp = &cc->gpr[ngpr]; \ | ||
| 198 | if (ngpr + n > maxgpr) { \ | ||
| 199 | nsp += ngpr + n - maxgpr; /* Assumes contiguous gpr/stack fields. */ \ | ||
| 200 | if (nsp > CCALL_MAXSTACK) goto err_nyi; /* Too many arguments. */ \ | ||
| 201 | ngpr = maxgpr; \ | ||
| 202 | } else { \ | ||
| 203 | ngpr += n; \ | ||
| 204 | } \ | ||
| 205 | goto done; \ | ||
| 206 | } | ||
| 207 | |||
| 167 | #elif LJ_TARGET_PPCSPE | 208 | #elif LJ_TARGET_PPCSPE |
| 168 | /* -- PPC/SPE calling conventions ----------------------------------------- */ | 209 | /* -- PPC/SPE calling conventions ----------------------------------------- */ |
| 169 | 210 | ||
diff --git a/src/lj_ccall.h b/src/lj_ccall.h index 83e2403d..d0979781 100644 --- a/src/lj_ccall.h +++ b/src/lj_ccall.h | |||
| @@ -47,6 +47,16 @@ typedef LJ_ALIGN(16) union FPRArg { | |||
| 47 | 47 | ||
| 48 | typedef intptr_t GPRArg; | 48 | typedef intptr_t GPRArg; |
| 49 | 49 | ||
| 50 | #elif LJ_TARGET_ARM | ||
| 51 | |||
| 52 | #define CCALL_NARG_GPR 4 | ||
| 53 | #define CCALL_NARG_FPR 0 | ||
| 54 | #define CCALL_NRET_GPR 2 /* For softfp double. */ | ||
| 55 | #define CCALL_NRET_FPR 0 | ||
| 56 | #define CCALL_SPS_FREE 0 /* NYI */ | ||
| 57 | |||
| 58 | typedef intptr_t GPRArg; | ||
| 59 | |||
| 50 | #elif LJ_TARGET_PPCSPE | 60 | #elif LJ_TARGET_PPCSPE |
| 51 | 61 | ||
| 52 | #define CCALL_NARG_GPR 8 | 62 | #define CCALL_NARG_GPR 8 |
| @@ -91,10 +101,10 @@ typedef struct CCallState { | |||
| 91 | #elif LJ_TARGET_X86 | 101 | #elif LJ_TARGET_X86 |
| 92 | uint8_t resx87; /* Result on x87 stack: 1:float, 2:double. */ | 102 | uint8_t resx87; /* Result on x87 stack: 1:float, 2:double. */ |
| 93 | #endif | 103 | #endif |
| 94 | GPRArg gpr[CCALL_NUM_GPR]; /* Arguments/results in GPRs. */ | ||
| 95 | #if CCALL_NUM_FPR | 104 | #if CCALL_NUM_FPR |
| 96 | FPRArg fpr[CCALL_NUM_FPR]; /* Arguments/results in FPRs. */ | 105 | FPRArg fpr[CCALL_NUM_FPR]; /* Arguments/results in FPRs. */ |
| 97 | #endif | 106 | #endif |
| 107 | GPRArg gpr[CCALL_NUM_GPR]; /* Arguments/results in GPRs. */ | ||
| 98 | GPRArg stack[CCALL_MAXSTACK]; /* Stack slots. */ | 108 | GPRArg stack[CCALL_MAXSTACK]; /* Stack slots. */ |
| 99 | } CCallState; | 109 | } CCallState; |
| 100 | 110 | ||
