rob.hh revision 2665
11689SN/A/*
21689SN/A * Copyright (c) 2004-2005 The Regents of The University of Michigan
31689SN/A * All rights reserved.
41689SN/A *
51689SN/A * Redistribution and use in source and binary forms, with or without
61689SN/A * modification, are permitted provided that the following conditions are
71689SN/A * met: redistributions of source code must retain the above copyright
81689SN/A * notice, this list of conditions and the following disclaimer;
91689SN/A * redistributions in binary form must reproduce the above copyright
101689SN/A * notice, this list of conditions and the following disclaimer in the
111689SN/A * documentation and/or other materials provided with the distribution;
121689SN/A * neither the name of the copyright holders nor the names of its
131689SN/A * contributors may be used to endorse or promote products derived from
141689SN/A * this software without specific prior written permission.
151689SN/A *
161689SN/A * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
171689SN/A * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
181689SN/A * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
191689SN/A * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
201689SN/A * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
211689SN/A * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
221689SN/A * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
231689SN/A * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
241689SN/A * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
251689SN/A * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
261689SN/A * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
272665Ssaidi@eecs.umich.edu *
282665Ssaidi@eecs.umich.edu * Authors: Kevin Lim
291689SN/A */
301689SN/A
311060SN/A// Todo: Probably add in support for scheduling events (more than one as
321060SN/A// well) on the case of the ROB being empty or full.  Considering tracking
331060SN/A// free entries instead of insts in ROB.  Differentiate between squashing
341060SN/A// all instructions after the instruction, and all instructions after *and*
351060SN/A// including that instruction.
361060SN/A
371755SN/A#ifndef __CPU_O3_CPU_ROB_HH__
381755SN/A#define __CPU_O3_CPU_ROB_HH__
391060SN/A
401461SN/A#include <utility>
411461SN/A#include <vector>
421060SN/A
431060SN/A/**
441060SN/A * ROB class.  Uses the instruction list that exists within the CPU to
451061SN/A * represent the ROB.  This class doesn't contain that list, but instead
461061SN/A * a pointer to the CPU to get access to the list.  The ROB, in this first
471061SN/A * implementation, is largely what drives squashing.
481060SN/A */
491061SN/Atemplate <class Impl>
501060SN/Aclass ROB
511060SN/A{
522107SN/A  protected:
532107SN/A    typedef TheISA::RegIndex RegIndex;
541060SN/A  public:
551060SN/A    //Typedefs from the Impl.
561060SN/A    typedef typename Impl::FullCPU FullCPU;
571061SN/A    typedef typename Impl::DynInstPtr DynInstPtr;
581060SN/A
591461SN/A    typedef std::pair<RegIndex, PhysRegIndex> UnmapInfo_t;
601061SN/A    typedef typename list<DynInstPtr>::iterator InstIt_t;
611060SN/A
621060SN/A  public:
631060SN/A    /** ROB constructor.
641763SN/A     *  @param _numEntries Number of entries in ROB.
651763SN/A     *  @param _squashWidth Number of instructions that can be squashed in a
661060SN/A     *                       single cycle.
671060SN/A     */
681060SN/A    ROB(unsigned _numEntries, unsigned _squashWidth);
691060SN/A
701060SN/A    /** Function to set the CPU pointer, necessary due to which object the ROB
711060SN/A     *  is created within.
721763SN/A     *  @param cpu_ptr Pointer to the implementation specific full CPU object.
731060SN/A     */
741060SN/A    void setCPU(FullCPU *cpu_ptr);
751060SN/A
761060SN/A    /** Function to insert an instruction into the ROB.  The parameter inst is
771060SN/A     *  not truly required, but is useful for checking correctness.  Note
781060SN/A     *  that whatever calls this function must ensure that there is enough
791060SN/A     *  space within the ROB for the new instruction.
801763SN/A     *  @param inst The instruction being inserted into the ROB.
811060SN/A     *  @todo Remove the parameter once correctness is ensured.
821060SN/A     */
831061SN/A    void insertInst(DynInstPtr &inst);
841060SN/A
851060SN/A    /** Returns pointer to the head instruction within the ROB.  There is
861060SN/A     *  no guarantee as to the return value if the ROB is empty.
871060SN/A     *  @retval Pointer to the DynInst that is at the head of the ROB.
881060SN/A     */
891061SN/A    DynInstPtr readHeadInst() { return cpu->instList.front(); }
901060SN/A
911061SN/A    DynInstPtr readTailInst() { return (*tail); }
921060SN/A
931060SN/A    void retireHead();
941060SN/A
951060SN/A    bool isHeadReady();
961060SN/A
971060SN/A    unsigned numFreeEntries();
981060SN/A
991060SN/A    bool isFull()
1001060SN/A    { return numInstsInROB == numEntries; }
1011060SN/A
1021060SN/A    bool isEmpty()
1031060SN/A    { return numInstsInROB == 0; }
1041060SN/A
1051060SN/A    void doSquash();
1061060SN/A
1071060SN/A    void squash(InstSeqNum squash_num);
1081060SN/A
1091060SN/A    uint64_t readHeadPC();
1101060SN/A
1111060SN/A    uint64_t readHeadNextPC();
1121060SN/A
1131060SN/A    InstSeqNum readHeadSeqNum();
1141060SN/A
1151060SN/A    uint64_t readTailPC();
1161060SN/A
1171060SN/A    InstSeqNum readTailSeqNum();
1181060SN/A
1191060SN/A    /** Checks if the ROB is still in the process of squashing instructions.
1201060SN/A     *  @retval Whether or not the ROB is done squashing.
1211060SN/A     */
1221060SN/A    bool isDoneSquashing() const { return doneSquashing; }
1231060SN/A
1241060SN/A    /** This is more of a debugging function than anything.  Use
1251060SN/A     *  numInstsInROB to get the instructions in the ROB unless you are
1261060SN/A     *  double checking that variable.
1271060SN/A     */
1281060SN/A    int countInsts();
1291060SN/A
1301060SN/A  private:
1311060SN/A
1321060SN/A    /** Pointer to the CPU. */
1331060SN/A    FullCPU *cpu;
1341060SN/A
1351061SN/A    /** Number of instructions in the ROB. */
1361060SN/A    unsigned numEntries;
1371060SN/A
1381060SN/A    /** Number of instructions that can be squashed in a single cycle. */
1391060SN/A    unsigned squashWidth;
1401060SN/A
1411061SN/A    /** Iterator pointing to the instruction which is the last instruction
1421061SN/A     *  in the ROB.  This may at times be invalid (ie when the ROB is empty),
1431061SN/A     *  however it should never be incorrect.
1441061SN/A     */
1451061SN/A    InstIt_t tail;
1461060SN/A
1471061SN/A    /** Iterator used for walking through the list of instructions when
1481061SN/A     *  squashing.  Used so that there is persistent state between cycles;
1491061SN/A     *  when squashing, the instructions are marked as squashed but not
1501061SN/A     *  immediately removed, meaning the tail iterator remains the same before
1511061SN/A     *  and after a squash.
1521061SN/A     *  This will always be set to cpu->instList.end() if it is invalid.
1531061SN/A     */
1541061SN/A    InstIt_t squashIt;
1551060SN/A
1561061SN/A    /** Number of instructions in the ROB. */
1571060SN/A    int numInstsInROB;
1581060SN/A
1591060SN/A    /** The sequence number of the squashed instruction. */
1601060SN/A    InstSeqNum squashedSeqNum;
1611060SN/A
1621060SN/A    /** Is the ROB done squashing. */
1631060SN/A    bool doneSquashing;
1641060SN/A};
1651060SN/A
1661755SN/A#endif //__CPU_O3_CPU_ROB_HH__
167