clang: lib/Basic/Builtins.cpp Source File (original) (raw)

1

2

3

4

5

6

7

8

9

10

11

12

18#include "llvm/ADT/StringRef.h"

19using namespace clang;

20

22 switch (ID) {

23#define HEADER(ID, NAME) \

24 case ID: \

25 return NAME;

26#include "clang/Basic/BuiltinHeaders.def"

27#undef HEADER

28 };

29 llvm_unreachable("Unknown HeaderDesc::HeaderID enum");

30}

31

33 {"not a builtin function", nullptr, nullptr, nullptr, HeaderDesc::NO_HEADER,

35#define BUILTIN(ID, TYPE, ATTRS) \

36 {#ID, TYPE, ATTRS, nullptr, HeaderDesc::NO_HEADER, ALL_LANGUAGES},

37#define LANGBUILTIN(ID, TYPE, ATTRS, LANGS) \

38 {#ID, TYPE, ATTRS, nullptr, HeaderDesc::NO_HEADER, LANGS},

39#define LIBBUILTIN(ID, TYPE, ATTRS, HEADER, LANGS) \

40 {#ID, TYPE, ATTRS, nullptr, HeaderDesc::HEADER, LANGS},

41#include "clang/Basic/Builtins.inc"

42};

43

44const Builtin::Info &Builtin::Context::getRecord(unsigned ID) const {

48 (TSRecords.size() + AuxTSRecords.size())) &&

49 "Invalid builtin ID!");

53}

54

57 assert(TSRecords.empty() && "Already initialized target?");

58 TSRecords = Target.getTargetBuiltins();

59 if (AuxTarget)

61}

62

64 bool InStdNamespace = FuncName.consume_front("std-");

66 ++i) {

68 (bool)strchr(BuiltinInfo[i].Attributes, 'z') == InStdNamespace)

69 return strchr(BuiltinInfo[i].Attributes, 'f') != nullptr;

70 }

71

72 return false;

73}

74

75

78

80 return false;

81

83 return false;

84

85 if (LangOpts.NoMathBuiltin && BuiltinInfo.Header.ID == HeaderDesc::MATH_H)

86 return false;

87

89 return false;

90

92 return false;

93

95 return false;

96

98 return false;

99

101 return false;

102

104 return false;

105

107 return false;

108

109

110

111

112

115 return false;

116

118 return false;

119

121 return false;

122

124 return false;

125

127 return false;

128 return true;

129}

130

131

132

133

136

140 }

141

142

143 for (unsigned i = 0, e = TSRecords.size(); i != e; ++i)

146

147

148 for (unsigned i = 0, e = AuxTSRecords.size(); i != e; ++i)

149 Table.get(AuxTSRecords[i].Name)

151

152

153 for (llvm::StringRef Name : LangOpts.NoBuiltinFuncs) {

154 bool InStdNamespace = Name.consume_front("std-");

155 auto NameIt = Table.find(Name);

156 if (NameIt != Table.end()) {

157 unsigned ID = NameIt->second->getBuiltinID();

159 isInStdNamespace(ID) == InStdNamespace) {

160 NameIt->second->clearBuiltinID();

161 }

162 }

163 }

164}

165

167 return (llvm::Twine("'") + getName(ID) + "'").str();

168}

169

171 const char *WidthPos = ::strchr(getRecord(ID).Attributes, 'V');

172 if (!WidthPos)

173 return 0;

174

175 ++WidthPos;

176 assert(*WidthPos == ':' &&

177 "Vector width specifier must be followed by a ':'");

178 ++WidthPos;

179

180 char *EndPos;

181 unsigned Width = ::strtol(WidthPos, &EndPos, 10);

182 assert(*EndPos == ':' && "Vector width specific must end with a ':'");

183 return Width;

184}

185

186bool Builtin::Context::isLike(unsigned ID, unsigned &FormatIdx,

187 bool &HasVAListArg, const char *Fmt) const {

188 assert(Fmt && "Not passed a format string");

189 assert(::strlen(Fmt) == 2 &&

190 "Format string needs to be two characters long");

191 assert(::toupper(Fmt[0]) == Fmt[1] &&

192 "Format string is not in the form \"xX\"");

193

194 const char *Like = ::strpbrk(getRecord(ID).Attributes, Fmt);

195 if (!Like)

196 return false;

197

198 HasVAListArg = (*Like == Fmt[1]);

199

200 ++Like;

201 assert(*Like == ':' && "Format specifier must be followed by a ':'");

202 ++Like;

203

204 assert(::strchr(Like, ':') && "Format specifier must end with a ':'");

205 FormatIdx = ::strtol(Like, nullptr, 10);

206 return true;

207}

208

