exec_context.hh revision 13610
111147Smitch.hayenga@arm.com/*
213610Sgiacomo.gabrielli@arm.com * Copyright (c) 2014-2017 ARM Limited
311147Smitch.hayenga@arm.com * All rights reserved
411147Smitch.hayenga@arm.com *
511147Smitch.hayenga@arm.com * The license below extends only to copyright in the software and shall
611147Smitch.hayenga@arm.com * not be construed as granting a license to any other intellectual
711147Smitch.hayenga@arm.com * property including but not limited to intellectual property relating
811147Smitch.hayenga@arm.com * to a hardware implementation of the functionality of the software
911147Smitch.hayenga@arm.com * licensed hereunder.  You may use the software subject to the license
1011147Smitch.hayenga@arm.com * terms below provided that you ensure that this notice is replicated
1111147Smitch.hayenga@arm.com * unmodified and in its entirety in all distributions of the software,
1211147Smitch.hayenga@arm.com * modified or unmodified, in source code or in binary form.
1311147Smitch.hayenga@arm.com *
1411147Smitch.hayenga@arm.com * Copyright (c) 2002-2005 The Regents of The University of Michigan
1511147Smitch.hayenga@arm.com * All rights reserved.
1611147Smitch.hayenga@arm.com *
1711147Smitch.hayenga@arm.com * Redistribution and use in source and binary forms, with or without
1811147Smitch.hayenga@arm.com * modification, are permitted provided that the following conditions are
1911147Smitch.hayenga@arm.com * met: redistributions of source code must retain the above copyright
2011147Smitch.hayenga@arm.com * notice, this list of conditions and the following disclaimer;
2111147Smitch.hayenga@arm.com * redistributions in binary form must reproduce the above copyright
2211147Smitch.hayenga@arm.com * notice, this list of conditions and the following disclaimer in the
2311147Smitch.hayenga@arm.com * documentation and/or other materials provided with the distribution;
2411147Smitch.hayenga@arm.com * neither the name of the copyright holders nor the names of its
2511147Smitch.hayenga@arm.com * contributors may be used to endorse or promote products derived from
2611147Smitch.hayenga@arm.com * this software without specific prior written permission.
2711147Smitch.hayenga@arm.com *
2811147Smitch.hayenga@arm.com * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
2911147Smitch.hayenga@arm.com * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
3011147Smitch.hayenga@arm.com * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
3111147Smitch.hayenga@arm.com * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
3211147Smitch.hayenga@arm.com * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
3311147Smitch.hayenga@arm.com * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
3411147Smitch.hayenga@arm.com * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
3511147Smitch.hayenga@arm.com * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
3611147Smitch.hayenga@arm.com * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
3711147Smitch.hayenga@arm.com * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
3811147Smitch.hayenga@arm.com * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
3911147Smitch.hayenga@arm.com *
4011147Smitch.hayenga@arm.com * Authors: Kevin Lim
4111147Smitch.hayenga@arm.com *          Andreas Sandberg
4211147Smitch.hayenga@arm.com *          Mitch Hayenga
4311147Smitch.hayenga@arm.com */
4411147Smitch.hayenga@arm.com
4511147Smitch.hayenga@arm.com#ifndef __CPU_SIMPLE_EXEC_CONTEXT_HH__
4611147Smitch.hayenga@arm.com#define __CPU_SIMPLE_EXEC_CONTEXT_HH__
4711147Smitch.hayenga@arm.com
4811147Smitch.hayenga@arm.com#include "arch/registers.hh"
4911147Smitch.hayenga@arm.com#include "base/types.hh"
5011147Smitch.hayenga@arm.com#include "config/the_isa.hh"
5111147Smitch.hayenga@arm.com#include "cpu/base.hh"
5211147Smitch.hayenga@arm.com#include "cpu/exec_context.hh"
5312104Snathanael.premillieu@arm.com#include "cpu/reg_class.hh"
5411147Smitch.hayenga@arm.com#include "cpu/simple/base.hh"
5511147Smitch.hayenga@arm.com#include "cpu/static_inst_fwd.hh"
5611147Smitch.hayenga@arm.com#include "cpu/translation.hh"
5711608Snikos.nikoleris@arm.com#include "mem/request.hh"
5811147Smitch.hayenga@arm.com
5911147Smitch.hayenga@arm.comclass BaseSimpleCPU;
6011147Smitch.hayenga@arm.com
6111147Smitch.hayenga@arm.comclass SimpleExecContext : public ExecContext {
6211147Smitch.hayenga@arm.com  protected:
6311147Smitch.hayenga@arm.com    typedef TheISA::CCReg CCReg;
6412109SRekai.GonzalezAlberquilla@arm.com    using VecRegContainer = TheISA::VecRegContainer;
6512109SRekai.GonzalezAlberquilla@arm.com    using VecElem = TheISA::VecElem;
6611147Smitch.hayenga@arm.com
6711147Smitch.hayenga@arm.com  public:
6811147Smitch.hayenga@arm.com    BaseSimpleCPU *cpu;
6911147Smitch.hayenga@arm.com    SimpleThread* thread;
7011147Smitch.hayenga@arm.com
7111147Smitch.hayenga@arm.com    // This is the offset from the current pc that fetch should be performed
7211147Smitch.hayenga@arm.com    Addr fetchOffset;
7311147Smitch.hayenga@arm.com    // This flag says to stay at the current pc. This is useful for
7411147Smitch.hayenga@arm.com    // instructions which go beyond MachInst boundaries.
7511147Smitch.hayenga@arm.com    bool stayAtPC;
7611147Smitch.hayenga@arm.com
7711147Smitch.hayenga@arm.com    // Branch prediction
7811147Smitch.hayenga@arm.com    TheISA::PCState predPC;
7911147Smitch.hayenga@arm.com
8011147Smitch.hayenga@arm.com    /** PER-THREAD STATS */
8111147Smitch.hayenga@arm.com
8211147Smitch.hayenga@arm.com    // Number of simulated instructions
8311147Smitch.hayenga@arm.com    Counter numInst;
8411147Smitch.hayenga@arm.com    Stats::Scalar numInsts;
8511147Smitch.hayenga@arm.com    Counter numOp;
8611147Smitch.hayenga@arm.com    Stats::Scalar numOps;
8711147Smitch.hayenga@arm.com
8811147Smitch.hayenga@arm.com    // Number of integer alu accesses
8911147Smitch.hayenga@arm.com    Stats::Scalar numIntAluAccesses;
9011147Smitch.hayenga@arm.com
9111147Smitch.hayenga@arm.com    // Number of float alu accesses
9211147Smitch.hayenga@arm.com    Stats::Scalar numFpAluAccesses;
9311147Smitch.hayenga@arm.com
9412110SRekai.GonzalezAlberquilla@arm.com    // Number of vector alu accesses
9512110SRekai.GonzalezAlberquilla@arm.com    Stats::Scalar numVecAluAccesses;
9612110SRekai.GonzalezAlberquilla@arm.com
9711147Smitch.hayenga@arm.com    // Number of function calls/returns
9811147Smitch.hayenga@arm.com    Stats::Scalar numCallsReturns;
9911147Smitch.hayenga@arm.com
10011147Smitch.hayenga@arm.com    // Conditional control instructions;
10111147Smitch.hayenga@arm.com    Stats::Scalar numCondCtrlInsts;
10211147Smitch.hayenga@arm.com
10311147Smitch.hayenga@arm.com    // Number of int instructions
10411147Smitch.hayenga@arm.com    Stats::Scalar numIntInsts;
10511147Smitch.hayenga@arm.com
10611147Smitch.hayenga@arm.com    // Number of float instructions
10711147Smitch.hayenga@arm.com    Stats::Scalar numFpInsts;
10811147Smitch.hayenga@arm.com
10912110SRekai.GonzalezAlberquilla@arm.com    // Number of vector instructions
11012110SRekai.GonzalezAlberquilla@arm.com    Stats::Scalar numVecInsts;
11112110SRekai.GonzalezAlberquilla@arm.com
11211147Smitch.hayenga@arm.com    // Number of integer register file accesses
11311147Smitch.hayenga@arm.com    Stats::Scalar numIntRegReads;
11411147Smitch.hayenga@arm.com    Stats::Scalar numIntRegWrites;
11511147Smitch.hayenga@arm.com
11611147Smitch.hayenga@arm.com    // Number of float register file accesses
11711147Smitch.hayenga@arm.com    Stats::Scalar numFpRegReads;
11811147Smitch.hayenga@arm.com    Stats::Scalar numFpRegWrites;
11911147Smitch.hayenga@arm.com
12012109SRekai.GonzalezAlberquilla@arm.com    // Number of vector register file accesses
12112109SRekai.GonzalezAlberquilla@arm.com    mutable Stats::Scalar numVecRegReads;
12212109SRekai.GonzalezAlberquilla@arm.com    Stats::Scalar numVecRegWrites;
12312109SRekai.GonzalezAlberquilla@arm.com
12413610Sgiacomo.gabrielli@arm.com    // Number of predicate register file accesses
12513610Sgiacomo.gabrielli@arm.com    mutable Stats::Scalar numVecPredRegReads;
12613610Sgiacomo.gabrielli@arm.com    Stats::Scalar numVecPredRegWrites;
12713610Sgiacomo.gabrielli@arm.com
12811147Smitch.hayenga@arm.com    // Number of condition code register file accesses
12911147Smitch.hayenga@arm.com    Stats::Scalar numCCRegReads;
13011147Smitch.hayenga@arm.com    Stats::Scalar numCCRegWrites;
13111147Smitch.hayenga@arm.com
13211147Smitch.hayenga@arm.com    // Number of simulated memory references
13311147Smitch.hayenga@arm.com    Stats::Scalar numMemRefs;
13411147Smitch.hayenga@arm.com    Stats::Scalar numLoadInsts;
13511147Smitch.hayenga@arm.com    Stats::Scalar numStoreInsts;
13611147Smitch.hayenga@arm.com
13711147Smitch.hayenga@arm.com    // Number of idle cycles
13811147Smitch.hayenga@arm.com    Stats::Formula numIdleCycles;
13911147Smitch.hayenga@arm.com
14011147Smitch.hayenga@arm.com    // Number of busy cycles
14111147Smitch.hayenga@arm.com    Stats::Formula numBusyCycles;
14211147Smitch.hayenga@arm.com
14311147Smitch.hayenga@arm.com    // Number of simulated loads
14411147Smitch.hayenga@arm.com    Counter numLoad;
14511147Smitch.hayenga@arm.com
14611147Smitch.hayenga@arm.com    // Number of idle cycles
14711147Smitch.hayenga@arm.com    Stats::Average notIdleFraction;
14811147Smitch.hayenga@arm.com    Stats::Formula idleFraction;
14911147Smitch.hayenga@arm.com
15011147Smitch.hayenga@arm.com    // Number of cycles stalled for I-cache responses
15111147Smitch.hayenga@arm.com    Stats::Scalar icacheStallCycles;
15211147Smitch.hayenga@arm.com    Counter lastIcacheStall;
15311147Smitch.hayenga@arm.com
15411147Smitch.hayenga@arm.com    // Number of cycles stalled for D-cache responses
15511147Smitch.hayenga@arm.com    Stats::Scalar dcacheStallCycles;
15611147Smitch.hayenga@arm.com    Counter lastDcacheStall;
15711147Smitch.hayenga@arm.com
15811147Smitch.hayenga@arm.com    /// @{
15911147Smitch.hayenga@arm.com    /// Total number of branches fetched
16011147Smitch.hayenga@arm.com    Stats::Scalar numBranches;
16111147Smitch.hayenga@arm.com    /// Number of branches predicted as taken
16211147Smitch.hayenga@arm.com    Stats::Scalar numPredictedBranches;
16311147Smitch.hayenga@arm.com    /// Number of misprediced branches
16411147Smitch.hayenga@arm.com    Stats::Scalar numBranchMispred;
16511147Smitch.hayenga@arm.com    /// @}
16611147Smitch.hayenga@arm.com
16711147Smitch.hayenga@arm.com   // Instruction mix histogram by OpClass
16811147Smitch.hayenga@arm.com   Stats::Vector statExecutedInstType;
16911147Smitch.hayenga@arm.com
17011147Smitch.hayenga@arm.com  public:
17111147Smitch.hayenga@arm.com    /** Constructor */
17211147Smitch.hayenga@arm.com    SimpleExecContext(BaseSimpleCPU* _cpu, SimpleThread* _thread)
17311147Smitch.hayenga@arm.com        : cpu(_cpu), thread(_thread), fetchOffset(0), stayAtPC(false),
17411147Smitch.hayenga@arm.com        numInst(0), numOp(0), numLoad(0), lastIcacheStall(0), lastDcacheStall(0)
17511147Smitch.hayenga@arm.com    { }
17611147Smitch.hayenga@arm.com
17711147Smitch.hayenga@arm.com    /** Reads an integer register. */
17813557Sgabeblack@google.com    RegVal
17913557Sgabeblack@google.com    readIntRegOperand(const StaticInst *si, int idx) override
18011147Smitch.hayenga@arm.com    {
18111147Smitch.hayenga@arm.com        numIntRegReads++;
18212106SRekai.GonzalezAlberquilla@arm.com        const RegId& reg = si->srcRegIdx(idx);
18312106SRekai.GonzalezAlberquilla@arm.com        assert(reg.isIntReg());
18412106SRekai.GonzalezAlberquilla@arm.com        return thread->readIntReg(reg.index());
18511147Smitch.hayenga@arm.com    }
18611147Smitch.hayenga@arm.com
18711147Smitch.hayenga@arm.com    /** Sets an integer register to a value. */
18813557Sgabeblack@google.com    void
18913557Sgabeblack@google.com    setIntRegOperand(const StaticInst *si, int idx, RegVal val) override
19011147Smitch.hayenga@arm.com    {
19111147Smitch.hayenga@arm.com        numIntRegWrites++;
19212106SRekai.GonzalezAlberquilla@arm.com        const RegId& reg = si->destRegIdx(idx);
19312106SRekai.GonzalezAlberquilla@arm.com        assert(reg.isIntReg());
19412106SRekai.GonzalezAlberquilla@arm.com        thread->setIntReg(reg.index(), val);
19511147Smitch.hayenga@arm.com    }
19611147Smitch.hayenga@arm.com
19711147Smitch.hayenga@arm.com    /** Reads a floating point register in its binary format, instead
19811147Smitch.hayenga@arm.com     * of by value. */
19913557Sgabeblack@google.com    RegVal
20013557Sgabeblack@google.com    readFloatRegOperandBits(const StaticInst *si, int idx) override
20111147Smitch.hayenga@arm.com    {
20211147Smitch.hayenga@arm.com        numFpRegReads++;
20312106SRekai.GonzalezAlberquilla@arm.com        const RegId& reg = si->srcRegIdx(idx);
20412106SRekai.GonzalezAlberquilla@arm.com        assert(reg.isFloatReg());
20512106SRekai.GonzalezAlberquilla@arm.com        return thread->readFloatRegBits(reg.index());
20611147Smitch.hayenga@arm.com    }
20711147Smitch.hayenga@arm.com
20811147Smitch.hayenga@arm.com    /** Sets the bits of a floating point register of single width
20911147Smitch.hayenga@arm.com     * to a binary value. */
21013557Sgabeblack@google.com    void
21113557Sgabeblack@google.com    setFloatRegOperandBits(const StaticInst *si, int idx, RegVal val) override
21211147Smitch.hayenga@arm.com    {
21311147Smitch.hayenga@arm.com        numFpRegWrites++;
21412106SRekai.GonzalezAlberquilla@arm.com        const RegId& reg = si->destRegIdx(idx);
21512106SRekai.GonzalezAlberquilla@arm.com        assert(reg.isFloatReg());
21612106SRekai.GonzalezAlberquilla@arm.com        thread->setFloatRegBits(reg.index(), val);
21711147Smitch.hayenga@arm.com    }
21811147Smitch.hayenga@arm.com
21912109SRekai.GonzalezAlberquilla@arm.com    /** Reads a vector register. */
22013557Sgabeblack@google.com    const VecRegContainer &
22112109SRekai.GonzalezAlberquilla@arm.com    readVecRegOperand(const StaticInst *si, int idx) const override
22212109SRekai.GonzalezAlberquilla@arm.com    {
22312109SRekai.GonzalezAlberquilla@arm.com        numVecRegReads++;
22412109SRekai.GonzalezAlberquilla@arm.com        const RegId& reg = si->srcRegIdx(idx);
22512109SRekai.GonzalezAlberquilla@arm.com        assert(reg.isVecReg());
22612109SRekai.GonzalezAlberquilla@arm.com        return thread->readVecReg(reg);
22712109SRekai.GonzalezAlberquilla@arm.com    }
22812109SRekai.GonzalezAlberquilla@arm.com
22912109SRekai.GonzalezAlberquilla@arm.com    /** Reads a vector register for modification. */
23013557Sgabeblack@google.com    VecRegContainer &
23112109SRekai.GonzalezAlberquilla@arm.com    getWritableVecRegOperand(const StaticInst *si, int idx) override
23212109SRekai.GonzalezAlberquilla@arm.com    {
23312109SRekai.GonzalezAlberquilla@arm.com        numVecRegWrites++;
23412109SRekai.GonzalezAlberquilla@arm.com        const RegId& reg = si->destRegIdx(idx);
23512109SRekai.GonzalezAlberquilla@arm.com        assert(reg.isVecReg());
23612109SRekai.GonzalezAlberquilla@arm.com        return thread->getWritableVecReg(reg);
23712109SRekai.GonzalezAlberquilla@arm.com    }
23812109SRekai.GonzalezAlberquilla@arm.com
23912109SRekai.GonzalezAlberquilla@arm.com    /** Sets a vector register to a value. */
24013557Sgabeblack@google.com    void
24113557Sgabeblack@google.com    setVecRegOperand(const StaticInst *si, int idx,
24213557Sgabeblack@google.com                     const VecRegContainer& val) override
24312109SRekai.GonzalezAlberquilla@arm.com    {
24412109SRekai.GonzalezAlberquilla@arm.com        numVecRegWrites++;
24512109SRekai.GonzalezAlberquilla@arm.com        const RegId& reg = si->destRegIdx(idx);
24612109SRekai.GonzalezAlberquilla@arm.com        assert(reg.isVecReg());
24712109SRekai.GonzalezAlberquilla@arm.com        thread->setVecReg(reg, val);
24812109SRekai.GonzalezAlberquilla@arm.com    }
24912109SRekai.GonzalezAlberquilla@arm.com
25012109SRekai.GonzalezAlberquilla@arm.com    /** Vector Register Lane Interfaces. */
25112109SRekai.GonzalezAlberquilla@arm.com    /** @{ */
25212109SRekai.GonzalezAlberquilla@arm.com    /** Reads source vector lane. */
25312109SRekai.GonzalezAlberquilla@arm.com    template <typename VecElem>
25412109SRekai.GonzalezAlberquilla@arm.com    VecLaneT<VecElem, true>
25512109SRekai.GonzalezAlberquilla@arm.com    readVecLaneOperand(const StaticInst *si, int idx) const
25612109SRekai.GonzalezAlberquilla@arm.com    {
25712109SRekai.GonzalezAlberquilla@arm.com        numVecRegReads++;
25812109SRekai.GonzalezAlberquilla@arm.com        const RegId& reg = si->srcRegIdx(idx);
25912109SRekai.GonzalezAlberquilla@arm.com        assert(reg.isVecReg());
26012109SRekai.GonzalezAlberquilla@arm.com        return thread->readVecLane<VecElem>(reg);
26112109SRekai.GonzalezAlberquilla@arm.com    }
26212109SRekai.GonzalezAlberquilla@arm.com    /** Reads source vector 8bit operand. */
26312109SRekai.GonzalezAlberquilla@arm.com    virtual ConstVecLane8
26412109SRekai.GonzalezAlberquilla@arm.com    readVec8BitLaneOperand(const StaticInst *si, int idx) const
26512109SRekai.GonzalezAlberquilla@arm.com                            override
26612109SRekai.GonzalezAlberquilla@arm.com    { return readVecLaneOperand<uint8_t>(si, idx); }
26712109SRekai.GonzalezAlberquilla@arm.com
26812109SRekai.GonzalezAlberquilla@arm.com    /** Reads source vector 16bit operand. */
26912109SRekai.GonzalezAlberquilla@arm.com    virtual ConstVecLane16
27012109SRekai.GonzalezAlberquilla@arm.com    readVec16BitLaneOperand(const StaticInst *si, int idx) const
27112109SRekai.GonzalezAlberquilla@arm.com                            override
27212109SRekai.GonzalezAlberquilla@arm.com    { return readVecLaneOperand<uint16_t>(si, idx); }
27312109SRekai.GonzalezAlberquilla@arm.com
27412109SRekai.GonzalezAlberquilla@arm.com    /** Reads source vector 32bit operand. */
27512109SRekai.GonzalezAlberquilla@arm.com    virtual ConstVecLane32
27612109SRekai.GonzalezAlberquilla@arm.com    readVec32BitLaneOperand(const StaticInst *si, int idx) const
27712109SRekai.GonzalezAlberquilla@arm.com                            override
27812109SRekai.GonzalezAlberquilla@arm.com    { return readVecLaneOperand<uint32_t>(si, idx); }
27912109SRekai.GonzalezAlberquilla@arm.com
28012109SRekai.GonzalezAlberquilla@arm.com    /** Reads source vector 64bit operand. */
28112109SRekai.GonzalezAlberquilla@arm.com    virtual ConstVecLane64
28212109SRekai.GonzalezAlberquilla@arm.com    readVec64BitLaneOperand(const StaticInst *si, int idx) const
28312109SRekai.GonzalezAlberquilla@arm.com                            override
28412109SRekai.GonzalezAlberquilla@arm.com    { return readVecLaneOperand<uint64_t>(si, idx); }
28512109SRekai.GonzalezAlberquilla@arm.com
28612109SRekai.GonzalezAlberquilla@arm.com    /** Write a lane of the destination vector operand. */
28712109SRekai.GonzalezAlberquilla@arm.com    template <typename LD>
28812109SRekai.GonzalezAlberquilla@arm.com    void
28912109SRekai.GonzalezAlberquilla@arm.com    setVecLaneOperandT(const StaticInst *si, int idx,
29012109SRekai.GonzalezAlberquilla@arm.com            const LD& val)
29112109SRekai.GonzalezAlberquilla@arm.com    {
29212109SRekai.GonzalezAlberquilla@arm.com        numVecRegWrites++;
29312109SRekai.GonzalezAlberquilla@arm.com        const RegId& reg = si->destRegIdx(idx);
29412109SRekai.GonzalezAlberquilla@arm.com        assert(reg.isVecReg());
29512109SRekai.GonzalezAlberquilla@arm.com        return thread->setVecLane(reg, val);
29612109SRekai.GonzalezAlberquilla@arm.com    }
29712109SRekai.GonzalezAlberquilla@arm.com    /** Write a lane of the destination vector operand. */
29812109SRekai.GonzalezAlberquilla@arm.com    virtual void
29912109SRekai.GonzalezAlberquilla@arm.com    setVecLaneOperand(const StaticInst *si, int idx,
30012109SRekai.GonzalezAlberquilla@arm.com            const LaneData<LaneSize::Byte>& val) override
30112109SRekai.GonzalezAlberquilla@arm.com    { return setVecLaneOperandT(si, idx, val); }
30212109SRekai.GonzalezAlberquilla@arm.com    /** Write a lane of the destination vector operand. */
30312109SRekai.GonzalezAlberquilla@arm.com    virtual void
30412109SRekai.GonzalezAlberquilla@arm.com    setVecLaneOperand(const StaticInst *si, int idx,
30512109SRekai.GonzalezAlberquilla@arm.com            const LaneData<LaneSize::TwoByte>& val) override
30612109SRekai.GonzalezAlberquilla@arm.com    { return setVecLaneOperandT(si, idx, val); }
30712109SRekai.GonzalezAlberquilla@arm.com    /** Write a lane of the destination vector operand. */
30812109SRekai.GonzalezAlberquilla@arm.com    virtual void
30912109SRekai.GonzalezAlberquilla@arm.com    setVecLaneOperand(const StaticInst *si, int idx,
31012109SRekai.GonzalezAlberquilla@arm.com            const LaneData<LaneSize::FourByte>& val) override
31112109SRekai.GonzalezAlberquilla@arm.com    { return setVecLaneOperandT(si, idx, val); }
31212109SRekai.GonzalezAlberquilla@arm.com    /** Write a lane of the destination vector operand. */
31312109SRekai.GonzalezAlberquilla@arm.com    virtual void
31412109SRekai.GonzalezAlberquilla@arm.com    setVecLaneOperand(const StaticInst *si, int idx,
31512109SRekai.GonzalezAlberquilla@arm.com            const LaneData<LaneSize::EightByte>& val) override
31612109SRekai.GonzalezAlberquilla@arm.com    { return setVecLaneOperandT(si, idx, val); }
31712109SRekai.GonzalezAlberquilla@arm.com    /** @} */
31812109SRekai.GonzalezAlberquilla@arm.com
31912109SRekai.GonzalezAlberquilla@arm.com    /** Reads an element of a vector register. */
32013557Sgabeblack@google.com    VecElem
32113557Sgabeblack@google.com    readVecElemOperand(const StaticInst *si, int idx) const override
32212109SRekai.GonzalezAlberquilla@arm.com    {
32312109SRekai.GonzalezAlberquilla@arm.com        numVecRegReads++;
32413598Sgiacomo.travaglini@arm.com        const RegId& reg = si->srcRegIdx(idx);
32512109SRekai.GonzalezAlberquilla@arm.com        assert(reg.isVecElem());
32612109SRekai.GonzalezAlberquilla@arm.com        return thread->readVecElem(reg);
32712109SRekai.GonzalezAlberquilla@arm.com    }
32812109SRekai.GonzalezAlberquilla@arm.com
32912109SRekai.GonzalezAlberquilla@arm.com    /** Sets an element of a vector register to a value. */
33013557Sgabeblack@google.com    void
33113557Sgabeblack@google.com    setVecElemOperand(const StaticInst *si, int idx,
33213557Sgabeblack@google.com                      const VecElem val) override
33312109SRekai.GonzalezAlberquilla@arm.com    {
33412109SRekai.GonzalezAlberquilla@arm.com        numVecRegWrites++;
33512109SRekai.GonzalezAlberquilla@arm.com        const RegId& reg = si->destRegIdx(idx);
33612109SRekai.GonzalezAlberquilla@arm.com        assert(reg.isVecElem());
33712109SRekai.GonzalezAlberquilla@arm.com        thread->setVecElem(reg, val);
33812109SRekai.GonzalezAlberquilla@arm.com    }
33912109SRekai.GonzalezAlberquilla@arm.com
34013610Sgiacomo.gabrielli@arm.com    const VecPredRegContainer&
34113610Sgiacomo.gabrielli@arm.com    readVecPredRegOperand(const StaticInst *si, int idx) const override
34213610Sgiacomo.gabrielli@arm.com    {
34313610Sgiacomo.gabrielli@arm.com        numVecPredRegReads++;
34413610Sgiacomo.gabrielli@arm.com        const RegId& reg = si->srcRegIdx(idx);
34513610Sgiacomo.gabrielli@arm.com        assert(reg.isVecPredReg());
34613610Sgiacomo.gabrielli@arm.com        return thread->readVecPredReg(reg);
34713610Sgiacomo.gabrielli@arm.com    }
34813610Sgiacomo.gabrielli@arm.com
34913610Sgiacomo.gabrielli@arm.com    VecPredRegContainer&
35013610Sgiacomo.gabrielli@arm.com    getWritableVecPredRegOperand(const StaticInst *si, int idx) override
35113610Sgiacomo.gabrielli@arm.com    {
35213610Sgiacomo.gabrielli@arm.com        numVecPredRegWrites++;
35313610Sgiacomo.gabrielli@arm.com        const RegId& reg = si->destRegIdx(idx);
35413610Sgiacomo.gabrielli@arm.com        assert(reg.isVecPredReg());
35513610Sgiacomo.gabrielli@arm.com        return thread->getWritableVecPredReg(reg);
35613610Sgiacomo.gabrielli@arm.com    }
35713610Sgiacomo.gabrielli@arm.com
35813610Sgiacomo.gabrielli@arm.com    void
35913610Sgiacomo.gabrielli@arm.com    setVecPredRegOperand(const StaticInst *si, int idx,
36013610Sgiacomo.gabrielli@arm.com                         const VecPredRegContainer& val) override
36113610Sgiacomo.gabrielli@arm.com    {
36213610Sgiacomo.gabrielli@arm.com        numVecPredRegWrites++;
36313610Sgiacomo.gabrielli@arm.com        const RegId& reg = si->destRegIdx(idx);
36413610Sgiacomo.gabrielli@arm.com        assert(reg.isVecPredReg());
36513610Sgiacomo.gabrielli@arm.com        thread->setVecPredReg(reg, val);
36613610Sgiacomo.gabrielli@arm.com    }
36713610Sgiacomo.gabrielli@arm.com
36813557Sgabeblack@google.com    CCReg
36913557Sgabeblack@google.com    readCCRegOperand(const StaticInst *si, int idx) override
37011147Smitch.hayenga@arm.com    {
37111147Smitch.hayenga@arm.com        numCCRegReads++;
37212106SRekai.GonzalezAlberquilla@arm.com        const RegId& reg = si->srcRegIdx(idx);
37312106SRekai.GonzalezAlberquilla@arm.com        assert(reg.isCCReg());
37412106SRekai.GonzalezAlberquilla@arm.com        return thread->readCCReg(reg.index());
37511147Smitch.hayenga@arm.com    }
37611147Smitch.hayenga@arm.com
37713557Sgabeblack@google.com    void
37813557Sgabeblack@google.com    setCCRegOperand(const StaticInst *si, int idx, CCReg val) override
37911147Smitch.hayenga@arm.com    {
38011147Smitch.hayenga@arm.com        numCCRegWrites++;
38112106SRekai.GonzalezAlberquilla@arm.com        const RegId& reg = si->destRegIdx(idx);
38212106SRekai.GonzalezAlberquilla@arm.com        assert(reg.isCCReg());
38312106SRekai.GonzalezAlberquilla@arm.com        thread->setCCReg(reg.index(), val);
38411147Smitch.hayenga@arm.com    }
38511147Smitch.hayenga@arm.com
38613557Sgabeblack@google.com    RegVal
38713557Sgabeblack@google.com    readMiscRegOperand(const StaticInst *si, int idx) override
38811147Smitch.hayenga@arm.com    {
38911147Smitch.hayenga@arm.com        numIntRegReads++;
39012106SRekai.GonzalezAlberquilla@arm.com        const RegId& reg = si->srcRegIdx(idx);
39112106SRekai.GonzalezAlberquilla@arm.com        assert(reg.isMiscReg());
39212106SRekai.GonzalezAlberquilla@arm.com        return thread->readMiscReg(reg.index());
39311147Smitch.hayenga@arm.com    }
39411147Smitch.hayenga@arm.com
39513557Sgabeblack@google.com    void
39613582Sgabeblack@google.com    setMiscRegOperand(const StaticInst *si, int idx, RegVal val) override
39711147Smitch.hayenga@arm.com    {
39811147Smitch.hayenga@arm.com        numIntRegWrites++;
39912106SRekai.GonzalezAlberquilla@arm.com        const RegId& reg = si->destRegIdx(idx);
40012106SRekai.GonzalezAlberquilla@arm.com        assert(reg.isMiscReg());
40112106SRekai.GonzalezAlberquilla@arm.com        thread->setMiscReg(reg.index(), val);
40211147Smitch.hayenga@arm.com    }
40311147Smitch.hayenga@arm.com
40411147Smitch.hayenga@arm.com    /**
40511147Smitch.hayenga@arm.com     * Reads a miscellaneous register, handling any architectural
40611147Smitch.hayenga@arm.com     * side effects due to reading that register.
40711147Smitch.hayenga@arm.com     */
40813557Sgabeblack@google.com    RegVal
40913557Sgabeblack@google.com    readMiscReg(int misc_reg) override
41011147Smitch.hayenga@arm.com    {
41111147Smitch.hayenga@arm.com        numIntRegReads++;
41211147Smitch.hayenga@arm.com        return thread->readMiscReg(misc_reg);
41311147Smitch.hayenga@arm.com    }
41411147Smitch.hayenga@arm.com
41511147Smitch.hayenga@arm.com    /**
41611147Smitch.hayenga@arm.com     * Sets a miscellaneous register, handling any architectural
41711147Smitch.hayenga@arm.com     * side effects due to writing that register.
41811147Smitch.hayenga@arm.com     */
41913557Sgabeblack@google.com    void
42013582Sgabeblack@google.com    setMiscReg(int misc_reg, RegVal val) override
42111147Smitch.hayenga@arm.com    {
42211147Smitch.hayenga@arm.com        numIntRegWrites++;
42311147Smitch.hayenga@arm.com        thread->setMiscReg(misc_reg, val);
42411147Smitch.hayenga@arm.com    }
42511147Smitch.hayenga@arm.com
42613557Sgabeblack@google.com    PCState
42713557Sgabeblack@google.com    pcState() const override
42811147Smitch.hayenga@arm.com    {
42911147Smitch.hayenga@arm.com        return thread->pcState();
43011147Smitch.hayenga@arm.com    }
43111147Smitch.hayenga@arm.com
43213557Sgabeblack@google.com    void
43313557Sgabeblack@google.com    pcState(const PCState &val) override
43411147Smitch.hayenga@arm.com    {
43511147Smitch.hayenga@arm.com        thread->pcState(val);
43611147Smitch.hayenga@arm.com    }
43711147Smitch.hayenga@arm.com
43811147Smitch.hayenga@arm.com
43913557Sgabeblack@google.com    Fault
44013557Sgabeblack@google.com    readMem(Addr addr, uint8_t *data, unsigned int size,
44113557Sgabeblack@google.com            Request::Flags flags) override
44211147Smitch.hayenga@arm.com    {
44311147Smitch.hayenga@arm.com        return cpu->readMem(addr, data, size, flags);
44411147Smitch.hayenga@arm.com    }
44511147Smitch.hayenga@arm.com
44613557Sgabeblack@google.com    Fault
44713557Sgabeblack@google.com    initiateMemRead(Addr addr, unsigned int size,
44813557Sgabeblack@google.com                    Request::Flags flags) override
44911303Ssteve.reinhardt@amd.com    {
45011303Ssteve.reinhardt@amd.com        return cpu->initiateMemRead(addr, size, flags);
45111303Ssteve.reinhardt@amd.com    }
45211303Ssteve.reinhardt@amd.com
45313557Sgabeblack@google.com    Fault
45413557Sgabeblack@google.com    writeMem(uint8_t *data, unsigned int size, Addr addr,
45513557Sgabeblack@google.com             Request::Flags flags, uint64_t *res) override
45611147Smitch.hayenga@arm.com    {
45711147Smitch.hayenga@arm.com        return cpu->writeMem(data, size, addr, flags, res);
45811147Smitch.hayenga@arm.com    }
45911147Smitch.hayenga@arm.com
46011147Smitch.hayenga@arm.com    /**
46111147Smitch.hayenga@arm.com     * Sets the number of consecutive store conditional failures.
46211147Smitch.hayenga@arm.com     */
46313557Sgabeblack@google.com    void
46413557Sgabeblack@google.com    setStCondFailures(unsigned int sc_failures) override
46511147Smitch.hayenga@arm.com    {
46611147Smitch.hayenga@arm.com        thread->setStCondFailures(sc_failures);
46711147Smitch.hayenga@arm.com    }
46811147Smitch.hayenga@arm.com
46911147Smitch.hayenga@arm.com    /**
47011147Smitch.hayenga@arm.com     * Returns the number of consecutive store conditional failures.
47111147Smitch.hayenga@arm.com     */
47213557Sgabeblack@google.com    unsigned int
47313557Sgabeblack@google.com    readStCondFailures() const override
47411147Smitch.hayenga@arm.com    {
47511147Smitch.hayenga@arm.com        return thread->readStCondFailures();
47611147Smitch.hayenga@arm.com    }
47711147Smitch.hayenga@arm.com
47811147Smitch.hayenga@arm.com    /**
47911147Smitch.hayenga@arm.com     * Executes a syscall specified by the callnum.
48011147Smitch.hayenga@arm.com     */
48113557Sgabeblack@google.com    void
48213557Sgabeblack@google.com    syscall(int64_t callnum, Fault *fault) override
48311147Smitch.hayenga@arm.com    {
48411147Smitch.hayenga@arm.com        if (FullSystem)
48511147Smitch.hayenga@arm.com            panic("Syscall emulation isn't available in FS mode.");
48611147Smitch.hayenga@arm.com
48711877Sbrandon.potter@amd.com        thread->syscall(callnum, fault);
48811147Smitch.hayenga@arm.com    }
48911147Smitch.hayenga@arm.com
49011147Smitch.hayenga@arm.com    /** Returns a pointer to the ThreadContext. */
49113557Sgabeblack@google.com    ThreadContext *tcBase() override { return thread->getTC(); }
49211147Smitch.hayenga@arm.com
49311147Smitch.hayenga@arm.com    /**
49411147Smitch.hayenga@arm.com     * Somewhat Alpha-specific function that handles returning from an
49511147Smitch.hayenga@arm.com     * error or interrupt.
49611147Smitch.hayenga@arm.com     */
49713557Sgabeblack@google.com    Fault hwrei() override { return thread->hwrei(); }
49811147Smitch.hayenga@arm.com
49911147Smitch.hayenga@arm.com    /**
50011147Smitch.hayenga@arm.com     * Check for special simulator handling of specific PAL calls.  If
50111147Smitch.hayenga@arm.com     * return value is false, actual PAL call will be suppressed.
50211147Smitch.hayenga@arm.com     */
50313557Sgabeblack@google.com    bool
50413557Sgabeblack@google.com    simPalCheck(int palFunc) override
50511147Smitch.hayenga@arm.com    {
50611147Smitch.hayenga@arm.com        return thread->simPalCheck(palFunc);
50711147Smitch.hayenga@arm.com    }
50811147Smitch.hayenga@arm.com
50913557Sgabeblack@google.com    bool
51013557Sgabeblack@google.com    readPredicate() const override
51111147Smitch.hayenga@arm.com    {
51211147Smitch.hayenga@arm.com        return thread->readPredicate();
51311147Smitch.hayenga@arm.com    }
51411147Smitch.hayenga@arm.com
51513557Sgabeblack@google.com    void
51613557Sgabeblack@google.com    setPredicate(bool val) override
51711147Smitch.hayenga@arm.com    {
51811147Smitch.hayenga@arm.com        thread->setPredicate(val);
51911147Smitch.hayenga@arm.com
52011147Smitch.hayenga@arm.com        if (cpu->traceData) {
52111147Smitch.hayenga@arm.com            cpu->traceData->setPredicate(val);
52211147Smitch.hayenga@arm.com        }
52311147Smitch.hayenga@arm.com    }
52411147Smitch.hayenga@arm.com
52511147Smitch.hayenga@arm.com    /**
52611147Smitch.hayenga@arm.com     * Invalidate a page in the DTLB <i>and</i> ITLB.
52711147Smitch.hayenga@arm.com     */
52813557Sgabeblack@google.com    void
52913557Sgabeblack@google.com    demapPage(Addr vaddr, uint64_t asn) override
53011147Smitch.hayenga@arm.com    {
53111147Smitch.hayenga@arm.com        thread->demapPage(vaddr, asn);
53211147Smitch.hayenga@arm.com    }
53311147Smitch.hayenga@arm.com
53413557Sgabeblack@google.com    void
53513557Sgabeblack@google.com    armMonitor(Addr address) override
53611147Smitch.hayenga@arm.com    {
53711148Smitch.hayenga@arm.com        cpu->armMonitor(thread->threadId(), address);
53811147Smitch.hayenga@arm.com    }
53911147Smitch.hayenga@arm.com
54013557Sgabeblack@google.com    bool
54113557Sgabeblack@google.com    mwait(PacketPtr pkt) override
54211147Smitch.hayenga@arm.com    {
54311148Smitch.hayenga@arm.com        return cpu->mwait(thread->threadId(), pkt);
54411147Smitch.hayenga@arm.com    }
54511147Smitch.hayenga@arm.com
54613557Sgabeblack@google.com    void
54713557Sgabeblack@google.com    mwaitAtomic(ThreadContext *tc) override
54811147Smitch.hayenga@arm.com    {
54911148Smitch.hayenga@arm.com        cpu->mwaitAtomic(thread->threadId(), tc, thread->dtb);
55011147Smitch.hayenga@arm.com    }
55111147Smitch.hayenga@arm.com
55213557Sgabeblack@google.com    AddressMonitor *
55313557Sgabeblack@google.com    getAddrMonitor() override
55411147Smitch.hayenga@arm.com    {
55511148Smitch.hayenga@arm.com        return cpu->getCpuAddrMonitor(thread->threadId());
55611147Smitch.hayenga@arm.com    }
55711147Smitch.hayenga@arm.com
55811147Smitch.hayenga@arm.com#if THE_ISA == MIPS_ISA
55913557Sgabeblack@google.com    RegVal
56013557Sgabeblack@google.com    readRegOtherThread(const RegId& reg, ThreadID tid=InvalidThreadID)
56111168Sandreas.hansson@arm.com        override
56211147Smitch.hayenga@arm.com    {
56311147Smitch.hayenga@arm.com        panic("Simple CPU models do not support multithreaded "
56411147Smitch.hayenga@arm.com              "register access.");
56511147Smitch.hayenga@arm.com    }
56611147Smitch.hayenga@arm.com
56713557Sgabeblack@google.com    void
56813557Sgabeblack@google.com    setRegOtherThread(const RegId& reg, RegVal val,
56913557Sgabeblack@google.com                      ThreadID tid=InvalidThreadID) override
57011147Smitch.hayenga@arm.com    {
57111147Smitch.hayenga@arm.com        panic("Simple CPU models do not support multithreaded "
57211147Smitch.hayenga@arm.com              "register access.");
57311147Smitch.hayenga@arm.com    }
57411147Smitch.hayenga@arm.com#endif
57511147Smitch.hayenga@arm.com
57611147Smitch.hayenga@arm.com};
57711147Smitch.hayenga@arm.com
57811147Smitch.hayenga@arm.com#endif // __CPU_EXEC_CONTEXT_HH__
579