LLVM: lib/CodeGen/BasicBlockSections.cpp Source File (original) (raw)

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

33

34

35

36

37

38

39

40

41

42

43

44

45

46

47

48

49

50

51

52

53

54

55

56

57

58

59

60

61

62

63

64

65

66

67

68

69

70

86#include

87

88using namespace llvm;

89

90

91

92

93

95 "bbsections-cold-text-prefix",

96 cl::desc("The text prefix to use for cold basic block clusters"),

98

100 "bbsections-detect-source-drift",

101 cl::desc("This checks if there is a fdo instr. profile hash "

102 "mismatch for this function"),

104

105namespace {

106

108public:

109 static char ID;

110

112

115 }

116

117 StringRef getPassName() const override {

118 return "Basic Block Sections Analysis";

119 }

120

121 void getAnalysisUsage(AnalysisUsage &AU) const override;

122

123

124

125 bool runOnMachineFunction(MachineFunction &MF) override;

126

127private:

128 bool handleBBSections(MachineFunction &MF);

129 bool handleBBAddrMap(MachineFunction &MF);

130};

131

132}

133

134char BasicBlockSections::ID = 0;

136 BasicBlockSections, "bbsections-prepare",

137 "Prepares for basic block sections, by splitting functions "

138 "into clusters of basic blocks.",

139 false, false)

142 "Prepares for basic block sections, by splitting functions "

143 "into clusters of basic blocks.",

145

146

147

148static void

153 for (auto &MBB : MF) {

154 auto NextMBBI = std::next(MBB.getIterator());

155 auto *FTMBB = PreLayoutFallThroughs[MBB.getNumber()];

156

157

158

159

160

161

162 if (FTMBB && (MBB.isEndSection() || &*NextMBBI != FTMBB))

163 TII->insertUnconditionalBranch(MBB, FTMBB, MBB.findBranchDebugLoc());

164

165

166

167 if (MBB.isEndSection())

168 continue;

169

170

171

172 Cond.clear();

175 continue;

176 MBB.updateTerminator(FTMBB);

177 }

178}

179

180

181

182

188 if (!OptWeightInfo)

189 return BBClusterInfos;

190 auto BlockWeights = OptWeightInfo->BlockWeights;

191 auto EdgeWeights = OptWeightInfo->EdgeWeights;

192

194 if (MF.size() <= 2) {

195 for (auto &MBB : MF) {

196 if (MBB.isEntryBlock() || BlockWeights[&MBB] > 0) {

198 }

199 }

200 } else {

203 std::vector<const MachineBasicBlock *> OrigOrder;

204 OrigOrder.reserve(MF.size());

206

207

209

210

211 for (auto &MBB : MF) {

212 auto NonDbgInsts =

214 int NumInsts = std::distance(NonDbgInsts.begin(), NonDbgInsts.end());

215 BlockSizes[MBB.getNumber()] = 4 * NumInsts;

216 BlockCounts[MBB.getNumber()] = BlockWeights[&MBB];

217 OrigOrder.push_back(&MBB);

218 }

219

220

221 for (auto &MBB : MF) {

222 for (auto *Succ : MBB.successors()) {

223 auto EdgeWeight = EdgeWeights[std::make_pair(&MBB, Succ)];

225 static_cast<uint64_t>(Succ->getNumber()),

226 EdgeWeight});

227 }

228 }

229

230

231 auto Result = computeExtTspLayout(BlockSizes, BlockCounts, JumpCounts);

233 auto Block = OrigOrder[R];

234 if (Block->isEntryBlock() || BlockWeights[Block] > 0)

236 }

237 }

238

239

240 if (!HotMBBs.empty()) {

241 unsigned CurrentPosition = 0;

242 for (auto &MBB : HotMBBs) {

243 if (MBB->getBBID()) {

244 BBClusterInfos.push_back({*(MBB->getBBID()), 0, CurrentPosition++});

245 }

246 }

247 }

248 return BBClusterInfos;

249}

250

251

252

253

254

255

256

257

258

259

260static void

264

265

266

267 std::optional EHPadsSectionID;

268

269 for (auto &MBB : MF) {

270

271

272

274

275

276

277

278 MBB.setSectionID(MBB.getNumber());

279 } else {

280 auto I = FuncClusterInfo.find(*MBB.getBBID());

281 if (I != FuncClusterInfo.end()) {

282 MBB.setSectionID(I->second.ClusterID);

283 } else {

285 *MBB.getParent()->getSubtarget().getInstrInfo();

286

287 if (TII.isMBBSafeToSplitToCold(MBB)) {

288

289

291 }

292 }

293 }

294

295 if (MBB.isEHPad() && EHPadsSectionID != MBB.getSectionID() &&

297

298

299

301 : MBB.getSectionID();

302 }

303 }

304

305

306

308 for (auto &MBB : MF)

309 if (MBB.isEHPad())

310 MBB.setSectionID(*EHPadsSectionID);

