cpu.hh revision 6022
1/*
2 * Copyright (c) 2004-2005 The Regents of The University of Michigan
3 * All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions are
7 * met: redistributions of source code must retain the above copyright
8 * notice, this list of conditions and the following disclaimer;
9 * redistributions in binary form must reproduce the above copyright
10 * notice, this list of conditions and the following disclaimer in the
11 * documentation and/or other materials provided with the distribution;
12 * neither the name of the copyright holders nor the names of its
13 * contributors may be used to endorse or promote products derived from
14 * this software without specific prior written permission.
15 *
16 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
17 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
18 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
19 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
20 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
21 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
22 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
23 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
24 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
25 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
26 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27 *
28 * Authors: Kevin Lim
29 *          Korey Sewell
30 */
31
32#ifndef __CPU_O3_CPU_HH__
33#define __CPU_O3_CPU_HH__
34
35#include <iostream>
36#include <list>
37#include <queue>
38#include <set>
39#include <vector>
40
41#include "arch/types.hh"
42#include "base/statistics.hh"
43#include "base/timebuf.hh"
44#include "config/full_system.hh"
45#include "config/use_checker.hh"
46#include "cpu/activity.hh"
47#include "cpu/base.hh"
48#include "cpu/simple_thread.hh"
49#include "cpu/o3/comm.hh"
50#include "cpu/o3/cpu_policy.hh"
51#include "cpu/o3/scoreboard.hh"
52#include "cpu/o3/thread_state.hh"
53//#include "cpu/o3/thread_context.hh"
54#include "sim/process.hh"
55
56#include "params/DerivO3CPU.hh"
57
58template <class>
59class Checker;
60class ThreadContext;
61template <class>
62class O3ThreadContext;
63
64class Checkpoint;
65class MemObject;
66class Process;
67
68class BaseCPUParams;
69
70class BaseO3CPU : public BaseCPU
71{
72    //Stuff that's pretty ISA independent will go here.
73  public:
74    BaseO3CPU(BaseCPUParams *params);
75
76    void regStats();
77};
78
79/**
80 * FullO3CPU class, has each of the stages (fetch through commit)
81 * within it, as well as all of the time buffers between stages.  The
82 * tick() function for the CPU is defined here.
83 */
84template <class Impl>
85class FullO3CPU : public BaseO3CPU
86{
87  public:
88    // Typedefs from the Impl here.
89    typedef typename Impl::CPUPol CPUPolicy;
90    typedef typename Impl::DynInstPtr DynInstPtr;
91    typedef typename Impl::O3CPU O3CPU;
92
93    typedef O3ThreadState<Impl> ImplState;
94    typedef O3ThreadState<Impl> Thread;
95
96    typedef typename std::list<DynInstPtr>::iterator ListIt;
97
98    friend class O3ThreadContext<Impl>;
99
100  public:
101    enum Status {
102        Running,
103        Idle,
104        Halted,
105        Blocked,
106        SwitchedOut
107    };
108
109    TheISA::TLB * itb;
110    TheISA::TLB * dtb;
111
112    /** Overall CPU status. */
113    Status _status;
114
115    /** Per-thread status in CPU, used for SMT.  */
116    Status _threadStatus[Impl::MaxThreads];
117
118  private:
119    class TickEvent : public Event
120    {
121      private:
122        /** Pointer to the CPU. */
123        FullO3CPU<Impl> *cpu;
124
125      public:
126        /** Constructs a tick event. */
127        TickEvent(FullO3CPU<Impl> *c);
128
129        /** Processes a tick event, calling tick() on the CPU. */
130        void process();
131        /** Returns the description of the tick event. */
132        const char *description() const;
133    };
134
135    /** The tick event used for scheduling CPU ticks. */
136    TickEvent tickEvent;
137
138    /** Schedule tick event, regardless of its current state. */
139    void scheduleTickEvent(int delay)
140    {
141        if (tickEvent.squashed())
142            reschedule(tickEvent, nextCycle(curTick + ticks(delay)));
143        else if (!tickEvent.scheduled())
144            schedule(tickEvent, nextCycle(curTick + ticks(delay)));
145    }
146
147    /** Unschedule tick event, regardless of its current state. */
148    void unscheduleTickEvent()
149    {
150        if (tickEvent.scheduled())
151            tickEvent.squash();
152    }
153
154    class ActivateThreadEvent : public Event
155    {
156      private:
157        /** Number of Thread to Activate */
158        int tid;
159
160        /** Pointer to the CPU. */
161        FullO3CPU<Impl> *cpu;
162
163      public:
164        /** Constructs the event. */
165        ActivateThreadEvent();
166
167        /** Initialize Event */
168        void init(int thread_num, FullO3CPU<Impl> *thread_cpu);
169
170        /** Processes the event, calling activateThread() on the CPU. */
171        void process();
172
173        /** Returns the description of the event. */
174        const char *description() const;
175    };
176
177    /** Schedule thread to activate , regardless of its current state. */
178    void scheduleActivateThreadEvent(int tid, int delay)
179    {
180        // Schedule thread to activate, regardless of its current state.
181        if (activateThreadEvent[tid].squashed())
182            reschedule(activateThreadEvent[tid],
183                nextCycle(curTick + ticks(delay)));
184        else if (!activateThreadEvent[tid].scheduled())
185            schedule(activateThreadEvent[tid],
186                nextCycle(curTick + ticks(delay)));
187    }
188
189    /** Unschedule actiavte thread event, regardless of its current state. */
190    void unscheduleActivateThreadEvent(int tid)
191    {
192        if (activateThreadEvent[tid].scheduled())
193            activateThreadEvent[tid].squash();
194    }
195
196    /** The tick event used for scheduling CPU ticks. */
197    ActivateThreadEvent activateThreadEvent[Impl::MaxThreads];
198
199    class DeallocateContextEvent : public Event
200    {
201      private:
202        /** Number of Thread to deactivate */
203        int tid;
204
205        /** Should the thread be removed from the CPU? */
206        bool remove;
207
208        /** Pointer to the CPU. */
209        FullO3CPU<Impl> *cpu;
210
211      public:
212        /** Constructs the event. */
213        DeallocateContextEvent();
214
215        /** Initialize Event */
216        void init(int thread_num, FullO3CPU<Impl> *thread_cpu);
217
218        /** Processes the event, calling activateThread() on the CPU. */
219        void process();
220
221        /** Sets whether the thread should also be removed from the CPU. */
222        void setRemove(bool _remove) { remove = _remove; }
223
224        /** Returns the description of the event. */
225        const char *description() const;
226    };
227
228    /** Schedule cpu to deallocate thread context.*/
229    void scheduleDeallocateContextEvent(int tid, bool remove, int delay)
230    {
231        // Schedule thread to activate, regardless of its current state.
232        if (deallocateContextEvent[tid].squashed())
233            reschedule(deallocateContextEvent[tid],
234                nextCycle(curTick + ticks(delay)));
235        else if (!deallocateContextEvent[tid].scheduled())
236            schedule(deallocateContextEvent[tid],
237                nextCycle(curTick + ticks(delay)));
238    }
239
240    /** Unschedule thread deallocation in CPU */
241    void unscheduleDeallocateContextEvent(int tid)
242    {
243        if (deallocateContextEvent[tid].scheduled())
244            deallocateContextEvent[tid].squash();
245    }
246
247    /** The tick event used for scheduling CPU ticks. */
248    DeallocateContextEvent deallocateContextEvent[Impl::MaxThreads];
249
250  public:
251    /** Constructs a CPU with the given parameters. */
252    FullO3CPU(DerivO3CPUParams *params);
253    /** Destructor. */
254    ~FullO3CPU();
255
256    /** Registers statistics. */
257    void regStats();
258
259    void demapPage(Addr vaddr, uint64_t asn)
260    {
261        this->itb->demapPage(vaddr, asn);
262        this->dtb->demapPage(vaddr, asn);
263    }
264
265    void demapInstPage(Addr vaddr, uint64_t asn)
266    {
267        this->itb->demapPage(vaddr, asn);
268    }
269
270    void demapDataPage(Addr vaddr, uint64_t asn)
271    {
272        this->dtb->demapPage(vaddr, asn);
273    }
274
275    /** Returns a specific port. */
276    Port *getPort(const std::string &if_name, int idx);
277
278    /** Ticks CPU, calling tick() on each stage, and checking the overall
279     *  activity to see if the CPU should deschedule itself.
280     */
281    void tick();
282
283    /** Initialize the CPU */
284    void init();
285
286    /** Returns the Number of Active Threads in the CPU */
287    int numActiveThreads()
288    { return activeThreads.size(); }
289
290    /** Add Thread to Active Threads List */
291    void activateThread(unsigned tid);
292
293    /** Remove Thread from Active Threads List */
294    void deactivateThread(unsigned tid);
295
296    /** Setup CPU to insert a thread's context */
297    void insertThread(unsigned tid);
298
299    /** Remove all of a thread's context from CPU */
300    void removeThread(unsigned tid);
301
302    /** Count the Total Instructions Committed in the CPU. */
303    virtual Counter totalInstructions() const
304    {
305        Counter total(0);
306
307        for (int i=0; i < thread.size(); i++)
308            total += thread[i]->numInst;
309
310        return total;
311    }
312
313    /** Add Thread to Active Threads List. */
314    void activateContext(int tid, int delay);
315
316    /** Remove Thread from Active Threads List */
317    void suspendContext(int tid);
318
319    /** Remove Thread from Active Threads List &&
320     *  Possibly Remove Thread Context from CPU.
321     */
322    bool deallocateContext(int tid, bool remove, int delay = 1);
323
324    /** Remove Thread from Active Threads List &&
325     *  Remove Thread Context from CPU.
326     */
327    void haltContext(int tid);
328
329    /** Activate a Thread When CPU Resources are Available. */
330    void activateWhenReady(int tid);
331
332    /** Add or Remove a Thread Context in the CPU. */
333    void doContextSwitch();
334
335    /** Update The Order In Which We Process Threads. */
336    void updateThreadPriority();
337
338    /** Serialize state. */
339    virtual void serialize(std::ostream &os);
340
341    /** Unserialize from a checkpoint. */
342    virtual void unserialize(Checkpoint *cp, const std::string &section);
343
344  public:
345#if !FULL_SYSTEM
346    /** Executes a syscall.
347     * @todo: Determine if this needs to be virtual.
348     */
349    void syscall(int64_t callnum, int tid);
350#endif
351
352    /** Starts draining the CPU's pipeline of all instructions in
353     * order to stop all memory accesses. */
354    virtual unsigned int drain(Event *drain_event);
355
356    /** Resumes execution after a drain. */
357    virtual void resume();
358
359    /** Signals to this CPU that a stage has completed switching out. */
360    void signalDrained();
361
362    /** Switches out this CPU. */
363    virtual void switchOut();
364
365    /** Takes over from another CPU. */
366    virtual void takeOverFrom(BaseCPU *oldCPU);
367
368    /** Get the current instruction sequence number, and increment it. */
369    InstSeqNum getAndIncrementInstSeq()
370    { return globalSeqNum++; }
371
372    /** Traps to handle given fault. */
373    void trap(Fault fault, unsigned tid);
374
375#if FULL_SYSTEM
376    /** HW return from error interrupt. */
377    Fault hwrei(unsigned tid);
378
379    bool simPalCheck(int palFunc, unsigned tid);
380
381    /** Returns the Fault for any valid interrupt. */
382    Fault getInterrupts();
383
384    /** Processes any an interrupt fault. */
385    void processInterrupts(Fault interrupt);
386
387    /** Halts the CPU. */
388    void halt() { panic("Halt not implemented!\n"); }
389
390    /** Update the Virt and Phys ports of all ThreadContexts to
391     * reflect change in memory connections. */
392    void updateMemPorts();
393
394    /** Check if this address is a valid instruction address. */
395    bool validInstAddr(Addr addr) { return true; }
396
397    /** Check if this address is a valid data address. */
398    bool validDataAddr(Addr addr) { return true; }
399
400    /** Get instruction asid. */
401    int getInstAsid(unsigned tid)
402    { return regFile.miscRegs[tid].getInstAsid(); }
403
404    /** Get data asid. */
405    int getDataAsid(unsigned tid)
406    { return regFile.miscRegs[tid].getDataAsid(); }
407#else
408    /** Get instruction asid. */
409    int getInstAsid(unsigned tid)
410    { return thread[tid]->getInstAsid(); }
411
412    /** Get data asid. */
413    int getDataAsid(unsigned tid)
414    { return thread[tid]->getDataAsid(); }
415
416#endif
417
418    /** Register accessors.  Index refers to the physical register index. */
419
420    /** Reads a miscellaneous register. */
421    TheISA::MiscReg readMiscRegNoEffect(int misc_reg, unsigned tid);
422
423    /** Reads a misc. register, including any side effects the read
424     * might have as defined by the architecture.
425     */
426    TheISA::MiscReg readMiscReg(int misc_reg, unsigned tid);
427
428    /** Sets a miscellaneous register. */
429    void setMiscRegNoEffect(int misc_reg, const TheISA::MiscReg &val, unsigned tid);
430
431    /** Sets a misc. register, including any side effects the write
432     * might have as defined by the architecture.
433     */
434    void setMiscReg(int misc_reg, const TheISA::MiscReg &val,
435            unsigned tid);
436
437    uint64_t readIntReg(int reg_idx);
438
439    TheISA::FloatReg readFloatReg(int reg_idx);
440
441    TheISA::FloatReg readFloatReg(int reg_idx, int width);
442
443    TheISA::FloatRegBits readFloatRegBits(int reg_idx);
444
445    TheISA::FloatRegBits readFloatRegBits(int reg_idx, int width);
446
447    void setIntReg(int reg_idx, uint64_t val);
448
449    void setFloatReg(int reg_idx, TheISA::FloatReg val);
450
451    void setFloatReg(int reg_idx, TheISA::FloatReg val, int width);
452
453    void setFloatRegBits(int reg_idx, TheISA::FloatRegBits val);
454
455    void setFloatRegBits(int reg_idx, TheISA::FloatRegBits val, int width);
456
457    uint64_t readArchIntReg(int reg_idx, unsigned tid);
458
459    float readArchFloatRegSingle(int reg_idx, unsigned tid);
460
461    double readArchFloatRegDouble(int reg_idx, unsigned tid);
462
463    uint64_t readArchFloatRegInt(int reg_idx, unsigned tid);
464
465    /** Architectural register accessors.  Looks up in the commit
466     * rename table to obtain the true physical index of the
467     * architected register first, then accesses that physical
468     * register.
469     */
470    void setArchIntReg(int reg_idx, uint64_t val, unsigned tid);
471
472    void setArchFloatRegSingle(int reg_idx, float val, unsigned tid);
473
474    void setArchFloatRegDouble(int reg_idx, double val, unsigned tid);
475
476    void setArchFloatRegInt(int reg_idx, uint64_t val, unsigned tid);
477
478    /** Reads the commit PC of a specific thread. */
479    Addr readPC(unsigned tid);
480
481    /** Sets the commit PC of a specific thread. */
482    void setPC(Addr new_PC, unsigned tid);
483
484    /** Reads the commit micro PC of a specific thread. */
485    Addr readMicroPC(unsigned tid);
486
487    /** Sets the commmit micro PC of a specific thread. */
488    void setMicroPC(Addr new_microPC, unsigned tid);
489
490    /** Reads the next PC of a specific thread. */
491    Addr readNextPC(unsigned tid);
492
493    /** Sets the next PC of a specific thread. */
494    void setNextPC(Addr val, unsigned tid);
495
496    /** Reads the next NPC of a specific thread. */
497    Addr readNextNPC(unsigned tid);
498
499    /** Sets the next NPC of a specific thread. */
500    void setNextNPC(Addr val, unsigned tid);
501
502    /** Reads the commit next micro PC of a specific thread. */
503    Addr readNextMicroPC(unsigned tid);
504
505    /** Sets the commit next micro PC of a specific thread. */
506    void setNextMicroPC(Addr val, unsigned tid);
507
508    /** Initiates a squash of all in-flight instructions for a given
509     * thread.  The source of the squash is an external update of
510     * state through the TC.
511     */
512    void squashFromTC(unsigned tid);
513
514    /** Function to add instruction onto the head of the list of the
515     *  instructions.  Used when new instructions are fetched.
516     */
517    ListIt addInst(DynInstPtr &inst);
518
519    /** Function to tell the CPU that an instruction has completed. */
520    void instDone(unsigned tid);
521
522    /** Add Instructions to the CPU Remove List*/
523    void addToRemoveList(DynInstPtr &inst);
524
525    /** Remove an instruction from the front end of the list.  There's
526     *  no restriction on location of the instruction.
527     */
528    void removeFrontInst(DynInstPtr &inst);
529
530    /** Remove all instructions that are not currently in the ROB.
531     *  There's also an option to not squash delay slot instructions.*/
532    void removeInstsNotInROB(unsigned tid);
533
534    /** Remove all instructions younger than the given sequence number. */
535    void removeInstsUntil(const InstSeqNum &seq_num,unsigned tid);
536
537    /** Removes the instruction pointed to by the iterator. */
538    inline void squashInstIt(const ListIt &instIt, const unsigned &tid);
539
540    /** Cleans up all instructions on the remove list. */
541    void cleanUpRemovedInsts();
542
543    /** Debug function to print all instructions on the list. */
544    void dumpInsts();
545
546  public:
547#ifndef NDEBUG
548    /** Count of total number of dynamic instructions in flight. */
549    int instcount;
550#endif
551
552    /** List of all the instructions in flight. */
553    std::list<DynInstPtr> instList;
554
555    /** List of all the instructions that will be removed at the end of this
556     *  cycle.
557     */
558    std::queue<ListIt> removeList;
559
560#ifdef DEBUG
561    /** Debug structure to keep track of the sequence numbers still in
562     * flight.
563     */
564    std::set<InstSeqNum> snList;
565#endif
566
567    /** Records if instructions need to be removed this cycle due to
568     *  being retired or squashed.
569     */
570    bool removeInstsThisCycle;
571
572  protected:
573    /** The fetch stage. */
574    typename CPUPolicy::Fetch fetch;
575
576    /** The decode stage. */
577    typename CPUPolicy::Decode decode;
578
579    /** The dispatch stage. */
580    typename CPUPolicy::Rename rename;
581
582    /** The issue/execute/writeback stages. */
583    typename CPUPolicy::IEW iew;
584
585    /** The commit stage. */
586    typename CPUPolicy::Commit commit;
587
588    /** The register file. */
589    typename CPUPolicy::RegFile regFile;
590
591    /** The free list. */
592    typename CPUPolicy::FreeList freeList;
593
594    /** The rename map. */
595    typename CPUPolicy::RenameMap renameMap[Impl::MaxThreads];
596
597    /** The commit rename map. */
598    typename CPUPolicy::RenameMap commitRenameMap[Impl::MaxThreads];
599
600    /** The re-order buffer. */
601    typename CPUPolicy::ROB rob;
602
603    /** Active Threads List */
604    std::list<unsigned> activeThreads;
605
606    /** Integer Register Scoreboard */
607    Scoreboard scoreboard;
608
609  public:
610    /** Enum to give each stage a specific index, so when calling
611     *  activateStage() or deactivateStage(), they can specify which stage
612     *  is being activated/deactivated.
613     */
614    enum StageIdx {
615        FetchIdx,
616        DecodeIdx,
617        RenameIdx,
618        IEWIdx,
619        CommitIdx,
620        NumStages };
621
622    /** Typedefs from the Impl to get the structs that each of the
623     *  time buffers should use.
624     */
625    typedef typename CPUPolicy::TimeStruct TimeStruct;
626
627    typedef typename CPUPolicy::FetchStruct FetchStruct;
628
629    typedef typename CPUPolicy::DecodeStruct DecodeStruct;
630
631    typedef typename CPUPolicy::RenameStruct RenameStruct;
632
633    typedef typename CPUPolicy::IEWStruct IEWStruct;
634
635    /** The main time buffer to do backwards communication. */
636    TimeBuffer<TimeStruct> timeBuffer;
637
638    /** The fetch stage's instruction queue. */
639    TimeBuffer<FetchStruct> fetchQueue;
640
641    /** The decode stage's instruction queue. */
642    TimeBuffer<DecodeStruct> decodeQueue;
643
644    /** The rename stage's instruction queue. */
645    TimeBuffer<RenameStruct> renameQueue;
646
647    /** The IEW stage's instruction queue. */
648    TimeBuffer<IEWStruct> iewQueue;
649
650  private:
651    /** The activity recorder; used to tell if the CPU has any
652     * activity remaining or if it can go to idle and deschedule
653     * itself.
654     */
655    ActivityRecorder activityRec;
656
657  public:
658    /** Records that there was time buffer activity this cycle. */
659    void activityThisCycle() { activityRec.activity(); }
660
661    /** Changes a stage's status to active within the activity recorder. */
662    void activateStage(const StageIdx idx)
663    { activityRec.activateStage(idx); }
664
665    /** Changes a stage's status to inactive within the activity recorder. */
666    void deactivateStage(const StageIdx idx)
667    { activityRec.deactivateStage(idx); }
668
669    /** Wakes the CPU, rescheduling the CPU if it's not already active. */
670    void wakeCPU();
671
672#if FULL_SYSTEM
673    virtual void wakeup();
674#endif
675
676    /** Gets a free thread id. Use if thread ids change across system. */
677    int getFreeTid();
678
679  public:
680    /** Returns a pointer to a thread context. */
681    ThreadContext *tcBase(unsigned tid)
682    {
683        return thread[tid]->getTC();
684    }
685
686    /** The global sequence number counter. */
687    InstSeqNum globalSeqNum;//[Impl::MaxThreads];
688
689#if USE_CHECKER
690    /** Pointer to the checker, which can dynamically verify
691     * instruction results at run time.  This can be set to NULL if it
692     * is not being used.
693     */
694    Checker<DynInstPtr> *checker;
695#endif
696
697#if FULL_SYSTEM
698    /** Pointer to the system. */
699    System *system;
700
701    /** Pointer to physical memory. */
702    PhysicalMemory *physmem;
703#endif
704
705    /** Event to call process() on once draining has completed. */
706    Event *drainEvent;
707
708    /** Counter of how many stages have completed draining. */
709    int drainCount;
710
711    /** Pointers to all of the threads in the CPU. */
712    std::vector<Thread *> thread;
713
714    /** Whether or not the CPU should defer its registration. */
715    bool deferRegistration;
716
717    /** Is there a context switch pending? */
718    bool contextSwitch;
719
720    /** Threads Scheduled to Enter CPU */
721    std::list<int> cpuWaitList;
722
723    /** The cycle that the CPU was last running, used for statistics. */
724    Tick lastRunningCycle;
725
726    /** The cycle that the CPU was last activated by a new thread*/
727    Tick lastActivatedCycle;
728
729    /** Number of Threads CPU can process */
730    unsigned numThreads;
731
732    /** Mapping for system thread id to cpu id */
733    std::map<unsigned,unsigned> threadMap;
734
735    /** Available thread ids in the cpu*/
736    std::vector<unsigned> tids;
737
738    /** CPU read function, forwards read to LSQ. */
739    template <class T>
740    Fault read(RequestPtr &req, T &data, int load_idx)
741    {
742        return this->iew.ldstQueue.read(req, data, load_idx);
743    }
744
745    /** CPU write function, forwards write to LSQ. */
746    template <class T>
747    Fault write(RequestPtr &req, T &data, int store_idx)
748    {
749        return this->iew.ldstQueue.write(req, data, store_idx);
750    }
751
752    Addr lockAddr;
753
754    /** Temporary fix for the lock flag, works in the UP case. */
755    bool lockFlag;
756
757    /** Stat for total number of times the CPU is descheduled. */
758    Stats::Scalar timesIdled;
759    /** Stat for total number of cycles the CPU spends descheduled. */
760    Stats::Scalar idleCycles;
761    /** Stat for the number of committed instructions per thread. */
762    Stats::Vector committedInsts;
763    /** Stat for the total number of committed instructions. */
764    Stats::Scalar totalCommittedInsts;
765    /** Stat for the CPI per thread. */
766    Stats::Formula cpi;
767    /** Stat for the total CPI. */
768    Stats::Formula totalCpi;
769    /** Stat for the IPC per thread. */
770    Stats::Formula ipc;
771    /** Stat for the total IPC. */
772    Stats::Formula totalIpc;
773};
774
775#endif // __CPU_O3_CPU_HH__
776