diff options
| author | Mike Pall <mike> | 2012-06-13 02:32:24 +0200 |
|---|---|---|
| committer | Mike Pall <mike> | 2012-06-13 02:32:24 +0200 |
| commit | ca6bf2d9a41fb2c0c80bafdbaf2e29421b2cb55d (patch) | |
| tree | 2489b763b62323fe844789f611325528c1806e82 /src | |
| parent | 4f9db0fbc3368a7f78370c33740e34cb1d391383 (diff) | |
| download | luajit-ca6bf2d9a41fb2c0c80bafdbaf2e29421b2cb55d.tar.gz luajit-ca6bf2d9a41fb2c0c80bafdbaf2e29421b2cb55d.tar.bz2 luajit-ca6bf2d9a41fb2c0c80bafdbaf2e29421b2cb55d.zip | |
CONSOLE: Handle P64, GPR64, TOC* and PPE (PS3) in PPC interpreter.
PS3 build command: make HOST_CC="gcc -m32" CROSS=ppu-lv2-
Diffstat (limited to 'src')
| -rw-r--r-- | src/Makefile | 5 | ||||
| -rw-r--r-- | src/host/buildvm_asm.c | 9 | ||||
| -rw-r--r-- | src/lj_arch.h | 5 | ||||
| -rw-r--r-- | src/lj_frame.h | 11 | ||||
| -rw-r--r-- | src/vm_ppc.dasc | 610 |
5 files changed, 456 insertions, 184 deletions
diff --git a/src/Makefile b/src/Makefile index 58dcdc01..c3aa2ca2 100644 --- a/src/Makefile +++ b/src/Makefile | |||
| @@ -404,8 +404,11 @@ ifeq (ppc,$(TARGET_LJARCH)) | |||
| 404 | ifneq (,$(findstring LJ_ARCH_ROUND 1,$(TARGET_TESTARCH))) | 404 | ifneq (,$(findstring LJ_ARCH_ROUND 1,$(TARGET_TESTARCH))) |
| 405 | DASM_AFLAGS+= -D ROUND | 405 | DASM_AFLAGS+= -D ROUND |
| 406 | endif | 406 | endif |
| 407 | ifneq (,$(findstring LJ_ARCH_PPC64 1,$(TARGET_TESTARCH))) | ||
| 408 | DASM_AFLAGS+= -D GPR64 | ||
| 409 | endif | ||
| 407 | ifeq (PS3,$(TARGET_SYS)) | 410 | ifeq (PS3,$(TARGET_SYS)) |
| 408 | DASM_AFLAGS+= -D PS3 | 411 | DASM_AFLAGS+= -D PPE -D TOC |
| 409 | endif | 412 | endif |
| 410 | endif | 413 | endif |
| 411 | endif | 414 | endif |
diff --git a/src/host/buildvm_asm.c b/src/host/buildvm_asm.c index 992c3509..08264c8b 100644 --- a/src/host/buildvm_asm.c +++ b/src/host/buildvm_asm.c | |||
| @@ -108,11 +108,16 @@ static void emit_asm_wordreloc(BuildCtx *ctx, uint8_t *p, int n, | |||
| 108 | exit(1); | 108 | exit(1); |
| 109 | } | 109 | } |
| 110 | #elif LJ_TARGET_PPC || LJ_TARGET_PPCSPE | 110 | #elif LJ_TARGET_PPC || LJ_TARGET_PPCSPE |
| 111 | #if LJ_TARGET_PS3 | ||
| 112 | #define TOCPREFIX "." | ||
| 113 | #else | ||
| 114 | #define TOCPREFIX "" | ||
| 115 | #endif | ||
| 111 | if ((ins >> 26) == 16) { | 116 | if ((ins >> 26) == 16) { |
| 112 | fprintf(ctx->fp, "\t%s %d, %d, %s\n", | 117 | fprintf(ctx->fp, "\t%s %d, %d, " TOCPREFIX "%s\n", |
| 113 | (ins & 1) ? "bcl" : "bc", (ins >> 21) & 31, (ins >> 16) & 31, sym); | 118 | (ins & 1) ? "bcl" : "bc", (ins >> 21) & 31, (ins >> 16) & 31, sym); |
| 114 | } else if ((ins >> 26) == 18) { | 119 | } else if ((ins >> 26) == 18) { |
| 115 | fprintf(ctx->fp, "\t%s %s\n", (ins & 1) ? "bl" : "b", sym); | 120 | fprintf(ctx->fp, "\t%s " TOCPREFIX "%s\n", (ins & 1) ? "bl" : "b", sym); |
| 116 | } else { | 121 | } else { |
| 117 | fprintf(stderr, | 122 | fprintf(stderr, |
| 118 | "Error: unsupported opcode %08x for %s symbol relocation.\n", | 123 | "Error: unsupported opcode %08x for %s symbol relocation.\n", |
diff --git a/src/lj_arch.h b/src/lj_arch.h index 7604d84b..c9e9b307 100644 --- a/src/lj_arch.h +++ b/src/lj_arch.h | |||
| @@ -174,7 +174,11 @@ | |||
| 174 | #elif LUAJIT_TARGET == LUAJIT_ARCH_PPC | 174 | #elif LUAJIT_TARGET == LUAJIT_ARCH_PPC |
| 175 | 175 | ||
| 176 | #define LJ_ARCH_NAME "ppc" | 176 | #define LJ_ARCH_NAME "ppc" |
| 177 | #if _LP64 | ||
| 178 | #define LJ_ARCH_BITS 64 | ||
| 179 | #else | ||
| 177 | #define LJ_ARCH_BITS 32 | 180 | #define LJ_ARCH_BITS 32 |
| 181 | #endif | ||
| 178 | #define LJ_ARCH_ENDIAN LUAJIT_BE | 182 | #define LJ_ARCH_ENDIAN LUAJIT_BE |
| 179 | #define LJ_ARCH_HASFPU 1 | 183 | #define LJ_ARCH_HASFPU 1 |
| 180 | #define LJ_TARGET_PPC 1 | 184 | #define LJ_TARGET_PPC 1 |
| @@ -200,6 +204,7 @@ | |||
| 200 | #endif | 204 | #endif |
| 201 | #if __PPC64__ || __powerpc64__ || LJ_TARGET_XBOX360 | 205 | #if __PPC64__ || __powerpc64__ || LJ_TARGET_XBOX360 |
| 202 | #define LJ_ARCH_PPC64 1 | 206 | #define LJ_ARCH_PPC64 1 |
| 207 | #define LJ_ARCH_NOFFI 1 | ||
| 203 | #endif | 208 | #endif |
| 204 | #if _ARCH_PPCSQ | 209 | #if _ARCH_PPCSQ |
| 205 | #define LJ_ARCH_SQRT 1 | 210 | #define LJ_ARCH_SQRT 1 |
diff --git a/src/lj_frame.h b/src/lj_frame.h index e5a56897..b8429c2a 100644 --- a/src/lj_frame.h +++ b/src/lj_frame.h | |||
| @@ -100,6 +100,16 @@ enum { | |||
| 100 | #define CFRAME_SIZE 64 | 100 | #define CFRAME_SIZE 64 |
| 101 | #define CFRAME_SHIFT_MULTRES 3 | 101 | #define CFRAME_SHIFT_MULTRES 3 |
| 102 | #elif LJ_TARGET_PPC | 102 | #elif LJ_TARGET_PPC |
| 103 | #if LJ_ARCH_PPC64 | ||
| 104 | #define CFRAME_OFS_ERRF 472 | ||
| 105 | #define CFRAME_OFS_NRES 468 | ||
| 106 | #define CFRAME_OFS_PREV 448 | ||
| 107 | #define CFRAME_OFS_L 464 | ||
| 108 | #define CFRAME_OFS_PC 460 | ||
| 109 | #define CFRAME_OFS_MULTRES 456 | ||
| 110 | #define CFRAME_SIZE 400 | ||
| 111 | #define CFRAME_SHIFT_MULTRES 3 | ||
| 112 | #else | ||
| 103 | #define CFRAME_OFS_ERRF 48 | 113 | #define CFRAME_OFS_ERRF 48 |
| 104 | #define CFRAME_OFS_NRES 44 | 114 | #define CFRAME_OFS_NRES 44 |
| 105 | #define CFRAME_OFS_PREV 40 | 115 | #define CFRAME_OFS_PREV 40 |
| @@ -108,6 +118,7 @@ enum { | |||
| 108 | #define CFRAME_OFS_MULTRES 28 | 118 | #define CFRAME_OFS_MULTRES 28 |
| 109 | #define CFRAME_SIZE 272 | 119 | #define CFRAME_SIZE 272 |
| 110 | #define CFRAME_SHIFT_MULTRES 3 | 120 | #define CFRAME_SHIFT_MULTRES 3 |
| 121 | #endif | ||
| 111 | #elif LJ_TARGET_PPCSPE | 122 | #elif LJ_TARGET_PPCSPE |
| 112 | #define CFRAME_OFS_ERRF 28 | 123 | #define CFRAME_OFS_ERRF 28 |
| 113 | #define CFRAME_OFS_NRES 24 | 124 | #define CFRAME_OFS_NRES 24 |
diff --git a/src/vm_ppc.dasc b/src/vm_ppc.dasc index db946190..b84a1fc2 100644 --- a/src/vm_ppc.dasc +++ b/src/vm_ppc.dasc | |||
| @@ -15,6 +15,67 @@ | |||
| 15 | | | 15 | | |
| 16 | |//----------------------------------------------------------------------- | 16 | |//----------------------------------------------------------------------- |
| 17 | | | 17 | | |
| 18 | |// DynASM defines used by the PPC port: | ||
| 19 | |// | ||
| 20 | |// P64 64 bit pointers (only for GPR64 testing). | ||
| 21 | |// Note: a full PPC64 _LP64 port is not planned. | ||
| 22 | |// GPR64 64 bit registers (but possibly 32 bit pointers, e.g. PS3). | ||
| 23 | |// Affects reg saves, stack layout, carry/overflow/dot flags etc. | ||
| 24 | |// TOC Need table of contents (64 bit or 32 bit variant, e.g. PS3). | ||
| 25 | |// Function pointers are really a struct: code, TOC, env (optional). | ||
| 26 | |// TOCENV Function pointers have an environment pointer, too (not on PS3). | ||
| 27 | |// PPE Power Processor Element of Cell (PS3) or Xenon (XBox 360). | ||
| 28 | |// Must avoid (slow) micro-coded instructions. | ||
| 29 | | | ||
| 30 | |.if P64 | ||
| 31 | |.define TOC, 1 | ||
| 32 | |.define TOCENV, 1 | ||
| 33 | |.macro lpx, a, b, c; ldx a, b, c; .endmacro | ||
| 34 | |.macro lp, a, b; ld a, b; .endmacro | ||
| 35 | |.macro stp, a, b; std a, b; .endmacro | ||
| 36 | |.define decode_OPP, decode_OP8 | ||
| 37 | |.else | ||
| 38 | |.macro lpx, a, b, c; lwzx a, b, c; .endmacro | ||
| 39 | |.macro lp, a, b; lwz a, b; .endmacro | ||
| 40 | |.macro stp, a, b; stw a, b; .endmacro | ||
| 41 | |.define decode_OPP, decode_OP4 | ||
| 42 | |.if FFI | ||
| 43 | |// Missing: Calling conventions, 64 bit regs, TOC. | ||
| 44 | |.error lib_ffi not yet implemented for PPC64 | ||
| 45 | |.endif | ||
| 46 | |.endif | ||
| 47 | | | ||
| 48 | |// Convenience macros for TOC handling. | ||
| 49 | |.if TOC | ||
| 50 | |// Linker needs a TOC patch area for every external call relocation. | ||
| 51 | |.macro blex, target; bl extern target; nop; .endmacro | ||
| 52 | |.macro .toc, a, b; a, b; .endmacro | ||
| 53 | |.if P64 | ||
| 54 | |.define TOC_OFS, 8 | ||
| 55 | |.define ENV_OFS, 16 | ||
| 56 | |.else | ||
| 57 | |.define TOC_OFS, 4 | ||
| 58 | |.define ENV_OFS, 8 | ||
| 59 | |.endif | ||
| 60 | |.else // No TOC. | ||
| 61 | |.macro blex, target; bl extern target; .endmacro | ||
| 62 | |.macro .toc, a, b; .endmacro | ||
| 63 | |.endif | ||
| 64 | |.macro .tocenv, a, b; .if TOCENV; a, b; .endif; .endmacro | ||
| 65 | | | ||
| 66 | |.macro .gpr64, a, b; .if GPR64; a, b; .endif; .endmacro | ||
| 67 | | | ||
| 68 | |.macro andix., y, a, i | ||
| 69 | |.if PPE | ||
| 70 | | rlwinm y, a, 0, 31-lj_fls(i), 31-lj_ffs(i) | ||
| 71 | | cmpwi y, 0 | ||
| 72 | |.else | ||
| 73 | | andi. y, a, i | ||
| 74 | |.endif | ||
| 75 | |.endmacro | ||
| 76 | | | ||
| 77 | |//----------------------------------------------------------------------- | ||
| 78 | | | ||
| 18 | |// Fixed register assignments for the interpreter. | 79 | |// Fixed register assignments for the interpreter. |
| 19 | |// Don't use: r1 = sp, r2 and r13 = reserved (TOC, TLS or SDATA) | 80 | |// Don't use: r1 = sp, r2 and r13 = reserved (TOC, TLS or SDATA) |
| 20 | | | 81 | | |
| @@ -62,14 +123,47 @@ | |||
| 62 | |.define CRET1, r3 | 123 | |.define CRET1, r3 |
| 63 | |.define CRET2, r4 | 124 | |.define CRET2, r4 |
| 64 | | | 125 | | |
| 126 | |.define TOCREG, r2 // TOC register (only used by C code). | ||
| 127 | |.define ENVREG, r11 // Environment pointer (nested C functions). | ||
| 128 | | | ||
| 65 | |// Stack layout while in interpreter. Must match with lj_frame.h. | 129 | |// Stack layout while in interpreter. Must match with lj_frame.h. |
| 130 | |.if GPR64 | ||
| 131 | | | ||
| 132 | |// 508(sp) // \ 32 bit C frame info. | ||
| 133 | |.define SAVE_ERRF, 472(sp) // | | ||
| 134 | |.define SAVE_NRES, 468(sp) // | | ||
| 135 | |.define SAVE_L, 464(sp) // > Parameter save area. | ||
| 136 | |.define SAVE_PC, 460(sp) // | | ||
| 137 | |.define SAVE_MULTRES, 456(sp) // | | ||
| 138 | |.define SAVE_CFRAME, 448(sp) // / 64 bit C frame chain. | ||
| 139 | |.define SAVE_LR, 416(sp) | ||
| 140 | |.define CFRAME_SPACE, 400 // Delta for sp. | ||
| 141 | |// Back chain for sp: 400(sp) <-- sp entering interpreter | ||
| 142 | |.define SAVE_FPR_, 256 // .. 256+18*8: 64 bit FPR saves. | ||
| 143 | |.define SAVE_GPR_, 112 // .. 112+18*8: 64 bit GPR saves. | ||
| 144 | |// 48(sp) // Callee parameter save area (ABI mandated). | ||
| 145 | |.define SAVE_TOC, 40(sp) // TOC save area. | ||
| 146 | |.define TMPD_LO, 36(sp) // \ Link editor temp (ABI mandated). | ||
| 147 | |.define TMPD_HI, 32(sp) // / | ||
| 148 | |.define TONUM_LO, 28(sp) // \ Compiler temp (ABI mandated). | ||
| 149 | |.define TONUM_HI, 24(sp) // / | ||
| 150 | |// Next frame lr: 16(sp) | ||
| 151 | |.define SAVE_CR, 8(sp) // 64 bit CR save. | ||
| 152 | |// Back chain for sp: 0(sp) <-- sp while in interpreter | ||
| 153 | | | ||
| 154 | |.define TMPD_BLO, 39(sp) | ||
| 155 | |.define TMPD, TMPD_HI | ||
| 156 | |.define TONUM_D, TONUM_HI | ||
| 157 | | | ||
| 158 | |.else | ||
| 159 | | | ||
| 66 | |.define SAVE_LR, 276(sp) | 160 | |.define SAVE_LR, 276(sp) |
| 67 | |.define CFRAME_SPACE, 272 // Delta for sp. | 161 | |.define CFRAME_SPACE, 272 // Delta for sp. |
| 68 | |// Back chain for sp: 272(sp) <-- sp entering interpreter | 162 | |// Back chain for sp: 272(sp) <-- sp entering interpreter |
| 69 | |.define SAVE_FPR_, 128 // .. 128+18*8: 64 bit FPR saves. | 163 | |.define SAVE_FPR_, 128 // .. 128+18*8: 64 bit FPR saves. |
| 70 | |.define SAVE_GPR_, 56 // .. 56+18*4: 32 bit GPR saves. | 164 | |.define SAVE_GPR_, 56 // .. 56+18*4: 32 bit GPR saves. |
| 71 | |.define SAVE_CR, 52(sp) // 32 bit CR save. | 165 | |.define SAVE_CR, 52(sp) // 32 bit CR save. |
| 72 | |.define SAVE_ERRF, 48(sp) // 32 bit C frame info. | 166 | |.define SAVE_ERRF, 48(sp) // 32 bit C frame info. |
| 73 | |.define SAVE_NRES, 44(sp) | 167 | |.define SAVE_NRES, 44(sp) |
| 74 | |.define SAVE_CFRAME, 40(sp) | 168 | |.define SAVE_CFRAME, 40(sp) |
| 75 | |.define SAVE_L, 36(sp) | 169 | |.define SAVE_L, 36(sp) |
| @@ -87,33 +181,63 @@ | |||
| 87 | |.define TMPD, TMPD_HI | 181 | |.define TMPD, TMPD_HI |
| 88 | |.define TONUM_D, TONUM_HI | 182 | |.define TONUM_D, TONUM_HI |
| 89 | | | 183 | | |
| 184 | |.endif | ||
| 185 | | | ||
| 90 | |.macro save_, reg | 186 | |.macro save_, reg |
| 187 | |.if GPR64 | ||
| 188 | | std r..reg, SAVE_GPR_+(reg-14)*8(sp) | ||
| 189 | |.else | ||
| 91 | | stw r..reg, SAVE_GPR_+(reg-14)*4(sp) | 190 | | stw r..reg, SAVE_GPR_+(reg-14)*4(sp) |
| 191 | |.endif | ||
| 92 | | stfd f..reg, SAVE_FPR_+(reg-14)*8(sp) | 192 | | stfd f..reg, SAVE_FPR_+(reg-14)*8(sp) |
| 93 | |.endmacro | 193 | |.endmacro |
| 94 | |.macro rest_, reg | 194 | |.macro rest_, reg |
| 195 | |.if GPR64 | ||
| 196 | | ld r..reg, SAVE_GPR_+(reg-14)*8(sp) | ||
| 197 | |.else | ||
| 95 | | lwz r..reg, SAVE_GPR_+(reg-14)*4(sp) | 198 | | lwz r..reg, SAVE_GPR_+(reg-14)*4(sp) |
| 199 | |.endif | ||
| 96 | | lfd f..reg, SAVE_FPR_+(reg-14)*8(sp) | 200 | | lfd f..reg, SAVE_FPR_+(reg-14)*8(sp) |
| 97 | |.endmacro | 201 | |.endmacro |
| 98 | | | 202 | | |
| 99 | |.macro saveregs | 203 | |.macro saveregs |
| 204 | |.if GPR64 | ||
| 205 | | stdu sp, -CFRAME_SPACE(sp) | ||
| 206 | |.else | ||
| 100 | | stwu sp, -CFRAME_SPACE(sp) | 207 | | stwu sp, -CFRAME_SPACE(sp) |
| 208 | |.endif | ||
| 101 | | save_ 14; save_ 15; save_ 16 | 209 | | save_ 14; save_ 15; save_ 16 |
| 102 | | mflr r0 | 210 | | mflr r0 |
| 103 | | save_ 17; save_ 18; save_ 19; save_ 20; save_ 21; save_ 22 | 211 | | save_ 17; save_ 18; save_ 19; save_ 20; save_ 21; save_ 22 |
| 104 | | stw r0, SAVE_LR | 212 | |.if GPR64 |
| 213 | | std r0, SAVE_LR | ||
| 214 | |.else | ||
| 215 | | stw r0, SAVE_LR | ||
| 216 | |.endif | ||
| 105 | | save_ 23; save_ 24; save_ 25 | 217 | | save_ 23; save_ 24; save_ 25 |
| 106 | | mfcr r0 | 218 | | mfcr r0 |
| 107 | | save_ 26; save_ 27; save_ 28; save_ 29; save_ 30; save_ 31 | 219 | | save_ 26; save_ 27; save_ 28; save_ 29; save_ 30; save_ 31 |
| 220 | |.if GPR64 | ||
| 221 | | std r0, SAVE_CR | ||
| 222 | |.else | ||
| 108 | | stw r0, SAVE_CR | 223 | | stw r0, SAVE_CR |
| 224 | |.endif | ||
| 225 | | .toc std TOCREG, SAVE_TOC | ||
| 109 | |.endmacro | 226 | |.endmacro |
| 110 | | | 227 | | |
| 111 | |.macro restoreregs | 228 | |.macro restoreregs |
| 229 | |.if GPR64 | ||
| 230 | | ld r0, SAVE_LR; ld r12, SAVE_CR | ||
| 231 | |.else | ||
| 112 | | lwz r0, SAVE_LR; lwz r12, SAVE_CR | 232 | | lwz r0, SAVE_LR; lwz r12, SAVE_CR |
| 233 | |.endif | ||
| 113 | | rest_ 14; rest_ 15; rest_ 16; rest_ 17; rest_ 18; rest_ 19 | 234 | | rest_ 14; rest_ 15; rest_ 16; rest_ 17; rest_ 18; rest_ 19 |
| 114 | | mtlr r0; mtcrf 0x38, r12 | 235 | | mtlr r0; |
| 236 | |.if PPE; mtocrf 0x20, r12; .else; mtcrf 0x38, r12; .endif | ||
| 115 | | rest_ 20; rest_ 21; rest_ 22; rest_ 23; rest_ 24; rest_ 25 | 237 | | rest_ 20; rest_ 21; rest_ 22; rest_ 23; rest_ 24; rest_ 25 |
| 238 | |.if PPE; mtocrf 0x10, r12; .endif | ||
| 116 | | rest_ 26; rest_ 27; rest_ 28; rest_ 29; rest_ 30; rest_ 31 | 239 | | rest_ 26; rest_ 27; rest_ 28; rest_ 29; rest_ 30; rest_ 31 |
| 240 | |.if PPE; mtocrf 0x08, r12; .endif | ||
| 117 | | addi sp, sp, CFRAME_SPACE | 241 | | addi sp, sp, CFRAME_SPACE |
| 118 | |.endmacro | 242 | |.endmacro |
| 119 | | | 243 | | |
| @@ -176,6 +300,7 @@ | |||
| 176 | | | 300 | | |
| 177 | |// Instruction decode. | 301 | |// Instruction decode. |
| 178 | |.macro decode_OP4, dst, ins; rlwinm dst, ins, 2, 22, 29; .endmacro | 302 | |.macro decode_OP4, dst, ins; rlwinm dst, ins, 2, 22, 29; .endmacro |
| 303 | |.macro decode_OP8, dst, ins; rlwinm dst, ins, 3, 21, 28; .endmacro | ||
| 179 | |.macro decode_RA8, dst, ins; rlwinm dst, ins, 27, 21, 28; .endmacro | 304 | |.macro decode_RA8, dst, ins; rlwinm dst, ins, 27, 21, 28; .endmacro |
| 180 | |.macro decode_RB8, dst, ins; rlwinm dst, ins, 11, 21, 28; .endmacro | 305 | |.macro decode_RB8, dst, ins; rlwinm dst, ins, 11, 21, 28; .endmacro |
| 181 | |.macro decode_RC8, dst, ins; rlwinm dst, ins, 19, 21, 28; .endmacro | 306 | |.macro decode_RC8, dst, ins; rlwinm dst, ins, 19, 21, 28; .endmacro |
| @@ -191,8 +316,8 @@ | |||
| 191 | |.endmacro | 316 | |.endmacro |
| 192 | |// Instruction decode+dispatch. Note: optimized for e300! | 317 | |// Instruction decode+dispatch. Note: optimized for e300! |
| 193 | |.macro ins_NEXT2 | 318 | |.macro ins_NEXT2 |
| 194 | | decode_OP4 TMP1, INS | 319 | | decode_OPP TMP1, INS |
| 195 | | lwzx TMP0, DISPATCH, TMP1 | 320 | | lpx TMP0, DISPATCH, TMP1 |
| 196 | | mtctr TMP0 | 321 | | mtctr TMP0 |
| 197 | | decode_RB8 RB, INS | 322 | | decode_RB8 RB, INS |
| 198 | | decode_RD8 RD, INS | 323 | | decode_RD8 RD, INS |
| @@ -235,9 +360,9 @@ | |||
| 235 | | lwz PC, LFUNC:RB->pc | 360 | | lwz PC, LFUNC:RB->pc |
| 236 | | lwz INS, 0(PC) | 361 | | lwz INS, 0(PC) |
| 237 | | addi PC, PC, 4 | 362 | | addi PC, PC, 4 |
| 238 | | decode_OP4 TMP1, INS | 363 | | decode_OPP TMP1, INS |
| 239 | | decode_RA8 RA, INS | 364 | | decode_RA8 RA, INS |
| 240 | | lwzx TMP0, DISPATCH, TMP1 | 365 | | lpx TMP0, DISPATCH, TMP1 |
| 241 | | add RA, RA, BASE | 366 | | add RA, RA, BASE |
| 242 | | mtctr TMP0 | 367 | | mtctr TMP0 |
| 243 | | bctr | 368 | | bctr |
| @@ -316,7 +441,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 316 | | | 441 | | |
| 317 | |->vm_returnp: | 442 | |->vm_returnp: |
| 318 | | // See vm_return. Also: TMP2 = previous base. | 443 | | // See vm_return. Also: TMP2 = previous base. |
| 319 | | andi. TMP0, PC, FRAME_P | 444 | | andix. TMP0, PC, FRAME_P |
| 320 | | li TMP1, LJ_TTRUE | 445 | | li TMP1, LJ_TTRUE |
| 321 | | beq ->cont_dispatch | 446 | | beq ->cont_dispatch |
| 322 | | | 447 | | |
| @@ -327,7 +452,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 327 | | stwu TMP1, FRAME_PC(RA) // Prepend true to results. | 452 | | stwu TMP1, FRAME_PC(RA) // Prepend true to results. |
| 328 | | | 453 | | |
| 329 | |->vm_returnc: | 454 | |->vm_returnc: |
| 330 | | andi. TMP0, PC, FRAME_TYPE | 455 | | andix. TMP0, PC, FRAME_TYPE |
| 331 | | addi RD, RD, 8 // RD = (nresults+1)*8. | 456 | | addi RD, RD, 8 // RD = (nresults+1)*8. |
| 332 | | mr MULTRES, RD | 457 | | mr MULTRES, RD |
| 333 | | beq ->BC_RET_Z // Handle regular return to Lua. | 458 | | beq ->BC_RET_Z // Handle regular return to Lua. |
| @@ -342,7 +467,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 342 | | bney ->vm_returnp | 467 | | bney ->vm_returnp |
| 343 | | | 468 | | |
| 344 | | addic. TMP1, RD, -8 | 469 | | addic. TMP1, RD, -8 |
| 345 | | stw TMP2, L->base | 470 | | stp TMP2, L->base |
| 346 | | lwz TMP2, SAVE_NRES | 471 | | lwz TMP2, SAVE_NRES |
| 347 | | subi BASE, BASE, 8 | 472 | | subi BASE, BASE, 8 |
| 348 | | st_vmstate | 473 | | st_vmstate |
| @@ -360,12 +485,12 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 360 | | cmpw TMP2, RD // More/less results wanted? | 485 | | cmpw TMP2, RD // More/less results wanted? |
| 361 | | bne >6 | 486 | | bne >6 |
| 362 | |3: | 487 | |3: |
| 363 | | stw BASE, L->top // Store new top. | 488 | | stp BASE, L->top // Store new top. |
| 364 | | | 489 | | |
| 365 | |->vm_leave_cp: | 490 | |->vm_leave_cp: |
| 366 | | lwz TMP0, SAVE_CFRAME // Restore previous C frame. | 491 | | lp TMP0, SAVE_CFRAME // Restore previous C frame. |
| 367 | | li CRET1, 0 // Ok return status for vm_pcall. | 492 | | li CRET1, 0 // Ok return status for vm_pcall. |
| 368 | | stw TMP0, L->cframe | 493 | | stp TMP0, L->cframe |
| 369 | | | 494 | | |
| 370 | |->vm_leave_unw: | 495 | |->vm_leave_unw: |
| 371 | | restoreregs | 496 | | restoreregs |
| @@ -395,7 +520,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 395 | | // - A C function grows the stack (a lot). | 520 | | // - A C function grows the stack (a lot). |
| 396 | | // - The GC shrinks the stack in between. | 521 | | // - The GC shrinks the stack in between. |
| 397 | | // - A return back from a lua_call() with (high) nresults adjustment. | 522 | | // - A return back from a lua_call() with (high) nresults adjustment. |
| 398 | | stw BASE, L->top // Save current top held in BASE (yes). | 523 | | stp BASE, L->top // Save current top held in BASE (yes). |
| 399 | | mr SAVE0, RD | 524 | | mr SAVE0, RD |
| 400 | | mr CARG2, TMP2 | 525 | | mr CARG2, TMP2 |
| 401 | | mr CARG1, L | 526 | | mr CARG1, L |
| @@ -403,7 +528,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 403 | | lwz TMP2, SAVE_NRES | 528 | | lwz TMP2, SAVE_NRES |
| 404 | | mr RD, SAVE0 | 529 | | mr RD, SAVE0 |
| 405 | | slwi TMP2, TMP2, 3 | 530 | | slwi TMP2, TMP2, 3 |
| 406 | | lwz BASE, L->top // Need the (realloced) L->top in BASE. | 531 | | lp BASE, L->top // Need the (realloced) L->top in BASE. |
| 407 | | b <2 | 532 | | b <2 |
| 408 | | | 533 | | |
| 409 | |->vm_unwind_c: // Unwind C stack, return from vm_pcall. | 534 | |->vm_unwind_c: // Unwind C stack, return from vm_pcall. |
| @@ -412,6 +537,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 412 | | mr CRET1, CARG2 | 537 | | mr CRET1, CARG2 |
| 413 | |->vm_unwind_c_eh: // Landing pad for external unwinder. | 538 | |->vm_unwind_c_eh: // Landing pad for external unwinder. |
| 414 | | lwz L, SAVE_L | 539 | | lwz L, SAVE_L |
| 540 | | .toc ld TOCREG, SAVE_TOC | ||
| 415 | | li TMP0, ~LJ_VMST_C | 541 | | li TMP0, ~LJ_VMST_C |
| 416 | | lwz GL:TMP1, L->glref | 542 | | lwz GL:TMP1, L->glref |
| 417 | | stw TMP0, GL:TMP1->vmstate | 543 | | stw TMP0, GL:TMP1->vmstate |
| @@ -419,11 +545,16 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 419 | | | 545 | | |
| 420 | |->vm_unwind_ff: // Unwind C stack, return from ff pcall. | 546 | |->vm_unwind_ff: // Unwind C stack, return from ff pcall. |
| 421 | | // (void *cframe) | 547 | | // (void *cframe) |
| 548 | |.if GPR64 | ||
| 549 | | rldicr sp, CARG1, 0, 61 | ||
| 550 | |.else | ||
| 422 | | rlwinm sp, CARG1, 0, 0, 29 | 551 | | rlwinm sp, CARG1, 0, 0, 29 |
| 552 | |.endif | ||
| 423 | |->vm_unwind_ff_eh: // Landing pad for external unwinder. | 553 | |->vm_unwind_ff_eh: // Landing pad for external unwinder. |
| 424 | | lwz L, SAVE_L | 554 | | lwz L, SAVE_L |
| 555 | | .toc ld TOCREG, SAVE_TOC | ||
| 425 | | li TISNUM, LJ_TISNUM // Setup type comparison constants. | 556 | | li TISNUM, LJ_TISNUM // Setup type comparison constants. |
| 426 | | lwz BASE, L->base | 557 | | lp BASE, L->base |
| 427 | | lus TMP3, 0x59c0 // TOBIT = 2^52 + 2^51 (float). | 558 | | lus TMP3, 0x59c0 // TOBIT = 2^52 + 2^51 (float). |
| 428 | | lwz DISPATCH, L->glref // Setup pointer to dispatch table. | 559 | | lwz DISPATCH, L->glref // Setup pointer to dispatch table. |
| 429 | | li ZERO, 0 | 560 | | li ZERO, 0 |
| @@ -455,17 +586,17 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 455 | | // BASE = new base, RA = BASE+framesize*8, RC = nargs*8, PC = first PC | 586 | | // BASE = new base, RA = BASE+framesize*8, RC = nargs*8, PC = first PC |
| 456 | | add RC, BASE, RC | 587 | | add RC, BASE, RC |
| 457 | | sub RA, RA, BASE | 588 | | sub RA, RA, BASE |
| 458 | | stw BASE, L->base | 589 | | stp BASE, L->base |
| 459 | | addi PC, PC, 4 // Must point after first instruction. | 590 | | addi PC, PC, 4 // Must point after first instruction. |
| 460 | | stw RC, L->top | 591 | | stp RC, L->top |
| 461 | | srwi CARG2, RA, 3 | 592 | | srwi CARG2, RA, 3 |
| 462 | |2: | 593 | |2: |
| 463 | | // L->base = new base, L->top = top | 594 | | // L->base = new base, L->top = top |
| 464 | | stw PC, SAVE_PC | 595 | | stw PC, SAVE_PC |
| 465 | | mr CARG1, L | 596 | | mr CARG1, L |
| 466 | | bl extern lj_state_growstack // (lua_State *L, int n) | 597 | | bl extern lj_state_growstack // (lua_State *L, int n) |
| 467 | | lwz BASE, L->base | 598 | | lp BASE, L->base |
| 468 | | lwz RC, L->top | 599 | | lp RC, L->top |
| 469 | | lwz LFUNC:RB, FRAME_FUNC(BASE) | 600 | | lwz LFUNC:RB, FRAME_FUNC(BASE) |
| 470 | | sub RC, RC, BASE | 601 | | sub RC, RC, BASE |
| 471 | | // BASE = new base, RB = LFUNC/CFUNC, RC = nargs*8, FRAME_PC(BASE) = PC | 602 | | // BASE = new base, RB = LFUNC/CFUNC, RC = nargs*8, FRAME_PC(BASE) = PC |
| @@ -489,16 +620,16 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 489 | | stw CARG3, SAVE_NRES | 620 | | stw CARG3, SAVE_NRES |
| 490 | | cmplwi TMP1, 0 | 621 | | cmplwi TMP1, 0 |
| 491 | | stw CARG3, SAVE_ERRF | 622 | | stw CARG3, SAVE_ERRF |
| 492 | | stw TMP0, L->cframe | 623 | | stp TMP0, L->cframe |
| 493 | | stw CARG3, SAVE_CFRAME | 624 | | stp CARG3, SAVE_CFRAME |
| 494 | | stw CARG1, SAVE_PC // Any value outside of bytecode is ok. | 625 | | stw CARG1, SAVE_PC // Any value outside of bytecode is ok. |
| 495 | | beq >3 | 626 | | beq >3 |
| 496 | | | 627 | | |
| 497 | | // Resume after yield (like a return). | 628 | | // Resume after yield (like a return). |
| 498 | | mr RA, BASE | 629 | | mr RA, BASE |
| 499 | | lwz BASE, L->base | 630 | | lp BASE, L->base |
| 500 | | li TISNUM, LJ_TISNUM // Setup type comparison constants. | 631 | | li TISNUM, LJ_TISNUM // Setup type comparison constants. |
| 501 | | lwz TMP1, L->top | 632 | | lp TMP1, L->top |
| 502 | | lwz PC, FRAME_PC(BASE) | 633 | | lwz PC, FRAME_PC(BASE) |
| 503 | | lus TMP3, 0x59c0 // TOBIT = 2^52 + 2^51 (float). | 634 | | lus TMP3, 0x59c0 // TOBIT = 2^52 + 2^51 (float). |
| 504 | | stb CARG3, L->status | 635 | | stb CARG3, L->status |
| @@ -513,7 +644,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 513 | | li_vmstate INTERP | 644 | | li_vmstate INTERP |
| 514 | | li ZERO, 0 | 645 | | li ZERO, 0 |
| 515 | | st_vmstate | 646 | | st_vmstate |
| 516 | | andi. TMP0, PC, FRAME_TYPE | 647 | | andix. TMP0, PC, FRAME_TYPE |
| 517 | | mr MULTRES, RD | 648 | | mr MULTRES, RD |
| 518 | | lfs TONUM, TMPD | 649 | | lfs TONUM, TMPD |
| 519 | | li TISNIL, LJ_TNIL | 650 | | li TISNIL, LJ_TNIL |
| @@ -533,21 +664,21 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 533 | | li PC, FRAME_C | 664 | | li PC, FRAME_C |
| 534 | | | 665 | | |
| 535 | |1: // Entry point for vm_pcall above (PC = ftype). | 666 | |1: // Entry point for vm_pcall above (PC = ftype). |
| 536 | | lwz TMP1, L:CARG1->cframe | 667 | | lp TMP1, L:CARG1->cframe |
| 537 | | stw CARG3, SAVE_NRES | 668 | | stw CARG3, SAVE_NRES |
| 538 | | mr L, CARG1 | 669 | | mr L, CARG1 |
| 539 | | stw CARG1, SAVE_L | 670 | | stw CARG1, SAVE_L |
| 540 | | mr BASE, CARG2 | 671 | | mr BASE, CARG2 |
| 541 | | stw sp, L->cframe // Add our C frame to cframe chain. | 672 | | stp sp, L->cframe // Add our C frame to cframe chain. |
| 542 | | lwz DISPATCH, L->glref // Setup pointer to dispatch table. | 673 | | lwz DISPATCH, L->glref // Setup pointer to dispatch table. |
| 543 | | stw CARG1, SAVE_PC // Any value outside of bytecode is ok. | 674 | | stw CARG1, SAVE_PC // Any value outside of bytecode is ok. |
| 544 | | stw TMP1, SAVE_CFRAME | 675 | | stp TMP1, SAVE_CFRAME |
| 545 | | addi DISPATCH, DISPATCH, GG_G2DISP | 676 | | addi DISPATCH, DISPATCH, GG_G2DISP |
| 546 | | | 677 | | |
| 547 | |3: // Entry point for vm_cpcall/vm_resume (BASE = base, PC = ftype). | 678 | |3: // Entry point for vm_cpcall/vm_resume (BASE = base, PC = ftype). |
| 548 | | lwz TMP2, L->base // TMP2 = old base (used in vmeta_call). | 679 | | lp TMP2, L->base // TMP2 = old base (used in vmeta_call). |
| 549 | | li TISNUM, LJ_TISNUM // Setup type comparison constants. | 680 | | li TISNUM, LJ_TISNUM // Setup type comparison constants. |
| 550 | | lwz TMP1, L->top | 681 | | lp TMP1, L->top |
| 551 | | lus TMP3, 0x59c0 // TOBIT = 2^52 + 2^51 (float). | 682 | | lus TMP3, 0x59c0 // TOBIT = 2^52 + 2^51 (float). |
| 552 | | add PC, PC, BASE | 683 | | add PC, PC, BASE |
| 553 | | stw TMP3, TMPD | 684 | | stw TMP3, TMPD |
| @@ -580,18 +711,24 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 580 | | mr L, CARG1 | 711 | | mr L, CARG1 |
| 581 | | lwz TMP0, L:CARG1->stack | 712 | | lwz TMP0, L:CARG1->stack |
| 582 | | stw CARG1, SAVE_L | 713 | | stw CARG1, SAVE_L |
| 583 | | lwz TMP1, L->top | 714 | | lp TMP1, L->top |
| 584 | | stw CARG1, SAVE_PC // Any value outside of bytecode is ok. | 715 | | stw CARG1, SAVE_PC // Any value outside of bytecode is ok. |
| 585 | | sub TMP0, TMP0, TMP1 // Compute -savestack(L, L->top). | 716 | | sub TMP0, TMP0, TMP1 // Compute -savestack(L, L->top). |
| 586 | | lwz TMP1, L->cframe | 717 | | lp TMP1, L->cframe |
| 587 | | stw sp, L->cframe // Add our C frame to cframe chain. | 718 | | stp sp, L->cframe // Add our C frame to cframe chain. |
| 719 | | .toc lp CARG4, 0(CARG4) | ||
| 588 | | li TMP2, 0 | 720 | | li TMP2, 0 |
| 589 | | stw TMP0, SAVE_NRES // Neg. delta means cframe w/o frame. | 721 | | stw TMP0, SAVE_NRES // Neg. delta means cframe w/o frame. |
| 590 | | stw TMP2, SAVE_ERRF // No error function. | 722 | | stw TMP2, SAVE_ERRF // No error function. |
| 591 | | stw TMP1, SAVE_CFRAME | 723 | | stp TMP1, SAVE_CFRAME |
| 592 | | mtctr CARG4 | 724 | | mtctr CARG4 |
| 593 | | bctrl // (lua_State *L, lua_CFunction func, void *ud) | 725 | | bctrl // (lua_State *L, lua_CFunction func, void *ud) |
| 726 | |.if PPE | ||
| 727 | | mr BASE, CRET1 | ||
| 728 | | cmpwi CRET1, 0 | ||
| 729 | |.else | ||
| 594 | | mr. BASE, CRET1 | 730 | | mr. BASE, CRET1 |
| 731 | |.endif | ||
| 595 | | lwz DISPATCH, L->glref // Setup pointer to dispatch table. | 732 | | lwz DISPATCH, L->glref // Setup pointer to dispatch table. |
| 596 | | li PC, FRAME_CP | 733 | | li PC, FRAME_CP |
| 597 | | addi DISPATCH, DISPATCH, GG_G2DISP | 734 | | addi DISPATCH, DISPATCH, GG_G2DISP |
| @@ -643,7 +780,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 643 | | decode_RB8 SAVE0, INS | 780 | | decode_RB8 SAVE0, INS |
| 644 | | lfd f0, 0(RA) | 781 | | lfd f0, 0(RA) |
| 645 | | add TMP1, BASE, SAVE0 | 782 | | add TMP1, BASE, SAVE0 |
| 646 | | stw BASE, L->base | 783 | | stp BASE, L->base |
| 647 | | cmplw TMP1, CARG2 | 784 | | cmplw TMP1, CARG2 |
| 648 | | sub CARG3, CARG2, TMP1 | 785 | | sub CARG3, CARG2, TMP1 |
| 649 | | decode_RA8 RA, INS | 786 | | decode_RA8 RA, INS |
| @@ -695,7 +832,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 695 | | add CARG2, BASE, RB | 832 | | add CARG2, BASE, RB |
| 696 | | add CARG3, BASE, RC | 833 | | add CARG3, BASE, RC |
| 697 | |1: | 834 | |1: |
| 698 | | stw BASE, L->base | 835 | | stp BASE, L->base |
| 699 | | mr CARG1, L | 836 | | mr CARG1, L |
| 700 | | stw PC, SAVE_PC | 837 | | stw PC, SAVE_PC |
| 701 | | bl extern lj_meta_tget // (lua_State *L, TValue *o, TValue *k) | 838 | | bl extern lj_meta_tget // (lua_State *L, TValue *o, TValue *k) |
| @@ -710,7 +847,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 710 | |3: // Call __index metamethod. | 847 | |3: // Call __index metamethod. |
| 711 | | // BASE = base, L->top = new base, stack = cont/func/t/k | 848 | | // BASE = base, L->top = new base, stack = cont/func/t/k |
| 712 | | subfic TMP1, BASE, FRAME_CONT | 849 | | subfic TMP1, BASE, FRAME_CONT |
| 713 | | lwz BASE, L->top | 850 | | lp BASE, L->top |
| 714 | | stw PC, -16(BASE) // [cont|PC] | 851 | | stw PC, -16(BASE) // [cont|PC] |
| 715 | | add PC, TMP1, BASE | 852 | | add PC, TMP1, BASE |
| 716 | | lwz LFUNC:RB, FRAME_FUNC(BASE) // Guaranteed to be a function here. | 853 | | lwz LFUNC:RB, FRAME_FUNC(BASE) // Guaranteed to be a function here. |
| @@ -760,7 +897,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 760 | | add CARG2, BASE, RB | 897 | | add CARG2, BASE, RB |
| 761 | | add CARG3, BASE, RC | 898 | | add CARG3, BASE, RC |
| 762 | |1: | 899 | |1: |
| 763 | | stw BASE, L->base | 900 | | stp BASE, L->base |
| 764 | | mr CARG1, L | 901 | | mr CARG1, L |
| 765 | | stw PC, SAVE_PC | 902 | | stw PC, SAVE_PC |
| 766 | | bl extern lj_meta_tset // (lua_State *L, TValue *o, TValue *k) | 903 | | bl extern lj_meta_tset // (lua_State *L, TValue *o, TValue *k) |
| @@ -776,7 +913,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 776 | |3: // Call __newindex metamethod. | 913 | |3: // Call __newindex metamethod. |
| 777 | | // BASE = base, L->top = new base, stack = cont/func/t/k/(v) | 914 | | // BASE = base, L->top = new base, stack = cont/func/t/k/(v) |
| 778 | | subfic TMP1, BASE, FRAME_CONT | 915 | | subfic TMP1, BASE, FRAME_CONT |
| 779 | | lwz BASE, L->top | 916 | | lp BASE, L->top |
| 780 | | stw PC, -16(BASE) // [cont|PC] | 917 | | stw PC, -16(BASE) // [cont|PC] |
| 781 | | add PC, TMP1, BASE | 918 | | add PC, TMP1, BASE |
| 782 | | lwz LFUNC:RB, FRAME_FUNC(BASE) // Guaranteed to be a function here. | 919 | | lwz LFUNC:RB, FRAME_FUNC(BASE) // Guaranteed to be a function here. |
| @@ -800,7 +937,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 800 | |.else | 937 | |.else |
| 801 | | add CARG3, BASE, RD | 938 | | add CARG3, BASE, RD |
| 802 | |.endif | 939 | |.endif |
| 803 | | stw BASE, L->base | 940 | | stp BASE, L->base |
| 804 | | decode_OP1 CARG4, INS | 941 | | decode_OP1 CARG4, INS |
| 805 | | bl extern lj_meta_comp // (lua_State *L, TValue *o1, *o2, int op) | 942 | | bl extern lj_meta_comp // (lua_State *L, TValue *o1, *o2, int op) |
| 806 | | // Returns 0/1 or TValue * (metamethod). | 943 | | // Returns 0/1 or TValue * (metamethod). |
| @@ -827,6 +964,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 827 | | | 964 | | |
| 828 | |->cont_condt: // RA = resultptr | 965 | |->cont_condt: // RA = resultptr |
| 829 | | lwz TMP0, 0(RA) | 966 | | lwz TMP0, 0(RA) |
| 967 | | .gpr64 extsw TMP0, TMP0 | ||
| 830 | | subfic TMP0, TMP0, LJ_TTRUE // Branch if result is true. | 968 | | subfic TMP0, TMP0, LJ_TTRUE // Branch if result is true. |
| 831 | | subfe CRET1, CRET1, CRET1 | 969 | | subfe CRET1, CRET1, CRET1 |
| 832 | | not CRET1, CRET1 | 970 | | not CRET1, CRET1 |
| @@ -834,6 +972,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 834 | | | 972 | | |
| 835 | |->cont_condf: // RA = resultptr | 973 | |->cont_condf: // RA = resultptr |
| 836 | | lwz TMP0, 0(RA) | 974 | | lwz TMP0, 0(RA) |
| 975 | | .gpr64 extsw TMP0, TMP0 | ||
| 837 | | subfic TMP0, TMP0, LJ_TTRUE // Branch if result is false. | 976 | | subfic TMP0, TMP0, LJ_TTRUE // Branch if result is false. |
| 838 | | subfe CRET1, CRET1, CRET1 | 977 | | subfe CRET1, CRET1, CRET1 |
| 839 | | b <4 | 978 | | b <4 |
| @@ -841,7 +980,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 841 | |->vmeta_equal: | 980 | |->vmeta_equal: |
| 842 | | // CARG2, CARG3, CARG4 are already set by BC_ISEQV/BC_ISNEV. | 981 | | // CARG2, CARG3, CARG4 are already set by BC_ISEQV/BC_ISNEV. |
| 843 | | subi PC, PC, 4 | 982 | | subi PC, PC, 4 |
| 844 | | stw BASE, L->base | 983 | | stp BASE, L->base |
| 845 | | mr CARG1, L | 984 | | mr CARG1, L |
| 846 | | stw PC, SAVE_PC | 985 | | stw PC, SAVE_PC |
| 847 | | bl extern lj_meta_equal // (lua_State *L, GCobj *o1, *o2, int ne) | 986 | | bl extern lj_meta_equal // (lua_State *L, GCobj *o1, *o2, int ne) |
| @@ -852,7 +991,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 852 | |.if FFI | 991 | |.if FFI |
| 853 | | mr CARG2, INS | 992 | | mr CARG2, INS |
| 854 | | subi PC, PC, 4 | 993 | | subi PC, PC, 4 |
| 855 | | stw BASE, L->base | 994 | | stp BASE, L->base |
| 856 | | mr CARG1, L | 995 | | mr CARG1, L |
| 857 | | stw PC, SAVE_PC | 996 | | stw PC, SAVE_PC |
| 858 | | bl extern lj_meta_equal_cd // (lua_State *L, BCIns op) | 997 | | bl extern lj_meta_equal_cd // (lua_State *L, BCIns op) |
| @@ -897,7 +1036,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 897 | |.endif | 1036 | |.endif |
| 898 | |1: | 1037 | |1: |
| 899 | | add CARG2, BASE, RA | 1038 | | add CARG2, BASE, RA |
| 900 | | stw BASE, L->base | 1039 | | stp BASE, L->base |
| 901 | | mr CARG1, L | 1040 | | mr CARG1, L |
| 902 | | stw PC, SAVE_PC | 1041 | | stw PC, SAVE_PC |
| 903 | | decode_OP1 CARG5, INS // Caveat: CARG5 overlaps INS. | 1042 | | decode_OP1 CARG5, INS // Caveat: CARG5 overlaps INS. |
| @@ -922,7 +1061,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 922 | | mr SAVE0, CARG1 | 1061 | | mr SAVE0, CARG1 |
| 923 | #endif | 1062 | #endif |
| 924 | | mr CARG2, RD | 1063 | | mr CARG2, RD |
| 925 | | stw BASE, L->base | 1064 | | stp BASE, L->base |
| 926 | | mr CARG1, L | 1065 | | mr CARG1, L |
| 927 | | stw PC, SAVE_PC | 1066 | | stw PC, SAVE_PC |
| 928 | | bl extern lj_meta_len // (lua_State *L, TValue *o) | 1067 | | bl extern lj_meta_len // (lua_State *L, TValue *o) |
| @@ -941,7 +1080,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 941 | |->vmeta_call: // Resolve and call __call metamethod. | 1080 | |->vmeta_call: // Resolve and call __call metamethod. |
| 942 | | // TMP2 = old base, BASE = new base, RC = nargs*8 | 1081 | | // TMP2 = old base, BASE = new base, RC = nargs*8 |
| 943 | | mr CARG1, L | 1082 | | mr CARG1, L |
| 944 | | stw TMP2, L->base // This is the callers base! | 1083 | | stp TMP2, L->base // This is the callers base! |
| 945 | | subi CARG2, BASE, 8 | 1084 | | subi CARG2, BASE, 8 |
| 946 | | stw PC, SAVE_PC | 1085 | | stw PC, SAVE_PC |
| 947 | | add CARG3, BASE, RC | 1086 | | add CARG3, BASE, RC |
| @@ -954,7 +1093,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 954 | |->vmeta_callt: // Resolve __call for BC_CALLT. | 1093 | |->vmeta_callt: // Resolve __call for BC_CALLT. |
| 955 | | // BASE = old base, RA = new base, RC = nargs*8 | 1094 | | // BASE = old base, RA = new base, RC = nargs*8 |
| 956 | | mr CARG1, L | 1095 | | mr CARG1, L |
| 957 | | stw BASE, L->base | 1096 | | stp BASE, L->base |
| 958 | | subi CARG2, RA, 8 | 1097 | | subi CARG2, RA, 8 |
| 959 | | stw PC, SAVE_PC | 1098 | | stw PC, SAVE_PC |
| 960 | | add CARG3, RA, RC | 1099 | | add CARG3, RA, RC |
| @@ -969,7 +1108,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 969 | | | 1108 | | |
| 970 | |->vmeta_for: | 1109 | |->vmeta_for: |
| 971 | | mr CARG1, L | 1110 | | mr CARG1, L |
| 972 | | stw BASE, L->base | 1111 | | stp BASE, L->base |
| 973 | | mr CARG2, RA | 1112 | | mr CARG2, RA |
| 974 | | stw PC, SAVE_PC | 1113 | | stw PC, SAVE_PC |
| 975 | | mr SAVE0, INS | 1114 | | mr SAVE0, INS |
| @@ -1068,6 +1207,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 1068 | | cmplwi NARGS8:RC, 8 | 1207 | | cmplwi NARGS8:RC, 8 |
| 1069 | | lwz CARG1, 0(BASE) | 1208 | | lwz CARG1, 0(BASE) |
| 1070 | | blt ->fff_fallback | 1209 | | blt ->fff_fallback |
| 1210 | | .gpr64 extsw CARG1, CARG1 | ||
| 1071 | | subfc TMP0, TISNUM, CARG1 | 1211 | | subfc TMP0, TISNUM, CARG1 |
| 1072 | | subfe TMP2, CARG1, CARG1 | 1212 | | subfe TMP2, CARG1, CARG1 |
| 1073 | | orc TMP1, TMP2, TMP0 | 1213 | | orc TMP1, TMP2, TMP0 |
| @@ -1118,6 +1258,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 1118 | | | 1258 | | |
| 1119 | |6: | 1259 | |6: |
| 1120 | | cmpwi CARG3, LJ_TUDATA; beq <1 | 1260 | | cmpwi CARG3, LJ_TUDATA; beq <1 |
| 1261 | | .gpr64 extsw CARG3, CARG3 | ||
| 1121 | | subfc TMP0, TISNUM, CARG3 | 1262 | | subfc TMP0, TISNUM, CARG3 |
| 1122 | | subfe TMP2, CARG3, CARG3 | 1263 | | subfe TMP2, CARG3, CARG3 |
| 1123 | | orc TMP1, TMP2, TMP0 | 1264 | | orc TMP1, TMP2, TMP0 |
| @@ -1135,7 +1276,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 1135 | | cmplwi TAB:TMP1, 0 | 1276 | | cmplwi TAB:TMP1, 0 |
| 1136 | | lbz TMP3, TAB:CARG1->marked | 1277 | | lbz TMP3, TAB:CARG1->marked |
| 1137 | | bne ->fff_fallback | 1278 | | bne ->fff_fallback |
| 1138 | | andi. TMP0, TMP3, LJ_GC_BLACK // isblack(table) | 1279 | | andix. TMP0, TMP3, LJ_GC_BLACK // isblack(table) |
| 1139 | | stw TAB:CARG2, TAB:CARG1->metatable | 1280 | | stw TAB:CARG2, TAB:CARG1->metatable |
| 1140 | | beq ->fff_restv | 1281 | | beq ->fff_restv |
| 1141 | | barrierback TAB:CARG1, TMP3, TMP0 | 1282 | | barrierback TAB:CARG1, TMP3, TMP0 |
| @@ -1174,7 +1315,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 1174 | | lwz TMP0, DISPATCH_GL(gcroot[GCROOT_BASEMT_NUM])(DISPATCH) | 1315 | | lwz TMP0, DISPATCH_GL(gcroot[GCROOT_BASEMT_NUM])(DISPATCH) |
| 1175 | | checknum CARG3 | 1316 | | checknum CARG3 |
| 1176 | | cmplwi cr1, TMP0, 0 | 1317 | | cmplwi cr1, TMP0, 0 |
| 1177 | | stw BASE, L->base // Add frame since C call can throw. | 1318 | | stp BASE, L->base // Add frame since C call can throw. |
| 1178 | | crorc 4*cr0+eq, 4*cr0+gt, 4*cr1+eq | 1319 | | crorc 4*cr0+eq, 4*cr0+gt, 4*cr1+eq |
| 1179 | | stw PC, SAVE_PC // Redundant (but a defined value). | 1320 | | stw PC, SAVE_PC // Redundant (but a defined value). |
| 1180 | | beq ->fff_fallback | 1321 | | beq ->fff_fallback |
| @@ -1201,9 +1342,9 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 1201 | | checktab CARG1 | 1342 | | checktab CARG1 |
| 1202 | | lwz PC, FRAME_PC(BASE) | 1343 | | lwz PC, FRAME_PC(BASE) |
| 1203 | | bne ->fff_fallback | 1344 | | bne ->fff_fallback |
| 1204 | | stw BASE, L->base // Add frame since C call can throw. | 1345 | | stp BASE, L->base // Add frame since C call can throw. |
| 1205 | | mr CARG1, L | 1346 | | mr CARG1, L |
| 1206 | | stw BASE, L->top // Dummy frame length is ok. | 1347 | | stp BASE, L->top // Dummy frame length is ok. |
| 1207 | | la CARG3, 8(BASE) | 1348 | | la CARG3, 8(BASE) |
| 1208 | | stw PC, SAVE_PC | 1349 | | stw PC, SAVE_PC |
| 1209 | | bl extern lj_tab_next // (lua_State *L, GCtab *t, TValue *key) | 1350 | | bl extern lj_tab_next // (lua_State *L, GCtab *t, TValue *key) |
| @@ -1372,10 +1513,10 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 1372 | | lwz L:CARG1, CFUNC:RB->upvalue[0].gcr | 1513 | | lwz L:CARG1, CFUNC:RB->upvalue[0].gcr |
| 1373 | |.endif | 1514 | |.endif |
| 1374 | | lbz TMP0, L:CARG1->status | 1515 | | lbz TMP0, L:CARG1->status |
| 1375 | | lwz TMP1, L:CARG1->cframe | 1516 | | lp TMP1, L:CARG1->cframe |
| 1376 | | lwz CARG2, L:CARG1->top | 1517 | | lp CARG2, L:CARG1->top |
| 1377 | | cmplwi cr0, TMP0, LUA_YIELD | 1518 | | cmplwi cr0, TMP0, LUA_YIELD |
| 1378 | | lwz TMP2, L:CARG1->base | 1519 | | lp TMP2, L:CARG1->base |
| 1379 | | cmplwi cr1, TMP1, 0 | 1520 | | cmplwi cr1, TMP1, 0 |
| 1380 | | lwz TMP0, L:CARG1->maxstack | 1521 | | lwz TMP0, L:CARG1->maxstack |
| 1381 | | cmplw cr7, CARG2, TMP2 | 1522 | | cmplw cr7, CARG2, TMP2 |
| @@ -1387,7 +1528,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 1387 | | cror 4*cr6+lt, 4*cr6+lt, 4*cr6+gt | 1528 | | cror 4*cr6+lt, 4*cr6+lt, 4*cr6+gt |
| 1388 | | stw PC, SAVE_PC | 1529 | | stw PC, SAVE_PC |
| 1389 | | cror 4*cr6+lt, 4*cr6+lt, 4*cr1+gt // cond1 || cond2 || stackov | 1530 | | cror 4*cr6+lt, 4*cr6+lt, 4*cr1+gt // cond1 || cond2 || stackov |
| 1390 | | stw BASE, L->base | 1531 | | stp BASE, L->base |
| 1391 | | blt cr6, ->fff_fallback | 1532 | | blt cr6, ->fff_fallback |
| 1392 | |1: | 1533 | |1: |
| 1393 | |.if resume | 1534 | |.if resume |
| @@ -1395,9 +1536,9 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 1395 | | subi NARGS8:RC, NARGS8:RC, 8 | 1536 | | subi NARGS8:RC, NARGS8:RC, 8 |
| 1396 | | subi TMP2, TMP2, 8 | 1537 | | subi TMP2, TMP2, 8 |
| 1397 | |.endif | 1538 | |.endif |
| 1398 | | stw TMP2, L:CARG1->top | 1539 | | stp TMP2, L:CARG1->top |
| 1399 | | li TMP1, 0 | 1540 | | li TMP1, 0 |
| 1400 | | stw BASE, L->top | 1541 | | stp BASE, L->top |
| 1401 | |2: // Move args to coroutine. | 1542 | |2: // Move args to coroutine. |
| 1402 | | cmpw TMP1, NARGS8:RC | 1543 | | cmpw TMP1, NARGS8:RC |
| 1403 | | lfdx f0, BASE, TMP1 | 1544 | | lfdx f0, BASE, TMP1 |
| @@ -1412,11 +1553,11 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 1412 | | bl ->vm_resume // (lua_State *L, TValue *base, 0, 0) | 1553 | | bl ->vm_resume // (lua_State *L, TValue *base, 0, 0) |
| 1413 | | // Returns thread status. | 1554 | | // Returns thread status. |
| 1414 | |4: | 1555 | |4: |
| 1415 | | lwz TMP2, L:SAVE0->base | 1556 | | lp TMP2, L:SAVE0->base |
| 1416 | | cmplwi CRET1, LUA_YIELD | 1557 | | cmplwi CRET1, LUA_YIELD |
| 1417 | | lwz TMP3, L:SAVE0->top | 1558 | | lp TMP3, L:SAVE0->top |
| 1418 | | li_vmstate INTERP | 1559 | | li_vmstate INTERP |
| 1419 | | lwz BASE, L->base | 1560 | | lp BASE, L->base |
| 1420 | | st_vmstate | 1561 | | st_vmstate |
| 1421 | | bgt >8 | 1562 | | bgt >8 |
| 1422 | | sub RD, TMP3, TMP2 | 1563 | | sub RD, TMP3, TMP2 |
| @@ -1429,7 +1570,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 1429 | | bgt >9 // Need to grow stack? | 1570 | | bgt >9 // Need to grow stack? |
| 1430 | | | 1571 | | |
| 1431 | | subi TMP3, RD, 8 | 1572 | | subi TMP3, RD, 8 |
| 1432 | | stw TMP2, L:SAVE0->top // Clear coroutine stack. | 1573 | | stp TMP2, L:SAVE0->top // Clear coroutine stack. |
| 1433 | |5: // Move results from coroutine. | 1574 | |5: // Move results from coroutine. |
| 1434 | | cmplw TMP1, TMP3 | 1575 | | cmplw TMP1, TMP3 |
| 1435 | | lfdx f0, TMP2, TMP1 | 1576 | | lfdx f0, TMP2, TMP1 |
| @@ -1437,7 +1578,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 1437 | | addi TMP1, TMP1, 8 | 1578 | | addi TMP1, TMP1, 8 |
| 1438 | | bne <5 | 1579 | | bne <5 |
| 1439 | |6: | 1580 | |6: |
| 1440 | | andi. TMP0, PC, FRAME_TYPE | 1581 | | andix. TMP0, PC, FRAME_TYPE |
| 1441 | |.if resume | 1582 | |.if resume |
| 1442 | | li TMP1, LJ_TTRUE | 1583 | | li TMP1, LJ_TTRUE |
| 1443 | | la RA, -8(BASE) | 1584 | | la RA, -8(BASE) |
| @@ -1455,11 +1596,11 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 1455 | | | 1596 | | |
| 1456 | |8: // Coroutine returned with error (at co->top-1). | 1597 | |8: // Coroutine returned with error (at co->top-1). |
| 1457 | |.if resume | 1598 | |.if resume |
| 1458 | | andi. TMP0, PC, FRAME_TYPE | 1599 | | andix. TMP0, PC, FRAME_TYPE |
| 1459 | | la TMP3, -8(TMP3) | 1600 | | la TMP3, -8(TMP3) |
| 1460 | | li TMP1, LJ_TFALSE | 1601 | | li TMP1, LJ_TFALSE |
| 1461 | | lfd f0, 0(TMP3) | 1602 | | lfd f0, 0(TMP3) |
| 1462 | | stw TMP3, L:SAVE0->top // Remove error from coroutine stack. | 1603 | | stp TMP3, L:SAVE0->top // Remove error from coroutine stack. |
| 1463 | | li RD, (2+1)*8 | 1604 | | li RD, (2+1)*8 |
| 1464 | | stw TMP1, -8(BASE) // Prepend false to results. | 1605 | | stw TMP1, -8(BASE) // Prepend false to results. |
| 1465 | | la RA, -8(BASE) | 1606 | | la RA, -8(BASE) |
| @@ -1483,14 +1624,14 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 1483 | | coroutine_resume_wrap 0 // coroutine.wrap | 1624 | | coroutine_resume_wrap 0 // coroutine.wrap |
| 1484 | | | 1625 | | |
| 1485 | |.ffunc coroutine_yield | 1626 | |.ffunc coroutine_yield |
| 1486 | | lwz TMP0, L->cframe | 1627 | | lp TMP0, L->cframe |
| 1487 | | add TMP1, BASE, NARGS8:RC | 1628 | | add TMP1, BASE, NARGS8:RC |
| 1488 | | stw BASE, L->base | 1629 | | stp BASE, L->base |
| 1489 | | andi. TMP0, TMP0, CFRAME_RESUME | 1630 | | andix. TMP0, TMP0, CFRAME_RESUME |
| 1490 | | stw TMP1, L->top | 1631 | | stp TMP1, L->top |
| 1491 | | li CRET1, LUA_YIELD | 1632 | | li CRET1, LUA_YIELD |
| 1492 | | beq ->fff_fallback | 1633 | | beq ->fff_fallback |
| 1493 | | stw ZERO, L->cframe | 1634 | | stp ZERO, L->cframe |
| 1494 | | stb CRET1, L->status | 1635 | | stb CRET1, L->status |
| 1495 | | b ->vm_leave_unw | 1636 | | b ->vm_leave_unw |
| 1496 | | | 1637 | | |
| @@ -1502,8 +1643,15 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 1502 | | bne >2 | 1643 | | bne >2 |
| 1503 | | srawi TMP1, CARG1, 31 | 1644 | | srawi TMP1, CARG1, 31 |
| 1504 | | xor TMP2, TMP1, CARG1 | 1645 | | xor TMP2, TMP1, CARG1 |
| 1646 | |.if GPR64 | ||
| 1647 | | lus TMP0, 0x8000 | ||
| 1648 | | sub CARG1, TMP2, TMP1 | ||
| 1649 | | cmplw CARG1, TMP0 | ||
| 1650 | | beq >1 | ||
| 1651 | |.else | ||
| 1505 | | sub. CARG1, TMP2, TMP1 | 1652 | | sub. CARG1, TMP2, TMP1 |
| 1506 | | blt >1 | 1653 | | blt >1 |
| 1654 | |.endif | ||
| 1507 | |->fff_resi: | 1655 | |->fff_resi: |
| 1508 | | lwz PC, FRAME_PC(BASE) | 1656 | | lwz PC, FRAME_PC(BASE) |
| 1509 | | la RA, -8(BASE) | 1657 | | la RA, -8(BASE) |
| @@ -1531,7 +1679,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 1531 | | li RD, (1+1)*8 | 1679 | | li RD, (1+1)*8 |
| 1532 | |->fff_res: | 1680 | |->fff_res: |
| 1533 | | // RA = results, RD = (nresults+1)*8, PC = return. | 1681 | | // RA = results, RD = (nresults+1)*8, PC = return. |
| 1534 | | andi. TMP0, PC, FRAME_TYPE | 1682 | | andix. TMP0, PC, FRAME_TYPE |
| 1535 | | mr MULTRES, RD | 1683 | | mr MULTRES, RD |
| 1536 | | bney ->vm_return | 1684 | | bney ->vm_return |
| 1537 | | lwz INS, -4(PC) | 1685 | | lwz INS, -4(PC) |
| @@ -1553,13 +1701,13 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 1553 | | | 1701 | | |
| 1554 | |.macro math_extern, func | 1702 | |.macro math_extern, func |
| 1555 | | .ffunc_n math_ .. func | 1703 | | .ffunc_n math_ .. func |
| 1556 | | bl extern func | 1704 | | blex func |
| 1557 | | b ->fff_resn | 1705 | | b ->fff_resn |
| 1558 | |.endmacro | 1706 | |.endmacro |
| 1559 | | | 1707 | | |
| 1560 | |.macro math_extern2, func | 1708 | |.macro math_extern2, func |
| 1561 | | .ffunc_nn math_ .. func | 1709 | | .ffunc_nn math_ .. func |
| 1562 | | bl extern func | 1710 | | blex func |
| 1563 | | b ->fff_resn | 1711 | | b ->fff_resn |
| 1564 | |.endmacro | 1712 | |.endmacro |
| 1565 | | | 1713 | | |
| @@ -1580,14 +1728,14 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 1580 | | slwi CARG2, CARG1, 11 | 1728 | | slwi CARG2, CARG1, 11 |
| 1581 | | bge cr1, >4 | 1729 | | bge cr1, >4 |
| 1582 | | slw TMP3, TMP1, TMP2 | 1730 | | slw TMP3, TMP1, TMP2 |
| 1583 | | srw CARG1, TMP1, TMP0 | 1731 | | srw RD, TMP1, TMP0 |
| 1584 | | or TMP3, TMP3, CARG2 | 1732 | | or TMP3, TMP3, CARG2 |
| 1585 | | srawi TMP2, CARG3, 31 | 1733 | | srawi TMP2, CARG3, 31 |
| 1586 | |.if "func" == "floor" | 1734 | |.if "func" == "floor" |
| 1587 | | and TMP1, TMP3, TMP2 | 1735 | | and TMP1, TMP3, TMP2 |
| 1588 | | addic TMP0, TMP1, -1 | 1736 | | addic TMP0, TMP1, -1 |
| 1589 | | subfe TMP1, TMP0, TMP1 | 1737 | | subfe TMP1, TMP0, TMP1 |
| 1590 | | add CARG1, CARG1, TMP1 | 1738 | | add CARG1, RD, TMP1 |
| 1591 | | xor CARG1, CARG1, TMP2 | 1739 | | xor CARG1, CARG1, TMP2 |
| 1592 | | sub CARG1, CARG1, TMP2 | 1740 | | sub CARG1, CARG1, TMP2 |
| 1593 | | b ->fff_resi | 1741 | | b ->fff_resi |
| @@ -1595,18 +1743,18 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 1595 | | andc TMP1, TMP3, TMP2 | 1743 | | andc TMP1, TMP3, TMP2 |
| 1596 | | addic TMP0, TMP1, -1 | 1744 | | addic TMP0, TMP1, -1 |
| 1597 | | subfe TMP1, TMP0, TMP1 | 1745 | | subfe TMP1, TMP0, TMP1 |
| 1598 | | addo. CARG1, CARG1, TMP1 | 1746 | | add CARG1, RD, TMP1 |
| 1747 | | cmpw CARG1, RD | ||
| 1599 | | xor CARG1, CARG1, TMP2 | 1748 | | xor CARG1, CARG1, TMP2 |
| 1600 | | sub CARG1, CARG1, TMP2 | 1749 | | sub CARG1, CARG1, TMP2 |
| 1601 | | bns ->fff_resi | 1750 | | bge ->fff_resi |
| 1602 | | // Potential overflow. | 1751 | | // Overflow to 2^31. |
| 1603 | | mcrxr cr0; bley ->fff_resi // Ignore unrelated overflow. | ||
| 1604 | | lus CARG3, 0x41e0 // 2^31. | 1752 | | lus CARG3, 0x41e0 // 2^31. |
| 1605 | | li CARG1, 0 | 1753 | | li CARG1, 0 |
| 1606 | | b ->fff_restv | 1754 | | b ->fff_restv |
| 1607 | |.endif | 1755 | |.endif |
| 1608 | |3: // |x| < 1 | 1756 | |3: // |x| < 1 |
| 1609 | | add TMP2, CARG3, CARG3 | 1757 | | slwi TMP2, CARG3, 1 |
| 1610 | | srawi TMP1, CARG3, 31 | 1758 | | srawi TMP1, CARG3, 31 |
| 1611 | | or TMP2, CARG1, TMP2 // ztest = (hi+hi) | lo | 1759 | | or TMP2, CARG1, TMP2 // ztest = (hi+hi) | lo |
| 1612 | |.if "func" == "floor" | 1760 | |.if "func" == "floor" |
| @@ -1625,13 +1773,18 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 1625 | |.if "func" == "floor" | 1773 | |.if "func" == "floor" |
| 1626 | | or TMP1, TMP1, CARG2 | 1774 | | or TMP1, TMP1, CARG2 |
| 1627 | |.endif | 1775 | |.endif |
| 1776 | |.if PPE | ||
| 1777 | | orc TMP1, TMP1, TMP2 | ||
| 1778 | | cmpwi TMP1, 0 | ||
| 1779 | |.else | ||
| 1628 | | orc. TMP1, TMP1, TMP2 | 1780 | | orc. TMP1, TMP1, TMP2 |
| 1781 | |.endif | ||
| 1629 | | crand 4*cr0+eq, 4*cr0+eq, 4*cr1+eq | 1782 | | crand 4*cr0+eq, 4*cr0+eq, 4*cr1+eq |
| 1630 | | lus CARG1, 0x8000 // -(2^31). | 1783 | | lus CARG1, 0x8000 // -(2^31). |
| 1631 | | beqy ->fff_resi | 1784 | | beqy ->fff_resi |
| 1632 | |5: | 1785 | |5: |
| 1633 | | lfd FARG1, 0(BASE) | 1786 | | lfd FARG1, 0(BASE) |
| 1634 | | bl extern func | 1787 | | blex func |
| 1635 | | b ->fff_resn | 1788 | | b ->fff_resn |
| 1636 | |.endmacro | 1789 | |.endmacro |
| 1637 | | | 1790 | | |
| @@ -1644,7 +1797,13 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 1644 | | math_extern ceil | 1797 | | math_extern ceil |
| 1645 | |.endif | 1798 | |.endif |
| 1646 | | | 1799 | | |
| 1800 | |.if SQRT | ||
| 1801 | |.ffunc_n math_sqrt | ||
| 1802 | | fsqrt FARG1, FARG1 | ||
| 1803 | | b ->fff_resn | ||
| 1804 | |.else | ||
| 1647 | | math_extern sqrt | 1805 | | math_extern sqrt |
| 1806 | |.endif | ||
| 1648 | | math_extern log | 1807 | | math_extern log |
| 1649 | | math_extern log10 | 1808 | | math_extern log10 |
| 1650 | | math_extern exp | 1809 | | math_extern exp |
| @@ -1673,21 +1832,33 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 1673 | | lwz CARG3, 0(BASE) | 1832 | | lwz CARG3, 0(BASE) |
| 1674 | | lfd FARG1, 0(BASE) | 1833 | | lfd FARG1, 0(BASE) |
| 1675 | | lwz CARG4, 8(BASE) | 1834 | | lwz CARG4, 8(BASE) |
| 1835 | |.if GPR64 | ||
| 1836 | | lwz CARG2, 12(BASE) | ||
| 1837 | |.else | ||
| 1676 | | lwz CARG1, 12(BASE) | 1838 | | lwz CARG1, 12(BASE) |
| 1839 | |.endif | ||
| 1677 | | blt ->fff_fallback | 1840 | | blt ->fff_fallback |
| 1678 | | checknum CARG3; bge ->fff_fallback | 1841 | | checknum CARG3; bge ->fff_fallback |
| 1679 | | checknum CARG4; bne ->fff_fallback | 1842 | | checknum CARG4; bne ->fff_fallback |
| 1680 | |.else | 1843 | |.else |
| 1681 | |.ffunc_nn math_ldexp | 1844 | |.ffunc_nn math_ldexp |
| 1845 | |.if GPR64 | ||
| 1846 | | toint CARG2, FARG2 | ||
| 1847 | |.else | ||
| 1682 | | toint CARG1, FARG2 | 1848 | | toint CARG1, FARG2 |
| 1683 | |.endif | 1849 | |.endif |
| 1684 | | bl extern ldexp | 1850 | |.endif |
| 1851 | | blex ldexp | ||
| 1685 | | b ->fff_resn | 1852 | | b ->fff_resn |
| 1686 | | | 1853 | | |
| 1687 | |.ffunc_n math_frexp | 1854 | |.ffunc_n math_frexp |
| 1855 | |.if GPR64 | ||
| 1856 | | la CARG2, DISPATCH_GL(tmptv)(DISPATCH) | ||
| 1857 | |.else | ||
| 1688 | | la CARG1, DISPATCH_GL(tmptv)(DISPATCH) | 1858 | | la CARG1, DISPATCH_GL(tmptv)(DISPATCH) |
| 1859 | |.endif | ||
| 1689 | | lwz PC, FRAME_PC(BASE) | 1860 | | lwz PC, FRAME_PC(BASE) |
| 1690 | | bl extern frexp | 1861 | | blex frexp |
| 1691 | | lwz TMP1, DISPATCH_GL(tmptv)(DISPATCH) | 1862 | | lwz TMP1, DISPATCH_GL(tmptv)(DISPATCH) |
| 1692 | | la RA, -8(BASE) | 1863 | | la RA, -8(BASE) |
| 1693 | |.if not DUALNUM | 1864 | |.if not DUALNUM |
| @@ -1704,9 +1875,13 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 1704 | | b ->fff_res | 1875 | | b ->fff_res |
| 1705 | | | 1876 | | |
| 1706 | |.ffunc_n math_modf | 1877 | |.ffunc_n math_modf |
| 1878 | |.if GPR64 | ||
| 1879 | | la CARG2, -8(BASE) | ||
| 1880 | |.else | ||
| 1707 | | la CARG1, -8(BASE) | 1881 | | la CARG1, -8(BASE) |
| 1882 | |.endif | ||
| 1708 | | lwz PC, FRAME_PC(BASE) | 1883 | | lwz PC, FRAME_PC(BASE) |
| 1709 | | bl extern modf | 1884 | | blex modf |
| 1710 | | la RA, -8(BASE) | 1885 | | la RA, -8(BASE) |
| 1711 | | stfd FARG1, 0(BASE) | 1886 | | stfd FARG1, 0(BASE) |
| 1712 | | li RD, (2+1)*8 | 1887 | | li RD, (2+1)*8 |
| @@ -1736,6 +1911,9 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 1736 | | and TMP3, TMP3, TMP0 | 1911 | | and TMP3, TMP3, TMP0 |
| 1737 | |.endif | 1912 | |.endif |
| 1738 | | add CARG1, TMP3, CARG2 | 1913 | | add CARG1, TMP3, CARG2 |
| 1914 | |.if GPR64 | ||
| 1915 | | rldicl CARG1, CARG1, 0, 32 | ||
| 1916 | |.endif | ||
| 1739 | | addi TMP1, TMP1, 8 | 1917 | | addi TMP1, TMP1, 8 |
| 1740 | | b <1 | 1918 | | b <1 |
| 1741 | |3: | 1919 | |3: |
| @@ -1849,11 +2027,11 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 1849 | | cmplwi TMP0, 255; bgt ->fff_fallback | 2027 | | cmplwi TMP0, 255; bgt ->fff_fallback |
| 1850 | |->fff_newstr: | 2028 | |->fff_newstr: |
| 1851 | | mr CARG1, L | 2029 | | mr CARG1, L |
| 1852 | | stw BASE, L->base | 2030 | | stp BASE, L->base |
| 1853 | | stw PC, SAVE_PC | 2031 | | stw PC, SAVE_PC |
| 1854 | | bl extern lj_str_new // (lua_State *L, char *str, size_t l) | 2032 | | bl extern lj_str_new // (lua_State *L, char *str, size_t l) |
| 1855 | | // Returns GCstr *. | 2033 | | // Returns GCstr *. |
| 1856 | | lwz BASE, L->base | 2034 | | lp BASE, L->base |
| 1857 | | li CARG3, LJ_TSTR | 2035 | | li CARG3, LJ_TSTR |
| 1858 | | b ->fff_restv | 2036 | | b ->fff_restv |
| 1859 | | | 2037 | | |
| @@ -1906,6 +2084,10 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 1906 | | addi CARG3, CARG3, 1 | 2084 | | addi CARG3, CARG3, 1 |
| 1907 | | add CARG2, CARG2, TMP1 | 2085 | | add CARG2, CARG2, TMP1 |
| 1908 | | andc CARG3, CARG3, TMP0 | 2086 | | andc CARG3, CARG3, TMP0 |
| 2087 | |.if GPR64 | ||
| 2088 | | rldicl CARG2, CARG2, 0, 32 | ||
| 2089 | | rldicl CARG3, CARG3, 0, 32 | ||
| 2090 | |.endif | ||
| 1909 | | b ->fff_newstr | 2091 | | b ->fff_newstr |
| 1910 | | | 2092 | | |
| 1911 | |5: // Negative end or overflow. | 2093 | |5: // Negative end or overflow. |
| @@ -1916,6 +2098,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 1916 | | b <2 | 2098 | | b <2 |
| 1917 | | | 2099 | | |
| 1918 | |7: // Negative start or underflow. | 2100 | |7: // Negative start or underflow. |
| 2101 | | .gpr64 extsw TMP1, TMP1 | ||
| 1919 | | addic CARG3, TMP1, -1 | 2102 | | addic CARG3, TMP1, -1 |
| 1920 | | subfe CARG3, CARG3, CARG3 | 2103 | | subfe CARG3, CARG3, CARG3 |
| 1921 | | srawi CARG2, TMP3, 31 // Note: modifies carry. | 2104 | | srawi CARG2, TMP3, 31 // Note: modifies carry. |
| @@ -1953,7 +2136,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 1953 | | cmplw cr1, TMP1, CARG3 | 2136 | | cmplw cr1, TMP1, CARG3 |
| 1954 | | bne ->fff_fallback // Fallback for > 1-char strings. | 2137 | | bne ->fff_fallback // Fallback for > 1-char strings. |
| 1955 | | lbz TMP0, STR:CARG1[1] | 2138 | | lbz TMP0, STR:CARG1[1] |
| 1956 | | lwz CARG2, DISPATCH_GL(tmpbuf.buf)(DISPATCH) | 2139 | | lp CARG2, DISPATCH_GL(tmpbuf.buf)(DISPATCH) |
| 1957 | | blt cr1, ->fff_fallback | 2140 | | blt cr1, ->fff_fallback |
| 1958 | |1: // Fill buffer with char. Yes, this is suboptimal code (do you care?). | 2141 | |1: // Fill buffer with char. Yes, this is suboptimal code (do you care?). |
| 1959 | | cmplwi TMP2, 0 | 2142 | | cmplwi TMP2, 0 |
| @@ -1977,7 +2160,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 1977 | | bne ->fff_fallback | 2160 | | bne ->fff_fallback |
| 1978 | | lwz CARG3, STR:CARG1->len | 2161 | | lwz CARG3, STR:CARG1->len |
| 1979 | | la CARG1, #STR(STR:CARG1) | 2162 | | la CARG1, #STR(STR:CARG1) |
| 1980 | | lwz CARG2, DISPATCH_GL(tmpbuf.buf)(DISPATCH) | 2163 | | lp CARG2, DISPATCH_GL(tmpbuf.buf)(DISPATCH) |
| 1981 | | li TMP2, 0 | 2164 | | li TMP2, 0 |
| 1982 | | cmplw TMP1, CARG3 | 2165 | | cmplw TMP1, CARG3 |
| 1983 | | subi TMP3, CARG3, 1 | 2166 | | subi TMP3, CARG3, 1 |
| @@ -2003,7 +2186,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 2003 | | bne ->fff_fallback | 2186 | | bne ->fff_fallback |
| 2004 | | lwz CARG3, STR:CARG1->len | 2187 | | lwz CARG3, STR:CARG1->len |
| 2005 | | la CARG1, #STR(STR:CARG1) | 2188 | | la CARG1, #STR(STR:CARG1) |
| 2006 | | lwz CARG2, DISPATCH_GL(tmpbuf.buf)(DISPATCH) | 2189 | | lp CARG2, DISPATCH_GL(tmpbuf.buf)(DISPATCH) |
| 2007 | | cmplw TMP1, CARG3 | 2190 | | cmplw TMP1, CARG3 |
| 2008 | | li TMP2, 0 | 2191 | | li TMP2, 0 |
| 2009 | | blt ->fff_fallback | 2192 | | blt ->fff_fallback |
| @@ -2015,7 +2198,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 2015 | | xori TMP3, TMP1, 0x20 | 2198 | | xori TMP3, TMP1, 0x20 |
| 2016 | | addic TMP0, TMP0, -26 | 2199 | | addic TMP0, TMP0, -26 |
| 2017 | | subfe TMP3, TMP3, TMP3 | 2200 | | subfe TMP3, TMP3, TMP3 |
| 2018 | | andi. TMP3, TMP3, 0x20 | 2201 | | rlwinm TMP3, TMP3, 0, 26, 26 // x &= 0x20. |
| 2019 | | xor TMP1, TMP1, TMP3 | 2202 | | xor TMP1, TMP1, TMP3 |
| 2020 | | stbx TMP1, CARG2, TMP2 | 2203 | | stbx TMP1, CARG2, TMP2 |
| 2021 | | addi TMP2, TMP2, 1 | 2204 | | addi TMP2, TMP2, 1 |
| @@ -2156,27 +2339,28 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 2156 | | | 2339 | | |
| 2157 | |->fff_fallback: // Call fast function fallback handler. | 2340 | |->fff_fallback: // Call fast function fallback handler. |
| 2158 | | // BASE = new base, RB = CFUNC, RC = nargs*8 | 2341 | | // BASE = new base, RB = CFUNC, RC = nargs*8 |
| 2159 | | lwz TMP3, CFUNC:RB->f | 2342 | | lp TMP3, CFUNC:RB->f |
| 2160 | | add TMP1, BASE, NARGS8:RC | 2343 | | add TMP1, BASE, NARGS8:RC |
| 2161 | | lwz PC, FRAME_PC(BASE) // Fallback may overwrite PC. | 2344 | | lwz PC, FRAME_PC(BASE) // Fallback may overwrite PC. |
| 2162 | | addi TMP0, TMP1, 8*LUA_MINSTACK | 2345 | | addi TMP0, TMP1, 8*LUA_MINSTACK |
| 2163 | | lwz TMP2, L->maxstack | 2346 | | lwz TMP2, L->maxstack |
| 2164 | | stw PC, SAVE_PC // Redundant (but a defined value). | 2347 | | stw PC, SAVE_PC // Redundant (but a defined value). |
| 2348 | | .toc lp TMP3, 0(TMP3) | ||
| 2165 | | cmplw TMP0, TMP2 | 2349 | | cmplw TMP0, TMP2 |
| 2166 | | stw BASE, L->base | 2350 | | stp BASE, L->base |
| 2167 | | stw TMP1, L->top | 2351 | | stp TMP1, L->top |
| 2168 | | mr CARG1, L | 2352 | | mr CARG1, L |
| 2169 | | bgt >5 // Need to grow stack. | 2353 | | bgt >5 // Need to grow stack. |
| 2170 | | mtctr TMP3 | 2354 | | mtctr TMP3 |
| 2171 | | bctrl // (lua_State *L) | 2355 | | bctrl // (lua_State *L) |
| 2172 | | // Either throws an error, or recovers and returns -1, 0 or nresults+1. | 2356 | | // Either throws an error, or recovers and returns -1, 0 or nresults+1. |
| 2173 | | lwz BASE, L->base | 2357 | | lp BASE, L->base |
| 2174 | | cmpwi CRET1, 0 | 2358 | | cmpwi CRET1, 0 |
| 2175 | | slwi RD, CRET1, 3 | 2359 | | slwi RD, CRET1, 3 |
| 2176 | | la RA, -8(BASE) | 2360 | | la RA, -8(BASE) |
| 2177 | | bgt ->fff_res // Returned nresults+1? | 2361 | | bgt ->fff_res // Returned nresults+1? |
| 2178 | |1: // Returned 0 or -1: retry fast path. | 2362 | |1: // Returned 0 or -1: retry fast path. |
| 2179 | | lwz TMP0, L->top | 2363 | | lp TMP0, L->top |
| 2180 | | lwz LFUNC:RB, FRAME_FUNC(BASE) | 2364 | | lwz LFUNC:RB, FRAME_FUNC(BASE) |
| 2181 | | sub NARGS8:RC, TMP0, BASE | 2365 | | sub NARGS8:RC, TMP0, BASE |
| 2182 | | bne ->vm_call_tail // Returned -1? | 2366 | | bne ->vm_call_tail // Returned -1? |
| @@ -2184,7 +2368,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 2184 | | | 2368 | | |
| 2185 | |// Reconstruct previous base for vmeta_call during tailcall. | 2369 | |// Reconstruct previous base for vmeta_call during tailcall. |
| 2186 | |->vm_call_tail: | 2370 | |->vm_call_tail: |
| 2187 | | andi. TMP0, PC, FRAME_TYPE | 2371 | | andix. TMP0, PC, FRAME_TYPE |
| 2188 | | rlwinm TMP1, PC, 0, 0, 28 | 2372 | | rlwinm TMP1, PC, 0, 0, 28 |
| 2189 | | bne >3 | 2373 | | bne >3 |
| 2190 | | lwz INS, -4(PC) | 2374 | | lwz INS, -4(PC) |
| @@ -2197,22 +2381,22 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 2197 | |5: // Grow stack for fallback handler. | 2381 | |5: // Grow stack for fallback handler. |
| 2198 | | li CARG2, LUA_MINSTACK | 2382 | | li CARG2, LUA_MINSTACK |
| 2199 | | bl extern lj_state_growstack // (lua_State *L, int n) | 2383 | | bl extern lj_state_growstack // (lua_State *L, int n) |
| 2200 | | lwz BASE, L->base | 2384 | | lp BASE, L->base |
| 2201 | | cmpw TMP0, TMP0 // Set 4*cr0+eq to force retry. | 2385 | | cmpw TMP0, TMP0 // Set 4*cr0+eq to force retry. |
| 2202 | | b <1 | 2386 | | b <1 |
| 2203 | | | 2387 | | |
| 2204 | |->fff_gcstep: // Call GC step function. | 2388 | |->fff_gcstep: // Call GC step function. |
| 2205 | | // BASE = new base, RC = nargs*8 | 2389 | | // BASE = new base, RC = nargs*8 |
| 2206 | | mflr SAVE0 | 2390 | | mflr SAVE0 |
| 2207 | | stw BASE, L->base | 2391 | | stp BASE, L->base |
| 2208 | | add TMP0, BASE, NARGS8:RC | 2392 | | add TMP0, BASE, NARGS8:RC |
| 2209 | | stw PC, SAVE_PC // Redundant (but a defined value). | 2393 | | stw PC, SAVE_PC // Redundant (but a defined value). |
| 2210 | | stw TMP0, L->top | 2394 | | stp TMP0, L->top |
| 2211 | | mr CARG1, L | 2395 | | mr CARG1, L |
| 2212 | | bl extern lj_gc_step // (lua_State *L) | 2396 | | bl extern lj_gc_step // (lua_State *L) |
| 2213 | | lwz BASE, L->base | 2397 | | lp BASE, L->base |
| 2214 | | mtlr SAVE0 | 2398 | | mtlr SAVE0 |
| 2215 | | lwz TMP0, L->top | 2399 | | lp TMP0, L->top |
| 2216 | | sub NARGS8:RC, TMP0, BASE | 2400 | | sub NARGS8:RC, TMP0, BASE |
| 2217 | | lwz CFUNC:RB, FRAME_FUNC(BASE) | 2401 | | lwz CFUNC:RB, FRAME_FUNC(BASE) |
| 2218 | | blr | 2402 | | blr |
| @@ -2224,11 +2408,11 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 2224 | |->vm_record: // Dispatch target for recording phase. | 2408 | |->vm_record: // Dispatch target for recording phase. |
| 2225 | |.if JIT | 2409 | |.if JIT |
| 2226 | | lbz TMP3, DISPATCH_GL(hookmask)(DISPATCH) | 2410 | | lbz TMP3, DISPATCH_GL(hookmask)(DISPATCH) |
| 2227 | | andi. TMP0, TMP3, HOOK_VMEVENT // No recording while in vmevent. | 2411 | | andix. TMP0, TMP3, HOOK_VMEVENT // No recording while in vmevent. |
| 2228 | | bne >5 | 2412 | | bne >5 |
| 2229 | | // Decrement the hookcount for consistency, but always do the call. | 2413 | | // Decrement the hookcount for consistency, but always do the call. |
| 2230 | | lwz TMP2, DISPATCH_GL(hookcount)(DISPATCH) | 2414 | | lwz TMP2, DISPATCH_GL(hookcount)(DISPATCH) |
| 2231 | | andi. TMP0, TMP3, HOOK_ACTIVE | 2415 | | andix. TMP0, TMP3, HOOK_ACTIVE |
| 2232 | | bne >1 | 2416 | | bne >1 |
| 2233 | | subi TMP2, TMP2, 1 | 2417 | | subi TMP2, TMP2, 1 |
| 2234 | | andi. TMP0, TMP3, LUA_MASKLINE|LUA_MASKCOUNT | 2418 | | andi. TMP0, TMP3, LUA_MASKLINE|LUA_MASKCOUNT |
| @@ -2239,18 +2423,18 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 2239 | | | 2423 | | |
| 2240 | |->vm_rethook: // Dispatch target for return hooks. | 2424 | |->vm_rethook: // Dispatch target for return hooks. |
| 2241 | | lbz TMP3, DISPATCH_GL(hookmask)(DISPATCH) | 2425 | | lbz TMP3, DISPATCH_GL(hookmask)(DISPATCH) |
| 2242 | | andi. TMP0, TMP3, HOOK_ACTIVE // Hook already active? | 2426 | | andix. TMP0, TMP3, HOOK_ACTIVE // Hook already active? |
| 2243 | | beq >1 | 2427 | | beq >1 |
| 2244 | |5: // Re-dispatch to static ins. | 2428 | |5: // Re-dispatch to static ins. |
| 2245 | | addi TMP1, TMP1, GG_DISP2STATIC // Assumes decode_OP4 TMP1, INS. | 2429 | | addi TMP1, TMP1, GG_DISP2STATIC // Assumes decode_OPP TMP1, INS. |
| 2246 | | lwzx TMP0, DISPATCH, TMP1 | 2430 | | lpx TMP0, DISPATCH, TMP1 |
| 2247 | | mtctr TMP0 | 2431 | | mtctr TMP0 |
| 2248 | | bctr | 2432 | | bctr |
| 2249 | | | 2433 | | |
| 2250 | |->vm_inshook: // Dispatch target for instr/line hooks. | 2434 | |->vm_inshook: // Dispatch target for instr/line hooks. |
| 2251 | | lbz TMP3, DISPATCH_GL(hookmask)(DISPATCH) | 2435 | | lbz TMP3, DISPATCH_GL(hookmask)(DISPATCH) |
| 2252 | | lwz TMP2, DISPATCH_GL(hookcount)(DISPATCH) | 2436 | | lwz TMP2, DISPATCH_GL(hookcount)(DISPATCH) |
| 2253 | | andi. TMP0, TMP3, HOOK_ACTIVE // Hook already active? | 2437 | | andix. TMP0, TMP3, HOOK_ACTIVE // Hook already active? |
| 2254 | | rlwinm TMP0, TMP3, 31-LUA_HOOKLINE, 31, 0 | 2438 | | rlwinm TMP0, TMP3, 31-LUA_HOOKLINE, 31, 0 |
| 2255 | | bne <5 | 2439 | | bne <5 |
| 2256 | | | 2440 | | |
| @@ -2264,18 +2448,18 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 2264 | | mr CARG1, L | 2448 | | mr CARG1, L |
| 2265 | | stw MULTRES, SAVE_MULTRES | 2449 | | stw MULTRES, SAVE_MULTRES |
| 2266 | | mr CARG2, PC | 2450 | | mr CARG2, PC |
| 2267 | | stw BASE, L->base | 2451 | | stp BASE, L->base |
| 2268 | | // SAVE_PC must hold the _previous_ PC. The callee updates it with PC. | 2452 | | // SAVE_PC must hold the _previous_ PC. The callee updates it with PC. |
| 2269 | | bl extern lj_dispatch_ins // (lua_State *L, const BCIns *pc) | 2453 | | bl extern lj_dispatch_ins // (lua_State *L, const BCIns *pc) |
| 2270 | |3: | 2454 | |3: |
| 2271 | | lwz BASE, L->base | 2455 | | lp BASE, L->base |
| 2272 | |4: // Re-dispatch to static ins. | 2456 | |4: // Re-dispatch to static ins. |
| 2273 | | lwz INS, -4(PC) | 2457 | | lwz INS, -4(PC) |
| 2274 | | decode_OP4 TMP1, INS | 2458 | | decode_OPP TMP1, INS |
| 2275 | | decode_RB8 RB, INS | 2459 | | decode_RB8 RB, INS |
| 2276 | | addi TMP1, TMP1, GG_DISP2STATIC | 2460 | | addi TMP1, TMP1, GG_DISP2STATIC |
| 2277 | | decode_RD8 RD, INS | 2461 | | decode_RD8 RD, INS |
| 2278 | | lwzx TMP0, DISPATCH, TMP1 | 2462 | | lpx TMP0, DISPATCH, TMP1 |
| 2279 | | decode_RA8 RA, INS | 2463 | | decode_RA8 RA, INS |
| 2280 | | decode_RC8 RC, INS | 2464 | | decode_RC8 RC, INS |
| 2281 | | mtctr TMP0 | 2465 | | mtctr TMP0 |
| @@ -2295,10 +2479,10 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 2295 | | mr CARG2, PC | 2479 | | mr CARG2, PC |
| 2296 | | stw L, DISPATCH_J(L)(DISPATCH) | 2480 | | stw L, DISPATCH_J(L)(DISPATCH) |
| 2297 | | lbz TMP1, PC2PROTO(framesize)(TMP1) | 2481 | | lbz TMP1, PC2PROTO(framesize)(TMP1) |
| 2298 | | stw BASE, L->base | 2482 | | stp BASE, L->base |
| 2299 | | slwi TMP1, TMP1, 3 | 2483 | | slwi TMP1, TMP1, 3 |
| 2300 | | add TMP1, BASE, TMP1 | 2484 | | add TMP1, BASE, TMP1 |
| 2301 | | stw TMP1, L->top | 2485 | | stp TMP1, L->top |
| 2302 | | bl extern lj_trace_hot // (jit_State *J, const BCIns *pc) | 2486 | | bl extern lj_trace_hot // (jit_State *J, const BCIns *pc) |
| 2303 | | b <3 | 2487 | | b <3 |
| 2304 | |.endif | 2488 | |.endif |
| @@ -2317,13 +2501,13 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 2317 | | add TMP0, BASE, RC | 2501 | | add TMP0, BASE, RC |
| 2318 | | stw PC, SAVE_PC | 2502 | | stw PC, SAVE_PC |
| 2319 | | mr CARG1, L | 2503 | | mr CARG1, L |
| 2320 | | stw BASE, L->base | 2504 | | stp BASE, L->base |
| 2321 | | sub RA, RA, BASE | 2505 | | sub RA, RA, BASE |
| 2322 | | stw TMP0, L->top | 2506 | | stp TMP0, L->top |
| 2323 | | bl extern lj_dispatch_call // (lua_State *L, const BCIns *pc) | 2507 | | bl extern lj_dispatch_call // (lua_State *L, const BCIns *pc) |
| 2324 | | // Returns ASMFunction. | 2508 | | // Returns ASMFunction. |
| 2325 | | lwz BASE, L->base | 2509 | | lp BASE, L->base |
| 2326 | | lwz TMP0, L->top | 2510 | | lp TMP0, L->top |
| 2327 | | stw ZERO, SAVE_PC // Invalidate for subsequent line hook. | 2511 | | stw ZERO, SAVE_PC // Invalidate for subsequent line hook. |
| 2328 | | sub NARGS8:RC, TMP0, BASE | 2512 | | sub NARGS8:RC, TMP0, BASE |
| 2329 | | add RA, BASE, RA | 2513 | | add RA, BASE, RA |
| @@ -2369,22 +2553,26 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 2369 | | lwz L, DISPATCH_GL(jit_L)(DISPATCH) | 2553 | | lwz L, DISPATCH_GL(jit_L)(DISPATCH) |
| 2370 | | savex_ 28,29,30,31 | 2554 | | savex_ 28,29,30,31 |
| 2371 | | sub CARG3, TMP0, CARG3 // Compute exit number. | 2555 | | sub CARG3, TMP0, CARG3 // Compute exit number. |
| 2372 | | lwz BASE, DISPATCH_GL(jit_base)(DISPATCH) | 2556 | | lp BASE, DISPATCH_GL(jit_base)(DISPATCH) |
| 2373 | | srwi CARG3, CARG3, 2 | 2557 | | srwi CARG3, CARG3, 2 |
| 2374 | | stw L, DISPATCH_J(L)(DISPATCH) | 2558 | | stw L, DISPATCH_J(L)(DISPATCH) |
| 2375 | | subi CARG3, CARG3, 2 | 2559 | | subi CARG3, CARG3, 2 |
| 2376 | | stw TMP1, DISPATCH_GL(jit_L)(DISPATCH) | 2560 | | stw TMP1, DISPATCH_GL(jit_L)(DISPATCH) |
| 2377 | | stw CARG4, DISPATCH_J(parent)(DISPATCH) | 2561 | | stw CARG4, DISPATCH_J(parent)(DISPATCH) |
| 2378 | | stw BASE, L->base | 2562 | | stp BASE, L->base |
| 2379 | | addi CARG1, DISPATCH, GG_DISP2J | 2563 | | addi CARG1, DISPATCH, GG_DISP2J |
| 2380 | | stw CARG3, DISPATCH_J(exitno)(DISPATCH) | 2564 | | stw CARG3, DISPATCH_J(exitno)(DISPATCH) |
| 2381 | | addi CARG2, sp, 16 | 2565 | | addi CARG2, sp, 16 |
| 2382 | | bl extern lj_trace_exit // (jit_State *J, ExitState *ex) | 2566 | | bl extern lj_trace_exit // (jit_State *J, ExitState *ex) |
| 2383 | | // Returns MULTRES (unscaled) or negated error code. | 2567 | | // Returns MULTRES (unscaled) or negated error code. |
| 2384 | | lwz TMP1, L->cframe | 2568 | | lp TMP1, L->cframe |
| 2385 | | lwz TMP2, 0(sp) | 2569 | | lwz TMP2, 0(sp) |
| 2386 | | lwz BASE, L->base | 2570 | | lp BASE, L->base |
| 2571 | |.if GPR64 | ||
| 2572 | | rldicr sp, TMP1, 0, 61 | ||
| 2573 | |.else | ||
| 2387 | | rlwinm sp, TMP1, 0, 0, 29 | 2574 | | rlwinm sp, TMP1, 0, 0, 29 |
| 2575 | |.endif | ||
| 2388 | | lwz PC, SAVE_PC // Get SAVE_PC. | 2576 | | lwz PC, SAVE_PC // Get SAVE_PC. |
| 2389 | | stw TMP2, 0(sp) | 2577 | | stw TMP2, 0(sp) |
| 2390 | | stw L, SAVE_L // Set SAVE_L (on-trace resume/yield). | 2578 | | stw L, SAVE_L // Set SAVE_L (on-trace resume/yield). |
| @@ -2422,9 +2610,9 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 2422 | | addi PC, PC, 4 | 2610 | | addi PC, PC, 4 |
| 2423 | | // Assumes TISNIL == ~LJ_VMST_INTERP == -1. | 2611 | | // Assumes TISNIL == ~LJ_VMST_INTERP == -1. |
| 2424 | | stw TISNIL, DISPATCH_GL(vmstate)(DISPATCH) | 2612 | | stw TISNIL, DISPATCH_GL(vmstate)(DISPATCH) |
| 2425 | | decode_OP4 TMP1, INS | 2613 | | decode_OPP TMP1, INS |
| 2426 | | decode_RA8 RA, INS | 2614 | | decode_RA8 RA, INS |
| 2427 | | lwzx TMP0, DISPATCH, TMP1 | 2615 | | lpx TMP0, DISPATCH, TMP1 |
| 2428 | | mtctr TMP0 | 2616 | | mtctr TMP0 |
| 2429 | | cmplwi TMP1, BC_FUNCF*4 // Function header? | 2617 | | cmplwi TMP1, BC_FUNCF*4 // Function header? |
| 2430 | | bge >2 | 2618 | | bge >2 |
| @@ -2452,7 +2640,12 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 2452 | |->vm_modi: | 2640 | |->vm_modi: |
| 2453 | | divwo. TMP0, CARG1, CARG2 | 2641 | | divwo. TMP0, CARG1, CARG2 |
| 2454 | | bso >1 | 2642 | | bso >1 |
| 2643 | |.if GPR64 | ||
| 2644 | | xor CARG3, CARG1, CARG2 | ||
| 2645 | | cmpwi CARG3, 0 | ||
| 2646 | |.else | ||
| 2455 | | xor. CARG3, CARG1, CARG2 | 2647 | | xor. CARG3, CARG1, CARG2 |
| 2648 | |.endif | ||
| 2456 | | mullw TMP0, TMP0, CARG2 | 2649 | | mullw TMP0, TMP0, CARG2 |
| 2457 | | sub CARG1, CARG1, TMP0 | 2650 | | sub CARG1, CARG1, TMP0 |
| 2458 | | bgelr | 2651 | | bgelr |
| @@ -2474,6 +2667,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 2474 | |// Flush D-Cache and invalidate I-Cache. Assumes 32 byte cache line size. | 2667 | |// Flush D-Cache and invalidate I-Cache. Assumes 32 byte cache line size. |
| 2475 | |// This is a good lower bound, except for very ancient PPC models. | 2668 | |// This is a good lower bound, except for very ancient PPC models. |
| 2476 | |->vm_cachesync: | 2669 | |->vm_cachesync: |
| 2670 | |.if JIT or FFI | ||
| 2477 | | // Compute start of first cache line and number of cache lines. | 2671 | | // Compute start of first cache line and number of cache lines. |
| 2478 | | rlwinm CARG1, CARG1, 0, 0, 26 | 2672 | | rlwinm CARG1, CARG1, 0, 0, 26 |
| 2479 | | sub CARG2, CARG2, CARG1 | 2673 | | sub CARG2, CARG2, CARG1 |
| @@ -2494,6 +2688,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 2494 | | bdnz <1 | 2688 | | bdnz <1 |
| 2495 | | isync | 2689 | | isync |
| 2496 | | blr | 2690 | | blr |
| 2691 | |.endif | ||
| 2497 | | | 2692 | | |
| 2498 | |//----------------------------------------------------------------------- | 2693 | |//----------------------------------------------------------------------- |
| 2499 | |//-- FFI helper functions ----------------------------------------------- | 2694 | |//-- FFI helper functions ----------------------------------------------- |
| @@ -2530,9 +2725,9 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 2530 | | mr CARG2, sp | 2725 | | mr CARG2, sp |
| 2531 | | bl extern lj_ccallback_enter // (CTState *cts, void *cf) | 2726 | | bl extern lj_ccallback_enter // (CTState *cts, void *cf) |
| 2532 | | // Returns lua_State *. | 2727 | | // Returns lua_State *. |
| 2533 | | lwz BASE, L:CRET1->base | 2728 | | lp BASE, L:CRET1->base |
| 2534 | | li TISNUM, LJ_TISNUM // Setup type comparison constants. | 2729 | | li TISNUM, LJ_TISNUM // Setup type comparison constants. |
| 2535 | | lwz RC, L:CRET1->top | 2730 | | lp RC, L:CRET1->top |
| 2536 | | lus TMP3, 0x59c0 // TOBIT = 2^52 + 2^51 (float). | 2731 | | lus TMP3, 0x59c0 // TOBIT = 2^52 + 2^51 (float). |
| 2537 | | li ZERO, 0 | 2732 | | li ZERO, 0 |
| 2538 | | mr L, CRET1 | 2733 | | mr L, CRET1 |
| @@ -2554,9 +2749,9 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 2554 | |->cont_ffi_callback: // Return from FFI callback. | 2749 | |->cont_ffi_callback: // Return from FFI callback. |
| 2555 | |.if FFI | 2750 | |.if FFI |
| 2556 | | lwz CTSTATE, DISPATCH_GL(ctype_state)(DISPATCH) | 2751 | | lwz CTSTATE, DISPATCH_GL(ctype_state)(DISPATCH) |
| 2557 | | stw BASE, L->base | 2752 | | stp BASE, L->base |
| 2558 | | stw RB, L->top | 2753 | | stp RB, L->top |
| 2559 | | stw L, CTSTATE->L | 2754 | | stp L, CTSTATE->L |
| 2560 | | mr CARG1, CTSTATE | 2755 | | mr CARG1, CTSTATE |
| 2561 | | mr CARG2, RA | 2756 | | mr CARG2, RA |
| 2562 | | bl extern lj_ccallback_leave // (CTState *cts, TValue *o) | 2757 | | bl extern lj_ccallback_leave // (CTState *cts, TValue *o) |
| @@ -2604,7 +2799,7 @@ static void build_subroutines(BuildCtx *ctx) | |||
| 2604 | | lfd f7, CCSTATE->fpr[6] | 2799 | | lfd f7, CCSTATE->fpr[6] |
| 2605 | | lfd f8, CCSTATE->fpr[7] | 2800 | | lfd f8, CCSTATE->fpr[7] |
| 2606 | |3: | 2801 | |3: |
| 2607 | | lwz TMP0, CCSTATE->func | 2802 | | lp TMP0, CCSTATE->func |
| 2608 | | lwz CARG2, CCSTATE->gpr[1] | 2803 | | lwz CARG2, CCSTATE->gpr[1] |
| 2609 | | lwz CARG3, CCSTATE->gpr[2] | 2804 | | lwz CARG3, CCSTATE->gpr[2] |
| 2610 | | lwz CARG4, CCSTATE->gpr[3] | 2805 | | lwz CARG4, CCSTATE->gpr[3] |
| @@ -2832,7 +3027,7 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 2832 | | cmplwi TAB:TMP2, 0 | 3027 | | cmplwi TAB:TMP2, 0 |
| 2833 | | beq <1 // No metatable? | 3028 | | beq <1 // No metatable? |
| 2834 | | lbz TMP2, TAB:TMP2->nomm | 3029 | | lbz TMP2, TAB:TMP2->nomm |
| 2835 | | andi. TMP2, TMP2, 1<<MM_eq | 3030 | | andix. TMP2, TMP2, 1<<MM_eq |
| 2836 | | bne <1 // Or 'no __eq' flag set? | 3031 | | bne <1 // Or 'no __eq' flag set? |
| 2837 | | mr PC, SAVE0 // Restore old PC. | 3032 | | mr PC, SAVE0 // Restore old PC. |
| 2838 | | b ->vmeta_equal // Handle __eq metamethod. | 3033 | | b ->vmeta_equal // Handle __eq metamethod. |
| @@ -2851,6 +3046,7 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 2851 | | cmpwi TMP0, LJ_TCDATA | 3046 | | cmpwi TMP0, LJ_TCDATA |
| 2852 | |.endif | 3047 | |.endif |
| 2853 | | lwzx STR:TMP1, KBASE, RD // KBASE-4-str_const*4 | 3048 | | lwzx STR:TMP1, KBASE, RD // KBASE-4-str_const*4 |
| 3049 | | .gpr64 extsw TMP0, TMP0 | ||
| 2854 | | subfic TMP0, TMP0, LJ_TSTR | 3050 | | subfic TMP0, TMP0, LJ_TSTR |
| 2855 | |.if FFI | 3051 | |.if FFI |
| 2856 | | beq ->vmeta_equal_cd | 3052 | | beq ->vmeta_equal_cd |
| @@ -2969,6 +3165,7 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 2969 | | beq ->vmeta_equal_cd | 3165 | | beq ->vmeta_equal_cd |
| 2970 | |.endif | 3166 | |.endif |
| 2971 | | decode_RD4 TMP2, TMP2 | 3167 | | decode_RD4 TMP2, TMP2 |
| 3168 | | .gpr64 extsw TMP0, TMP0 | ||
| 2972 | | addic TMP0, TMP0, -1 | 3169 | | addic TMP0, TMP0, -1 |
| 2973 | | addis TMP2, TMP2, -(BCBIAS_J*4 >> 16) | 3170 | | addis TMP2, TMP2, -(BCBIAS_J*4 >> 16) |
| 2974 | | subfe TMP1, TMP1, TMP1 | 3171 | | subfe TMP1, TMP1, TMP1 |
| @@ -2989,6 +3186,7 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 2989 | | lwz INS, 0(PC) | 3186 | | lwz INS, 0(PC) |
| 2990 | | addi PC, PC, 4 | 3187 | | addi PC, PC, 4 |
| 2991 | if (op == BC_IST || op == BC_ISF) { | 3188 | if (op == BC_IST || op == BC_ISF) { |
| 3189 | | .gpr64 extsw TMP0, TMP0 | ||
| 2992 | | subfic TMP0, TMP0, LJ_TTRUE | 3190 | | subfic TMP0, TMP0, LJ_TTRUE |
| 2993 | | decode_RD4 TMP2, INS | 3191 | | decode_RD4 TMP2, INS |
| 2994 | | subfe TMP1, TMP1, TMP1 | 3192 | | subfe TMP1, TMP1, TMP1 |
| @@ -3030,6 +3228,7 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 3030 | | // RA = dst*8, RD = src*8 | 3228 | | // RA = dst*8, RD = src*8 |
| 3031 | | ins_next1 | 3229 | | ins_next1 |
| 3032 | | lwzx TMP0, BASE, RD | 3230 | | lwzx TMP0, BASE, RD |
| 3231 | | .gpr64 extsw TMP0, TMP0 | ||
| 3033 | | subfic TMP1, TMP0, LJ_TTRUE | 3232 | | subfic TMP1, TMP0, LJ_TTRUE |
| 3034 | | adde TMP0, TMP0, TMP1 | 3233 | | adde TMP0, TMP0, TMP1 |
| 3035 | | stwx TMP0, BASE, RA | 3234 | | stwx TMP0, BASE, RA |
| @@ -3042,16 +3241,26 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 3042 | | checknum TMP1 | 3241 | | checknum TMP1 |
| 3043 | |.if DUALNUM | 3242 | |.if DUALNUM |
| 3044 | | bne >5 | 3243 | | bne >5 |
| 3244 | |.if GPR64 | ||
| 3245 | | lus TMP2, 0x8000 | ||
| 3246 | | neg TMP0, TMP0 | ||
| 3247 | | cmplw TMP0, TMP2 | ||
| 3248 | | beq >4 | ||
| 3249 | |.else | ||
| 3045 | | nego. TMP0, TMP0 | 3250 | | nego. TMP0, TMP0 |
| 3046 | | bso >4 | 3251 | | bso >4 |
| 3047 | |1: | 3252 | |1: |
| 3253 | |.endif | ||
| 3048 | | ins_next1 | 3254 | | ins_next1 |
| 3049 | | stwux TISNUM, RA, BASE | 3255 | | stwux TISNUM, RA, BASE |
| 3050 | | stw TMP0, 4(RA) | 3256 | | stw TMP0, 4(RA) |
| 3051 | |3: | 3257 | |3: |
| 3052 | | ins_next2 | 3258 | | ins_next2 |
| 3053 | |4: // Potential overflow. | 3259 | |4: |
| 3260 | |.if not GPR64 | ||
| 3261 | | // Potential overflow. | ||
| 3054 | | mcrxr cr0; bley <1 // Ignore unrelated overflow. | 3262 | | mcrxr cr0; bley <1 // Ignore unrelated overflow. |
| 3263 | |.endif | ||
| 3055 | | lus TMP1, 0x41e0 // 2^31. | 3264 | | lus TMP1, 0x41e0 // 2^31. |
| 3056 | | li TMP0, 0 | 3265 | | li TMP0, 0 |
| 3057 | | b >7 | 3266 | | b >7 |
| @@ -3101,7 +3310,7 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 3101 | #ifdef LUAJIT_ENABLE_LUA52COMPAT | 3310 | #ifdef LUAJIT_ENABLE_LUA52COMPAT |
| 3102 | |9: | 3311 | |9: |
| 3103 | | lbz TMP0, TAB:TMP2->nomm | 3312 | | lbz TMP0, TAB:TMP2->nomm |
| 3104 | | andi. TMP0, TMP0, 1<<MM_len | 3313 | | andix. TMP0, TMP0, 1<<MM_len |
| 3105 | | bne <3 // 'no __len' flag set: done. | 3314 | | bne <3 // 'no __len' flag set: done. |
| 3106 | | b ->vmeta_len | 3315 | | b ->vmeta_len |
| 3107 | #endif | 3316 | #endif |
| @@ -3180,7 +3389,7 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 3180 | |->BC_MODVN_Z: | 3389 | |->BC_MODVN_Z: |
| 3181 | | fdiv FARG1, b, c | 3390 | | fdiv FARG1, b, c |
| 3182 | | // NYI: Use internal implementation of floor. | 3391 | | // NYI: Use internal implementation of floor. |
| 3183 | | bl extern floor // floor(b/c) | 3392 | | blex floor // floor(b/c) |
| 3184 | | fmul a, FARG1, c | 3393 | | fmul a, FARG1, c |
| 3185 | | fsub a, b, a // b - floor(b/c)*c | 3394 | | fsub a, b, a // b - floor(b/c)*c |
| 3186 | |.endmacro | 3395 | |.endmacro |
| @@ -3267,10 +3476,32 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 3267 | |.endmacro | 3476 | |.endmacro |
| 3268 | 3477 | ||
| 3269 | case BC_ADDVN: case BC_ADDNV: case BC_ADDVV: | 3478 | case BC_ADDVN: case BC_ADDNV: case BC_ADDVV: |
| 3479 | |.if GPR64 | ||
| 3480 | |.macro addo32., y, a, b | ||
| 3481 | | // Need to check overflow for (a<<32) + (b<<32). | ||
| 3482 | | rldicr TMP0, a, 32, 31 | ||
| 3483 | | rldicr TMP3, b, 32, 31 | ||
| 3484 | | addo. TMP0, TMP0, TMP3 | ||
| 3485 | | add y, a, b | ||
| 3486 | |.endmacro | ||
| 3487 | | ins_arith addo32., fadd | ||
| 3488 | |.else | ||
| 3270 | | ins_arith addo., fadd | 3489 | | ins_arith addo., fadd |
| 3490 | |.endif | ||
| 3271 | break; | 3491 | break; |
| 3272 | case BC_SUBVN: case BC_SUBNV: case BC_SUBVV: | 3492 | case BC_SUBVN: case BC_SUBNV: case BC_SUBVV: |
| 3493 | |.if GPR64 | ||
| 3494 | |.macro subo32., y, a, b | ||
| 3495 | | // Need to check overflow for (a<<32) - (b<<32). | ||
| 3496 | | rldicr TMP0, a, 32, 31 | ||
| 3497 | | rldicr TMP3, b, 32, 31 | ||
| 3498 | | subo. TMP0, TMP0, TMP3 | ||
| 3499 | | sub y, a, b | ||
| 3500 | |.endmacro | ||
| 3501 | | ins_arith subo32., fsub | ||
| 3502 | |.else | ||
| 3273 | | ins_arith subo., fsub | 3503 | | ins_arith subo., fsub |
| 3504 | |.endif | ||
| 3274 | break; | 3505 | break; |
| 3275 | case BC_MULVN: case BC_MULNV: case BC_MULVV: | 3506 | case BC_MULVN: case BC_MULNV: case BC_MULVV: |
| 3276 | | ins_arith mullwo., fmul | 3507 | | ins_arith mullwo., fmul |
| @@ -3294,7 +3525,7 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 3294 | | checknum cr1, TMP2 | 3525 | | checknum cr1, TMP2 |
| 3295 | | crand 4*cr0+lt, 4*cr0+lt, 4*cr1+lt | 3526 | | crand 4*cr0+lt, 4*cr0+lt, 4*cr1+lt |
| 3296 | | bge ->vmeta_arith_vv | 3527 | | bge ->vmeta_arith_vv |
| 3297 | | bl extern pow | 3528 | | blex pow |
| 3298 | | ins_next1 | 3529 | | ins_next1 |
| 3299 | | stfdx FARG1, BASE, RA | 3530 | | stfdx FARG1, BASE, RA |
| 3300 | | ins_next2 | 3531 | | ins_next2 |
| @@ -3303,7 +3534,7 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 3303 | case BC_CAT: | 3534 | case BC_CAT: |
| 3304 | | // RA = dst*8, RB = src_start*8, RC = src_end*8 | 3535 | | // RA = dst*8, RB = src_start*8, RC = src_end*8 |
| 3305 | | sub CARG3, RC, RB | 3536 | | sub CARG3, RC, RB |
| 3306 | | stw BASE, L->base | 3537 | | stp BASE, L->base |
| 3307 | | add CARG2, BASE, RC | 3538 | | add CARG2, BASE, RC |
| 3308 | | mr SAVE0, RB | 3539 | | mr SAVE0, RB |
| 3309 | |->BC_CAT_Z: | 3540 | |->BC_CAT_Z: |
| @@ -3313,7 +3544,7 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 3313 | | bl extern lj_meta_cat // (lua_State *L, TValue *top, int left) | 3544 | | bl extern lj_meta_cat // (lua_State *L, TValue *top, int left) |
| 3314 | | // Returns NULL (finished) or TValue * (metamethod). | 3545 | | // Returns NULL (finished) or TValue * (metamethod). |
| 3315 | | cmplwi CRET1, 0 | 3546 | | cmplwi CRET1, 0 |
| 3316 | | lwz BASE, L->base | 3547 | | lp BASE, L->base |
| 3317 | | bne ->vmeta_binop | 3548 | | bne ->vmeta_binop |
| 3318 | | ins_next1 | 3549 | | ins_next1 |
| 3319 | | lfdx f0, BASE, SAVE0 // Copy result from RB to RA. | 3550 | | lfdx f0, BASE, SAVE0 // Copy result from RB to RA. |
| @@ -3427,7 +3658,7 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 3427 | | lwzx UPVAL:RB, LFUNC:RB, RA | 3658 | | lwzx UPVAL:RB, LFUNC:RB, RA |
| 3428 | | lbz TMP3, UPVAL:RB->marked | 3659 | | lbz TMP3, UPVAL:RB->marked |
| 3429 | | lwz CARG2, UPVAL:RB->v | 3660 | | lwz CARG2, UPVAL:RB->v |
| 3430 | | andi. TMP3, TMP3, LJ_GC_BLACK // isblack(uv) | 3661 | | andix. TMP3, TMP3, LJ_GC_BLACK // isblack(uv) |
| 3431 | | lbz TMP0, UPVAL:RB->closed | 3662 | | lbz TMP0, UPVAL:RB->closed |
| 3432 | | lwz TMP2, 0(RD) | 3663 | | lwz TMP2, 0(RD) |
| 3433 | | stfd f0, 0(CARG2) | 3664 | | stfd f0, 0(CARG2) |
| @@ -3443,7 +3674,7 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 3443 | | cmplwi TMP2, LJ_TISGCV - (LJ_TISNUM+1) | 3674 | | cmplwi TMP2, LJ_TISGCV - (LJ_TISNUM+1) |
| 3444 | | bge <1 // tvisgcv(v) | 3675 | | bge <1 // tvisgcv(v) |
| 3445 | | lbz TMP3, GCOBJ:TMP1->gch.marked | 3676 | | lbz TMP3, GCOBJ:TMP1->gch.marked |
| 3446 | | andi. TMP3, TMP3, LJ_GC_WHITES // iswhite(v) | 3677 | | andix. TMP3, TMP3, LJ_GC_WHITES // iswhite(v) |
| 3447 | | la CARG1, GG_DISP2G(DISPATCH) | 3678 | | la CARG1, GG_DISP2G(DISPATCH) |
| 3448 | | // Crossed a write barrier. Move the barrier forward. | 3679 | | // Crossed a write barrier. Move the barrier forward. |
| 3449 | | beq <1 | 3680 | | beq <1 |
| @@ -3461,7 +3692,7 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 3461 | | lwzx UPVAL:RB, LFUNC:RB, RA | 3692 | | lwzx UPVAL:RB, LFUNC:RB, RA |
| 3462 | | lbz TMP3, UPVAL:RB->marked | 3693 | | lbz TMP3, UPVAL:RB->marked |
| 3463 | | lwz CARG2, UPVAL:RB->v | 3694 | | lwz CARG2, UPVAL:RB->v |
| 3464 | | andi. TMP3, TMP3, LJ_GC_BLACK // isblack(uv) | 3695 | | andix. TMP3, TMP3, LJ_GC_BLACK // isblack(uv) |
| 3465 | | lbz TMP3, STR:TMP1->marked | 3696 | | lbz TMP3, STR:TMP1->marked |
| 3466 | | lbz TMP2, UPVAL:RB->closed | 3697 | | lbz TMP2, UPVAL:RB->closed |
| 3467 | | li TMP0, LJ_TSTR | 3698 | | li TMP0, LJ_TSTR |
| @@ -3472,7 +3703,7 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 3472 | | ins_next | 3703 | | ins_next |
| 3473 | | | 3704 | | |
| 3474 | |2: // Check if string is white and ensure upvalue is closed. | 3705 | |2: // Check if string is white and ensure upvalue is closed. |
| 3475 | | andi. TMP3, TMP3, LJ_GC_WHITES // iswhite(str) | 3706 | | andix. TMP3, TMP3, LJ_GC_WHITES // iswhite(str) |
| 3476 | | cmplwi cr1, TMP2, 0 | 3707 | | cmplwi cr1, TMP2, 0 |
| 3477 | | cror 4*cr0+eq, 4*cr0+eq, 4*cr1+eq | 3708 | | cror 4*cr0+eq, 4*cr0+eq, 4*cr1+eq |
| 3478 | | la CARG1, GG_DISP2G(DISPATCH) | 3709 | | la CARG1, GG_DISP2G(DISPATCH) |
| @@ -3511,13 +3742,13 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 3511 | | // RA = level*8, RD = target | 3742 | | // RA = level*8, RD = target |
| 3512 | | lwz TMP1, L->openupval | 3743 | | lwz TMP1, L->openupval |
| 3513 | | branch_RD // Do this first since RD is not saved. | 3744 | | branch_RD // Do this first since RD is not saved. |
| 3514 | | stw BASE, L->base | 3745 | | stp BASE, L->base |
| 3515 | | cmplwi TMP1, 0 | 3746 | | cmplwi TMP1, 0 |
| 3516 | | mr CARG1, L | 3747 | | mr CARG1, L |
| 3517 | | beq >1 | 3748 | | beq >1 |
| 3518 | | add CARG2, BASE, RA | 3749 | | add CARG2, BASE, RA |
| 3519 | | bl extern lj_func_closeuv // (lua_State *L, TValue *level) | 3750 | | bl extern lj_func_closeuv // (lua_State *L, TValue *level) |
| 3520 | | lwz BASE, L->base | 3751 | | lp BASE, L->base |
| 3521 | |1: | 3752 | |1: |
| 3522 | | ins_next | 3753 | | ins_next |
| 3523 | break; | 3754 | break; |
| @@ -3525,7 +3756,7 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 3525 | case BC_FNEW: | 3756 | case BC_FNEW: |
| 3526 | | // RA = dst*8, RD = proto_const*8 (~) (holding function prototype) | 3757 | | // RA = dst*8, RD = proto_const*8 (~) (holding function prototype) |
| 3527 | | srwi TMP1, RD, 1 | 3758 | | srwi TMP1, RD, 1 |
| 3528 | | stw BASE, L->base | 3759 | | stp BASE, L->base |
| 3529 | | subfic TMP1, TMP1, -4 | 3760 | | subfic TMP1, TMP1, -4 |
| 3530 | | stw PC, SAVE_PC | 3761 | | stw PC, SAVE_PC |
| 3531 | | lwzx CARG2, KBASE, TMP1 // KBASE-4-tab_const*4 | 3762 | | lwzx CARG2, KBASE, TMP1 // KBASE-4-tab_const*4 |
| @@ -3534,7 +3765,7 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 3534 | | // (lua_State *L, GCproto *pt, GCfuncL *parent) | 3765 | | // (lua_State *L, GCproto *pt, GCfuncL *parent) |
| 3535 | | bl extern lj_func_newL_gc | 3766 | | bl extern lj_func_newL_gc |
| 3536 | | // Returns GCfuncL *. | 3767 | | // Returns GCfuncL *. |
| 3537 | | lwz BASE, L->base | 3768 | | lp BASE, L->base |
| 3538 | | li TMP0, LJ_TFUNC | 3769 | | li TMP0, LJ_TFUNC |
| 3539 | | stwux TMP0, RA, BASE | 3770 | | stwux TMP0, RA, BASE |
| 3540 | | stw LFUNC:CRET1, 4(RA) | 3771 | | stw LFUNC:CRET1, 4(RA) |
| @@ -3549,7 +3780,7 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 3549 | | lwz TMP0, DISPATCH_GL(gc.total)(DISPATCH) | 3780 | | lwz TMP0, DISPATCH_GL(gc.total)(DISPATCH) |
| 3550 | | mr CARG1, L | 3781 | | mr CARG1, L |
| 3551 | | lwz TMP1, DISPATCH_GL(gc.threshold)(DISPATCH) | 3782 | | lwz TMP1, DISPATCH_GL(gc.threshold)(DISPATCH) |
| 3552 | | stw BASE, L->base | 3783 | | stp BASE, L->base |
| 3553 | | cmplw TMP0, TMP1 | 3784 | | cmplw TMP0, TMP1 |
| 3554 | | stw PC, SAVE_PC | 3785 | | stw PC, SAVE_PC |
| 3555 | | bge >5 | 3786 | | bge >5 |
| @@ -3568,7 +3799,7 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 3568 | | bl extern lj_tab_dup // (lua_State *L, Table *kt) | 3799 | | bl extern lj_tab_dup // (lua_State *L, Table *kt) |
| 3569 | | // Returns Table *. | 3800 | | // Returns Table *. |
| 3570 | } | 3801 | } |
| 3571 | | lwz BASE, L->base | 3802 | | lp BASE, L->base |
| 3572 | | li TMP0, LJ_TTAB | 3803 | | li TMP0, LJ_TTAB |
| 3573 | | stwux TMP0, RA, BASE | 3804 | | stwux TMP0, RA, BASE |
| 3574 | | stw TAB:CRET1, 4(RA) | 3805 | | stw TAB:CRET1, 4(RA) |
| @@ -3650,7 +3881,7 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 3650 | | cmplwi TAB:TMP2, 0 | 3881 | | cmplwi TAB:TMP2, 0 |
| 3651 | | beq <1 // No metatable: done. | 3882 | | beq <1 // No metatable: done. |
| 3652 | | lbz TMP0, TAB:TMP2->nomm | 3883 | | lbz TMP0, TAB:TMP2->nomm |
| 3653 | | andi. TMP0, TMP0, 1<<MM_index | 3884 | | andix. TMP0, TMP0, 1<<MM_index |
| 3654 | | bne <1 // 'no __index' flag set: done. | 3885 | | bne <1 // 'no __index' flag set: done. |
| 3655 | | b ->vmeta_tgetv | 3886 | | b ->vmeta_tgetv |
| 3656 | | | 3887 | | |
| @@ -3705,7 +3936,7 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 3705 | | cmplwi TAB:TMP2, 0 | 3936 | | cmplwi TAB:TMP2, 0 |
| 3706 | | beq <3 // No metatable: done. | 3937 | | beq <3 // No metatable: done. |
| 3707 | | lbz TMP0, TAB:TMP2->nomm | 3938 | | lbz TMP0, TAB:TMP2->nomm |
| 3708 | | andi. TMP0, TMP0, 1<<MM_index | 3939 | | andix. TMP0, TMP0, 1<<MM_index |
| 3709 | | bne <3 // 'no __index' flag set: done. | 3940 | | bne <3 // 'no __index' flag set: done. |
| 3710 | | b ->vmeta_tgets | 3941 | | b ->vmeta_tgets |
| 3711 | break; | 3942 | break; |
| @@ -3731,7 +3962,7 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 3731 | | cmplwi TAB:TMP2, 0 | 3962 | | cmplwi TAB:TMP2, 0 |
| 3732 | | beq <1 // No metatable: done. | 3963 | | beq <1 // No metatable: done. |
| 3733 | | lbz TMP2, TAB:TMP2->nomm | 3964 | | lbz TMP2, TAB:TMP2->nomm |
| 3734 | | andi. TMP2, TMP2, 1<<MM_index | 3965 | | andix. TMP2, TMP2, 1<<MM_index |
| 3735 | | bne <1 // 'no __index' flag set: done. | 3966 | | bne <1 // 'no __index' flag set: done. |
| 3736 | | b ->vmeta_tgetb // Caveat: preserve TMP0! | 3967 | | b ->vmeta_tgetb // Caveat: preserve TMP0! |
| 3737 | break; | 3968 | break; |
| @@ -3776,7 +4007,7 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 3776 | | lfdx f14, BASE, RA | 4007 | | lfdx f14, BASE, RA |
| 3777 | | checknil TMP2; beq >3 | 4008 | | checknil TMP2; beq >3 |
| 3778 | |1: | 4009 | |1: |
| 3779 | | andi. TMP2, TMP3, LJ_GC_BLACK // isblack(table) | 4010 | | andix. TMP2, TMP3, LJ_GC_BLACK // isblack(table) |
| 3780 | | stfdx f14, TMP1, TMP0 | 4011 | | stfdx f14, TMP1, TMP0 |
| 3781 | | bne >7 | 4012 | | bne >7 |
| 3782 | |2: | 4013 | |2: |
| @@ -3787,7 +4018,7 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 3787 | | cmplwi TAB:TMP2, 0 | 4018 | | cmplwi TAB:TMP2, 0 |
| 3788 | | beq <1 // No metatable: done. | 4019 | | beq <1 // No metatable: done. |
| 3789 | | lbz TMP2, TAB:TMP2->nomm | 4020 | | lbz TMP2, TAB:TMP2->nomm |
| 3790 | | andi. TMP2, TMP2, 1<<MM_newindex | 4021 | | andix. TMP2, TMP2, 1<<MM_newindex |
| 3791 | | bne <1 // 'no __newindex' flag set: done. | 4022 | | bne <1 // 'no __newindex' flag set: done. |
| 3792 | | b ->vmeta_tsetv | 4023 | | b ->vmeta_tsetv |
| 3793 | | | 4024 | | |
| @@ -3833,7 +4064,7 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 3833 | | cmpw TMP0, STR:RC; bne >5 | 4064 | | cmpw TMP0, STR:RC; bne >5 |
| 3834 | | checknil CARG2; beq >4 // Key found, but nil value? | 4065 | | checknil CARG2; beq >4 // Key found, but nil value? |
| 3835 | |2: | 4066 | |2: |
| 3836 | | andi. TMP0, TMP3, LJ_GC_BLACK // isblack(table) | 4067 | | andix. TMP0, TMP3, LJ_GC_BLACK // isblack(table) |
| 3837 | | stfd f14, NODE:TMP2->val | 4068 | | stfd f14, NODE:TMP2->val |
| 3838 | | bne >7 | 4069 | | bne >7 |
| 3839 | |3: | 4070 | |3: |
| @@ -3844,7 +4075,7 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 3844 | | cmplwi TAB:TMP1, 0 | 4075 | | cmplwi TAB:TMP1, 0 |
| 3845 | | beq <2 // No metatable: done. | 4076 | | beq <2 // No metatable: done. |
| 3846 | | lbz TMP0, TAB:TMP1->nomm | 4077 | | lbz TMP0, TAB:TMP1->nomm |
| 3847 | | andi. TMP0, TMP0, 1<<MM_newindex | 4078 | | andix. TMP0, TMP0, 1<<MM_newindex |
| 3848 | | bne <2 // 'no __newindex' flag set: done. | 4079 | | bne <2 // 'no __newindex' flag set: done. |
| 3849 | | b ->vmeta_tsets | 4080 | | b ->vmeta_tsets |
| 3850 | | | 4081 | | |
| @@ -3860,10 +4091,10 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 3860 | | stw PC, SAVE_PC | 4091 | | stw PC, SAVE_PC |
| 3861 | | mr CARG1, L | 4092 | | mr CARG1, L |
| 3862 | | cmplwi TAB:TMP1, 0 | 4093 | | cmplwi TAB:TMP1, 0 |
| 3863 | | stw BASE, L->base | 4094 | | stp BASE, L->base |
| 3864 | | beq >6 // No metatable: continue. | 4095 | | beq >6 // No metatable: continue. |
| 3865 | | lbz TMP0, TAB:TMP1->nomm | 4096 | | lbz TMP0, TAB:TMP1->nomm |
| 3866 | | andi. TMP0, TMP0, 1<<MM_newindex | 4097 | | andix. TMP0, TMP0, 1<<MM_newindex |
| 3867 | | beq ->vmeta_tsets // 'no __newindex' flag NOT set: check. | 4098 | | beq ->vmeta_tsets // 'no __newindex' flag NOT set: check. |
| 3868 | |6: | 4099 | |6: |
| 3869 | | li TMP0, LJ_TSTR | 4100 | | li TMP0, LJ_TSTR |
| @@ -3872,7 +4103,7 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 3872 | | stw TMP0, 0(CARG3) | 4103 | | stw TMP0, 0(CARG3) |
| 3873 | | bl extern lj_tab_newkey // (lua_State *L, GCtab *t, TValue *k) | 4104 | | bl extern lj_tab_newkey // (lua_State *L, GCtab *t, TValue *k) |
| 3874 | | // Returns TValue *. | 4105 | | // Returns TValue *. |
| 3875 | | lwz BASE, L->base | 4106 | | lp BASE, L->base |
| 3876 | | stfd f14, 0(CRET1) | 4107 | | stfd f14, 0(CRET1) |
| 3877 | | b <3 // No 2nd write barrier needed. | 4108 | | b <3 // No 2nd write barrier needed. |
| 3878 | | | 4109 | | |
| @@ -3895,7 +4126,7 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 3895 | | lwzx TMP1, TMP2, RC | 4126 | | lwzx TMP1, TMP2, RC |
| 3896 | | checknil TMP1; beq >5 | 4127 | | checknil TMP1; beq >5 |
| 3897 | |1: | 4128 | |1: |
| 3898 | | andi. TMP0, TMP3, LJ_GC_BLACK // isblack(table) | 4129 | | andix. TMP0, TMP3, LJ_GC_BLACK // isblack(table) |
| 3899 | | stfdx f14, TMP2, RC | 4130 | | stfdx f14, TMP2, RC |
| 3900 | | bne >7 | 4131 | | bne >7 |
| 3901 | |2: | 4132 | |2: |
| @@ -3906,7 +4137,7 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 3906 | | cmplwi TAB:TMP1, 0 | 4137 | | cmplwi TAB:TMP1, 0 |
| 3907 | | beq <1 // No metatable: done. | 4138 | | beq <1 // No metatable: done. |
| 3908 | | lbz TMP1, TAB:TMP1->nomm | 4139 | | lbz TMP1, TAB:TMP1->nomm |
| 3909 | | andi. TMP1, TMP1, 1<<MM_newindex | 4140 | | andix. TMP1, TMP1, 1<<MM_newindex |
| 3910 | | bne <1 // 'no __newindex' flag set: done. | 4141 | | bne <1 // 'no __newindex' flag set: done. |
| 3911 | | b ->vmeta_tsetb // Caveat: preserve TMP0! | 4142 | | b ->vmeta_tsetb // Caveat: preserve TMP0! |
| 3912 | | | 4143 | | |
| @@ -3934,7 +4165,7 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 3934 | | lwz TMP0, TAB:CARG2->array | 4165 | | lwz TMP0, TAB:CARG2->array |
| 3935 | | bgt >5 | 4166 | | bgt >5 |
| 3936 | | add TMP1, TMP1, TMP0 | 4167 | | add TMP1, TMP1, TMP0 |
| 3937 | | andi. TMP0, TMP3, LJ_GC_BLACK // isblack(table) | 4168 | | andix. TMP0, TMP3, LJ_GC_BLACK // isblack(table) |
| 3938 | |3: // Copy result slots to table. | 4169 | |3: // Copy result slots to table. |
| 3939 | | lfd f0, 0(RA) | 4170 | | lfd f0, 0(RA) |
| 3940 | | addi RA, RA, 8 | 4171 | | addi RA, RA, 8 |
| @@ -3947,7 +4178,7 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 3947 | | ins_next | 4178 | | ins_next |
| 3948 | | | 4179 | | |
| 3949 | |5: // Need to resize array part. | 4180 | |5: // Need to resize array part. |
| 3950 | | stw BASE, L->base | 4181 | | stp BASE, L->base |
| 3951 | | mr CARG1, L | 4182 | | mr CARG1, L |
| 3952 | | stw PC, SAVE_PC | 4183 | | stw PC, SAVE_PC |
| 3953 | | mr SAVE0, RD | 4184 | | mr SAVE0, RD |
| @@ -3994,7 +4225,7 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 3994 | | addi RA, RA, 8 | 4225 | | addi RA, RA, 8 |
| 3995 | | bne ->vmeta_callt | 4226 | | bne ->vmeta_callt |
| 3996 | |->BC_CALLT_Z: | 4227 | |->BC_CALLT_Z: |
| 3997 | | andi. TMP0, TMP1, FRAME_TYPE // Caveat: preserve cr0 until the crand. | 4228 | | andix. TMP0, TMP1, FRAME_TYPE // Caveat: preserve cr0 until the crand. |
| 3998 | | lbz TMP3, LFUNC:RB->ffid | 4229 | | lbz TMP3, LFUNC:RB->ffid |
| 3999 | | xori TMP2, TMP1, FRAME_VARG | 4230 | | xori TMP2, TMP1, FRAME_VARG |
| 4000 | | cmplwi cr1, NARGS8:RC, 0 | 4231 | | cmplwi cr1, NARGS8:RC, 0 |
| @@ -4027,11 +4258,11 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 4027 | | b <4 | 4258 | | b <4 |
| 4028 | | | 4259 | | |
| 4029 | |7: // Tailcall from a vararg function. | 4260 | |7: // Tailcall from a vararg function. |
| 4030 | | andi. TMP0, TMP2, FRAME_TYPEP | 4261 | | andix. TMP0, TMP2, FRAME_TYPEP |
| 4031 | | bne <1 // Vararg frame below? | 4262 | | bne <1 // Vararg frame below? |
| 4032 | | sub BASE, BASE, TMP2 // Relocate BASE down. | 4263 | | sub BASE, BASE, TMP2 // Relocate BASE down. |
| 4033 | | lwz TMP1, FRAME_PC(BASE) | 4264 | | lwz TMP1, FRAME_PC(BASE) |
| 4034 | | andi. TMP0, TMP1, FRAME_TYPE | 4265 | | andix. TMP0, TMP1, FRAME_TYPE |
| 4035 | | b <1 | 4266 | | b <1 |
| 4036 | break; | 4267 | break; |
| 4037 | 4268 | ||
| @@ -4169,7 +4400,12 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 4169 | | sub RC, RC, TMP0 // RC = vbase | 4400 | | sub RC, RC, TMP0 // RC = vbase |
| 4170 | | // Note: RC may now be even _above_ BASE if nargs was < numparams. | 4401 | | // Note: RC may now be even _above_ BASE if nargs was < numparams. |
| 4171 | | cmplwi cr1, RB, 0 | 4402 | | cmplwi cr1, RB, 0 |
| 4403 | |.if PPE | ||
| 4404 | | sub TMP1, TMP3, RC | ||
| 4405 | | cmpwi TMP1, 0 | ||
| 4406 | |.else | ||
| 4172 | | sub. TMP1, TMP3, RC | 4407 | | sub. TMP1, TMP3, RC |
| 4408 | |.endif | ||
| 4173 | | beq cr1, >5 // Copy all varargs? | 4409 | | beq cr1, >5 // Copy all varargs? |
| 4174 | | subi TMP2, TMP2, 16 | 4410 | | subi TMP2, TMP2, 16 |
| 4175 | | ble >2 // No vararg slots? | 4411 | | ble >2 // No vararg slots? |
| @@ -4209,14 +4445,14 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 4209 | | | 4445 | | |
| 4210 | |7: // Grow stack for varargs. | 4446 | |7: // Grow stack for varargs. |
| 4211 | | mr CARG1, L | 4447 | | mr CARG1, L |
| 4212 | | stw RA, L->top | 4448 | | stp RA, L->top |
| 4213 | | sub SAVE0, RC, BASE // Need delta, because BASE may change. | 4449 | | sub SAVE0, RC, BASE // Need delta, because BASE may change. |
| 4214 | | stw BASE, L->base | 4450 | | stp BASE, L->base |
| 4215 | | sub RA, RA, BASE | 4451 | | sub RA, RA, BASE |
| 4216 | | stw PC, SAVE_PC | 4452 | | stw PC, SAVE_PC |
| 4217 | | srwi CARG2, TMP1, 3 | 4453 | | srwi CARG2, TMP1, 3 |
| 4218 | | bl extern lj_state_growstack // (lua_State *L, int n) | 4454 | | bl extern lj_state_growstack // (lua_State *L, int n) |
| 4219 | | lwz BASE, L->base | 4455 | | lp BASE, L->base |
| 4220 | | add RA, BASE, RA | 4456 | | add RA, BASE, RA |
| 4221 | | add RC, BASE, SAVE0 | 4457 | | add RC, BASE, SAVE0 |
| 4222 | | subi TMP3, BASE, 8 | 4458 | | subi TMP3, BASE, 8 |
| @@ -4237,7 +4473,7 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 4237 | | add RA, BASE, RA | 4473 | | add RA, BASE, RA |
| 4238 | | mr MULTRES, RD | 4474 | | mr MULTRES, RD |
| 4239 | |1: | 4475 | |1: |
| 4240 | | andi. TMP0, PC, FRAME_TYPE | 4476 | | andix. TMP0, PC, FRAME_TYPE |
| 4241 | | xori TMP1, PC, FRAME_VARG | 4477 | | xori TMP1, PC, FRAME_VARG |
| 4242 | | bne ->BC_RETV_Z | 4478 | | bne ->BC_RETV_Z |
| 4243 | | | 4479 | | |
| @@ -4280,7 +4516,7 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 4280 | | b <5 | 4516 | | b <5 |
| 4281 | | | 4517 | | |
| 4282 | |->BC_RETV_Z: // Non-standard return case. | 4518 | |->BC_RETV_Z: // Non-standard return case. |
| 4283 | | andi. TMP2, TMP1, FRAME_TYPEP | 4519 | | andix. TMP2, TMP1, FRAME_TYPEP |
| 4284 | | bne ->vm_return | 4520 | | bne ->vm_return |
| 4285 | | // Return from vararg function: relocate BASE down. | 4521 | | // Return from vararg function: relocate BASE down. |
| 4286 | | sub BASE, BASE, TMP1 | 4522 | | sub BASE, BASE, TMP1 |
| @@ -4293,7 +4529,7 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 4293 | | lwz PC, FRAME_PC(BASE) | 4529 | | lwz PC, FRAME_PC(BASE) |
| 4294 | | add RA, BASE, RA | 4530 | | add RA, BASE, RA |
| 4295 | | mr MULTRES, RD | 4531 | | mr MULTRES, RD |
| 4296 | | andi. TMP0, PC, FRAME_TYPE | 4532 | | andix. TMP0, PC, FRAME_TYPE |
| 4297 | | xori TMP1, PC, FRAME_VARG | 4533 | | xori TMP1, PC, FRAME_VARG |
| 4298 | | bney ->BC_RETV_Z | 4534 | | bney ->BC_RETV_Z |
| 4299 | | | 4535 | | |
| @@ -4348,7 +4584,15 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 4348 | if (vk) { | 4584 | if (vk) { |
| 4349 | | lwz CARG3, FORL_STEP*8+4(RA) | 4585 | | lwz CARG3, FORL_STEP*8+4(RA) |
| 4350 | | bne >9 | 4586 | | bne >9 |
| 4587 | |.if GPR64 | ||
| 4588 | | // Need to check overflow for (a<<32) + (b<<32). | ||
| 4589 | | rldicr TMP0, CARG1, 32, 31 | ||
| 4590 | | rldicr TMP2, CARG3, 32, 31 | ||
| 4591 | | add CARG1, CARG1, CARG3 | ||
| 4592 | | addo. TMP0, TMP0, TMP2 | ||
| 4593 | |.else | ||
| 4351 | | addo. CARG1, CARG1, CARG3 | 4594 | | addo. CARG1, CARG1, CARG3 |
| 4595 | |.endif | ||
| 4352 | | cmpwi cr6, CARG3, 0 | 4596 | | cmpwi cr6, CARG3, 0 |
| 4353 | | lwz CARG2, FORL_STOP*8+4(RA) | 4597 | | lwz CARG2, FORL_STOP*8+4(RA) |
| 4354 | | bso >6 | 4598 | | bso >6 |
| @@ -4536,7 +4780,7 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 4536 | | stw ZERO, DISPATCH_GL(vmstate)(DISPATCH) | 4780 | | stw ZERO, DISPATCH_GL(vmstate)(DISPATCH) |
| 4537 | | lwzx TRACE:TMP2, TMP1, RD | 4781 | | lwzx TRACE:TMP2, TMP1, RD |
| 4538 | | mcrxr cr0 // Clear SO flag. | 4782 | | mcrxr cr0 // Clear SO flag. |
| 4539 | | lwz TMP2, TRACE:TMP2->mcode | 4783 | | lp TMP2, TRACE:TMP2->mcode |
| 4540 | | stw BASE, DISPATCH_GL(jit_base)(DISPATCH) | 4784 | | stw BASE, DISPATCH_GL(jit_base)(DISPATCH) |
| 4541 | | mtctr TMP2 | 4785 | | mtctr TMP2 |
| 4542 | | stw L, DISPATCH_GL(jit_L)(DISPATCH) | 4786 | | stw L, DISPATCH_GL(jit_L)(DISPATCH) |
| @@ -4642,29 +4886,33 @@ static void build_ins(BuildCtx *ctx, BCOp op, int defop) | |||
| 4642 | case BC_FUNCCW: | 4886 | case BC_FUNCCW: |
| 4643 | | // BASE = new base, RA = BASE+framesize*8, RB = CFUNC, RC = nargs*8 | 4887 | | // BASE = new base, RA = BASE+framesize*8, RB = CFUNC, RC = nargs*8 |
| 4644 | if (op == BC_FUNCC) { | 4888 | if (op == BC_FUNCC) { |
| 4645 | | lwz TMP3, CFUNC:RB->f | 4889 | | lp RD, CFUNC:RB->f |
| 4646 | } else { | 4890 | } else { |
| 4647 | | lwz TMP3, DISPATCH_GL(wrapf)(DISPATCH) | 4891 | | lp RD, DISPATCH_GL(wrapf)(DISPATCH) |
| 4648 | } | 4892 | } |
| 4649 | | add TMP1, RA, NARGS8:RC | 4893 | | add TMP1, RA, NARGS8:RC |
| 4650 | | lwz TMP2, L->maxstack | 4894 | | lwz TMP2, L->maxstack |
| 4895 | | .toc lp TMP3, 0(RD) | ||
| 4651 | | add RC, BASE, NARGS8:RC | 4896 | | add RC, BASE, NARGS8:RC |
| 4652 | | stw BASE, L->base | 4897 | | stp BASE, L->base |
| 4653 | | cmplw TMP1, TMP2 | 4898 | | cmplw TMP1, TMP2 |
| 4654 | | stw RC, L->top | 4899 | | stp RC, L->top |
| 4655 | | li_vmstate C | 4900 | | li_vmstate C |
| 4656 | | mtctr TMP3 | 4901 | | mtctr TMP3 |
| 4657 | if (op == BC_FUNCCW) { | 4902 | if (op == BC_FUNCCW) { |
| 4658 | | lwz CARG2, CFUNC:RB->f | 4903 | | lp CARG2, CFUNC:RB->f |
| 4659 | } | 4904 | } |
| 4660 | | mr CARG1, L | 4905 | | mr CARG1, L |
| 4661 | | bgt ->vm_growstack_c // Need to grow stack. | 4906 | | bgt ->vm_growstack_c // Need to grow stack. |
| 4907 | | .toc lp TOCREG, TOC_OFS(RD) | ||
| 4908 | | .tocenv lp ENVREG, ENV_OFS(RD) | ||
| 4662 | | st_vmstate | 4909 | | st_vmstate |
| 4663 | | bctrl // (lua_State *L [, lua_CFunction f]) | 4910 | | bctrl // (lua_State *L [, lua_CFunction f]) |
| 4664 | | // Returns nresults. | 4911 | | // Returns nresults. |
| 4665 | | lwz BASE, L->base | 4912 | | lp BASE, L->base |
| 4913 | | .toc ld TOCREG, SAVE_TOC | ||
| 4666 | | slwi RD, CRET1, 3 | 4914 | | slwi RD, CRET1, 3 |
| 4667 | | lwz TMP1, L->top | 4915 | | lp TMP1, L->top |
| 4668 | | li_vmstate INTERP | 4916 | | li_vmstate INTERP |
| 4669 | | lwz PC, FRAME_PC(BASE) // Fetch PC of caller. | 4917 | | lwz PC, FRAME_PC(BASE) // Fetch PC of caller. |
| 4670 | | sub RA, TMP1, RD // RA = L->top - nresults*8 | 4918 | | sub RA, TMP1, RD // RA = L->top - nresults*8 |
