diff options
Diffstat (limited to 'src/arch/sparc')
-rw-r--r-- | src/arch/sparc/asi.cc | 6 | ||||
-rw-r--r-- | src/arch/sparc/asi.hh | 1 | ||||
-rw-r--r-- | src/arch/sparc/isa/decoder.isa | 4 | ||||
-rw-r--r-- | src/arch/sparc/miscregfile.hh | 17 | ||||
-rw-r--r-- | src/arch/sparc/tlb.cc | 3 | ||||
-rw-r--r-- | src/arch/sparc/ua2005.cc | 50 | ||||
-rw-r--r-- | src/arch/sparc/utility.hh | 15 |
7 files changed, 87 insertions, 9 deletions
diff --git a/src/arch/sparc/asi.cc b/src/arch/sparc/asi.cc index d8cd84af5..254635bff 100644 --- a/src/arch/sparc/asi.cc +++ b/src/arch/sparc/asi.cc @@ -247,7 +247,8 @@ namespace SparcISA bool AsiIsCmt(ASI asi) { return - (asi == ASI_CMT_PER_STRAND); + (asi == ASI_CMT_PER_STRAND) || + (asi == ASI_CMT_SHARED); } bool AsiIsQueue(ASI asi) @@ -295,7 +296,8 @@ namespace SparcISA bool AsiIsReg(ASI asi) { return AsiIsMmu(asi) || AsiIsScratchPad(asi) || - AsiIsSparcError(asi) || AsiIsInterrupt(asi); + AsiIsSparcError(asi) || AsiIsInterrupt(asi) + || AsiIsCmt(asi); } bool AsiIsSparcError(ASI asi) diff --git a/src/arch/sparc/asi.hh b/src/arch/sparc/asi.hh index 166c3867e..eba2d518f 100644 --- a/src/arch/sparc/asi.hh +++ b/src/arch/sparc/asi.hh @@ -115,6 +115,7 @@ namespace SparcISA ASI_IMMU_CTXT_NONZERO_TSB_BASE_PS1 = 0x3E, ASI_IMMU_CTXT_NONZERO_CONFIG = 0x3F, ASI_STREAM_MA = 0x40, + ASI_CMT_SHARED = 0x41, //0x41 implementation dependent ASI_SPARC_BIST_CONTROL = 0x42, ASI_INST_MASK_REG = 0x42, diff --git a/src/arch/sparc/isa/decoder.isa b/src/arch/sparc/isa/decoder.isa index 2e85e1274..70afe19b6 100644 --- a/src/arch/sparc/isa/decoder.isa +++ b/src/arch/sparc/isa/decoder.isa @@ -620,10 +620,6 @@ decode OP default Unknown::unknown() }}); 0x19: Priv::wrstick_cmpr({{StickCmpr = Rs1 ^ Rs2_or_imm13;}}); 0x1A: Priv::wrstrand_sts_reg({{ - if(Pstate<2:> && !Hpstate<2:>) - StrandStsReg = StrandStsReg<63:1> | - (Rs1 ^ Rs2_or_imm13)<0:>; - else StrandStsReg = Rs1 ^ Rs2_or_imm13; }}); //0x1A is supposed to be reserved, but it writes the strand diff --git a/src/arch/sparc/miscregfile.hh b/src/arch/sparc/miscregfile.hh index 6063c21c8..867f959e1 100644 --- a/src/arch/sparc/miscregfile.hh +++ b/src/arch/sparc/miscregfile.hh @@ -163,6 +163,23 @@ namespace SparcISA const static int ie = 0x2; }; + struct STS { + const static int st_idle = 0x00; + const static int st_wait = 0x01; + const static int st_halt = 0x02; + const static int st_run = 0x05; + const static int st_spec_run = 0x07; + const static int st_spec_rdy = 0x13; + const static int st_ready = 0x19; + const static int active = 0x01; + const static int speculative = 0x04; + const static int shft_id = 8; + const static int shft_fsm0 = 31; + const static int shft_fsm1 = 26; + const static int shft_fsm2 = 21; + const static int shft_fsm3 = 16; + }; + const int NumMiscArchRegs = MISCREG_NUMMISCREGS; const int NumMiscRegs = MISCREG_NUMMISCREGS; diff --git a/src/arch/sparc/tlb.cc b/src/arch/sparc/tlb.cc index c39969769..09266fd6e 100644 --- a/src/arch/sparc/tlb.cc +++ b/src/arch/sparc/tlb.cc @@ -693,6 +693,9 @@ DTB::translate(RequestPtr &req, ThreadContext *tc, bool write) if (AsiIsPartialStore(asi)) panic("Partial Store ASIs not supported\n"); + if (AsiIsCmt(asi)) + panic("Cmt ASI registers not implmented\n"); + if (AsiIsInterrupt(asi)) goto handleIntRegAccess; if (AsiIsMmu(asi)) diff --git a/src/arch/sparc/ua2005.cc b/src/arch/sparc/ua2005.cc index 6c8a987fe..439f38457 100644 --- a/src/arch/sparc/ua2005.cc +++ b/src/arch/sparc/ua2005.cc @@ -26,11 +26,13 @@ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ +#include "arch/sparc/kernel_stats.hh" #include "arch/sparc/miscregfile.hh" #include "base/bitfield.hh" #include "base/trace.hh" #include "cpu/base.hh" #include "cpu/thread_context.hh" +#include "sim/system.hh" using namespace SparcISA; @@ -185,10 +187,21 @@ MiscRegFile::setFSReg(int miscReg, const MiscReg &val, ThreadContext *tc) #endif break; case MISCREG_HTSTATE: - case MISCREG_STRAND_STS_REG: setRegNoEffect(miscReg, val); break; + case MISCREG_STRAND_STS_REG: + if (bits(val,2,2)) + panic("No support for setting spec_en bit\n"); + setRegNoEffect(miscReg, bits(val,0,0)); + if (!bits(val,0,0)) { + // Time to go to sleep + tc->suspend(); + if (tc->getKernelStats()) + tc->getKernelStats()->quiesce(); + } + break; + default: panic("Invalid write to FS misc register %s\n", getMiscRegName(miscReg)); } @@ -197,6 +210,8 @@ MiscRegFile::setFSReg(int miscReg, const MiscReg &val, ThreadContext *tc) MiscReg MiscRegFile::readFSReg(int miscReg, ThreadContext * tc) { + uint64_t temp; + switch (miscReg) { /* Privileged registers. */ case MISCREG_QUEUE_CPU_MONDO_HEAD: @@ -214,7 +229,6 @@ MiscRegFile::readFSReg(int miscReg, ThreadContext * tc) case MISCREG_HPSTATE: case MISCREG_HINTP: case MISCREG_HTSTATE: - case MISCREG_STRAND_STS_REG: case MISCREG_HSTICK_CMPR: return readRegNoEffect(miscReg) ; @@ -223,6 +237,38 @@ MiscRegFile::readFSReg(int miscReg, ThreadContext * tc) case MISCREG_HVER: return NWindows | MaxTL << 8 | MaxGL << 16; + case MISCREG_STRAND_STS_REG: + System *sys; + int x; + sys = tc->getSystemPtr(); + + temp = readRegNoEffect(miscReg) & (STS::active | STS::speculative); + // Check that the CPU array is fully populated (by calling getNumCPus()) + assert(sys->getNumCPUs() > tc->readCpuId()); + + temp |= tc->readCpuId() << STS::shft_id; + + for (x = tc->readCpuId() & ~3; x < sys->threadContexts.size(); x++) { + switch (sys->threadContexts[x]->status()) { + case ThreadContext::Active: + temp |= STS::st_run << (STS::shft_fsm0 - + ((x & 0x3) * (STS::shft_fsm0-STS::shft_fsm1))); + break; + case ThreadContext::Suspended: + // should this be idle? + temp |= STS::st_idle << (STS::shft_fsm0 - + ((x & 0x3) * (STS::shft_fsm0-STS::shft_fsm1))); + break; + case ThreadContext::Halted: + temp |= STS::st_halt << (STS::shft_fsm0 - + ((x & 0x3) * (STS::shft_fsm0-STS::shft_fsm1))); + break; + default: + panic("What state are we in?!\n"); + } // switch + } // for + + return temp; default: panic("Invalid read to FS misc register\n"); } diff --git a/src/arch/sparc/utility.hh b/src/arch/sparc/utility.hh index 64b91695e..dc9201401 100644 --- a/src/arch/sparc/utility.hh +++ b/src/arch/sparc/utility.hh @@ -112,7 +112,20 @@ namespace SparcISA inline void initCPU(ThreadContext *tc, int cpuId) { static Fault por = new PowerOnReset(); - por->invoke(tc); + if (cpuId == 0) + por->invoke(tc); + + } + + inline void startupCPU(ThreadContext *tc, int cpuId) + { +#if FULL_SYSTEM + // Other CPUs will get activated by IPIs + if (cpuId == 0) + tc->activate(0); +#else + tc->activate(0); +#endif } } // namespace SparcISA |