DeclObjC.h revision bf393be8a0b8b573ceb23ed19ac953832a2a69e4
1//===--- DeclObjC.h - Classes for representing 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 DeclObjC interface and subclasses.
11//
12//===----------------------------------------------------------------------===//
13
14#ifndef LLVM_CLANG_AST_DECLOBJC_H
15#define LLVM_CLANG_AST_DECLOBJC_H
16
17#include "clang/AST/Decl.h"
18#include "clang/AST/SelectorLocationsKind.h"
19#include "llvm/ADT/STLExtras.h"
20#include "llvm/Support/Compiler.h"
21
22namespace clang {
23class Expr;
24class Stmt;
25class FunctionDecl;
26class RecordDecl;
27class ObjCIvarDecl;
28class ObjCMethodDecl;
29class ObjCProtocolDecl;
30class ObjCCategoryDecl;
31class ObjCPropertyDecl;
32class ObjCPropertyImplDecl;
33class CXXCtorInitializer;
34
35class ObjCListBase {
36  void operator=(const ObjCListBase &);     // DO NOT IMPLEMENT
37  ObjCListBase(const ObjCListBase&);        // DO NOT IMPLEMENT
38protected:
39  /// List is an array of pointers to objects that are not owned by this object.
40  void **List;
41  unsigned NumElts;
42
43public:
44  ObjCListBase() : List(0), NumElts(0) {}
45  unsigned size() const { return NumElts; }
46  bool empty() const { return NumElts == 0; }
47
48protected:
49  void set(void *const* InList, unsigned Elts, ASTContext &Ctx);
50};
51
52
53/// ObjCList - This is a simple template class used to hold various lists of
54/// decls etc, which is heavily used by the ObjC front-end.  This only use case
55/// this supports is setting the list all at once and then reading elements out
56/// of it.
57template <typename T>
58class ObjCList : public ObjCListBase {
59public:
60  void set(T* const* InList, unsigned Elts, ASTContext &Ctx) {
61    ObjCListBase::set(reinterpret_cast<void*const*>(InList), Elts, Ctx);
62  }
63
64  typedef T* const * iterator;
65  iterator begin() const { return (iterator)List; }
66  iterator end() const { return (iterator)List+NumElts; }
67
68  T* operator[](unsigned Idx) const {
69    assert(Idx < NumElts && "Invalid access");
70    return (T*)List[Idx];
71  }
72};
73
74/// \brief A list of Objective-C protocols, along with the source
75/// locations at which they were referenced.
76class ObjCProtocolList : public ObjCList<ObjCProtocolDecl> {
77  SourceLocation *Locations;
78
79  using ObjCList<ObjCProtocolDecl>::set;
80
81public:
82  ObjCProtocolList() : ObjCList<ObjCProtocolDecl>(), Locations(0) { }
83
84  typedef const SourceLocation *loc_iterator;
85  loc_iterator loc_begin() const { return Locations; }
86  loc_iterator loc_end() const { return Locations + size(); }
87
88  void set(ObjCProtocolDecl* const* InList, unsigned Elts,
89           const SourceLocation *Locs, ASTContext &Ctx);
90};
91
92
93/// ObjCMethodDecl - Represents an instance or class method declaration.
94/// ObjC methods can be declared within 4 contexts: class interfaces,
95/// categories, protocols, and class implementations. While C++ member
96/// functions leverage C syntax, Objective-C method syntax is modeled after
97/// Smalltalk (using colons to specify argument types/expressions).
98/// Here are some brief examples:
99///
100/// Setter/getter instance methods:
101/// - (void)setMenu:(NSMenu *)menu;
102/// - (NSMenu *)menu;
103///
104/// Instance method that takes 2 NSView arguments:
105/// - (void)replaceSubview:(NSView *)oldView with:(NSView *)newView;
106///
107/// Getter class method:
108/// + (NSMenu *)defaultMenu;
109///
110/// A selector represents a unique name for a method. The selector names for
111/// the above methods are setMenu:, menu, replaceSubview:with:, and defaultMenu.
112///
113class ObjCMethodDecl : public NamedDecl, public DeclContext {
114public:
115  enum ImplementationControl { None, Required, Optional };
116private:
117  // The conventional meaning of this method; an ObjCMethodFamily.
118  // This is not serialized; instead, it is computed on demand and
119  // cached.
120  mutable unsigned Family : ObjCMethodFamilyBitWidth;
121
122  /// instance (true) or class (false) method.
123  unsigned IsInstance : 1;
124  unsigned IsVariadic : 1;
125
126  // Synthesized declaration method for a property setter/getter
127  unsigned IsSynthesized : 1;
128
129  // Method has a definition.
130  unsigned IsDefined : 1;
131
132  /// \brief Method redeclaration in the same interface.
133  unsigned IsRedeclaration : 1;
134
135  /// \brief Is redeclared in the same interface.
136  mutable unsigned HasRedeclaration : 1;
137
138  // NOTE: VC++ treats enums as signed, avoid using ImplementationControl enum
139  /// @required/@optional
140  unsigned DeclImplementation : 2;
141
142  // NOTE: VC++ treats enums as signed, avoid using the ObjCDeclQualifier enum
143  /// in, inout, etc.
144  unsigned objcDeclQualifier : 6;
145
146  /// \brief Indicates whether this method has a related result type.
147  unsigned RelatedResultType : 1;
148
149  /// \brief Whether the locations of the selector identifiers are in a
150  /// "standard" position, a enum SelectorLocationsKind.
151  unsigned SelLocsKind : 2;
152
153  // Result type of this method.
154  QualType MethodDeclType;
155
156  // Type source information for the result type.
157  TypeSourceInfo *ResultTInfo;
158
159  /// \brief Array of ParmVarDecls for the formal parameters of this method
160  /// and optionally followed by selector locations.
161  void *ParamsAndSelLocs;
162  unsigned NumParams;
163
164  /// List of attributes for this method declaration.
165  SourceLocation EndLoc; // the location of the ';' or '}'.
166
167  // The following are only used for method definitions, null otherwise.
168  // FIXME: space savings opportunity, consider a sub-class.
169  Stmt *Body;
170
171  /// SelfDecl - Decl for the implicit self parameter. This is lazily
172  /// constructed by createImplicitParams.
173  ImplicitParamDecl *SelfDecl;
174  /// CmdDecl - Decl for the implicit _cmd parameter. This is lazily
175  /// constructed by createImplicitParams.
176  ImplicitParamDecl *CmdDecl;
177
178  SelectorLocationsKind getSelLocsKind() const {
179    return (SelectorLocationsKind)SelLocsKind;
180  }
181  bool hasStandardSelLocs() const {
182    return getSelLocsKind() != SelLoc_NonStandard;
183  }
184
185  /// \brief Get a pointer to the stored selector identifiers locations array.
186  /// No locations will be stored if HasStandardSelLocs is true.
187  SourceLocation *getStoredSelLocs() {
188    return reinterpret_cast<SourceLocation*>(getParams() + NumParams);
189  }
190  const SourceLocation *getStoredSelLocs() const {
191    return reinterpret_cast<const SourceLocation*>(getParams() + NumParams);
192  }
193
194  /// \brief Get a pointer to the stored selector identifiers locations array.
195  /// No locations will be stored if HasStandardSelLocs is true.
196  ParmVarDecl **getParams() {
197    return reinterpret_cast<ParmVarDecl **>(ParamsAndSelLocs);
198  }
199  const ParmVarDecl *const *getParams() const {
200    return reinterpret_cast<const ParmVarDecl *const *>(ParamsAndSelLocs);
201  }
202
203  /// \brief Get the number of stored selector identifiers locations.
204  /// No locations will be stored if HasStandardSelLocs is true.
205  unsigned getNumStoredSelLocs() const {
206    if (hasStandardSelLocs())
207      return 0;
208    return getNumSelectorLocs();
209  }
210
211  void setParamsAndSelLocs(ASTContext &C,
212                           ArrayRef<ParmVarDecl*> Params,
213                           ArrayRef<SourceLocation> SelLocs);
214
215  ObjCMethodDecl(SourceLocation beginLoc, SourceLocation endLoc,
216                 Selector SelInfo, QualType T,
217                 TypeSourceInfo *ResultTInfo,
218                 DeclContext *contextDecl,
219                 bool isInstance = true,
220                 bool isVariadic = false,
221                 bool isSynthesized = false,
222                 bool isImplicitlyDeclared = false,
223                 bool isDefined = false,
224                 ImplementationControl impControl = None,
225                 bool HasRelatedResultType = false)
226  : NamedDecl(ObjCMethod, contextDecl, beginLoc, SelInfo),
227    DeclContext(ObjCMethod), Family(InvalidObjCMethodFamily),
228    IsInstance(isInstance), IsVariadic(isVariadic),
229    IsSynthesized(isSynthesized),
230    IsDefined(isDefined), IsRedeclaration(0), HasRedeclaration(0),
231    DeclImplementation(impControl), objcDeclQualifier(OBJC_TQ_None),
232    RelatedResultType(HasRelatedResultType),
233    SelLocsKind(SelLoc_StandardNoSpace),
234    MethodDeclType(T), ResultTInfo(ResultTInfo),
235    ParamsAndSelLocs(0), NumParams(0),
236    EndLoc(endLoc), Body(0), SelfDecl(0), CmdDecl(0) {
237    setImplicit(isImplicitlyDeclared);
238  }
239
240  /// \brief A definition will return its interface declaration.
241  /// An interface declaration will return its definition.
242  /// Otherwise it will return itself.
243  virtual ObjCMethodDecl *getNextRedeclaration();
244
245public:
246  static ObjCMethodDecl *Create(ASTContext &C,
247                                SourceLocation beginLoc,
248                                SourceLocation endLoc,
249                                Selector SelInfo,
250                                QualType T,
251                                TypeSourceInfo *ResultTInfo,
252                                DeclContext *contextDecl,
253                                bool isInstance = true,
254                                bool isVariadic = false,
255                                bool isSynthesized = false,
256                                bool isImplicitlyDeclared = false,
257                                bool isDefined = false,
258                                ImplementationControl impControl = None,
259                                bool HasRelatedResultType = false);
260
261  static ObjCMethodDecl *CreateDeserialized(ASTContext &C, unsigned ID);
262
263  virtual ObjCMethodDecl *getCanonicalDecl();
264  const ObjCMethodDecl *getCanonicalDecl() const {
265    return const_cast<ObjCMethodDecl*>(this)->getCanonicalDecl();
266  }
267
268  ObjCDeclQualifier getObjCDeclQualifier() const {
269    return ObjCDeclQualifier(objcDeclQualifier);
270  }
271  void setObjCDeclQualifier(ObjCDeclQualifier QV) { objcDeclQualifier = QV; }
272
273  /// \brief Determine whether this method has a result type that is related
274  /// to the message receiver's type.
275  bool hasRelatedResultType() const { return RelatedResultType; }
276
277  /// \brief Note whether this method has a related result type.
278  void SetRelatedResultType(bool RRT = true) { RelatedResultType = RRT; }
279
280  /// \brief True if this is a method redeclaration in the same interface.
281  bool isRedeclaration() const { return IsRedeclaration; }
282  void setAsRedeclaration(const ObjCMethodDecl *PrevMethod);
283
284  // Location information, modeled after the Stmt API.
285  SourceLocation getLocStart() const LLVM_READONLY { return getLocation(); }
286  SourceLocation getLocEnd() const LLVM_READONLY { return EndLoc; }
287  void setEndLoc(SourceLocation Loc) { EndLoc = Loc; }
288  virtual SourceRange getSourceRange() const LLVM_READONLY {
289    return SourceRange(getLocation(), EndLoc);
290  }
291
292  SourceLocation getSelectorStartLoc() const {
293    if (isImplicit())
294      return getLocStart();
295    return getSelectorLoc(0);
296  }
297  SourceLocation getSelectorLoc(unsigned Index) const {
298    assert(Index < getNumSelectorLocs() && "Index out of range!");
299    if (hasStandardSelLocs())
300      return getStandardSelectorLoc(Index, getSelector(),
301                                   getSelLocsKind() == SelLoc_StandardWithSpace,
302                      llvm::makeArrayRef(const_cast<ParmVarDecl**>(getParams()),
303                                         NumParams),
304                                   EndLoc);
305    return getStoredSelLocs()[Index];
306  }
307
308  void getSelectorLocs(SmallVectorImpl<SourceLocation> &SelLocs) const;
309
310  unsigned getNumSelectorLocs() const {
311    if (isImplicit())
312      return 0;
313    Selector Sel = getSelector();
314    if (Sel.isUnarySelector())
315      return 1;
316    return Sel.getNumArgs();
317  }
318
319  ObjCInterfaceDecl *getClassInterface();
320  const ObjCInterfaceDecl *getClassInterface() const {
321    return const_cast<ObjCMethodDecl*>(this)->getClassInterface();
322  }
323
324  Selector getSelector() const { return getDeclName().getObjCSelector(); }
325
326  QualType getResultType() const { return MethodDeclType; }
327  void setResultType(QualType T) { MethodDeclType = T; }
328
329  /// \brief Determine the type of an expression that sends a message to this
330  /// function.
331  QualType getSendResultType() const {
332    return getResultType().getNonLValueExprType(getASTContext());
333  }
334
335  TypeSourceInfo *getResultTypeSourceInfo() const { return ResultTInfo; }
336  void setResultTypeSourceInfo(TypeSourceInfo *TInfo) { ResultTInfo = TInfo; }
337
338  // Iterator access to formal parameters.
339  unsigned param_size() const { return NumParams; }
340  typedef const ParmVarDecl *const *param_const_iterator;
341  typedef ParmVarDecl *const *param_iterator;
342  param_const_iterator param_begin() const { return getParams(); }
343  param_const_iterator param_end() const { return getParams() + NumParams; }
344  param_iterator param_begin() { return getParams(); }
345  param_iterator param_end() { return getParams() + NumParams; }
346  // This method returns and of the parameters which are part of the selector
347  // name mangling requirements.
348  param_const_iterator sel_param_end() const {
349    return param_begin() + getSelector().getNumArgs();
350  }
351
352  /// \brief Sets the method's parameters and selector source locations.
353  /// If the method is implicit (not coming from source) \arg SelLocs is
354  /// ignored.
355  void setMethodParams(ASTContext &C,
356                       ArrayRef<ParmVarDecl*> Params,
357                       ArrayRef<SourceLocation> SelLocs =
358                           ArrayRef<SourceLocation>());
359
360  // Iterator access to parameter types.
361  typedef std::const_mem_fun_t<QualType, ParmVarDecl> deref_fun;
362  typedef llvm::mapped_iterator<param_const_iterator, deref_fun>
363      arg_type_iterator;
364
365  arg_type_iterator arg_type_begin() const {
366    return llvm::map_iterator(param_begin(), deref_fun(&ParmVarDecl::getType));
367  }
368  arg_type_iterator arg_type_end() const {
369    return llvm::map_iterator(param_end(), deref_fun(&ParmVarDecl::getType));
370  }
371
372  /// createImplicitParams - Used to lazily create the self and cmd
373  /// implict parameters. This must be called prior to using getSelfDecl()
374  /// or getCmdDecl(). The call is ignored if the implicit paramters
375  /// have already been created.
376  void createImplicitParams(ASTContext &Context, const ObjCInterfaceDecl *ID);
377
378  ImplicitParamDecl * getSelfDecl() const { return SelfDecl; }
379  void setSelfDecl(ImplicitParamDecl *SD) { SelfDecl = SD; }
380  ImplicitParamDecl * getCmdDecl() const { return CmdDecl; }
381  void setCmdDecl(ImplicitParamDecl *CD) { CmdDecl = CD; }
382
383  /// Determines the family of this method.
384  ObjCMethodFamily getMethodFamily() const;
385
386  bool isInstanceMethod() const { return IsInstance; }
387  void setInstanceMethod(bool isInst) { IsInstance = isInst; }
388  bool isVariadic() const { return IsVariadic; }
389  void setVariadic(bool isVar) { IsVariadic = isVar; }
390
391  bool isClassMethod() const { return !IsInstance; }
392
393  bool isSynthesized() const { return IsSynthesized; }
394  void setSynthesized(bool isSynth) { IsSynthesized = isSynth; }
395
396  bool isDefined() const { return IsDefined; }
397  void setDefined(bool isDefined) { IsDefined = isDefined; }
398
399  // Related to protocols declared in  @protocol
400  void setDeclImplementation(ImplementationControl ic) {
401    DeclImplementation = ic;
402  }
403  ImplementationControl getImplementationControl() const {
404    return ImplementationControl(DeclImplementation);
405  }
406
407  virtual Stmt *getBody() const {
408    return (Stmt*) Body;
409  }
410  CompoundStmt *getCompoundBody() { return (CompoundStmt*)Body; }
411  void setBody(Stmt *B) { Body = B; }
412
413  /// \brief Returns whether this specific method is a definition.
414  bool isThisDeclarationADefinition() const { return Body; }
415
416  // Implement isa/cast/dyncast/etc.
417  static bool classof(const Decl *D) { return classofKind(D->getKind()); }
418  static bool classof(const ObjCMethodDecl *D) { return true; }
419  static bool classofKind(Kind K) { return K == ObjCMethod; }
420  static DeclContext *castToDeclContext(const ObjCMethodDecl *D) {
421    return static_cast<DeclContext *>(const_cast<ObjCMethodDecl*>(D));
422  }
423  static ObjCMethodDecl *castFromDeclContext(const DeclContext *DC) {
424    return static_cast<ObjCMethodDecl *>(const_cast<DeclContext*>(DC));
425  }
426
427  friend class ASTDeclReader;
428  friend class ASTDeclWriter;
429};
430
431/// ObjCContainerDecl - Represents a container for method declarations.
432/// Current sub-classes are ObjCInterfaceDecl, ObjCCategoryDecl,
433/// ObjCProtocolDecl, and ObjCImplDecl.
434///
435class ObjCContainerDecl : public NamedDecl, public DeclContext {
436  virtual void anchor();
437
438  SourceLocation AtStart;
439
440  // These two locations in the range mark the end of the method container.
441  // The first points to the '@' token, and the second to the 'end' token.
442  SourceRange AtEnd;
443public:
444
445  ObjCContainerDecl(Kind DK, DeclContext *DC,
446                    IdentifierInfo *Id, SourceLocation nameLoc,
447                    SourceLocation atStartLoc)
448    : NamedDecl(DK, DC, nameLoc, Id), DeclContext(DK), AtStart(atStartLoc) {}
449
450  // Iterator access to properties.
451  typedef specific_decl_iterator<ObjCPropertyDecl> prop_iterator;
452  prop_iterator prop_begin() const {
453    return prop_iterator(decls_begin());
454  }
455  prop_iterator prop_end() const {
456    return prop_iterator(decls_end());
457  }
458
459  // Iterator access to instance/class methods.
460  typedef specific_decl_iterator<ObjCMethodDecl> method_iterator;
461  method_iterator meth_begin() const {
462    return method_iterator(decls_begin());
463  }
464  method_iterator meth_end() const {
465    return method_iterator(decls_end());
466  }
467
468  typedef filtered_decl_iterator<ObjCMethodDecl,
469                                 &ObjCMethodDecl::isInstanceMethod>
470    instmeth_iterator;
471  instmeth_iterator instmeth_begin() const {
472    return instmeth_iterator(decls_begin());
473  }
474  instmeth_iterator instmeth_end() const {
475    return instmeth_iterator(decls_end());
476  }
477
478  typedef filtered_decl_iterator<ObjCMethodDecl,
479                                 &ObjCMethodDecl::isClassMethod>
480    classmeth_iterator;
481  classmeth_iterator classmeth_begin() const {
482    return classmeth_iterator(decls_begin());
483  }
484  classmeth_iterator classmeth_end() const {
485    return classmeth_iterator(decls_end());
486  }
487
488  // Get the local instance/class method declared in this interface.
489  ObjCMethodDecl *getMethod(Selector Sel, bool isInstance) const;
490  ObjCMethodDecl *getInstanceMethod(Selector Sel) const {
491    return getMethod(Sel, true/*isInstance*/);
492  }
493  ObjCMethodDecl *getClassMethod(Selector Sel) const {
494    return getMethod(Sel, false/*isInstance*/);
495  }
496  ObjCIvarDecl *getIvarDecl(IdentifierInfo *Id) const;
497
498  ObjCPropertyDecl *FindPropertyDeclaration(IdentifierInfo *PropertyId) const;
499
500  SourceLocation getAtStartLoc() const { return AtStart; }
501  void setAtStartLoc(SourceLocation Loc) { AtStart = Loc; }
502
503  // Marks the end of the container.
504  SourceRange getAtEndRange() const {
505    return AtEnd;
506  }
507  void setAtEndRange(SourceRange atEnd) {
508    AtEnd = atEnd;
509  }
510
511  virtual SourceRange getSourceRange() const LLVM_READONLY {
512    return SourceRange(AtStart, getAtEndRange().getEnd());
513  }
514
515  // Implement isa/cast/dyncast/etc.
516  static bool classof(const Decl *D) { return classofKind(D->getKind()); }
517  static bool classof(const ObjCContainerDecl *D) { return true; }
518  static bool classofKind(Kind K) {
519    return K >= firstObjCContainer &&
520           K <= lastObjCContainer;
521  }
522
523  static DeclContext *castToDeclContext(const ObjCContainerDecl *D) {
524    return static_cast<DeclContext *>(const_cast<ObjCContainerDecl*>(D));
525  }
526  static ObjCContainerDecl *castFromDeclContext(const DeclContext *DC) {
527    return static_cast<ObjCContainerDecl *>(const_cast<DeclContext*>(DC));
528  }
529};
530
531/// ObjCInterfaceDecl - Represents an ObjC class declaration. For example:
532///
533///   // MostPrimitive declares no super class (not particularly useful).
534///   @interface MostPrimitive
535///     // no instance variables or methods.
536///   @end
537///
538///   // NSResponder inherits from NSObject & implements NSCoding (a protocol).
539///   @interface NSResponder : NSObject <NSCoding>
540///   { // instance variables are represented by ObjCIvarDecl.
541///     id nextResponder; // nextResponder instance variable.
542///   }
543///   - (NSResponder *)nextResponder; // return a pointer to NSResponder.
544///   - (void)mouseMoved:(NSEvent *)theEvent; // return void, takes a pointer
545///   @end                                    // to an NSEvent.
546///
547///   Unlike C/C++, forward class declarations are accomplished with @class.
548///   Unlike C/C++, @class allows for a list of classes to be forward declared.
549///   Unlike C++, ObjC is a single-rooted class model. In Cocoa, classes
550///   typically inherit from NSObject (an exception is NSProxy).
551///
552class ObjCInterfaceDecl : public ObjCContainerDecl
553                        , public Redeclarable<ObjCInterfaceDecl> {
554  virtual void anchor();
555
556  /// TypeForDecl - This indicates the Type object that represents this
557  /// TypeDecl.  It is a cache maintained by ASTContext::getObjCInterfaceType
558  mutable const Type *TypeForDecl;
559  friend class ASTContext;
560
561  struct DefinitionData {
562    /// \brief The definition of this class, for quick access from any
563    /// declaration.
564    ObjCInterfaceDecl *Definition;
565
566    /// Class's super class.
567    ObjCInterfaceDecl *SuperClass;
568
569    /// Protocols referenced in the @interface  declaration
570    ObjCProtocolList ReferencedProtocols;
571
572    /// Protocols reference in both the @interface and class extensions.
573    ObjCList<ObjCProtocolDecl> AllReferencedProtocols;
574
575    /// \brief List of categories and class extensions defined for this class.
576    ///
577    /// Categories are stored as a linked list in the AST, since the categories
578    /// and class extensions come long after the initial interface declaration,
579    /// and we avoid dynamically-resized arrays in the AST wherever possible.
580    ObjCCategoryDecl *CategoryList;
581
582    /// IvarList - List of all ivars defined by this class; including class
583    /// extensions and implementation. This list is built lazily.
584    ObjCIvarDecl *IvarList;
585
586    /// \brief Indicates that the contents of this Objective-C class will be
587    /// completed by the external AST source when required.
588    mutable bool ExternallyCompleted : 1;
589
590    /// \brief The location of the superclass, if any.
591    SourceLocation SuperClassLoc;
592
593    /// \brief The location of the last location in this declaration, before
594    /// the properties/methods. For example, this will be the '>', '}', or
595    /// identifier,
596    SourceLocation EndLoc;
597
598    DefinitionData() : Definition(), SuperClass(), CategoryList(), IvarList(),
599                       ExternallyCompleted() { }
600  };
601
602  ObjCInterfaceDecl(DeclContext *DC, SourceLocation atLoc, IdentifierInfo *Id,
603                    SourceLocation CLoc, ObjCInterfaceDecl *PrevDecl,
604                    bool isInternal);
605
606  void LoadExternalDefinition() const;
607
608  /// \brief Contains a pointer to the data associated with this class,
609  /// which will be NULL if this class has not yet been defined.
610  DefinitionData *Data;
611
612  DefinitionData &data() const {
613    assert(Data != 0 && "Declaration has no definition!");
614    return *Data;
615  }
616
617  /// \brief Allocate the definition data for this class.
618  void allocateDefinitionData();
619
620  typedef Redeclarable<ObjCInterfaceDecl> redeclarable_base;
621  virtual ObjCInterfaceDecl *getNextRedeclaration() {
622    return RedeclLink.getNext();
623  }
624  virtual ObjCInterfaceDecl *getPreviousDeclImpl() {
625    return getPreviousDecl();
626  }
627  virtual ObjCInterfaceDecl *getMostRecentDeclImpl() {
628    return getMostRecentDecl();
629  }
630
631public:
632  static ObjCInterfaceDecl *Create(const ASTContext &C, DeclContext *DC,
633                                   SourceLocation atLoc,
634                                   IdentifierInfo *Id,
635                                   ObjCInterfaceDecl *PrevDecl,
636                                   SourceLocation ClassLoc = SourceLocation(),
637                                   bool isInternal = false);
638
639  static ObjCInterfaceDecl *CreateDeserialized(ASTContext &C, unsigned ID);
640
641  virtual SourceRange getSourceRange() const LLVM_READONLY {
642    if (isThisDeclarationADefinition())
643      return ObjCContainerDecl::getSourceRange();
644
645    return SourceRange(getAtStartLoc(), getLocation());
646  }
647
648  /// \brief Indicate that this Objective-C class is complete, but that
649  /// the external AST source will be responsible for filling in its contents
650  /// when a complete class is required.
651  void setExternallyCompleted();
652
653  const ObjCProtocolList &getReferencedProtocols() const {
654    assert(hasDefinition() && "Caller did not check for forward reference!");
655    if (data().ExternallyCompleted)
656      LoadExternalDefinition();
657
658    return data().ReferencedProtocols;
659  }
660
661  ObjCImplementationDecl *getImplementation() const;
662  void setImplementation(ObjCImplementationDecl *ImplD);
663
664  ObjCCategoryDecl *FindCategoryDeclaration(IdentifierInfo *CategoryId) const;
665
666  // Get the local instance/class method declared in a category.
667  ObjCMethodDecl *getCategoryInstanceMethod(Selector Sel) const;
668  ObjCMethodDecl *getCategoryClassMethod(Selector Sel) const;
669  ObjCMethodDecl *getCategoryMethod(Selector Sel, bool isInstance) const {
670    return isInstance ? getInstanceMethod(Sel)
671                      : getClassMethod(Sel);
672  }
673
674  typedef ObjCProtocolList::iterator protocol_iterator;
675
676  protocol_iterator protocol_begin() const {
677    // FIXME: Should make sure no callers ever do this.
678    if (!hasDefinition())
679      return protocol_iterator();
680
681    if (data().ExternallyCompleted)
682      LoadExternalDefinition();
683
684    return data().ReferencedProtocols.begin();
685  }
686  protocol_iterator protocol_end() const {
687    // FIXME: Should make sure no callers ever do this.
688    if (!hasDefinition())
689      return protocol_iterator();
690
691    if (data().ExternallyCompleted)
692      LoadExternalDefinition();
693
694    return data().ReferencedProtocols.end();
695  }
696
697  typedef ObjCProtocolList::loc_iterator protocol_loc_iterator;
698
699  protocol_loc_iterator protocol_loc_begin() const {
700    // FIXME: Should make sure no callers ever do this.
701    if (!hasDefinition())
702      return protocol_loc_iterator();
703
704    if (data().ExternallyCompleted)
705      LoadExternalDefinition();
706
707    return data().ReferencedProtocols.loc_begin();
708  }
709
710  protocol_loc_iterator protocol_loc_end() const {
711    // FIXME: Should make sure no callers ever do this.
712    if (!hasDefinition())
713      return protocol_loc_iterator();
714
715    if (data().ExternallyCompleted)
716      LoadExternalDefinition();
717
718    return data().ReferencedProtocols.loc_end();
719  }
720
721  typedef ObjCList<ObjCProtocolDecl>::iterator all_protocol_iterator;
722
723  all_protocol_iterator all_referenced_protocol_begin() const {
724    // FIXME: Should make sure no callers ever do this.
725    if (!hasDefinition())
726      return all_protocol_iterator();
727
728    if (data().ExternallyCompleted)
729      LoadExternalDefinition();
730
731    return data().AllReferencedProtocols.empty()
732             ? protocol_begin()
733             : data().AllReferencedProtocols.begin();
734  }
735  all_protocol_iterator all_referenced_protocol_end() const {
736    // FIXME: Should make sure no callers ever do this.
737    if (!hasDefinition())
738      return all_protocol_iterator();
739
740    if (data().ExternallyCompleted)
741      LoadExternalDefinition();
742
743    return data().AllReferencedProtocols.empty()
744             ? protocol_end()
745             : data().AllReferencedProtocols.end();
746  }
747
748  typedef specific_decl_iterator<ObjCIvarDecl> ivar_iterator;
749
750  ivar_iterator ivar_begin() const {
751    if (const ObjCInterfaceDecl *Def = getDefinition())
752      return ivar_iterator(Def->decls_begin());
753
754    // FIXME: Should make sure no callers ever do this.
755    return ivar_iterator();
756  }
757  ivar_iterator ivar_end() const {
758    if (const ObjCInterfaceDecl *Def = getDefinition())
759      return ivar_iterator(Def->decls_end());
760
761    // FIXME: Should make sure no callers ever do this.
762    return ivar_iterator();
763  }
764
765  unsigned ivar_size() const {
766    return std::distance(ivar_begin(), ivar_end());
767  }
768
769  bool ivar_empty() const { return ivar_begin() == ivar_end(); }
770
771  ObjCIvarDecl *all_declared_ivar_begin();
772  const ObjCIvarDecl *all_declared_ivar_begin() const {
773    // Even though this modifies IvarList, it's conceptually const:
774    // the ivar chain is essentially a cached property of ObjCInterfaceDecl.
775    return const_cast<ObjCInterfaceDecl *>(this)->all_declared_ivar_begin();
776  }
777  void setIvarList(ObjCIvarDecl *ivar) { data().IvarList = ivar; }
778
779  /// setProtocolList - Set the list of protocols that this interface
780  /// implements.
781  void setProtocolList(ObjCProtocolDecl *const* List, unsigned Num,
782                       const SourceLocation *Locs, ASTContext &C) {
783    data().ReferencedProtocols.set(List, Num, Locs, C);
784  }
785
786  /// mergeClassExtensionProtocolList - Merge class extension's protocol list
787  /// into the protocol list for this class.
788  void mergeClassExtensionProtocolList(ObjCProtocolDecl *const* List,
789                                       unsigned Num,
790                                       ASTContext &C);
791
792  /// \brief Determine whether this particular declaration of this class is
793  /// actually also a definition.
794  bool isThisDeclarationADefinition() const {
795    return Data && Data->Definition == this;
796  }
797
798  /// \brief Determine whether this class has been defined.
799  bool hasDefinition() const { return Data; }
800
801  /// \brief Retrieve the definition of this class, or NULL if this class
802  /// has been forward-declared (with @class) but not yet defined (with
803  /// @interface).
804  ObjCInterfaceDecl *getDefinition() {
805    return hasDefinition()? Data->Definition : 0;
806  }
807
808  /// \brief Retrieve the definition of this class, or NULL if this class
809  /// has been forward-declared (with @class) but not yet defined (with
810  /// @interface).
811  const ObjCInterfaceDecl *getDefinition() const {
812    return hasDefinition()? Data->Definition : 0;
813  }
814
815  /// \brief Starts the definition of this Objective-C class, taking it from
816  /// a forward declaration (@class) to a definition (@interface).
817  void startDefinition();
818
819  ObjCInterfaceDecl *getSuperClass() const {
820    // FIXME: Should make sure no callers ever do this.
821    if (!hasDefinition())
822      return 0;
823
824    if (data().ExternallyCompleted)
825      LoadExternalDefinition();
826
827    return data().SuperClass;
828  }
829
830  void setSuperClass(ObjCInterfaceDecl * superCls) {
831    data().SuperClass =
832      (superCls && superCls->hasDefinition()) ? superCls->getDefinition()
833                                              : superCls;
834  }
835
836  ObjCCategoryDecl* getCategoryList() const {
837    // FIXME: Should make sure no callers ever do this.
838    if (!hasDefinition())
839      return 0;
840
841    if (data().ExternallyCompleted)
842      LoadExternalDefinition();
843
844    return data().CategoryList;
845  }
846
847  void setCategoryList(ObjCCategoryDecl *category) {
848    data().CategoryList = category;
849  }
850
851  ObjCCategoryDecl* getFirstClassExtension() const;
852
853  ObjCPropertyDecl
854    *FindPropertyVisibleInPrimaryClass(IdentifierInfo *PropertyId) const;
855
856  /// isSuperClassOf - Return true if this class is the specified class or is a
857  /// super class of the specified interface class.
858  bool isSuperClassOf(const ObjCInterfaceDecl *I) const {
859    // If RHS is derived from LHS it is OK; else it is not OK.
860    while (I != NULL) {
861      if (declaresSameEntity(this, I))
862        return true;
863
864      I = I->getSuperClass();
865    }
866    return false;
867  }
868
869  /// isArcWeakrefUnavailable - Checks for a class or one of its super classes
870  /// to be incompatible with __weak references. Returns true if it is.
871  bool isArcWeakrefUnavailable() const {
872    const ObjCInterfaceDecl *Class = this;
873    while (Class) {
874      if (Class->hasAttr<ArcWeakrefUnavailableAttr>())
875        return true;
876      Class = Class->getSuperClass();
877   }
878   return false;
879  }
880
881  /// isObjCRequiresPropertyDefs - Checks that a class or one of its super
882  /// classes must not be auto-synthesized. Returns class decl. if it must not be;
883  /// 0, otherwise.
884  const ObjCInterfaceDecl *isObjCRequiresPropertyDefs() const {
885    const ObjCInterfaceDecl *Class = this;
886    while (Class) {
887      if (Class->hasAttr<ObjCRequiresPropertyDefsAttr>())
888        return Class;
889      Class = Class->getSuperClass();
890   }
891   return 0;
892  }
893
894  ObjCIvarDecl *lookupInstanceVariable(IdentifierInfo *IVarName,
895                                       ObjCInterfaceDecl *&ClassDeclared);
896  ObjCIvarDecl *lookupInstanceVariable(IdentifierInfo *IVarName) {
897    ObjCInterfaceDecl *ClassDeclared;
898    return lookupInstanceVariable(IVarName, ClassDeclared);
899  }
900
901  // Lookup a method. First, we search locally. If a method isn't
902  // found, we search referenced protocols and class categories.
903  ObjCMethodDecl *lookupMethod(Selector Sel, bool isInstance,
904                               bool shallowCategoryLookup= false) const;
905  ObjCMethodDecl *lookupInstanceMethod(Selector Sel,
906                            bool shallowCategoryLookup = false) const {
907    return lookupMethod(Sel, true/*isInstance*/, shallowCategoryLookup);
908  }
909  ObjCMethodDecl *lookupClassMethod(Selector Sel,
910                     bool shallowCategoryLookup = false) const {
911    return lookupMethod(Sel, false/*isInstance*/, shallowCategoryLookup);
912  }
913  ObjCInterfaceDecl *lookupInheritedClass(const IdentifierInfo *ICName);
914
915  // Lookup a method in the classes implementation hierarchy.
916  ObjCMethodDecl *lookupPrivateMethod(const Selector &Sel, bool Instance=true);
917
918  SourceLocation getEndOfDefinitionLoc() const {
919    if (!hasDefinition())
920      return getLocation();
921
922    return data().EndLoc;
923  }
924
925  void setEndOfDefinitionLoc(SourceLocation LE) { data().EndLoc = LE; }
926
927  void setSuperClassLoc(SourceLocation Loc) { data().SuperClassLoc = Loc; }
928  SourceLocation getSuperClassLoc() const { return data().SuperClassLoc; }
929
930  /// isImplicitInterfaceDecl - check that this is an implicitly declared
931  /// ObjCInterfaceDecl node. This is for legacy objective-c @implementation
932  /// declaration without an @interface declaration.
933  bool isImplicitInterfaceDecl() const {
934    return hasDefinition() ? Data->Definition->isImplicit() : isImplicit();
935  }
936
937  /// ClassImplementsProtocol - Checks that 'lProto' protocol
938  /// has been implemented in IDecl class, its super class or categories (if
939  /// lookupCategory is true).
940  bool ClassImplementsProtocol(ObjCProtocolDecl *lProto,
941                               bool lookupCategory,
942                               bool RHSIsQualifiedID = false);
943
944  typedef redeclarable_base::redecl_iterator redecl_iterator;
945  using redeclarable_base::redecls_begin;
946  using redeclarable_base::redecls_end;
947  using redeclarable_base::getPreviousDecl;
948  using redeclarable_base::getMostRecentDecl;
949
950  /// Retrieves the canonical declaration of this Objective-C class.
951  ObjCInterfaceDecl *getCanonicalDecl() {
952    return getFirstDeclaration();
953  }
954  const ObjCInterfaceDecl *getCanonicalDecl() const {
955    return getFirstDeclaration();
956  }
957
958  // Low-level accessor
959  const Type *getTypeForDecl() const { return TypeForDecl; }
960  void setTypeForDecl(const Type *TD) const { TypeForDecl = TD; }
961
962  static bool classof(const Decl *D) { return classofKind(D->getKind()); }
963  static bool classof(const ObjCInterfaceDecl *D) { return true; }
964  static bool classofKind(Kind K) { return K == ObjCInterface; }
965
966  friend class ASTReader;
967  friend class ASTDeclReader;
968  friend class ASTDeclWriter;
969};
970
971/// ObjCIvarDecl - Represents an ObjC instance variable. In general, ObjC
972/// instance variables are identical to C. The only exception is Objective-C
973/// supports C++ style access control. For example:
974///
975///   @interface IvarExample : NSObject
976///   {
977///     id defaultToProtected;
978///   @public:
979///     id canBePublic; // same as C++.
980///   @protected:
981///     id canBeProtected; // same as C++.
982///   @package:
983///     id canBePackage; // framework visibility (not available in C++).
984///   }
985///
986class ObjCIvarDecl : public FieldDecl {
987  virtual void anchor();
988
989public:
990  enum AccessControl {
991    None, Private, Protected, Public, Package
992  };
993
994private:
995  ObjCIvarDecl(ObjCContainerDecl *DC, SourceLocation StartLoc,
996               SourceLocation IdLoc, IdentifierInfo *Id,
997               QualType T, TypeSourceInfo *TInfo, AccessControl ac, Expr *BW,
998               bool synthesized)
999    : FieldDecl(ObjCIvar, DC, StartLoc, IdLoc, Id, T, TInfo, BW,
1000                /*Mutable=*/false, /*HasInit=*/false),
1001      NextIvar(0), DeclAccess(ac), Synthesized(synthesized) {}
1002
1003public:
1004  static ObjCIvarDecl *Create(ASTContext &C, ObjCContainerDecl *DC,
1005                              SourceLocation StartLoc, SourceLocation IdLoc,
1006                              IdentifierInfo *Id, QualType T,
1007                              TypeSourceInfo *TInfo,
1008                              AccessControl ac, Expr *BW = NULL,
1009                              bool synthesized=false);
1010
1011  static ObjCIvarDecl *CreateDeserialized(ASTContext &C, unsigned ID);
1012
1013  /// \brief Return the class interface that this ivar is logically contained
1014  /// in; this is either the interface where the ivar was declared, or the
1015  /// interface the ivar is conceptually a part of in the case of synthesized
1016  /// ivars.
1017  const ObjCInterfaceDecl *getContainingInterface() const;
1018
1019  ObjCIvarDecl *getNextIvar() { return NextIvar; }
1020  const ObjCIvarDecl *getNextIvar() const { return NextIvar; }
1021  void setNextIvar(ObjCIvarDecl *ivar) { NextIvar = ivar; }
1022
1023  void setAccessControl(AccessControl ac) { DeclAccess = ac; }
1024
1025  AccessControl getAccessControl() const { return AccessControl(DeclAccess); }
1026
1027  AccessControl getCanonicalAccessControl() const {
1028    return DeclAccess == None ? Protected : AccessControl(DeclAccess);
1029  }
1030
1031  void setSynthesize(bool synth) { Synthesized = synth; }
1032  bool getSynthesize() const { return Synthesized; }
1033
1034  // Implement isa/cast/dyncast/etc.
1035  static bool classof(const Decl *D) { return classofKind(D->getKind()); }
1036  static bool classof(const ObjCIvarDecl *D) { return true; }
1037  static bool classofKind(Kind K) { return K == ObjCIvar; }
1038private:
1039  /// NextIvar - Next Ivar in the list of ivars declared in class; class's
1040  /// extensions and class's implementation
1041  ObjCIvarDecl *NextIvar;
1042
1043  // NOTE: VC++ treats enums as signed, avoid using the AccessControl enum
1044  unsigned DeclAccess : 3;
1045  unsigned Synthesized : 1;
1046};
1047
1048
1049/// ObjCAtDefsFieldDecl - Represents a field declaration created by an
1050///  @defs(...).
1051class ObjCAtDefsFieldDecl : public FieldDecl {
1052  virtual void anchor();
1053  ObjCAtDefsFieldDecl(DeclContext *DC, SourceLocation StartLoc,
1054                      SourceLocation IdLoc, IdentifierInfo *Id,
1055                      QualType T, Expr *BW)
1056    : FieldDecl(ObjCAtDefsField, DC, StartLoc, IdLoc, Id, T,
1057                /*TInfo=*/0, // FIXME: Do ObjCAtDefs have declarators ?
1058                BW, /*Mutable=*/false, /*HasInit=*/false) {}
1059
1060public:
1061  static ObjCAtDefsFieldDecl *Create(ASTContext &C, DeclContext *DC,
1062                                     SourceLocation StartLoc,
1063                                     SourceLocation IdLoc, IdentifierInfo *Id,
1064                                     QualType T, Expr *BW);
1065
1066  static ObjCAtDefsFieldDecl *CreateDeserialized(ASTContext &C, unsigned ID);
1067
1068  // Implement isa/cast/dyncast/etc.
1069  static bool classof(const Decl *D) { return classofKind(D->getKind()); }
1070  static bool classof(const ObjCAtDefsFieldDecl *D) { return true; }
1071  static bool classofKind(Kind K) { return K == ObjCAtDefsField; }
1072};
1073
1074/// ObjCProtocolDecl - Represents a protocol declaration. ObjC protocols
1075/// declare a pure abstract type (i.e no instance variables are permitted).
1076/// Protocols originally drew inspiration from C++ pure virtual functions (a C++
1077/// feature with nice semantics and lousy syntax:-). Here is an example:
1078///
1079/// @protocol NSDraggingInfo <refproto1, refproto2>
1080/// - (NSWindow *)draggingDestinationWindow;
1081/// - (NSImage *)draggedImage;
1082/// @end
1083///
1084/// This says that NSDraggingInfo requires two methods and requires everything
1085/// that the two "referenced protocols" 'refproto1' and 'refproto2' require as
1086/// well.
1087///
1088/// @interface ImplementsNSDraggingInfo : NSObject <NSDraggingInfo>
1089/// @end
1090///
1091/// ObjC protocols inspired Java interfaces. Unlike Java, ObjC classes and
1092/// protocols are in distinct namespaces. For example, Cocoa defines both
1093/// an NSObject protocol and class (which isn't allowed in Java). As a result,
1094/// protocols are referenced using angle brackets as follows:
1095///
1096/// id <NSDraggingInfo> anyObjectThatImplementsNSDraggingInfo;
1097///
1098class ObjCProtocolDecl : public ObjCContainerDecl,
1099                         public Redeclarable<ObjCProtocolDecl> {
1100  virtual void anchor();
1101
1102  struct DefinitionData {
1103    // \brief The declaration that defines this protocol.
1104    ObjCProtocolDecl *Definition;
1105
1106    /// \brief Referenced protocols
1107    ObjCProtocolList ReferencedProtocols;
1108  };
1109
1110  DefinitionData *Data;
1111
1112  DefinitionData &data() const {
1113    assert(Data && "Objective-C protocol has no definition!");
1114    return *Data;
1115  }
1116
1117  ObjCProtocolDecl(DeclContext *DC, IdentifierInfo *Id,
1118                   SourceLocation nameLoc, SourceLocation atStartLoc,
1119                   ObjCProtocolDecl *PrevDecl);
1120
1121  void allocateDefinitionData();
1122
1123  typedef Redeclarable<ObjCProtocolDecl> redeclarable_base;
1124  virtual ObjCProtocolDecl *getNextRedeclaration() {
1125    return RedeclLink.getNext();
1126  }
1127  virtual ObjCProtocolDecl *getPreviousDeclImpl() {
1128    return getPreviousDecl();
1129  }
1130  virtual ObjCProtocolDecl *getMostRecentDeclImpl() {
1131    return getMostRecentDecl();
1132  }
1133
1134public:
1135  static ObjCProtocolDecl *Create(ASTContext &C, DeclContext *DC,
1136                                  IdentifierInfo *Id,
1137                                  SourceLocation nameLoc,
1138                                  SourceLocation atStartLoc,
1139                                  ObjCProtocolDecl *PrevDecl);
1140
1141  static ObjCProtocolDecl *CreateDeserialized(ASTContext &C, unsigned ID);
1142
1143  const ObjCProtocolList &getReferencedProtocols() const {
1144    assert(hasDefinition() && "No definition available!");
1145    return data().ReferencedProtocols;
1146  }
1147  typedef ObjCProtocolList::iterator protocol_iterator;
1148  protocol_iterator protocol_begin() const {
1149    if (!hasDefinition())
1150      return protocol_iterator();
1151
1152    return data().ReferencedProtocols.begin();
1153  }
1154  protocol_iterator protocol_end() const {
1155    if (!hasDefinition())
1156      return protocol_iterator();
1157
1158    return data().ReferencedProtocols.end();
1159  }
1160  typedef ObjCProtocolList::loc_iterator protocol_loc_iterator;
1161  protocol_loc_iterator protocol_loc_begin() const {
1162    if (!hasDefinition())
1163      return protocol_loc_iterator();
1164
1165    return data().ReferencedProtocols.loc_begin();
1166  }
1167  protocol_loc_iterator protocol_loc_end() const {
1168    if (!hasDefinition())
1169      return protocol_loc_iterator();
1170
1171    return data().ReferencedProtocols.loc_end();
1172  }
1173  unsigned protocol_size() const {
1174    if (!hasDefinition())
1175      return 0;
1176
1177    return data().ReferencedProtocols.size();
1178  }
1179
1180  /// setProtocolList - Set the list of protocols that this interface
1181  /// implements.
1182  void setProtocolList(ObjCProtocolDecl *const*List, unsigned Num,
1183                       const SourceLocation *Locs, ASTContext &C) {
1184    assert(Data && "Protocol is not defined");
1185    data().ReferencedProtocols.set(List, Num, Locs, C);
1186  }
1187
1188  ObjCProtocolDecl *lookupProtocolNamed(IdentifierInfo *PName);
1189
1190  // Lookup a method. First, we search locally. If a method isn't
1191  // found, we search referenced protocols and class categories.
1192  ObjCMethodDecl *lookupMethod(Selector Sel, bool isInstance) const;
1193  ObjCMethodDecl *lookupInstanceMethod(Selector Sel) const {
1194    return lookupMethod(Sel, true/*isInstance*/);
1195  }
1196  ObjCMethodDecl *lookupClassMethod(Selector Sel) const {
1197    return lookupMethod(Sel, false/*isInstance*/);
1198  }
1199
1200  /// \brief Determine whether this protocol has a definition.
1201  bool hasDefinition() const { return Data != 0; }
1202
1203  /// \brief Retrieve the definition of this protocol, if any.
1204  ObjCProtocolDecl *getDefinition() {
1205    return Data? Data->Definition : 0;
1206  }
1207
1208  /// \brief Retrieve the definition of this protocol, if any.
1209  const ObjCProtocolDecl *getDefinition() const {
1210    return Data? Data->Definition : 0;
1211  }
1212
1213  /// \brief Determine whether this particular declaration is also the
1214  /// definition.
1215  bool isThisDeclarationADefinition() const {
1216    return getDefinition() == this;
1217  }
1218
1219  /// \brief Starts the definition of this Objective-C protocol.
1220  void startDefinition();
1221
1222  virtual SourceRange getSourceRange() const LLVM_READONLY {
1223    if (isThisDeclarationADefinition())
1224      return ObjCContainerDecl::getSourceRange();
1225
1226    return SourceRange(getAtStartLoc(), getLocation());
1227  }
1228
1229  typedef redeclarable_base::redecl_iterator redecl_iterator;
1230  using redeclarable_base::redecls_begin;
1231  using redeclarable_base::redecls_end;
1232  using redeclarable_base::getPreviousDecl;
1233  using redeclarable_base::getMostRecentDecl;
1234
1235  /// Retrieves the canonical declaration of this Objective-C protocol.
1236  ObjCProtocolDecl *getCanonicalDecl() {
1237    return getFirstDeclaration();
1238  }
1239  const ObjCProtocolDecl *getCanonicalDecl() const {
1240    return getFirstDeclaration();
1241  }
1242
1243  static bool classof(const Decl *D) { return classofKind(D->getKind()); }
1244  static bool classof(const ObjCProtocolDecl *D) { return true; }
1245  static bool classofKind(Kind K) { return K == ObjCProtocol; }
1246
1247  friend class ASTReader;
1248  friend class ASTDeclReader;
1249  friend class ASTDeclWriter;
1250};
1251
1252/// ObjCCategoryDecl - Represents a category declaration. A category allows
1253/// you to add methods to an existing class (without subclassing or modifying
1254/// the original class interface or implementation:-). Categories don't allow
1255/// you to add instance data. The following example adds "myMethod" to all
1256/// NSView's within a process:
1257///
1258/// @interface NSView (MyViewMethods)
1259/// - myMethod;
1260/// @end
1261///
1262/// Categories also allow you to split the implementation of a class across
1263/// several files (a feature more naturally supported in C++).
1264///
1265/// Categories were originally inspired by dynamic languages such as Common
1266/// Lisp and Smalltalk.  More traditional class-based languages (C++, Java)
1267/// don't support this level of dynamism, which is both powerful and dangerous.
1268///
1269class ObjCCategoryDecl : public ObjCContainerDecl {
1270  virtual void anchor();
1271
1272  /// Interface belonging to this category
1273  ObjCInterfaceDecl *ClassInterface;
1274
1275  /// referenced protocols in this category.
1276  ObjCProtocolList ReferencedProtocols;
1277
1278  /// Next category belonging to this class.
1279  /// FIXME: this should not be a singly-linked list.  Move storage elsewhere.
1280  ObjCCategoryDecl *NextClassCategory;
1281
1282  /// true of class extension has at least one bitfield ivar.
1283  bool HasSynthBitfield : 1;
1284
1285  /// \brief The location of the category name in this declaration.
1286  SourceLocation CategoryNameLoc;
1287
1288  /// class extension may have private ivars.
1289  SourceLocation IvarLBraceLoc;
1290  SourceLocation IvarRBraceLoc;
1291
1292  ObjCCategoryDecl(DeclContext *DC, SourceLocation AtLoc,
1293                   SourceLocation ClassNameLoc, SourceLocation CategoryNameLoc,
1294                   IdentifierInfo *Id, ObjCInterfaceDecl *IDecl,
1295                   SourceLocation IvarLBraceLoc=SourceLocation(),
1296                   SourceLocation IvarRBraceLoc=SourceLocation())
1297    : ObjCContainerDecl(ObjCCategory, DC, Id, ClassNameLoc, AtLoc),
1298      ClassInterface(IDecl), NextClassCategory(0), HasSynthBitfield(false),
1299      CategoryNameLoc(CategoryNameLoc),
1300      IvarLBraceLoc(IvarLBraceLoc), IvarRBraceLoc(IvarRBraceLoc) {
1301  }
1302public:
1303
1304  static ObjCCategoryDecl *Create(ASTContext &C, DeclContext *DC,
1305                                  SourceLocation AtLoc,
1306                                  SourceLocation ClassNameLoc,
1307                                  SourceLocation CategoryNameLoc,
1308                                  IdentifierInfo *Id,
1309                                  ObjCInterfaceDecl *IDecl,
1310                                  SourceLocation IvarLBraceLoc=SourceLocation(),
1311                                  SourceLocation IvarRBraceLoc=SourceLocation());
1312  static ObjCCategoryDecl *CreateDeserialized(ASTContext &C, unsigned ID);
1313
1314  ObjCInterfaceDecl *getClassInterface() { return ClassInterface; }
1315  const ObjCInterfaceDecl *getClassInterface() const { return ClassInterface; }
1316
1317  ObjCCategoryImplDecl *getImplementation() const;
1318  void setImplementation(ObjCCategoryImplDecl *ImplD);
1319
1320  /// setProtocolList - Set the list of protocols that this interface
1321  /// implements.
1322  void setProtocolList(ObjCProtocolDecl *const*List, unsigned Num,
1323                       const SourceLocation *Locs, ASTContext &C) {
1324    ReferencedProtocols.set(List, Num, Locs, C);
1325  }
1326
1327  const ObjCProtocolList &getReferencedProtocols() const {
1328    return ReferencedProtocols;
1329  }
1330
1331  typedef ObjCProtocolList::iterator protocol_iterator;
1332  protocol_iterator protocol_begin() const {return ReferencedProtocols.begin();}
1333  protocol_iterator protocol_end() const { return ReferencedProtocols.end(); }
1334  unsigned protocol_size() const { return ReferencedProtocols.size(); }
1335  typedef ObjCProtocolList::loc_iterator protocol_loc_iterator;
1336  protocol_loc_iterator protocol_loc_begin() const {
1337    return ReferencedProtocols.loc_begin();
1338  }
1339  protocol_loc_iterator protocol_loc_end() const {
1340    return ReferencedProtocols.loc_end();
1341  }
1342
1343  ObjCCategoryDecl *getNextClassCategory() const { return NextClassCategory; }
1344
1345  bool IsClassExtension() const { return getIdentifier() == 0; }
1346  const ObjCCategoryDecl *getNextClassExtension() const;
1347
1348  bool hasSynthBitfield() const { return HasSynthBitfield; }
1349  void setHasSynthBitfield (bool val) { HasSynthBitfield = val; }
1350
1351  typedef specific_decl_iterator<ObjCIvarDecl> ivar_iterator;
1352  ivar_iterator ivar_begin() const {
1353    return ivar_iterator(decls_begin());
1354  }
1355  ivar_iterator ivar_end() const {
1356    return ivar_iterator(decls_end());
1357  }
1358  unsigned ivar_size() const {
1359    return std::distance(ivar_begin(), ivar_end());
1360  }
1361  bool ivar_empty() const {
1362    return ivar_begin() == ivar_end();
1363  }
1364
1365  SourceLocation getCategoryNameLoc() const { return CategoryNameLoc; }
1366  void setCategoryNameLoc(SourceLocation Loc) { CategoryNameLoc = Loc; }
1367
1368  void setIvarLBraceLoc(SourceLocation Loc) { IvarLBraceLoc = Loc; }
1369  SourceLocation getIvarLBraceLoc() const { return IvarLBraceLoc; }
1370  void setIvarRBraceLoc(SourceLocation Loc) { IvarRBraceLoc = Loc; }
1371  SourceLocation getIvarRBraceLoc() const { return IvarRBraceLoc; }
1372
1373  static bool classof(const Decl *D) { return classofKind(D->getKind()); }
1374  static bool classof(const ObjCCategoryDecl *D) { return true; }
1375  static bool classofKind(Kind K) { return K == ObjCCategory; }
1376
1377  friend class ASTDeclReader;
1378  friend class ASTDeclWriter;
1379};
1380
1381class ObjCImplDecl : public ObjCContainerDecl {
1382  virtual void anchor();
1383
1384  /// Class interface for this class/category implementation
1385  ObjCInterfaceDecl *ClassInterface;
1386
1387protected:
1388  ObjCImplDecl(Kind DK, DeclContext *DC,
1389               ObjCInterfaceDecl *classInterface,
1390               SourceLocation nameLoc, SourceLocation atStartLoc)
1391    : ObjCContainerDecl(DK, DC,
1392                        classInterface? classInterface->getIdentifier() : 0,
1393                        nameLoc, atStartLoc),
1394      ClassInterface(classInterface) {}
1395
1396public:
1397  const ObjCInterfaceDecl *getClassInterface() const { return ClassInterface; }
1398  ObjCInterfaceDecl *getClassInterface() { return ClassInterface; }
1399  void setClassInterface(ObjCInterfaceDecl *IFace);
1400
1401  void addInstanceMethod(ObjCMethodDecl *method) {
1402    // FIXME: Context should be set correctly before we get here.
1403    method->setLexicalDeclContext(this);
1404    addDecl(method);
1405  }
1406  void addClassMethod(ObjCMethodDecl *method) {
1407    // FIXME: Context should be set correctly before we get here.
1408    method->setLexicalDeclContext(this);
1409    addDecl(method);
1410  }
1411
1412  void addPropertyImplementation(ObjCPropertyImplDecl *property);
1413
1414  ObjCPropertyImplDecl *FindPropertyImplDecl(IdentifierInfo *propertyId) const;
1415  ObjCPropertyImplDecl *FindPropertyImplIvarDecl(IdentifierInfo *ivarId) const;
1416
1417  // Iterator access to properties.
1418  typedef specific_decl_iterator<ObjCPropertyImplDecl> propimpl_iterator;
1419  propimpl_iterator propimpl_begin() const {
1420    return propimpl_iterator(decls_begin());
1421  }
1422  propimpl_iterator propimpl_end() const {
1423    return propimpl_iterator(decls_end());
1424  }
1425
1426  static bool classof(const Decl *D) { return classofKind(D->getKind()); }
1427  static bool classof(const ObjCImplDecl *D) { return true; }
1428  static bool classofKind(Kind K) {
1429    return K >= firstObjCImpl && K <= lastObjCImpl;
1430  }
1431};
1432
1433/// ObjCCategoryImplDecl - An object of this class encapsulates a category
1434/// @implementation declaration. If a category class has declaration of a
1435/// property, its implementation must be specified in the category's
1436/// @implementation declaration. Example:
1437/// @interface I @end
1438/// @interface I(CATEGORY)
1439///    @property int p1, d1;
1440/// @end
1441/// @implementation I(CATEGORY)
1442///  @dynamic p1,d1;
1443/// @end
1444///
1445/// ObjCCategoryImplDecl
1446class ObjCCategoryImplDecl : public ObjCImplDecl {
1447  virtual void anchor();
1448
1449  // Category name
1450  IdentifierInfo *Id;
1451
1452  // Category name location
1453  SourceLocation CategoryNameLoc;
1454
1455  ObjCCategoryImplDecl(DeclContext *DC, IdentifierInfo *Id,
1456                       ObjCInterfaceDecl *classInterface,
1457                       SourceLocation nameLoc, SourceLocation atStartLoc,
1458                       SourceLocation CategoryNameLoc)
1459    : ObjCImplDecl(ObjCCategoryImpl, DC, classInterface, nameLoc, atStartLoc),
1460      Id(Id), CategoryNameLoc(CategoryNameLoc) {}
1461public:
1462  static ObjCCategoryImplDecl *Create(ASTContext &C, DeclContext *DC,
1463                                      IdentifierInfo *Id,
1464                                      ObjCInterfaceDecl *classInterface,
1465                                      SourceLocation nameLoc,
1466                                      SourceLocation atStartLoc,
1467                                      SourceLocation CategoryNameLoc);
1468  static ObjCCategoryImplDecl *CreateDeserialized(ASTContext &C, unsigned ID);
1469
1470  /// getIdentifier - Get the identifier that names the category
1471  /// interface associated with this implementation.
1472  /// FIXME: This is a bad API, we are overriding the NamedDecl::getIdentifier()
1473  /// to mean something different. For example:
1474  /// ((NamedDecl *)SomeCategoryImplDecl)->getIdentifier()
1475  /// returns the class interface name, whereas
1476  /// ((ObjCCategoryImplDecl *)SomeCategoryImplDecl)->getIdentifier()
1477  /// returns the category name.
1478  IdentifierInfo *getIdentifier() const {
1479    return Id;
1480  }
1481  void setIdentifier(IdentifierInfo *II) { Id = II; }
1482
1483  ObjCCategoryDecl *getCategoryDecl() const;
1484
1485  SourceLocation getCategoryNameLoc() const { return CategoryNameLoc; }
1486
1487  /// getName - Get the name of identifier for the class interface associated
1488  /// with this implementation as a StringRef.
1489  //
1490  // FIXME: This is a bad API, we are overriding the NamedDecl::getName, to mean
1491  // something different.
1492  StringRef getName() const {
1493    return Id ? Id->getNameStart() : "";
1494  }
1495
1496  /// getNameAsCString - Get the name of identifier for the class
1497  /// interface associated with this implementation as a C string
1498  /// (const char*).
1499  //
1500  // FIXME: Deprecated, move clients to getName().
1501  const char *getNameAsCString() const {
1502    return Id ? Id->getNameStart() : "";
1503  }
1504
1505  /// @brief Get the name of the class associated with this interface.
1506  //
1507  // FIXME: Deprecated, move clients to getName().
1508  std::string getNameAsString() const {
1509    return getName();
1510  }
1511
1512  static bool classof(const Decl *D) { return classofKind(D->getKind()); }
1513  static bool classof(const ObjCCategoryImplDecl *D) { return true; }
1514  static bool classofKind(Kind K) { return K == ObjCCategoryImpl;}
1515
1516  friend class ASTDeclReader;
1517  friend class ASTDeclWriter;
1518};
1519
1520raw_ostream &operator<<(raw_ostream &OS, const ObjCCategoryImplDecl &CID);
1521
1522/// ObjCImplementationDecl - Represents a class definition - this is where
1523/// method definitions are specified. For example:
1524///
1525/// @code
1526/// @implementation MyClass
1527/// - (void)myMethod { /* do something */ }
1528/// @end
1529/// @endcode
1530///
1531/// Typically, instance variables are specified in the class interface,
1532/// *not* in the implementation. Nevertheless (for legacy reasons), we
1533/// allow instance variables to be specified in the implementation.  When
1534/// specified, they need to be *identical* to the interface.
1535///
1536class ObjCImplementationDecl : public ObjCImplDecl {
1537  virtual void anchor();
1538  /// Implementation Class's super class.
1539  ObjCInterfaceDecl *SuperClass;
1540  /// @implementation may have private ivars.
1541  SourceLocation IvarLBraceLoc;
1542  SourceLocation IvarRBraceLoc;
1543
1544  /// Support for ivar initialization.
1545  /// IvarInitializers - The arguments used to initialize the ivars
1546  CXXCtorInitializer **IvarInitializers;
1547  unsigned NumIvarInitializers;
1548
1549  /// true if class has a .cxx_[construct,destruct] method.
1550  bool HasCXXStructors : 1;
1551
1552  /// true of class extension has at least one bitfield ivar.
1553  bool HasSynthBitfield : 1;
1554
1555  ObjCImplementationDecl(DeclContext *DC,
1556                         ObjCInterfaceDecl *classInterface,
1557                         ObjCInterfaceDecl *superDecl,
1558                         SourceLocation nameLoc, SourceLocation atStartLoc,
1559                         SourceLocation IvarLBraceLoc=SourceLocation(),
1560                         SourceLocation IvarRBraceLoc=SourceLocation())
1561    : ObjCImplDecl(ObjCImplementation, DC, classInterface, nameLoc, atStartLoc),
1562       SuperClass(superDecl), IvarLBraceLoc(IvarLBraceLoc),
1563       IvarRBraceLoc(IvarRBraceLoc),
1564       IvarInitializers(0), NumIvarInitializers(0),
1565       HasCXXStructors(false), HasSynthBitfield(false){}
1566public:
1567  static ObjCImplementationDecl *Create(ASTContext &C, DeclContext *DC,
1568                                        ObjCInterfaceDecl *classInterface,
1569                                        ObjCInterfaceDecl *superDecl,
1570                                        SourceLocation nameLoc,
1571                                        SourceLocation atStartLoc,
1572                                        SourceLocation IvarLBraceLoc=SourceLocation(),
1573                                        SourceLocation IvarRBraceLoc=SourceLocation());
1574
1575  static ObjCImplementationDecl *CreateDeserialized(ASTContext &C, unsigned ID);
1576
1577  /// init_iterator - Iterates through the ivar initializer list.
1578  typedef CXXCtorInitializer **init_iterator;
1579
1580  /// init_const_iterator - Iterates through the ivar initializer list.
1581  typedef CXXCtorInitializer * const * init_const_iterator;
1582
1583  /// init_begin() - Retrieve an iterator to the first initializer.
1584  init_iterator       init_begin()       { return IvarInitializers; }
1585  /// begin() - Retrieve an iterator to the first initializer.
1586  init_const_iterator init_begin() const { return IvarInitializers; }
1587
1588  /// init_end() - Retrieve an iterator past the last initializer.
1589  init_iterator       init_end()       {
1590    return IvarInitializers + NumIvarInitializers;
1591  }
1592  /// end() - Retrieve an iterator past the last initializer.
1593  init_const_iterator init_end() const {
1594    return IvarInitializers + NumIvarInitializers;
1595  }
1596  /// getNumArgs - Number of ivars which must be initialized.
1597  unsigned getNumIvarInitializers() const {
1598    return NumIvarInitializers;
1599  }
1600
1601  void setNumIvarInitializers(unsigned numNumIvarInitializers) {
1602    NumIvarInitializers = numNumIvarInitializers;
1603  }
1604
1605  void setIvarInitializers(ASTContext &C,
1606                           CXXCtorInitializer ** initializers,
1607                           unsigned numInitializers);
1608
1609  bool hasCXXStructors() const { return HasCXXStructors; }
1610  void setHasCXXStructors(bool val) { HasCXXStructors = val; }
1611
1612  bool hasSynthBitfield() const { return HasSynthBitfield; }
1613  void setHasSynthBitfield (bool val) { HasSynthBitfield = val; }
1614
1615  /// getIdentifier - Get the identifier that names the class
1616  /// interface associated with this implementation.
1617  IdentifierInfo *getIdentifier() const {
1618    return getClassInterface()->getIdentifier();
1619  }
1620
1621  /// getName - Get the name of identifier for the class interface associated
1622  /// with this implementation as a StringRef.
1623  //
1624  // FIXME: This is a bad API, we are overriding the NamedDecl::getName, to mean
1625  // something different.
1626  StringRef getName() const {
1627    assert(getIdentifier() && "Name is not a simple identifier");
1628    return getIdentifier()->getName();
1629  }
1630
1631  /// getNameAsCString - Get the name of identifier for the class
1632  /// interface associated with this implementation as a C string
1633  /// (const char*).
1634  //
1635  // FIXME: Move to StringRef API.
1636  const char *getNameAsCString() const {
1637    return getName().data();
1638  }
1639
1640  /// @brief Get the name of the class associated with this interface.
1641  //
1642  // FIXME: Move to StringRef API.
1643  std::string getNameAsString() const {
1644    return getName();
1645  }
1646
1647  const ObjCInterfaceDecl *getSuperClass() const { return SuperClass; }
1648  ObjCInterfaceDecl *getSuperClass() { return SuperClass; }
1649
1650  void setSuperClass(ObjCInterfaceDecl * superCls) { SuperClass = superCls; }
1651
1652  void setIvarLBraceLoc(SourceLocation Loc) { IvarLBraceLoc = Loc; }
1653  SourceLocation getIvarLBraceLoc() const { return IvarLBraceLoc; }
1654  void setIvarRBraceLoc(SourceLocation Loc) { IvarRBraceLoc = Loc; }
1655  SourceLocation getIvarRBraceLoc() const { return IvarRBraceLoc; }
1656
1657  typedef specific_decl_iterator<ObjCIvarDecl> ivar_iterator;
1658  ivar_iterator ivar_begin() const {
1659    return ivar_iterator(decls_begin());
1660  }
1661  ivar_iterator ivar_end() const {
1662    return ivar_iterator(decls_end());
1663  }
1664  unsigned ivar_size() const {
1665    return std::distance(ivar_begin(), ivar_end());
1666  }
1667  bool ivar_empty() const {
1668    return ivar_begin() == ivar_end();
1669  }
1670
1671  static bool classof(const Decl *D) { return classofKind(D->getKind()); }
1672  static bool classof(const ObjCImplementationDecl *D) { return true; }
1673  static bool classofKind(Kind K) { return K == ObjCImplementation; }
1674
1675  friend class ASTDeclReader;
1676  friend class ASTDeclWriter;
1677};
1678
1679raw_ostream &operator<<(raw_ostream &OS, const ObjCImplementationDecl &ID);
1680
1681/// ObjCCompatibleAliasDecl - Represents alias of a class. This alias is
1682/// declared as @compatibility_alias alias class.
1683class ObjCCompatibleAliasDecl : public NamedDecl {
1684  virtual void anchor();
1685  /// Class that this is an alias of.
1686  ObjCInterfaceDecl *AliasedClass;
1687
1688  ObjCCompatibleAliasDecl(DeclContext *DC, SourceLocation L, IdentifierInfo *Id,
1689                          ObjCInterfaceDecl* aliasedClass)
1690    : NamedDecl(ObjCCompatibleAlias, DC, L, Id), AliasedClass(aliasedClass) {}
1691public:
1692  static ObjCCompatibleAliasDecl *Create(ASTContext &C, DeclContext *DC,
1693                                         SourceLocation L, IdentifierInfo *Id,
1694                                         ObjCInterfaceDecl* aliasedClass);
1695
1696  static ObjCCompatibleAliasDecl *CreateDeserialized(ASTContext &C,
1697                                                     unsigned ID);
1698
1699  const ObjCInterfaceDecl *getClassInterface() const { return AliasedClass; }
1700  ObjCInterfaceDecl *getClassInterface() { return AliasedClass; }
1701  void setClassInterface(ObjCInterfaceDecl *D) { AliasedClass = D; }
1702
1703  static bool classof(const Decl *D) { return classofKind(D->getKind()); }
1704  static bool classof(const ObjCCompatibleAliasDecl *D) { return true; }
1705  static bool classofKind(Kind K) { return K == ObjCCompatibleAlias; }
1706
1707};
1708
1709/// ObjCPropertyDecl - Represents one property declaration in an interface.
1710/// For example:
1711/// @property (assign, readwrite) int MyProperty;
1712///
1713class ObjCPropertyDecl : public NamedDecl {
1714  virtual void anchor();
1715public:
1716  enum PropertyAttributeKind {
1717    OBJC_PR_noattr    = 0x00,
1718    OBJC_PR_readonly  = 0x01,
1719    OBJC_PR_getter    = 0x02,
1720    OBJC_PR_assign    = 0x04,
1721    OBJC_PR_readwrite = 0x08,
1722    OBJC_PR_retain    = 0x10,
1723    OBJC_PR_copy      = 0x20,
1724    OBJC_PR_nonatomic = 0x40,
1725    OBJC_PR_setter    = 0x80,
1726    OBJC_PR_atomic    = 0x100,
1727    OBJC_PR_weak      = 0x200,
1728    OBJC_PR_strong    = 0x400,
1729    OBJC_PR_unsafe_unretained = 0x800
1730    // Adding a property should change NumPropertyAttrsBits
1731  };
1732
1733  enum {
1734    /// \brief Number of bits fitting all the property attributes.
1735    NumPropertyAttrsBits = 12
1736  };
1737
1738  enum SetterKind { Assign, Retain, Copy, Weak };
1739  enum PropertyControl { None, Required, Optional };
1740private:
1741  SourceLocation AtLoc;   // location of @property
1742  SourceLocation LParenLoc; // location of '(' starting attribute list or null.
1743  TypeSourceInfo *DeclType;
1744  unsigned PropertyAttributes : NumPropertyAttrsBits;
1745  unsigned PropertyAttributesAsWritten : NumPropertyAttrsBits;
1746  // @required/@optional
1747  unsigned PropertyImplementation : 2;
1748
1749  Selector GetterName;    // getter name of NULL if no getter
1750  Selector SetterName;    // setter name of NULL if no setter
1751
1752  ObjCMethodDecl *GetterMethodDecl; // Declaration of getter instance method
1753  ObjCMethodDecl *SetterMethodDecl; // Declaration of setter instance method
1754  ObjCIvarDecl *PropertyIvarDecl;   // Synthesize ivar for this property
1755
1756  ObjCPropertyDecl(DeclContext *DC, SourceLocation L, IdentifierInfo *Id,
1757                   SourceLocation AtLocation,  SourceLocation LParenLocation,
1758                   TypeSourceInfo *T)
1759    : NamedDecl(ObjCProperty, DC, L, Id), AtLoc(AtLocation),
1760      LParenLoc(LParenLocation), DeclType(T),
1761      PropertyAttributes(OBJC_PR_noattr),
1762      PropertyAttributesAsWritten(OBJC_PR_noattr),
1763      PropertyImplementation(None),
1764      GetterName(Selector()),
1765      SetterName(Selector()),
1766      GetterMethodDecl(0), SetterMethodDecl(0) , PropertyIvarDecl(0) {}
1767public:
1768  static ObjCPropertyDecl *Create(ASTContext &C, DeclContext *DC,
1769                                  SourceLocation L,
1770                                  IdentifierInfo *Id, SourceLocation AtLocation,
1771                                  SourceLocation LParenLocation,
1772                                  TypeSourceInfo *T,
1773                                  PropertyControl propControl = None);
1774
1775  static ObjCPropertyDecl *CreateDeserialized(ASTContext &C, unsigned ID);
1776
1777  SourceLocation getAtLoc() const { return AtLoc; }
1778  void setAtLoc(SourceLocation L) { AtLoc = L; }
1779
1780  SourceLocation getLParenLoc() const { return LParenLoc; }
1781  void setLParenLoc(SourceLocation L) { LParenLoc = L; }
1782
1783  TypeSourceInfo *getTypeSourceInfo() const { return DeclType; }
1784  QualType getType() const { return DeclType->getType(); }
1785  void setType(TypeSourceInfo *T) { DeclType = T; }
1786
1787  PropertyAttributeKind getPropertyAttributes() const {
1788    return PropertyAttributeKind(PropertyAttributes);
1789  }
1790  void setPropertyAttributes(PropertyAttributeKind PRVal) {
1791    PropertyAttributes |= PRVal;
1792  }
1793
1794  PropertyAttributeKind getPropertyAttributesAsWritten() const {
1795    return PropertyAttributeKind(PropertyAttributesAsWritten);
1796  }
1797
1798  bool hasWrittenStorageAttribute() const {
1799    return PropertyAttributesAsWritten & (OBJC_PR_assign | OBJC_PR_copy |
1800        OBJC_PR_unsafe_unretained | OBJC_PR_retain | OBJC_PR_strong |
1801        OBJC_PR_weak);
1802  }
1803
1804  void setPropertyAttributesAsWritten(PropertyAttributeKind PRVal) {
1805    PropertyAttributesAsWritten = PRVal;
1806  }
1807
1808 void makeitReadWriteAttribute(void) {
1809    PropertyAttributes &= ~OBJC_PR_readonly;
1810    PropertyAttributes |= OBJC_PR_readwrite;
1811 }
1812
1813  // Helper methods for accessing attributes.
1814
1815  /// isReadOnly - Return true iff the property has a setter.
1816  bool isReadOnly() const {
1817    return (PropertyAttributes & OBJC_PR_readonly);
1818  }
1819
1820  /// isAtomic - Return true if the property is atomic.
1821  bool isAtomic() const {
1822    return (PropertyAttributes & OBJC_PR_atomic);
1823  }
1824
1825  /// isRetaining - Return true if the property retains its value.
1826  bool isRetaining() const {
1827    return (PropertyAttributes &
1828            (OBJC_PR_retain | OBJC_PR_strong | OBJC_PR_copy));
1829  }
1830
1831  /// getSetterKind - Return the method used for doing assignment in
1832  /// the property setter. This is only valid if the property has been
1833  /// defined to have a setter.
1834  SetterKind getSetterKind() const {
1835    if (PropertyAttributes & OBJC_PR_strong)
1836      return getType()->isBlockPointerType() ? Copy : Retain;
1837    if (PropertyAttributes & OBJC_PR_retain)
1838      return Retain;
1839    if (PropertyAttributes & OBJC_PR_copy)
1840      return Copy;
1841    if (PropertyAttributes & OBJC_PR_weak)
1842      return Weak;
1843    return Assign;
1844  }
1845
1846  Selector getGetterName() const { return GetterName; }
1847  void setGetterName(Selector Sel) { GetterName = Sel; }
1848
1849  Selector getSetterName() const { return SetterName; }
1850  void setSetterName(Selector Sel) { SetterName = Sel; }
1851
1852  ObjCMethodDecl *getGetterMethodDecl() const { return GetterMethodDecl; }
1853  void setGetterMethodDecl(ObjCMethodDecl *gDecl) { GetterMethodDecl = gDecl; }
1854
1855  ObjCMethodDecl *getSetterMethodDecl() const { return SetterMethodDecl; }
1856  void setSetterMethodDecl(ObjCMethodDecl *gDecl) { SetterMethodDecl = gDecl; }
1857
1858  // Related to @optional/@required declared in @protocol
1859  void setPropertyImplementation(PropertyControl pc) {
1860    PropertyImplementation = pc;
1861  }
1862  PropertyControl getPropertyImplementation() const {
1863    return PropertyControl(PropertyImplementation);
1864  }
1865
1866  void setPropertyIvarDecl(ObjCIvarDecl *Ivar) {
1867    PropertyIvarDecl = Ivar;
1868  }
1869  ObjCIvarDecl *getPropertyIvarDecl() const {
1870    return PropertyIvarDecl;
1871  }
1872
1873  virtual SourceRange getSourceRange() const LLVM_READONLY {
1874    return SourceRange(AtLoc, getLocation());
1875  }
1876
1877  /// Lookup a property by name in the specified DeclContext.
1878  static ObjCPropertyDecl *findPropertyDecl(const DeclContext *DC,
1879                                            IdentifierInfo *propertyID);
1880
1881  static bool classof(const Decl *D) { return classofKind(D->getKind()); }
1882  static bool classof(const ObjCPropertyDecl *D) { return true; }
1883  static bool classofKind(Kind K) { return K == ObjCProperty; }
1884};
1885
1886/// ObjCPropertyImplDecl - Represents implementation declaration of a property
1887/// in a class or category implementation block. For example:
1888/// @synthesize prop1 = ivar1;
1889///
1890class ObjCPropertyImplDecl : public Decl {
1891public:
1892  enum Kind {
1893    Synthesize,
1894    Dynamic
1895  };
1896private:
1897  SourceLocation AtLoc;   // location of @synthesize or @dynamic
1898
1899  /// \brief For @synthesize, the location of the ivar, if it was written in
1900  /// the source code.
1901  ///
1902  /// \code
1903  /// @synthesize int a = b
1904  /// \endcode
1905  SourceLocation IvarLoc;
1906
1907  /// Property declaration being implemented
1908  ObjCPropertyDecl *PropertyDecl;
1909
1910  /// Null for @dynamic. Required for @synthesize.
1911  ObjCIvarDecl *PropertyIvarDecl;
1912
1913  /// Null for @dynamic. Non-null if property must be copy-constructed in getter
1914  Expr *GetterCXXConstructor;
1915
1916  /// Null for @dynamic. Non-null if property has assignment operator to call
1917  /// in Setter synthesis.
1918  Expr *SetterCXXAssignment;
1919
1920  ObjCPropertyImplDecl(DeclContext *DC, SourceLocation atLoc, SourceLocation L,
1921                       ObjCPropertyDecl *property,
1922                       Kind PK,
1923                       ObjCIvarDecl *ivarDecl,
1924                       SourceLocation ivarLoc)
1925    : Decl(ObjCPropertyImpl, DC, L), AtLoc(atLoc),
1926      IvarLoc(ivarLoc), PropertyDecl(property), PropertyIvarDecl(ivarDecl),
1927      GetterCXXConstructor(0), SetterCXXAssignment(0) {
1928    assert (PK == Dynamic || PropertyIvarDecl);
1929  }
1930
1931public:
1932  static ObjCPropertyImplDecl *Create(ASTContext &C, DeclContext *DC,
1933                                      SourceLocation atLoc, SourceLocation L,
1934                                      ObjCPropertyDecl *property,
1935                                      Kind PK,
1936                                      ObjCIvarDecl *ivarDecl,
1937                                      SourceLocation ivarLoc);
1938
1939  static ObjCPropertyImplDecl *CreateDeserialized(ASTContext &C, unsigned ID);
1940
1941  virtual SourceRange getSourceRange() const LLVM_READONLY;
1942
1943  SourceLocation getLocStart() const LLVM_READONLY { return AtLoc; }
1944  void setAtLoc(SourceLocation Loc) { AtLoc = Loc; }
1945
1946  ObjCPropertyDecl *getPropertyDecl() const {
1947    return PropertyDecl;
1948  }
1949  void setPropertyDecl(ObjCPropertyDecl *Prop) { PropertyDecl = Prop; }
1950
1951  Kind getPropertyImplementation() const {
1952    return PropertyIvarDecl ? Synthesize : Dynamic;
1953  }
1954
1955  ObjCIvarDecl *getPropertyIvarDecl() const {
1956    return PropertyIvarDecl;
1957  }
1958  SourceLocation getPropertyIvarDeclLoc() const { return IvarLoc; }
1959
1960  void setPropertyIvarDecl(ObjCIvarDecl *Ivar,
1961                           SourceLocation IvarLoc) {
1962    PropertyIvarDecl = Ivar;
1963    this->IvarLoc = IvarLoc;
1964  }
1965
1966  Expr *getGetterCXXConstructor() const {
1967    return GetterCXXConstructor;
1968  }
1969  void setGetterCXXConstructor(Expr *getterCXXConstructor) {
1970    GetterCXXConstructor = getterCXXConstructor;
1971  }
1972
1973  Expr *getSetterCXXAssignment() const {
1974    return SetterCXXAssignment;
1975  }
1976  void setSetterCXXAssignment(Expr *setterCXXAssignment) {
1977    SetterCXXAssignment = setterCXXAssignment;
1978  }
1979
1980  static bool classof(const Decl *D) { return classofKind(D->getKind()); }
1981  static bool classof(const ObjCPropertyImplDecl *D) { return true; }
1982  static bool classofKind(Decl::Kind K) { return K == ObjCPropertyImpl; }
1983
1984  friend class ASTDeclReader;
1985};
1986
1987}  // end namespace clang
1988#endif
1989