kernel-mode #1
@ -173,6 +173,36 @@ class PrivCPU(CPU):
|
||||
if self._time_timecmp < (time.perf_counter_ns() // self.TIME_RESOLUTION_NS) - self._time_start:
|
||||
self.pending_traps.append(TimerInterrupt())
|
||||
self._time_interrupt_enabled = False
|
||||
print(FMT_CPU + "[CPU] raising timer interrupt: tartegt: {}, current: {}".format(self._time_timecmp, (time.perf_counter_ns() // self.TIME_RESOLUTION_NS) - self._time_start) + FMT_NONE)
|
||||
|
||||
def _check_interrupt(self):
|
||||
pass
|
||||
if not (len(self.pending_traps) > 0 and self.csr.get_mstatus('mie')):
|
||||
return
|
||||
# select best interrupt
|
||||
# TODO: actually select based on the official ranking
|
||||
trap = self.pending_traps.pop() # use the most recent trap
|
||||
print(FMT_CPU + "[CPU] taking trap {}!".format(trap) + FMT_NONE)
|
||||
|
||||
if trap.priv != PrivModes.MACHINE:
|
||||
print(FMT_CPU + "[CPU] Trap not targeting machine mode encountered! - undefined behaviour!" + FMT_NONE)
|
||||
|
||||
if self.mode != PrivModes.USER:
|
||||
print(FMT_CPU + "[CPU] Trap triggered outside of user mode?!" + FMT_NONE)
|
||||
|
||||
self.csr.set_mstatus('mpie', self.csr.get_mstatus('mie'))
|
||||
self.csr.set_mstatus('mpp', self.mode.value)
|
||||
self.csr.set_mstatus('mie', 0)
|
||||
self.csr.set('mcause', trap.mcause)
|
||||
self.csr.set('mepc', self.pc)
|
||||
self.csr.set('mtval', trap.mtval)
|
||||
self.mode = trap.priv
|
||||
mtvec = self.csr.get('mtvec')
|
||||
if mtvec & 0b11 == 0:
|
||||
self.pc = mtvec
|
||||
if mtvec & 0b11 == 1:
|
||||
self.pc = (mtvec & 0b11111111111111111111111111111100) + (trap.code * 4)
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user