version 1.1.1.1, 2012/02/21 23:05:52
|
version 1.1.1.2, 2012/02/21 23:50:25
|
Line 1
|
Line 1
|
/* |
/* |
* Stack-less Just-In-Time compiler |
* Stack-less Just-In-Time compiler |
* |
* |
* Copyright 2009-2010 Zoltan Herczeg (hzmester@freemail.hu). All rights reserved. | * Copyright 2009-2012 Zoltan Herczeg (hzmester@freemail.hu). All rights reserved. |
* |
* |
* Redistribution and use in source and binary forms, with or without modification, are |
* Redistribution and use in source and binary forms, with or without modification, are |
* permitted provided that the following conditions are met: |
* permitted provided that the following conditions are met: |
Line 26
|
Line 26
|
|
|
SLJIT_API_FUNC_ATTRIBUTE SLJIT_CONST char* sljit_get_platform_name() |
SLJIT_API_FUNC_ATTRIBUTE SLJIT_CONST char* sljit_get_platform_name() |
{ |
{ |
#if (defined SLJIT_CONFIG_MIPS_32 && SLJIT_CONFIG_MIPS_32) | return "MIPS" SLJIT_CPUINFO; |
return "mips-32"; | |
#else | |
#error "mips-64 is not yet supported" | |
#endif | |
} |
} |
|
|
/* Latest MIPS architecture. */ |
/* Latest MIPS architecture. */ |
Line 109 typedef sljit_ui sljit_ins;
|
Line 105 typedef sljit_ui sljit_ins;
|
#define BREAK (HI(0) | LO(13)) |
#define BREAK (HI(0) | LO(13)) |
#define C_UN_D (HI(17) | FMT_D | LO(49)) |
#define C_UN_D (HI(17) | FMT_D | LO(49)) |
#define C_UEQ_D (HI(17) | FMT_D | LO(51)) |
#define C_UEQ_D (HI(17) | FMT_D | LO(51)) |
|
#define C_ULE_D (HI(17) | FMT_D | LO(55)) |
#define C_ULT_D (HI(17) | FMT_D | LO(53)) |
#define C_ULT_D (HI(17) | FMT_D | LO(53)) |
|
#define DIV (HI(0) | LO(26)) |
|
#define DIVU (HI(0) | LO(27)) |
#define DIV_D (HI(17) | FMT_D | LO(3)) |
#define DIV_D (HI(17) | FMT_D | LO(3)) |
#define J (HI(2)) |
#define J (HI(2)) |
#define JAL (HI(3)) |
#define JAL (HI(3)) |
Line 128 typedef sljit_ui sljit_ins;
|
Line 127 typedef sljit_ui sljit_ins;
|
#define MOVZ (HI(0) | LO(10)) |
#define MOVZ (HI(0) | LO(10)) |
#define MUL_D (HI(17) | FMT_D | LO(2)) |
#define MUL_D (HI(17) | FMT_D | LO(2)) |
#define MULT (HI(0) | LO(24)) |
#define MULT (HI(0) | LO(24)) |
|
#define MULTU (HI(0) | LO(25)) |
#define NOP (HI(0) | LO(0)) |
#define NOP (HI(0) | LO(0)) |
#define NOR (HI(0) | LO(39)) |
#define NOR (HI(0) | LO(39)) |
#define OR (HI(0) | LO(37)) |
#define OR (HI(0) | LO(37)) |
Line 455 static int emit_op(struct sljit_compiler *compiler, in
|
Line 455 static int emit_op(struct sljit_compiler *compiler, in
|
int src1, sljit_w src1w, |
int src1, sljit_w src1w, |
int src2, sljit_w src2w); |
int src2, sljit_w src2w); |
|
|
SLJIT_API_FUNC_ATTRIBUTE int sljit_emit_enter(struct sljit_compiler *compiler, int args, int temporaries, int generals, int local_size) | SLJIT_API_FUNC_ATTRIBUTE int sljit_emit_enter(struct sljit_compiler *compiler, int args, int temporaries, int saveds, int local_size) |
{ |
{ |
sljit_ins base; |
sljit_ins base; |
|
|
CHECK_ERROR(); |
CHECK_ERROR(); |
check_sljit_emit_enter(compiler, args, temporaries, generals, local_size); | check_sljit_emit_enter(compiler, args, temporaries, saveds, local_size); |
|
|
compiler->temporaries = temporaries; |
compiler->temporaries = temporaries; |
compiler->generals = generals; | compiler->saveds = saveds; |
|
|
compiler->has_locals = local_size > 0; |
compiler->has_locals = local_size > 0; |
local_size += (generals + 2 + 4) * sizeof(sljit_w); | local_size += (saveds + 2 + 4) * sizeof(sljit_w); |
local_size = (local_size + 15) & ~0xf; |
local_size = (local_size + 15) & ~0xf; |
compiler->local_size = local_size; |
compiler->local_size = local_size; |
|
|
Line 486 SLJIT_API_FUNC_ATTRIBUTE int sljit_emit_enter(struct s
|
Line 486 SLJIT_API_FUNC_ATTRIBUTE int sljit_emit_enter(struct s
|
FAIL_IF(push_inst(compiler, STACK_STORE | base | TA(RETURN_ADDR_REG) | IMM(local_size - 1 * (int)sizeof(sljit_w)), MOVABLE_INS)); |
FAIL_IF(push_inst(compiler, STACK_STORE | base | TA(RETURN_ADDR_REG) | IMM(local_size - 1 * (int)sizeof(sljit_w)), MOVABLE_INS)); |
if (compiler->has_locals) |
if (compiler->has_locals) |
FAIL_IF(push_inst(compiler, STACK_STORE | base | T(SLJIT_LOCALS_REG) | IMM(local_size - 2 * (int)sizeof(sljit_w)), MOVABLE_INS)); |
FAIL_IF(push_inst(compiler, STACK_STORE | base | T(SLJIT_LOCALS_REG) | IMM(local_size - 2 * (int)sizeof(sljit_w)), MOVABLE_INS)); |
if (generals >= 1) | if (saveds >= 1) |
FAIL_IF(push_inst(compiler, STACK_STORE | base | T(SLJIT_GENERAL_REG1) | IMM(local_size - 3 * (int)sizeof(sljit_w)), MOVABLE_INS)); | FAIL_IF(push_inst(compiler, STACK_STORE | base | T(SLJIT_SAVED_REG1) | IMM(local_size - 3 * (int)sizeof(sljit_w)), MOVABLE_INS)); |
if (generals >= 2) | if (saveds >= 2) |
FAIL_IF(push_inst(compiler, STACK_STORE | base | T(SLJIT_GENERAL_REG2) | IMM(local_size - 4 * (int)sizeof(sljit_w)), MOVABLE_INS)); | FAIL_IF(push_inst(compiler, STACK_STORE | base | T(SLJIT_SAVED_REG2) | IMM(local_size - 4 * (int)sizeof(sljit_w)), MOVABLE_INS)); |
if (generals >= 3) | if (saveds >= 3) |
FAIL_IF(push_inst(compiler, STACK_STORE | base | T(SLJIT_GENERAL_REG3) | IMM(local_size - 5 * (int)sizeof(sljit_w)), MOVABLE_INS)); | FAIL_IF(push_inst(compiler, STACK_STORE | base | T(SLJIT_SAVED_REG3) | IMM(local_size - 5 * (int)sizeof(sljit_w)), MOVABLE_INS)); |
if (generals >= 4) | if (saveds >= 4) |
FAIL_IF(push_inst(compiler, STACK_STORE | base | T(SLJIT_GENERAL_EREG1) | IMM(local_size - 6 * (int)sizeof(sljit_w)), MOVABLE_INS)); | FAIL_IF(push_inst(compiler, STACK_STORE | base | T(SLJIT_SAVED_EREG1) | IMM(local_size - 6 * (int)sizeof(sljit_w)), MOVABLE_INS)); |
if (generals >= 5) | if (saveds >= 5) |
FAIL_IF(push_inst(compiler, STACK_STORE | base | T(SLJIT_GENERAL_EREG2) | IMM(local_size - 7 * (int)sizeof(sljit_w)), MOVABLE_INS)); | FAIL_IF(push_inst(compiler, STACK_STORE | base | T(SLJIT_SAVED_EREG2) | IMM(local_size - 7 * (int)sizeof(sljit_w)), MOVABLE_INS)); |
|
|
if (compiler->has_locals) |
if (compiler->has_locals) |
FAIL_IF(push_inst(compiler, ADDIU_W | S(REAL_STACK_PTR) | T(SLJIT_LOCALS_REG) | IMM(4 * sizeof(sljit_w)), DR(SLJIT_LOCALS_REG))); |
FAIL_IF(push_inst(compiler, ADDIU_W | S(REAL_STACK_PTR) | T(SLJIT_LOCALS_REG) | IMM(4 * sizeof(sljit_w)), DR(SLJIT_LOCALS_REG))); |
|
|
if (args >= 1) |
if (args >= 1) |
FAIL_IF(push_inst(compiler, ADDU_W | SA(4) | TA(0) | D(SLJIT_GENERAL_REG1), DR(SLJIT_GENERAL_REG1))); | FAIL_IF(push_inst(compiler, ADDU_W | SA(4) | TA(0) | D(SLJIT_SAVED_REG1), DR(SLJIT_SAVED_REG1))); |
if (args >= 2) |
if (args >= 2) |
FAIL_IF(push_inst(compiler, ADDU_W | SA(5) | TA(0) | D(SLJIT_GENERAL_REG2), DR(SLJIT_GENERAL_REG2))); | FAIL_IF(push_inst(compiler, ADDU_W | SA(5) | TA(0) | D(SLJIT_SAVED_REG2), DR(SLJIT_SAVED_REG2))); |
if (args >= 3) |
if (args >= 3) |
FAIL_IF(push_inst(compiler, ADDU_W | SA(6) | TA(0) | D(SLJIT_GENERAL_REG3), DR(SLJIT_GENERAL_REG3))); | FAIL_IF(push_inst(compiler, ADDU_W | SA(6) | TA(0) | D(SLJIT_SAVED_REG3), DR(SLJIT_SAVED_REG3))); |
|
|
return SLJIT_SUCCESS; |
return SLJIT_SUCCESS; |
} |
} |
|
|
SLJIT_API_FUNC_ATTRIBUTE void sljit_fake_enter(struct sljit_compiler *compiler, int args, int temporaries, int generals, int local_size) | SLJIT_API_FUNC_ATTRIBUTE void sljit_set_context(struct sljit_compiler *compiler, int args, int temporaries, int saveds, int local_size) |
{ |
{ |
CHECK_ERROR_VOID(); |
CHECK_ERROR_VOID(); |
check_sljit_fake_enter(compiler, args, temporaries, generals, local_size); | check_sljit_set_context(compiler, args, temporaries, saveds, local_size); |
|
|
compiler->temporaries = temporaries; |
compiler->temporaries = temporaries; |
compiler->generals = generals; | compiler->saveds = saveds; |
|
|
compiler->has_locals = local_size > 0; |
compiler->has_locals = local_size > 0; |
local_size += (generals + 2 + 4) * sizeof(sljit_w); | local_size += (saveds + 2 + 4) * sizeof(sljit_w); |
compiler->local_size = (local_size + 15) & ~0xf; |
compiler->local_size = (local_size + 15) & ~0xf; |
} |
} |
|
|
SLJIT_API_FUNC_ATTRIBUTE int sljit_emit_return(struct sljit_compiler *compiler, int src, sljit_w srcw) | SLJIT_API_FUNC_ATTRIBUTE int sljit_emit_return(struct sljit_compiler *compiler, int op, int src, sljit_w srcw) |
{ |
{ |
int local_size; |
int local_size; |
sljit_ins base; |
sljit_ins base; |
|
|
CHECK_ERROR(); |
CHECK_ERROR(); |
check_sljit_emit_return(compiler, src, srcw); | check_sljit_emit_return(compiler, op, src, srcw); |
|
|
local_size = compiler->local_size; | FAIL_IF(emit_mov_before_return(compiler, op, src, srcw)); |
|
|
if (src != SLJIT_UNUSED && src != SLJIT_RETURN_REG) | local_size = compiler->local_size; |
FAIL_IF(emit_op(compiler, SLJIT_MOV, WORD_DATA, SLJIT_RETURN_REG, 0, TMP_REG1, 0, src, srcw)); | |
| |
if (local_size <= SIMM_MAX) |
if (local_size <= SIMM_MAX) |
base = S(REAL_STACK_PTR); |
base = S(REAL_STACK_PTR); |
else { |
else { |
Line 546 SLJIT_API_FUNC_ATTRIBUTE int sljit_emit_return(struct
|
Line 544 SLJIT_API_FUNC_ATTRIBUTE int sljit_emit_return(struct
|
} |
} |
|
|
FAIL_IF(push_inst(compiler, STACK_LOAD | base | TA(RETURN_ADDR_REG) | IMM(local_size - 1 * (int)sizeof(sljit_w)), RETURN_ADDR_REG)); |
FAIL_IF(push_inst(compiler, STACK_LOAD | base | TA(RETURN_ADDR_REG) | IMM(local_size - 1 * (int)sizeof(sljit_w)), RETURN_ADDR_REG)); |
if (compiler->generals >= 5) | if (compiler->saveds >= 5) |
FAIL_IF(push_inst(compiler, STACK_LOAD | base | T(SLJIT_GENERAL_EREG2) | IMM(local_size - 7 * (int)sizeof(sljit_w)), DR(SLJIT_GENERAL_EREG2))); | FAIL_IF(push_inst(compiler, STACK_LOAD | base | T(SLJIT_SAVED_EREG2) | IMM(local_size - 7 * (int)sizeof(sljit_w)), DR(SLJIT_SAVED_EREG2))); |
if (compiler->generals >= 4) | if (compiler->saveds >= 4) |
FAIL_IF(push_inst(compiler, STACK_LOAD | base | T(SLJIT_GENERAL_EREG1) | IMM(local_size - 6 * (int)sizeof(sljit_w)), DR(SLJIT_GENERAL_EREG1))); | FAIL_IF(push_inst(compiler, STACK_LOAD | base | T(SLJIT_SAVED_EREG1) | IMM(local_size - 6 * (int)sizeof(sljit_w)), DR(SLJIT_SAVED_EREG1))); |
if (compiler->generals >= 3) | if (compiler->saveds >= 3) |
FAIL_IF(push_inst(compiler, STACK_LOAD | base | T(SLJIT_GENERAL_REG3) | IMM(local_size - 5 * (int)sizeof(sljit_w)), DR(SLJIT_GENERAL_REG3))); | FAIL_IF(push_inst(compiler, STACK_LOAD | base | T(SLJIT_SAVED_REG3) | IMM(local_size - 5 * (int)sizeof(sljit_w)), DR(SLJIT_SAVED_REG3))); |
if (compiler->generals >= 2) | if (compiler->saveds >= 2) |
FAIL_IF(push_inst(compiler, STACK_LOAD | base | T(SLJIT_GENERAL_REG2) | IMM(local_size - 4 * (int)sizeof(sljit_w)), DR(SLJIT_GENERAL_REG2))); | FAIL_IF(push_inst(compiler, STACK_LOAD | base | T(SLJIT_SAVED_REG2) | IMM(local_size - 4 * (int)sizeof(sljit_w)), DR(SLJIT_SAVED_REG2))); |
if (compiler->generals >= 1) | if (compiler->saveds >= 1) |
FAIL_IF(push_inst(compiler, STACK_LOAD | base | T(SLJIT_GENERAL_REG1) | IMM(local_size - 3 * (int)sizeof(sljit_w)), DR(SLJIT_GENERAL_REG1))); | FAIL_IF(push_inst(compiler, STACK_LOAD | base | T(SLJIT_SAVED_REG1) | IMM(local_size - 3 * (int)sizeof(sljit_w)), DR(SLJIT_SAVED_REG1))); |
if (compiler->has_locals) |
if (compiler->has_locals) |
FAIL_IF(push_inst(compiler, STACK_LOAD | base | T(SLJIT_LOCALS_REG) | IMM(local_size - 2 * (int)sizeof(sljit_w)), DR(SLJIT_LOCALS_REG))); |
FAIL_IF(push_inst(compiler, STACK_LOAD | base | T(SLJIT_LOCALS_REG) | IMM(local_size - 2 * (int)sizeof(sljit_w)), DR(SLJIT_LOCALS_REG))); |
|
|
Line 929 SLJIT_API_FUNC_ATTRIBUTE int sljit_emit_op0(struct slj
|
Line 927 SLJIT_API_FUNC_ATTRIBUTE int sljit_emit_op0(struct slj
|
return push_inst(compiler, BREAK, UNMOVABLE_INS); |
return push_inst(compiler, BREAK, UNMOVABLE_INS); |
case SLJIT_NOP: |
case SLJIT_NOP: |
return push_inst(compiler, NOP, UNMOVABLE_INS); |
return push_inst(compiler, NOP, UNMOVABLE_INS); |
|
case SLJIT_UMUL: |
|
case SLJIT_SMUL: |
|
FAIL_IF(push_inst(compiler, (op == SLJIT_UMUL ? MULTU : MULT) | S(SLJIT_TEMPORARY_REG1) | T(SLJIT_TEMPORARY_REG2), MOVABLE_INS)); |
|
FAIL_IF(push_inst(compiler, MFLO | D(SLJIT_TEMPORARY_REG1), DR(SLJIT_TEMPORARY_REG1))); |
|
return push_inst(compiler, MFHI | D(SLJIT_TEMPORARY_REG2), DR(SLJIT_TEMPORARY_REG2)); |
|
case SLJIT_UDIV: |
|
case SLJIT_SDIV: |
|
#if !(defined SLJIT_MIPS_32_64 && SLJIT_MIPS_32_64) |
|
FAIL_IF(push_inst(compiler, NOP, UNMOVABLE_INS)); |
|
FAIL_IF(push_inst(compiler, NOP, UNMOVABLE_INS)); |
|
#endif |
|
FAIL_IF(push_inst(compiler, (op == SLJIT_UDIV ? DIVU : DIV) | S(SLJIT_TEMPORARY_REG1) | T(SLJIT_TEMPORARY_REG2), MOVABLE_INS)); |
|
FAIL_IF(push_inst(compiler, MFLO | D(SLJIT_TEMPORARY_REG1), DR(SLJIT_TEMPORARY_REG1))); |
|
return push_inst(compiler, MFHI | D(SLJIT_TEMPORARY_REG2), DR(SLJIT_TEMPORARY_REG2)); |
} |
} |
|
|
return SLJIT_SUCCESS; |
return SLJIT_SUCCESS; |
Line 1054 SLJIT_API_FUNC_ATTRIBUTE int sljit_emit_op2(struct slj
|
Line 1066 SLJIT_API_FUNC_ATTRIBUTE int sljit_emit_op2(struct slj
|
#endif |
#endif |
} |
} |
|
|
|
SLJIT_API_FUNC_ATTRIBUTE int sljit_get_register_index(int reg) |
|
{ |
|
check_sljit_get_register_index(reg); |
|
return reg_map[reg]; |
|
} |
|
|
|
SLJIT_API_FUNC_ATTRIBUTE int sljit_emit_op_custom(struct sljit_compiler *compiler, |
|
void *instruction, int size) |
|
{ |
|
CHECK_ERROR(); |
|
check_sljit_emit_op_custom(compiler, instruction, size); |
|
SLJIT_ASSERT(size == 4); |
|
|
|
return push_inst(compiler, *(sljit_ins*)instruction, UNMOVABLE_INS); |
|
} |
|
|
/* --------------------------------------------------------------------- */ |
/* --------------------------------------------------------------------- */ |
/* Floating point operators */ |
/* Floating point operators */ |
/* --------------------------------------------------------------------- */ |
/* --------------------------------------------------------------------- */ |
Line 1232 SLJIT_API_FUNC_ATTRIBUTE int sljit_emit_fop2(struct sl
|
Line 1260 SLJIT_API_FUNC_ATTRIBUTE int sljit_emit_fop2(struct sl
|
/* Other instructions */ |
/* Other instructions */ |
/* --------------------------------------------------------------------- */ |
/* --------------------------------------------------------------------- */ |
|
|
SLJIT_API_FUNC_ATTRIBUTE int sljit_emit_fast_enter(struct sljit_compiler *compiler, int dst, sljit_w dstw, int args, int temporaries, int generals, int local_size) | SLJIT_API_FUNC_ATTRIBUTE int sljit_emit_fast_enter(struct sljit_compiler *compiler, int dst, sljit_w dstw, int args, int temporaries, int saveds, int local_size) |
{ |
{ |
CHECK_ERROR(); |
CHECK_ERROR(); |
check_sljit_emit_fast_enter(compiler, dst, dstw, args, temporaries, generals, local_size); | check_sljit_emit_fast_enter(compiler, dst, dstw, args, temporaries, saveds, local_size); |
|
|
compiler->temporaries = temporaries; |
compiler->temporaries = temporaries; |
compiler->generals = generals; | compiler->saveds = saveds; |
|
|
compiler->has_locals = local_size > 0; |
compiler->has_locals = local_size > 0; |
local_size += (generals + 2 + 4) * sizeof(sljit_w); | local_size += (saveds + 2 + 4) * sizeof(sljit_w); |
compiler->local_size = (local_size + 15) & ~0xf; |
compiler->local_size = (local_size + 15) & ~0xf; |
|
|
if (dst >= SLJIT_TEMPORARY_REG1 && dst <= SLJIT_NO_REGISTERS) |
if (dst >= SLJIT_TEMPORARY_REG1 && dst <= SLJIT_NO_REGISTERS) |
Line 1554 SLJIT_API_FUNC_ATTRIBUTE struct sljit_jump* sljit_emit
|
Line 1582 SLJIT_API_FUNC_ATTRIBUTE struct sljit_jump* sljit_emit
|
|
|
#undef RESOLVE_IMM1 |
#undef RESOLVE_IMM1 |
#undef RESOLVE_IMM2 |
#undef RESOLVE_IMM2 |
|
|
|
SLJIT_API_FUNC_ATTRIBUTE struct sljit_jump* sljit_emit_fcmp(struct sljit_compiler *compiler, int type, |
|
int src1, sljit_w src1w, |
|
int src2, sljit_w src2w) |
|
{ |
|
struct sljit_jump *jump; |
|
sljit_ins inst; |
|
int if_true; |
|
|
|
CHECK_ERROR_PTR(); |
|
check_sljit_emit_fcmp(compiler, type, src1, src1w, src2, src2w); |
|
|
|
compiler->cache_arg = 0; |
|
compiler->cache_argw = 0; |
|
|
|
if (src1 > SLJIT_FLOAT_REG4) { |
|
PTR_FAIL_IF(emit_fpu_data_transfer(compiler, TMP_FREG1, 1, src1, src1w)); |
|
src1 = TMP_FREG1; |
|
} |
|
if (src2 > SLJIT_FLOAT_REG4) { |
|
PTR_FAIL_IF(emit_fpu_data_transfer(compiler, TMP_FREG2, 1, src2, src2w)); |
|
src2 = TMP_FREG2; |
|
} |
|
|
|
jump = (struct sljit_jump*)ensure_abuf(compiler, sizeof(struct sljit_jump)); |
|
PTR_FAIL_IF(!jump); |
|
set_jump(jump, compiler, type & SLJIT_REWRITABLE_JUMP); |
|
jump->flags |= IS_BIT16_COND; |
|
type &= 0xff; |
|
|
|
switch (type) { |
|
case SLJIT_C_FLOAT_EQUAL: |
|
inst = C_UEQ_D; |
|
if_true = 1; |
|
break; |
|
case SLJIT_C_FLOAT_NOT_EQUAL: |
|
inst = C_UEQ_D; |
|
if_true = 0; |
|
break; |
|
case SLJIT_C_FLOAT_LESS: |
|
inst = C_ULT_D; |
|
if_true = 1; |
|
break; |
|
case SLJIT_C_FLOAT_GREATER_EQUAL: |
|
inst = C_ULT_D; |
|
if_true = 0; |
|
break; |
|
case SLJIT_C_FLOAT_GREATER: |
|
inst = C_ULE_D; |
|
if_true = 0; |
|
break; |
|
case SLJIT_C_FLOAT_LESS_EQUAL: |
|
inst = C_ULE_D; |
|
if_true = 1; |
|
break; |
|
case SLJIT_C_FLOAT_NAN: |
|
inst = C_UN_D; |
|
if_true = 1; |
|
break; |
|
case SLJIT_C_FLOAT_NOT_NAN: |
|
default: /* Make compilers happy. */ |
|
inst = C_UN_D; |
|
if_true = 0; |
|
break; |
|
} |
|
|
|
PTR_FAIL_IF(push_inst(compiler, inst | FT(src2) | FS(src1), UNMOVABLE_INS)); |
|
/* Intentionally the other opcode. */ |
|
PTR_FAIL_IF(push_inst(compiler, (if_true ? BC1F : BC1T) | JUMP_LENGTH, UNMOVABLE_INS)); |
|
PTR_FAIL_IF(emit_const(compiler, TMP_REG2, 0)); |
|
PTR_FAIL_IF(push_inst(compiler, JR | S(TMP_REG2), UNMOVABLE_INS)); |
|
jump->addr = compiler->size; |
|
PTR_FAIL_IF(push_inst(compiler, NOP, UNMOVABLE_INS)); |
|
return jump; |
|
} |
|
|
#undef JUMP_LENGTH |
#undef JUMP_LENGTH |
#undef BR_Z |
#undef BR_Z |