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
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
|
//===- HexagonMCChecker.h - Instruction bundle checking ---------*- C++ -*-===//
//
// The LLVM Compiler Infrastructure
//
// This file is distributed under the University of Illinois Open Source
// License. See LICENSE.TXT for details.
//
//===----------------------------------------------------------------------===//
//
// This implements the checking of insns inside a bundle according to the
// packet constraint rules of the Hexagon ISA.
//
//===----------------------------------------------------------------------===//
#ifndef LLVM_LIB_TARGET_HEXAGON_MCTARGETDESC_HEXAGONMCCHECKER_H
#define LLVM_LIB_TARGET_HEXAGON_MCTARGETDESC_HEXAGONMCCHECKER_H
#include "MCTargetDesc/HexagonMCInstrInfo.h"
#include "MCTargetDesc/HexagonMCTargetDesc.h"
#include "llvm/ADT/DenseMap.h"
#include "llvm/ADT/SmallVector.h"
#include "llvm/Support/SMLoc.h"
#include <set>
#include <utility>
namespace llvm {
class MCContext;
class MCInst;
class MCInstrInfo;
class MCRegisterInfo;
class MCSubtargetInfo;
/// Check for a valid bundle.
class HexagonMCChecker {
MCContext &Context;
MCInst &MCB;
const MCRegisterInfo &RI;
MCInstrInfo const &MCII;
MCSubtargetInfo const &STI;
bool ReportErrors;
/// Set of definitions: register #, if predicated, if predicated true.
using PredSense = std::pair<unsigned, bool>;
static const PredSense Unconditional;
using PredSet = std::multiset<PredSense>;
using PredSetIterator = std::multiset<PredSense>::iterator;
using DefsIterator = DenseMap<unsigned, PredSet>::iterator;
DenseMap<unsigned, PredSet> Defs;
/// Set of weak definitions whose clashes should be enforced selectively.
using SoftDefsIterator = std::set<unsigned>::iterator;
std::set<unsigned> SoftDefs;
/// Set of temporary definitions not committed to the register file.
using TmpDefsIterator = std::set<unsigned>::iterator;
std::set<unsigned> TmpDefs;
/// Set of new predicates used.
using NewPredsIterator = std::set<unsigned>::iterator;
std::set<unsigned> NewPreds;
/// Set of predicates defined late.
using LatePredsIterator = std::multiset<unsigned>::iterator;
std::multiset<unsigned> LatePreds;
/// Set of uses.
using UsesIterator = std::set<unsigned>::iterator;
std::set<unsigned> Uses;
/// Pre-defined set of read-only registers.
using ReadOnlyIterator = std::set<unsigned>::iterator;
std::set<unsigned> ReadOnly;
void init();
void init(MCInst const &);
void initReg(MCInst const &, unsigned, unsigned &PredReg, bool &isTrue);
bool registerUsed(unsigned Register);
std::tuple<MCInst const *, unsigned, HexagonMCInstrInfo::PredicateInfo>
registerProducer(unsigned Register,
HexagonMCInstrInfo::PredicateInfo Predicated);
// Checks performed.
bool checkBranches();
bool checkPredicates();
bool checkNewValues();
bool checkRegisters();
bool checkRegistersReadOnly();
void checkRegisterCurDefs();
bool checkSolo();
bool checkShuffle();
bool checkSlots();
bool checkAXOK();
bool checkHWLoop();
bool checkCOFMax1();
static void compoundRegisterMap(unsigned &);
bool isPredicateRegister(unsigned R) const {
return (Hexagon::P0 == R || Hexagon::P1 == R || Hexagon::P2 == R ||
Hexagon::P3 == R);
}
bool isLoopRegister(unsigned R) const {
return (Hexagon::SA0 == R || Hexagon::LC0 == R || Hexagon::SA1 == R ||
Hexagon::LC1 == R);
}
public:
explicit HexagonMCChecker(MCContext &Context, MCInstrInfo const &MCII,
MCSubtargetInfo const &STI, MCInst &mcb,
const MCRegisterInfo &ri, bool ReportErrors = true);
explicit HexagonMCChecker(HexagonMCChecker const &Check,
MCSubtargetInfo const &STI, bool CopyReportErrors);
bool check(bool FullCheck = true);
void reportErrorRegisters(unsigned Register);
void reportErrorNewValue(unsigned Register);
void reportError(SMLoc Loc, Twine const &Msg);
void reportNote(SMLoc Loc, Twine const &Msg);
void reportError(Twine const &Msg);
void reportWarning(Twine const &Msg);
void reportBranchErrors();
};
} // end namespace llvm
#endif // LLVM_LIB_TARGET_HEXAGON_MCTARGETDESC_HEXAGONMCCHECKER_H
|