Attr.h revision cf2a7211b4785068c7efa836baab90b198a4d2a6
1//===--- Attr.h - Classes for representing expressions ----------*- 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//  This file defines the Attr interface and subclasses.
11//
12//===----------------------------------------------------------------------===//
13
14#ifndef LLVM_CLANG_AST_ATTR_H
15#define LLVM_CLANG_AST_ATTR_H
16
17#include <cassert>
18#include <cstring>
19#include <string>
20#include <algorithm>
21
22namespace clang {
23  class ASTContext;
24
25/// Attr - This represents one attribute.
26class Attr {
27public:
28  enum Kind {
29    Alias,
30    Aligned,
31    AlwaysInline,
32    AnalyzerNoReturn, // Clang-specific.
33    Annotate,
34    AsmLabel, // Represent GCC asm label extension.
35    Blocks,
36    Cleanup,
37    Const,
38    Constructor,
39    DLLExport,
40    DLLImport,
41    Deprecated,
42    Destructor,
43    FastCall,
44    Format,
45    GNUInline,
46    IBOutletKind, // Clang-specific.  Use "Kind" suffix to not conflict with
47    NoReturn,
48    NoThrow,
49    Nodebug,
50    Noinline,
51    NonNull,
52    ObjCException,
53    ObjCNSObject,
54    Overloadable, // Clang-specific
55    Packed,
56    Pure,
57    Regparm,
58    Section,
59    StdCall,
60    TransparentUnion,
61    Unavailable,
62    Unused,
63    Used,
64    Visibility,
65    WarnUnusedResult,
66    Weak,
67    WeakImport
68  };
69
70private:
71  Attr *Next;
72  Kind AttrKind;
73  bool Inherited : 1;
74
75protected:
76  void* operator new(size_t bytes) throw() {
77    assert(0 && "Attrs cannot be allocated with regular 'new'.");
78    return 0;
79  }
80  void operator delete(void* data) throw() {
81    assert(0 && "Attrs cannot be released with regular 'delete'.");
82  }
83
84protected:
85  Attr(Kind AK) : Next(0), AttrKind(AK), Inherited(false) {}
86  virtual ~Attr() {
87    assert(Next == 0 && "Destroy didn't work");
88  }
89public:
90
91  void Destroy(ASTContext &C);
92
93  /// \brief Whether this attribute should be merged to new
94  /// declarations.
95  virtual bool isMerged() const { return true; }
96
97  Kind getKind() const { return AttrKind; }
98
99  Attr *getNext() { return Next; }
100  const Attr *getNext() const { return Next; }
101  void setNext(Attr *next) { Next = next; }
102
103  bool isInherited() const { return Inherited; }
104  void setInherited(bool value) { Inherited = value; }
105
106  void addAttr(Attr *attr) {
107    assert((attr != 0) && "addAttr(): attr is null");
108
109    // FIXME: This doesn't preserve the order in any way.
110    attr->Next = Next;
111    Next = attr;
112  }
113
114  // Implement isa/cast/dyncast/etc.
115  static bool classof(const Attr *) { return true; }
116};
117
118class PackedAttr : public Attr {
119  unsigned Alignment;
120
121public:
122  PackedAttr(unsigned alignment) : Attr(Packed), Alignment(alignment) {}
123
124  /// getAlignment - The specified alignment in bits.
125  unsigned getAlignment() const { return Alignment; }
126
127  // Implement isa/cast/dyncast/etc.
128  static bool classof(const Attr *A) {
129    return A->getKind() == Packed;
130  }
131  static bool classof(const PackedAttr *A) { return true; }
132};
133
134class AlignedAttr : public Attr {
135  unsigned Alignment;
136public:
137  AlignedAttr(unsigned alignment) : Attr(Aligned), Alignment(alignment) {}
138
139  /// getAlignment - The specified alignment in bits.
140  unsigned getAlignment() const { return Alignment; }
141
142  // Implement isa/cast/dyncast/etc.
143  static bool classof(const Attr *A) {
144    return A->getKind() == Aligned;
145  }
146  static bool classof(const AlignedAttr *A) { return true; }
147};
148
149class AnnotateAttr : public Attr {
150  std::string Annotation;
151public:
152  AnnotateAttr(const std::string &ann) : Attr(Annotate), Annotation(ann) {}
153
154  const std::string& getAnnotation() const { return Annotation; }
155
156  // Implement isa/cast/dyncast/etc.
157  static bool classof(const Attr *A) {
158    return A->getKind() == Annotate;
159  }
160  static bool classof(const AnnotateAttr *A) { return true; }
161};
162
163class AsmLabelAttr : public Attr {
164  std::string Label;
165public:
166  AsmLabelAttr(const std::string &L) : Attr(AsmLabel), Label(L) {}
167
168  const std::string& getLabel() const { return Label; }
169
170  // Implement isa/cast/dyncast/etc.
171  static bool classof(const Attr *A) {
172    return A->getKind() == AsmLabel;
173  }
174  static bool classof(const AsmLabelAttr *A) { return true; }
175};
176
177class AlwaysInlineAttr : public Attr {
178public:
179  AlwaysInlineAttr() : Attr(AlwaysInline) {}
180
181  // Implement isa/cast/dyncast/etc.
182
183  static bool classof(const Attr *A) { return A->getKind() == AlwaysInline; }
184  static bool classof(const AlwaysInlineAttr *A) { return true; }
185};
186
187class AliasAttr : public Attr {
188  std::string Aliasee;
189public:
190  AliasAttr(const std::string &aliasee) : Attr(Alias), Aliasee(aliasee) {}
191
192  const std::string& getAliasee() const { return Aliasee; }
193
194  // Implement isa/cast/dyncast/etc.
195
196  static bool classof(const Attr *A) { return A->getKind() == Alias; }
197  static bool classof(const AliasAttr *A) { return true; }
198};
199
200class ConstructorAttr : public Attr {
201  int priority;
202public:
203  ConstructorAttr(int p) : Attr(Constructor), priority(p) {}
204
205  int getPriority() const { return priority; }
206
207  // Implement isa/cast/dyncast/etc.
208  static bool classof(const Attr *A) { return A->getKind() == Constructor; }
209  static bool classof(const ConstructorAttr *A) { return true; }
210};
211
212class DestructorAttr : public Attr {
213  int priority;
214public:
215  DestructorAttr(int p) : Attr(Destructor), priority(p) {}
216
217  int getPriority() const { return priority; }
218
219  // Implement isa/cast/dyncast/etc.
220  static bool classof(const Attr *A) { return A->getKind() == Destructor; }
221  static bool classof(const DestructorAttr *A) { return true; }
222};
223
224
225class GNUInlineAttr : public Attr {
226public:
227  GNUInlineAttr() : Attr(GNUInline) {}
228
229  // Implement isa/cast/dyncast/etc.
230  static bool classof(const Attr *A) { return A->getKind() == GNUInline; }
231  static bool classof(const GNUInlineAttr *A) { return true; }
232};
233
234class IBOutletAttr : public Attr {
235public:
236  IBOutletAttr() : Attr(IBOutletKind) {}
237
238  // Implement isa/cast/dyncast/etc.
239  static bool classof(const Attr *A) {
240    return A->getKind() == IBOutletKind;
241  }
242  static bool classof(const IBOutletAttr *A) { return true; }
243};
244
245class NoReturnAttr : public Attr {
246public:
247  NoReturnAttr() : Attr(NoReturn) {}
248
249  // Implement isa/cast/dyncast/etc.
250  static bool classof(const Attr *A) { return A->getKind() == NoReturn; }
251  static bool classof(const NoReturnAttr *A) { return true; }
252};
253
254class AnalyzerNoReturnAttr : public Attr {
255public:
256  AnalyzerNoReturnAttr() : Attr(AnalyzerNoReturn) {}
257
258  // Implement isa/cast/dyncast/etc.
259  static bool classof(const Attr *A) {
260    return A->getKind() == AnalyzerNoReturn;
261  }
262  static bool classof(const AnalyzerNoReturnAttr *A) { return true; }
263};
264
265class DeprecatedAttr : public Attr {
266public:
267  DeprecatedAttr() : Attr(Deprecated) {}
268
269  // Implement isa/cast/dyncast/etc.
270  static bool classof(const Attr *A) { return A->getKind() == Deprecated; }
271  static bool classof(const DeprecatedAttr *A) { return true; }
272};
273
274class SectionAttr : public Attr {
275  std::string Name;
276public:
277  SectionAttr(const std::string &N) : Attr(Section), Name(N) {}
278
279  const std::string& getName() const { return Name; }
280
281  // Implement isa/cast/dyncast/etc.
282  static bool classof(const Attr *A) {
283    return A->getKind() == Section;
284  }
285  static bool classof(const SectionAttr *A) { return true; }
286};
287
288class UnavailableAttr : public Attr {
289public:
290  UnavailableAttr() : Attr(Unavailable) {}
291
292  // Implement isa/cast/dyncast/etc.
293
294  static bool classof(const Attr *A) { return A->getKind() == Unavailable; }
295  static bool classof(const UnavailableAttr *A) { return true; }
296};
297
298class UnusedAttr : public Attr {
299public:
300  UnusedAttr() : Attr(Unused) {}
301
302  // Implement isa/cast/dyncast/etc.
303  static bool classof(const Attr *A) { return A->getKind() == Unused; }
304  static bool classof(const UnusedAttr *A) { return true; }
305};
306
307class UsedAttr : public Attr {
308public:
309  UsedAttr() : Attr(Used) {}
310
311  // Implement isa/cast/dyncast/etc.
312  static bool classof(const Attr *A) { return A->getKind() == Used; }
313  static bool classof(const UsedAttr *A) { return true; }
314};
315
316class WeakAttr : public Attr {
317public:
318  WeakAttr() : Attr(Weak) {}
319
320  // Implement isa/cast/dyncast/etc.
321
322  static bool classof(const Attr *A) { return A->getKind() == Weak; }
323  static bool classof(const WeakAttr *A) { return true; }
324};
325
326class WeakImportAttr : public Attr {
327public:
328  WeakImportAttr() : Attr(WeakImport) {}
329
330  // Implement isa/cast/dyncast/etc.
331
332  static bool classof(const Attr *A) { return A->getKind() == WeakImport; }
333  static bool classof(const WeakImportAttr *A) { return true; }
334};
335
336class NoThrowAttr : public Attr {
337public:
338  NoThrowAttr() : Attr(NoThrow) {}
339
340  // Implement isa/cast/dyncast/etc.
341  static bool classof(const Attr *A) { return A->getKind() == NoThrow; }
342  static bool classof(const NoThrowAttr *A) { return true; }
343};
344
345class ConstAttr : public Attr {
346public:
347  ConstAttr() : Attr(Const) {}
348
349  // Implement isa/cast/dyncast/etc.
350  static bool classof(const Attr *A) { return A->getKind() == Const; }
351  static bool classof(const ConstAttr *A) { return true; }
352};
353
354class PureAttr : public Attr {
355public:
356  PureAttr() : Attr(Pure) {}
357
358  // Implement isa/cast/dyncast/etc.
359  static bool classof(const Attr *A) { return A->getKind() == Pure; }
360  static bool classof(const PureAttr *A) { return true; }
361};
362
363class NonNullAttr : public Attr {
364  unsigned* ArgNums;
365  unsigned Size;
366public:
367  NonNullAttr(unsigned* arg_nums = 0, unsigned size = 0) : Attr(NonNull),
368    ArgNums(0), Size(0) {
369
370    if (size == 0) return;
371    assert(arg_nums);
372    ArgNums = new unsigned[size];
373    Size = size;
374    memcpy(ArgNums, arg_nums, sizeof(*ArgNums)*size);
375  }
376
377  virtual ~NonNullAttr() {
378    delete [] ArgNums;
379  }
380
381  typedef const unsigned *iterator;
382  iterator begin() const { return ArgNums; }
383  iterator end() const { return ArgNums + Size; }
384  unsigned size() const { return Size; }
385
386  bool isNonNull(unsigned arg) const {
387    return ArgNums ? std::binary_search(ArgNums, ArgNums+Size, arg) : true;
388  }
389
390  static bool classof(const Attr *A) { return A->getKind() == NonNull; }
391  static bool classof(const NonNullAttr *A) { return true; }
392};
393
394class FormatAttr : public Attr {
395  std::string Type;
396  int formatIdx, firstArg;
397public:
398  FormatAttr(const std::string &type, int idx, int first) : Attr(Format),
399             Type(type), formatIdx(idx), firstArg(first) {}
400
401  const std::string& getType() const { return Type; }
402  void setType(const std::string &type) { Type = type; }
403  int getFormatIdx() const { return formatIdx; }
404  int getFirstArg() const { return firstArg; }
405
406  // Implement isa/cast/dyncast/etc.
407
408  static bool classof(const Attr *A) { return A->getKind() == Format; }
409  static bool classof(const FormatAttr *A) { return true; }
410};
411
412class VisibilityAttr : public Attr {
413public:
414  /// @brief An enumeration for the kinds of visibility of symbols.
415  enum VisibilityTypes {
416    DefaultVisibility = 0,
417    HiddenVisibility,
418    ProtectedVisibility
419  };
420private:
421  VisibilityTypes VisibilityType;
422public:
423  VisibilityAttr(VisibilityTypes v) : Attr(Visibility),
424                 VisibilityType(v) {}
425
426  VisibilityTypes getVisibility() const { return VisibilityType; }
427
428  // Implement isa/cast/dyncast/etc.
429
430  static bool classof(const Attr *A) { return A->getKind() == Visibility; }
431  static bool classof(const VisibilityAttr *A) { return true; }
432};
433
434class DLLImportAttr : public Attr {
435public:
436  DLLImportAttr() : Attr(DLLImport) {}
437
438  // Implement isa/cast/dyncast/etc.
439
440  static bool classof(const Attr *A) { return A->getKind() == DLLImport; }
441  static bool classof(const DLLImportAttr *A) { return true; }
442};
443
444class DLLExportAttr : public Attr {
445public:
446  DLLExportAttr() : Attr(DLLExport) {}
447
448  // Implement isa/cast/dyncast/etc.
449
450  static bool classof(const Attr *A) { return A->getKind() == DLLExport; }
451  static bool classof(const DLLExportAttr *A) { return true; }
452};
453
454class FastCallAttr : public Attr {
455public:
456  FastCallAttr() : Attr(FastCall) {}
457
458  // Implement isa/cast/dyncast/etc.
459
460  static bool classof(const Attr *A) { return A->getKind() == FastCall; }
461  static bool classof(const FastCallAttr *A) { return true; }
462};
463
464class StdCallAttr : public Attr {
465public:
466  StdCallAttr() : Attr(StdCall) {}
467
468  // Implement isa/cast/dyncast/etc.
469
470  static bool classof(const Attr *A) { return A->getKind() == StdCall; }
471  static bool classof(const StdCallAttr *A) { return true; }
472};
473
474class TransparentUnionAttr : public Attr {
475public:
476  TransparentUnionAttr() : Attr(TransparentUnion) {}
477
478  // Implement isa/cast/dyncast/etc.
479
480  static bool classof(const Attr *A) { return A->getKind() == TransparentUnion; }
481  static bool classof(const TransparentUnionAttr *A) { return true; }
482};
483
484class ObjCNSObjectAttr : public Attr {
485// Implement isa/cast/dyncast/etc.
486public:
487  ObjCNSObjectAttr() : Attr(ObjCNSObject) {}
488
489static bool classof(const Attr *A) { return A->getKind() == ObjCNSObject; }
490static bool classof(const ObjCNSObjectAttr *A) { return true; }
491};
492
493
494class ObjCExceptionAttr : public Attr {
495public:
496  ObjCExceptionAttr() : Attr(ObjCException) {}
497
498  // Implement isa/cast/dyncast/etc.
499  static bool classof(const Attr *A) { return A->getKind() == ObjCException; }
500  static bool classof(const ObjCExceptionAttr *A) { return true; }
501};
502
503
504class OverloadableAttr : public Attr {
505public:
506  OverloadableAttr() : Attr(Overloadable) { }
507
508  virtual bool isMerged() const { return false; }
509
510  static bool classof(const Attr *A) { return A->getKind() == Overloadable; }
511  static bool classof(const OverloadableAttr *) { return true; }
512};
513
514class BlocksAttr : public Attr {
515public:
516  enum BlocksAttrTypes {
517    ByRef = 0
518  };
519private:
520  BlocksAttrTypes BlocksAttrType;
521public:
522  BlocksAttr(BlocksAttrTypes t) : Attr(Blocks), BlocksAttrType(t) {}
523
524  BlocksAttrTypes getType() const { return BlocksAttrType; }
525
526  // Implement isa/cast/dyncast/etc.
527
528  static bool classof(const Attr *A) { return A->getKind() == Blocks; }
529  static bool classof(const BlocksAttr *A) { return true; }
530};
531
532class FunctionDecl;
533
534class CleanupAttr : public Attr {
535  FunctionDecl *FD;
536
537public:
538  CleanupAttr(FunctionDecl *fd) : Attr(Cleanup), FD(fd) {}
539
540  const FunctionDecl *getFunctionDecl() const { return FD; }
541
542  // Implement isa/cast/dyncast/etc.
543
544  static bool classof(const Attr *A) { return A->getKind() == Cleanup; }
545  static bool classof(const CleanupAttr *A) { return true; }
546};
547
548class NodebugAttr : public Attr {
549public:
550  NodebugAttr() : Attr(Nodebug) {}
551
552  // Implement isa/cast/dyncast/etc.
553
554  static bool classof(const Attr *A) { return A->getKind() == Nodebug; }
555  static bool classof(const NodebugAttr *A) { return true; }
556};
557
558class WarnUnusedResultAttr : public Attr {
559public:
560  WarnUnusedResultAttr() : Attr(WarnUnusedResult) {}
561
562  // Implement isa/cast/dyncast/etc.
563  static bool classof(const Attr *A) { return A->getKind() == WarnUnusedResult;}
564  static bool classof(const WarnUnusedResultAttr *A) { return true; }
565};
566
567class NoinlineAttr : public Attr {
568public:
569  NoinlineAttr() : Attr(Noinline) {}
570
571  // Implement isa/cast/dyncast/etc.
572
573  static bool classof(const Attr *A) { return A->getKind() == Noinline; }
574  static bool classof(const NoinlineAttr *A) { return true; }
575};
576
577class RegparmAttr : public Attr {
578  unsigned NumParams;
579
580public:
581  RegparmAttr(unsigned np) : Attr(Regparm), NumParams(np) {}
582
583  unsigned getNumParams() const { return NumParams; }
584
585  // Implement isa/cast/dyncast/etc.
586
587  static bool classof(const Attr *A) { return A->getKind() == Regparm; }
588  static bool classof(const RegparmAttr *A) { return true; }
589};
590}  // end namespace clang
591
592#endif
593