blob: 2fc8419177420cd5ad26b4a11c79546c03f14b0a [file] [log] [blame]
Tobias Grosser37c9b8e2014-03-04 14:59:00 +00001//===------ PollyIRBuilder.cpp --------------------------------------------===//
2//
3// The LLVM Compiler Infrastructure
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
9//
10// The Polly IRBuilder file contains Polly specific extensions for the IRBuilder
11// that are used e.g. to emit the llvm.loop.parallel metadata.
12//
13//===----------------------------------------------------------------------===//
14
15#include "polly/CodeGen/IRBuilder.h"
Johannes Doerfertc7b719f2014-10-01 20:10:44 +000016
Tobias Grosser37c9b8e2014-03-04 14:59:00 +000017#include "llvm/IR/Metadata.h"
18#include "llvm/Support/Debug.h"
19
20using namespace llvm;
21using namespace polly;
22
Johannes Doerfertc7b719f2014-10-01 20:10:44 +000023/// @brief Get the loop id metadata node.
24///
25/// Each loop is identified by a self referencing metadata node of the form:
26///
27/// '!n = metadata !{metadata !n}'
28///
29/// This functions creates such metadata on demand if not yet available.
30///
31/// @return The loop id metadata node.
32static MDNode *getLoopID(Loop *L) {
33 Value *Args[] = {0};
34 MDNode *LoopID = MDNode::get(L->getHeader()->getContext(), Args);
Tobias Grosser37c9b8e2014-03-04 14:59:00 +000035 LoopID->replaceOperandWith(0, LoopID);
36 return LoopID;
37}
38
Johannes Doerfertc7b719f2014-10-01 20:10:44 +000039void polly::LoopAnnotator::pushLoop(Loop *L, bool IsParallel) {
40 ActiveLoops.push_back(L);
41 if (!IsParallel)
Tobias Grosser37c9b8e2014-03-04 14:59:00 +000042 return;
43
Johannes Doerfertc7b719f2014-10-01 20:10:44 +000044 BasicBlock *Header = L->getHeader();
45 MDNode *Id = getLoopID(L);
46 Value *Args[] = {Id};
47 MDNode *Ids = ParallelLoops.empty()
48 ? MDNode::get(Header->getContext(), Args)
49 : MDNode::concatenate(ParallelLoops.back(), Id);
50 ParallelLoops.push_back(Ids);
51}
52
53void polly::LoopAnnotator::popLoop(bool IsParallel) {
54 ActiveLoops.pop_back();
55 if (!IsParallel)
Tobias Grosser37c9b8e2014-03-04 14:59:00 +000056 return;
57
Johannes Doerfertc7b719f2014-10-01 20:10:44 +000058 assert(!ParallelLoops.empty() && "Expected a parallel loop to pop");
59 ParallelLoops.pop_back();
60}
61
62void polly::LoopAnnotator::annotateLoopLatch(BranchInst *B, Loop *L,
63 bool IsParallel) const {
64 if (!IsParallel)
65 return;
66
67 assert(!ParallelLoops.empty() && "Expected a parallel loop to annotate");
68 MDNode *Ids = ParallelLoops.back();
69 MDNode *Id = cast<MDNode>(Ids->getOperand(Ids->getNumOperands() - 1));
70 B->setMetadata("llvm.loop", Id);
71}
72
73void polly::LoopAnnotator::annotate(Instruction *Inst) {
74 if (!Inst->mayReadOrWriteMemory() || ParallelLoops.empty())
75 return;
76
77 Inst->setMetadata("llvm.mem.parallel_loop_access", ParallelLoops.back());
Tobias Grosser37c9b8e2014-03-04 14:59:00 +000078}