10 #include "softfloat.h"
12 processor_t::processor_t(sim_t
* _sim
, char* _mem
, size_t _memsz
)
13 : sim(_sim
), mmu(_mem
,_memsz
)
15 memset(R
,0,sizeof(R
));
16 memset(FR
,0,sizeof(FR
));
26 interrupts_pending
= 0;
27 set_sr(SR_S
| (support_64bit
? SR_SX
: 0));
30 memset(counters
,0,sizeof(counters
));
32 // a few assumptions about endianness, including freg_t union
33 static_assert(BYTE_ORDER
== LITTLE_ENDIAN
);
34 static_assert(sizeof(freg_t
) == 8);
35 static_assert(sizeof(reg_t
) == 8);
37 static_assert(sizeof(insn_t
) == 4);
38 static_assert(sizeof(uint128_t
) == 16 && sizeof(int128_t
) == 16);
41 void processor_t::init(uint32_t _id
)
46 void processor_t::set_sr(uint32_t val
)
50 sr
&= ~(SR_SX
| SR_UX
);
52 gprlen
= ((sr
& SR_S
) ? (sr
& SR_SX
) : (sr
& SR_UX
)) ? 64 : 32;
55 void processor_t::set_fsr(uint32_t val
)
57 fsr
= val
& ~FSR_ZERO
;
58 softfloat_roundingMode
= (fsr
& FSR_RD
) >> FSR_RD_SHIFT
;
61 void processor_t::step(size_t n
, bool noisy
)
68 uint32_t interrupts
= interrupts_pending
& ((sr
& SR_IM
) >> SR_IM_SHIFT
);
69 if((sr
& SR_ET
) && interrupts
)
71 for(int i
= 0; interrupts
; i
++, interrupts
>>= 1)
76 insn_t insn
= mmu
.load_insn(pc
);
78 reg_t npc
= pc
+sizeof(insn
);
88 if(count
++ == compare
)
89 interrupts_pending
|= 1 << TIMER_IRQ
;
100 void processor_t::take_trap(trap_t t
, bool noisy
)
102 demand(t
< NUM_TRAPS
, "internal error: bad trap number %d", int(t
));
103 demand(sr
& SR_ET
, "error mode on core %d!\ntrap %s, pc 0x%016llx",
104 id
, trap_name(t
), (unsigned long long)pc
);
106 printf("core %3d: trap %s, pc 0x%016llx\n",
107 id
, trap_name(t
), (unsigned long long)pc
);
109 set_sr((((sr
& ~SR_ET
) | SR_S
) & ~SR_PS
) | ((sr
& SR_S
) ? SR_PS
: 0));
112 badvaddr
= mmu
.get_badvaddr();
115 void processor_t::disasm(insn_t insn
, reg_t pc
)
117 printf("core %3d: 0x%016llx (0x%08x) ",id
,(unsigned long long)pc
,insn
.bits
);
119 #ifdef RISCV_HAVE_LIBOPCODES
120 disassemble_info info
;
121 INIT_DISASSEMBLE_INFO(info
, stdout
, fprintf
);
122 info
.flavour
= bfd_target_unknown_flavour
;
123 info
.arch
= bfd_arch_mips
;
124 info
.mach
= 101; // XXX bfd_mach_mips_riscv requires modified bfd.h
125 info
.endian
= BFD_ENDIAN_LITTLE
;
126 info
.buffer
= (bfd_byte
*)&insn
;
127 info
.buffer_length
= sizeof(insn
);
128 info
.buffer_vma
= pc
;
130 demand(print_insn_little_mips(pc
, &info
) == sizeof(insn
), "disasm bug!");