210 bool &HasVAListArg) {

211 return isLike(ID, FormatIdx, HasVAListArg, "pP");

212}

213

215 bool &HasVAListArg) {

216 return isLike(ID, FormatIdx, HasVAListArg, "sS");

217}

218

221 const char *CalleePos = ::strchr(getRecord(ID).Attributes, 'C');

222 if (!CalleePos)

223 return false;

224

225 ++CalleePos;

226 assert(*CalleePos == '<' &&

227 "Callback callee specifier must be followed by a '<'");

228 ++CalleePos;

229

230 char *EndPos;

231 int CalleeIdx = ::strtol(CalleePos, &EndPos, 10);

232 assert(CalleeIdx >= 0 && "Callee index is supposed to be positive!");

233 Encoding.push_back(CalleeIdx);

234

235 while (*EndPos == ',') {

236 const char *PayloadPos = EndPos + 1;

237

238 int PayloadIdx = ::strtol(PayloadPos, &EndPos, 10);

239 Encoding.push_back(PayloadIdx);

240 }

241

242 assert(*EndPos == '>' && "Callback callee specifier must end with a '>'");

243 return true;

244}

245

248 ID == Builtin::BI__builtin_assume_aligned ||

249 (!hasReferenceArgsOrResult(ID) && !hasCustomTypechecking(ID)) ||

250 isInStdNamespace(ID);

251}

252

254 StringRef RequiredFeatures, const llvm::StringMap &TargetFetureMap) {

255

256 if (RequiredFeatures.empty())

257 return true;

258 assert(!RequiredFeatures.contains(' ') && "Space in feature list");

259

261 return TF.hasRequiredFeatures(RequiredFeatures);

262}

static bool builtinIsSupported(const Builtin::Info &BuiltinInfo, const LangOptions &LangOpts)

Is this builtin supported according to the given language options?

static constexpr Builtin::Info BuiltinInfo[]

Defines enum values for all the target-independent builtin functions.

Defines the clang::IdentifierInfo, clang::IdentifierTable, and clang::Selector interfaces.

Defines the clang::LangOptions interface.

llvm::MachO::Target Target

static std::string getName(const CallEvent &Call)

std::string getQuotedName(unsigned ID) const

Return a quoted name for the specified builtin for use in diagnostics.

bool performsCallback(unsigned ID, llvm::SmallVectorImpl< int > &Encoding) const

Determine whether this builtin has callback behavior (see llvm::AbstractCallSites for details).

bool isAuxBuiltinID(unsigned ID) const

Return true if builtin ID belongs to AuxTarget.

static bool isBuiltinFunc(llvm::StringRef Name)

Returns true if this is a libc/libm function without the '__builtin_' prefix.

unsigned getRequiredVectorWidth(unsigned ID) const

unsigned getAuxBuiltinID(unsigned ID) const

Return real builtin ID (i.e.

void initializeBuiltins(IdentifierTable &Table, const LangOptions &LangOpts)

Mark the identifiers for all the builtins with their appropriate builtin ID # and mark any non-portab...

bool isScanfLike(unsigned ID, unsigned &FormatIdx, bool &HasVAListArg)

Determine whether this builtin is like scanf in its formatting rules and, if so, set the index to the...

bool canBeRedeclared(unsigned ID) const

Returns true if this is a builtin that can be redeclared.

bool isPrintfLike(unsigned ID, unsigned &FormatIdx, bool &HasVAListArg)

Determine whether this builtin is like printf in its formatting rules and, if so, set the index to th...

void InitializeTarget(const TargetInfo &Target, const TargetInfo *AuxTarget)

Perform target-specific initialization.

TargetFeatures - This class is used to check whether the builtin function has the required tagert spe...

void setBuiltinID(unsigned ID)

Implements an efficient mapping from strings to IdentifierInfo nodes.

iterator find(StringRef Name) const

IdentifierInfo & get(StringRef Name)

Return the identifier token info for the specified named identifier.

Keeps track of the various options that can be enabled, which controls the dialect of C or C++ that i...

std::vector< std::string > NoBuiltinFuncs

A list of all -fno-builtin-* function names (e.g., memset).

unsigned getOpenCLCompatibleVersion() const

Return the OpenCL version that kernel language is compatible with.

Exposes information about the current target.

virtual ArrayRef< Builtin::Info > getTargetBuiltins() const =0

Return information about target-specific builtins for the current primary target, and info about whic...

Defines the clang::TargetInfo interface.

bool evaluateRequiredTargetFeatures(llvm::StringRef RequiredFatures, const llvm::StringMap< bool > &TargetFetureMap)

Returns true if the required target features of a builtin function are enabled.

The JSON file list parser is used to communicate input to InstallAPI.