Commit 77b73de67632ed04acad4d816741ba27427cadac
1 parent
877d8ad7
Use rem/div[u]_i32 drop div[u]2_i32
git-svn-id: svn://svn.savannah.nongnu.org/qemu/trunk@4722 c046a42c-6fe2-441c-8c8c-71466251a162
Showing
2 changed files
with
26 additions
and
113 deletions
tcg/ppc/tcg-target.c
@@ -23,8 +23,6 @@ | @@ -23,8 +23,6 @@ | ||
23 | */ | 23 | */ |
24 | 24 | ||
25 | static uint8_t *tb_ret_addr; | 25 | static uint8_t *tb_ret_addr; |
26 | -static uint8_t *udiv_addr; | ||
27 | -static uint8_t *div_addr; | ||
28 | 26 | ||
29 | #define FAST_PATH | 27 | #define FAST_PATH |
30 | #if TARGET_PHYS_ADDR_BITS <= 32 | 28 | #if TARGET_PHYS_ADDR_BITS <= 32 |
@@ -137,22 +135,6 @@ static const int tcg_target_callee_save_regs[] = { | @@ -137,22 +135,6 @@ static const int tcg_target_callee_save_regs[] = { | ||
137 | TCG_REG_R31 | 135 | TCG_REG_R31 |
138 | }; | 136 | }; |
139 | 137 | ||
140 | -static const int div_save_regs[] = { | ||
141 | - TCG_REG_R4, | ||
142 | - TCG_REG_R5, | ||
143 | - TCG_REG_R7, | ||
144 | - TCG_REG_R8, | ||
145 | - TCG_REG_R9, | ||
146 | - TCG_REG_R10, | ||
147 | - TCG_REG_R11, | ||
148 | - TCG_REG_R12, | ||
149 | - TCG_REG_R13, /* should r13 be saved? */ | ||
150 | - TCG_REG_R24, | ||
151 | - TCG_REG_R25, | ||
152 | - TCG_REG_R26, | ||
153 | - TCG_REG_R27, | ||
154 | -}; | ||
155 | - | ||
156 | static uint32_t reloc_pc24_val (void *pc, tcg_target_long target) | 138 | static uint32_t reloc_pc24_val (void *pc, tcg_target_long target) |
157 | { | 139 | { |
158 | tcg_target_long disp; | 140 | tcg_target_long disp; |
@@ -817,22 +799,6 @@ static void tcg_out_qemu_st (TCGContext *s, const TCGArg *args, int opc) | @@ -817,22 +799,6 @@ static void tcg_out_qemu_st (TCGContext *s, const TCGArg *args, int opc) | ||
817 | #endif | 799 | #endif |
818 | } | 800 | } |
819 | 801 | ||
820 | -static uint64_t ppc_udiv_helper (uint64_t a, uint32_t b) | ||
821 | -{ | ||
822 | - uint64_t rem, quo; | ||
823 | - quo = a / b; | ||
824 | - rem = a % b; | ||
825 | - return (rem << 32) | (uint32_t) quo; | ||
826 | -} | ||
827 | - | ||
828 | -static uint64_t ppc_div_helper (int64_t a, int32_t b) | ||
829 | -{ | ||
830 | - int64_t rem, quo; | ||
831 | - quo = a / b; | ||
832 | - rem = a % b; | ||
833 | - return (rem << 32) | (uint32_t) quo; | ||
834 | -} | ||
835 | - | ||
836 | void tcg_target_qemu_prologue (TCGContext *s) | 802 | void tcg_target_qemu_prologue (TCGContext *s) |
837 | { | 803 | { |
838 | int i, j, frame_size; | 804 | int i, j, frame_size; |
@@ -871,49 +837,6 @@ void tcg_target_qemu_prologue (TCGContext *s) | @@ -871,49 +837,6 @@ void tcg_target_qemu_prologue (TCGContext *s) | ||
871 | tcg_out32 (s, MTSPR | RS (0) | LR); | 837 | tcg_out32 (s, MTSPR | RS (0) | LR); |
872 | tcg_out32 (s, ADDI | RT (1) | RA (1) | frame_size); | 838 | tcg_out32 (s, ADDI | RT (1) | RA (1) | frame_size); |
873 | tcg_out32 (s, BCLR | BO_ALWAYS); | 839 | tcg_out32 (s, BCLR | BO_ALWAYS); |
874 | - | ||
875 | - /* div trampolines */ | ||
876 | - for (j = 0; j < 2; ++j) { | ||
877 | - tcg_target_long target; | ||
878 | - | ||
879 | - frame_size = 8 + ARRAY_SIZE (div_save_regs) * 4; | ||
880 | - frame_size = (frame_size + 15) & ~15; | ||
881 | - | ||
882 | - if (j == 0) { | ||
883 | - target = (tcg_target_long) ppc_udiv_helper; | ||
884 | - udiv_addr = s->code_ptr; | ||
885 | - } | ||
886 | - else { | ||
887 | - target = (tcg_target_long) ppc_div_helper; | ||
888 | - div_addr = s->code_ptr; | ||
889 | - } | ||
890 | - | ||
891 | - tcg_out32 (s, MFSPR | RT (0) | LR); | ||
892 | - tcg_out32 (s, STWU | RS (1) | RA (1) | (-frame_size & 0xffff)); | ||
893 | - for (i = 0; i < ARRAY_SIZE (div_save_regs); ++i) | ||
894 | - tcg_out32 (s, (STW | ||
895 | - | RS (div_save_regs[i]) | ||
896 | - | RA (1) | ||
897 | - | (i * 4 + 8) | ||
898 | - ) | ||
899 | - ); | ||
900 | - tcg_out32 (s, STW | RS (0) | RA (1) | (frame_size - 4)); | ||
901 | - tcg_out_mov (s, 4, 6); | ||
902 | - tcg_out_b (s, LK, target); | ||
903 | - tcg_out_mov (s, 6, 4); | ||
904 | - | ||
905 | - for (i = 0; i < ARRAY_SIZE (div_save_regs); ++i) | ||
906 | - tcg_out32 (s, (LWZ | ||
907 | - | RT (div_save_regs[i]) | ||
908 | - | RA (1) | ||
909 | - | (i * 4 + 8) | ||
910 | - ) | ||
911 | - ); | ||
912 | - tcg_out32 (s, LWZ | RT (0) | RA (1) | (frame_size - 4)); | ||
913 | - tcg_out32 (s, MTSPR | RS (0) | LR); | ||
914 | - tcg_out32 (s, ADDI | RT (1) | RA (1) | frame_size); | ||
915 | - tcg_out32 (s, BCLR | BO_ALWAYS); | ||
916 | - } | ||
917 | } | 840 | } |
918 | 841 | ||
919 | static void tcg_out_ld (TCGContext *s, TCGType type, int ret, int arg1, | 842 | static void tcg_out_ld (TCGContext *s, TCGType type, int ret, int arg1, |
@@ -1095,34 +1018,6 @@ static void tcg_out_brcond2(TCGContext *s, | @@ -1095,34 +1018,6 @@ static void tcg_out_brcond2(TCGContext *s, | ||
1095 | tcg_out_label(s, label_next, (tcg_target_long)s->code_ptr); | 1018 | tcg_out_label(s, label_next, (tcg_target_long)s->code_ptr); |
1096 | } | 1019 | } |
1097 | 1020 | ||
1098 | -static void tcg_out_div2 (TCGContext *s, int uns) | ||
1099 | -{ | ||
1100 | - void *label1_ptr, *label2_ptr; | ||
1101 | - | ||
1102 | - if (uns) | ||
1103 | - tcg_out32 (s, CMPLI | BF (7) | RA (3)); | ||
1104 | - else { | ||
1105 | - tcg_out32 (s, SRAWI | RS (4) | RA (0) | 31); | ||
1106 | - tcg_out32 (s, CMPL | BF (7) | RA (3) | RB (4)); | ||
1107 | - } | ||
1108 | - | ||
1109 | - label1_ptr = s->code_ptr; | ||
1110 | - tcg_out32 (s, BC | BI (7, CR_EQ) | BO_COND_TRUE); | ||
1111 | - | ||
1112 | - tcg_out_b (s, LK, (tcg_target_long) (uns ? udiv_addr : div_addr)); | ||
1113 | - | ||
1114 | - label2_ptr = s->code_ptr; | ||
1115 | - tcg_out32 (s, B); | ||
1116 | - | ||
1117 | - reloc_pc14 (label1_ptr, (tcg_target_long) s->code_ptr); | ||
1118 | - | ||
1119 | - tcg_out32 (s, (uns ? DIVWU : DIVW) | TAB (6, 4, 5)); | ||
1120 | - tcg_out32 (s, MULLW | TAB (0, 6, 5)); | ||
1121 | - tcg_out32 (s, SUBF | TAB (3, 0, 4)); | ||
1122 | - | ||
1123 | - reloc_pc24 (label2_ptr, (tcg_target_long) s->code_ptr); | ||
1124 | -} | ||
1125 | - | ||
1126 | static void tcg_out_op(TCGContext *s, int opc, const TCGArg *args, | 1021 | static void tcg_out_op(TCGContext *s, int opc, const TCGArg *args, |
1127 | const int *const_args) | 1022 | const int *const_args) |
1128 | { | 1023 | { |
@@ -1301,6 +1196,27 @@ static void tcg_out_op(TCGContext *s, int opc, const TCGArg *args, | @@ -1301,6 +1196,27 @@ static void tcg_out_op(TCGContext *s, int opc, const TCGArg *args, | ||
1301 | else | 1196 | else |
1302 | tcg_out32 (s, MULLW | TAB (args[0], args[1], args[2])); | 1197 | tcg_out32 (s, MULLW | TAB (args[0], args[1], args[2])); |
1303 | break; | 1198 | break; |
1199 | + | ||
1200 | + case INDEX_op_div_i32: | ||
1201 | + tcg_out32 (s, DIVW | TAB (args[0], args[1], args[2])); | ||
1202 | + break; | ||
1203 | + | ||
1204 | + case INDEX_op_divu_i32: | ||
1205 | + tcg_out32 (s, DIVWU | TAB (args[0], args[1], args[2])); | ||
1206 | + break; | ||
1207 | + | ||
1208 | + case INDEX_op_rem_i32: | ||
1209 | + tcg_out32 (s, DIVW | TAB (0, args[1], args[2])); | ||
1210 | + tcg_out32 (s, MULLW | TAB (0, 0, args[2])); | ||
1211 | + tcg_out32 (s, SUBF | TAB (args[0], 0, args[1])); | ||
1212 | + break; | ||
1213 | + | ||
1214 | + case INDEX_op_remu_i32: | ||
1215 | + tcg_out32 (s, DIVWU | TAB (0, args[1], args[2])); | ||
1216 | + tcg_out32 (s, MULLW | TAB (0, 0, args[2])); | ||
1217 | + tcg_out32 (s, SUBF | TAB (args[0], 0, args[1])); | ||
1218 | + break; | ||
1219 | + | ||
1304 | case INDEX_op_mulu2_i32: | 1220 | case INDEX_op_mulu2_i32: |
1305 | if (args[0] == args[2] || args[0] == args[3]) { | 1221 | if (args[0] == args[2] || args[0] == args[3]) { |
1306 | tcg_out32 (s, MULLW | TAB (0, args[2], args[3])); | 1222 | tcg_out32 (s, MULLW | TAB (0, args[2], args[3])); |
@@ -1312,12 +1228,6 @@ static void tcg_out_op(TCGContext *s, int opc, const TCGArg *args, | @@ -1312,12 +1228,6 @@ static void tcg_out_op(TCGContext *s, int opc, const TCGArg *args, | ||
1312 | tcg_out32 (s, MULHWU | TAB (args[1], args[2], args[3])); | 1228 | tcg_out32 (s, MULHWU | TAB (args[1], args[2], args[3])); |
1313 | } | 1229 | } |
1314 | break; | 1230 | break; |
1315 | - case INDEX_op_div2_i32: | ||
1316 | - tcg_out_div2 (s, 0); | ||
1317 | - break; | ||
1318 | - case INDEX_op_divu2_i32: | ||
1319 | - tcg_out_div2 (s, 1); | ||
1320 | - break; | ||
1321 | 1231 | ||
1322 | case INDEX_op_shl_i32: | 1232 | case INDEX_op_shl_i32: |
1323 | if (const_args[2]) { | 1233 | if (const_args[2]) { |
@@ -1458,9 +1368,11 @@ static const TCGTargetOpDef ppc_op_defs[] = { | @@ -1458,9 +1368,11 @@ static const TCGTargetOpDef ppc_op_defs[] = { | ||
1458 | 1368 | ||
1459 | { INDEX_op_add_i32, { "r", "r", "ri" } }, | 1369 | { INDEX_op_add_i32, { "r", "r", "ri" } }, |
1460 | { INDEX_op_mul_i32, { "r", "r", "ri" } }, | 1370 | { INDEX_op_mul_i32, { "r", "r", "ri" } }, |
1371 | + { INDEX_op_div_i32, { "r", "r", "r" } }, | ||
1372 | + { INDEX_op_divu_i32, { "r", "r", "r" } }, | ||
1373 | + { INDEX_op_rem_i32, { "r", "r", "r" } }, | ||
1374 | + { INDEX_op_remu_i32, { "r", "r", "r" } }, | ||
1461 | { INDEX_op_mulu2_i32, { "r", "r", "r", "r" } }, | 1375 | { INDEX_op_mulu2_i32, { "r", "r", "r", "r" } }, |
1462 | - { INDEX_op_div2_i32, { "D", "A", "B", "1", "C" } }, | ||
1463 | - { INDEX_op_divu2_i32, { "D", "A", "B", "1", "C" } }, | ||
1464 | { INDEX_op_sub_i32, { "r", "r", "ri" } }, | 1376 | { INDEX_op_sub_i32, { "r", "r", "ri" } }, |
1465 | { INDEX_op_and_i32, { "r", "r", "ri" } }, | 1377 | { INDEX_op_and_i32, { "r", "r", "ri" } }, |
1466 | { INDEX_op_or_i32, { "r", "r", "ri" } }, | 1378 | { INDEX_op_or_i32, { "r", "r", "ri" } }, |
tcg/ppc/tcg-target.h
@@ -70,6 +70,7 @@ enum { | @@ -70,6 +70,7 @@ enum { | ||
70 | 70 | ||
71 | /* optional instructions */ | 71 | /* optional instructions */ |
72 | #define TCG_TARGET_HAS_neg_i32 | 72 | #define TCG_TARGET_HAS_neg_i32 |
73 | +#define TCG_TARGET_HAS_div_i32 | ||
73 | 74 | ||
74 | #define TCG_AREG0 TCG_REG_R27 | 75 | #define TCG_AREG0 TCG_REG_R27 |
75 | #define TCG_AREG1 TCG_REG_R24 | 76 | #define TCG_AREG1 TCG_REG_R24 |