OptParserEmitter.cpp 15 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502
  1. //===- OptParserEmitter.cpp - Table Driven Command Line Parsing -----------===//
  2. //
  3. // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
  4. // See https://llvm.org/LICENSE.txt for license information.
  5. // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
  6. //
  7. //===----------------------------------------------------------------------===//
  8. #include "OptEmitter.h"
  9. #include "llvm/ADT/STLExtras.h"
  10. #include "llvm/ADT/SmallString.h"
  11. #include "llvm/ADT/Twine.h"
  12. #include "llvm/Support/raw_ostream.h"
  13. #include "llvm/TableGen/Record.h"
  14. #include "llvm/TableGen/TableGenBackend.h"
  15. #include <cstring>
  16. #include <map>
  17. #include <memory>
  18. using namespace llvm;
  19. static std::string getOptionName(const Record &R) {
  20. // Use the record name unless EnumName is defined.
  21. if (isa<UnsetInit>(R.getValueInit("EnumName")))
  22. return std::string(R.getName());
  23. return std::string(R.getValueAsString("EnumName"));
  24. }
  25. static raw_ostream &write_cstring(raw_ostream &OS, llvm::StringRef Str) {
  26. OS << '"';
  27. OS.write_escaped(Str);
  28. OS << '"';
  29. return OS;
  30. }
  31. static std::string getOptionSpelling(const Record &R, size_t &PrefixLength) {
  32. std::vector<StringRef> Prefixes = R.getValueAsListOfStrings("Prefixes");
  33. StringRef Name = R.getValueAsString("Name");
  34. if (Prefixes.empty()) {
  35. PrefixLength = 0;
  36. return Name.str();
  37. }
  38. PrefixLength = Prefixes[0].size();
  39. return (Twine(Prefixes[0]) + Twine(Name)).str();
  40. }
  41. static std::string getOptionSpelling(const Record &R) {
  42. size_t PrefixLength;
  43. return getOptionSpelling(R, PrefixLength);
  44. }
  45. static void emitNameUsingSpelling(raw_ostream &OS, const Record &R) {
  46. size_t PrefixLength;
  47. OS << "llvm::StringLiteral(";
  48. write_cstring(
  49. OS, StringRef(getOptionSpelling(R, PrefixLength)).substr(PrefixLength));
  50. OS << ")";
  51. }
  52. class MarshallingInfo {
  53. public:
  54. static constexpr const char *MacroName = "OPTION_WITH_MARSHALLING";
  55. const Record &R;
  56. bool ShouldAlwaysEmit;
  57. StringRef MacroPrefix;
  58. StringRef KeyPath;
  59. StringRef DefaultValue;
  60. StringRef NormalizedValuesScope;
  61. StringRef ImpliedCheck;
  62. StringRef ImpliedValue;
  63. StringRef ShouldParse;
  64. StringRef Normalizer;
  65. StringRef Denormalizer;
  66. StringRef ValueMerger;
  67. StringRef ValueExtractor;
  68. int TableIndex = -1;
  69. std::vector<StringRef> Values;
  70. std::vector<StringRef> NormalizedValues;
  71. std::string ValueTableName;
  72. static size_t NextTableIndex;
  73. static constexpr const char *ValueTablePreamble = R"(
  74. struct SimpleEnumValue {
  75. const char *Name;
  76. unsigned Value;
  77. };
  78. struct SimpleEnumValueTable {
  79. const SimpleEnumValue *Table;
  80. unsigned Size;
  81. };
  82. )";
  83. static constexpr const char *ValueTablesDecl =
  84. "static const SimpleEnumValueTable SimpleEnumValueTables[] = ";
  85. MarshallingInfo(const Record &R) : R(R) {}
  86. std::string getMacroName() const {
  87. return (MacroPrefix + MarshallingInfo::MacroName).str();
  88. }
  89. void emit(raw_ostream &OS) const {
  90. write_cstring(OS, StringRef(getOptionSpelling(R)));
  91. OS << ", ";
  92. OS << ShouldParse;
  93. OS << ", ";
  94. OS << ShouldAlwaysEmit;
  95. OS << ", ";
  96. OS << KeyPath;
  97. OS << ", ";
  98. emitScopedNormalizedValue(OS, DefaultValue);
  99. OS << ", ";
  100. OS << ImpliedCheck;
  101. OS << ", ";
  102. emitScopedNormalizedValue(OS, ImpliedValue);
  103. OS << ", ";
  104. OS << Normalizer;
  105. OS << ", ";
  106. OS << Denormalizer;
  107. OS << ", ";
  108. OS << ValueMerger;
  109. OS << ", ";
  110. OS << ValueExtractor;
  111. OS << ", ";
  112. OS << TableIndex;
  113. }
  114. std::optional<StringRef> emitValueTable(raw_ostream &OS) const {
  115. if (TableIndex == -1)
  116. return {};
  117. OS << "static const SimpleEnumValue " << ValueTableName << "[] = {\n";
  118. for (unsigned I = 0, E = Values.size(); I != E; ++I) {
  119. OS << "{";
  120. write_cstring(OS, Values[I]);
  121. OS << ",";
  122. OS << "static_cast<unsigned>(";
  123. emitScopedNormalizedValue(OS, NormalizedValues[I]);
  124. OS << ")},";
  125. }
  126. OS << "};\n";
  127. return StringRef(ValueTableName);
  128. }
  129. private:
  130. void emitScopedNormalizedValue(raw_ostream &OS,
  131. StringRef NormalizedValue) const {
  132. if (!NormalizedValuesScope.empty())
  133. OS << NormalizedValuesScope << "::";
  134. OS << NormalizedValue;
  135. }
  136. };
  137. size_t MarshallingInfo::NextTableIndex = 0;
  138. static MarshallingInfo createMarshallingInfo(const Record &R) {
  139. assert(!isa<UnsetInit>(R.getValueInit("KeyPath")) &&
  140. !isa<UnsetInit>(R.getValueInit("DefaultValue")) &&
  141. !isa<UnsetInit>(R.getValueInit("ValueMerger")) &&
  142. "MarshallingInfo must have a provide a keypath, default value and a "
  143. "value merger");
  144. MarshallingInfo Ret(R);
  145. Ret.ShouldAlwaysEmit = R.getValueAsBit("ShouldAlwaysEmit");
  146. Ret.MacroPrefix = R.getValueAsString("MacroPrefix");
  147. Ret.KeyPath = R.getValueAsString("KeyPath");
  148. Ret.DefaultValue = R.getValueAsString("DefaultValue");
  149. Ret.NormalizedValuesScope = R.getValueAsString("NormalizedValuesScope");
  150. Ret.ImpliedCheck = R.getValueAsString("ImpliedCheck");
  151. Ret.ImpliedValue =
  152. R.getValueAsOptionalString("ImpliedValue").value_or(Ret.DefaultValue);
  153. Ret.ShouldParse = R.getValueAsString("ShouldParse");
  154. Ret.Normalizer = R.getValueAsString("Normalizer");
  155. Ret.Denormalizer = R.getValueAsString("Denormalizer");
  156. Ret.ValueMerger = R.getValueAsString("ValueMerger");
  157. Ret.ValueExtractor = R.getValueAsString("ValueExtractor");
  158. if (!isa<UnsetInit>(R.getValueInit("NormalizedValues"))) {
  159. assert(!isa<UnsetInit>(R.getValueInit("Values")) &&
  160. "Cannot provide normalized values for value-less options");
  161. Ret.TableIndex = MarshallingInfo::NextTableIndex++;
  162. Ret.NormalizedValues = R.getValueAsListOfStrings("NormalizedValues");
  163. Ret.Values.reserve(Ret.NormalizedValues.size());
  164. Ret.ValueTableName = getOptionName(R) + "ValueTable";
  165. StringRef ValuesStr = R.getValueAsString("Values");
  166. for (;;) {
  167. size_t Idx = ValuesStr.find(',');
  168. if (Idx == StringRef::npos)
  169. break;
  170. if (Idx > 0)
  171. Ret.Values.push_back(ValuesStr.slice(0, Idx));
  172. ValuesStr = ValuesStr.slice(Idx + 1, StringRef::npos);
  173. }
  174. if (!ValuesStr.empty())
  175. Ret.Values.push_back(ValuesStr);
  176. assert(Ret.Values.size() == Ret.NormalizedValues.size() &&
  177. "The number of normalized values doesn't match the number of "
  178. "values");
  179. }
  180. return Ret;
  181. }
  182. /// OptParserEmitter - This tablegen backend takes an input .td file
  183. /// describing a list of options and emits a data structure for parsing and
  184. /// working with those options when given an input command line.
  185. namespace llvm {
  186. void EmitOptParser(RecordKeeper &Records, raw_ostream &OS) {
  187. // Get the option groups and options.
  188. const std::vector<Record*> &Groups =
  189. Records.getAllDerivedDefinitions("OptionGroup");
  190. std::vector<Record*> Opts = Records.getAllDerivedDefinitions("Option");
  191. emitSourceFileHeader("Option Parsing Definitions", OS);
  192. array_pod_sort(Opts.begin(), Opts.end(), CompareOptionRecords);
  193. // Generate prefix groups.
  194. typedef SmallVector<SmallString<2>, 2> PrefixKeyT;
  195. typedef std::map<PrefixKeyT, std::string> PrefixesT;
  196. PrefixesT Prefixes;
  197. Prefixes.insert(std::make_pair(PrefixKeyT(), "prefix_0"));
  198. unsigned CurPrefix = 0;
  199. for (const Record &R : llvm::make_pointee_range(Opts)) {
  200. std::vector<StringRef> RPrefixes = R.getValueAsListOfStrings("Prefixes");
  201. PrefixKeyT PrefixKey(RPrefixes.begin(), RPrefixes.end());
  202. unsigned NewPrefix = CurPrefix + 1;
  203. std::string Prefix = (Twine("prefix_") + Twine(NewPrefix)).str();
  204. if (Prefixes.insert(std::make_pair(PrefixKey, Prefix)).second)
  205. CurPrefix = NewPrefix;
  206. }
  207. DenseSet<StringRef> PrefixesUnionSet;
  208. for (const auto &Prefix : Prefixes)
  209. PrefixesUnionSet.insert(Prefix.first.begin(), Prefix.first.end());
  210. SmallVector<StringRef> PrefixesUnion(PrefixesUnionSet.begin(),
  211. PrefixesUnionSet.end());
  212. array_pod_sort(PrefixesUnion.begin(), PrefixesUnion.end());
  213. // Dump prefixes.
  214. OS << "/////////\n";
  215. OS << "// Prefixes\n\n";
  216. OS << "#ifdef PREFIX\n";
  217. OS << "#define COMMA ,\n";
  218. for (const auto &Prefix : Prefixes) {
  219. OS << "PREFIX(";
  220. // Prefix name.
  221. OS << Prefix.second;
  222. // Prefix values.
  223. OS << ", {";
  224. for (const auto &PrefixKey : Prefix.first)
  225. OS << "llvm::StringLiteral(\"" << PrefixKey << "\") COMMA ";
  226. // Append an empty element to avoid ending up with an empty array.
  227. OS << "llvm::StringLiteral(\"\")})\n";
  228. }
  229. OS << "#undef COMMA\n";
  230. OS << "#endif // PREFIX\n\n";
  231. // Dump prefix unions.
  232. OS << "/////////\n";
  233. OS << "// Prefix Union\n\n";
  234. OS << "#ifdef PREFIX_UNION\n";
  235. OS << "#define COMMA ,\n";
  236. OS << "PREFIX_UNION({\n";
  237. for (const auto &Prefix : PrefixesUnion) {
  238. OS << "llvm::StringLiteral(\"" << Prefix << "\") COMMA ";
  239. }
  240. OS << "llvm::StringLiteral(\"\")})\n";
  241. OS << "#undef COMMA\n";
  242. OS << "#endif // PREFIX_UNION\n\n";
  243. // Dump groups.
  244. OS << "/////////\n";
  245. OS << "// ValuesCode\n\n";
  246. OS << "#ifdef OPTTABLE_VALUES_CODE\n";
  247. for (const Record &R : llvm::make_pointee_range(Opts)) {
  248. // The option values, if any;
  249. if (!isa<UnsetInit>(R.getValueInit("ValuesCode"))) {
  250. assert(isa<UnsetInit>(R.getValueInit("Values")) &&
  251. "Cannot choose between Values and ValuesCode");
  252. OS << "#define VALUES_CODE " << getOptionName(R) << "_Values\n";
  253. OS << R.getValueAsString("ValuesCode") << "\n";
  254. OS << "#undef VALUES_CODE\n";
  255. }
  256. }
  257. OS << "#endif\n";
  258. OS << "/////////\n";
  259. OS << "// Groups\n\n";
  260. OS << "#ifdef OPTION\n";
  261. for (const Record &R : llvm::make_pointee_range(Groups)) {
  262. // Start a single option entry.
  263. OS << "OPTION(";
  264. // The option prefix;
  265. OS << "llvm::ArrayRef<llvm::StringLiteral>()";
  266. // The option string.
  267. OS << ", \"" << R.getValueAsString("Name") << '"';
  268. // The option identifier name.
  269. OS << ", " << getOptionName(R);
  270. // The option kind.
  271. OS << ", Group";
  272. // The containing option group (if any).
  273. OS << ", ";
  274. if (const DefInit *DI = dyn_cast<DefInit>(R.getValueInit("Group")))
  275. OS << getOptionName(*DI->getDef());
  276. else
  277. OS << "INVALID";
  278. // The other option arguments (unused for groups).
  279. OS << ", INVALID, nullptr, 0, 0";
  280. // The option help text.
  281. if (!isa<UnsetInit>(R.getValueInit("HelpText"))) {
  282. OS << ",\n";
  283. OS << " ";
  284. write_cstring(OS, R.getValueAsString("HelpText"));
  285. } else
  286. OS << ", nullptr";
  287. // The option meta-variable name (unused).
  288. OS << ", nullptr";
  289. // The option Values (unused for groups).
  290. OS << ", nullptr)\n";
  291. }
  292. OS << "\n";
  293. OS << "//////////\n";
  294. OS << "// Options\n\n";
  295. auto WriteOptRecordFields = [&](raw_ostream &OS, const Record &R) {
  296. // The option prefix;
  297. std::vector<StringRef> RPrefixes = R.getValueAsListOfStrings("Prefixes");
  298. OS << Prefixes[PrefixKeyT(RPrefixes.begin(), RPrefixes.end())] << ", ";
  299. // The option string.
  300. emitNameUsingSpelling(OS, R);
  301. // The option identifier name.
  302. OS << ", " << getOptionName(R);
  303. // The option kind.
  304. OS << ", " << R.getValueAsDef("Kind")->getValueAsString("Name");
  305. // The containing option group (if any).
  306. OS << ", ";
  307. const ListInit *GroupFlags = nullptr;
  308. if (const DefInit *DI = dyn_cast<DefInit>(R.getValueInit("Group"))) {
  309. GroupFlags = DI->getDef()->getValueAsListInit("Flags");
  310. OS << getOptionName(*DI->getDef());
  311. } else
  312. OS << "INVALID";
  313. // The option alias (if any).
  314. OS << ", ";
  315. if (const DefInit *DI = dyn_cast<DefInit>(R.getValueInit("Alias")))
  316. OS << getOptionName(*DI->getDef());
  317. else
  318. OS << "INVALID";
  319. // The option alias arguments (if any).
  320. // Emitted as a \0 separated list in a string, e.g. ["foo", "bar"]
  321. // would become "foo\0bar\0". Note that the compiler adds an implicit
  322. // terminating \0 at the end.
  323. OS << ", ";
  324. std::vector<StringRef> AliasArgs = R.getValueAsListOfStrings("AliasArgs");
  325. if (AliasArgs.size() == 0) {
  326. OS << "nullptr";
  327. } else {
  328. OS << "\"";
  329. for (StringRef AliasArg : AliasArgs)
  330. OS << AliasArg << "\\0";
  331. OS << "\"";
  332. }
  333. // The option flags.
  334. OS << ", ";
  335. int NumFlags = 0;
  336. const ListInit *LI = R.getValueAsListInit("Flags");
  337. for (Init *I : *LI)
  338. OS << (NumFlags++ ? " | " : "") << cast<DefInit>(I)->getDef()->getName();
  339. if (GroupFlags) {
  340. for (Init *I : *GroupFlags)
  341. OS << (NumFlags++ ? " | " : "")
  342. << cast<DefInit>(I)->getDef()->getName();
  343. }
  344. if (NumFlags == 0)
  345. OS << '0';
  346. // The option parameter field.
  347. OS << ", " << R.getValueAsInt("NumArgs");
  348. // The option help text.
  349. if (!isa<UnsetInit>(R.getValueInit("HelpText"))) {
  350. OS << ",\n";
  351. OS << " ";
  352. write_cstring(OS, R.getValueAsString("HelpText"));
  353. } else
  354. OS << ", nullptr";
  355. // The option meta-variable name.
  356. OS << ", ";
  357. if (!isa<UnsetInit>(R.getValueInit("MetaVarName")))
  358. write_cstring(OS, R.getValueAsString("MetaVarName"));
  359. else
  360. OS << "nullptr";
  361. // The option Values. Used for shell autocompletion.
  362. OS << ", ";
  363. if (!isa<UnsetInit>(R.getValueInit("Values")))
  364. write_cstring(OS, R.getValueAsString("Values"));
  365. else if (!isa<UnsetInit>(R.getValueInit("ValuesCode"))) {
  366. OS << getOptionName(R) << "_Values";
  367. }
  368. else
  369. OS << "nullptr";
  370. };
  371. auto IsMarshallingOption = [](const Record &R) {
  372. return !isa<UnsetInit>(R.getValueInit("KeyPath")) &&
  373. !R.getValueAsString("KeyPath").empty();
  374. };
  375. std::vector<const Record *> OptsWithMarshalling;
  376. for (const Record &R : llvm::make_pointee_range(Opts)) {
  377. // Start a single option entry.
  378. OS << "OPTION(";
  379. WriteOptRecordFields(OS, R);
  380. OS << ")\n";
  381. if (IsMarshallingOption(R))
  382. OptsWithMarshalling.push_back(&R);
  383. }
  384. OS << "#endif // OPTION\n";
  385. auto CmpMarshallingOpts = [](const Record *const *A, const Record *const *B) {
  386. unsigned AID = (*A)->getID();
  387. unsigned BID = (*B)->getID();
  388. if (AID < BID)
  389. return -1;
  390. if (AID > BID)
  391. return 1;
  392. return 0;
  393. };
  394. // The RecordKeeper stores records (options) in lexicographical order, and we
  395. // have reordered the options again when generating prefix groups. We need to
  396. // restore the original definition order of options with marshalling to honor
  397. // the topology of the dependency graph implied by `DefaultAnyOf`.
  398. array_pod_sort(OptsWithMarshalling.begin(), OptsWithMarshalling.end(),
  399. CmpMarshallingOpts);
  400. std::vector<MarshallingInfo> MarshallingInfos;
  401. MarshallingInfos.reserve(OptsWithMarshalling.size());
  402. for (const auto *R : OptsWithMarshalling)
  403. MarshallingInfos.push_back(createMarshallingInfo(*R));
  404. for (const auto &MI : MarshallingInfos) {
  405. OS << "#ifdef " << MI.getMacroName() << "\n";
  406. OS << MI.getMacroName() << "(";
  407. WriteOptRecordFields(OS, MI.R);
  408. OS << ", ";
  409. MI.emit(OS);
  410. OS << ")\n";
  411. OS << "#endif // " << MI.getMacroName() << "\n";
  412. }
  413. OS << "\n";
  414. OS << "#ifdef SIMPLE_ENUM_VALUE_TABLE";
  415. OS << "\n";
  416. OS << MarshallingInfo::ValueTablePreamble;
  417. std::vector<StringRef> ValueTableNames;
  418. for (const auto &MI : MarshallingInfos)
  419. if (auto MaybeValueTableName = MI.emitValueTable(OS))
  420. ValueTableNames.push_back(*MaybeValueTableName);
  421. OS << MarshallingInfo::ValueTablesDecl << "{";
  422. for (auto ValueTableName : ValueTableNames)
  423. OS << "{" << ValueTableName << ", std::size(" << ValueTableName << ")},\n";
  424. OS << "};\n";
  425. OS << "static const unsigned SimpleEnumValueTablesSize = "
  426. "std::size(SimpleEnumValueTables);\n";
  427. OS << "#endif // SIMPLE_ENUM_VALUE_TABLE\n";
  428. OS << "\n";
  429. OS << "\n";
  430. }
  431. } // end namespace llvm