/* Definitions to support the system control coprocessor. Copyright 2001, 2003 Brian R. Gaeke. This file is part of VMIPS. VMIPS is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version. VMIPS is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with VMIPS; if not, write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */ #ifndef _CPZERO_H_ #define _CPZERO_H_ #include "tlbentry.h" #include class CPU; class DeviceExc; class IntCtrl; #define TLB_ENTRIES 64 class CPZero { TLBEntry tlb[TLB_ENTRIES]; uint32 reg[32]; CPU *cpu; IntCtrl *intc; // Return TRUE if interrupts are enabled, FALSE otherwise. bool interrupts_enabled(void) const; // Return TRUE if the cpu is running in kernel mode, FALSE otherwise. bool kernel_mode(void) const; // Return the currently pending interrupts. uint32 getIP(void); void mfc0_emulate(uint32 instr, uint32 pc); void mtc0_emulate(uint32 instr, uint32 pc); void bc0x_emulate(uint32 instr, uint32 pc); void tlbr_emulate(uint32 instr, uint32 pc); void tlbwi_emulate(uint32 instr, uint32 pc); void tlbwr_emulate(uint32 instr, uint32 pc); void tlbp_emulate(uint32 instr, uint32 pc); void rfe_emulate(uint32 instr, uint32 pc); void load_addr_trans_excp_info(uint32 va, uint32 vpn, TLBEntry *match); int find_matching_tlb_entry(uint32 asid, uint32 asid); uint32 tlb_translate(uint32 seg, uint32 vaddr, int mode, bool *cacheable, DeviceExc *client); public: bool tlb_miss_user; // Write TLB entry number INDEX with the contents of the EntryHi // and EntryLo registers. void tlb_write(unsigned index); // Return the contents of the readable bits of register REG. uint32 read_reg(uint32 reg); // Change the contents of the writable bits of register REG to DATA. void write_reg(uint32 reg, uint32 data); /* Convention says that CP0's condition is TRUE if the memory write-back buffer is empty. Because memory writes are fast as far as the emulation is concerned, the write buffer is always empty for CP0. */ bool cpCond() { return true; } CPZero(CPU *m, IntCtrl *i) : cpu (m), intc (i) { } void reset(void); /* Request to translate virtual address VADDR, while the processor is in mode MODE to a physical address. CLIENT is the entity that will recieve any interrupts generated by the attempted translation. On return CACHEABLE will be set to TRUE if the returned address is cacheable, it will be set to FALSE otherwise. Returns the physical address corresponding to VADDR if such a translation is possible, otherwise an interrupt is raised with CLIENT and the return value is undefined. */ uint32 address_trans(uint32 vaddr, int mode, bool *cacheable, DeviceExc *client); void enter_exception(uint32 pc, uint32 excCode, uint32 ce, bool dly); bool use_boot_excp_address(void); bool caches_isolated(void); /* Return TRUE if the instruction and data caches are swapped, FALSE otherwise. */ bool caches_swapped(void); bool cop_usable (int coprocno); void cpzero_emulate(uint32 instr, uint32 pc); // Write the state of the CP0 registers to stream F. void dump_regs(FILE *f); // Write the state of the TLB to stream F. void dump_tlb(FILE *f); // Write the state of the CP0 registers and the TLB to stream F. void dump_regs_and_tlb(FILE *f); /* Change the CP0 random register after an instruction step. */ void adjust_random(void); /* Return TRUE if there is an interrupt which should be handled at the next available opportunity, FALSE otherwise. */ bool interrupt_pending(void); void read_debug_info(uint32 *status, uint32 *bad, uint32 *cause); void write_debug_info(uint32 status, uint32 bad, uint32 cause); /* TLB translate VADDR without exceptions. Returns true if a valid TLB mapping is found, false otherwise. If VADDR has no valid mapping, PADDR is written with 0xffffffff, otherwise it is written with the translation. */ bool debug_tlb_translate(uint32 vaddr, uint32 *paddr); }; #endif /* _CPZERO_H_ */