diff options
Diffstat (limited to 'src/arch/alpha/ev5.cc')
-rw-r--r-- | src/arch/alpha/ev5.cc | 367 |
1 files changed, 185 insertions, 182 deletions
diff --git a/src/arch/alpha/ev5.cc b/src/arch/alpha/ev5.cc index 45d2ff5a5..166d42bc6 100644 --- a/src/arch/alpha/ev5.cc +++ b/src/arch/alpha/ev5.cc @@ -44,7 +44,7 @@ #include "sim/debug.hh" #include "sim/sim_exit.hh" -using namespace AlphaISA; +namespace AlphaISA { #if FULL_SYSTEM @@ -53,14 +53,14 @@ using namespace AlphaISA; // Machine dependent functions // void -AlphaISA::initCPU(ThreadContext *tc, int cpuId) +initCPU(ThreadContext *tc, int cpuId) { initIPRs(tc, cpuId); tc->setIntReg(16, cpuId); tc->setIntReg(0, cpuId); - AlphaISA::AlphaFault *reset = new AlphaISA::ResetFault; + AlphaFault *reset = new ResetFault; tc->setPC(tc->readMiscRegNoEffect(IPR_PAL_BASE) + reset->vect()); tc->setNextPC(tc->readPC() + sizeof(MachInst)); @@ -71,7 +71,7 @@ AlphaISA::initCPU(ThreadContext *tc, int cpuId) template <class CPU> void -AlphaISA::processInterrupts(CPU *cpu) +processInterrupts(CPU *cpu) { //Check if there are any outstanding interrupts //Handle the interrupts @@ -117,7 +117,7 @@ AlphaISA::processInterrupts(CPU *cpu) template <class CPU> void -AlphaISA::zeroRegisters(CPU *cpu) +zeroRegisters(CPU *cpu) { // Insure ISA semantics // (no longer very clean due to the change in setIntReg() in the @@ -126,33 +126,16 @@ AlphaISA::zeroRegisters(CPU *cpu) cpu->thread->setFloatReg(ZeroReg, 0.0); } -Fault -SimpleThread::hwrei() -{ - if (!(readPC() & 0x3)) - return new UnimplementedOpcodeFault; - - setNextPC(readMiscRegNoEffect(AlphaISA::IPR_EXC_ADDR)); - - if (!misspeculating()) { - if (kernelStats) - kernelStats->hwrei(); - } - - // FIXME: XXX check for interrupts? XXX - return NoFault; -} - int -AlphaISA::MiscRegFile::getInstAsid() +MiscRegFile::getInstAsid() { - return AlphaISA::ITB_ASN_ASN(ipr[IPR_ITB_ASN]); + return ITB_ASN_ASN(ipr[IPR_ITB_ASN]); } int -AlphaISA::MiscRegFile::getDataAsid() +MiscRegFile::getDataAsid() { - return AlphaISA::DTB_ASN_ASN(ipr[IPR_DTB_ASN]); + return DTB_ASN_ASN(ipr[IPR_DTB_ASN]); } #endif @@ -162,90 +145,90 @@ AlphaISA::MiscRegFile::getDataAsid() // // void -AlphaISA::initIPRs(ThreadContext *tc, int cpuId) +initIPRs(ThreadContext *tc, int cpuId) { for (int i = 0; i < NumInternalProcRegs; ++i) { tc->setMiscRegNoEffect(i, 0); } - tc->setMiscRegNoEffect(IPR_PAL_BASE, AlphaISA::PalBase); + tc->setMiscRegNoEffect(IPR_PAL_BASE, PalBase); tc->setMiscRegNoEffect(IPR_MCSR, 0x6); tc->setMiscRegNoEffect(IPR_PALtemp16, cpuId); } -AlphaISA::MiscReg -AlphaISA::MiscRegFile::readIpr(int idx, ThreadContext *tc) +MiscReg +MiscRegFile::readIpr(int idx, ThreadContext *tc) { uint64_t retval = 0; // return value, default 0 switch (idx) { - case AlphaISA::IPR_PALtemp0: - case AlphaISA::IPR_PALtemp1: - case AlphaISA::IPR_PALtemp2: - case AlphaISA::IPR_PALtemp3: - case AlphaISA::IPR_PALtemp4: - case AlphaISA::IPR_PALtemp5: - case AlphaISA::IPR_PALtemp6: - case AlphaISA::IPR_PALtemp7: - case AlphaISA::IPR_PALtemp8: - case AlphaISA::IPR_PALtemp9: - case AlphaISA::IPR_PALtemp10: - case AlphaISA::IPR_PALtemp11: - case AlphaISA::IPR_PALtemp12: - case AlphaISA::IPR_PALtemp13: - case AlphaISA::IPR_PALtemp14: - case AlphaISA::IPR_PALtemp15: - case AlphaISA::IPR_PALtemp16: - case AlphaISA::IPR_PALtemp17: - case AlphaISA::IPR_PALtemp18: - case AlphaISA::IPR_PALtemp19: - case AlphaISA::IPR_PALtemp20: - case AlphaISA::IPR_PALtemp21: - case AlphaISA::IPR_PALtemp22: - case AlphaISA::IPR_PALtemp23: - case AlphaISA::IPR_PAL_BASE: - - case AlphaISA::IPR_IVPTBR: - case AlphaISA::IPR_DC_MODE: - case AlphaISA::IPR_MAF_MODE: - case AlphaISA::IPR_ISR: - case AlphaISA::IPR_EXC_ADDR: - case AlphaISA::IPR_IC_PERR_STAT: - case AlphaISA::IPR_DC_PERR_STAT: - case AlphaISA::IPR_MCSR: - case AlphaISA::IPR_ASTRR: - case AlphaISA::IPR_ASTER: - case AlphaISA::IPR_SIRR: - case AlphaISA::IPR_ICSR: - case AlphaISA::IPR_ICM: - case AlphaISA::IPR_DTB_CM: - case AlphaISA::IPR_IPLR: - case AlphaISA::IPR_INTID: - case AlphaISA::IPR_PMCTR: + case IPR_PALtemp0: + case IPR_PALtemp1: + case IPR_PALtemp2: + case IPR_PALtemp3: + case IPR_PALtemp4: + case IPR_PALtemp5: + case IPR_PALtemp6: + case IPR_PALtemp7: + case IPR_PALtemp8: + case IPR_PALtemp9: + case IPR_PALtemp10: + case IPR_PALtemp11: + case IPR_PALtemp12: + case IPR_PALtemp13: + case IPR_PALtemp14: + case IPR_PALtemp15: + case IPR_PALtemp16: + case IPR_PALtemp17: + case IPR_PALtemp18: + case IPR_PALtemp19: + case IPR_PALtemp20: + case IPR_PALtemp21: + case IPR_PALtemp22: + case IPR_PALtemp23: + case IPR_PAL_BASE: + + case IPR_IVPTBR: + case IPR_DC_MODE: + case IPR_MAF_MODE: + case IPR_ISR: + case IPR_EXC_ADDR: + case IPR_IC_PERR_STAT: + case IPR_DC_PERR_STAT: + case IPR_MCSR: + case IPR_ASTRR: + case IPR_ASTER: + case IPR_SIRR: + case IPR_ICSR: + case IPR_ICM: + case IPR_DTB_CM: + case IPR_IPLR: + case IPR_INTID: + case IPR_PMCTR: // no side-effect retval = ipr[idx]; break; - case AlphaISA::IPR_CC: + case IPR_CC: retval |= ipr[idx] & ULL(0xffffffff00000000); retval |= tc->getCpuPtr()->curCycle() & ULL(0x00000000ffffffff); break; - case AlphaISA::IPR_VA: + case IPR_VA: retval = ipr[idx]; break; - case AlphaISA::IPR_VA_FORM: - case AlphaISA::IPR_MM_STAT: - case AlphaISA::IPR_IFAULT_VA_FORM: - case AlphaISA::IPR_EXC_MASK: - case AlphaISA::IPR_EXC_SUM: + case IPR_VA_FORM: + case IPR_MM_STAT: + case IPR_IFAULT_VA_FORM: + case IPR_EXC_MASK: + case IPR_EXC_SUM: retval = ipr[idx]; break; - case AlphaISA::IPR_DTB_PTE: + case IPR_DTB_PTE: { - AlphaISA::TlbEntry &entry + TlbEntry &entry = tc->getDTBPtr()->index(!tc->misspeculating()); retval |= ((uint64_t)entry.ppn & ULL(0x7ffffff)) << 32; @@ -259,15 +242,15 @@ AlphaISA::MiscRegFile::readIpr(int idx, ThreadContext *tc) break; // write only registers - case AlphaISA::IPR_HWINT_CLR: - case AlphaISA::IPR_SL_XMIT: - case AlphaISA::IPR_DC_FLUSH: - case AlphaISA::IPR_IC_FLUSH: - case AlphaISA::IPR_ALT_MODE: - case AlphaISA::IPR_DTB_IA: - case AlphaISA::IPR_DTB_IAP: - case AlphaISA::IPR_ITB_IA: - case AlphaISA::IPR_ITB_IAP: + case IPR_HWINT_CLR: + case IPR_SL_XMIT: + case IPR_DC_FLUSH: + case IPR_IC_FLUSH: + case IPR_ALT_MODE: + case IPR_DTB_IA: + case IPR_DTB_IAP: + case IPR_ITB_IA: + case IPR_ITB_IAP: panic("Tried to read write only register %d\n", idx); break; @@ -286,7 +269,7 @@ int break_ipl = -1; #endif void -AlphaISA::MiscRegFile::setIpr(int idx, uint64_t val, ThreadContext *tc) +MiscRegFile::setIpr(int idx, uint64_t val, ThreadContext *tc) { uint64_t old; @@ -294,52 +277,52 @@ AlphaISA::MiscRegFile::setIpr(int idx, uint64_t val, ThreadContext *tc) return; switch (idx) { - case AlphaISA::IPR_PALtemp0: - case AlphaISA::IPR_PALtemp1: - case AlphaISA::IPR_PALtemp2: - case AlphaISA::IPR_PALtemp3: - case AlphaISA::IPR_PALtemp4: - case AlphaISA::IPR_PALtemp5: - case AlphaISA::IPR_PALtemp6: - case AlphaISA::IPR_PALtemp7: - case AlphaISA::IPR_PALtemp8: - case AlphaISA::IPR_PALtemp9: - case AlphaISA::IPR_PALtemp10: - case AlphaISA::IPR_PALtemp11: - case AlphaISA::IPR_PALtemp12: - case AlphaISA::IPR_PALtemp13: - case AlphaISA::IPR_PALtemp14: - case AlphaISA::IPR_PALtemp15: - case AlphaISA::IPR_PALtemp16: - case AlphaISA::IPR_PALtemp17: - case AlphaISA::IPR_PALtemp18: - case AlphaISA::IPR_PALtemp19: - case AlphaISA::IPR_PALtemp20: - case AlphaISA::IPR_PALtemp21: - case AlphaISA::IPR_PALtemp22: - case AlphaISA::IPR_PAL_BASE: - case AlphaISA::IPR_IC_PERR_STAT: - case AlphaISA::IPR_DC_PERR_STAT: - case AlphaISA::IPR_PMCTR: + case IPR_PALtemp0: + case IPR_PALtemp1: + case IPR_PALtemp2: + case IPR_PALtemp3: + case IPR_PALtemp4: + case IPR_PALtemp5: + case IPR_PALtemp6: + case IPR_PALtemp7: + case IPR_PALtemp8: + case IPR_PALtemp9: + case IPR_PALtemp10: + case IPR_PALtemp11: + case IPR_PALtemp12: + case IPR_PALtemp13: + case IPR_PALtemp14: + case IPR_PALtemp15: + case IPR_PALtemp16: + case IPR_PALtemp17: + case IPR_PALtemp18: + case IPR_PALtemp19: + case IPR_PALtemp20: + case IPR_PALtemp21: + case IPR_PALtemp22: + case IPR_PAL_BASE: + case IPR_IC_PERR_STAT: + case IPR_DC_PERR_STAT: + case IPR_PMCTR: // write entire quad w/ no side-effect ipr[idx] = val; break; - case AlphaISA::IPR_CC_CTL: + case IPR_CC_CTL: // This IPR resets the cycle counter. We assume this only // happens once... let's verify that. assert(ipr[idx] == 0); ipr[idx] = 1; break; - case AlphaISA::IPR_CC: + case IPR_CC: // This IPR only writes the upper 64 bits. It's ok to write // all 64 here since we mask out the lower 32 in rpcc (see // isa_desc). ipr[idx] = val; break; - case AlphaISA::IPR_PALtemp23: + case IPR_PALtemp23: // write entire quad w/ no side-effect old = ipr[idx]; ipr[idx] = val; @@ -349,23 +332,23 @@ AlphaISA::MiscRegFile::setIpr(int idx, uint64_t val, ThreadContext *tc) #endif break; - case AlphaISA::IPR_DTB_PTE: + case IPR_DTB_PTE: // write entire quad w/ no side-effect, tag is forthcoming ipr[idx] = val; break; - case AlphaISA::IPR_EXC_ADDR: + case IPR_EXC_ADDR: // second least significant bit in PC is always zero ipr[idx] = val & ~2; break; - case AlphaISA::IPR_ASTRR: - case AlphaISA::IPR_ASTER: + case IPR_ASTRR: + case IPR_ASTER: // only write least significant four bits - privilege mask ipr[idx] = val & 0xf; break; - case AlphaISA::IPR_IPLR: + case IPR_IPLR: #ifdef DEBUG if (break_ipl != -1 && break_ipl == (val & 0x1f)) debug_break(); @@ -379,175 +362,175 @@ AlphaISA::MiscRegFile::setIpr(int idx, uint64_t val, ThreadContext *tc) #endif break; - case AlphaISA::IPR_DTB_CM: + case IPR_DTB_CM: #if FULL_SYSTEM if (val & 0x18) { if (tc->getKernelStats()) - tc->getKernelStats()->mode(AlphaISA::Kernel::user, tc); + tc->getKernelStats()->mode(Kernel::user, tc); } else { if (tc->getKernelStats()) - tc->getKernelStats()->mode(AlphaISA::Kernel::kernel, tc); + tc->getKernelStats()->mode(Kernel::kernel, tc); } #endif - case AlphaISA::IPR_ICM: + case IPR_ICM: // only write two mode bits - processor mode ipr[idx] = val & 0x18; break; - case AlphaISA::IPR_ALT_MODE: + case IPR_ALT_MODE: // only write two mode bits - processor mode ipr[idx] = val & 0x18; break; - case AlphaISA::IPR_MCSR: + case IPR_MCSR: // more here after optimization... ipr[idx] = val; break; - case AlphaISA::IPR_SIRR: + case IPR_SIRR: // only write software interrupt mask ipr[idx] = val & 0x7fff0; break; - case AlphaISA::IPR_ICSR: + case IPR_ICSR: ipr[idx] = val & ULL(0xffffff0300); break; - case AlphaISA::IPR_IVPTBR: - case AlphaISA::IPR_MVPTBR: + case IPR_IVPTBR: + case IPR_MVPTBR: ipr[idx] = val & ULL(0xffffffffc0000000); break; - case AlphaISA::IPR_DC_TEST_CTL: + case IPR_DC_TEST_CTL: ipr[idx] = val & 0x1ffb; break; - case AlphaISA::IPR_DC_MODE: - case AlphaISA::IPR_MAF_MODE: + case IPR_DC_MODE: + case IPR_MAF_MODE: ipr[idx] = val & 0x3f; break; - case AlphaISA::IPR_ITB_ASN: + case IPR_ITB_ASN: ipr[idx] = val & 0x7f0; break; - case AlphaISA::IPR_DTB_ASN: + case IPR_DTB_ASN: ipr[idx] = val & ULL(0xfe00000000000000); break; - case AlphaISA::IPR_EXC_SUM: - case AlphaISA::IPR_EXC_MASK: + case IPR_EXC_SUM: + case IPR_EXC_MASK: // any write to this register clears it ipr[idx] = 0; break; - case AlphaISA::IPR_INTID: - case AlphaISA::IPR_SL_RCV: - case AlphaISA::IPR_MM_STAT: - case AlphaISA::IPR_ITB_PTE_TEMP: - case AlphaISA::IPR_DTB_PTE_TEMP: + case IPR_INTID: + case IPR_SL_RCV: + case IPR_MM_STAT: + case IPR_ITB_PTE_TEMP: + case IPR_DTB_PTE_TEMP: // read-only registers panic("Tried to write read only ipr %d\n", idx); - case AlphaISA::IPR_HWINT_CLR: - case AlphaISA::IPR_SL_XMIT: - case AlphaISA::IPR_DC_FLUSH: - case AlphaISA::IPR_IC_FLUSH: + case IPR_HWINT_CLR: + case IPR_SL_XMIT: + case IPR_DC_FLUSH: + case IPR_IC_FLUSH: // the following are write only ipr[idx] = val; break; - case AlphaISA::IPR_DTB_IA: + case IPR_DTB_IA: // really a control write ipr[idx] = 0; tc->getDTBPtr()->flushAll(); break; - case AlphaISA::IPR_DTB_IAP: + case IPR_DTB_IAP: // really a control write ipr[idx] = 0; tc->getDTBPtr()->flushProcesses(); break; - case AlphaISA::IPR_DTB_IS: + case IPR_DTB_IS: // really a control write ipr[idx] = val; tc->getDTBPtr()->flushAddr(val, - AlphaISA::DTB_ASN_ASN(ipr[AlphaISA::IPR_DTB_ASN])); + DTB_ASN_ASN(ipr[IPR_DTB_ASN])); break; - case AlphaISA::IPR_DTB_TAG: { - struct AlphaISA::TlbEntry entry; + case IPR_DTB_TAG: { + struct TlbEntry entry; // FIXME: granularity hints NYI... - if (AlphaISA::DTB_PTE_GH(ipr[AlphaISA::IPR_DTB_PTE]) != 0) + if (DTB_PTE_GH(ipr[IPR_DTB_PTE]) != 0) panic("PTE GH field != 0"); // write entire quad ipr[idx] = val; // construct PTE for new entry - entry.ppn = AlphaISA::DTB_PTE_PPN(ipr[AlphaISA::IPR_DTB_PTE]); - entry.xre = AlphaISA::DTB_PTE_XRE(ipr[AlphaISA::IPR_DTB_PTE]); - entry.xwe = AlphaISA::DTB_PTE_XWE(ipr[AlphaISA::IPR_DTB_PTE]); - entry.fonr = AlphaISA::DTB_PTE_FONR(ipr[AlphaISA::IPR_DTB_PTE]); - entry.fonw = AlphaISA::DTB_PTE_FONW(ipr[AlphaISA::IPR_DTB_PTE]); - entry.asma = AlphaISA::DTB_PTE_ASMA(ipr[AlphaISA::IPR_DTB_PTE]); - entry.asn = AlphaISA::DTB_ASN_ASN(ipr[AlphaISA::IPR_DTB_ASN]); + entry.ppn = DTB_PTE_PPN(ipr[IPR_DTB_PTE]); + entry.xre = DTB_PTE_XRE(ipr[IPR_DTB_PTE]); + entry.xwe = DTB_PTE_XWE(ipr[IPR_DTB_PTE]); + entry.fonr = DTB_PTE_FONR(ipr[IPR_DTB_PTE]); + entry.fonw = DTB_PTE_FONW(ipr[IPR_DTB_PTE]); + entry.asma = DTB_PTE_ASMA(ipr[IPR_DTB_PTE]); + entry.asn = DTB_ASN_ASN(ipr[IPR_DTB_ASN]); // insert new TAG/PTE value into data TLB tc->getDTBPtr()->insert(val, entry); } break; - case AlphaISA::IPR_ITB_PTE: { - struct AlphaISA::TlbEntry entry; + case IPR_ITB_PTE: { + struct TlbEntry entry; // FIXME: granularity hints NYI... - if (AlphaISA::ITB_PTE_GH(val) != 0) + if (ITB_PTE_GH(val) != 0) panic("PTE GH field != 0"); // write entire quad ipr[idx] = val; // construct PTE for new entry - entry.ppn = AlphaISA::ITB_PTE_PPN(val); - entry.xre = AlphaISA::ITB_PTE_XRE(val); + entry.ppn = ITB_PTE_PPN(val); + entry.xre = ITB_PTE_XRE(val); entry.xwe = 0; - entry.fonr = AlphaISA::ITB_PTE_FONR(val); - entry.fonw = AlphaISA::ITB_PTE_FONW(val); - entry.asma = AlphaISA::ITB_PTE_ASMA(val); - entry.asn = AlphaISA::ITB_ASN_ASN(ipr[AlphaISA::IPR_ITB_ASN]); + entry.fonr = ITB_PTE_FONR(val); + entry.fonw = ITB_PTE_FONW(val); + entry.asma = ITB_PTE_ASMA(val); + entry.asn = ITB_ASN_ASN(ipr[IPR_ITB_ASN]); // insert new TAG/PTE value into data TLB - tc->getITBPtr()->insert(ipr[AlphaISA::IPR_ITB_TAG], entry); + tc->getITBPtr()->insert(ipr[IPR_ITB_TAG], entry); } break; - case AlphaISA::IPR_ITB_IA: + case IPR_ITB_IA: // really a control write ipr[idx] = 0; tc->getITBPtr()->flushAll(); break; - case AlphaISA::IPR_ITB_IAP: + case IPR_ITB_IAP: // really a control write ipr[idx] = 0; tc->getITBPtr()->flushProcesses(); break; - case AlphaISA::IPR_ITB_IS: + case IPR_ITB_IS: // really a control write ipr[idx] = val; tc->getITBPtr()->flushAddr(val, - AlphaISA::ITB_ASN_ASN(ipr[AlphaISA::IPR_ITB_ASN])); + ITB_ASN_ASN(ipr[IPR_ITB_ASN])); break; default: @@ -560,14 +543,34 @@ AlphaISA::MiscRegFile::setIpr(int idx, uint64_t val, ThreadContext *tc) void -AlphaISA::copyIprs(ThreadContext *src, ThreadContext *dest) +copyIprs(ThreadContext *src, ThreadContext *dest) { for (int i = 0; i < NumInternalProcRegs; ++i) { dest->setMiscRegNoEffect(i, src->readMiscRegNoEffect(i)); } } +} // namespace AlphaISA + #if FULL_SYSTEM +using namespace AlphaISA; + +Fault +SimpleThread::hwrei() +{ + if (!(readPC() & 0x3)) + return new UnimplementedOpcodeFault; + + setNextPC(readMiscRegNoEffect(IPR_EXC_ADDR)); + + if (!misspeculating()) { + if (kernelStats) + kernelStats->hwrei(); + } + + // FIXME: XXX check for interrupts? XXX + return NoFault; +} /** * Check for special simulator handling of specific PAL calls. |