// Todo: // Add a couple of the branch fields to DynInst. Figure out where DynInst // should try to compute the target of a PC-relative branch. Try to avoid // having so many returns within the code. // Fix up squashing too, as it's too // dependent upon the iew stage continually telling it to squash. #ifndef __SIMPLE_DECODE_HH__ #define __SIMPLE_DECODE_HH__ #include //Will want to include: time buffer, structs, #include "base/timebuf.hh" #include "cpu/beta_cpu/comm.hh" using namespace std; template class SimpleDecode { private: // Typedefs from the Impl. typedef typename Impl::ISA ISA; typedef typename Impl::DynInst DynInst; typedef typename Impl::FullCPU FullCPU; typedef typename Impl::Params Params; typedef typename Impl::FetchStruct FetchStruct; typedef typename Impl::DecodeStruct DecodeStruct; typedef typename Impl::TimeStruct TimeStruct; // Typedefs from the ISA. typedef typename ISA::Addr Addr; public: // The only time decode will become blocked is if dispatch becomes // blocked, which means IQ or ROB is probably full. enum Status { Running, Idle, Squashing, Blocked, Unblocking }; private: // May eventually need statuses on a per thread basis. Status _status; public: SimpleDecode(Params ¶ms); void setCPU(FullCPU *cpu_ptr); void setTimeBuffer(TimeBuffer *tb_ptr); void setDecodeQueue(TimeBuffer *dq_ptr); void setFetchQueue(TimeBuffer *fq_ptr); void tick(); void decode(); // Might want to make squash a friend function. void squash(); private: void block(); inline void unblock(); void squash(DynInst *inst); // Interfaces to objects outside of decode. /** CPU interface. */ FullCPU *cpu; /** Time buffer interface. */ TimeBuffer *timeBuffer; /** Wire to get rename's output from backwards time buffer. */ typename TimeBuffer::wire fromRename; /** Wire to get iew's information from backwards time buffer. */ typename TimeBuffer::wire fromIEW; /** Wire to get commit's information from backwards time buffer. */ typename TimeBuffer::wire fromCommit; /** Wire to write information heading to previous stages. */ // Might not be the best name as not only fetch will read it. typename TimeBuffer::wire toFetch; /** Decode instruction queue. */ TimeBuffer *decodeQueue; /** Wire used to write any information heading to rename. */ typename TimeBuffer::wire toRename; /** Fetch instruction queue interface. */ TimeBuffer *fetchQueue; /** Wire to get fetch's output from fetch queue. */ typename TimeBuffer::wire fromFetch; /** Skid buffer between fetch and decode. */ queue skidBuffer; private: //Consider making these unsigned to avoid any confusion. /** Rename to decode delay, in ticks. */ unsigned renameToDecodeDelay; /** IEW to decode delay, in ticks. */ unsigned iewToDecodeDelay; /** Commit to decode delay, in ticks. */ unsigned commitToDecodeDelay; /** Fetch to decode delay, in ticks. */ unsigned fetchToDecodeDelay; /** The width of decode, in instructions. */ unsigned decodeWidth; }; #endif // __SIMPLE_DECODE_HH__