simple_thread.hh revision 14022
12SN/A/*
210292SAndreas.Sandberg@ARM.com * Copyright (c) 2011-2012, 2016-2018 ARM Limited
310292SAndreas.Sandberg@ARM.com * Copyright (c) 2013 Advanced Micro Devices, Inc.
410292SAndreas.Sandberg@ARM.com * All rights reserved
54039Sbinkertn@umich.edu *
62SN/A * The license below extends only to copyright in the software and shall
72SN/A * not be construed as granting a license to any other intellectual
82SN/A * property including but not limited to intellectual property relating
92SN/A * to a hardware implementation of the functionality of the software
102SN/A * licensed hereunder.  You may use the software subject to the license
112SN/A * terms below provided that you ensure that this notice is replicated
122SN/A * unmodified and in its entirety in all distributions of the software,
132SN/A * modified or unmodified, in source code or in binary form.
142SN/A *
152SN/A * Copyright (c) 2001-2006 The Regents of The University of Michigan
162SN/A * All rights reserved.
172SN/A *
182SN/A * Redistribution and use in source and binary forms, with or without
192SN/A * modification, are permitted provided that the following conditions are
202SN/A * met: redistributions of source code must retain the above copyright
212SN/A * notice, this list of conditions and the following disclaimer;
222SN/A * redistributions in binary form must reproduce the above copyright
232SN/A * notice, this list of conditions and the following disclaimer in the
242SN/A * documentation and/or other materials provided with the distribution;
252SN/A * neither the name of the copyright holders nor the names of its
262SN/A * contributors may be used to endorse or promote products derived from
272SN/A * this software without specific prior written permission.
282SN/A *
292SN/A * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
302665Ssaidi@eecs.umich.edu * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
312665Ssaidi@eecs.umich.edu * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
322665Ssaidi@eecs.umich.edu * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
3310475SAndrew.Bardsley@arm.com * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
342SN/A * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
352SN/A * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
361354SN/A * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
371354SN/A * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
382SN/A * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
394046Sbinkertn@umich.edu * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
402SN/A *
4156SN/A * Authors: Steve Reinhardt
428232Snate@binkert.org *          Nathan Binkert
431031SN/A */
446214Snate@binkert.org
454167Sbinkertn@umich.edu#ifndef __CPU_SIMPLE_THREAD_HH__
462SN/A#define __CPU_SIMPLE_THREAD_HH__
472SN/A
482SN/A#include "arch/decoder.hh"
4910475SAndrew.Bardsley@arm.com#include "arch/generic/tlb.hh"
5010475SAndrew.Bardsley@arm.com#include "arch/isa.hh"
5110475SAndrew.Bardsley@arm.com#include "arch/isa_traits.hh"
5210475SAndrew.Bardsley@arm.com#include "arch/registers.hh"
5310475SAndrew.Bardsley@arm.com#include "arch/types.hh"
5410475SAndrew.Bardsley@arm.com#include "base/types.hh"
5510475SAndrew.Bardsley@arm.com#include "config/the_isa.hh"
568232Snate@binkert.org#include "cpu/thread_context.hh"
5710475SAndrew.Bardsley@arm.com#include "cpu/thread_state.hh"
5810475SAndrew.Bardsley@arm.com#include "debug/CCRegs.hh"
5910475SAndrew.Bardsley@arm.com#include "debug/FloatRegs.hh"
6010475SAndrew.Bardsley@arm.com#include "debug/IntRegs.hh"
6110475SAndrew.Bardsley@arm.com#include "debug/VecPredRegs.hh"
6210475SAndrew.Bardsley@arm.com#include "debug/VecRegs.hh"
6310475SAndrew.Bardsley@arm.com#include "mem/page_table.hh"
6410475SAndrew.Bardsley@arm.com#include "mem/request.hh"
6510475SAndrew.Bardsley@arm.com#include "sim/byteswap.hh"
6610475SAndrew.Bardsley@arm.com#include "sim/eventq.hh"
6710475SAndrew.Bardsley@arm.com#include "sim/process.hh"
6810475SAndrew.Bardsley@arm.com#include "sim/serialize.hh"
6910475SAndrew.Bardsley@arm.com#include "sim/system.hh"
7010475SAndrew.Bardsley@arm.com
7110475SAndrew.Bardsley@arm.comclass BaseCPU;
7210475SAndrew.Bardsley@arm.comclass CheckerCPU;
7310475SAndrew.Bardsley@arm.com
7410475SAndrew.Bardsley@arm.comclass FunctionProfile;
7510475SAndrew.Bardsley@arm.comclass ProfileNode;
7610475SAndrew.Bardsley@arm.com
7710475SAndrew.Bardsley@arm.comnamespace Kernel {
7810475SAndrew.Bardsley@arm.com    class Statistics;
7910475SAndrew.Bardsley@arm.com}
8010475SAndrew.Bardsley@arm.com
8110475SAndrew.Bardsley@arm.com/**
8210475SAndrew.Bardsley@arm.com * The SimpleThread object provides a combination of the ThreadState
8310475SAndrew.Bardsley@arm.com * object and the ThreadContext interface. It implements the
8410475SAndrew.Bardsley@arm.com * ThreadContext interface and adds to the ThreadState object by adding all
8510475SAndrew.Bardsley@arm.com * the objects needed for simple functional execution, including a
8610475SAndrew.Bardsley@arm.com * simple architectural register file, and pointers to the ITB and DTB
8710475SAndrew.Bardsley@arm.com * in full system mode. For CPU models that do not need more advanced
8810475SAndrew.Bardsley@arm.com * ways to hold state (i.e. a separate physical register file, or
8910475SAndrew.Bardsley@arm.com * separate fetch and commit PC's), this SimpleThread class provides
9010475SAndrew.Bardsley@arm.com * all the necessary state for full architecture-level functional
9110475SAndrew.Bardsley@arm.com * simulation.  See the AtomicSimpleCPU or TimingSimpleCPU for
9210475SAndrew.Bardsley@arm.com * examples.
9310475SAndrew.Bardsley@arm.com */
9410475SAndrew.Bardsley@arm.com
9510475SAndrew.Bardsley@arm.comclass SimpleThread : public ThreadState, public ThreadContext
9610475SAndrew.Bardsley@arm.com{
9710475SAndrew.Bardsley@arm.com  protected:
9810475SAndrew.Bardsley@arm.com    typedef TheISA::MachInst MachInst;
9910475SAndrew.Bardsley@arm.com    using VecRegContainer = TheISA::VecRegContainer;
10010475SAndrew.Bardsley@arm.com    using VecElem = TheISA::VecElem;
10110475SAndrew.Bardsley@arm.com    using VecPredRegContainer = TheISA::VecPredRegContainer;
10210475SAndrew.Bardsley@arm.com  public:
10310475SAndrew.Bardsley@arm.com    typedef ThreadContext::Status Status;
10410475SAndrew.Bardsley@arm.com
10510475SAndrew.Bardsley@arm.com  protected:
10610475SAndrew.Bardsley@arm.com    RegVal floatRegs[TheISA::NumFloatRegs];
10710475SAndrew.Bardsley@arm.com    RegVal intRegs[TheISA::NumIntRegs];
10810475SAndrew.Bardsley@arm.com    VecRegContainer vecRegs[TheISA::NumVecRegs];
10910475SAndrew.Bardsley@arm.com    VecPredRegContainer vecPredRegs[TheISA::NumVecPredRegs];
11010475SAndrew.Bardsley@arm.com#ifdef ISA_HAS_CC_REGS
11110475SAndrew.Bardsley@arm.com    RegVal ccRegs[TheISA::NumCCRegs];
11210475SAndrew.Bardsley@arm.com#endif
11310475SAndrew.Bardsley@arm.com    TheISA::ISA *const isa;    // one "instance" of the current ISA.
1144046Sbinkertn@umich.edu
1152SN/A    TheISA::PCState _pcState;
11610475SAndrew.Bardsley@arm.com
11710475SAndrew.Bardsley@arm.com    /** Did this instruction execute or is it predicated false */
11810475SAndrew.Bardsley@arm.com    bool predicate;
11910475SAndrew.Bardsley@arm.com
1204046Sbinkertn@umich.edu    /** True if the memory access should be skipped for this instruction */
1212SN/A    bool memAccPredicate;
1227811Ssteve.reinhardt@amd.com
1234039Sbinkertn@umich.edu  public:
1241070SN/A    std::string name() const
1251070SN/A    {
1261070SN/A        return csprintf("%s.[tid:%i]", baseCpu->name(), threadId());
1271070SN/A    }
1281070SN/A
1291070SN/A    System *system;
1301070SN/A
1311070SN/A    BaseTLB *itb;
1321070SN/A    BaseTLB *dtb;
13310475SAndrew.Bardsley@arm.com
13410475SAndrew.Bardsley@arm.com    TheISA::Decoder decoder;
13510475SAndrew.Bardsley@arm.com
1362SN/A    // constructor: initialize SimpleThread from given process structure
13710259SAndrew.Bardsley@arm.com    // FS
13810259SAndrew.Bardsley@arm.com    SimpleThread(BaseCPU *_cpu, int _thread_num, System *_system,
13910259SAndrew.Bardsley@arm.com                 BaseTLB *_itb, BaseTLB *_dtb, TheISA::ISA *_isa,
14010259SAndrew.Bardsley@arm.com                 bool use_kernel_stats = true);
14110259SAndrew.Bardsley@arm.com    // SE
14210259SAndrew.Bardsley@arm.com    SimpleThread(BaseCPU *_cpu, int _thread_num, System *_system,
14310259SAndrew.Bardsley@arm.com                 Process *_process, BaseTLB *_itb, BaseTLB *_dtb,
14410259SAndrew.Bardsley@arm.com                 TheISA::ISA *_isa);
14510259SAndrew.Bardsley@arm.com
14610259SAndrew.Bardsley@arm.com    virtual ~SimpleThread() {}
14710259SAndrew.Bardsley@arm.com
14810259SAndrew.Bardsley@arm.com    void takeOverFrom(ThreadContext *oldContext) override;
14910259SAndrew.Bardsley@arm.com
15010259SAndrew.Bardsley@arm.com    void regStats(const std::string &name) override;
1512SN/A
1522SN/A    void copyState(ThreadContext *oldContext);
1532SN/A
1542SN/A    void serialize(CheckpointOut &cp) const override;
1552SN/A    void unserialize(CheckpointIn &cp) override;
1562SN/A    void startup();
1572SN/A
1582SN/A    /***************************************************************
1592SN/A     *  SimpleThread functions to provide CPU with access to various
1602SN/A     *  state.
1612SN/A     **************************************************************/
1622SN/A
1638232Snate@binkert.org    /** Returns the pointer to this SimpleThread's ThreadContext. Used
1642SN/A     *  when a ThreadContext must be passed to objects outside of the
16510475SAndrew.Bardsley@arm.com     *  CPU.
16610475SAndrew.Bardsley@arm.com     */
16710475SAndrew.Bardsley@arm.com    ThreadContext *getTC() { return this; }
16810475SAndrew.Bardsley@arm.com
1692SN/A    void demapPage(Addr vaddr, uint64_t asn)
1702SN/A    {
17110475SAndrew.Bardsley@arm.com        itb->demapPage(vaddr, asn);
17210475SAndrew.Bardsley@arm.com        dtb->demapPage(vaddr, asn);
17310475SAndrew.Bardsley@arm.com    }
17410475SAndrew.Bardsley@arm.com
17510475SAndrew.Bardsley@arm.com    void demapInstPage(Addr vaddr, uint64_t asn)
17610475SAndrew.Bardsley@arm.com    {
1772SN/A        itb->demapPage(vaddr, asn);
1782SN/A    }
17910475SAndrew.Bardsley@arm.com
18010475SAndrew.Bardsley@arm.com    void demapDataPage(Addr vaddr, uint64_t asn)
18110475SAndrew.Bardsley@arm.com    {
18210475SAndrew.Bardsley@arm.com        dtb->demapPage(vaddr, asn);
18310475SAndrew.Bardsley@arm.com    }
18410475SAndrew.Bardsley@arm.com
1855806Ssaidi@eecs.umich.edu    void dumpFuncProfile() override;
1865806Ssaidi@eecs.umich.edu
18710475SAndrew.Bardsley@arm.com    /*******************************************
18810475SAndrew.Bardsley@arm.com     * ThreadContext interface functions.
18910475SAndrew.Bardsley@arm.com     ******************************************/
19010475SAndrew.Bardsley@arm.com
19110475SAndrew.Bardsley@arm.com    BaseCPU *getCpuPtr() override { return baseCpu; }
19210475SAndrew.Bardsley@arm.com
1932SN/A    int cpuId() const override { return ThreadState::cpuId(); }
1942SN/A    uint32_t socketId() const override { return ThreadState::socketId(); }
19510475SAndrew.Bardsley@arm.com    int threadId() const override { return ThreadState::threadId(); }
19610475SAndrew.Bardsley@arm.com    void setThreadId(int id) override { ThreadState::setThreadId(id); }
1974046Sbinkertn@umich.edu    ContextID contextId() const override { return ThreadState::contextId(); }
1984046Sbinkertn@umich.edu    void setContextId(ContextID id) override { ThreadState::setContextId(id); }
19910475SAndrew.Bardsley@arm.com
20010475SAndrew.Bardsley@arm.com    BaseTLB *getITBPtr() override { return itb; }
2012SN/A
2022SN/A    BaseTLB *getDTBPtr() override { return dtb; }
20310475SAndrew.Bardsley@arm.com
20410475SAndrew.Bardsley@arm.com    CheckerCPU *getCheckerCpuPtr() override { return NULL; }
205507SN/A
206507SN/A    TheISA::ISA *getIsaPtr() override { return isa; }
2072SN/A
2082SN/A    TheISA::Decoder *getDecoderPtr() override { return &decoder; }
2092SN/A
2104046Sbinkertn@umich.edu    System *getSystemPtr() override { return system; }
2114041Sbinkertn@umich.edu
2125806Ssaidi@eecs.umich.edu    Kernel::Statistics *
2134041Sbinkertn@umich.edu    getKernelStats() override
2144046Sbinkertn@umich.edu    {
2154041Sbinkertn@umich.edu        return ThreadState::getKernelStats();
2164041Sbinkertn@umich.edu    }
2172SN/A
2185543Ssaidi@eecs.umich.edu    PortProxy &getPhysProxy() override { return ThreadState::getPhysProxy(); }
2192SN/A    PortProxy &getVirtProxy() override { return ThreadState::getVirtProxy(); }
2201354SN/A
221    void initMemProxies(ThreadContext *tc) override
222    {
223        ThreadState::initMemProxies(tc);
224    }
225
226    PortProxy &
227    getMemProxy() override
228    {
229        return ThreadState::getMemProxy();
230    }
231
232    Process *getProcessPtr() override { return ThreadState::getProcessPtr(); }
233    void setProcessPtr(Process *p) override { ThreadState::setProcessPtr(p); }
234
235    Status status() const override { return _status; }
236
237    void setStatus(Status newStatus) override { _status = newStatus; }
238
239    /// Set the status to Active.
240    void activate() override;
241
242    /// Set the status to Suspended.
243    void suspend() override;
244
245    /// Set the status to Halted.
246    void halt() override;
247
248    EndQuiesceEvent *
249    getQuiesceEvent() override
250    {
251        return ThreadState::getQuiesceEvent();
252    }
253
254    Tick
255    readLastActivate() override
256    {
257        return ThreadState::readLastActivate();
258    }
259    Tick
260    readLastSuspend() override
261    {
262        return ThreadState::readLastSuspend();
263    }
264
265    void profileClear() override { ThreadState::profileClear(); }
266    void profileSample() override { ThreadState::profileSample(); }
267
268    void copyArchRegs(ThreadContext *tc) override;
269
270    void clearArchRegs() override
271    {
272        _pcState = 0;
273        memset(intRegs, 0, sizeof(intRegs));
274        memset(floatRegs, 0, sizeof(floatRegs));
275        for (int i = 0; i < TheISA::NumVecRegs; i++) {
276            vecRegs[i].zero();
277        }
278        for (int i = 0; i < TheISA::NumVecPredRegs; i++) {
279            vecPredRegs[i].reset();
280        }
281#ifdef ISA_HAS_CC_REGS
282        memset(ccRegs, 0, sizeof(ccRegs));
283#endif
284        isa->clear();
285    }
286
287    //
288    // New accessors for new decoder.
289    //
290    RegVal
291    readIntReg(RegIndex reg_idx) const override
292    {
293        int flatIndex = isa->flattenIntIndex(reg_idx);
294        assert(flatIndex < TheISA::NumIntRegs);
295        uint64_t regVal(readIntRegFlat(flatIndex));
296        DPRINTF(IntRegs, "Reading int reg %d (%d) as %#x.\n",
297                reg_idx, flatIndex, regVal);
298        return regVal;
299    }
300
301    RegVal
302    readFloatReg(RegIndex reg_idx) const override
303    {
304        int flatIndex = isa->flattenFloatIndex(reg_idx);
305        assert(flatIndex < TheISA::NumFloatRegs);
306        RegVal regVal(readFloatRegFlat(flatIndex));
307        DPRINTF(FloatRegs, "Reading float reg %d (%d) bits as %#x.\n",
308                reg_idx, flatIndex, regVal);
309        return regVal;
310    }
311
312    const VecRegContainer&
313    readVecReg(const RegId& reg) const override
314    {
315        int flatIndex = isa->flattenVecIndex(reg.index());
316        assert(flatIndex < TheISA::NumVecRegs);
317        const VecRegContainer& regVal = readVecRegFlat(flatIndex);
318        DPRINTF(VecRegs, "Reading vector reg %d (%d) as %s.\n",
319                reg.index(), flatIndex, regVal.print());
320        return regVal;
321    }
322
323    VecRegContainer&
324    getWritableVecReg(const RegId& reg) override
325    {
326        int flatIndex = isa->flattenVecIndex(reg.index());
327        assert(flatIndex < TheISA::NumVecRegs);
328        VecRegContainer& regVal = getWritableVecRegFlat(flatIndex);
329        DPRINTF(VecRegs, "Reading vector reg %d (%d) as %s for modify.\n",
330                reg.index(), flatIndex, regVal.print());
331        return regVal;
332    }
333
334    /** Vector Register Lane Interfaces. */
335    /** @{ */
336    /** Reads source vector <T> operand. */
337    template <typename T>
338    VecLaneT<T, true>
339    readVecLane(const RegId& reg) const
340    {
341        int flatIndex = isa->flattenVecIndex(reg.index());
342        assert(flatIndex < TheISA::NumVecRegs);
343        auto regVal = readVecLaneFlat<T>(flatIndex, reg.elemIndex());
344        DPRINTF(VecRegs, "Reading vector lane %d (%d)[%d] as %lx.\n",
345                reg.index(), flatIndex, reg.elemIndex(), regVal);
346        return regVal;
347    }
348
349    /** Reads source vector 8bit operand. */
350    virtual ConstVecLane8
351    readVec8BitLaneReg(const RegId &reg) const override
352    {
353        return readVecLane<uint8_t>(reg);
354    }
355
356    /** Reads source vector 16bit operand. */
357    virtual ConstVecLane16
358    readVec16BitLaneReg(const RegId &reg) const override
359    {
360        return readVecLane<uint16_t>(reg);
361    }
362
363    /** Reads source vector 32bit operand. */
364    virtual ConstVecLane32
365    readVec32BitLaneReg(const RegId &reg) const override
366    {
367        return readVecLane<uint32_t>(reg);
368    }
369
370    /** Reads source vector 64bit operand. */
371    virtual ConstVecLane64
372    readVec64BitLaneReg(const RegId &reg) const override
373    {
374        return readVecLane<uint64_t>(reg);
375    }
376
377    /** Write a lane of the destination vector register. */
378    template <typename LD>
379    void
380    setVecLaneT(const RegId &reg, const LD &val)
381    {
382        int flatIndex = isa->flattenVecIndex(reg.index());
383        assert(flatIndex < TheISA::NumVecRegs);
384        setVecLaneFlat(flatIndex, reg.elemIndex(), val);
385        DPRINTF(VecRegs, "Reading vector lane %d (%d)[%d] to %lx.\n",
386                reg.index(), flatIndex, reg.elemIndex(), val);
387    }
388    virtual void
389    setVecLane(const RegId &reg, const LaneData<LaneSize::Byte> &val) override
390    {
391        return setVecLaneT(reg, val);
392    }
393    virtual void
394    setVecLane(const RegId &reg,
395               const LaneData<LaneSize::TwoByte> &val) override
396    {
397        return setVecLaneT(reg, val);
398    }
399    virtual void
400    setVecLane(const RegId &reg,
401               const LaneData<LaneSize::FourByte> &val) override
402    {
403        return setVecLaneT(reg, val);
404    }
405    virtual void
406    setVecLane(const RegId &reg,
407               const LaneData<LaneSize::EightByte> &val) override
408    {
409        return setVecLaneT(reg, val);
410    }
411    /** @} */
412
413    const VecElem &
414    readVecElem(const RegId &reg) const override
415    {
416        int flatIndex = isa->flattenVecElemIndex(reg.index());
417        assert(flatIndex < TheISA::NumVecRegs);
418        const VecElem& regVal = readVecElemFlat(flatIndex, reg.elemIndex());
419        DPRINTF(VecRegs, "Reading element %d of vector reg %d (%d) as"
420                " %#x.\n", reg.elemIndex(), reg.index(), flatIndex, regVal);
421        return regVal;
422    }
423
424    const VecPredRegContainer &
425    readVecPredReg(const RegId &reg) const override
426    {
427        int flatIndex = isa->flattenVecPredIndex(reg.index());
428        assert(flatIndex < TheISA::NumVecPredRegs);
429        const VecPredRegContainer& regVal = readVecPredRegFlat(flatIndex);
430        DPRINTF(VecPredRegs, "Reading predicate reg %d (%d) as %s.\n",
431                reg.index(), flatIndex, regVal.print());
432        return regVal;
433    }
434
435    VecPredRegContainer &
436    getWritableVecPredReg(const RegId &reg) override
437    {
438        int flatIndex = isa->flattenVecPredIndex(reg.index());
439        assert(flatIndex < TheISA::NumVecPredRegs);
440        VecPredRegContainer& regVal = getWritableVecPredRegFlat(flatIndex);
441        DPRINTF(VecPredRegs,
442                "Reading predicate reg %d (%d) as %s for modify.\n",
443                reg.index(), flatIndex, regVal.print());
444        return regVal;
445    }
446
447    RegVal
448    readCCReg(RegIndex reg_idx) const override
449    {
450#ifdef ISA_HAS_CC_REGS
451        int flatIndex = isa->flattenCCIndex(reg_idx);
452        assert(0 <= flatIndex);
453        assert(flatIndex < TheISA::NumCCRegs);
454        uint64_t regVal(readCCRegFlat(flatIndex));
455        DPRINTF(CCRegs, "Reading CC reg %d (%d) as %#x.\n",
456                reg_idx, flatIndex, regVal);
457        return regVal;
458#else
459        panic("Tried to read a CC register.");
460        return 0;
461#endif
462    }
463
464    void
465    setIntReg(RegIndex reg_idx, RegVal val) override
466    {
467        int flatIndex = isa->flattenIntIndex(reg_idx);
468        assert(flatIndex < TheISA::NumIntRegs);
469        DPRINTF(IntRegs, "Setting int reg %d (%d) to %#x.\n",
470                reg_idx, flatIndex, val);
471        setIntRegFlat(flatIndex, val);
472    }
473
474    void
475    setFloatReg(RegIndex reg_idx, RegVal val) override
476    {
477        int flatIndex = isa->flattenFloatIndex(reg_idx);
478        assert(flatIndex < TheISA::NumFloatRegs);
479        // XXX: Fix array out of bounds compiler error for gem5.fast
480        // when checkercpu enabled
481        if (flatIndex < TheISA::NumFloatRegs)
482            setFloatRegFlat(flatIndex, val);
483        DPRINTF(FloatRegs, "Setting float reg %d (%d) bits to %#x.\n",
484                reg_idx, flatIndex, val);
485    }
486
487    void
488    setVecReg(const RegId &reg, const VecRegContainer &val) override
489    {
490        int flatIndex = isa->flattenVecIndex(reg.index());
491        assert(flatIndex < TheISA::NumVecRegs);
492        setVecRegFlat(flatIndex, val);
493        DPRINTF(VecRegs, "Setting vector reg %d (%d) to %s.\n",
494                reg.index(), flatIndex, val.print());
495    }
496
497    void
498    setVecElem(const RegId &reg, const VecElem &val) override
499    {
500        int flatIndex = isa->flattenVecElemIndex(reg.index());
501        assert(flatIndex < TheISA::NumVecRegs);
502        setVecElemFlat(flatIndex, reg.elemIndex(), val);
503        DPRINTF(VecRegs, "Setting element %d of vector reg %d (%d) to"
504                " %#x.\n", reg.elemIndex(), reg.index(), flatIndex, val);
505    }
506
507    void
508    setVecPredReg(const RegId &reg, const VecPredRegContainer &val) override
509    {
510        int flatIndex = isa->flattenVecPredIndex(reg.index());
511        assert(flatIndex < TheISA::NumVecPredRegs);
512        setVecPredRegFlat(flatIndex, val);
513        DPRINTF(VecPredRegs, "Setting predicate reg %d (%d) to %s.\n",
514                reg.index(), flatIndex, val.print());
515    }
516
517    void
518    setCCReg(RegIndex reg_idx, RegVal val) override
519    {
520#ifdef ISA_HAS_CC_REGS
521        int flatIndex = isa->flattenCCIndex(reg_idx);
522        assert(flatIndex < TheISA::NumCCRegs);
523        DPRINTF(CCRegs, "Setting CC reg %d (%d) to %#x.\n",
524                reg_idx, flatIndex, val);
525        setCCRegFlat(flatIndex, val);
526#else
527        panic("Tried to set a CC register.");
528#endif
529    }
530
531    TheISA::PCState pcState() const override { return _pcState; }
532    void pcState(const TheISA::PCState &val) override { _pcState = val; }
533
534    void
535    pcStateNoRecord(const TheISA::PCState &val) override
536    {
537        _pcState = val;
538    }
539
540    Addr instAddr() const override  { return _pcState.instAddr(); }
541    Addr nextInstAddr() const override { return _pcState.nextInstAddr(); }
542    MicroPC microPC() const override { return _pcState.microPC(); }
543    bool readPredicate() const { return predicate; }
544    void setPredicate(bool val) { predicate = val; }
545
546    RegVal
547    readMiscRegNoEffect(RegIndex misc_reg) const override
548    {
549        return isa->readMiscRegNoEffect(misc_reg);
550    }
551
552    RegVal
553    readMiscReg(RegIndex misc_reg) override
554    {
555        return isa->readMiscReg(misc_reg, this);
556    }
557
558    void
559    setMiscRegNoEffect(RegIndex misc_reg, RegVal val) override
560    {
561        return isa->setMiscRegNoEffect(misc_reg, val);
562    }
563
564    void
565    setMiscReg(RegIndex misc_reg, RegVal val) override
566    {
567        return isa->setMiscReg(misc_reg, val, this);
568    }
569
570    RegId
571    flattenRegId(const RegId& regId) const override
572    {
573        return isa->flattenRegId(regId);
574    }
575
576    unsigned readStCondFailures() const override { return storeCondFailures; }
577
578    bool
579    readMemAccPredicate()
580    {
581        return memAccPredicate;
582    }
583
584    void
585    setMemAccPredicate(bool val)
586    {
587        memAccPredicate = val;
588    }
589
590    void
591    setStCondFailures(unsigned sc_failures) override
592    {
593        storeCondFailures = sc_failures;
594    }
595
596    Counter
597    readFuncExeInst() const override
598    {
599        return ThreadState::readFuncExeInst();
600    }
601
602    void
603    syscall(int64_t callnum, Fault *fault) override
604    {
605        process->syscall(callnum, this, fault);
606    }
607
608    RegVal readIntRegFlat(RegIndex idx) const override { return intRegs[idx]; }
609    void
610    setIntRegFlat(RegIndex idx, RegVal val) override
611    {
612        intRegs[idx] = val;
613    }
614
615    RegVal
616    readFloatRegFlat(RegIndex idx) const override
617    {
618        return floatRegs[idx];
619    }
620    void
621    setFloatRegFlat(RegIndex idx, RegVal val) override
622    {
623        floatRegs[idx] = val;
624    }
625
626    const VecRegContainer &
627    readVecRegFlat(RegIndex reg) const override
628    {
629        return vecRegs[reg];
630    }
631
632    VecRegContainer &
633    getWritableVecRegFlat(RegIndex reg) override
634    {
635        return vecRegs[reg];
636    }
637
638    void
639    setVecRegFlat(RegIndex reg, const VecRegContainer &val) override
640    {
641        vecRegs[reg] = val;
642    }
643
644    template <typename T>
645    VecLaneT<T, true>
646    readVecLaneFlat(RegIndex reg, int lId) const
647    {
648        return vecRegs[reg].laneView<T>(lId);
649    }
650
651    template <typename LD>
652    void
653    setVecLaneFlat(RegIndex reg, int lId, const LD &val)
654    {
655        vecRegs[reg].laneView<typename LD::UnderlyingType>(lId) = val;
656    }
657
658    const VecElem &
659    readVecElemFlat(RegIndex reg, const ElemIndex &elemIndex) const override
660    {
661        return vecRegs[reg].as<TheISA::VecElem>()[elemIndex];
662    }
663
664    void
665    setVecElemFlat(RegIndex reg, const ElemIndex &elemIndex,
666                   const VecElem &val) override
667    {
668        vecRegs[reg].as<TheISA::VecElem>()[elemIndex] = val;
669    }
670
671    const VecPredRegContainer &
672    readVecPredRegFlat(RegIndex reg) const override
673    {
674        return vecPredRegs[reg];
675    }
676
677    VecPredRegContainer &
678    getWritableVecPredRegFlat(RegIndex reg) override
679    {
680        return vecPredRegs[reg];
681    }
682
683    void
684    setVecPredRegFlat(RegIndex reg, const VecPredRegContainer &val) override
685    {
686        vecPredRegs[reg] = val;
687    }
688
689#ifdef ISA_HAS_CC_REGS
690    RegVal readCCRegFlat(RegIndex idx) const override { return ccRegs[idx]; }
691    void setCCRegFlat(RegIndex idx, RegVal val) override { ccRegs[idx] = val; }
692#else
693    RegVal
694    readCCRegFlat(RegIndex idx) const override
695    {
696        panic("readCCRegFlat w/no CC regs!\n");
697    }
698
699    void
700    setCCRegFlat(RegIndex idx, RegVal val) override
701    {
702        panic("setCCRegFlat w/no CC regs!\n");
703    }
704#endif
705};
706
707
708#endif // __CPU_CPU_EXEC_CONTEXT_HH__
709