Ejemplo n.º 1
0
void computeProcResourceMasks(const MCSchedModel &SM,
                              SmallVectorImpl<uint64_t> &Masks) {
  unsigned ProcResourceID = 0;

  // Create a unique bitmask for every processor resource unit.
  // Skip resource at index 0, since it always references 'InvalidUnit'.
  Masks.resize(SM.getNumProcResourceKinds());
  for (unsigned I = 1, E = SM.getNumProcResourceKinds(); I < E; ++I) {
    const MCProcResourceDesc &Desc = *SM.getProcResource(I);
    if (Desc.SubUnitsIdxBegin)
      continue;
    Masks[I] = 1ULL << ProcResourceID;
    ProcResourceID++;
  }

  // Create a unique bitmask for every processor resource group.
  for (unsigned I = 1, E = SM.getNumProcResourceKinds(); I < E; ++I) {
    const MCProcResourceDesc &Desc = *SM.getProcResource(I);
    if (!Desc.SubUnitsIdxBegin)
      continue;
    Masks[I] = 1ULL << ProcResourceID;
    for (unsigned U = 0; U < Desc.NumUnits; ++U) {
      uint64_t OtherMask = Masks[Desc.SubUnitsIdxBegin[U]];
      Masks[I] |= OtherMask;
    }
    ProcResourceID++;
  }
}
Ejemplo n.º 2
0
void RegisterFile::initialize(const MCSchedModel &SM, unsigned NumRegs) {
  // Create a default register file that "sees" all the machine registers
  // declared by the target. The number of physical registers in the default
  // register file is set equal to `NumRegs`. A value of zero for `NumRegs`
  // means: this register file has an unbounded number of physical registers.
  addRegisterFile({} /* all registers */, NumRegs);
  if (!SM.hasExtraProcessorInfo())
    return;

  // For each user defined register file, allocate a RegisterMappingTracker
  // object. The size of every register file, as well as the mapping between
  // register files and register classes is specified via tablegen.
  const MCExtraProcessorInfo &Info = SM.getExtraProcessorInfo();
  for (unsigned I = 0, E = Info.NumRegisterFiles; I < E; ++I) {
    const MCRegisterFileDesc &RF = Info.RegisterFiles[I];
    // Skip invalid register files with zero physical registers.
    unsigned Length = RF.NumRegisterCostEntries;
    if (!RF.NumPhysRegs)
      continue;
    // The cost of a register definition is equivalent to the number of
    // physical registers that are allocated at register renaming stage.
    const MCRegisterCostEntry *FirstElt =
        &Info.RegisterCostTable[RF.RegisterCostEntryIdx];
    addRegisterFile(ArrayRef<MCRegisterCostEntry>(FirstElt, Length),
                    RF.NumPhysRegs);
  }
}
Ejemplo n.º 3
0
/// \brief Gets latency information for \p Inst, based on \p DC information.
/// \return The maximum expected latency over all the definitions or -1
/// if no information is available.
static int getLatency(LLVMDisasmContext *DC, const MCInst &Inst) {
  // Try to compute scheduling information.
  const MCSubtargetInfo *STI = DC->getSubtargetInfo();
  const MCSchedModel SCModel = STI->getSchedModel();
  const int NoInformationAvailable = -1;

  // Check if we have a scheduling model for instructions.
  if (!SCModel.hasInstrSchedModel())
    // Try to fall back to the itinerary model if the scheduling model doesn't
    // have a scheduling table.  Note the default does not have a table.
    return getItineraryLatency(DC, Inst);

  // Get the scheduling class of the requested instruction.
  const MCInstrDesc& Desc = DC->getInstrInfo()->get(Inst.getOpcode());
  unsigned SCClass = Desc.getSchedClass();
  const MCSchedClassDesc *SCDesc = SCModel.getSchedClassDesc(SCClass);
  // Resolving the variant SchedClass requires an MI to pass to
  // SubTargetInfo::resolveSchedClass.
  if (!SCDesc || !SCDesc->isValid() || SCDesc->isVariant())
    return NoInformationAvailable;

  // Compute output latency.
  int Latency = 0;
  for (unsigned DefIdx = 0, DefEnd = SCDesc->NumWriteLatencyEntries;
       DefIdx != DefEnd; ++DefIdx) {
    // Lookup the definition's write latency in SubtargetInfo.
    const MCWriteLatencyEntry *WLEntry = STI->getWriteLatencyEntry(SCDesc,
                                                                   DefIdx);
    Latency = std::max(Latency, WLEntry->Cycles);
  }

  return Latency;
}
Ejemplo n.º 4
0
RetireControlUnit::RetireControlUnit(const MCSchedModel &SM)
    : NextAvailableSlotIdx(0), CurrentInstructionSlotIdx(0),
      AvailableSlots(SM.MicroOpBufferSize), MaxRetirePerCycle(0) {
  // Check if the scheduling model provides extra information about the machine
  // processor. If so, then use that information to set the reorder buffer size
  // and the maximum number of instructions retired per cycle.
  if (SM.hasExtraProcessorInfo()) {
    const MCExtraProcessorInfo &EPI = SM.getExtraProcessorInfo();
    if (EPI.ReorderBufferSize)
      AvailableSlots = EPI.ReorderBufferSize;
    MaxRetirePerCycle = EPI.MaxRetirePerCycle;
  }

  assert(AvailableSlots && "Invalid reorder buffer size!");
  Queue.resize(AvailableSlots);
}