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