1 /* 2 * OpenRISC translation 3 * 4 * Copyright (c) 2011-2012 Jia Liu <proljc@gmail.com> 5 * Feng Gao <gf91597@gmail.com> 6 * 7 * This library is free software; you can redistribute it and/or 8 * modify it under the terms of the GNU Lesser General Public 9 * License as published by the Free Software Foundation; either 10 * version 2 of the License, or (at your option) any later version. 11 * 12 * This library is distributed in the hope that it will be useful, 13 * but WITHOUT ANY WARRANTY; without even the implied warranty of 14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 15 * Lesser General Public License for more details. 16 * 17 * You should have received a copy of the GNU Lesser General Public 18 * License along with this library; if not, see <http://www.gnu.org/licenses/>. 19 */ 20 21 #include "qemu/osdep.h" 22 #include "cpu.h" 23 #include "exec/exec-all.h" 24 #include "disas/disas.h" 25 #include "tcg-op.h" 26 #include "qemu-common.h" 27 #include "qemu/log.h" 28 #include "qemu/bitops.h" 29 #include "exec/cpu_ldst.h" 30 31 #include "exec/helper-proto.h" 32 #include "exec/helper-gen.h" 33 34 #include "trace-tcg.h" 35 #include "exec/log.h" 36 37 38 #define OPENRISC_DISAS 39 40 #ifdef OPENRISC_DISAS 41 # define LOG_DIS(...) qemu_log_mask(CPU_LOG_TB_IN_ASM, ## __VA_ARGS__) 42 #else 43 # define LOG_DIS(...) do { } while (0) 44 #endif 45 46 typedef struct DisasContext { 47 TranslationBlock *tb; 48 target_ulong pc, ppc, npc; 49 uint32_t tb_flags, synced_flags, flags; 50 uint32_t is_jmp; 51 uint32_t mem_idx; 52 int singlestep_enabled; 53 uint32_t delayed_branch; 54 } DisasContext; 55 56 static TCGv_env cpu_env; 57 static TCGv cpu_sr; 58 static TCGv cpu_R[32]; 59 static TCGv cpu_pc; 60 static TCGv jmp_pc; /* l.jr/l.jalr temp pc */ 61 static TCGv cpu_npc; 62 static TCGv cpu_ppc; 63 static TCGv_i32 env_btaken; /* bf/bnf , F flag taken */ 64 static TCGv_i32 fpcsr; 65 static TCGv machi, maclo; 66 static TCGv fpmaddhi, fpmaddlo; 67 static TCGv_i32 env_flags; 68 #include "exec/gen-icount.h" 69 70 void openrisc_translate_init(void) 71 { 72 static const char * const regnames[] = { 73 "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", 74 "r8", "r9", "r10", "r11", "r12", "r13", "r14", "r15", 75 "r16", "r17", "r18", "r19", "r20", "r21", "r22", "r23", 76 "r24", "r25", "r26", "r27", "r28", "r29", "r30", "r31", 77 }; 78 int i; 79 80 cpu_env = tcg_global_reg_new_ptr(TCG_AREG0, "env"); 81 tcg_ctx.tcg_env = cpu_env; 82 cpu_sr = tcg_global_mem_new(cpu_env, 83 offsetof(CPUOpenRISCState, sr), "sr"); 84 env_flags = tcg_global_mem_new_i32(cpu_env, 85 offsetof(CPUOpenRISCState, flags), 86 "flags"); 87 cpu_pc = tcg_global_mem_new(cpu_env, 88 offsetof(CPUOpenRISCState, pc), "pc"); 89 cpu_npc = tcg_global_mem_new(cpu_env, 90 offsetof(CPUOpenRISCState, npc), "npc"); 91 cpu_ppc = tcg_global_mem_new(cpu_env, 92 offsetof(CPUOpenRISCState, ppc), "ppc"); 93 jmp_pc = tcg_global_mem_new(cpu_env, 94 offsetof(CPUOpenRISCState, jmp_pc), "jmp_pc"); 95 env_btaken = tcg_global_mem_new_i32(cpu_env, 96 offsetof(CPUOpenRISCState, btaken), 97 "btaken"); 98 fpcsr = tcg_global_mem_new_i32(cpu_env, 99 offsetof(CPUOpenRISCState, fpcsr), 100 "fpcsr"); 101 machi = tcg_global_mem_new(cpu_env, 102 offsetof(CPUOpenRISCState, machi), 103 "machi"); 104 maclo = tcg_global_mem_new(cpu_env, 105 offsetof(CPUOpenRISCState, maclo), 106 "maclo"); 107 fpmaddhi = tcg_global_mem_new(cpu_env, 108 offsetof(CPUOpenRISCState, fpmaddhi), 109 "fpmaddhi"); 110 fpmaddlo = tcg_global_mem_new(cpu_env, 111 offsetof(CPUOpenRISCState, fpmaddlo), 112 "fpmaddlo"); 113 for (i = 0; i < 32; i++) { 114 cpu_R[i] = tcg_global_mem_new(cpu_env, 115 offsetof(CPUOpenRISCState, gpr[i]), 116 regnames[i]); 117 } 118 } 119 120 /* Writeback SR_F translation space to execution space. */ 121 static inline void wb_SR_F(void) 122 { 123 TCGLabel *label = gen_new_label(); 124 tcg_gen_andi_tl(cpu_sr, cpu_sr, ~SR_F); 125 tcg_gen_brcondi_tl(TCG_COND_EQ, env_btaken, 0, label); 126 tcg_gen_ori_tl(cpu_sr, cpu_sr, SR_F); 127 gen_set_label(label); 128 } 129 130 static inline int zero_extend(unsigned int val, int width) 131 { 132 return val & ((1 << width) - 1); 133 } 134 135 static inline int sign_extend(unsigned int val, int width) 136 { 137 int sval; 138 139 /* LSL */ 140 val <<= TARGET_LONG_BITS - width; 141 sval = val; 142 /* ASR. */ 143 sval >>= TARGET_LONG_BITS - width; 144 return sval; 145 } 146 147 static inline void gen_sync_flags(DisasContext *dc) 148 { 149 /* Sync the tb dependent flag between translate and runtime. */ 150 if (dc->tb_flags != dc->synced_flags) { 151 tcg_gen_movi_tl(env_flags, dc->tb_flags); 152 dc->synced_flags = dc->tb_flags; 153 } 154 } 155 156 static void gen_exception(DisasContext *dc, unsigned int excp) 157 { 158 TCGv_i32 tmp = tcg_const_i32(excp); 159 gen_helper_exception(cpu_env, tmp); 160 tcg_temp_free_i32(tmp); 161 } 162 163 static void gen_illegal_exception(DisasContext *dc) 164 { 165 tcg_gen_movi_tl(cpu_pc, dc->pc); 166 gen_exception(dc, EXCP_ILLEGAL); 167 dc->is_jmp = DISAS_UPDATE; 168 } 169 170 /* not used yet, open it when we need or64. */ 171 /*#ifdef TARGET_OPENRISC64 172 static void check_ob64s(DisasContext *dc) 173 { 174 if (!(dc->flags & CPUCFGR_OB64S)) { 175 gen_illegal_exception(dc); 176 } 177 } 178 179 static void check_of64s(DisasContext *dc) 180 { 181 if (!(dc->flags & CPUCFGR_OF64S)) { 182 gen_illegal_exception(dc); 183 } 184 } 185 186 static void check_ov64s(DisasContext *dc) 187 { 188 if (!(dc->flags & CPUCFGR_OV64S)) { 189 gen_illegal_exception(dc); 190 } 191 } 192 #endif*/ 193 194 static inline bool use_goto_tb(DisasContext *dc, target_ulong dest) 195 { 196 if (unlikely(dc->singlestep_enabled)) { 197 return false; 198 } 199 200 #ifndef CONFIG_USER_ONLY 201 return (dc->tb->pc & TARGET_PAGE_MASK) == (dest & TARGET_PAGE_MASK); 202 #else 203 return true; 204 #endif 205 } 206 207 static void gen_goto_tb(DisasContext *dc, int n, target_ulong dest) 208 { 209 if (use_goto_tb(dc, dest)) { 210 tcg_gen_movi_tl(cpu_pc, dest); 211 tcg_gen_goto_tb(n); 212 tcg_gen_exit_tb((uintptr_t)dc->tb + n); 213 } else { 214 tcg_gen_movi_tl(cpu_pc, dest); 215 if (dc->singlestep_enabled) { 216 gen_exception(dc, EXCP_DEBUG); 217 } 218 tcg_gen_exit_tb(0); 219 } 220 } 221 222 static void gen_jump(DisasContext *dc, uint32_t imm, uint32_t reg, uint32_t op0) 223 { 224 target_ulong tmp_pc; 225 /* N26, 26bits imm */ 226 tmp_pc = sign_extend((imm<<2), 26) + dc->pc; 227 228 switch (op0) { 229 case 0x00: /* l.j */ 230 tcg_gen_movi_tl(jmp_pc, tmp_pc); 231 break; 232 case 0x01: /* l.jal */ 233 tcg_gen_movi_tl(cpu_R[9], (dc->pc + 8)); 234 tcg_gen_movi_tl(jmp_pc, tmp_pc); 235 break; 236 case 0x03: /* l.bnf */ 237 case 0x04: /* l.bf */ 238 { 239 TCGLabel *lab = gen_new_label(); 240 TCGv sr_f = tcg_temp_new(); 241 tcg_gen_movi_tl(jmp_pc, dc->pc+8); 242 tcg_gen_andi_tl(sr_f, cpu_sr, SR_F); 243 tcg_gen_brcondi_i32(op0 == 0x03 ? TCG_COND_EQ : TCG_COND_NE, 244 sr_f, SR_F, lab); 245 tcg_gen_movi_tl(jmp_pc, tmp_pc); 246 gen_set_label(lab); 247 tcg_temp_free(sr_f); 248 } 249 break; 250 case 0x11: /* l.jr */ 251 tcg_gen_mov_tl(jmp_pc, cpu_R[reg]); 252 break; 253 case 0x12: /* l.jalr */ 254 tcg_gen_movi_tl(cpu_R[9], (dc->pc + 8)); 255 tcg_gen_mov_tl(jmp_pc, cpu_R[reg]); 256 break; 257 default: 258 gen_illegal_exception(dc); 259 break; 260 } 261 262 dc->delayed_branch = 2; 263 dc->tb_flags |= D_FLAG; 264 gen_sync_flags(dc); 265 } 266 267 268 static void dec_calc(DisasContext *dc, uint32_t insn) 269 { 270 uint32_t op0, op1, op2; 271 uint32_t ra, rb, rd; 272 op0 = extract32(insn, 0, 4); 273 op1 = extract32(insn, 8, 2); 274 op2 = extract32(insn, 6, 2); 275 ra = extract32(insn, 16, 5); 276 rb = extract32(insn, 11, 5); 277 rd = extract32(insn, 21, 5); 278 279 switch (op0) { 280 case 0x0000: 281 switch (op1) { 282 case 0x00: /* l.add */ 283 LOG_DIS("l.add r%d, r%d, r%d\n", rd, ra, rb); 284 { 285 TCGLabel *lab = gen_new_label(); 286 TCGv_i64 ta = tcg_temp_new_i64(); 287 TCGv_i64 tb = tcg_temp_new_i64(); 288 TCGv_i64 td = tcg_temp_local_new_i64(); 289 TCGv_i32 res = tcg_temp_local_new_i32(); 290 TCGv_i32 sr_ove = tcg_temp_local_new_i32(); 291 tcg_gen_extu_i32_i64(ta, cpu_R[ra]); 292 tcg_gen_extu_i32_i64(tb, cpu_R[rb]); 293 tcg_gen_add_i64(td, ta, tb); 294 tcg_gen_extrl_i64_i32(res, td); 295 tcg_gen_shri_i64(td, td, 31); 296 tcg_gen_andi_i64(td, td, 0x3); 297 /* Jump to lab when no overflow. */ 298 tcg_gen_brcondi_i64(TCG_COND_EQ, td, 0x0, lab); 299 tcg_gen_brcondi_i64(TCG_COND_EQ, td, 0x3, lab); 300 tcg_gen_ori_i32(cpu_sr, cpu_sr, (SR_OV | SR_CY)); 301 tcg_gen_andi_i32(sr_ove, cpu_sr, SR_OVE); 302 tcg_gen_brcondi_i32(TCG_COND_NE, sr_ove, SR_OVE, lab); 303 gen_exception(dc, EXCP_RANGE); 304 gen_set_label(lab); 305 tcg_gen_mov_i32(cpu_R[rd], res); 306 tcg_temp_free_i64(ta); 307 tcg_temp_free_i64(tb); 308 tcg_temp_free_i64(td); 309 tcg_temp_free_i32(res); 310 tcg_temp_free_i32(sr_ove); 311 } 312 break; 313 default: 314 gen_illegal_exception(dc); 315 break; 316 } 317 break; 318 319 case 0x0001: /* l.addc */ 320 switch (op1) { 321 case 0x00: 322 LOG_DIS("l.addc r%d, r%d, r%d\n", rd, ra, rb); 323 { 324 TCGLabel *lab = gen_new_label(); 325 TCGv_i64 ta = tcg_temp_new_i64(); 326 TCGv_i64 tb = tcg_temp_new_i64(); 327 TCGv_i64 tcy = tcg_temp_local_new_i64(); 328 TCGv_i64 td = tcg_temp_local_new_i64(); 329 TCGv_i32 res = tcg_temp_local_new_i32(); 330 TCGv_i32 sr_cy = tcg_temp_local_new_i32(); 331 TCGv_i32 sr_ove = tcg_temp_local_new_i32(); 332 tcg_gen_extu_i32_i64(ta, cpu_R[ra]); 333 tcg_gen_extu_i32_i64(tb, cpu_R[rb]); 334 tcg_gen_andi_i32(sr_cy, cpu_sr, SR_CY); 335 tcg_gen_extu_i32_i64(tcy, sr_cy); 336 tcg_gen_shri_i64(tcy, tcy, 10); 337 tcg_gen_add_i64(td, ta, tb); 338 tcg_gen_add_i64(td, td, tcy); 339 tcg_gen_extrl_i64_i32(res, td); 340 tcg_gen_shri_i64(td, td, 32); 341 tcg_gen_andi_i64(td, td, 0x3); 342 /* Jump to lab when no overflow. */ 343 tcg_gen_brcondi_i64(TCG_COND_EQ, td, 0x0, lab); 344 tcg_gen_brcondi_i64(TCG_COND_EQ, td, 0x3, lab); 345 tcg_gen_ori_i32(cpu_sr, cpu_sr, (SR_OV | SR_CY)); 346 tcg_gen_andi_i32(sr_ove, cpu_sr, SR_OVE); 347 tcg_gen_brcondi_i32(TCG_COND_NE, sr_ove, SR_OVE, lab); 348 gen_exception(dc, EXCP_RANGE); 349 gen_set_label(lab); 350 tcg_gen_mov_i32(cpu_R[rd], res); 351 tcg_temp_free_i64(ta); 352 tcg_temp_free_i64(tb); 353 tcg_temp_free_i64(tcy); 354 tcg_temp_free_i64(td); 355 tcg_temp_free_i32(res); 356 tcg_temp_free_i32(sr_cy); 357 tcg_temp_free_i32(sr_ove); 358 } 359 break; 360 default: 361 gen_illegal_exception(dc); 362 break; 363 } 364 break; 365 366 case 0x0002: /* l.sub */ 367 switch (op1) { 368 case 0x00: 369 LOG_DIS("l.sub r%d, r%d, r%d\n", rd, ra, rb); 370 { 371 TCGLabel *lab = gen_new_label(); 372 TCGv_i64 ta = tcg_temp_new_i64(); 373 TCGv_i64 tb = tcg_temp_new_i64(); 374 TCGv_i64 td = tcg_temp_local_new_i64(); 375 TCGv_i32 res = tcg_temp_local_new_i32(); 376 TCGv_i32 sr_ove = tcg_temp_local_new_i32(); 377 378 tcg_gen_extu_i32_i64(ta, cpu_R[ra]); 379 tcg_gen_extu_i32_i64(tb, cpu_R[rb]); 380 tcg_gen_sub_i64(td, ta, tb); 381 tcg_gen_extrl_i64_i32(res, td); 382 tcg_gen_shri_i64(td, td, 31); 383 tcg_gen_andi_i64(td, td, 0x3); 384 /* Jump to lab when no overflow. */ 385 tcg_gen_brcondi_i64(TCG_COND_EQ, td, 0x0, lab); 386 tcg_gen_brcondi_i64(TCG_COND_EQ, td, 0x3, lab); 387 tcg_gen_ori_i32(cpu_sr, cpu_sr, (SR_OV | SR_CY)); 388 tcg_gen_andi_i32(sr_ove, cpu_sr, SR_OVE); 389 tcg_gen_brcondi_i32(TCG_COND_NE, sr_ove, SR_OVE, lab); 390 gen_exception(dc, EXCP_RANGE); 391 gen_set_label(lab); 392 tcg_gen_mov_i32(cpu_R[rd], res); 393 tcg_temp_free_i64(ta); 394 tcg_temp_free_i64(tb); 395 tcg_temp_free_i64(td); 396 tcg_temp_free_i32(res); 397 tcg_temp_free_i32(sr_ove); 398 } 399 break; 400 default: 401 gen_illegal_exception(dc); 402 break; 403 } 404 break; 405 406 case 0x0003: /* l.and */ 407 switch (op1) { 408 case 0x00: 409 LOG_DIS("l.and r%d, r%d, r%d\n", rd, ra, rb); 410 tcg_gen_and_tl(cpu_R[rd], cpu_R[ra], cpu_R[rb]); 411 break; 412 default: 413 gen_illegal_exception(dc); 414 break; 415 } 416 break; 417 418 case 0x0004: /* l.or */ 419 switch (op1) { 420 case 0x00: 421 LOG_DIS("l.or r%d, r%d, r%d\n", rd, ra, rb); 422 tcg_gen_or_tl(cpu_R[rd], cpu_R[ra], cpu_R[rb]); 423 break; 424 default: 425 gen_illegal_exception(dc); 426 break; 427 } 428 break; 429 430 case 0x0005: 431 switch (op1) { 432 case 0x00: /* l.xor */ 433 LOG_DIS("l.xor r%d, r%d, r%d\n", rd, ra, rb); 434 tcg_gen_xor_tl(cpu_R[rd], cpu_R[ra], cpu_R[rb]); 435 break; 436 default: 437 gen_illegal_exception(dc); 438 break; 439 } 440 break; 441 442 case 0x0006: 443 switch (op1) { 444 case 0x03: /* l.mul */ 445 LOG_DIS("l.mul r%d, r%d, r%d\n", rd, ra, rb); 446 if (ra != 0 && rb != 0) { 447 gen_helper_mul32(cpu_R[rd], cpu_env, cpu_R[ra], cpu_R[rb]); 448 } else { 449 tcg_gen_movi_tl(cpu_R[rd], 0x0); 450 } 451 break; 452 default: 453 gen_illegal_exception(dc); 454 break; 455 } 456 break; 457 458 case 0x0009: 459 switch (op1) { 460 case 0x03: /* l.div */ 461 LOG_DIS("l.div r%d, r%d, r%d\n", rd, ra, rb); 462 { 463 TCGLabel *lab0 = gen_new_label(); 464 TCGLabel *lab1 = gen_new_label(); 465 TCGLabel *lab2 = gen_new_label(); 466 TCGLabel *lab3 = gen_new_label(); 467 TCGv_i32 sr_ove = tcg_temp_local_new_i32(); 468 if (rb == 0) { 469 tcg_gen_ori_tl(cpu_sr, cpu_sr, (SR_OV | SR_CY)); 470 tcg_gen_andi_tl(sr_ove, cpu_sr, SR_OVE); 471 tcg_gen_brcondi_tl(TCG_COND_NE, sr_ove, SR_OVE, lab0); 472 gen_exception(dc, EXCP_RANGE); 473 gen_set_label(lab0); 474 } else { 475 tcg_gen_brcondi_tl(TCG_COND_EQ, cpu_R[rb], 476 0x00000000, lab1); 477 tcg_gen_brcondi_tl(TCG_COND_NE, cpu_R[ra], 478 0x80000000, lab2); 479 tcg_gen_brcondi_tl(TCG_COND_NE, cpu_R[rb], 480 0xffffffff, lab2); 481 gen_set_label(lab1); 482 tcg_gen_ori_tl(cpu_sr, cpu_sr, (SR_OV | SR_CY)); 483 tcg_gen_andi_tl(sr_ove, cpu_sr, SR_OVE); 484 tcg_gen_brcondi_tl(TCG_COND_NE, sr_ove, SR_OVE, lab3); 485 gen_exception(dc, EXCP_RANGE); 486 gen_set_label(lab2); 487 tcg_gen_div_tl(cpu_R[rd], cpu_R[ra], cpu_R[rb]); 488 gen_set_label(lab3); 489 } 490 tcg_temp_free_i32(sr_ove); 491 } 492 break; 493 494 default: 495 gen_illegal_exception(dc); 496 break; 497 } 498 break; 499 500 case 0x000a: 501 switch (op1) { 502 case 0x03: /* l.divu */ 503 LOG_DIS("l.divu r%d, r%d, r%d\n", rd, ra, rb); 504 { 505 TCGLabel *lab0 = gen_new_label(); 506 TCGLabel *lab1 = gen_new_label(); 507 TCGLabel *lab2 = gen_new_label(); 508 TCGv_i32 sr_ove = tcg_temp_local_new_i32(); 509 if (rb == 0) { 510 tcg_gen_ori_tl(cpu_sr, cpu_sr, (SR_OV | SR_CY)); 511 tcg_gen_andi_tl(sr_ove, cpu_sr, SR_OVE); 512 tcg_gen_brcondi_tl(TCG_COND_NE, sr_ove, SR_OVE, lab0); 513 gen_exception(dc, EXCP_RANGE); 514 gen_set_label(lab0); 515 } else { 516 tcg_gen_brcondi_tl(TCG_COND_NE, cpu_R[rb], 517 0x00000000, lab1); 518 tcg_gen_ori_tl(cpu_sr, cpu_sr, (SR_OV | SR_CY)); 519 tcg_gen_andi_tl(sr_ove, cpu_sr, SR_OVE); 520 tcg_gen_brcondi_tl(TCG_COND_NE, sr_ove, SR_OVE, lab2); 521 gen_exception(dc, EXCP_RANGE); 522 gen_set_label(lab1); 523 tcg_gen_divu_tl(cpu_R[rd], cpu_R[ra], cpu_R[rb]); 524 gen_set_label(lab2); 525 } 526 tcg_temp_free_i32(sr_ove); 527 } 528 break; 529 530 default: 531 gen_illegal_exception(dc); 532 break; 533 } 534 break; 535 536 case 0x000b: 537 switch (op1) { 538 case 0x03: /* l.mulu */ 539 LOG_DIS("l.mulu r%d, r%d, r%d\n", rd, ra, rb); 540 if (rb != 0 && ra != 0) { 541 TCGv_i64 result = tcg_temp_local_new_i64(); 542 TCGv_i64 tra = tcg_temp_local_new_i64(); 543 TCGv_i64 trb = tcg_temp_local_new_i64(); 544 TCGv_i64 high = tcg_temp_new_i64(); 545 TCGv_i32 sr_ove = tcg_temp_local_new_i32(); 546 TCGLabel *lab = gen_new_label(); 547 /* Calculate each result. */ 548 tcg_gen_extu_i32_i64(tra, cpu_R[ra]); 549 tcg_gen_extu_i32_i64(trb, cpu_R[rb]); 550 tcg_gen_mul_i64(result, tra, trb); 551 tcg_temp_free_i64(tra); 552 tcg_temp_free_i64(trb); 553 tcg_gen_shri_i64(high, result, TARGET_LONG_BITS); 554 /* Overflow or not. */ 555 tcg_gen_brcondi_i64(TCG_COND_EQ, high, 0x00000000, lab); 556 tcg_gen_ori_tl(cpu_sr, cpu_sr, (SR_OV | SR_CY)); 557 tcg_gen_andi_tl(sr_ove, cpu_sr, SR_OVE); 558 tcg_gen_brcondi_tl(TCG_COND_NE, sr_ove, SR_OVE, lab); 559 gen_exception(dc, EXCP_RANGE); 560 gen_set_label(lab); 561 tcg_temp_free_i64(high); 562 tcg_gen_trunc_i64_tl(cpu_R[rd], result); 563 tcg_temp_free_i64(result); 564 tcg_temp_free_i32(sr_ove); 565 } else { 566 tcg_gen_movi_tl(cpu_R[rd], 0); 567 } 568 break; 569 570 default: 571 gen_illegal_exception(dc); 572 break; 573 } 574 break; 575 576 case 0x000e: 577 switch (op1) { 578 case 0x00: /* l.cmov */ 579 LOG_DIS("l.cmov r%d, r%d, r%d\n", rd, ra, rb); 580 { 581 TCGLabel *lab = gen_new_label(); 582 TCGv res = tcg_temp_local_new(); 583 TCGv sr_f = tcg_temp_new(); 584 tcg_gen_andi_tl(sr_f, cpu_sr, SR_F); 585 tcg_gen_mov_tl(res, cpu_R[rb]); 586 tcg_gen_brcondi_tl(TCG_COND_NE, sr_f, SR_F, lab); 587 tcg_gen_mov_tl(res, cpu_R[ra]); 588 gen_set_label(lab); 589 tcg_gen_mov_tl(cpu_R[rd], res); 590 tcg_temp_free(sr_f); 591 tcg_temp_free(res); 592 } 593 break; 594 595 default: 596 gen_illegal_exception(dc); 597 break; 598 } 599 break; 600 601 case 0x000f: 602 switch (op1) { 603 case 0x00: /* l.ff1 */ 604 LOG_DIS("l.ff1 r%d, r%d, r%d\n", rd, ra, rb); 605 tcg_gen_ctzi_tl(cpu_R[rd], cpu_R[ra], -1); 606 tcg_gen_addi_tl(cpu_R[rd], cpu_R[rd], 1); 607 break; 608 case 0x01: /* l.fl1 */ 609 LOG_DIS("l.fl1 r%d, r%d, r%d\n", rd, ra, rb); 610 tcg_gen_clzi_tl(cpu_R[rd], cpu_R[ra], TARGET_LONG_BITS); 611 tcg_gen_subfi_tl(cpu_R[rd], TARGET_LONG_BITS, cpu_R[rd]); 612 break; 613 614 default: 615 gen_illegal_exception(dc); 616 break; 617 } 618 break; 619 620 case 0x0008: 621 switch (op1) { 622 case 0x00: 623 switch (op2) { 624 case 0x00: /* l.sll */ 625 LOG_DIS("l.sll r%d, r%d, r%d\n", rd, ra, rb); 626 tcg_gen_shl_tl(cpu_R[rd], cpu_R[ra], cpu_R[rb]); 627 break; 628 case 0x01: /* l.srl */ 629 LOG_DIS("l.srl r%d, r%d, r%d\n", rd, ra, rb); 630 tcg_gen_shr_tl(cpu_R[rd], cpu_R[ra], cpu_R[rb]); 631 break; 632 case 0x02: /* l.sra */ 633 LOG_DIS("l.sra r%d, r%d, r%d\n", rd, ra, rb); 634 tcg_gen_sar_tl(cpu_R[rd], cpu_R[ra], cpu_R[rb]); 635 break; 636 case 0x03: /* l.ror */ 637 LOG_DIS("l.ror r%d, r%d, r%d\n", rd, ra, rb); 638 tcg_gen_rotr_tl(cpu_R[rd], cpu_R[ra], cpu_R[rb]); 639 break; 640 641 default: 642 gen_illegal_exception(dc); 643 break; 644 } 645 break; 646 647 default: 648 gen_illegal_exception(dc); 649 break; 650 } 651 break; 652 653 case 0x000c: 654 switch (op1) { 655 case 0x00: 656 switch (op2) { 657 case 0x00: /* l.exths */ 658 LOG_DIS("l.exths r%d, r%d\n", rd, ra); 659 tcg_gen_ext16s_tl(cpu_R[rd], cpu_R[ra]); 660 break; 661 case 0x01: /* l.extbs */ 662 LOG_DIS("l.extbs r%d, r%d\n", rd, ra); 663 tcg_gen_ext8s_tl(cpu_R[rd], cpu_R[ra]); 664 break; 665 case 0x02: /* l.exthz */ 666 LOG_DIS("l.exthz r%d, r%d\n", rd, ra); 667 tcg_gen_ext16u_tl(cpu_R[rd], cpu_R[ra]); 668 break; 669 case 0x03: /* l.extbz */ 670 LOG_DIS("l.extbz r%d, r%d\n", rd, ra); 671 tcg_gen_ext8u_tl(cpu_R[rd], cpu_R[ra]); 672 break; 673 674 default: 675 gen_illegal_exception(dc); 676 break; 677 } 678 break; 679 680 default: 681 gen_illegal_exception(dc); 682 break; 683 } 684 break; 685 686 case 0x000d: 687 switch (op1) { 688 case 0x00: 689 switch (op2) { 690 case 0x00: /* l.extws */ 691 LOG_DIS("l.extws r%d, r%d\n", rd, ra); 692 tcg_gen_ext32s_tl(cpu_R[rd], cpu_R[ra]); 693 break; 694 case 0x01: /* l.extwz */ 695 LOG_DIS("l.extwz r%d, r%d\n", rd, ra); 696 tcg_gen_ext32u_tl(cpu_R[rd], cpu_R[ra]); 697 break; 698 699 default: 700 gen_illegal_exception(dc); 701 break; 702 } 703 break; 704 705 default: 706 gen_illegal_exception(dc); 707 break; 708 } 709 break; 710 711 default: 712 gen_illegal_exception(dc); 713 break; 714 } 715 } 716 717 static void dec_misc(DisasContext *dc, uint32_t insn) 718 { 719 uint32_t op0, op1; 720 uint32_t ra, rb, rd; 721 #ifdef OPENRISC_DISAS 722 uint32_t L6, K5; 723 #endif 724 uint32_t I16, I5, I11, N26, tmp; 725 TCGMemOp mop; 726 727 op0 = extract32(insn, 26, 6); 728 op1 = extract32(insn, 24, 2); 729 ra = extract32(insn, 16, 5); 730 rb = extract32(insn, 11, 5); 731 rd = extract32(insn, 21, 5); 732 #ifdef OPENRISC_DISAS 733 L6 = extract32(insn, 5, 6); 734 K5 = extract32(insn, 0, 5); 735 #endif 736 I16 = extract32(insn, 0, 16); 737 I5 = extract32(insn, 21, 5); 738 I11 = extract32(insn, 0, 11); 739 N26 = extract32(insn, 0, 26); 740 tmp = (I5<<11) + I11; 741 742 switch (op0) { 743 case 0x00: /* l.j */ 744 LOG_DIS("l.j %d\n", N26); 745 gen_jump(dc, N26, 0, op0); 746 break; 747 748 case 0x01: /* l.jal */ 749 LOG_DIS("l.jal %d\n", N26); 750 gen_jump(dc, N26, 0, op0); 751 break; 752 753 case 0x03: /* l.bnf */ 754 LOG_DIS("l.bnf %d\n", N26); 755 gen_jump(dc, N26, 0, op0); 756 break; 757 758 case 0x04: /* l.bf */ 759 LOG_DIS("l.bf %d\n", N26); 760 gen_jump(dc, N26, 0, op0); 761 break; 762 763 case 0x05: 764 switch (op1) { 765 case 0x01: /* l.nop */ 766 LOG_DIS("l.nop %d\n", I16); 767 break; 768 769 default: 770 gen_illegal_exception(dc); 771 break; 772 } 773 break; 774 775 case 0x11: /* l.jr */ 776 LOG_DIS("l.jr r%d\n", rb); 777 gen_jump(dc, 0, rb, op0); 778 break; 779 780 case 0x12: /* l.jalr */ 781 LOG_DIS("l.jalr r%d\n", rb); 782 gen_jump(dc, 0, rb, op0); 783 break; 784 785 case 0x13: /* l.maci */ 786 LOG_DIS("l.maci %d, r%d, %d\n", I5, ra, I11); 787 { 788 TCGv_i64 t1 = tcg_temp_new_i64(); 789 TCGv_i64 t2 = tcg_temp_new_i64(); 790 TCGv_i32 dst = tcg_temp_new_i32(); 791 TCGv ttmp = tcg_const_tl(tmp); 792 tcg_gen_mul_tl(dst, cpu_R[ra], ttmp); 793 tcg_gen_ext_i32_i64(t1, dst); 794 tcg_gen_concat_i32_i64(t2, maclo, machi); 795 tcg_gen_add_i64(t2, t2, t1); 796 tcg_gen_extrl_i64_i32(maclo, t2); 797 tcg_gen_shri_i64(t2, t2, 32); 798 tcg_gen_extrl_i64_i32(machi, t2); 799 tcg_temp_free_i32(dst); 800 tcg_temp_free(ttmp); 801 tcg_temp_free_i64(t1); 802 tcg_temp_free_i64(t2); 803 } 804 break; 805 806 case 0x09: /* l.rfe */ 807 LOG_DIS("l.rfe\n"); 808 { 809 #if defined(CONFIG_USER_ONLY) 810 return; 811 #else 812 if (dc->mem_idx == MMU_USER_IDX) { 813 gen_illegal_exception(dc); 814 return; 815 } 816 gen_helper_rfe(cpu_env); 817 dc->is_jmp = DISAS_UPDATE; 818 #endif 819 } 820 break; 821 822 case 0x1c: /* l.cust1 */ 823 LOG_DIS("l.cust1\n"); 824 break; 825 826 case 0x1d: /* l.cust2 */ 827 LOG_DIS("l.cust2\n"); 828 break; 829 830 case 0x1e: /* l.cust3 */ 831 LOG_DIS("l.cust3\n"); 832 break; 833 834 case 0x1f: /* l.cust4 */ 835 LOG_DIS("l.cust4\n"); 836 break; 837 838 case 0x3c: /* l.cust5 */ 839 LOG_DIS("l.cust5 r%d, r%d, r%d, %d, %d\n", rd, ra, rb, L6, K5); 840 break; 841 842 case 0x3d: /* l.cust6 */ 843 LOG_DIS("l.cust6\n"); 844 break; 845 846 case 0x3e: /* l.cust7 */ 847 LOG_DIS("l.cust7\n"); 848 break; 849 850 case 0x3f: /* l.cust8 */ 851 LOG_DIS("l.cust8\n"); 852 break; 853 854 /* not used yet, open it when we need or64. */ 855 /*#ifdef TARGET_OPENRISC64 856 case 0x20: l.ld 857 LOG_DIS("l.ld r%d, r%d, %d\n", rd, ra, I16); 858 check_ob64s(dc); 859 mop = MO_TEQ; 860 goto do_load; 861 #endif*/ 862 863 case 0x21: /* l.lwz */ 864 LOG_DIS("l.lwz r%d, r%d, %d\n", rd, ra, I16); 865 mop = MO_TEUL; 866 goto do_load; 867 868 case 0x22: /* l.lws */ 869 LOG_DIS("l.lws r%d, r%d, %d\n", rd, ra, I16); 870 mop = MO_TESL; 871 goto do_load; 872 873 case 0x23: /* l.lbz */ 874 LOG_DIS("l.lbz r%d, r%d, %d\n", rd, ra, I16); 875 mop = MO_UB; 876 goto do_load; 877 878 case 0x24: /* l.lbs */ 879 LOG_DIS("l.lbs r%d, r%d, %d\n", rd, ra, I16); 880 mop = MO_SB; 881 goto do_load; 882 883 case 0x25: /* l.lhz */ 884 LOG_DIS("l.lhz r%d, r%d, %d\n", rd, ra, I16); 885 mop = MO_TEUW; 886 goto do_load; 887 888 case 0x26: /* l.lhs */ 889 LOG_DIS("l.lhs r%d, r%d, %d\n", rd, ra, I16); 890 mop = MO_TESW; 891 goto do_load; 892 893 do_load: 894 { 895 TCGv t0 = tcg_temp_new(); 896 tcg_gen_addi_tl(t0, cpu_R[ra], sign_extend(I16, 16)); 897 tcg_gen_qemu_ld_tl(cpu_R[rd], t0, dc->mem_idx, mop); 898 tcg_temp_free(t0); 899 } 900 break; 901 902 case 0x27: /* l.addi */ 903 LOG_DIS("l.addi r%d, r%d, %d\n", rd, ra, I16); 904 { 905 if (I16 == 0) { 906 tcg_gen_mov_tl(cpu_R[rd], cpu_R[ra]); 907 } else { 908 TCGLabel *lab = gen_new_label(); 909 TCGv_i64 ta = tcg_temp_new_i64(); 910 TCGv_i64 td = tcg_temp_local_new_i64(); 911 TCGv_i32 res = tcg_temp_local_new_i32(); 912 TCGv_i32 sr_ove = tcg_temp_local_new_i32(); 913 tcg_gen_extu_i32_i64(ta, cpu_R[ra]); 914 tcg_gen_addi_i64(td, ta, sign_extend(I16, 16)); 915 tcg_gen_extrl_i64_i32(res, td); 916 tcg_gen_shri_i64(td, td, 32); 917 tcg_gen_andi_i64(td, td, 0x3); 918 /* Jump to lab when no overflow. */ 919 tcg_gen_brcondi_i64(TCG_COND_EQ, td, 0x0, lab); 920 tcg_gen_brcondi_i64(TCG_COND_EQ, td, 0x3, lab); 921 tcg_gen_ori_i32(cpu_sr, cpu_sr, (SR_OV | SR_CY)); 922 tcg_gen_andi_i32(sr_ove, cpu_sr, SR_OVE); 923 tcg_gen_brcondi_i32(TCG_COND_NE, sr_ove, SR_OVE, lab); 924 gen_exception(dc, EXCP_RANGE); 925 gen_set_label(lab); 926 tcg_gen_mov_i32(cpu_R[rd], res); 927 tcg_temp_free_i64(ta); 928 tcg_temp_free_i64(td); 929 tcg_temp_free_i32(res); 930 tcg_temp_free_i32(sr_ove); 931 } 932 } 933 break; 934 935 case 0x28: /* l.addic */ 936 LOG_DIS("l.addic r%d, r%d, %d\n", rd, ra, I16); 937 { 938 TCGLabel *lab = gen_new_label(); 939 TCGv_i64 ta = tcg_temp_new_i64(); 940 TCGv_i64 td = tcg_temp_local_new_i64(); 941 TCGv_i64 tcy = tcg_temp_local_new_i64(); 942 TCGv_i32 res = tcg_temp_local_new_i32(); 943 TCGv_i32 sr_cy = tcg_temp_local_new_i32(); 944 TCGv_i32 sr_ove = tcg_temp_local_new_i32(); 945 tcg_gen_extu_i32_i64(ta, cpu_R[ra]); 946 tcg_gen_andi_i32(sr_cy, cpu_sr, SR_CY); 947 tcg_gen_shri_i32(sr_cy, sr_cy, 10); 948 tcg_gen_extu_i32_i64(tcy, sr_cy); 949 tcg_gen_addi_i64(td, ta, sign_extend(I16, 16)); 950 tcg_gen_add_i64(td, td, tcy); 951 tcg_gen_extrl_i64_i32(res, td); 952 tcg_gen_shri_i64(td, td, 32); 953 tcg_gen_andi_i64(td, td, 0x3); 954 /* Jump to lab when no overflow. */ 955 tcg_gen_brcondi_i64(TCG_COND_EQ, td, 0x0, lab); 956 tcg_gen_brcondi_i64(TCG_COND_EQ, td, 0x3, lab); 957 tcg_gen_ori_i32(cpu_sr, cpu_sr, (SR_OV | SR_CY)); 958 tcg_gen_andi_i32(sr_ove, cpu_sr, SR_OVE); 959 tcg_gen_brcondi_i32(TCG_COND_NE, sr_ove, SR_OVE, lab); 960 gen_exception(dc, EXCP_RANGE); 961 gen_set_label(lab); 962 tcg_gen_mov_i32(cpu_R[rd], res); 963 tcg_temp_free_i64(ta); 964 tcg_temp_free_i64(td); 965 tcg_temp_free_i64(tcy); 966 tcg_temp_free_i32(res); 967 tcg_temp_free_i32(sr_cy); 968 tcg_temp_free_i32(sr_ove); 969 } 970 break; 971 972 case 0x29: /* l.andi */ 973 LOG_DIS("l.andi r%d, r%d, %d\n", rd, ra, I16); 974 tcg_gen_andi_tl(cpu_R[rd], cpu_R[ra], zero_extend(I16, 16)); 975 break; 976 977 case 0x2a: /* l.ori */ 978 LOG_DIS("l.ori r%d, r%d, %d\n", rd, ra, I16); 979 tcg_gen_ori_tl(cpu_R[rd], cpu_R[ra], zero_extend(I16, 16)); 980 break; 981 982 case 0x2b: /* l.xori */ 983 LOG_DIS("l.xori r%d, r%d, %d\n", rd, ra, I16); 984 tcg_gen_xori_tl(cpu_R[rd], cpu_R[ra], sign_extend(I16, 16)); 985 break; 986 987 case 0x2c: /* l.muli */ 988 LOG_DIS("l.muli r%d, r%d, %d\n", rd, ra, I16); 989 if (ra != 0 && I16 != 0) { 990 TCGv_i32 im = tcg_const_i32(I16); 991 gen_helper_mul32(cpu_R[rd], cpu_env, cpu_R[ra], im); 992 tcg_temp_free_i32(im); 993 } else { 994 tcg_gen_movi_tl(cpu_R[rd], 0x0); 995 } 996 break; 997 998 case 0x2d: /* l.mfspr */ 999 LOG_DIS("l.mfspr r%d, r%d, %d\n", rd, ra, I16); 1000 { 1001 #if defined(CONFIG_USER_ONLY) 1002 return; 1003 #else 1004 TCGv_i32 ti = tcg_const_i32(I16); 1005 if (dc->mem_idx == MMU_USER_IDX) { 1006 gen_illegal_exception(dc); 1007 return; 1008 } 1009 gen_helper_mfspr(cpu_R[rd], cpu_env, cpu_R[rd], cpu_R[ra], ti); 1010 tcg_temp_free_i32(ti); 1011 #endif 1012 } 1013 break; 1014 1015 case 0x30: /* l.mtspr */ 1016 LOG_DIS("l.mtspr %d, r%d, r%d, %d\n", I5, ra, rb, I11); 1017 { 1018 #if defined(CONFIG_USER_ONLY) 1019 return; 1020 #else 1021 TCGv_i32 im = tcg_const_i32(tmp); 1022 if (dc->mem_idx == MMU_USER_IDX) { 1023 gen_illegal_exception(dc); 1024 return; 1025 } 1026 gen_helper_mtspr(cpu_env, cpu_R[ra], cpu_R[rb], im); 1027 tcg_temp_free_i32(im); 1028 #endif 1029 } 1030 break; 1031 1032 /* not used yet, open it when we need or64. */ 1033 /*#ifdef TARGET_OPENRISC64 1034 case 0x34: l.sd 1035 LOG_DIS("l.sd %d, r%d, r%d, %d\n", I5, ra, rb, I11); 1036 check_ob64s(dc); 1037 mop = MO_TEQ; 1038 goto do_store; 1039 #endif*/ 1040 1041 case 0x35: /* l.sw */ 1042 LOG_DIS("l.sw %d, r%d, r%d, %d\n", I5, ra, rb, I11); 1043 mop = MO_TEUL; 1044 goto do_store; 1045 1046 case 0x36: /* l.sb */ 1047 LOG_DIS("l.sb %d, r%d, r%d, %d\n", I5, ra, rb, I11); 1048 mop = MO_UB; 1049 goto do_store; 1050 1051 case 0x37: /* l.sh */ 1052 LOG_DIS("l.sh %d, r%d, r%d, %d\n", I5, ra, rb, I11); 1053 mop = MO_TEUW; 1054 goto do_store; 1055 1056 do_store: 1057 { 1058 TCGv t0 = tcg_temp_new(); 1059 tcg_gen_addi_tl(t0, cpu_R[ra], sign_extend(tmp, 16)); 1060 tcg_gen_qemu_st_tl(cpu_R[rb], t0, dc->mem_idx, mop); 1061 tcg_temp_free(t0); 1062 } 1063 break; 1064 1065 default: 1066 gen_illegal_exception(dc); 1067 break; 1068 } 1069 } 1070 1071 static void dec_mac(DisasContext *dc, uint32_t insn) 1072 { 1073 uint32_t op0; 1074 uint32_t ra, rb; 1075 op0 = extract32(insn, 0, 4); 1076 ra = extract32(insn, 16, 5); 1077 rb = extract32(insn, 11, 5); 1078 1079 switch (op0) { 1080 case 0x0001: /* l.mac */ 1081 LOG_DIS("l.mac r%d, r%d\n", ra, rb); 1082 { 1083 TCGv_i32 t0 = tcg_temp_new_i32(); 1084 TCGv_i64 t1 = tcg_temp_new_i64(); 1085 TCGv_i64 t2 = tcg_temp_new_i64(); 1086 tcg_gen_mul_tl(t0, cpu_R[ra], cpu_R[rb]); 1087 tcg_gen_ext_i32_i64(t1, t0); 1088 tcg_gen_concat_i32_i64(t2, maclo, machi); 1089 tcg_gen_add_i64(t2, t2, t1); 1090 tcg_gen_extrl_i64_i32(maclo, t2); 1091 tcg_gen_shri_i64(t2, t2, 32); 1092 tcg_gen_extrl_i64_i32(machi, t2); 1093 tcg_temp_free_i32(t0); 1094 tcg_temp_free_i64(t1); 1095 tcg_temp_free_i64(t2); 1096 } 1097 break; 1098 1099 case 0x0002: /* l.msb */ 1100 LOG_DIS("l.msb r%d, r%d\n", ra, rb); 1101 { 1102 TCGv_i32 t0 = tcg_temp_new_i32(); 1103 TCGv_i64 t1 = tcg_temp_new_i64(); 1104 TCGv_i64 t2 = tcg_temp_new_i64(); 1105 tcg_gen_mul_tl(t0, cpu_R[ra], cpu_R[rb]); 1106 tcg_gen_ext_i32_i64(t1, t0); 1107 tcg_gen_concat_i32_i64(t2, maclo, machi); 1108 tcg_gen_sub_i64(t2, t2, t1); 1109 tcg_gen_extrl_i64_i32(maclo, t2); 1110 tcg_gen_shri_i64(t2, t2, 32); 1111 tcg_gen_extrl_i64_i32(machi, t2); 1112 tcg_temp_free_i32(t0); 1113 tcg_temp_free_i64(t1); 1114 tcg_temp_free_i64(t2); 1115 } 1116 break; 1117 1118 default: 1119 gen_illegal_exception(dc); 1120 break; 1121 } 1122 } 1123 1124 static void dec_logic(DisasContext *dc, uint32_t insn) 1125 { 1126 uint32_t op0; 1127 uint32_t rd, ra, L6; 1128 op0 = extract32(insn, 6, 2); 1129 rd = extract32(insn, 21, 5); 1130 ra = extract32(insn, 16, 5); 1131 L6 = extract32(insn, 0, 6); 1132 1133 switch (op0) { 1134 case 0x00: /* l.slli */ 1135 LOG_DIS("l.slli r%d, r%d, %d\n", rd, ra, L6); 1136 tcg_gen_shli_tl(cpu_R[rd], cpu_R[ra], (L6 & 0x1f)); 1137 break; 1138 1139 case 0x01: /* l.srli */ 1140 LOG_DIS("l.srli r%d, r%d, %d\n", rd, ra, L6); 1141 tcg_gen_shri_tl(cpu_R[rd], cpu_R[ra], (L6 & 0x1f)); 1142 break; 1143 1144 case 0x02: /* l.srai */ 1145 LOG_DIS("l.srai r%d, r%d, %d\n", rd, ra, L6); 1146 tcg_gen_sari_tl(cpu_R[rd], cpu_R[ra], (L6 & 0x1f)); break; 1147 1148 case 0x03: /* l.rori */ 1149 LOG_DIS("l.rori r%d, r%d, %d\n", rd, ra, L6); 1150 tcg_gen_rotri_tl(cpu_R[rd], cpu_R[ra], (L6 & 0x1f)); 1151 break; 1152 1153 default: 1154 gen_illegal_exception(dc); 1155 break; 1156 } 1157 } 1158 1159 static void dec_M(DisasContext *dc, uint32_t insn) 1160 { 1161 uint32_t op0; 1162 uint32_t rd; 1163 uint32_t K16; 1164 op0 = extract32(insn, 16, 1); 1165 rd = extract32(insn, 21, 5); 1166 K16 = extract32(insn, 0, 16); 1167 1168 switch (op0) { 1169 case 0x0: /* l.movhi */ 1170 LOG_DIS("l.movhi r%d, %d\n", rd, K16); 1171 tcg_gen_movi_tl(cpu_R[rd], (K16 << 16)); 1172 break; 1173 1174 case 0x1: /* l.macrc */ 1175 LOG_DIS("l.macrc r%d\n", rd); 1176 tcg_gen_mov_tl(cpu_R[rd], maclo); 1177 tcg_gen_movi_tl(maclo, 0x0); 1178 tcg_gen_movi_tl(machi, 0x0); 1179 break; 1180 1181 default: 1182 gen_illegal_exception(dc); 1183 break; 1184 } 1185 } 1186 1187 static void dec_comp(DisasContext *dc, uint32_t insn) 1188 { 1189 uint32_t op0; 1190 uint32_t ra, rb; 1191 1192 op0 = extract32(insn, 21, 5); 1193 ra = extract32(insn, 16, 5); 1194 rb = extract32(insn, 11, 5); 1195 1196 tcg_gen_movi_i32(env_btaken, 0x0); 1197 /* unsigned integers */ 1198 tcg_gen_ext32u_tl(cpu_R[ra], cpu_R[ra]); 1199 tcg_gen_ext32u_tl(cpu_R[rb], cpu_R[rb]); 1200 1201 switch (op0) { 1202 case 0x0: /* l.sfeq */ 1203 LOG_DIS("l.sfeq r%d, r%d\n", ra, rb); 1204 tcg_gen_setcond_tl(TCG_COND_EQ, env_btaken, cpu_R[ra], cpu_R[rb]); 1205 break; 1206 1207 case 0x1: /* l.sfne */ 1208 LOG_DIS("l.sfne r%d, r%d\n", ra, rb); 1209 tcg_gen_setcond_tl(TCG_COND_NE, env_btaken, cpu_R[ra], cpu_R[rb]); 1210 break; 1211 1212 case 0x2: /* l.sfgtu */ 1213 LOG_DIS("l.sfgtu r%d, r%d\n", ra, rb); 1214 tcg_gen_setcond_tl(TCG_COND_GTU, env_btaken, cpu_R[ra], cpu_R[rb]); 1215 break; 1216 1217 case 0x3: /* l.sfgeu */ 1218 LOG_DIS("l.sfgeu r%d, r%d\n", ra, rb); 1219 tcg_gen_setcond_tl(TCG_COND_GEU, env_btaken, cpu_R[ra], cpu_R[rb]); 1220 break; 1221 1222 case 0x4: /* l.sfltu */ 1223 LOG_DIS("l.sfltu r%d, r%d\n", ra, rb); 1224 tcg_gen_setcond_tl(TCG_COND_LTU, env_btaken, cpu_R[ra], cpu_R[rb]); 1225 break; 1226 1227 case 0x5: /* l.sfleu */ 1228 LOG_DIS("l.sfleu r%d, r%d\n", ra, rb); 1229 tcg_gen_setcond_tl(TCG_COND_LEU, env_btaken, cpu_R[ra], cpu_R[rb]); 1230 break; 1231 1232 case 0xa: /* l.sfgts */ 1233 LOG_DIS("l.sfgts r%d, r%d\n", ra, rb); 1234 tcg_gen_setcond_tl(TCG_COND_GT, env_btaken, cpu_R[ra], cpu_R[rb]); 1235 break; 1236 1237 case 0xb: /* l.sfges */ 1238 LOG_DIS("l.sfges r%d, r%d\n", ra, rb); 1239 tcg_gen_setcond_tl(TCG_COND_GE, env_btaken, cpu_R[ra], cpu_R[rb]); 1240 break; 1241 1242 case 0xc: /* l.sflts */ 1243 LOG_DIS("l.sflts r%d, r%d\n", ra, rb); 1244 tcg_gen_setcond_tl(TCG_COND_LT, env_btaken, cpu_R[ra], cpu_R[rb]); 1245 break; 1246 1247 case 0xd: /* l.sfles */ 1248 LOG_DIS("l.sfles r%d, r%d\n", ra, rb); 1249 tcg_gen_setcond_tl(TCG_COND_LE, env_btaken, cpu_R[ra], cpu_R[rb]); 1250 break; 1251 1252 default: 1253 gen_illegal_exception(dc); 1254 break; 1255 } 1256 wb_SR_F(); 1257 } 1258 1259 static void dec_compi(DisasContext *dc, uint32_t insn) 1260 { 1261 uint32_t op0; 1262 uint32_t ra, I16; 1263 1264 op0 = extract32(insn, 21, 5); 1265 ra = extract32(insn, 16, 5); 1266 I16 = extract32(insn, 0, 16); 1267 1268 tcg_gen_movi_i32(env_btaken, 0x0); 1269 I16 = sign_extend(I16, 16); 1270 1271 switch (op0) { 1272 case 0x0: /* l.sfeqi */ 1273 LOG_DIS("l.sfeqi r%d, %d\n", ra, I16); 1274 tcg_gen_setcondi_tl(TCG_COND_EQ, env_btaken, cpu_R[ra], I16); 1275 break; 1276 1277 case 0x1: /* l.sfnei */ 1278 LOG_DIS("l.sfnei r%d, %d\n", ra, I16); 1279 tcg_gen_setcondi_tl(TCG_COND_NE, env_btaken, cpu_R[ra], I16); 1280 break; 1281 1282 case 0x2: /* l.sfgtui */ 1283 LOG_DIS("l.sfgtui r%d, %d\n", ra, I16); 1284 tcg_gen_setcondi_tl(TCG_COND_GTU, env_btaken, cpu_R[ra], I16); 1285 break; 1286 1287 case 0x3: /* l.sfgeui */ 1288 LOG_DIS("l.sfgeui r%d, %d\n", ra, I16); 1289 tcg_gen_setcondi_tl(TCG_COND_GEU, env_btaken, cpu_R[ra], I16); 1290 break; 1291 1292 case 0x4: /* l.sfltui */ 1293 LOG_DIS("l.sfltui r%d, %d\n", ra, I16); 1294 tcg_gen_setcondi_tl(TCG_COND_LTU, env_btaken, cpu_R[ra], I16); 1295 break; 1296 1297 case 0x5: /* l.sfleui */ 1298 LOG_DIS("l.sfleui r%d, %d\n", ra, I16); 1299 tcg_gen_setcondi_tl(TCG_COND_LEU, env_btaken, cpu_R[ra], I16); 1300 break; 1301 1302 case 0xa: /* l.sfgtsi */ 1303 LOG_DIS("l.sfgtsi r%d, %d\n", ra, I16); 1304 tcg_gen_setcondi_tl(TCG_COND_GT, env_btaken, cpu_R[ra], I16); 1305 break; 1306 1307 case 0xb: /* l.sfgesi */ 1308 LOG_DIS("l.sfgesi r%d, %d\n", ra, I16); 1309 tcg_gen_setcondi_tl(TCG_COND_GE, env_btaken, cpu_R[ra], I16); 1310 break; 1311 1312 case 0xc: /* l.sfltsi */ 1313 LOG_DIS("l.sfltsi r%d, %d\n", ra, I16); 1314 tcg_gen_setcondi_tl(TCG_COND_LT, env_btaken, cpu_R[ra], I16); 1315 break; 1316 1317 case 0xd: /* l.sflesi */ 1318 LOG_DIS("l.sflesi r%d, %d\n", ra, I16); 1319 tcg_gen_setcondi_tl(TCG_COND_LE, env_btaken, cpu_R[ra], I16); 1320 break; 1321 1322 default: 1323 gen_illegal_exception(dc); 1324 break; 1325 } 1326 wb_SR_F(); 1327 } 1328 1329 static void dec_sys(DisasContext *dc, uint32_t insn) 1330 { 1331 uint32_t op0; 1332 #ifdef OPENRISC_DISAS 1333 uint32_t K16; 1334 #endif 1335 op0 = extract32(insn, 16, 10); 1336 #ifdef OPENRISC_DISAS 1337 K16 = extract32(insn, 0, 16); 1338 #endif 1339 1340 switch (op0) { 1341 case 0x000: /* l.sys */ 1342 LOG_DIS("l.sys %d\n", K16); 1343 tcg_gen_movi_tl(cpu_pc, dc->pc); 1344 gen_exception(dc, EXCP_SYSCALL); 1345 dc->is_jmp = DISAS_UPDATE; 1346 break; 1347 1348 case 0x100: /* l.trap */ 1349 LOG_DIS("l.trap %d\n", K16); 1350 #if defined(CONFIG_USER_ONLY) 1351 return; 1352 #else 1353 if (dc->mem_idx == MMU_USER_IDX) { 1354 gen_illegal_exception(dc); 1355 return; 1356 } 1357 tcg_gen_movi_tl(cpu_pc, dc->pc); 1358 gen_exception(dc, EXCP_TRAP); 1359 #endif 1360 break; 1361 1362 case 0x300: /* l.csync */ 1363 LOG_DIS("l.csync\n"); 1364 #if defined(CONFIG_USER_ONLY) 1365 return; 1366 #else 1367 if (dc->mem_idx == MMU_USER_IDX) { 1368 gen_illegal_exception(dc); 1369 return; 1370 } 1371 #endif 1372 break; 1373 1374 case 0x200: /* l.msync */ 1375 LOG_DIS("l.msync\n"); 1376 #if defined(CONFIG_USER_ONLY) 1377 return; 1378 #else 1379 if (dc->mem_idx == MMU_USER_IDX) { 1380 gen_illegal_exception(dc); 1381 return; 1382 } 1383 #endif 1384 break; 1385 1386 case 0x270: /* l.psync */ 1387 LOG_DIS("l.psync\n"); 1388 #if defined(CONFIG_USER_ONLY) 1389 return; 1390 #else 1391 if (dc->mem_idx == MMU_USER_IDX) { 1392 gen_illegal_exception(dc); 1393 return; 1394 } 1395 #endif 1396 break; 1397 1398 default: 1399 gen_illegal_exception(dc); 1400 break; 1401 } 1402 } 1403 1404 static void dec_float(DisasContext *dc, uint32_t insn) 1405 { 1406 uint32_t op0; 1407 uint32_t ra, rb, rd; 1408 op0 = extract32(insn, 0, 8); 1409 ra = extract32(insn, 16, 5); 1410 rb = extract32(insn, 11, 5); 1411 rd = extract32(insn, 21, 5); 1412 1413 switch (op0) { 1414 case 0x00: /* lf.add.s */ 1415 LOG_DIS("lf.add.s r%d, r%d, r%d\n", rd, ra, rb); 1416 gen_helper_float_add_s(cpu_R[rd], cpu_env, cpu_R[ra], cpu_R[rb]); 1417 break; 1418 1419 case 0x01: /* lf.sub.s */ 1420 LOG_DIS("lf.sub.s r%d, r%d, r%d\n", rd, ra, rb); 1421 gen_helper_float_sub_s(cpu_R[rd], cpu_env, cpu_R[ra], cpu_R[rb]); 1422 break; 1423 1424 1425 case 0x02: /* lf.mul.s */ 1426 LOG_DIS("lf.mul.s r%d, r%d, r%d\n", rd, ra, rb); 1427 if (ra != 0 && rb != 0) { 1428 gen_helper_float_mul_s(cpu_R[rd], cpu_env, cpu_R[ra], cpu_R[rb]); 1429 } else { 1430 tcg_gen_ori_tl(fpcsr, fpcsr, FPCSR_ZF); 1431 tcg_gen_movi_i32(cpu_R[rd], 0x0); 1432 } 1433 break; 1434 1435 case 0x03: /* lf.div.s */ 1436 LOG_DIS("lf.div.s r%d, r%d, r%d\n", rd, ra, rb); 1437 gen_helper_float_div_s(cpu_R[rd], cpu_env, cpu_R[ra], cpu_R[rb]); 1438 break; 1439 1440 case 0x04: /* lf.itof.s */ 1441 LOG_DIS("lf.itof r%d, r%d\n", rd, ra); 1442 gen_helper_itofs(cpu_R[rd], cpu_env, cpu_R[ra]); 1443 break; 1444 1445 case 0x05: /* lf.ftoi.s */ 1446 LOG_DIS("lf.ftoi r%d, r%d\n", rd, ra); 1447 gen_helper_ftois(cpu_R[rd], cpu_env, cpu_R[ra]); 1448 break; 1449 1450 case 0x06: /* lf.rem.s */ 1451 LOG_DIS("lf.rem.s r%d, r%d, r%d\n", rd, ra, rb); 1452 gen_helper_float_rem_s(cpu_R[rd], cpu_env, cpu_R[ra], cpu_R[rb]); 1453 break; 1454 1455 case 0x07: /* lf.madd.s */ 1456 LOG_DIS("lf.madd.s r%d, r%d, r%d\n", rd, ra, rb); 1457 gen_helper_float_muladd_s(cpu_R[rd], cpu_env, cpu_R[ra], cpu_R[rb]); 1458 break; 1459 1460 case 0x08: /* lf.sfeq.s */ 1461 LOG_DIS("lf.sfeq.s r%d, r%d\n", ra, rb); 1462 gen_helper_float_eq_s(env_btaken, cpu_env, cpu_R[ra], cpu_R[rb]); 1463 break; 1464 1465 case 0x09: /* lf.sfne.s */ 1466 LOG_DIS("lf.sfne.s r%d, r%d\n", ra, rb); 1467 gen_helper_float_ne_s(env_btaken, cpu_env, cpu_R[ra], cpu_R[rb]); 1468 break; 1469 1470 case 0x0a: /* lf.sfgt.s */ 1471 LOG_DIS("lf.sfgt.s r%d, r%d\n", ra, rb); 1472 gen_helper_float_gt_s(env_btaken, cpu_env, cpu_R[ra], cpu_R[rb]); 1473 break; 1474 1475 case 0x0b: /* lf.sfge.s */ 1476 LOG_DIS("lf.sfge.s r%d, r%d\n", ra, rb); 1477 gen_helper_float_ge_s(env_btaken, cpu_env, cpu_R[ra], cpu_R[rb]); 1478 break; 1479 1480 case 0x0c: /* lf.sflt.s */ 1481 LOG_DIS("lf.sflt.s r%d, r%d\n", ra, rb); 1482 gen_helper_float_lt_s(env_btaken, cpu_env, cpu_R[ra], cpu_R[rb]); 1483 break; 1484 1485 case 0x0d: /* lf.sfle.s */ 1486 LOG_DIS("lf.sfle.s r%d, r%d\n", ra, rb); 1487 gen_helper_float_le_s(env_btaken, cpu_env, cpu_R[ra], cpu_R[rb]); 1488 break; 1489 1490 /* not used yet, open it when we need or64. */ 1491 /*#ifdef TARGET_OPENRISC64 1492 case 0x10: lf.add.d 1493 LOG_DIS("lf.add.d r%d, r%d, r%d\n", rd, ra, rb); 1494 check_of64s(dc); 1495 gen_helper_float_add_d(cpu_R[rd], cpu_env, cpu_R[ra], cpu_R[rb]); 1496 break; 1497 1498 case 0x11: lf.sub.d 1499 LOG_DIS("lf.sub.d r%d, r%d, r%d\n", rd, ra, rb); 1500 check_of64s(dc); 1501 gen_helper_float_sub_d(cpu_R[rd], cpu_env, cpu_R[ra], cpu_R[rb]); 1502 break; 1503 1504 case 0x12: lf.mul.d 1505 LOG_DIS("lf.mul.d r%d, r%d, r%d\n", rd, ra, rb); 1506 check_of64s(dc); 1507 if (ra != 0 && rb != 0) { 1508 gen_helper_float_mul_d(cpu_R[rd], cpu_env, cpu_R[ra], cpu_R[rb]); 1509 } else { 1510 tcg_gen_ori_tl(fpcsr, fpcsr, FPCSR_ZF); 1511 tcg_gen_movi_i64(cpu_R[rd], 0x0); 1512 } 1513 break; 1514 1515 case 0x13: lf.div.d 1516 LOG_DIS("lf.div.d r%d, r%d, r%d\n", rd, ra, rb); 1517 check_of64s(dc); 1518 gen_helper_float_div_d(cpu_R[rd], cpu_env, cpu_R[ra], cpu_R[rb]); 1519 break; 1520 1521 case 0x14: lf.itof.d 1522 LOG_DIS("lf.itof r%d, r%d\n", rd, ra); 1523 check_of64s(dc); 1524 gen_helper_itofd(cpu_R[rd], cpu_env, cpu_R[ra]); 1525 break; 1526 1527 case 0x15: lf.ftoi.d 1528 LOG_DIS("lf.ftoi r%d, r%d\n", rd, ra); 1529 check_of64s(dc); 1530 gen_helper_ftoid(cpu_R[rd], cpu_env, cpu_R[ra]); 1531 break; 1532 1533 case 0x16: lf.rem.d 1534 LOG_DIS("lf.rem.d r%d, r%d, r%d\n", rd, ra, rb); 1535 check_of64s(dc); 1536 gen_helper_float_rem_d(cpu_R[rd], cpu_env, cpu_R[ra], cpu_R[rb]); 1537 break; 1538 1539 case 0x17: lf.madd.d 1540 LOG_DIS("lf.madd.d r%d, r%d, r%d\n", rd, ra, rb); 1541 check_of64s(dc); 1542 gen_helper_float_muladd_d(cpu_R[rd], cpu_env, cpu_R[ra], cpu_R[rb]); 1543 break; 1544 1545 case 0x18: lf.sfeq.d 1546 LOG_DIS("lf.sfeq.d r%d, r%d\n", ra, rb); 1547 check_of64s(dc); 1548 gen_helper_float_eq_d(env_btaken, cpu_env, cpu_R[ra], cpu_R[rb]); 1549 break; 1550 1551 case 0x1a: lf.sfgt.d 1552 LOG_DIS("lf.sfgt.d r%d, r%d\n", ra, rb); 1553 check_of64s(dc); 1554 gen_helper_float_gt_d(env_btaken, cpu_env, cpu_R[ra], cpu_R[rb]); 1555 break; 1556 1557 case 0x1b: lf.sfge.d 1558 LOG_DIS("lf.sfge.d r%d, r%d\n", ra, rb); 1559 check_of64s(dc); 1560 gen_helper_float_ge_d(env_btaken, cpu_env, cpu_R[ra], cpu_R[rb]); 1561 break; 1562 1563 case 0x19: lf.sfne.d 1564 LOG_DIS("lf.sfne.d r%d, r%d\n", ra, rb); 1565 check_of64s(dc); 1566 gen_helper_float_ne_d(env_btaken, cpu_env, cpu_R[ra], cpu_R[rb]); 1567 break; 1568 1569 case 0x1c: lf.sflt.d 1570 LOG_DIS("lf.sflt.d r%d, r%d\n", ra, rb); 1571 check_of64s(dc); 1572 gen_helper_float_lt_d(env_btaken, cpu_env, cpu_R[ra], cpu_R[rb]); 1573 break; 1574 1575 case 0x1d: lf.sfle.d 1576 LOG_DIS("lf.sfle.d r%d, r%d\n", ra, rb); 1577 check_of64s(dc); 1578 gen_helper_float_le_d(env_btaken, cpu_env, cpu_R[ra], cpu_R[rb]); 1579 break; 1580 #endif*/ 1581 1582 default: 1583 gen_illegal_exception(dc); 1584 break; 1585 } 1586 wb_SR_F(); 1587 } 1588 1589 static void disas_openrisc_insn(DisasContext *dc, OpenRISCCPU *cpu) 1590 { 1591 uint32_t op0; 1592 uint32_t insn; 1593 insn = cpu_ldl_code(&cpu->env, dc->pc); 1594 op0 = extract32(insn, 26, 6); 1595 1596 switch (op0) { 1597 case 0x06: 1598 dec_M(dc, insn); 1599 break; 1600 1601 case 0x08: 1602 dec_sys(dc, insn); 1603 break; 1604 1605 case 0x2e: 1606 dec_logic(dc, insn); 1607 break; 1608 1609 case 0x2f: 1610 dec_compi(dc, insn); 1611 break; 1612 1613 case 0x31: 1614 dec_mac(dc, insn); 1615 break; 1616 1617 case 0x32: 1618 dec_float(dc, insn); 1619 break; 1620 1621 case 0x38: 1622 dec_calc(dc, insn); 1623 break; 1624 1625 case 0x39: 1626 dec_comp(dc, insn); 1627 break; 1628 1629 default: 1630 dec_misc(dc, insn); 1631 break; 1632 } 1633 } 1634 1635 void gen_intermediate_code(CPUOpenRISCState *env, struct TranslationBlock *tb) 1636 { 1637 OpenRISCCPU *cpu = openrisc_env_get_cpu(env); 1638 CPUState *cs = CPU(cpu); 1639 struct DisasContext ctx, *dc = &ctx; 1640 uint32_t pc_start; 1641 uint32_t next_page_start; 1642 int num_insns; 1643 int max_insns; 1644 1645 pc_start = tb->pc; 1646 dc->tb = tb; 1647 1648 dc->is_jmp = DISAS_NEXT; 1649 dc->ppc = pc_start; 1650 dc->pc = pc_start; 1651 dc->flags = cpu->env.cpucfgr; 1652 dc->mem_idx = cpu_mmu_index(&cpu->env, false); 1653 dc->synced_flags = dc->tb_flags = tb->flags; 1654 dc->delayed_branch = !!(dc->tb_flags & D_FLAG); 1655 dc->singlestep_enabled = cs->singlestep_enabled; 1656 1657 next_page_start = (pc_start & TARGET_PAGE_MASK) + TARGET_PAGE_SIZE; 1658 num_insns = 0; 1659 max_insns = tb->cflags & CF_COUNT_MASK; 1660 1661 if (max_insns == 0) { 1662 max_insns = CF_COUNT_MASK; 1663 } 1664 if (max_insns > TCG_MAX_INSNS) { 1665 max_insns = TCG_MAX_INSNS; 1666 } 1667 1668 gen_tb_start(tb); 1669 1670 do { 1671 tcg_gen_insn_start(dc->pc); 1672 num_insns++; 1673 1674 if (unlikely(cpu_breakpoint_test(cs, dc->pc, BP_ANY))) { 1675 tcg_gen_movi_tl(cpu_pc, dc->pc); 1676 gen_exception(dc, EXCP_DEBUG); 1677 dc->is_jmp = DISAS_UPDATE; 1678 /* The address covered by the breakpoint must be included in 1679 [tb->pc, tb->pc + tb->size) in order to for it to be 1680 properly cleared -- thus we increment the PC here so that 1681 the logic setting tb->size below does the right thing. */ 1682 dc->pc += 4; 1683 break; 1684 } 1685 1686 if (num_insns == max_insns && (tb->cflags & CF_LAST_IO)) { 1687 gen_io_start(); 1688 } 1689 dc->ppc = dc->pc - 4; 1690 dc->npc = dc->pc + 4; 1691 tcg_gen_movi_tl(cpu_ppc, dc->ppc); 1692 tcg_gen_movi_tl(cpu_npc, dc->npc); 1693 disas_openrisc_insn(dc, cpu); 1694 dc->pc = dc->npc; 1695 /* delay slot */ 1696 if (dc->delayed_branch) { 1697 dc->delayed_branch--; 1698 if (!dc->delayed_branch) { 1699 dc->tb_flags &= ~D_FLAG; 1700 gen_sync_flags(dc); 1701 tcg_gen_mov_tl(cpu_pc, jmp_pc); 1702 tcg_gen_mov_tl(cpu_npc, jmp_pc); 1703 tcg_gen_movi_tl(jmp_pc, 0); 1704 tcg_gen_exit_tb(0); 1705 dc->is_jmp = DISAS_JUMP; 1706 break; 1707 } 1708 } 1709 } while (!dc->is_jmp 1710 && !tcg_op_buf_full() 1711 && !cs->singlestep_enabled 1712 && !singlestep 1713 && (dc->pc < next_page_start) 1714 && num_insns < max_insns); 1715 1716 if (tb->cflags & CF_LAST_IO) { 1717 gen_io_end(); 1718 } 1719 if (dc->is_jmp == DISAS_NEXT) { 1720 dc->is_jmp = DISAS_UPDATE; 1721 tcg_gen_movi_tl(cpu_pc, dc->pc); 1722 } 1723 if (unlikely(cs->singlestep_enabled)) { 1724 if (dc->is_jmp == DISAS_NEXT) { 1725 tcg_gen_movi_tl(cpu_pc, dc->pc); 1726 } 1727 gen_exception(dc, EXCP_DEBUG); 1728 } else { 1729 switch (dc->is_jmp) { 1730 case DISAS_NEXT: 1731 gen_goto_tb(dc, 0, dc->pc); 1732 break; 1733 default: 1734 case DISAS_JUMP: 1735 break; 1736 case DISAS_UPDATE: 1737 /* indicate that the hash table must be used 1738 to find the next TB */ 1739 tcg_gen_exit_tb(0); 1740 break; 1741 case DISAS_TB_JUMP: 1742 /* nothing more to generate */ 1743 break; 1744 } 1745 } 1746 1747 gen_tb_end(tb, num_insns); 1748 1749 tb->size = dc->pc - pc_start; 1750 tb->icount = num_insns; 1751 1752 #ifdef DEBUG_DISAS 1753 if (qemu_loglevel_mask(CPU_LOG_TB_IN_ASM) 1754 && qemu_log_in_addr_range(pc_start)) { 1755 qemu_log_lock(); 1756 qemu_log("----------------\n"); 1757 qemu_log("IN: %s\n", lookup_symbol(pc_start)); 1758 log_target_disas(cs, pc_start, dc->pc - pc_start, 0); 1759 qemu_log("\nisize=%d osize=%d\n", 1760 dc->pc - pc_start, tcg_op_buf_count()); 1761 qemu_log_unlock(); 1762 } 1763 #endif 1764 } 1765 1766 void openrisc_cpu_dump_state(CPUState *cs, FILE *f, 1767 fprintf_function cpu_fprintf, 1768 int flags) 1769 { 1770 OpenRISCCPU *cpu = OPENRISC_CPU(cs); 1771 CPUOpenRISCState *env = &cpu->env; 1772 int i; 1773 1774 cpu_fprintf(f, "PC=%08x\n", env->pc); 1775 for (i = 0; i < 32; ++i) { 1776 cpu_fprintf(f, "R%02d=%08x%c", i, env->gpr[i], 1777 (i % 4) == 3 ? '\n' : ' '); 1778 } 1779 } 1780 1781 void restore_state_to_opc(CPUOpenRISCState *env, TranslationBlock *tb, 1782 target_ulong *data) 1783 { 1784 env->pc = data[0]; 1785 } 1786