311}

312

317 for (auto &MBB : MF)

318 PreLayoutFallThroughs[MBB.getNumber()] =

319 MBB.getFallThrough(false);

320

321 MF.sort(MBBCmp);

323 "Entry block should not be displaced by basic block sections");

324

325

327

328

329

330

332}

333

334

335

336

337

339 std::optional CurrentSection;

341 if (MBB.empty() || MBB.getSectionID() == CurrentSection)

342 return false;

343 CurrentSection = MBB.getSectionID();

344 return true;

345 };

346

347 for (auto &MBB : MF) {

348 if (IsFirstNonEmptyBBInSection(MBB) && MBB.isEHPad()) {

350 while (MI->isEHLabel())

351 ++MI;

353 }

354 }

355}

356

359 return false;

360

361 const char MetadataName[] = "instr_prof_hash_mismatch";

363 if (Existing) {

365 for (const auto &N : Tuple->operands())

366 if (N.equalsStr(MetadataName))

367 return true;

368 }

369

370 return false;

371}

372

373

374

375bool BasicBlockSections::handleBBSections(MachineFunction &MF) {

378 return false;

379

380

381

382

383

384

385

388 return false;

389

393 if (auto *BMI = getAnalysisIfAvailable()) {

395 } else {

396 ClusterInfo = getAnalysis()

397 .getClusterInfoForFunction(MF.getName());

398 }

400 return false;

401 for (auto &BBClusterInfo : ClusterInfo) {

402 FuncClusterInfo.try_emplace(BBClusterInfo.BBID, BBClusterInfo);

403 }

404 }

405

406

407

409

412

413 const MachineBasicBlock &EntryBB = MF.front();

414 auto EntryBBSectionID = EntryBB.getSectionID();

415

416

417

418

419

420

421

422 auto MBBSectionOrder = [EntryBBSectionID](const MBBSectionID &LHS,

423 const MBBSectionID &RHS) {

424

425

426 if (LHS == EntryBBSectionID || RHS == EntryBBSectionID)

427 return LHS == EntryBBSectionID;

428 return LHS.Type == RHS.Type ? LHS.Number < RHS.Number : LHS.Type < RHS.Type;

429 };

430

431

432

433

434

435

436

437 auto Comparator = [&](const MachineBasicBlock &X,

438 const MachineBasicBlock &Y) {

439 auto XSectionID = X.getSectionID();

440 auto YSectionID = Y.getSectionID();

441 if (XSectionID != YSectionID)

442 return MBBSectionOrder(XSectionID, YSectionID);

443

444 if (&X == &EntryBB || &Y == &EntryBB)

445 return &X == &EntryBB;

446

447

448 if (XSectionID.Type == MBBSectionID::SectionType::Default)

449 return FuncClusterInfo.lookup(*X.getBBID()).PositionInCluster <

450 FuncClusterInfo.lookup(*Y.getBBID()).PositionInCluster;

451 return X.getNumber() < Y.getNumber();

452 };

453

456 return true;

457}

458

459

460

461

462

463bool BasicBlockSections::handleBBAddrMap(MachineFunction &MF) {

465 return false;

467 return true;

468}

469

470bool BasicBlockSections::runOnMachineFunction(MachineFunction &MF) {

471

472 auto R1 = handleBBSections(MF);

473

474 auto R2 = handleBBAddrMap(MF);

475

476

477 if (auto *WP = getAnalysisIfAvailable())

478 WP->getDomTree().updateBlockNumbers();

479 if (auto *WP = getAnalysisIfAvailable())

480 WP->getPostDomTree().updateBlockNumbers();

481

482 return R1 || R2;

483}

484

485void BasicBlockSections::getAnalysisUsage(AnalysisUsage &AU) const {

487 AU.addRequired();

492}

493

495 return new BasicBlockSections();

496}

assert(UImm &&(UImm !=~static_cast< T >(0)) &&"Invalid immediate!")

const TargetInstrInfo & TII

static void assignSections(MachineFunction &MF, const DenseMap< UniqueBBID, BBClusterInfo > &FuncClusterInfo)

Definition BasicBlockSections.cpp:261

static cl::opt< bool > BBSectionsDetectSourceDrift("bbsections-detect-source-drift", cl::desc("This checks if there is a fdo instr. profile hash " "mismatch for this function"), cl::init(true), cl::Hidden)

bbsections Prepares for basic block by splitting functions into clusters of basic static false void updateBranches(MachineFunction &MF, const SmallVector< MachineBasicBlock * > &PreLayoutFallThroughs)

Definition BasicBlockSections.cpp:149

static SmallVector< BBClusterInfo > createBBClusterInfoForFunction(MachineFunction &MF, const BasicBlockMatchingAndInference &BMI)

Definition BasicBlockSections.cpp:184

Declares methods and data structures for code layout algorithms.

#define INITIALIZE_PASS_DEPENDENCY(depName)

