DeclCXX.h revision 35bc0821c4f80041724cd4c5c4889b2581546a41
1//===-- DeclCXX.h - Classes for representing C++ declarations *- 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 C++ Decl subclasses.
11//
12//===----------------------------------------------------------------------===//
13
14#ifndef LLVM_CLANG_AST_DECLCXX_H
15#define LLVM_CLANG_AST_DECLCXX_H
16
17#include "clang/AST/Decl.h"
18
19namespace clang {
20class CXXRecordDecl;
21
22/// CXXFieldDecl - Represents an instance field of a C++ struct/union/class.
23class CXXFieldDecl : public FieldDecl {
24  CXXRecordDecl *Parent;
25
26  CXXFieldDecl(CXXRecordDecl *RD, SourceLocation L, IdentifierInfo *Id,
27               QualType T, Expr *BW = NULL)
28    : FieldDecl(CXXField, L, Id, T, BW), Parent(RD) {}
29public:
30  static CXXFieldDecl *Create(ASTContext &C, CXXRecordDecl *RD,SourceLocation L,
31                              IdentifierInfo *Id, QualType T, Expr *BW = NULL);
32
33  void setAccess(AccessSpecifier AS) { Access = AS; }
34  AccessSpecifier getAccess() const { return AccessSpecifier(Access); }
35  CXXRecordDecl *getParent() const { return Parent; }
36
37  // Implement isa/cast/dyncast/etc.
38  static bool classof(const Decl *D) { return D->getKind() == CXXField; }
39  static bool classof(const CXXFieldDecl *D) { return true; }
40};
41
42/// CXXRecordDecl - Represents a C++ struct/union/class.
43/// The only difference with RecordDecl is that CXXRecordDecl is a DeclContext.
44class CXXRecordDecl : public RecordDecl, public DeclContext {
45  CXXRecordDecl(TagKind TK, DeclContext *DC,
46                SourceLocation L, IdentifierInfo *Id)
47    : RecordDecl(CXXRecord, TK, DC, L, Id), DeclContext(CXXRecord) {}
48public:
49  static CXXRecordDecl *Create(ASTContext &C, TagKind TK, DeclContext *DC,
50                               SourceLocation L, IdentifierInfo *Id,
51                               CXXRecordDecl* PrevDecl=0);
52
53  const CXXFieldDecl *getMember(unsigned i) const {
54    return cast<const CXXFieldDecl>(RecordDecl::getMember(i));
55  }
56  CXXFieldDecl *getMember(unsigned i) {
57    return cast<CXXFieldDecl>(RecordDecl::getMember(i));
58  }
59
60  /// getMember - If the member doesn't exist, or there are no members, this
61  /// function will return 0;
62  CXXFieldDecl *getMember(IdentifierInfo *name) {
63    return cast_or_null<CXXFieldDecl>(RecordDecl::getMember(name));
64  }
65
66  static bool classof(const Decl *D) { return D->getKind() == CXXRecord; }
67  static bool classof(const CXXRecordDecl *D) { return true; }
68  static DeclContext *castToDeclContext(const CXXRecordDecl *D) {
69    return static_cast<DeclContext *>(const_cast<CXXRecordDecl*>(D));
70  }
71  static CXXRecordDecl *castFromDeclContext(const DeclContext *DC) {
72    return static_cast<CXXRecordDecl *>(const_cast<DeclContext*>(DC));
73  }
74
75protected:
76  /// EmitImpl - Serialize this CXXRecordDecl.  Called by Decl::Emit.
77  // FIXME: Implement this.
78  //virtual void EmitImpl(llvm::Serializer& S) const;
79
80  /// CreateImpl - Deserialize a CXXRecordDecl.  Called by Decl::Create.
81  // FIXME: Implement this.
82  static CXXRecordDecl* CreateImpl(Kind DK, llvm::Deserializer& D, ASTContext& C);
83
84  friend Decl* Decl::Create(llvm::Deserializer& D, ASTContext& C);
85};
86
87/// CXXMethodDecl - Represents a static or instance method of a
88/// struct/union/class.
89class CXXMethodDecl : public FunctionDecl {
90
91  CXXMethodDecl(CXXRecordDecl *RD, SourceLocation L,
92               IdentifierInfo *Id, QualType T,
93               bool isStatic, bool isInline, ScopedDecl *PrevDecl)
94    : FunctionDecl(CXXMethod, RD, L, Id, T, (isStatic ? Static : None),
95                   isInline, PrevDecl) {}
96public:
97  static CXXMethodDecl *Create(ASTContext &C, CXXRecordDecl *RD,
98                              SourceLocation L, IdentifierInfo *Id,
99                              QualType T, bool isStatic = false,
100                              bool isInline = false,  ScopedDecl *PrevDecl = 0);
101
102  bool isStatic() const { return getStorageClass() == Static; }
103  bool isInstance() const { return !isStatic(); }
104
105  void setAccess(AccessSpecifier AS) { Access = AS; }
106  AccessSpecifier getAccess() const { return AccessSpecifier(Access); }
107
108  /// getThisType - Returns the type of 'this' pointer.
109  /// Should only be called for instance methods.
110  QualType getThisType(ASTContext &C) const;
111
112  // Implement isa/cast/dyncast/etc.
113  static bool classof(const Decl *D) { return D->getKind() == CXXMethod; }
114  static bool classof(const CXXMethodDecl *D) { return true; }
115
116protected:
117  /// EmitImpl - Serialize this CXXMethodDecl.  Called by Decl::Emit.
118  // FIXME: Implement this.
119  //virtual void EmitImpl(llvm::Serializer& S) const;
120
121  /// CreateImpl - Deserialize a CXXMethodDecl.  Called by Decl::Create.
122  // FIXME: Implement this.
123  static CXXMethodDecl* CreateImpl(llvm::Deserializer& D, ASTContext& C);
124
125  friend Decl* Decl::Create(llvm::Deserializer& D, ASTContext& C);
126};
127
128/// CXXClassVarDecl - Represents a static data member of a struct/union/class.
129class CXXClassVarDecl : public VarDecl {
130
131  CXXClassVarDecl(CXXRecordDecl *RD, SourceLocation L,
132              IdentifierInfo *Id, QualType T, ScopedDecl *PrevDecl)
133    : VarDecl(CXXClassVar, RD, L, Id, T, None, PrevDecl) {}
134public:
135  static CXXClassVarDecl *Create(ASTContext &C, CXXRecordDecl *RD,
136                             SourceLocation L,IdentifierInfo *Id,
137                             QualType T, ScopedDecl *PrevDecl);
138
139  void setAccess(AccessSpecifier AS) { Access = AS; }
140  AccessSpecifier getAccess() const { return AccessSpecifier(Access); }
141
142  // Implement isa/cast/dyncast/etc.
143  static bool classof(const Decl *D) { return D->getKind() == CXXClassVar; }
144  static bool classof(const CXXClassVarDecl *D) { return true; }
145
146protected:
147  /// EmitImpl - Serialize this CXXClassVarDecl. Called by Decl::Emit.
148  // FIXME: Implement this.
149  //virtual void EmitImpl(llvm::Serializer& S) const;
150
151  /// CreateImpl - Deserialize a CXXClassVarDecl.  Called by Decl::Create.
152  // FIXME: Implement this.
153  static CXXClassVarDecl* CreateImpl(llvm::Deserializer& D, ASTContext& C);
154
155  friend Decl* Decl::Create(llvm::Deserializer& D, ASTContext& C);
156};
157
158
159/// CXXClassMemberWrapper - A wrapper class for C++ class member decls.
160/// Common functions like set/getAccess are included here to avoid bloating
161/// the interface of non-C++ specific decl classes, like NamedDecl.
162class CXXClassMemberWrapper {
163  Decl *MD;
164
165public:
166  CXXClassMemberWrapper(Decl *D) : MD(D) {
167    assert(isMember(D) && "Not a C++ class member!");
168  }
169
170  AccessSpecifier getAccess() const {
171    return AccessSpecifier(MD->Access);
172  }
173
174  void setAccess(AccessSpecifier AS) {
175    assert(AS != AS_none && "Access must be specified.");
176    MD->Access = AS;
177  }
178
179  CXXRecordDecl *getParent() const {
180    if (ScopedDecl *SD = dyn_cast<ScopedDecl>(MD)) {
181      return cast<CXXRecordDecl>(SD->getDeclContext());
182    }
183    return cast<CXXFieldDecl>(MD)->getParent();
184  }
185
186  static bool isMember(Decl *D) {
187    if (ScopedDecl *SD = dyn_cast<ScopedDecl>(D)) {
188      return isa<CXXRecordDecl>(SD->getDeclContext());
189    }
190    return isa<CXXFieldDecl>(D);
191  }
192};
193
194} // end namespace clang
195
196#endif
197