tblgen: Add support for non-inheritable attributes
[oota-llvm.git] / utils / TableGen / ClangAttrEmitter.cpp
1 //===- ClangAttrEmitter.cpp - Generate Clang attribute handling =-*- C++ -*--=//
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 // These tablegen backends emit Clang attribute processing code
11 //
12 //===----------------------------------------------------------------------===//
13
14 #include "ClangAttrEmitter.h"
15 #include "Record.h"
16 #include "llvm/ADT/StringSwitch.h"
17 #include <algorithm>
18 #include <cctype>
19
20 using namespace llvm;
21
22 static const std::vector<StringRef>
23 getValueAsListOfStrings(Record &R, StringRef FieldName) {
24   ListInit *List = R.getValueAsListInit(FieldName);
25   assert (List && "Got a null ListInit");
26
27   std::vector<StringRef> Strings;
28   Strings.reserve(List->getSize());
29
30   for (ListInit::iterator i = List->begin(), e = List->end(); i != e; ++i) {
31     assert(*i && "Got a null element in a ListInit");
32     if (StringInit *S = dynamic_cast<StringInit *>(*i))
33       Strings.push_back(S->getValue());
34     else if (CodeInit *C = dynamic_cast<CodeInit *>(*i))
35       Strings.push_back(C->getValue());
36     else
37       assert(false && "Got a non-string, non-code element in a ListInit");
38   }
39
40   return Strings;
41 }
42
43 std::string ReadPCHRecord(StringRef type) {
44   return StringSwitch<std::string>(type)
45     .EndsWith("Decl *", "cast_or_null<" + std::string(type, 0, type.size()-1) +
46               ">(GetDecl(Record[Idx++]))")
47     .Case("QualType", "GetType(Record[Idx++])")
48     .Default("Record[Idx++]");
49 }
50
51 // Assumes that the way to get the value is SA->getname()
52 std::string WritePCHRecord(StringRef type, StringRef name) {
53   return StringSwitch<std::string>(type)
54     .EndsWith("Decl *", "AddDeclRef(" + std::string(name) +
55                         ", Record);\n")
56     .Case("QualType", "AddTypeRef(" + std::string(name) + ", Record);\n")
57     .Default("Record.push_back(" + std::string(name) + ");\n");
58 }
59
60 namespace {
61   class Argument {
62     std::string lowerName, upperName;
63     StringRef attrName;
64
65   public:
66     Argument(Record &Arg, StringRef Attr)
67       : lowerName(Arg.getValueAsString("Name")), upperName(lowerName),
68         attrName(Attr) {
69       if (!lowerName.empty()) {
70         lowerName[0] = std::tolower(lowerName[0]);
71         upperName[0] = std::toupper(upperName[0]);
72       }
73     }
74     virtual ~Argument() {}
75
76     StringRef getLowerName() const { return lowerName; }
77     StringRef getUpperName() const { return upperName; }
78     StringRef getAttrName() const { return attrName; }
79
80     // These functions print the argument contents formatted in different ways.
81     virtual void writeAccessors(raw_ostream &OS) const = 0;
82     virtual void writeAccessorDefinitions(raw_ostream &OS) const {}
83     virtual void writeCloneArgs(raw_ostream &OS) const = 0;
84     virtual void writeCtorBody(raw_ostream &OS) const {}
85     virtual void writeCtorInitializers(raw_ostream &OS) const = 0;
86     virtual void writeCtorParameters(raw_ostream &OS) const = 0;
87     virtual void writeDeclarations(raw_ostream &OS) const = 0;
88     virtual void writePCHReadArgs(raw_ostream &OS) const = 0;
89     virtual void writePCHReadDecls(raw_ostream &OS) const = 0;
90     virtual void writePCHWrite(raw_ostream &OS) const = 0;
91   };
92
93   class SimpleArgument : public Argument {
94     std::string type;
95
96   public:
97     SimpleArgument(Record &Arg, StringRef Attr, std::string T)
98       : Argument(Arg, Attr), type(T)
99     {}
100
101     void writeAccessors(raw_ostream &OS) const {
102       OS << "  " << type << " get" << getUpperName() << "() const {\n";
103       OS << "    return " << getLowerName() << ";\n";
104       OS << "  }";
105     }
106     void writeCloneArgs(raw_ostream &OS) const {
107       OS << getLowerName();
108     }
109     void writeCtorInitializers(raw_ostream &OS) const {
110       OS << getLowerName() << "(" << getUpperName() << ")";
111     }
112     void writeCtorParameters(raw_ostream &OS) const {
113       OS << type << " " << getUpperName();
114     }
115     void writeDeclarations(raw_ostream &OS) const {
116       OS << type << " " << getLowerName() << ";";
117     }
118     void writePCHReadDecls(raw_ostream &OS) const {
119       std::string read = ReadPCHRecord(type);
120       OS << "    " << type << " " << getLowerName() << " = " << read << ";\n";
121     }
122     void writePCHReadArgs(raw_ostream &OS) const {
123       OS << getLowerName();
124     }
125     void writePCHWrite(raw_ostream &OS) const {
126       OS << "    " << WritePCHRecord(type, "SA->get" +
127                                            std::string(getUpperName()) + "()");
128     }
129   };
130
131   class StringArgument : public Argument {
132   public:
133     StringArgument(Record &Arg, StringRef Attr)
134       : Argument(Arg, Attr)
135     {}
136
137     void writeAccessors(raw_ostream &OS) const {
138       OS << "  llvm::StringRef get" << getUpperName() << "() const {\n";
139       OS << "    return llvm::StringRef(" << getLowerName() << ", "
140          << getLowerName() << "Length);\n";
141       OS << "  }\n";
142       OS << "  unsigned get" << getUpperName() << "Length() const {\n";
143       OS << "    return " << getLowerName() << "Length;\n";
144       OS << "  }\n";
145       OS << "  void set" << getUpperName()
146          << "(ASTContext &C, llvm::StringRef S) {\n";
147       OS << "    " << getLowerName() << "Length = S.size();\n";
148       OS << "    this->" << getLowerName() << " = new (C, 1) char ["
149          << getLowerName() << "Length];\n";
150       OS << "    std::memcpy(this->" << getLowerName() << ", S.data(), "
151          << getLowerName() << "Length);\n";
152       OS << "  }";
153     }
154     void writeCloneArgs(raw_ostream &OS) const {
155       OS << "get" << getUpperName() << "()";
156     }
157     void writeCtorBody(raw_ostream &OS) const {
158       OS << "      std::memcpy(" << getLowerName() << ", " << getUpperName()
159          << ".data(), " << getLowerName() << "Length);";
160     }
161     void writeCtorInitializers(raw_ostream &OS) const {
162       OS << getLowerName() << "Length(" << getUpperName() << ".size()),"
163          << getLowerName() << "(new (Ctx, 1) char[" << getLowerName()
164          << "Length])";
165     }
166     void writeCtorParameters(raw_ostream &OS) const {
167       OS << "llvm::StringRef " << getUpperName();
168     }
169     void writeDeclarations(raw_ostream &OS) const {
170       OS << "unsigned " << getLowerName() << "Length;\n";
171       OS << "char *" << getLowerName() << ";";
172     }
173     void writePCHReadDecls(raw_ostream &OS) const {
174       OS << "    std::string " << getLowerName()
175          << "= ReadString(Record, Idx);\n";
176     }
177     void writePCHReadArgs(raw_ostream &OS) const {
178       OS << getLowerName();
179     }
180     void writePCHWrite(raw_ostream &OS) const {
181       OS << "    AddString(SA->get" << getUpperName() << "(), Record);\n";
182     }
183   };
184
185   class AlignedArgument : public Argument {
186   public:
187     AlignedArgument(Record &Arg, StringRef Attr)
188       : Argument(Arg, Attr)
189     {}
190
191     void writeAccessors(raw_ostream &OS) const {
192       OS << "  bool is" << getUpperName() << "Dependent() const;\n";
193
194       OS << "  unsigned get" << getUpperName() << "(ASTContext &Ctx) const;\n";
195
196       OS << "  bool is" << getUpperName() << "Expr() const {\n";
197       OS << "    return is" << getLowerName() << "Expr;\n";
198       OS << "  }\n";
199
200       OS << "  Expr *get" << getUpperName() << "Expr() const {\n";
201       OS << "    assert(is" << getLowerName() << "Expr);\n";
202       OS << "    return " << getLowerName() << "Expr;\n";
203       OS << "  }\n";
204
205       OS << "  TypeSourceInfo *get" << getUpperName() << "Type() const {\n";
206       OS << "    assert(!is" << getLowerName() << "Expr);\n";
207       OS << "    return " << getLowerName() << "Type;\n";
208       OS << "  }";
209     }
210     void writeAccessorDefinitions(raw_ostream &OS) const {
211       OS << "bool " << getAttrName() << "Attr::is" << getUpperName()
212          << "Dependent() const {\n";
213       OS << "  if (is" << getLowerName() << "Expr)\n";
214       OS << "    return " << getLowerName() << "Expr && (" << getLowerName()
215          << "Expr->isValueDependent() || " << getLowerName()
216          << "Expr->isTypeDependent());\n"; 
217       OS << "  else\n";
218       OS << "    return " << getLowerName()
219          << "Type->getType()->isDependentType();\n";
220       OS << "}\n";
221
222       // FIXME: Do not do the calculation here
223       // FIXME: Handle types correctly
224       // A null pointer means maximum alignment
225       // FIXME: Load the platform-specific maximum alignment, rather than
226       //        16, the x86 max.
227       OS << "unsigned " << getAttrName() << "Attr::get" << getUpperName()
228          << "(ASTContext &Ctx) const {\n";
229       OS << "  assert(!is" << getUpperName() << "Dependent());\n";
230       OS << "  if (is" << getLowerName() << "Expr)\n";
231       OS << "    return (" << getLowerName() << "Expr ? " << getLowerName()
232          << "Expr->EvaluateAsInt(Ctx).getZExtValue() : 16)"
233          << "* Ctx.getCharWidth();\n";
234       OS << "  else\n";
235       OS << "    return 0; // FIXME\n";
236       OS << "}\n";
237     }
238     void writeCloneArgs(raw_ostream &OS) const {
239       OS << "is" << getLowerName() << "Expr, is" << getLowerName()
240          << "Expr ? static_cast<void*>(" << getLowerName()
241          << "Expr) : " << getLowerName()
242          << "Type";
243     }
244     void writeCtorBody(raw_ostream &OS) const {
245       OS << "    if (is" << getLowerName() << "Expr)\n";
246       OS << "       " << getLowerName() << "Expr = reinterpret_cast<Expr *>("
247          << getUpperName() << ");\n";
248       OS << "    else\n";
249       OS << "       " << getLowerName()
250          << "Type = reinterpret_cast<TypeSourceInfo *>(" << getUpperName()
251          << ");";
252     }
253     void writeCtorInitializers(raw_ostream &OS) const {
254       OS << "is" << getLowerName() << "Expr(Is" << getUpperName() << "Expr)";
255     }
256     void writeCtorParameters(raw_ostream &OS) const {
257       OS << "bool Is" << getUpperName() << "Expr, void *" << getUpperName();
258     }
259     void writeDeclarations(raw_ostream &OS) const {
260       OS << "bool is" << getLowerName() << "Expr;\n";
261       OS << "union {\n";
262       OS << "Expr *" << getLowerName() << "Expr;\n";
263       OS << "TypeSourceInfo *" << getLowerName() << "Type;\n";
264       OS << "};";
265     }
266     void writePCHReadArgs(raw_ostream &OS) const {
267       OS << "is" << getLowerName() << "Expr, " << getLowerName() << "Ptr";
268     }
269     void writePCHReadDecls(raw_ostream &OS) const {
270       OS << "    bool is" << getLowerName() << "Expr = Record[Idx++];\n";
271       OS << "    void *" << getLowerName() << "Ptr;\n";
272       OS << "    if (is" << getLowerName() << "Expr)\n";
273       OS << "      " << getLowerName() << "Ptr = ReadExpr(F);\n";
274       OS << "    else\n";
275       OS << "      " << getLowerName()
276          << "Ptr = GetTypeSourceInfo(F, Record, Idx);\n";
277     }
278     void writePCHWrite(raw_ostream &OS) const {
279       OS << "    Record.push_back(SA->is" << getUpperName() << "Expr());\n";
280       OS << "    if (SA->is" << getUpperName() << "Expr())\n";
281       OS << "      AddStmt(SA->get" << getUpperName() << "Expr());\n";
282       OS << "    else\n";
283       OS << "      AddTypeSourceInfo(SA->get" << getUpperName()
284          << "Type(), Record);\n";
285     }
286   };
287
288   class VariadicArgument : public Argument {
289     std::string type;
290
291   public:
292     VariadicArgument(Record &Arg, StringRef Attr, std::string T)
293       : Argument(Arg, Attr), type(T)
294     {}
295
296     std::string getType() const { return type; }
297
298     void writeAccessors(raw_ostream &OS) const {
299       OS << "  typedef " << type << "* " << getLowerName() << "_iterator;\n";
300       OS << "  " << getLowerName() << "_iterator " << getLowerName()
301          << "_begin() const {\n";
302       OS << "    return " << getLowerName() << ";\n";
303       OS << "  }\n";
304       OS << "  " << getLowerName() << "_iterator " << getLowerName()
305          << "_end() const {\n";
306       OS << "    return " << getLowerName() << " + " << getLowerName()
307          << "Size;\n";
308       OS << "  }\n";
309       OS << "  unsigned " << getLowerName() << "_size() const {\n"
310          << "    return " << getLowerName() << "Size;\n;";
311       OS << "  }";
312     }
313     void writeCloneArgs(raw_ostream &OS) const {
314       OS << getLowerName() << ", " << getLowerName() << "Size";
315     }
316     void writeCtorBody(raw_ostream &OS) const {
317       // FIXME: memcpy is not safe on non-trivial types.
318       OS << "    std::memcpy(" << getLowerName() << ", " << getUpperName()
319          << ", " << getLowerName() << "Size * sizeof(" << getType() << "));\n";
320     }
321     void writeCtorInitializers(raw_ostream &OS) const {
322       OS << getLowerName() << "Size(" << getUpperName() << "Size), "
323          << getLowerName() << "(new (Ctx, 16) " << getType() << "["
324          << getLowerName() << "Size])";
325     }
326     void writeCtorParameters(raw_ostream &OS) const {
327       OS << getType() << " *" << getUpperName() << ", unsigned "
328          << getUpperName() << "Size";
329     }
330     void writeDeclarations(raw_ostream &OS) const {
331       OS << "  unsigned " << getLowerName() << "Size;\n";
332       OS << "  " << getType() << " *" << getLowerName() << ";";
333     }
334     void writePCHReadDecls(raw_ostream &OS) const {
335       OS << "  unsigned " << getLowerName() << "Size = Record[Idx++];\n";
336       OS << "  llvm::SmallVector<" << type << ", 4> " << getLowerName()
337          << ";\n";
338       OS << "  " << getLowerName() << ".reserve(" << getLowerName()
339          << "Size);\n";
340       OS << "  for (unsigned i = " << getLowerName() << "Size; i; --i)\n";
341       
342       std::string read = ReadPCHRecord(type);
343       OS << "    " << getLowerName() << ".push_back(" << read << ");\n";
344     }
345     void writePCHReadArgs(raw_ostream &OS) const {
346       OS << getLowerName() << ".data(), " << getLowerName() << "Size";
347     }
348     void writePCHWrite(raw_ostream &OS) const{
349       OS << "    Record.push_back(SA->" << getLowerName() << "_size());\n";
350       OS << "    for (" << getAttrName() << "Attr::" << getLowerName()
351          << "_iterator i = SA->" << getLowerName() << "_begin(), e = SA->"
352          << getLowerName() << "_end(); i != e; ++i)\n";
353       OS << "      " << WritePCHRecord(type, "(*i)");
354     }
355   };
356
357   class EnumArgument : public Argument {
358     std::string type;
359     std::vector<StringRef> values, enums;
360   public:
361     EnumArgument(Record &Arg, StringRef Attr)
362       : Argument(Arg, Attr), type(Arg.getValueAsString("Type")),
363         values(getValueAsListOfStrings(Arg, "Values")),
364         enums(getValueAsListOfStrings(Arg, "Enums"))
365     {}
366
367     void writeAccessors(raw_ostream &OS) const {
368       OS << "  " << type << " get" << getUpperName() << "() const {\n";
369       OS << "    return " << getLowerName() << ";\n";
370       OS << "  }";
371     }
372     void writeCloneArgs(raw_ostream &OS) const {
373       OS << getLowerName();
374     }
375     void writeCtorInitializers(raw_ostream &OS) const {
376       OS << getLowerName() << "(" << getUpperName() << ")";
377     }
378     void writeCtorParameters(raw_ostream &OS) const {
379       OS << type << " " << getUpperName();
380     }
381     void writeDeclarations(raw_ostream &OS) const {
382       // Calculate the various enum values
383       std::vector<StringRef> uniques(enums);
384       std::sort(uniques.begin(), uniques.end());
385       uniques.erase(std::unique(uniques.begin(), uniques.end()),
386                     uniques.end());
387       // FIXME: Emit a proper error
388       assert(!uniques.empty());
389
390       std::vector<StringRef>::iterator i = uniques.begin(),
391                                        e = uniques.end();
392       // The last one needs to not have a comma.
393       --e;
394
395       OS << "public:\n";
396       OS << "  enum " << type << " {\n";
397       for (; i != e; ++i)
398         OS << "    " << *i << ",\n";
399       OS << "    " << *e << "\n";
400       OS << "  };\n";
401       OS << "private:\n";
402       OS << "  " << type << " " << getLowerName() << ";";
403     }
404     void writePCHReadDecls(raw_ostream &OS) const {
405       OS << "    " << getAttrName() << "Attr::" << type << " " << getLowerName()
406          << "(static_cast<" << getAttrName() << "Attr::" << type
407          << ">(Record[Idx++]));\n";
408     }
409     void writePCHReadArgs(raw_ostream &OS) const {
410       OS << getLowerName();
411     }
412     void writePCHWrite(raw_ostream &OS) const {
413       OS << "Record.push_back(SA->get" << getUpperName() << "());\n";
414     }
415   };
416 }
417
418 static Argument *createArgument(Record &Arg, StringRef Attr,
419                                 Record *Search = 0) {
420   if (!Search)
421     Search = &Arg;
422
423   Argument *Ptr = 0;
424   llvm::StringRef ArgName = Search->getName();
425
426   if (ArgName == "AlignedArgument") Ptr = new AlignedArgument(Arg, Attr);
427   else if (ArgName == "EnumArgument") Ptr = new EnumArgument(Arg, Attr);
428   else if (ArgName == "ExprArgument") Ptr = new SimpleArgument(Arg, Attr,
429                                                                "Expr *");
430   else if (ArgName == "FunctionArgument")
431     Ptr = new SimpleArgument(Arg, Attr, "FunctionDecl *");
432   else if (ArgName == "IdentifierArgument")
433     Ptr = new SimpleArgument(Arg, Attr, "IdentifierInfo *");
434   else if (ArgName == "IntArgument") Ptr = new SimpleArgument(Arg, Attr, "int");
435   else if (ArgName == "StringArgument") Ptr = new StringArgument(Arg, Attr);
436   else if (ArgName == "TypeArgument")
437     Ptr = new SimpleArgument(Arg, Attr, "QualType");
438   else if (ArgName == "UnsignedArgument")
439     Ptr = new SimpleArgument(Arg, Attr, "unsigned");
440   else if (ArgName == "VariadicUnsignedArgument")
441     Ptr = new VariadicArgument(Arg, Attr, "unsigned");
442
443   if (!Ptr) {
444     std::vector<Record*> Bases = Search->getSuperClasses();
445     for (std::vector<Record*>::iterator i = Bases.begin(), e = Bases.end();
446          i != e; ++i) {
447       Ptr = createArgument(Arg, Attr, *i);
448       if (Ptr)
449         break;
450     }
451   }
452   return Ptr;
453 }
454
455 void ClangAttrClassEmitter::run(raw_ostream &OS) {
456   OS << "// This file is generated by TableGen. Do not edit.\n\n";
457   OS << "#ifndef LLVM_CLANG_ATTR_CLASSES_INC\n";
458   OS << "#define LLVM_CLANG_ATTR_CLASSES_INC\n\n";
459
460   std::vector<Record*> Attrs = Records.getAllDerivedDefinitions("Attr");
461
462   for (std::vector<Record*>::iterator i = Attrs.begin(), e = Attrs.end();
463        i != e; ++i) {
464     Record &R = **i;
465     const std::string &SuperName = R.getSuperClasses().back()->getName();
466
467     OS << "class " << R.getName() << "Attr : public " << SuperName << " {\n";
468
469     std::vector<Record*> ArgRecords = R.getValueAsListOfDefs("Args");
470     std::vector<Argument*> Args;
471     std::vector<Argument*>::iterator ai, ae;
472     Args.reserve(ArgRecords.size());
473
474     for (std::vector<Record*>::iterator ri = ArgRecords.begin(),
475                                         re = ArgRecords.end();
476          ri != re; ++ri) {
477       Record &ArgRecord = **ri;
478       Argument *Arg = createArgument(ArgRecord, R.getName());
479       assert(Arg);
480       Args.push_back(Arg);
481
482       Arg->writeDeclarations(OS);
483       OS << "\n\n";
484     }
485
486     ae = Args.end();
487
488     OS << "\n public:\n";
489     OS << "  " << R.getName() << "Attr(SourceLocation L, ASTContext &Ctx\n";
490     
491     for (ai = Args.begin(); ai != ae; ++ai) {
492       OS << "              , ";
493       (*ai)->writeCtorParameters(OS);
494       OS << "\n";
495     }
496     
497     OS << "             )\n";
498     OS << "    : " << SuperName << "(attr::" << R.getName() << ", L)\n";
499
500     for (ai = Args.begin(); ai != ae; ++ai) {
501       OS << "              , ";
502       (*ai)->writeCtorInitializers(OS);
503       OS << "\n";
504     }
505
506     OS << "  {\n";
507   
508     for (ai = Args.begin(); ai != ae; ++ai) {
509       (*ai)->writeCtorBody(OS);
510       OS << "\n";
511     }
512     OS << "  }\n\n";
513
514     OS << "  virtual " << R.getName() << "Attr *clone (ASTContext &C) const;\n";
515
516     for (ai = Args.begin(); ai != ae; ++ai) {
517       (*ai)->writeAccessors(OS);
518       OS << "\n\n";
519     }
520
521     OS << R.getValueAsCode("AdditionalMembers");
522     OS << "\n\n";
523
524     OS << "  static bool classof(const Attr *A) { return A->getKind() == "
525        << "attr::" << R.getName() << "; }\n";
526     OS << "  static bool classof(const " << R.getName()
527        << "Attr *) { return true; }\n";
528     OS << "};\n\n";
529   }
530
531   OS << "#endif\n";
532 }
533
534 void ClangAttrImplEmitter::run(raw_ostream &OS) {
535   OS << "// This file is generated by TableGen. Do not edit.\n\n";
536
537   std::vector<Record*> Attrs = Records.getAllDerivedDefinitions("Attr");
538   std::vector<Record*>::iterator i = Attrs.begin(), e = Attrs.end(), ri, re;
539   std::vector<Argument*>::iterator ai, ae;
540
541   for (; i != e; ++i) {
542     Record &R = **i;
543     std::vector<Record*> ArgRecords = R.getValueAsListOfDefs("Args");
544     std::vector<Argument*> Args;
545     for (ri = ArgRecords.begin(), re = ArgRecords.end(); ri != re; ++ri)
546       Args.push_back(createArgument(**ri, R.getName()));
547
548     for (ai = Args.begin(), ae = Args.end(); ai != ae; ++ai)
549       (*ai)->writeAccessorDefinitions(OS);
550
551     OS << R.getName() << "Attr *" << R.getName()
552        << "Attr::clone(ASTContext &C) const {\n";
553     OS << "  return new (C) " << R.getName() << "Attr(getLocation(), C";
554     for (ai = Args.begin(); ai != ae; ++ai) {
555       OS << ", ";
556       (*ai)->writeCloneArgs(OS);
557     }
558     OS << ");\n}\n\n";
559   }
560 }
561
562 static void EmitAttrList(raw_ostream &OS, StringRef Class,
563                          const std::vector<Record*> &AttrList) {
564   std::vector<Record*>::const_iterator i = AttrList.begin(), e = AttrList.end();
565
566   if (i != e) {
567     // Move the end iterator back to emit the last attribute.
568     for(--e; i != e; ++i)
569       OS << Class << "(" << (*i)->getName() << ")\n";
570     
571     OS << "LAST_" << Class << "(" << (*i)->getName() << ")\n\n";
572   }
573 }
574
575 void ClangAttrListEmitter::run(raw_ostream &OS) {
576   OS << "// This file is generated by TableGen. Do not edit.\n\n";
577
578   OS << "#ifndef LAST_ATTR\n";
579   OS << "#define LAST_ATTR(NAME) ATTR(NAME)\n";
580   OS << "#endif\n\n";
581
582   OS << "#ifndef INHERITABLE_ATTR\n";
583   OS << "#define INHERITABLE_ATTR(NAME) ATTR(NAME)\n";
584   OS << "#endif\n\n";
585
586   OS << "#ifndef LAST_INHERITABLE_ATTR\n";
587   OS << "#define LAST_INHERITABLE_ATTR(NAME) INHERITABLE_ATTR(NAME)\n";
588   OS << "#endif\n\n";
589
590   Record *InhClass = Records.getClass("InheritableAttr");
591   std::vector<Record*> Attrs = Records.getAllDerivedDefinitions("Attr"),
592                        NonInhAttrs, InhAttrs;
593   for (std::vector<Record*>::iterator i = Attrs.begin(), e = Attrs.end();
594        i != e; ++i) {
595     if ((*i)->isSubClassOf(InhClass))
596       InhAttrs.push_back(*i);
597     else
598       NonInhAttrs.push_back(*i);
599   }
600
601   EmitAttrList(OS, "INHERITABLE_ATTR", InhAttrs);
602   EmitAttrList(OS, "ATTR", NonInhAttrs);
603
604   OS << "#undef LAST_ATTR\n";
605   OS << "#undef INHERITABLE_ATTR\n";
606   OS << "#undef LAST_INHERITABLE_ATTR\n";
607   OS << "#undef ATTR\n";
608 }
609
610 void ClangAttrPCHReadEmitter::run(raw_ostream &OS) {
611   OS << "// This file is generated by TableGen. Do not edit.\n\n";
612
613   Record *InhClass = Records.getClass("InheritableAttr");
614   std::vector<Record*> Attrs = Records.getAllDerivedDefinitions("Attr"),
615                        ArgRecords;
616   std::vector<Record*>::iterator i = Attrs.begin(), e = Attrs.end(), ai, ae;
617   std::vector<Argument*> Args;
618   std::vector<Argument*>::iterator ri, re;
619
620   OS << "  switch (Kind) {\n";
621   OS << "  default:\n";
622   OS << "    assert(0 && \"Unknown attribute!\");\n";
623   OS << "    break;\n";
624   for (; i != e; ++i) {
625     Record &R = **i;
626     OS << "  case attr::" << R.getName() << ": {\n";
627     if (R.isSubClassOf(InhClass))
628       OS << "    bool isInherited = Record[Idx++];\n";
629     ArgRecords = R.getValueAsListOfDefs("Args");
630     Args.clear();
631     for (ai = ArgRecords.begin(), ae = ArgRecords.end(); ai != ae; ++ai) {
632       Argument *A = createArgument(**ai, R.getName());
633       Args.push_back(A);
634       A->writePCHReadDecls(OS);
635     }
636     OS << "    New = new (*Context) " << R.getName() << "Attr(Loc, *Context";
637     for (ri = Args.begin(), re = Args.end(); ri != re; ++ri) {
638       OS << ", ";
639       (*ri)->writePCHReadArgs(OS);
640     }
641     OS << ");\n";
642     if (R.isSubClassOf(InhClass))
643       OS << "    cast<InheritableAttr>(New)->setInherited(isInherited);\n";
644     OS << "    break;\n";
645     OS << "  }\n";
646   }
647   OS << "  }\n";
648 }
649
650 void ClangAttrPCHWriteEmitter::run(raw_ostream &OS) {
651   Record *InhClass = Records.getClass("InheritableAttr");
652   std::vector<Record*> Attrs = Records.getAllDerivedDefinitions("Attr"), Args;
653   std::vector<Record*>::iterator i = Attrs.begin(), e = Attrs.end(), ai, ae;
654
655   OS << "  switch (A->getKind()) {\n";
656   OS << "  default:\n";
657   OS << "    llvm_unreachable(\"Unknown attribute kind!\");\n";
658   OS << "    break;\n";
659   for (; i != e; ++i) {
660     Record &R = **i;
661     OS << "  case attr::" << R.getName() << ": {\n";
662     Args = R.getValueAsListOfDefs("Args");
663     if (R.isSubClassOf(InhClass) || !Args.empty())
664       OS << "    const " << R.getName() << "Attr *SA = cast<" << R.getName()
665          << "Attr>(A);\n";
666     if (R.isSubClassOf(InhClass))
667       OS << "    Record.push_back(SA->isInherited());\n";
668     for (ai = Args.begin(), ae = Args.end(); ai != ae; ++ai)
669       createArgument(**ai, R.getName())->writePCHWrite(OS);
670     OS << "    break;\n";
671     OS << "  }\n";
672   }
673   OS << "  }\n";
674 }
675
676 void ClangAttrSpellingListEmitter::run(raw_ostream &OS) {
677   OS << "// This file is generated by TableGen. Do not edit.\n\n";
678
679   std::vector<Record*> Attrs = Records.getAllDerivedDefinitions("Attr");
680   
681   for (std::vector<Record*>::iterator I = Attrs.begin(), E = Attrs.end(); I != E; ++I) {
682     Record &Attr = **I;
683
684     std::vector<StringRef> Spellings = getValueAsListOfStrings(Attr, "Spellings");
685
686     for (std::vector<StringRef>::const_iterator I = Spellings.begin(), E = Spellings.end(); I != E; ++I) {
687       StringRef Spelling = *I;
688       OS << ".Case(\"" << Spelling << "\", true)\n";
689     }
690   }
691
692 }