#define INITIALIZE_PASS_END(passName, arg, name, cfg, analysis)

#define INITIALIZE_PASS_BEGIN(passName, arg, name, cfg, analysis)

const SmallVectorImpl< MachineOperand > MachineBasicBlock * TBB

const SmallVectorImpl< MachineOperand > & Cond

This file defines the SmallVector class.

static TableGen::Emitter::Opt Y("gen-skeleton-entry", EmitSkeleton, "Generate example skeleton entry")

static TableGen::Emitter::OptClass< SkeletonEmitter > X("gen-skeleton-class", "Generate example skeleton class")

AnalysisUsage & addUsedIfAvailable()

Add the specified Pass class to the set of analyses used by this pass.

AnalysisUsage & addRequired()

void setPreservesAll()

Set by analyses that do not transform their input at all.

std::optional< WeightInfo > getWeightInfo(StringRef FuncName) const

ValueT lookup(const_arg_type_t< KeyT > Val) const

lookup - Return the entry for the specified key, or a default constructed value if no such entry exis...

iterator find(const_arg_type_t< KeyT > Val)

std::pair< iterator, bool > try_emplace(KeyT &&Key, Ts &&...Args)

MDNode * getMetadata(unsigned KindID) const

Get the current metadata attachments for the given kind, if any.

MBBSectionID getSectionID() const

Returns the section ID of this basic block.

MachineInstrBundleIterator< MachineInstr > iterator

MachineFunctionPass - This class adapts the FunctionPass interface to allow convenient creation of pa...

void getAnalysisUsage(AnalysisUsage &AU) const override

getAnalysisUsage - Subclasses that override getAnalysisUsage must call this.

void setBBSectionsType(BasicBlockSection V)

const TargetSubtargetInfo & getSubtarget() const

getSubtarget - Return the subtarget for which this machine code is being compiled.

StringRef getName() const

getName - Return the name of the corresponding LLVM function.

bool hasBBSections() const

Returns true if this function has basic block sections enabled.

Function & getFunction()

Return the LLVM function that this machine code represents.

unsigned getNumBlockIDs() const

getNumBlockIDs - Return the number of MBB ID's allocated.

void RenumberBlocks(MachineBasicBlock *MBBFrom=nullptr)

RenumberBlocks - This discards all of the MachineBasicBlock numbers and recomputes them.

const MachineBasicBlock & front() const

void assignBeginEndSections()

Assign IsBeginSection IsEndSection fields for basic blocks in this function.

const TargetMachine & getTarget() const

getTarget - Return the target machine this machine code is compiled with

static LLVM_ABI PassRegistry * getPassRegistry()

getPassRegistry - Access the global registry object, which is automatically initialized at applicatio...

void push_back(const T &Elt)

This is a 'vector' (really, a variable-sized array), optimized for the case when the array is small.

TargetInstrInfo - Interface to description of machine instruction set.

virtual void insertNoop(MachineBasicBlock &MBB, MachineBasicBlock::iterator MI) const

Insert a noop into the instruction stream at the specified point.

llvm::BasicBlockSection getBBSectionsType() const

If basic blocks should be emitted into their own section, corresponding to -fbasic-block-sections.

virtual const TargetInstrInfo * getInstrInfo() const

unsigned ID

LLVM IR allows to use arbitrary numbers as calling convention identifiers.

initializer< Ty > init(const Ty &Val)

This is an optimization pass for GlobalISel generic memory operations.

LLVM_ABI MachineFunctionPass * createBasicBlockSectionsPass()

createBasicBlockSections Pass - This pass assigns sections to machine basic blocks and is enabled wit...

Definition BasicBlockSections.cpp:494

LLVM_ABI void initializeBasicBlockSectionsPass(PassRegistry &)

auto instructionsWithoutDebug(IterT It, IterT End, bool SkipPseudoOp=true)

Construct a range iterator which begins at It and moves forwards until End is reached,...

bool hasInstrProfHashMismatch(MachineFunction &MF)

This checks if the source of this function has drifted since this binary was profiled previously.

Definition BasicBlockSections.cpp:357

SmallPtrSet< SUnit *, 8 > ClusterInfo

Keep record of which SUnit are in the same cluster group.

decltype(auto) cast(const From &Val)

cast - Return the argument parameter cast to the specified type.

void avoidZeroOffsetLandingPad(MachineFunction &MF)

Definition BasicBlockSections.cpp:338

cl::opt< std::string > BBSectionsColdTextPrefix

function_ref< bool(const MachineBasicBlock &, const MachineBasicBlock &)> MachineBasicBlockComparator

void sortBasicBlocksAndUpdateBranches(MachineFunction &MF, MachineBasicBlockComparator MBBCmp)

Definition BasicBlockSections.cpp:313

LLVM_ABI static const MBBSectionID ExceptionSectionID

LLVM_ABI static const MBBSectionID ColdSectionID