From 5150271f621ecea3bbac3c602fed88be6164e578 Mon Sep 17 00:00:00 2001 From: Rhys Weatherley Date: Tue, 8 Jun 2004 02:30:55 +0000 Subject: [PATCH] More x86 instruction selection rules. --- ChangeLog | 3 + jit/jit-reg-alloc.c | 4 ++ jit/jit-rules-x86.c | 37 +++++++++++ jit/jit-rules-x86.sel | 140 ++++++++++++++++++++++++++++++++++++++++++ 4 files changed, 184 insertions(+) diff --git a/ChangeLog b/ChangeLog index cf4056f..a8ef464 100644 --- a/ChangeLog +++ b/ChangeLog @@ -7,6 +7,9 @@ * include/jit/jit-opcode.h, jit/jit-interp.c, jit/jit-opcode.c: remove obsolete opcodes which violate "_jit_load_opcode"'s rules. + * jit/jit-reg-alloc.c, jit/jit-rules-x86.c, jit/jit-rules-x86.sel: + more x86 instruction selection rules. + 2004-06-08 Miroslaw Dobrzanski-Neumann * jit/jit-alloc.c: fix ROUND_END_PTR so that it adds the size diff --git a/jit/jit-reg-alloc.c b/jit/jit-reg-alloc.c index 7fa88ca..5b0aa43 100644 --- a/jit/jit-reg-alloc.c +++ b/jit/jit-reg-alloc.c @@ -1493,6 +1493,10 @@ void _jit_regs_get_reg_pair(jit_gencode_t gen, int not_this1, int not_this2, } *reg = index; _jit_regs_want_reg(gen, index, 0); + if(!reg2) + { + return; + } for(; index < 8; ++index) { if((_jit_reg_info[index].flags & JIT_REG_WORD) == 0 || diff --git a/jit/jit-rules-x86.c b/jit/jit-rules-x86.c index f2a70ab..435723a 100644 --- a/jit/jit-rules-x86.c +++ b/jit/jit-rules-x86.c @@ -1381,6 +1381,43 @@ static unsigned char *mov_membase_reg_byte return inst; } +/* + * Store a byte value to a memindex address. + */ +static unsigned char *mov_memindex_reg_byte + (unsigned char *inst, int basereg, + unsigned offset, int indexreg, int srcreg) +{ + if(srcreg == X86_EAX || srcreg == X86_EBX || + srcreg == X86_ECX || srcreg == X86_EDX) + { + x86_mov_memindex_reg(inst, basereg, offset, indexreg, + 0, srcreg, 1); + } + else + { + int tempreg; + if(basereg != X86_EAX && indexreg != X86_EAX) + { + tempreg = X86_EAX; + } + else if(basereg != X86_ECX && indexreg != X86_ECX) + { + tempreg = X86_ECX; + } + else + { + tempreg = X86_EDX; + } + x86_push_reg(inst, tempreg); + x86_mov_reg_reg(inst, tempreg, srcreg, 4); + x86_mov_memindex_reg(inst, basereg, offset, indexreg, + 0, tempreg, 1); + x86_pop_reg(inst, tempreg); + } + return inst; +} + /* * Throw a builtin exception. */ diff --git a/jit/jit-rules-x86.sel b/jit/jit-rules-x86.sel index d00602c..9ec1d8d 100644 --- a/jit/jit-rules-x86.sel +++ b/jit/jit-rules-x86.sel @@ -2310,3 +2310,143 @@ JIT_OP_ADD_RELATIVE: unary x86_alu_reg_imm(inst, X86_ADD, $1, insn->value2->address); } } + +/* + * Array element loads and stores. + */ + +JIT_OP_LOAD_ELEMENT_SBYTE: binary + [reg, reg] -> { + x86_widen_memindex(inst, $1, $1, 0, $2, 0, 1, 0); + } + +JIT_OP_LOAD_ELEMENT_UBYTE: binary + [reg, reg] -> { + x86_widen_memindex(inst, $1, $1, 0, $2, 0, 0, 0); + } + +JIT_OP_LOAD_ELEMENT_SHORT: binary + [reg, reg] -> { + x86_widen_memindex(inst, $1, $1, 0, $2, 1, 1, 1); + } + +JIT_OP_LOAD_ELEMENT_USHORT: binary + [reg, reg] -> { + x86_widen_memindex(inst, $1, $1, 0, $2, 1, 0, 1); + } + +JIT_OP_LOAD_ELEMENT_INT: binary + [reg, reg] -> { + x86_mov_reg_memindex(inst, $1, $1, 0, $2, 2, 4); + } + +JIT_OP_LOAD_ELEMENT_LONG: manual + [] -> { + unsigned char *inst; + int reg, reg2, temp_reg, offset; + _jit_regs_force_out(gen, insn->dest, 1); + _jit_gen_fix_value(insn->dest); + reg = _jit_regs_load_value + (gen, insn->value1, 0, + (insn->flags & (JIT_INSN_VALUE1_NEXT_USE | + JIT_INSN_VALUE1_LIVE))); + reg2 = _jit_regs_load_value + (gen, insn->value2, 1, + (insn->flags & (JIT_INSN_VALUE2_NEXT_USE | + JIT_INSN_VALUE2_LIVE))); + _jit_regs_get_reg_pair(gen, reg, reg2, -1, &temp_reg, 0); + offset = insn->dest->frame_offset; + inst = gen->posn.ptr; + if(!jit_cache_check_for_n(&(gen->posn), 32)) + { + jit_cache_mark_full(&(gen->posn)); + return; + } + reg = _jit_reg_info[reg].cpu_reg; + reg2 = _jit_reg_info[reg2].cpu_reg; + temp_reg = _jit_reg_info[temp_reg].cpu_reg; + x86_mov_reg_memindex(inst, temp_reg, reg, 0, reg2, 3, 4); + x86_mov_reg_memindex(inst, reg2, reg, 4, reg2, 3, 4); + x86_mov_membase_reg(inst, X86_EBP, offset, temp_reg, 4); + x86_mov_membase_reg(inst, X86_EBP, offset + 4, reg2, 4); + gen->posn.ptr = inst; + } + +JIT_OP_LOAD_ELEMENT_FLOAT32: manual + [] -> { + /* TODO */ + TODO(); + } + +JIT_OP_LOAD_ELEMENT_FLOAT64: manual + [] -> { + /* TODO */ + TODO(); + } + +JIT_OP_LOAD_ELEMENT_NFLOAT: manual + [] -> { + /* TODO */ + TODO(); + } + +JIT_OP_STORE_ELEMENT_BYTE: ternary + [reg, reg, reg] -> { + inst = mov_memindex_reg_byte(inst, $1, 0, $2, $3); + } + +JIT_OP_STORE_ELEMENT_SHORT: ternary + [reg, reg, reg] -> { + x86_mov_memindex_reg(inst, $1, 0, $2, 1, $3, 2); + } + +JIT_OP_STORE_ELEMENT_INT: ternary + [reg, reg, reg] -> { + x86_mov_memindex_reg(inst, $1, 0, $2, 2, $3, 4); + } + +JIT_OP_STORE_ELEMENT_LONG: manual + [] -> { + /* TODO */ + TODO(); + } + +JIT_OP_STORE_ELEMENT_FLOAT32: ternary + [reg, reg, freg] -> { + /* TODO */ + TODO(); + } + +JIT_OP_STORE_ELEMENT_FLOAT64: ternary + [reg, reg, freg] -> { + /* TODO */ + TODO(); + } + +JIT_OP_STORE_ELEMENT_NFLOAT: ternary + [reg, reg, freg] -> { + /* TODO */ + TODO(); + } + +/* + * Block operations. + */ + +/* +#define JIT_OP_MEMCPY 0x0194 +#define JIT_OP_MEMMOVE 0x0195 +#define JIT_OP_MEMSET 0x0196 +*/ + +/* + * Allocate memory from the stack. + */ + +JIT_OP_ALLOCA: unary + [reg] -> { + x86_alu_reg_imm(inst, X86_ADD, $1, 15); + x86_alu_reg_imm(inst, X86_AND, $1, ~15); + x86_alu_reg_reg(inst, X86_SUB, X86_ESP, $1); + x86_mov_reg_reg(inst, $1, X86_ESP, 4); + }