# New Ticket Created by Jason Gloudon # Please include the string: [perl #21457] # in the subject line of all future correspondence about this issue. # <URL: http://rt.perl.org/rt2/Ticket/Display.html?id=21457 >
Here are some additional ops for the sun4 jit, a bit of name juggling to use templates in the jit directives and register allocation support. -- Jason -- attachment 1 ------------------------------------------------------ url: http://rt.perl.org/rt2/attach/53234/40147/51b1c5/sunjit.patch
Index: jit/sun4/core.jit =================================================================== RCS file: /cvs/public/parrot/jit/sun4/core.jit,v retrieving revision 1.2 diff -u -r1.2 core.jit --- jit/sun4/core.jit 20 May 2002 05:33:01 -0000 1.2 +++ jit/sun4/core.jit 4 Mar 2003 15:09:34 -0000 @@ -13,41 +13,180 @@ emitm_nop(NATIVECODE); } +TEMPLATE Parrot_set_x_x { + if(MAP[1] && MAP[2]){ + jit_emit_mov_rr<_N>(NATIVECODE, MAP[1], MAP[2]); + } + else if(MAP[1]){ + jit_emit_load<_N>(jit_info, interpreter, 2, MAP[1]); + } + else if(MAP[2]){ + jit_emit_store<_N>(jit_info, interpreter, 1, MAP[2]); + } + else { + jit_emit_load<_N>(jit_info, interpreter, 2, ISR1); + jit_emit_store<_N>(jit_info, interpreter, 1, ISR1); + } +} + Parrot_set_i_i { - Parrot_jit_int_load(jit_info, interpreter, 2, emitm_l(0)); - Parrot_jit_int_store(jit_info, interpreter, 1, emitm_l(0)); + Parrot_set_x_x s/<_N>/_i/ } -Parrot_set_i_ic { - Parrot_jit_int_load(jit_info, interpreter, 2, emitm_l(0)); - Parrot_jit_int_store(jit_info, interpreter, 1, emitm_l(0)); +Parrot_set_p_p { + Parrot_set_x_x s/<_N>/_i/ } -Parrot_set_n_nc { - Parrot_jit_int_load(jit_info, interpreter, 2, emitm_l(0)); - Parrot_jit_int_store(jit_info, interpreter, 1, emitm_l(0)); +Parrot_set_s_s { + Parrot_set_x_x s/<_N>/_i/ } Parrot_set_n_n { - Parrot_jit_int_load(jit_info, interpreter, 2, emitm_l(0)); - Parrot_jit_int_store(jit_info, interpreter, 1, emitm_l(0)); + Parrot_set_x_x s/<_N>/_n/ s/ISR/FSR/ +} + +TEMPLATE Parrot_set_x_xc { + if(MAP[1]){ + jit_emit_load<_N>(jit_info, interpreter, 2, MAP[1]); + } + else { + jit_emit_load<_N>(jit_info, interpreter, 2, ISR1); + jit_emit_store<_N>(jit_info, interpreter, 1, ISR1); + } +} + +Parrot_set_i_ic { + Parrot_set_x_xc s/<_N>/_i/ +} + +Parrot_set_n_nc { + Parrot_set_x_xc s/<_N>/_n/ s/ISR/FSR/ } Parrot_set_n_i { - Parrot_jit_float_load(jit_info, interpreter, 2, emitm_f(0)); - emitm_fitod(NATIVECODE, emitm_f(0), emitm_f(2)); - Parrot_jit_float_store(jit_info, interpreter, 1, emitm_f(2)); + /* There's no way to move a value directly between integer and floating + * point registers so the mapped integer register must be written to memory + */ + if(MAP[2]){ + jit_emit_store_i(jit_info, interpreter, 2, MAP[2]); + } + + jit_emit_load_n(jit_info, interpreter, 2, FSR1); + + /* If result register is mapped convert directly into the register */ + if(MAP[1]){ + emitm_fitod(NATIVECODE, FSR1, MAP[1]); + } + else { + emitm_fitod(NATIVECODE, FSR1, FSR2); + jit_emit_store_n(jit_info, interpreter, 1, FSR2); + } } Parrot_set_i_n { - Parrot_jit_float_load(jit_info, interpreter, 2, emitm_f(0)); - emitm_fdtoi(NATIVECODE, emitm_f(0), emitm_f(2)); - Parrot_jit_float_store(jit_info, interpreter, 1, emitm_f(2)); + if(MAP[2]){ + emitm_fdtoi(NATIVECODE, MAP[2], FSR2); + } + else { + jit_emit_load_n(jit_info, interpreter, 2, FSR1); + emitm_fdtoi(NATIVECODE, FSR1, FSR2); + } + + jit_emit_store_n(jit_info, interpreter, 1, FSR2); + + /* No float reg to integer reg move instruction available */ + if(MAP[1]){ + jit_emit_load_i(jit_info, interpreter, 1, MAP[1]); + } +} + +Parrot_set_i_nc { + if(MAP[2]){ + emitm_fdtoi(NATIVECODE, MAP[2], FSR1); + } + else { + jit_emit_load_n(jit_info, interpreter, 2, FSR2); + emitm_fdtoi(NATIVECODE, FSR2, FSR1); + } + + jit_emit_store_n(jit_info, interpreter, 1, FSR1); + + if(MAP[1]){ + jit_emit_load_i(jit_info, interpreter, 1, MAP[1]); + } +} + +TEMPLATE Parrot_binop_x_x { + int arg1, arg2; + + if (MAP[1]) { + arg1 = MAP[1]; + } + else { + arg1 = ISR1; + jit_emit_load<_N>(jit_info, interpreter, 1, ISR1); + } + + if (MAP[2]) { + arg2 = MAP[2]; + } + else { + arg2 = ISR2; + jit_emit_load<_N>(jit_info, interpreter, 2, ISR2); + } + + emitm_<op>(NATIVECODE, arg1, arg2, arg1); + + if(!MAP[1]){ + jit_emit_store<_N>(jit_info, interpreter, 1, ISR1); + } +} + +Parrot_add_i_i { + Parrot_binop_x_x s/<op>/add_r/ s/<_N>/_i/ +} + +Parrot_sub_i_i { + Parrot_binop_x_x s/<op>/sub_r/ s/<_N>/_i/ +} + +Parrot_bor_i_i { + Parrot_binop_x_x s/<op>/or_r/ s/<_N>/_i/ +} + +Parrot_bxor_i_i { + Parrot_binop_x_x s/<op>/xor_r/ s/<_N>/_i/ +} + +Parrot_band_i_i { + Parrot_binop_x_x s/<op>/and_r/ s/<_N>/_i/ +} + +Parrot_add_n_n { + Parrot_binop_x_x s/<op>/faddd/ s/<_N>/_n/ +} + +Parrot_sub_n_n { + Parrot_binop_x_x s/<op>/fsubd/ s/<_N>/_n/ +} + +Parrot_mul_n_n { + Parrot_binop_x_x s/<op>/fmuld/ s/<_N>/_n/ +} + +Parrot_div_n_n { + Parrot_binop_x_x s/<op>/fdivd/ s/<_N>/_n/ } Parrot_if_i_ic { - Parrot_jit_int_load(jit_info, interpreter, 1, emitm_l(0)); - emitm_subcc_r(NATIVECODE, emitm_l(0), emitm_g(0), emitm_g(0)); + if(MAP[1]){ + emitm_subcc_r(NATIVECODE, MAP[1], emitm_g(0), emitm_g(0)); + } + else { + jit_emit_load_i(jit_info, interpreter, 1, ISR1); + emitm_subcc_r(NATIVECODE, ISR1, emitm_g(0), emitm_g(0)); + } + Parrot_jit_bicc(jit_info, emitm_bne, 0, *INT_CONST[2]); emitm_nop(NATIVECODE); } Index: jit/sun4/jit_emit.h =================================================================== RCS file: /cvs/public/parrot/jit/sun4/jit_emit.h,v retrieving revision 1.21 diff -u -r1.21 jit_emit.h --- jit/sun4/jit_emit.h 25 Feb 2003 10:25:43 -0000 1.21 +++ jit/sun4/jit_emit.h 4 Mar 2003 15:09:36 -0000 @@ -72,6 +72,7 @@ emitm_rs1(rs1) | (low14); \ pc +=4 ; } +/* format 3b */ #define emitm_3a(pc, op, rd, op3, rs1, asi, rs2) \ emitm_fmt3(pc, op, rd, op3, rs1, ((asi) << 5) | (rs2)) @@ -231,6 +232,16 @@ /* Floating point operations */ +/* MOV */ +#define emitm_fmovs(pc, rs, rd) emitm_3c(pc, 2, rd, 064, 0, 0001, rs) + +/* Arithmetic operations */ +#define emitm_faddd(pc, rs1, rs2, rd) emitm_3c(pc, 2, rd, 064, rs1, 0102, rs2) +#define emitm_fsubd(pc, rs1, rs2, rd) emitm_3c(pc, 2, rd, 064, rs1, 0106, rs2) +#define emitm_fmuld(pc, rs1, rs2, rd) emitm_3c(pc, 2, rd, 064, rs1, 0112, rs2) +#define emitm_fdivd(pc, rs1, rs2, rd) emitm_3c(pc, 2, rd, 064, rs1, 0116, rs2) + +/* Floating <-> Integer Conversion */ #define emitm_fitod(pc, rs, rd) emitm_3c(pc, 2, rd, 064, 0, 0310, rs) #define emitm_fdtoi(pc, rs, rd) emitm_3c(pc, 2, rd, 064, 0, 0322, rs) @@ -262,6 +273,11 @@ /* Branch */ #define emitm_bicc(pc, a, cond, disp22) emitm_2b(pc, a, cond, 02, disp22) +#define jit_emit_mov_rr_i(pc, dst, src) emitm_mov(pc, src, dst) +#define jit_emit_mov_rr_n(pc, dst, src) { \ + emitm_fmovs(pc, src, dst); \ + emitm_fmovs(pc, (src)+1, (dst)+1); } + /* void main(){ char ar[1024]; @@ -292,15 +308,20 @@ /* The register containing the address of the opmap */ #define Parrot_jit_opmap emitm_i(3) -/* The scratch register used for certain address calculations */ -#define Parrot_jit_tmp emitm_l(7) +/* This scratch register is used for certain address calculations */ +#define ISR1 emitm_l(5) +#define ISR2 emitm_l(6) +#define FSR1 emitm_f(0) +#define FSR2 emitm_f(2) #define Parrot_jit_regbase_ptr(i) &((i)->ctx.int_reg.registers[0]) /* The offset of a Parrot register from the base register */ #define Parrot_jit_regoff(a, i) (unsigned)(a) - (unsigned)(Parrot_jit_regbase_ptr(i)) -/* Generate a jump to a bytecode address - uses the temporary register */ +/* Generate a jump to a bytecode address in reg_num + * - uses the temporary register + */ static void Parrot_jit_bytejump(Parrot_jit_info_t *jit_info, struct Parrot_Interp *interpreter, int reg_num) @@ -308,21 +329,21 @@ /* Construct the starting address of the byte code */ emitm_sethi(jit_info->native_ptr, emitm_hi22(interpreter->code->byte_code), - Parrot_jit_tmp); - emitm_or_i(jit_info->native_ptr, Parrot_jit_tmp, - emitm_lo10(interpreter->code->byte_code), Parrot_jit_tmp); + ISR2); + emitm_or_i(jit_info->native_ptr, ISR2, + emitm_lo10(interpreter->code->byte_code), ISR2); /* Calculates the offset into op_map shadow array * assuming sizeof(opcode_t) == sizeof(opmap array entry) */ - emitm_sub_r(jit_info->native_ptr, reg_num, Parrot_jit_tmp, - Parrot_jit_tmp); + emitm_sub_r(jit_info->native_ptr, reg_num, ISR2, + ISR2); /* Load the address of the native code from op_map */ - emitm_ld_r(jit_info->native_ptr, Parrot_jit_opmap, Parrot_jit_tmp, - Parrot_jit_tmp); + emitm_ld_r(jit_info->native_ptr, Parrot_jit_opmap, ISR2, + ISR2); /* This jumps to the address from op_map */ - emitm_jumpl_i(jit_info->native_ptr, Parrot_jit_tmp, 0, Parrot_jit_tmp); + emitm_jumpl_i(jit_info->native_ptr, ISR2, 0, ISR2); emitm_nop(jit_info->native_ptr); } @@ -353,7 +374,7 @@ } /* This function loads a value */ -static void Parrot_jit_int_load(Parrot_jit_info_t *jit_info, +static void jit_emit_load_i(Parrot_jit_info_t *jit_info, struct Parrot_Interp *interpreter, int param, int hwreg) @@ -381,8 +402,8 @@ constants[val]->u.number; /* Load double into integer registers */ - emitm_sethi(jit_info->native_ptr, emitm_hi22(val), Parrot_jit_tmp); - emitm_ldd_i(jit_info->native_ptr, Parrot_jit_tmp, emitm_lo10(val), + emitm_sethi(jit_info->native_ptr, emitm_hi22(val), ISR2); + emitm_ldd_i(jit_info->native_ptr, ISR2, emitm_lo10(val), hwreg); break; @@ -392,6 +413,18 @@ Parrot_jit_regoff(val, interpreter), hwreg); break; + case PARROT_ARG_P: + val = (int)&interpreter->ctx.pmc_reg.registers[val]; + emitm_ld_i(jit_info->native_ptr, Parrot_jit_regbase, + Parrot_jit_regoff(val, interpreter), hwreg); + break; + + case PARROT_ARG_S: + val = (int)&interpreter->ctx.string_reg.registers[val]; + emitm_ld_i(jit_info->native_ptr, Parrot_jit_regbase, + Parrot_jit_regoff(val, interpreter), hwreg); + break; + case PARROT_ARG_N: val = (int)&interpreter->ctx.num_reg.registers[val]; emitm_ldd_i(jit_info->native_ptr, Parrot_jit_regbase, @@ -405,7 +438,7 @@ } } -static void Parrot_jit_int_store(Parrot_jit_info_t *jit_info, +static void jit_emit_store_i(Parrot_jit_info_t *jit_info, struct Parrot_Interp *interpreter, int param, int hwreg) @@ -423,6 +456,18 @@ Parrot_jit_regoff(val, interpreter)); break; + case PARROT_ARG_P: + val = (int)&interpreter->ctx.pmc_reg.registers[val]; + emitm_st_i(jit_info->native_ptr, hwreg, Parrot_jit_regbase, + Parrot_jit_regoff(val, interpreter)); + break; + + case PARROT_ARG_S: + val = (int)&interpreter->ctx.string_reg.registers[val]; + emitm_st_i(jit_info->native_ptr, hwreg, Parrot_jit_regbase, + Parrot_jit_regoff(val, interpreter)); + break; + case PARROT_ARG_N: val = (int)&interpreter->ctx.num_reg.registers[val]; emitm_std_i(jit_info->native_ptr, hwreg, Parrot_jit_regbase, @@ -435,7 +480,7 @@ } } -static void Parrot_jit_float_load(Parrot_jit_info_t *jit_info, +static void jit_emit_load_n(Parrot_jit_info_t *jit_info, struct Parrot_Interp *interpreter, int param, int hwreg) @@ -447,6 +492,16 @@ val = jit_info->cur_op[param]; switch(op_type){ + case PARROT_ARG_NC: + val = (int)&interpreter->code->const_table-> + constants[val]->u.number; + + /* Load double into integer registers */ + emitm_sethi(jit_info->native_ptr, emitm_hi22(val), ISR2); + emitm_lddf_i(jit_info->native_ptr, ISR2, emitm_lo10(val), + hwreg); + break; + case PARROT_ARG_I: val = (int)&interpreter->ctx.int_reg.registers[val]; emitm_ldf_i(jit_info->native_ptr, Parrot_jit_regbase, @@ -465,7 +520,7 @@ } } -static void Parrot_jit_float_store(Parrot_jit_info_t *jit_info, +static void jit_emit_store_n(Parrot_jit_info_t *jit_info, struct Parrot_Interp *interpreter, int param, int hwreg) @@ -615,34 +670,52 @@ void Parrot_jit_emit_mov_mr(struct Parrot_Interp * interpreter, char *mem, int reg) { + emitm_st_i(((Parrot_jit_info_t *)(interpreter->jit_info))->native_ptr, + reg, Parrot_jit_regbase, Parrot_jit_regoff(mem, interpreter)); } /* move mem (i.e. intreg) to reg */ void Parrot_jit_emit_mov_rm(struct Parrot_Interp * interpreter, int reg, char *mem) { + emitm_ld_i(((Parrot_jit_info_t *)(interpreter->jit_info))->native_ptr, + Parrot_jit_regbase, Parrot_jit_regoff(mem, interpreter), reg); } /* move reg to mem (i.e. numreg) */ void Parrot_jit_emit_mov_mr_n(struct Parrot_Interp * interpreter, char *mem, int reg) { + emitm_stdf_i(((Parrot_jit_info_t *)(interpreter->jit_info))->native_ptr, + reg, Parrot_jit_regbase, Parrot_jit_regoff(mem, interpreter)); } /* move mem (i.e. numreg) to reg */ void Parrot_jit_emit_mov_rm_n(struct Parrot_Interp * interpreter, int reg, char *mem) { + emitm_lddf_i(((Parrot_jit_info_t *)(interpreter->jit_info))->native_ptr, + Parrot_jit_regbase, Parrot_jit_regoff(mem, interpreter), reg); } #else # define REQUIRES_CONSTANT_POOL 0 -# define INT_REGISTERS_TO_MAP 1 +# define INT_REGISTERS_TO_MAP 5 +# define FLOAT_REGISTERS_TO_MAP 6 #ifndef JIT_IMCC -char intval_map[INT_REGISTERS_TO_MAP] = { emitm_l(0) }; +char intval_map[INT_REGISTERS_TO_MAP] = + { emitm_l(0), emitm_l(1), emitm_l(2), emitm_l(3), emitm_l(4) + }; + +char floatval_map[] = + { emitm_f(4), emitm_f(6), emitm_f(8), emitm_f(10), emitm_f(12), emitm_f(14) + }; #endif + +#define PRESERVED_INT_REGS 5 +#define PRESERVED_FLOAT_REGS 0 #endif