base.hh

来自「M5,一个功能强大的多处理器系统模拟器.很多针对处理器架构,性能的研究都使用它作」· HH 代码 · 共 420 行

HH
420
字号
/* * Copyright (c) 2002, 2003, 2004, 2005 * The Regents of The University of Michigan * All Rights Reserved * * This code is part of the M5 simulator. * * Permission is granted to use, copy, create derivative works and * redistribute this software and such derivative works for any * purpose, so long as the copyright notice above, this grant of * permission, and the disclaimer below appear in all copies made; and * so long as the name of The University of Michigan is not used in * any advertising or publicity pertaining to the use or distribution * of this software without specific, written prior authorization. * * THIS SOFTWARE IS PROVIDED AS IS, WITHOUT REPRESENTATION FROM THE * UNIVERSITY OF MICHIGAN AS TO ITS FITNESS FOR ANY PURPOSE, AND * WITHOUT WARRANTY BY THE UNIVERSITY OF MICHIGAN OF ANY KIND, EITHER * EXPRESS OR IMPLIED, INCLUDING WITHOUT LIMITATION THE IMPLIED * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR * PURPOSE. THE REGENTS OF THE UNIVERSITY OF MICHIGAN SHALL NOT BE * LIABLE FOR ANY DAMAGES, INCLUDING DIRECT, SPECIAL, INDIRECT, * INCIDENTAL, OR CONSEQUENTIAL DAMAGES, WITH RESPECT TO ANY CLAIM * ARISING OUT OF OR IN CONNECTION WITH THE USE OF THE SOFTWARE, EVEN * IF IT HAS BEEN OR IS HEREAFTER ADVISED OF THE POSSIBILITY OF SUCH * DAMAGES. * * Authors: Steven K. Reinhardt *          David A. Greene *          Nathan L. Binkert */#ifndef __CPU_SIMPLE_BASE_HH__#define __CPU_SIMPLE_BASE_HH__#include "arch/predecoder.hh"#include "base/statistics.hh"#include "config/full_system.hh"#include "cpu/base.hh"#include "cpu/simple_thread.hh"#include "cpu/pc_event.hh"#include "cpu/static_inst.hh"#include "mem/packet.hh"#include "mem/port.hh"#include "mem/request.hh"#include "sim/eventq.hh"#include "sim/system.hh"// forward declarations#if FULL_SYSTEMclass Processor;namespace TheISA{    class ITB;    class DTB;}class MemObject;#elseclass Process;#endif // FULL_SYSTEMclass RemoteGDB;class GDBListener;namespace TheISA{    class Predecoder;}class ThreadContext;class Checkpoint;namespace Trace {    class InstRecord;}class BaseSimpleCPU : public BaseCPU{  protected:    typedef TheISA::MiscReg MiscReg;    typedef TheISA::FloatReg FloatReg;    typedef TheISA::FloatRegBits FloatRegBits;  protected:    Trace::InstRecord *traceData;    inline void checkPcEventQueue() {        Addr oldpc;        do {            oldpc = thread->readPC();            system->pcEventQueue.service(tc);        } while (oldpc != thread->readPC());    }  public:    void post_interrupt(int int_num, int index);    void zero_fill_64(Addr addr) {      static int warned = 0;      if (!warned) {        warn ("WH64 is not implemented");        warned = 1;      }    };  public:    struct Params : public BaseCPU::Params    {        TheISA::ITB *itb;        TheISA::DTB *dtb;#if !FULL_SYSTEM        Process *process;#endif    };    BaseSimpleCPU(Params *params);    virtual ~BaseSimpleCPU();  public:    /** SimpleThread object, provides all the architectural state. */    SimpleThread *thread;    /** ThreadContext object, provides an interface for external     * objects to modify this thread's state.     */    ThreadContext *tc;  protected:    int cpuId;  public:#if FULL_SYSTEM    Addr dbg_vtophys(Addr addr);    bool interval_stats;#endif    // current instruction    TheISA::MachInst inst;    // The predecoder    TheISA::Predecoder predecoder;    StaticInstPtr curStaticInst;    StaticInstPtr curMacroStaticInst;    //This is the offset from the current pc that fetch should be performed at    Addr fetchOffset;    //This flag says to stay at the current pc. This is useful for    //instructions which go beyond MachInst boundaries.    bool stayAtPC;    void checkForInterrupts();    Fault setupFetchRequest(Request *req);    void preExecute();    void postExecute();    void advancePC(Fault fault);    virtual void deallocateContext(int thread_num);    virtual void haltContext(int thread_num);    // statistics    virtual void regStats();    virtual void resetStats();    // number of simulated instructions    Counter numInst;    Counter startNumInst;    Stats::Scalar<> numInsts;    void countInst()    {        numInst++;        numInsts++;        thread->funcExeInst++;    }    virtual Counter totalInstructions() const    {        return numInst - startNumInst;    }    // Mask to align PCs to MachInst sized boundaries    static const Addr PCMask = ~((Addr)sizeof(TheISA::MachInst) - 1);    // number of simulated memory references    Stats::Scalar<> numMemRefs;    // number of simulated loads    Counter numLoad;    Counter startNumLoad;    // number of idle cycles    Stats::Average<> notIdleFraction;    Stats::Formula idleFraction;    // number of cycles stalled for I-cache responses    Stats::Scalar<> icacheStallCycles;    Counter lastIcacheStall;    // number of cycles stalled for I-cache retries    Stats::Scalar<> icacheRetryCycles;    Counter lastIcacheRetry;    // number of cycles stalled for D-cache responses    Stats::Scalar<> dcacheStallCycles;    Counter lastDcacheStall;    // number of cycles stalled for D-cache retries    Stats::Scalar<> dcacheRetryCycles;    Counter lastDcacheRetry;    virtual void serialize(std::ostream &os);    virtual void unserialize(Checkpoint *cp, const std::string &section);    // These functions are only used in CPU models that split    // effective address computation from the actual memory access.    void setEA(Addr EA) { panic("BaseSimpleCPU::setEA() not implemented\n"); }    Addr getEA() 	{ panic("BaseSimpleCPU::getEA() not implemented\n");        M5_DUMMY_RETURN}    void prefetch(Addr addr, unsigned flags)    {        // need to do this...    }    void writeHint(Addr addr, int size, unsigned flags)    {        // need to do this...    }    Fault copySrcTranslate(Addr src);    Fault copy(Addr dest);    // The register accessor methods provide the index of the    // instruction's operand (e.g., 0 or 1), not the architectural    // register index, to simplify the implementation of register    // renaming.  We find the architectural register index by indexing    // into the instruction's own operand index table.  Note that a    // raw pointer to the StaticInst is provided instead of a    // ref-counted StaticInstPtr to redice overhead.  This is fine as    // long as these methods don't copy the pointer into any long-term    // storage (which is pretty hard to imagine they would have reason    // to do).    uint64_t readIntRegOperand(const StaticInst *si, int idx)    {        return thread->readIntReg(si->srcRegIdx(idx));    }    FloatReg readFloatRegOperand(const StaticInst *si, int idx, int width)    {        int reg_idx = si->srcRegIdx(idx) - TheISA::FP_Base_DepTag;        return thread->readFloatReg(reg_idx, width);    }    FloatReg readFloatRegOperand(const StaticInst *si, int idx)    {        int reg_idx = si->srcRegIdx(idx) - TheISA::FP_Base_DepTag;        return thread->readFloatReg(reg_idx);    }    FloatRegBits readFloatRegOperandBits(const StaticInst *si, int idx,                                         int width)    {        int reg_idx = si->srcRegIdx(idx) - TheISA::FP_Base_DepTag;        return thread->readFloatRegBits(reg_idx, width);    }    FloatRegBits readFloatRegOperandBits(const StaticInst *si, int idx)    {        int reg_idx = si->srcRegIdx(idx) - TheISA::FP_Base_DepTag;        return thread->readFloatRegBits(reg_idx);    }    void setIntRegOperand(const StaticInst *si, int idx, uint64_t val)    {        thread->setIntReg(si->destRegIdx(idx), val);    }    void setFloatRegOperand(const StaticInst *si, int idx, FloatReg val,                            int width)    {        int reg_idx = si->destRegIdx(idx) - TheISA::FP_Base_DepTag;        thread->setFloatReg(reg_idx, val, width);    }    void setFloatRegOperand(const StaticInst *si, int idx, FloatReg val)    {        int reg_idx = si->destRegIdx(idx) - TheISA::FP_Base_DepTag;        thread->setFloatReg(reg_idx, val);    }    void setFloatRegOperandBits(const StaticInst *si, int idx,                                FloatRegBits val, int width)    {        int reg_idx = si->destRegIdx(idx) - TheISA::FP_Base_DepTag;        thread->setFloatRegBits(reg_idx, val, width);    }    void setFloatRegOperandBits(const StaticInst *si, int idx,                                FloatRegBits val)    {        int reg_idx = si->destRegIdx(idx) - TheISA::FP_Base_DepTag;        thread->setFloatRegBits(reg_idx, val);    }    uint64_t readPC() { return thread->readPC(); }    uint64_t readMicroPC() { return thread->readMicroPC(); }    uint64_t readNextPC() { return thread->readNextPC(); }    uint64_t readNextMicroPC() { return thread->readNextMicroPC(); }    uint64_t readNextNPC() { return thread->readNextNPC(); }    void setPC(uint64_t val) { thread->setPC(val); }    void setMicroPC(uint64_t val) { thread->setMicroPC(val); }    void setNextPC(uint64_t val) { thread->setNextPC(val); }    void setNextMicroPC(uint64_t val) { thread->setNextMicroPC(val); }    void setNextNPC(uint64_t val) { thread->setNextNPC(val); }    MiscReg readMiscRegNoEffect(int misc_reg)    {        return thread->readMiscRegNoEffect(misc_reg);    }    MiscReg readMiscReg(int misc_reg)    {        return thread->readMiscReg(misc_reg);    }    void setMiscRegNoEffect(int misc_reg, const MiscReg &val)    {        return thread->setMiscRegNoEffect(misc_reg, val);    }    void setMiscReg(int misc_reg, const MiscReg &val)    {        return thread->setMiscReg(misc_reg, val);    }    MiscReg readMiscRegOperandNoEffect(const StaticInst *si, int idx)    {        int reg_idx = si->srcRegIdx(idx) - TheISA::Ctrl_Base_DepTag;        return thread->readMiscRegNoEffect(reg_idx);    }    MiscReg readMiscRegOperand(const StaticInst *si, int idx)    {        int reg_idx = si->srcRegIdx(idx) - TheISA::Ctrl_Base_DepTag;        return thread->readMiscReg(reg_idx);    }    void setMiscRegOperandNoEffect(const StaticInst *si, int idx, const MiscReg &val)    {        int reg_idx = si->destRegIdx(idx) - TheISA::Ctrl_Base_DepTag;        return thread->setMiscRegNoEffect(reg_idx, val);    }    void setMiscRegOperand(            const StaticInst *si, int idx, const MiscReg &val)    {        int reg_idx = si->destRegIdx(idx) - TheISA::Ctrl_Base_DepTag;        return thread->setMiscReg(reg_idx, val);    }    void demapPage(Addr vaddr, uint64_t asn)    {        thread->demapPage(vaddr, asn);    }    void demapInstPage(Addr vaddr, uint64_t asn)    {        thread->demapInstPage(vaddr, asn);    }    void demapDataPage(Addr vaddr, uint64_t asn)    {        thread->demapDataPage(vaddr, asn);    }    unsigned readStCondFailures() {        return thread->readStCondFailures();    }    void setStCondFailures(unsigned sc_failures) {        thread->setStCondFailures(sc_failures);    }     MiscReg readRegOtherThread(int regIdx, int tid = -1)     {        panic("Simple CPU models do not support multithreaded "              "register access.\n");     }     void setRegOtherThread(int regIdx, const MiscReg &val, int tid = -1)     {        panic("Simple CPU models do not support multithreaded "              "register access.\n");     }    //Fault CacheOp(uint8_t Op, Addr EA);#if FULL_SYSTEM    Fault hwrei() { return thread->hwrei(); }    void ev5_trap(Fault fault) { fault->invoke(tc); }    bool simPalCheck(int palFunc) { return thread->simPalCheck(palFunc); }#else    void syscall(int64_t callnum) { thread->syscall(callnum); }#endif    bool misspeculating() { return thread->misspeculating(); }    ThreadContext *tcBase() { return tc; }};#endif // __CPU_SIMPLE_BASE_HH__

⌨️ 快捷键说明

复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?