From: Randolph C. <ta...@us...> - 2007-03-11 13:43:43
|
Update of /cvsroot/hppaqemu/hppaqemu/target-hppa In directory sc8-pr-cvs5.sourceforge.net:/tmp/cvs-serv3028/target-hppa Modified Files: op.c op_mem.h op_template.h translate.c Log Message: implement indexed and short displacement load and stores Index: translate.c =================================================================== RCS file: /cvsroot/hppaqemu/hppaqemu/target-hppa/translate.c,v retrieving revision 1.12 retrieving revision 1.13 diff -C2 -d -r1.12 -r1.13 *** translate.c 9 Mar 2007 23:46:36 -0000 1.12 --- translate.c 11 Mar 2007 13:43:27 -0000 1.13 *************** *** 39,43 **** target_ulong iaoq[2]; target_ulong iasq[2]; ! int is_br; struct TranslationBlock *tb; } DisasContext; --- 39,44 ---- target_ulong iaoq[2]; target_ulong iasq[2]; ! unsigned int is_br:1; ! unsigned int delay_slot_filled:1; struct TranslationBlock *tb; } DisasContext; *************** *** 79,83 **** } ! static GenOpFunc *gen_op_movl_TN_reg[2][32] = { { --- 80,84 ---- } ! static GenOpFunc *gen_op_movl_TN_reg[3][32] = { { *************** *** 147,154 **** gen_op_movl_gr30_T1, gen_op_movl_gr31_T1, } }; ! static GenOpFunc *gen_op_movl_reg_TN[2][32] = { { --- 148,188 ---- gen_op_movl_gr30_T1, gen_op_movl_gr31_T1, + }, { + gen_op_movl_gr0_T2, + gen_op_movl_gr1_T2, + gen_op_movl_gr2_T2, + gen_op_movl_gr3_T2, + gen_op_movl_gr4_T2, + gen_op_movl_gr5_T2, + gen_op_movl_gr6_T2, + gen_op_movl_gr7_T2, + gen_op_movl_gr8_T2, + gen_op_movl_gr9_T2, + gen_op_movl_gr10_T2, + gen_op_movl_gr11_T2, + gen_op_movl_gr12_T2, + gen_op_movl_gr13_T2, + gen_op_movl_gr14_T2, + gen_op_movl_gr15_T2, + gen_op_movl_gr16_T2, + gen_op_movl_gr17_T2, + gen_op_movl_gr18_T2, + gen_op_movl_gr19_T2, + gen_op_movl_gr20_T2, + gen_op_movl_gr21_T2, + gen_op_movl_gr22_T2, + gen_op_movl_gr23_T2, + gen_op_movl_gr24_T2, + gen_op_movl_gr25_T2, + gen_op_movl_gr26_T2, + gen_op_movl_gr27_T2, + gen_op_movl_gr28_T2, + gen_op_movl_gr29_T2, + gen_op_movl_gr30_T2, + gen_op_movl_gr31_T2, } }; ! static GenOpFunc *gen_op_movl_reg_TN[3][32] = { { *************** *** 218,221 **** --- 252,288 ---- gen_op_movl_T1_gr30, gen_op_movl_T1_gr31, + }, { + gen_op_movl_T2_gr0, + gen_op_movl_T2_gr1, + gen_op_movl_T2_gr2, + gen_op_movl_T2_gr3, + gen_op_movl_T2_gr4, + gen_op_movl_T2_gr5, + gen_op_movl_T2_gr6, + gen_op_movl_T2_gr7, + gen_op_movl_T2_gr8, + gen_op_movl_T2_gr9, + gen_op_movl_T2_gr10, + gen_op_movl_T2_gr11, + gen_op_movl_T2_gr12, + gen_op_movl_T2_gr13, + gen_op_movl_T2_gr14, + gen_op_movl_T2_gr15, + gen_op_movl_T2_gr16, + gen_op_movl_T2_gr17, + gen_op_movl_T2_gr18, + gen_op_movl_T2_gr19, + gen_op_movl_T2_gr20, + gen_op_movl_T2_gr21, + gen_op_movl_T2_gr22, + gen_op_movl_T2_gr23, + gen_op_movl_T2_gr24, + gen_op_movl_T2_gr25, + gen_op_movl_T2_gr26, + gen_op_movl_T2_gr27, + gen_op_movl_T2_gr28, + gen_op_movl_T2_gr29, + gen_op_movl_T2_gr30, + gen_op_movl_T2_gr31, } }; *************** *** 414,434 **** }; ! #define gen_op_ldst(name) gen_op_##name##_raw() ! ! static void gen_movl_imm_TN(int reg, int val) { gen_op_movl_TN_im[reg](val); } ! static void gen_movl_imm_T0(int val) { ! gen_movl_imm_TN(0, val); } ! static void gen_movl_imm_T1(int val) { ! gen_movl_imm_TN(1, val); } /* General registers */ static void gen_movl_reg_TN(int reg, int t) --- 481,501 ---- }; ! static void gen_movl_TN_im(int reg, int val) { gen_op_movl_TN_im[reg](val); } ! static void gen_movl_T0_im(int val) { ! gen_movl_TN_im(0, val); } ! static void gen_movl_T1_im(int val) { ! gen_movl_TN_im(1, val); } + #define gen_op_ldst(name) gen_op_##name##_raw() + /* General registers */ static void gen_movl_reg_TN(int reg, int t) *************** *** 447,450 **** --- 514,522 ---- } + static void gen_movl_reg_T2(int reg) + { + gen_movl_reg_TN(reg, 2); + } + static void gen_movl_TN_reg(int reg, int t) { *************** *** 462,465 **** --- 534,542 ---- } + static void gen_movl_T2_reg(int reg) + { + gen_movl_TN_reg(reg, 2); + } + /* Control registers */ static void gen_movl_cr_T0(int cr) *************** *** 507,510 **** --- 584,606 ---- #define gen_shift_T1(s) gen_op_shift##s##_T1() + static GenOpFunc *gen_op_shift_TN[2][4] = { + { + NULL, + gen_op_shift1_T0, + gen_op_shift2_T0, + gen_op_shift3_T0, + }, { + NULL, + gen_op_shift1_T1, + gen_op_shift2_T1, + gen_op_shift3_T1, + } + }; + + static void gen_shift_TN(int t, int shift) + { + gen_op_shift_TN[t][shift](); + } + static void gen_goto_tb(DisasContext *dc, int tb_num, target_ulong pc, target_ulong npc) *************** *** 543,554 **** for(j = 0; j < env->nb_breakpoints; j++) { if (env->breakpoints[j] == dc->iaoq[0]) { ! /* ! if (dc->iaoq[0] != pc_start) ! save_state(dc); gen_op_debug(); ! gen_op_movl_T0_GR0(); ! gen_op_exit_tb(); ! */ ! dc->is_br = 1; goto exit_gen_loop; } --- 639,650 ---- for(j = 0; j < env->nb_breakpoints; j++) { if (env->breakpoints[j] == dc->iaoq[0]) { ! /* ! if (dc->iaoq[0] != pc_start) ! save_state(dc); gen_op_debug(); ! gen_op_movl_T0_GR0(); ! gen_op_exit_tb(); ! */ ! dc->is_br = 1; goto exit_gen_loop; } *************** *** 567,578 **** } } ! last_pc = dc->iaoq[0]; ! disas_hppa_insn(dc); ! if (dc->is_br) ! break; ! /* if the next PC is different, we abort now */ ! if (dc->iaoq[0] != (last_pc + 4)) ! break; /* if we reach a page boundary, we stop generation so that the PC of a TT_TFAULT exception is always in the right page */ --- 663,674 ---- } } ! last_pc = dc->iaoq[0]; ! disas_hppa_insn(dc); ! if (dc->is_br) ! break; ! /* if the next PC is different, we abort now */ ! if (dc->iaoq[0] != (last_pc + 4)) ! break; /* if we reach a page boundary, we stop generation so that the PC of a TT_TFAULT exception is always in the right page */ *************** *** 588,592 **** } } while ((gen_opc_ptr < gen_opc_end) && ! (dc->iaoq[0] - pc_start) < (TARGET_PAGE_SIZE - 32)); exit_gen_loop: --- 684,688 ---- } } while ((gen_opc_ptr < gen_opc_end) && ! (dc->iaoq[0] - pc_start) < (TARGET_PAGE_SIZE - 32)); exit_gen_loop: *************** *** 599,606 **** if (dc->iaoq[0] != DYNAMIC_PC) gen_op_jmp_im(dc->iaoq[0]); ! /* save_npc(dc); gen_op_movl_T0_GR0(); ! */ gen_op_exit_tb(); } --- 695,702 ---- if (dc->iaoq[0] != DYNAMIC_PC) gen_op_jmp_im(dc->iaoq[0]); ! /* save_npc(dc); gen_op_movl_T0_GR0(); ! */ gen_op_exit_tb(); } *************** *** 627,634 **** #ifdef DEBUG_DISAS if (loglevel & CPU_LOG_TB_IN_ASM) { ! fprintf(logfile, "--------------\n"); ! fprintf(logfile, "IN: %s\n", lookup_symbol(pc_start)); ! target_disas(logfile, pc_start, last_pc + 4 - pc_start, 0); ! fprintf(logfile, "\n"); if (loglevel & CPU_LOG_TB_OP) { fprintf(logfile, "OP:\n"); --- 723,730 ---- #ifdef DEBUG_DISAS if (loglevel & CPU_LOG_TB_IN_ASM) { ! fprintf(logfile, "--------------\n"); ! fprintf(logfile, "IN: %s\n", lookup_symbol(pc_start)); ! target_disas(logfile, pc_start, last_pc + 4 - pc_start, 0); ! fprintf(logfile, "\n"); if (loglevel & CPU_LOG_TB_OP) { fprintf(logfile, "OP:\n"); *************** *** 651,654 **** --- 747,892 ---- } + #define LDST_CMPLT_NONE 0 + #define LDST_CMPLT_S 1 + #define LDST_CMPLT_SM 2 + #define LDST_CMPLT_M 3 + #define LDST_CMPLT_MA 4 + #define LDST_CMPLT_MB 5 + + static int get_ldst_cmplt(uint32_t insn) + { + int indexed_load = (field(insn, 12, 1) == 0); + if (indexed_load) + { + int u = field(insn, 13, 1); + int m = field(insn, 5, 1); + + if (u == 0 && m == 0) + return LDST_CMPLT_NONE; + else if (u == 0 && m == 1) + return LDST_CMPLT_M; + else if (u == 1 && m == 0) + return LDST_CMPLT_S; + else if (u == 1 && m == 1) + return LDST_CMPLT_SM; + } + else + { + int a = field(insn, 13, 1); + int m = field(insn, 5, 1); + uint32_t ext4 = field(insn, 6, 4); + uint32_t im5; + if (ext4 <= 7) /* load */ + im5 = field_signext(insn, 16, 5); + else /* store */ + im5 = field_signext(insn, 0, 5); + + if (m == 0) + return LDST_CMPLT_NONE; + else if (a == 0 && m == 1 && im5 != 0) + return LDST_CMPLT_MA; + else if (a == 1 && m == 1) + return LDST_CMPLT_MB; + } + return LDST_CMPLT_NONE; + } + + static void gen_load(uint32_t insn, int shift, GenOpFunc *op) + { + int indexed_load = (field(insn, 12, 1) == 0); + int cmplt = get_ldst_cmplt(insn); + uint32_t b = field(insn, 21, 5); + uint32_t t = field(insn, 0, 5); + + /* load value at address T0 to T1 */ + + if (indexed_load) + { + uint32_t x = field(insn, 16, 5); + switch (cmplt) + { + case LDST_CMPLT_S: + case LDST_CMPLT_SM: + gen_movl_T0_reg(x); + gen_shift_TN(0, shift); + break; + case LDST_CMPLT_M: + default: + gen_movl_T0_reg(x); + break; + } + } + else + { + uint32_t im5 = field_signext(insn, 16, 5); + gen_movl_T0_im(im5); + } + + switch (cmplt) + { + case LDST_CMPLT_MB: + /* dx in T0 */ + gen_movl_T1_reg(b); + gen_op_copy_T2_T0(); /* copy dx to T2 */ + gen_op_addl_T0_T1(); /* T0 = GR[b] + dx */ + gen_op_addl_T1_T2(); /* GR[b] += dx */ + gen_movl_reg_T1(b); + break; + case LDST_CMPLT_MA: + case LDST_CMPLT_M: + case LDST_CMPLT_SM: + /* dx in T0 */ + gen_movl_T1_reg(b); + gen_op_copy_T2_T1(); + gen_op_addl_T1_T0(); /* GR[b] += dx */ + gen_movl_reg_T1(b); + gen_op_copy_T0_T2(); /* T0 = GR[b] */ + break; + default: + /* dx in T0 */ + gen_movl_T1_reg(b); + gen_op_addl_T0_T1(); /* T0 = GR[b] + dx */ + break; + } + + op(); + gen_movl_reg_T1(t); + } + + static void gen_store(uint32_t insn, GenOpFunc *op) + { + uint32_t im5 = field_signext(insn, 0, 5); + uint32_t r = field(insn, 16, 5); + uint32_t b = field(insn, 21, 5); + int cmplt = get_ldst_cmplt(insn); + + /* store T1 at address T0 */ + + gen_movl_T0_im(im5); + switch (cmplt) + { + case LDST_CMPLT_MB: + gen_movl_T1_reg(b); + gen_op_copy_T2_T0(); /* T2 = dx */ + gen_op_addl_T0_T1(); /* offset = GR[b] + dx */ + gen_op_addl_T1_T2(); /* GR[b] += dx */ + gen_movl_reg_T1(b); + break; + case LDST_CMPLT_MA: + gen_movl_T1_reg(b); + gen_op_copy_T2_T1(); /* T2 = GR[b] */ + gen_op_addl_T1_T0(); /* GR[b] += dx */ + gen_movl_reg_T1(b); + gen_op_copy_T0_T2(); /* offset = GR[b] */ + break; + default: + gen_movl_T1_reg(b); + gen_op_addl_T0_T1(); /* offset = GR[b] + dx */ + break; + } + gen_movl_T1_reg(r); + op(); + } + static void disas_hppa_insn(DisasContext * dc) { *************** *** 688,700 **** switch(ext8) { case 0x00: /* BREAK */ ! gen_op_break(); ! break; case 0x20: /* SYNC, SYNCDMAA */ ! if (field(insn, 20, 1)) ! gen_op_syncdma(); else ! gen_op_sync(); ! break; case 0x60: /* RFI */ --- 926,938 ---- switch(ext8) { case 0x00: /* BREAK */ ! gen_op_break(); ! break; case 0x20: /* SYNC, SYNCDMAA */ ! if (field(insn, 20, 1)) ! gen_op_syncdma(); else ! gen_op_sync(); ! break; case 0x60: /* RFI */ *************** *** 710,713 **** --- 948,952 ---- case 0x6b: /* SSM */ + gen_op_check_priv0(); gen_op_ssm(field(insn, 16, 7)); gen_movl_reg_T0(field(insn, 0, 5)); *************** *** 715,718 **** --- 954,958 ---- case 0x73: /* RSM */ + gen_op_check_priv0(); gen_op_rsm(field(insn, 16, 7)); gen_movl_reg_T0(field(insn, 0, 5)); *************** *** 720,723 **** --- 960,964 ---- case 0xc3: /* MTSM */ + gen_op_check_priv0(); gen_movl_T0_reg(field(insn, 16, 5)); gen_op_mtsm(); *************** *** 745,748 **** --- 986,991 ---- uint32_t sr = field(insn, 13, 3); uint32_t t = field(insn, 0, 5); + if (sr >= 3) + gen_op_check_priv0(); gen_movl_T0_sr(sr); gen_movl_reg_T0(t); *************** *** 750,756 **** --- 993,1081 ---- } case 0xc2: /* MTCTL */ + { + uint32_t t, r; + t = field(insn, 21, 5); + r = field(insn, 16, 5); + if (t >= 1 && t < 7) + break; + if (t != 11) + gen_op_check_priv0(); + switch (t) + { + case 0: /* recovery counter */ + /* TODO: mask 32-bits for 64-bit op */ + case 14: + case 15: + case 16: + case 24: + case 25: + case 26: + case 27: + case 28: + case 29: + case 30: + case 31: + case 8: /* PID0 */ + case 9: /* PID1 */ + case 12: /* PID2 */ + case 13: /* PID3 */ + /* Undefined in PSW[Q] set */ + case 17: + case 18: + case 20: + case 21: + case 22: + gen_movl_T0_reg(r); + gen_movl_cr_T0(0); + break; + + case 23: + gen_movl_T0_cr(23); + gen_movl_T1_reg(r); + gen_op_andcm_T1_T0(); + gen_movl_cr_T0(23); + break; + + case 10: /* CCR/SCR */ + case 11: /* SAR - handled differently on 64-bit */ + gen_movl_T0_reg(r); + gen_op_movl_T1_im(0xffff); + gen_op_and_T1_T0(); + gen_movl_cr_T0(10); + break; + } + break; + } case 0x45: /* MFCTL */ + { + uint32_t r, t; + r = field(insn, 21, 5); + t = field(insn, 0, 5); + if (r >= 1 && r < 7) + break; + if (r != 11 && r != 26 && r != 27) + gen_op_check_priv0(); + if (r == 16) /* interval timer */ + gen_op_check_int_timer_priv(); + + if ((r >= 17 && r <= 22) || (r == 0)) + { + gen_movl_T0_cr(r); + gen_movl_reg_T0(t); + } + else if (r == 11) /* SAR */ + { + /* Check - may need to mask and shift */ + gen_movl_T0_cr(r); + gen_movl_reg_T0(t); + } + else if (r >= 8) + { + gen_movl_T0_cr(r); + gen_movl_reg_T0(t); + } break; + } default: *************** *** 786,790 **** ext8 = field(insn, 6, 8); ! switch (ext8) { case 0x40: /* IDTLBP */ --- 1111,1115 ---- ext8 = field(insn, 6, 8); ! switch (ext8) { case 0x40: /* IDTLBP */ *************** *** 904,908 **** case 0x26: /* UADDCM */ gen_op_com_T1(); ! gen_op_addl_T1_T0(); break; case 0x27: /* UADDCMT */ --- 1229,1233 ---- case 0x26: /* UADDCM */ gen_op_com_T1(); ! gen_op_addl_T0_T1(); break; case 0x27: /* UADDCMT */ *************** *** 910,926 **** break; case 0x28: /* ADDL */ ! gen_op_addl_T1_T0(); break; case 0x29: /* SH1ADDL */ gen_shift_T0(1); ! gen_op_addl_T1_T0(); break; case 0x2A: /* SH2ADDL */ gen_shift_T0(2); ! gen_op_addl_T1_T0(); break; case 0x2B: /* SH3ADDL */ gen_shift_T0(3); ! gen_op_addl_T1_T0(); break; case 0x2E: /* DCOR */ --- 1235,1251 ---- break; case 0x28: /* ADDL */ ! gen_op_addl_T0_T1(); break; case 0x29: /* SH1ADDL */ gen_shift_T0(1); ! gen_op_addl_T0_T1(); break; case 0x2A: /* SH2ADDL */ gen_shift_T0(2); ! gen_op_addl_T0_T1(); break; case 0x2B: /* SH3ADDL */ gen_shift_T0(3); ! gen_op_addl_T0_T1(); break; case 0x2E: /* DCOR */ *************** *** 946,974 **** case 0x03: /* Index_Mem */ { ! uint32_t ext4; ! ext4 = field(insn, 6, 4); ! if(field(insn, 12, 1)) { ! switch(ext4) { ! case 0x00: /* LDBX */ ! case 0x01: /* LDHX */ ! case 0x02: /* LDWX */ ! case 0x06: /* LDWAX */ ! case 0x07: /* LDCWX */ ! break; ! } ! } else { ! switch(ext4) { ! case 0x00: /* LDBS */ ! case 0x01: /* LDHS */ ! case 0x02: /* LDWS */ ! case 0x06: /* LDWAS */ ! case 0x07: /* LDCWS */ ! case 0x08: /* STBS */ ! case 0x09: /* STHS */ ! case 0x0a: /* STWS */ ! case 0x0c: /* STBYS */ ! case 0x0e: /* STWAS */ ! break; ! } } break; --- 1271,1317 ---- case 0x03: /* Index_Mem */ { ! uint32_t ext4 = field(insn, 6, 4); ! switch(ext4) { ! case 0x00: /* LDB */ ! gen_load(insn, 0, gen_op_ldb_raw); ! break; ! case 0x01: /* LDH */ ! gen_load(insn, 1, gen_op_ldh_raw); ! break; ! case 0x02: /* LDW */ ! gen_load(insn, 2, gen_op_ldw_raw); ! break; ! case 0x06: /* LDWA */ ! gen_op_check_priv0(); ! gen_load(insn, 2, gen_op_ldw_phys); ! break; ! case 0x07: /* LDCW */ ! gen_load(insn, 2, gen_op_ldcw_raw); ! break; ! case 0x08: /* STB */ ! gen_store(insn, gen_op_stb_raw); ! break; ! case 0x09: /* STH */ ! gen_store(insn, gen_op_sth_raw); ! break; ! case 0x0A: /* STW */ ! gen_store(insn, gen_op_stw_raw); ! break; ! ! case 0x0C: /* STBY */ ! break; ! ! case 0x0E: /* STWA */ ! gen_store(insn, gen_op_stw_phys); ! break; ! ! case 0x03: /* LDD */ ! case 0x04: /* LDDA */ ! case 0x05: /* LDCD */ ! case 0x0B: /* STD */ ! case 0x0D: /* STDBY */ ! case 0x0F: /* STDA */ ! /* XXX - pa20 */ ! break; } break; *************** *** 988,992 **** if(t) { im21 = field(insn, 0, 21) << (32 - 21); ! gen_movl_imm_T0(im21); gen_movl_reg_T0(t); } --- 1331,1335 ---- if(t) { im21 = field(insn, 0, 21) << (32 - 21); ! gen_movl_T0_im(im21); gen_movl_reg_T0(t); } *************** *** 1013,1017 **** im21 = field(insn, 0, 21) << (32 - 21); gen_movl_T1_reg(r); ! gen_movl_imm_T0(im21); gen_op_addl_T1_T0(); gen_movl_reg_T0(1); --- 1356,1360 ---- im21 = field(insn, 0, 21) << (32 - 21); gen_movl_T1_reg(r); ! gen_movl_T0_im(im21); gen_op_addl_T1_T0(); gen_movl_reg_T0(1); *************** *** 1042,1047 **** im14 = field_signext(insn, 0, 14); gen_movl_reg_T0(b); ! gen_movl_imm_T1(im14); ! gen_op_add_T1_T0(); gen_movl_T0_reg(t); break; --- 1385,1390 ---- im14 = field_signext(insn, 0, 14); gen_movl_reg_T0(b); ! gen_movl_T1_im(im14); ! gen_op_addl_T0_T1(); gen_movl_T0_reg(t); break; *************** *** 1050,1054 **** case 0x0e: /* Float */ case 0x0f: /* Product Specific */ ! break; case 0x10: /* LDB */ --- 1393,1397 ---- case 0x0e: /* Float */ case 0x0f: /* Product Specific */ ! break; case 0x10: /* LDB */ *************** *** 1062,1068 **** im14 = field_signext(insn, 0, 14); gen_movl_reg_T0(b); ! gen_movl_imm_T1(s); /* gen_op_space_sel_T0_T1(); */ ! gen_movl_imm_T1(im14); gen_op_add_T1_T0(); switch(op) { --- 1405,1411 ---- im14 = field_signext(insn, 0, 14); gen_movl_reg_T0(b); ! gen_movl_T1_im(s); /* gen_op_space_sel_T0_T1(); */ ! gen_movl_T1_im(im14); gen_op_add_T1_T0(); switch(op) { *************** *** 1094,1101 **** im14 = field_signext(insn, 0, 14); gen_movl_reg_T0(b); ! gen_movl_imm_T1(s); /* gen_op_space_sel_T0_T1(); */ ! gen_movl_imm_T1(im14); ! gen_op_add_T1_T0(); gen_movl_reg_T1(t); switch(op) { --- 1437,1444 ---- im14 = field_signext(insn, 0, 14); gen_movl_reg_T0(b); ! /* gen_movl_T1_im(s); */ /* gen_op_space_sel_T0_T1(); */ ! gen_movl_T1_im(im14); ! gen_op_addl_T0_T1(); gen_movl_reg_T1(t); switch(op) { *************** *** 1131,1137 **** im11 = field_signext(insn, 0, 11); gen_movl_reg_T0(r); ! gen_movl_imm_T1(im11); gen_op_add_T1_T0(); ! gen_movl_imm_T0(0); gen_movl_T0_reg(t); break; --- 1474,1480 ---- im11 = field_signext(insn, 0, 11); gen_movl_reg_T0(r); ! gen_movl_T1_im(im11); gen_op_add_T1_T0(); ! gen_movl_T0_im(0); gen_movl_T0_reg(t); break; *************** *** 1165,1169 **** im11 = field_signext(insn, 0, 11); gen_movl_reg_T0(r); ! gen_movl_imm_T0(im11); if(!field(insn, 11, 1)) gen_op_addit_T0(); --- 1508,1512 ---- im11 = field_signext(insn, 0, 11); gen_movl_reg_T0(r); ! gen_movl_T0_im(im11); if(!field(insn, 11, 1)) gen_op_addit_T0(); *************** *** 1178,1183 **** case 0x32: /* MOVB */ case 0x33: /* MOVIB */ ! /* FIXME */ ! dc->is_br = 1; break; --- 1521,1526 ---- case 0x32: /* MOVB */ case 0x33: /* MOVIB */ ! /* FIXME */ ! dc->is_br = 1; break; *************** *** 1229,1234 **** /* */ ! /* FIXME */ ! dc->is_br = 1; break; } --- 1572,1577 ---- /* */ ! /* FIXME */ ! dc->is_br = 1; break; } *************** *** 1257,1262 **** } ! /* FIXME */ ! dc->is_br = 1; break; } --- 1600,1605 ---- } ! /* FIXME */ ! dc->is_br = 1; break; } *************** *** 1277,1281 **** env = qemu_mallocz(sizeof(CPUHPPAState)); if (!env) ! return NULL; cpu_exec_init(env); tlb_flush(env, 1); --- 1620,1624 ---- env = qemu_mallocz(sizeof(CPUHPPAState)); if (!env) ! return NULL; cpu_exec_init(env); tlb_flush(env, 1); Index: op_template.h =================================================================== RCS file: /cvsroot/hppaqemu/hppaqemu/target-hppa/op_template.h,v retrieving revision 1.1 retrieving revision 1.2 diff -C2 -d -r1.1 -r1.2 *** op_template.h 27 Feb 2007 23:20:43 -0000 1.1 --- op_template.h 11 Mar 2007 13:43:26 -0000 1.2 *************** *** 30,33 **** --- 30,38 ---- } + void OPPROTO glue(op_movl_T2_, REGNAME)(void) + { + T2 = REG; + } + void OPPROTO glue(glue(op_movl_, REGNAME), _T0)(void) { *************** *** 40,43 **** --- 45,53 ---- } + void OPPROTO glue(glue(op_movl_, REGNAME), _T2)(void) + { + REG = T2; + } + #undef REG #undef REGNAME Index: op.c =================================================================== RCS file: /cvsroot/hppaqemu/hppaqemu/target-hppa/op.c,v retrieving revision 1.10 retrieving revision 1.11 diff -C2 -d -r1.10 -r1.11 *** op.c 10 Mar 2007 00:55:50 -0000 1.10 --- op.c 11 Mar 2007 13:43:26 -0000 1.11 *************** *** 242,251 **** void OPPROTO op_movl_T0_gr0(void) { ! T0 = 0; } void OPPROTO op_movl_T1_gr0(void) { ! T1 = 0; } --- 242,256 ---- void OPPROTO op_movl_T0_gr0(void) { ! T0 = 0; } void OPPROTO op_movl_T1_gr0(void) { ! T1 = 0; ! } ! ! void OPPROTO op_movl_T2_gr0(void) ! { ! T2 = 0; } *************** *** 258,261 **** --- 263,270 ---- } + void OPPROTO op_movl_gr0_T2(void) + { + } + void OPPROTO op_movl_T0_im(void) { *************** *** 268,271 **** --- 277,321 ---- } + #define OP_COPY(_t1, _t2) \ + void OPPROTO op_copy_##_t1##_##_t2(void) \ + { \ + _t1 = _t2; \ + } + OP_COPY(T0, T1) + OP_COPY(T0, T2) + OP_COPY(T1, T0) + OP_COPY(T1, T2) + OP_COPY(T2, T0) + OP_COPY(T2, T1) + + /* Memory operations */ + #define MEMSUFFIX _raw + #include "op_mem.h" + #ifndef CONFIG_USER_ONLY + #define MEMSUFFIX _kernel + #include "op_mem.h" + #define MEMSUFFIX _user + #include "op_mem.h" + #endif + + void OPPROTO op_ldcw_raw(void) + { + /* FIXME - should be atomic */ + T1 = ldl_raw((void *)T0); + stl_raw((void *)T0, 0); + } + + void OPPROTO op_ldw_phys(void) + { + /* FIXME - T0 contains a physical address */ + T1 = ldl_raw((void *)T0); + } + + void OPPROTO op_stw_phys(void) + { + /* FIXME - T0 contains a physical address */ + stl_raw((void *)T0, T1); + } + /* System operations */ void OPPROTO op_break(void) *************** *** 274,277 **** --- 324,340 ---- } + void OPPROTO op_check_priv0(void) + { + if (env->priv_level != 0) + raise_exception(EXCP_PRIVOP); + } + + void OPPROTO op_check_int_timer_priv(void) + { + /* secure interval timer */ + if ((env->psw & PSW_S) && env->priv_level != 0) + raise_exception(EXCP_PRIVOP); + } + void OPPROTO op_sync(void) { *************** *** 284,296 **** void OPPROTO op_rfi(void) { ! if (env->priv_level != 0) ! raise_exception(EXCP_PRIVOP); ! else { ! env->psw = env->cr[22]; /* ipsw */ ! env->iaoq[0] = env->cr[18]; /* iiaoq */ ! env->iaoq[1] = env->iiaoq_back; ! env->iasq[0] = env->cr[17]; /* iiasq */ ! env->iasq[1] = env->iiasq_back; ! } } --- 347,355 ---- void OPPROTO op_rfi(void) { ! env->psw = env->cr[22]; /* ipsw */ ! env->iaoq[0] = env->cr[18]; /* iiaoq */ ! env->iaoq[1] = env->iiaoq_back; ! env->iasq[0] = env->cr[17]; /* iiasq */ ! env->iasq[1] = env->iiasq_back; } *************** *** 309,314 **** void OPPROTO op_ssm(void) { - if (env->priv_level != 0) - raise_exception(EXCP_PRIVOP); T0 = env->psw & (PSW_W | PSW_E | PSW_O | PSW_G | PSW_F | PSW_R | PSW_Q | PSW_P | PSW_D | PSW_I); --- 368,371 ---- *************** *** 335,340 **** void OPPROTO op_rsm(void) { - if (env->priv_level != 0) - raise_exception(EXCP_PRIVOP); T0 = env->psw & (PSW_W | PSW_E | PSW_O | PSW_G | PSW_F | PSW_R | PSW_Q | PSW_P | PSW_D | PSW_I); --- 392,395 ---- *************** *** 361,366 **** void OPPROTO op_mtsm(void) { - if (env->priv_level != 0) - raise_exception(EXCP_PRIVOP); env->psw = env->psw & ~(PSW_W | PSW_E | PSW_O | PSW_G | PSW_F | PSW_R | PSW_Q | PSW_P | PSW_D | PSW_I); env->psw |= T0 & (PSW_W | PSW_E | PSW_O | PSW_G | PSW_F | PSW_R | PSW_Q | PSW_P | PSW_D | PSW_I); --- 416,419 ---- *************** *** 436,440 **** /* add logical */ ! void OPPROTO op_addl_T1_T0(void) { T0 += T1; --- 489,493 ---- /* add logical */ ! void OPPROTO op_addl_T0_T1(void) { T0 += T1; *************** *** 442,448 **** } ! void OPPROTO op_add2_T1_T0(void) { ! T0 += T1; } --- 495,506 ---- } ! void OPPROTO op_addl_T1_T0(void) { ! T1 += T0; ! } ! ! void OPPROTO op_addl_T1_T2(void) ! { ! T1 += T2; } *************** *** 492,501 **** void OPPROTO op_undef_insn(void) { ! /* XXX */ } void OPPROTO op_ill_insn(void) { ! /* XXX */ } --- 550,563 ---- void OPPROTO op_undef_insn(void) { ! /* undefined; let's kill the process so that we can easily identify ! * any incorrect insn decoding ! */ ! int *p = NULL; ! T0 = *p; } void OPPROTO op_ill_insn(void) { ! raise_exception(EXCP_ILLEGAL); } *************** *** 520,523 **** --- 582,590 ---- } + void OPPROTO op_shift1_T1(void) + { + T1 <<= 1; + } + void OPPROTO op_shift2_T0(void) { *************** *** 525,528 **** --- 592,600 ---- } + void OPPROTO op_shift2_T1(void) + { + T1 <<= 2; + } + void OPPROTO op_shift3_T0(void) { *************** *** 530,533 **** --- 602,610 ---- } + void OPPROTO op_shift3_T1(void) + { + T1 <<= 3; + } + void OPPROTO op_sub_T1_T0_cc(void) { *************** *** 650,653 **** env->iaoq[1] = env->iaoq[0] + 4; } - - #include "op_mem.h" --- 727,728 ---- Index: op_mem.h =================================================================== RCS file: /cvsroot/hppaqemu/hppaqemu/target-hppa/op_mem.h,v retrieving revision 1.2 retrieving revision 1.3 diff -C2 -d -r1.2 -r1.3 *** op_mem.h 4 Mar 2007 16:13:20 -0000 1.2 --- op_mem.h 11 Mar 2007 13:43:26 -0000 1.3 *************** *** 1,4 **** #define HPPA_LD_OP(name, qp) \ ! void OPPROTO glue(glue(op_, name), _raw)(void) \ { \ T1 = glue(qp, _raw)((void *)T0); \ --- 1,4 ---- #define HPPA_LD_OP(name, qp) \ ! void OPPROTO glue(glue(op_, name), MEMSUFFIX)(void) \ { \ T1 = glue(qp, _raw)((void *)T0); \ |