1/* 2 * Copyright (c) 2013-2014 ARM Limited 3 * All rights reserved 4 * 5 * The license below extends only to copyright in the software and shall 6 * not be construed as granting a license to any other intellectual 7 * property including but not limited to intellectual property relating 8 * to a hardware implementation of the functionality of the software 9 * licensed hereunder. You may use the software subject to the license 10 * terms below provided that you ensure that this notice is replicated 11 * unmodified and in its entirety in all distributions of the software, 12 * modified or unmodified, in source code or in binary form. 13 * 14 * Redistribution and use in source and binary forms, with or without 15 * modification, are permitted provided that the following conditions are 16 * met: redistributions of source code must retain the above copyright 17 * notice, this list of conditions and the following disclaimer; 18 * redistributions in binary form must reproduce the above copyright 19 * notice, this list of conditions and the following disclaimer in the 20 * documentation and/or other materials provided with the distribution; 21 * neither the name of the copyright holders nor the names of its 22 * contributors may be used to endorse or promote products derived from 23 * this software without specific prior written permission. 24 * 25 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 26 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 27 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 28 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 29 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 30 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 31 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 32 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 33 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 34 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 35 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 36 * 37 * Authors: Andrew Bardsley 38 */ 39 40/** 41 * @file 42 * 43 * Execute function unit descriptions and pipeline implementations. 44 */ 45 46#ifndef __CPU_MINOR_FUNC_UNIT_HH__ 47#define __CPU_MINOR_FUNC_UNIT_HH__ 48 49#include "cpu/minor/buffers.hh" 50#include "cpu/minor/dyn_inst.hh" 51#include "cpu/func_unit.hh" 52#include "cpu/timing_expr.hh" 53#include "params/MinorFU.hh" 54#include "params/MinorFUPool.hh" 55#include "params/MinorOpClass.hh" 56#include "params/MinorOpClassSet.hh" 57#include "sim/clocked_object.hh" 58 59/** Boxing for MinorOpClass to get around a build problem with C++11 but 60 * also allow for future additions to op class checking */ 61class MinorOpClass : public SimObject 62{ 63 public: 64 OpClass opClass; 65 66 public: 67 MinorOpClass(const MinorOpClassParams *params) : 68 SimObject(params), 69 opClass(params->opClass) 70 { } 71}; 72 73/** Wrapper for a matchable set of op classes */ 74class MinorOpClassSet : public SimObject 75{ 76 public: 77 std::vector<MinorOpClass *> opClasses; 78 79 /** Convenience packing of opClasses into a bit vector for easier 80 * testing */ 81 std::vector<bool> capabilityList; 82 83 public: 84 MinorOpClassSet(const MinorOpClassSetParams *params); 85 86 public: 87 /** Does this set support the given op class */ 88 bool provides(OpClass op_class) { return capabilityList[op_class]; } 89}; 90 91/** Extra timing capability to allow individual ops to have their source 92 * register dependency latencies tweaked based on the ExtMachInst of the 93 * source instruction. 94 */ 95class MinorFUTiming: public SimObject 96{ 97 public: 98 /** Mask off the ExtMachInst of an instruction before comparing with 99 * match */ 100 uint64_t mask; 101 uint64_t match; 102 103 /** Textual description of the decode's purpose */ 104 std::string description; 105 106 /** If true, instructions matching this mask/match should *not* be 107 * issued in this FU */ 108 bool suppress; 109 110 /** Extra latency that the instruction should spend at the end of 111 * the pipeline */ 112 Cycles extraCommitLat; 113 TimingExpr *extraCommitLatExpr; 114 115 /** Extra delay that results should show in the scoreboard after 116 * leaving the pipeline. If set to Cycles(0) for memory references, 117 * an 'unpredictable' return time will be set in the scoreboard 118 * blocking following dependent instructions from issuing */ 119 Cycles extraAssumedLat; 120 121 /** Cycle offsets from the scoreboard delivery times of register values 122 * for each of this instruction's source registers (in srcRegs order). 123 * The offsets are subtracted from the scoreboard returnCycle times. 124 * For example, for an instruction type with 3 source registers, 125 * [2, 1, 2] will allow the instruction to issue upto 2 cycles early 126 * for dependencies on the 1st and 3rd register and upto 1 cycle early 127 * on the 2nd. */ 128 std::vector<Cycles> srcRegsRelativeLats; 129 130 /** Extra opClasses check (after the FU one) */ 131 MinorOpClassSet *opClasses; 132 133 public: 134 MinorFUTiming(const MinorFUTimingParams *params); 135 136 public: 137 /** Does the extra decode in this object support the given op class */ 138 bool provides(OpClass op_class) { return opClasses->provides(op_class); } 139}; 140 141/** A functional unit that can execute any of opClasses operations with a 142 * single op(eration)Lat(ency) and issueLat(ency) associated with the unit 143 * rather than each operation (as in src/FuncUnit). 144 * 145 * This is very similar to cpu/func_unit but replicated here to allow 146 * the Minor functional units to change without having to disturb the common 147 * definition. 148 */ 149class MinorFU : public SimObject 150{ 151 public: 152 MinorOpClassSet *opClasses; 153 154 /** Delay from issuing the operation, to it reaching the 155 * end of the associated pipeline */ 156 Cycles opLat; 157 158 /** Delay after issuing an operation before the next 159 * operation can be issued */ 160 Cycles issueLat; 161 162 /** FUs which this pipeline can't receive a forwarded (i.e. relative 163 * latency != 0) result from */ 164 std::vector<unsigned int> cantForwardFromFUIndices; 165 166 /** Extra timing info to give timings to individual ops */ 167 std::vector<MinorFUTiming *> timings; 168 169 public: 170 MinorFU(const MinorFUParams *params) : 171 SimObject(params), 172 opClasses(params->opClasses), 173 opLat(params->opLat), 174 issueLat(params->issueLat), 175 cantForwardFromFUIndices(params->cantForwardFromFUIndices), 176 timings(params->timings) 177 { } 178}; 179 180/** A collection of MinorFUs */ 181class MinorFUPool : public SimObject 182{ 183 public: 184 std::vector<MinorFU *> funcUnits; 185 186 public: 187 MinorFUPool(const MinorFUPoolParams *params) : 188 SimObject(params), 189 funcUnits(params->funcUnits) 190 { } 191}; 192 193namespace Minor 194{ 195 196/** Container class to box instructions in the FUs to make those 197 * queues have correct bubble behaviour when stepped */ 198class QueuedInst 199{ 200 public: 201 MinorDynInstPtr inst; 202 203 public: 204 QueuedInst(MinorDynInstPtr inst_ = MinorDynInst::bubble()) : 205 inst(inst_) 206 { } 207 208 public: 209 /** Report and bubble interfaces */ 210 void reportData(std::ostream &os) const; 211 bool isBubble() const { return inst->isBubble(); } 212 213 static QueuedInst bubble() 214 { return QueuedInst(MinorDynInst::bubble()); } 215}; 216 217/** Functional units have pipelines which stall when an inst gets to 218 * their ends allowing Execute::commit to pick up timing-completed insts 219 * when it feels like it */ 220typedef SelfStallingPipeline<QueuedInst, 221 ReportTraitsAdaptor<QueuedInst> > FUPipelineBase; 222 223/** A functional unit configured from a MinorFU object */ 224class FUPipeline : public FUPipelineBase, public FuncUnit 225{ 226 public: 227 /** Functional unit description that this pipeline implements */ 228 const MinorFU &description; 229 230 /** An FUPipeline needs access to curCycle, use this timing source */ 231 ClockedObject &timeSource; 232 233 /** Set of operation classes supported by this FU */ 234 std::bitset<Num_OpClasses> capabilityList; 235 236 /** FUs which this pipeline can't receive a forwarded (i.e. relative 237 * latency != 0) result from */ 238 std::vector<bool> cantForwardFromFUIndices; 239 240 public: 241 /** When can a new instruction be inserted into the pipeline? This is 242 * an absolute cycle time unless it is 0 in which case the an 243 * instruction can be pushed straightaway */ 244 Cycles nextInsertCycle; 245 246 public: 247 FUPipeline(const std::string &name, const MinorFU &description_, 248 ClockedObject &timeSource_); 249 250 public: 251 /** How many cycles must from curCycle before insertion into the 252 * pipeline is allowed */ 253 Cycles cyclesBeforeInsert(); 254 255 /** Can an instruction be inserted now? */ 256 bool canInsert() const; 257 258 /** Find the extra timing information for this instruction. Returns 259 * NULL if no decode info. is found */ 260 MinorFUTiming *findTiming(const StaticInstPtr &inst); 261 262 /** Step the pipeline. Allow multiple steps? */ 263 void advance(); 264}; 265 266} 267 268#endif /* __CPU_MINOR_FUNC_UNIT_HH__ */ 269