1 //===- ExprObjC.h - Classes for representing ObjC expressions ---*- C++ -*-===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 //
9 //  This file defines the ExprObjC interface and subclasses.
10 //
11 //===----------------------------------------------------------------------===//
12 
13 #ifndef LLVM_CLANG_AST_EXPROBJC_H
14 #define LLVM_CLANG_AST_EXPROBJC_H
15 
16 #include "clang/AST/ComputeDependence.h"
17 #include "clang/AST/Decl.h"
18 #include "clang/AST/DeclObjC.h"
19 #include "clang/AST/DependenceFlags.h"
20 #include "clang/AST/Expr.h"
21 #include "clang/AST/OperationKinds.h"
22 #include "clang/AST/SelectorLocationsKind.h"
23 #include "clang/AST/Stmt.h"
24 #include "clang/AST/Type.h"
25 #include "clang/Basic/IdentifierTable.h"
26 #include "clang/Basic/LLVM.h"
27 #include "clang/Basic/SourceLocation.h"
28 #include "clang/Basic/Specifiers.h"
29 #include "llvm/ADT/ArrayRef.h"
30 #include "llvm/ADT/PointerIntPair.h"
31 #include "llvm/ADT/PointerUnion.h"
32 #include "llvm/ADT/StringRef.h"
33 #include "llvm/ADT/iterator_range.h"
34 #include "llvm/Support/Casting.h"
35 #include "llvm/Support/Compiler.h"
36 #include "llvm/Support/TrailingObjects.h"
37 #include "llvm/Support/VersionTuple.h"
38 #include "llvm/Support/type_traits.h"
39 #include <cassert>
40 #include <cstddef>
41 #include <cstdint>
42 #include <optional>
43 
44 namespace clang {
45 
46 class ASTContext;
47 class CXXBaseSpecifier;
48 
49 /// ObjCStringLiteral, used for Objective-C string literals
50 /// i.e. @"foo".
51 class ObjCStringLiteral : public Expr {
52   Stmt *String;
53   SourceLocation AtLoc;
54 
55 public:
ObjCStringLiteral(StringLiteral * SL,QualType T,SourceLocation L)56   ObjCStringLiteral(StringLiteral *SL, QualType T, SourceLocation L)
57       : Expr(ObjCStringLiteralClass, T, VK_PRValue, OK_Ordinary), String(SL),
58         AtLoc(L) {
59     setDependence(ExprDependence::None);
60   }
ObjCStringLiteral(EmptyShell Empty)61   explicit ObjCStringLiteral(EmptyShell Empty)
62       : Expr(ObjCStringLiteralClass, Empty) {}
63 
getString()64   StringLiteral *getString() { return cast<StringLiteral>(String); }
getString()65   const StringLiteral *getString() const { return cast<StringLiteral>(String); }
setString(StringLiteral * S)66   void setString(StringLiteral *S) { String = S; }
67 
getAtLoc()68   SourceLocation getAtLoc() const { return AtLoc; }
setAtLoc(SourceLocation L)69   void setAtLoc(SourceLocation L) { AtLoc = L; }
70 
getBeginLoc()71   SourceLocation getBeginLoc() const LLVM_READONLY { return AtLoc; }
getEndLoc()72   SourceLocation getEndLoc() const LLVM_READONLY { return String->getEndLoc(); }
73 
74   // Iterators
children()75   child_range children() { return child_range(&String, &String+1); }
76 
children()77   const_child_range children() const {
78     return const_child_range(&String, &String + 1);
79   }
80 
classof(const Stmt * T)81   static bool classof(const Stmt *T) {
82     return T->getStmtClass() == ObjCStringLiteralClass;
83   }
84 };
85 
86 /// ObjCBoolLiteralExpr - Objective-C Boolean Literal.
87 class ObjCBoolLiteralExpr : public Expr {
88   bool Value;
89   SourceLocation Loc;
90 
91 public:
ObjCBoolLiteralExpr(bool val,QualType Ty,SourceLocation l)92   ObjCBoolLiteralExpr(bool val, QualType Ty, SourceLocation l)
93       : Expr(ObjCBoolLiteralExprClass, Ty, VK_PRValue, OK_Ordinary), Value(val),
94         Loc(l) {
95     setDependence(ExprDependence::None);
96   }
ObjCBoolLiteralExpr(EmptyShell Empty)97   explicit ObjCBoolLiteralExpr(EmptyShell Empty)
98       : Expr(ObjCBoolLiteralExprClass, Empty) {}
99 
getValue()100   bool getValue() const { return Value; }
setValue(bool V)101   void setValue(bool V) { Value = V; }
102 
getBeginLoc()103   SourceLocation getBeginLoc() const LLVM_READONLY { return Loc; }
getEndLoc()104   SourceLocation getEndLoc() const LLVM_READONLY { return Loc; }
105 
getLocation()106   SourceLocation getLocation() const { return Loc; }
setLocation(SourceLocation L)107   void setLocation(SourceLocation L) { Loc = L; }
108 
109   // Iterators
children()110   child_range children() {
111     return child_range(child_iterator(), child_iterator());
112   }
113 
children()114   const_child_range children() const {
115     return const_child_range(const_child_iterator(), const_child_iterator());
116   }
117 
classof(const Stmt * T)118   static bool classof(const Stmt *T) {
119     return T->getStmtClass() == ObjCBoolLiteralExprClass;
120   }
121 };
122 
123 /// ObjCBoxedExpr - used for generalized expression boxing.
124 /// as in: @(strdup("hello world")), @(random()) or @(view.frame)
125 /// Also used for boxing non-parenthesized numeric literals;
126 /// as in: @42 or \@true (c++/objc++) or \@__objc_yes (c/objc).
127 class ObjCBoxedExpr : public Expr {
128   Stmt *SubExpr;
129   ObjCMethodDecl *BoxingMethod;
130   SourceRange Range;
131 
132 public:
133   friend class ASTStmtReader;
134 
ObjCBoxedExpr(Expr * E,QualType T,ObjCMethodDecl * method,SourceRange R)135   ObjCBoxedExpr(Expr *E, QualType T, ObjCMethodDecl *method, SourceRange R)
136       : Expr(ObjCBoxedExprClass, T, VK_PRValue, OK_Ordinary), SubExpr(E),
137         BoxingMethod(method), Range(R) {
138     setDependence(computeDependence(this));
139   }
ObjCBoxedExpr(EmptyShell Empty)140   explicit ObjCBoxedExpr(EmptyShell Empty)
141       : Expr(ObjCBoxedExprClass, Empty) {}
142 
getSubExpr()143   Expr *getSubExpr() { return cast<Expr>(SubExpr); }
getSubExpr()144   const Expr *getSubExpr() const { return cast<Expr>(SubExpr); }
145 
getBoxingMethod()146   ObjCMethodDecl *getBoxingMethod() const {
147     return BoxingMethod;
148   }
149 
150   // Indicates whether this boxed expression can be emitted as a compile-time
151   // constant.
isExpressibleAsConstantInitializer()152   bool isExpressibleAsConstantInitializer() const {
153     return !BoxingMethod && SubExpr;
154   }
155 
getAtLoc()156   SourceLocation getAtLoc() const { return Range.getBegin(); }
157 
getBeginLoc()158   SourceLocation getBeginLoc() const LLVM_READONLY { return Range.getBegin(); }
getEndLoc()159   SourceLocation getEndLoc() const LLVM_READONLY { return Range.getEnd(); }
160 
getSourceRange()161   SourceRange getSourceRange() const LLVM_READONLY {
162     return Range;
163   }
164 
165   // Iterators
children()166   child_range children() { return child_range(&SubExpr, &SubExpr+1); }
167 
children()168   const_child_range children() const {
169     return const_child_range(&SubExpr, &SubExpr + 1);
170   }
171 
172   using const_arg_iterator = ConstExprIterator;
173 
arg_begin()174   const_arg_iterator arg_begin() const {
175     return reinterpret_cast<Stmt const * const*>(&SubExpr);
176   }
177 
arg_end()178   const_arg_iterator arg_end() const {
179     return reinterpret_cast<Stmt const * const*>(&SubExpr + 1);
180   }
181 
classof(const Stmt * T)182   static bool classof(const Stmt *T) {
183     return T->getStmtClass() == ObjCBoxedExprClass;
184   }
185 };
186 
187 /// ObjCArrayLiteral - used for objective-c array containers; as in:
188 /// @[@"Hello", NSApp, [NSNumber numberWithInt:42]];
189 class ObjCArrayLiteral final
190     : public Expr,
191       private llvm::TrailingObjects<ObjCArrayLiteral, Expr *> {
192   unsigned NumElements;
193   SourceRange Range;
194   ObjCMethodDecl *ArrayWithObjectsMethod;
195 
196   ObjCArrayLiteral(ArrayRef<Expr *> Elements,
197                    QualType T, ObjCMethodDecl * Method,
198                    SourceRange SR);
199 
ObjCArrayLiteral(EmptyShell Empty,unsigned NumElements)200   explicit ObjCArrayLiteral(EmptyShell Empty, unsigned NumElements)
201       : Expr(ObjCArrayLiteralClass, Empty), NumElements(NumElements) {}
202 
203 public:
204   friend class ASTStmtReader;
205   friend TrailingObjects;
206 
207   static ObjCArrayLiteral *Create(const ASTContext &C,
208                                   ArrayRef<Expr *> Elements,
209                                   QualType T, ObjCMethodDecl * Method,
210                                   SourceRange SR);
211 
212   static ObjCArrayLiteral *CreateEmpty(const ASTContext &C,
213                                        unsigned NumElements);
214 
getBeginLoc()215   SourceLocation getBeginLoc() const LLVM_READONLY { return Range.getBegin(); }
getEndLoc()216   SourceLocation getEndLoc() const LLVM_READONLY { return Range.getEnd(); }
getSourceRange()217   SourceRange getSourceRange() const LLVM_READONLY { return Range; }
218 
219   /// Retrieve elements of array of literals.
getElements()220   Expr **getElements() { return getTrailingObjects<Expr *>(); }
221 
222   /// Retrieve elements of array of literals.
getElements()223   const Expr * const *getElements() const {
224     return getTrailingObjects<Expr *>();
225   }
226 
227   /// getNumElements - Return number of elements of objective-c array literal.
getNumElements()228   unsigned getNumElements() const { return NumElements; }
229 
230   /// getElement - Return the Element at the specified index.
getElement(unsigned Index)231   Expr *getElement(unsigned Index) {
232     assert((Index < NumElements) && "Arg access out of range!");
233     return getElements()[Index];
234   }
getElement(unsigned Index)235   const Expr *getElement(unsigned Index) const {
236     assert((Index < NumElements) && "Arg access out of range!");
237     return getElements()[Index];
238   }
239 
getArrayWithObjectsMethod()240   ObjCMethodDecl *getArrayWithObjectsMethod() const {
241     return ArrayWithObjectsMethod;
242   }
243 
244   // Iterators
children()245   child_range children() {
246     return child_range(reinterpret_cast<Stmt **>(getElements()),
247                        reinterpret_cast<Stmt **>(getElements()) + NumElements);
248   }
249 
children()250   const_child_range children() const {
251     auto Children = const_cast<ObjCArrayLiteral *>(this)->children();
252     return const_child_range(Children.begin(), Children.end());
253   }
254 
classof(const Stmt * T)255   static bool classof(const Stmt *T) {
256       return T->getStmtClass() == ObjCArrayLiteralClass;
257   }
258 };
259 
260 /// An element in an Objective-C dictionary literal.
261 ///
262 struct ObjCDictionaryElement {
263   /// The key for the dictionary element.
264   Expr *Key;
265 
266   /// The value of the dictionary element.
267   Expr *Value;
268 
269   /// The location of the ellipsis, if this is a pack expansion.
270   SourceLocation EllipsisLoc;
271 
272   /// The number of elements this pack expansion will expand to, if
273   /// this is a pack expansion and is known.
274   std::optional<unsigned> NumExpansions;
275 
276   /// Determines whether this dictionary element is a pack expansion.
isPackExpansionObjCDictionaryElement277   bool isPackExpansion() const { return EllipsisLoc.isValid(); }
278 };
279 
280 } // namespace clang
281 
282 namespace clang {
283 
284 /// Internal struct for storing Key/value pair.
285 struct ObjCDictionaryLiteral_KeyValuePair {
286   Expr *Key;
287   Expr *Value;
288 };
289 
290 /// Internal struct to describes an element that is a pack
291 /// expansion, used if any of the elements in the dictionary literal
292 /// are pack expansions.
293 struct ObjCDictionaryLiteral_ExpansionData {
294   /// The location of the ellipsis, if this element is a pack
295   /// expansion.
296   SourceLocation EllipsisLoc;
297 
298   /// If non-zero, the number of elements that this pack
299   /// expansion will expand to (+1).
300   unsigned NumExpansionsPlusOne;
301 };
302 
303 /// ObjCDictionaryLiteral - AST node to represent objective-c dictionary
304 /// literals; as in:  @{@"name" : NSUserName(), @"date" : [NSDate date] };
305 class ObjCDictionaryLiteral final
306     : public Expr,
307       private llvm::TrailingObjects<ObjCDictionaryLiteral,
308                                     ObjCDictionaryLiteral_KeyValuePair,
309                                     ObjCDictionaryLiteral_ExpansionData> {
310   /// The number of elements in this dictionary literal.
311   unsigned NumElements : 31;
312 
313   /// Determine whether this dictionary literal has any pack expansions.
314   ///
315   /// If the dictionary literal has pack expansions, then there will
316   /// be an array of pack expansion data following the array of
317   /// key/value pairs, which provide the locations of the ellipses (if
318   /// any) and number of elements in the expansion (if known). If
319   /// there are no pack expansions, we optimize away this storage.
320   LLVM_PREFERRED_TYPE(bool)
321   unsigned HasPackExpansions : 1;
322 
323   SourceRange Range;
324   ObjCMethodDecl *DictWithObjectsMethod;
325 
326   using KeyValuePair = ObjCDictionaryLiteral_KeyValuePair;
327   using ExpansionData = ObjCDictionaryLiteral_ExpansionData;
328 
329   ObjCDictionaryLiteral(ArrayRef<ObjCDictionaryElement> VK,
330                         bool HasPackExpansions,
331                         QualType T, ObjCMethodDecl *method,
332                         SourceRange SR);
333 
ObjCDictionaryLiteral(EmptyShell Empty,unsigned NumElements,bool HasPackExpansions)334   explicit ObjCDictionaryLiteral(EmptyShell Empty, unsigned NumElements,
335                                  bool HasPackExpansions)
336       : Expr(ObjCDictionaryLiteralClass, Empty), NumElements(NumElements),
337         HasPackExpansions(HasPackExpansions) {}
338 
numTrailingObjects(OverloadToken<KeyValuePair>)339   size_t numTrailingObjects(OverloadToken<KeyValuePair>) const {
340     return NumElements;
341   }
342 
343 public:
344   friend class ASTStmtReader;
345   friend class ASTStmtWriter;
346   friend TrailingObjects;
347 
348   static ObjCDictionaryLiteral *Create(const ASTContext &C,
349                                        ArrayRef<ObjCDictionaryElement> VK,
350                                        bool HasPackExpansions,
351                                        QualType T, ObjCMethodDecl *method,
352                                        SourceRange SR);
353 
354   static ObjCDictionaryLiteral *CreateEmpty(const ASTContext &C,
355                                             unsigned NumElements,
356                                             bool HasPackExpansions);
357 
358   /// getNumElements - Return number of elements of objective-c dictionary
359   /// literal.
getNumElements()360   unsigned getNumElements() const { return NumElements; }
361 
getKeyValueElement(unsigned Index)362   ObjCDictionaryElement getKeyValueElement(unsigned Index) const {
363     assert((Index < NumElements) && "Arg access out of range!");
364     const KeyValuePair &KV = getTrailingObjects<KeyValuePair>()[Index];
365     ObjCDictionaryElement Result = {KV.Key, KV.Value, SourceLocation(),
366                                     std::nullopt};
367     if (HasPackExpansions) {
368       const ExpansionData &Expansion =
369           getTrailingObjects<ExpansionData>()[Index];
370       Result.EllipsisLoc = Expansion.EllipsisLoc;
371       if (Expansion.NumExpansionsPlusOne > 0)
372         Result.NumExpansions = Expansion.NumExpansionsPlusOne - 1;
373     }
374     return Result;
375   }
376 
getDictWithObjectsMethod()377   ObjCMethodDecl *getDictWithObjectsMethod() const {
378     return DictWithObjectsMethod;
379   }
380 
getBeginLoc()381   SourceLocation getBeginLoc() const LLVM_READONLY { return Range.getBegin(); }
getEndLoc()382   SourceLocation getEndLoc() const LLVM_READONLY { return Range.getEnd(); }
getSourceRange()383   SourceRange getSourceRange() const LLVM_READONLY { return Range; }
384 
385   // Iterators
children()386   child_range children() {
387     // Note: we're taking advantage of the layout of the KeyValuePair struct
388     // here. If that struct changes, this code will need to change as well.
389     static_assert(sizeof(KeyValuePair) == sizeof(Stmt *) * 2,
390                   "KeyValuePair is expected size");
391     return child_range(
392         reinterpret_cast<Stmt **>(getTrailingObjects<KeyValuePair>()),
393         reinterpret_cast<Stmt **>(getTrailingObjects<KeyValuePair>()) +
394             NumElements * 2);
395   }
396 
children()397   const_child_range children() const {
398     auto Children = const_cast<ObjCDictionaryLiteral *>(this)->children();
399     return const_child_range(Children.begin(), Children.end());
400   }
401 
classof(const Stmt * T)402   static bool classof(const Stmt *T) {
403     return T->getStmtClass() == ObjCDictionaryLiteralClass;
404   }
405 };
406 
407 /// ObjCEncodeExpr, used for \@encode in Objective-C.  \@encode has the same
408 /// type and behavior as StringLiteral except that the string initializer is
409 /// obtained from ASTContext with the encoding type as an argument.
410 class ObjCEncodeExpr : public Expr {
411   TypeSourceInfo *EncodedType;
412   SourceLocation AtLoc, RParenLoc;
413 
414 public:
ObjCEncodeExpr(QualType T,TypeSourceInfo * EncodedType,SourceLocation at,SourceLocation rp)415   ObjCEncodeExpr(QualType T, TypeSourceInfo *EncodedType, SourceLocation at,
416                  SourceLocation rp)
417       : Expr(ObjCEncodeExprClass, T, VK_LValue, OK_Ordinary),
418         EncodedType(EncodedType), AtLoc(at), RParenLoc(rp) {
419     setDependence(computeDependence(this));
420   }
421 
ObjCEncodeExpr(EmptyShell Empty)422   explicit ObjCEncodeExpr(EmptyShell Empty) : Expr(ObjCEncodeExprClass, Empty){}
423 
getAtLoc()424   SourceLocation getAtLoc() const { return AtLoc; }
setAtLoc(SourceLocation L)425   void setAtLoc(SourceLocation L) { AtLoc = L; }
getRParenLoc()426   SourceLocation getRParenLoc() const { return RParenLoc; }
setRParenLoc(SourceLocation L)427   void setRParenLoc(SourceLocation L) { RParenLoc = L; }
428 
getEncodedType()429   QualType getEncodedType() const { return EncodedType->getType(); }
430 
getEncodedTypeSourceInfo()431   TypeSourceInfo *getEncodedTypeSourceInfo() const { return EncodedType; }
432 
setEncodedTypeSourceInfo(TypeSourceInfo * EncType)433   void setEncodedTypeSourceInfo(TypeSourceInfo *EncType) {
434     EncodedType = EncType;
435   }
436 
getBeginLoc()437   SourceLocation getBeginLoc() const LLVM_READONLY { return AtLoc; }
getEndLoc()438   SourceLocation getEndLoc() const LLVM_READONLY { return RParenLoc; }
439 
440   // Iterators
children()441   child_range children() {
442     return child_range(child_iterator(), child_iterator());
443   }
444 
children()445   const_child_range children() const {
446     return const_child_range(const_child_iterator(), const_child_iterator());
447   }
448 
classof(const Stmt * T)449   static bool classof(const Stmt *T) {
450     return T->getStmtClass() == ObjCEncodeExprClass;
451   }
452 };
453 
454 /// ObjCSelectorExpr used for \@selector in Objective-C.
455 class ObjCSelectorExpr : public Expr {
456   Selector SelName;
457   SourceLocation AtLoc, RParenLoc;
458 
459 public:
ObjCSelectorExpr(QualType T,Selector selInfo,SourceLocation at,SourceLocation rp)460   ObjCSelectorExpr(QualType T, Selector selInfo, SourceLocation at,
461                    SourceLocation rp)
462       : Expr(ObjCSelectorExprClass, T, VK_PRValue, OK_Ordinary),
463         SelName(selInfo), AtLoc(at), RParenLoc(rp) {
464     setDependence(ExprDependence::None);
465   }
ObjCSelectorExpr(EmptyShell Empty)466   explicit ObjCSelectorExpr(EmptyShell Empty)
467       : Expr(ObjCSelectorExprClass, Empty) {}
468 
getSelector()469   Selector getSelector() const { return SelName; }
setSelector(Selector S)470   void setSelector(Selector S) { SelName = S; }
471 
getAtLoc()472   SourceLocation getAtLoc() const { return AtLoc; }
getRParenLoc()473   SourceLocation getRParenLoc() const { return RParenLoc; }
setAtLoc(SourceLocation L)474   void setAtLoc(SourceLocation L) { AtLoc = L; }
setRParenLoc(SourceLocation L)475   void setRParenLoc(SourceLocation L) { RParenLoc = L; }
476 
getBeginLoc()477   SourceLocation getBeginLoc() const LLVM_READONLY { return AtLoc; }
getEndLoc()478   SourceLocation getEndLoc() const LLVM_READONLY { return RParenLoc; }
479 
480   /// getNumArgs - Return the number of actual arguments to this call.
getNumArgs()481   unsigned getNumArgs() const { return SelName.getNumArgs(); }
482 
483   // Iterators
children()484   child_range children() {
485     return child_range(child_iterator(), child_iterator());
486   }
487 
children()488   const_child_range children() const {
489     return const_child_range(const_child_iterator(), const_child_iterator());
490   }
491 
classof(const Stmt * T)492   static bool classof(const Stmt *T) {
493     return T->getStmtClass() == ObjCSelectorExprClass;
494   }
495 };
496 
497 /// ObjCProtocolExpr used for protocol expression in Objective-C.
498 ///
499 /// This is used as: \@protocol(foo), as in:
500 /// \code
501 ///   [obj conformsToProtocol:@protocol(foo)]
502 /// \endcode
503 ///
504 /// The return type is "Protocol*".
505 class ObjCProtocolExpr : public Expr {
506   ObjCProtocolDecl *TheProtocol;
507   SourceLocation AtLoc, ProtoLoc, RParenLoc;
508 
509 public:
510   friend class ASTStmtReader;
511   friend class ASTStmtWriter;
512 
ObjCProtocolExpr(QualType T,ObjCProtocolDecl * protocol,SourceLocation at,SourceLocation protoLoc,SourceLocation rp)513   ObjCProtocolExpr(QualType T, ObjCProtocolDecl *protocol, SourceLocation at,
514                    SourceLocation protoLoc, SourceLocation rp)
515       : Expr(ObjCProtocolExprClass, T, VK_PRValue, OK_Ordinary),
516         TheProtocol(protocol), AtLoc(at), ProtoLoc(protoLoc), RParenLoc(rp) {
517     setDependence(ExprDependence::None);
518   }
ObjCProtocolExpr(EmptyShell Empty)519   explicit ObjCProtocolExpr(EmptyShell Empty)
520       : Expr(ObjCProtocolExprClass, Empty) {}
521 
getProtocol()522   ObjCProtocolDecl *getProtocol() const { return TheProtocol; }
setProtocol(ObjCProtocolDecl * P)523   void setProtocol(ObjCProtocolDecl *P) { TheProtocol = P; }
524 
getProtocolIdLoc()525   SourceLocation getProtocolIdLoc() const { return ProtoLoc; }
getAtLoc()526   SourceLocation getAtLoc() const { return AtLoc; }
getRParenLoc()527   SourceLocation getRParenLoc() const { return RParenLoc; }
setAtLoc(SourceLocation L)528   void setAtLoc(SourceLocation L) { AtLoc = L; }
setRParenLoc(SourceLocation L)529   void setRParenLoc(SourceLocation L) { RParenLoc = L; }
530 
getBeginLoc()531   SourceLocation getBeginLoc() const LLVM_READONLY { return AtLoc; }
getEndLoc()532   SourceLocation getEndLoc() const LLVM_READONLY { return RParenLoc; }
533 
534   // Iterators
children()535   child_range children() {
536     return child_range(child_iterator(), child_iterator());
537   }
538 
children()539   const_child_range children() const {
540     return const_child_range(const_child_iterator(), const_child_iterator());
541   }
542 
classof(const Stmt * T)543   static bool classof(const Stmt *T) {
544     return T->getStmtClass() == ObjCProtocolExprClass;
545   }
546 };
547 
548 /// ObjCIvarRefExpr - A reference to an ObjC instance variable.
549 class ObjCIvarRefExpr : public Expr {
550   ObjCIvarDecl *D;
551   Stmt *Base;
552   SourceLocation Loc;
553 
554   /// OpLoc - This is the location of '.' or '->'
555   SourceLocation OpLoc;
556 
557   // True if this is "X->F", false if this is "X.F".
558   LLVM_PREFERRED_TYPE(bool)
559   bool IsArrow : 1;
560 
561   // True if ivar reference has no base (self assumed).
562   LLVM_PREFERRED_TYPE(bool)
563   bool IsFreeIvar : 1;
564 
565 public:
566   ObjCIvarRefExpr(ObjCIvarDecl *d, QualType t, SourceLocation l,
567                   SourceLocation oploc, Expr *base, bool arrow = false,
568                   bool freeIvar = false)
569       : Expr(ObjCIvarRefExprClass, t, VK_LValue,
570              d->isBitField() ? OK_BitField : OK_Ordinary),
571         D(d), Base(base), Loc(l), OpLoc(oploc), IsArrow(arrow),
572         IsFreeIvar(freeIvar) {
573     setDependence(computeDependence(this));
574   }
575 
ObjCIvarRefExpr(EmptyShell Empty)576   explicit ObjCIvarRefExpr(EmptyShell Empty)
577       : Expr(ObjCIvarRefExprClass, Empty) {}
578 
getDecl()579   ObjCIvarDecl *getDecl() { return D; }
getDecl()580   const ObjCIvarDecl *getDecl() const { return D; }
setDecl(ObjCIvarDecl * d)581   void setDecl(ObjCIvarDecl *d) { D = d; }
582 
getBase()583   const Expr *getBase() const { return cast<Expr>(Base); }
getBase()584   Expr *getBase() { return cast<Expr>(Base); }
setBase(Expr * base)585   void setBase(Expr * base) { Base = base; }
586 
isArrow()587   bool isArrow() const { return IsArrow; }
isFreeIvar()588   bool isFreeIvar() const { return IsFreeIvar; }
setIsArrow(bool A)589   void setIsArrow(bool A) { IsArrow = A; }
setIsFreeIvar(bool A)590   void setIsFreeIvar(bool A) { IsFreeIvar = A; }
591 
getLocation()592   SourceLocation getLocation() const { return Loc; }
setLocation(SourceLocation L)593   void setLocation(SourceLocation L) { Loc = L; }
594 
getBeginLoc()595   SourceLocation getBeginLoc() const LLVM_READONLY {
596     return isFreeIvar() ? Loc : getBase()->getBeginLoc();
597   }
getEndLoc()598   SourceLocation getEndLoc() const LLVM_READONLY { return Loc; }
599 
getOpLoc()600   SourceLocation getOpLoc() const { return OpLoc; }
setOpLoc(SourceLocation L)601   void setOpLoc(SourceLocation L) { OpLoc = L; }
602 
603   // Iterators
children()604   child_range children() { return child_range(&Base, &Base+1); }
605 
children()606   const_child_range children() const {
607     return const_child_range(&Base, &Base + 1);
608   }
609 
classof(const Stmt * T)610   static bool classof(const Stmt *T) {
611     return T->getStmtClass() == ObjCIvarRefExprClass;
612   }
613 };
614 
615 /// ObjCPropertyRefExpr - A dot-syntax expression to access an ObjC
616 /// property.
617 class ObjCPropertyRefExpr : public Expr {
618 private:
619   /// If the bool is true, this is an implicit property reference; the
620   /// pointer is an (optional) ObjCMethodDecl and Setter may be set.
621   /// if the bool is false, this is an explicit property reference;
622   /// the pointer is an ObjCPropertyDecl and Setter is always null.
623   llvm::PointerIntPair<NamedDecl *, 1, bool> PropertyOrGetter;
624 
625   /// Indicates whether the property reference will result in a message
626   /// to the getter, the setter, or both.
627   /// This applies to both implicit and explicit property references.
628   enum MethodRefFlags {
629     MethodRef_None = 0,
630     MethodRef_Getter = 0x1,
631     MethodRef_Setter = 0x2
632   };
633 
634   /// Contains the Setter method pointer and MethodRefFlags bit flags.
635   llvm::PointerIntPair<ObjCMethodDecl *, 2, unsigned> SetterAndMethodRefFlags;
636 
637   // FIXME: Maybe we should store the property identifier here,
638   // because it's not rederivable from the other data when there's an
639   // implicit property with no getter (because the 'foo' -> 'setFoo:'
640   // transformation is lossy on the first character).
641 
642   SourceLocation IdLoc;
643 
644   /// When the receiver in property access is 'super', this is
645   /// the location of the 'super' keyword.  When it's an interface,
646   /// this is that interface.
647   SourceLocation ReceiverLoc;
648   llvm::PointerUnion<Stmt *, const Type *, ObjCInterfaceDecl *> Receiver;
649 
650 public:
ObjCPropertyRefExpr(ObjCPropertyDecl * PD,QualType t,ExprValueKind VK,ExprObjectKind OK,SourceLocation l,Expr * base)651   ObjCPropertyRefExpr(ObjCPropertyDecl *PD, QualType t, ExprValueKind VK,
652                       ExprObjectKind OK, SourceLocation l, Expr *base)
653       : Expr(ObjCPropertyRefExprClass, t, VK, OK), PropertyOrGetter(PD, false),
654         IdLoc(l), Receiver(base) {
655     assert(t->isSpecificPlaceholderType(BuiltinType::PseudoObject));
656     setDependence(computeDependence(this));
657   }
658 
ObjCPropertyRefExpr(ObjCPropertyDecl * PD,QualType t,ExprValueKind VK,ExprObjectKind OK,SourceLocation l,SourceLocation sl,QualType st)659   ObjCPropertyRefExpr(ObjCPropertyDecl *PD, QualType t, ExprValueKind VK,
660                       ExprObjectKind OK, SourceLocation l, SourceLocation sl,
661                       QualType st)
662       : Expr(ObjCPropertyRefExprClass, t, VK, OK), PropertyOrGetter(PD, false),
663         IdLoc(l), ReceiverLoc(sl), Receiver(st.getTypePtr()) {
664     assert(t->isSpecificPlaceholderType(BuiltinType::PseudoObject));
665     setDependence(computeDependence(this));
666   }
667 
ObjCPropertyRefExpr(ObjCMethodDecl * Getter,ObjCMethodDecl * Setter,QualType T,ExprValueKind VK,ExprObjectKind OK,SourceLocation IdLoc,Expr * Base)668   ObjCPropertyRefExpr(ObjCMethodDecl *Getter, ObjCMethodDecl *Setter,
669                       QualType T, ExprValueKind VK, ExprObjectKind OK,
670                       SourceLocation IdLoc, Expr *Base)
671       : Expr(ObjCPropertyRefExprClass, T, VK, OK),
672         PropertyOrGetter(Getter, true), SetterAndMethodRefFlags(Setter, 0),
673         IdLoc(IdLoc), Receiver(Base) {
674     assert(T->isSpecificPlaceholderType(BuiltinType::PseudoObject));
675     setDependence(computeDependence(this));
676   }
677 
ObjCPropertyRefExpr(ObjCMethodDecl * Getter,ObjCMethodDecl * Setter,QualType T,ExprValueKind VK,ExprObjectKind OK,SourceLocation IdLoc,SourceLocation SuperLoc,QualType SuperTy)678   ObjCPropertyRefExpr(ObjCMethodDecl *Getter, ObjCMethodDecl *Setter,
679                       QualType T, ExprValueKind VK, ExprObjectKind OK,
680                       SourceLocation IdLoc, SourceLocation SuperLoc,
681                       QualType SuperTy)
682       : Expr(ObjCPropertyRefExprClass, T, VK, OK),
683         PropertyOrGetter(Getter, true), SetterAndMethodRefFlags(Setter, 0),
684         IdLoc(IdLoc), ReceiverLoc(SuperLoc), Receiver(SuperTy.getTypePtr()) {
685     assert(T->isSpecificPlaceholderType(BuiltinType::PseudoObject));
686     setDependence(computeDependence(this));
687   }
688 
ObjCPropertyRefExpr(ObjCMethodDecl * Getter,ObjCMethodDecl * Setter,QualType T,ExprValueKind VK,ExprObjectKind OK,SourceLocation IdLoc,SourceLocation ReceiverLoc,ObjCInterfaceDecl * Receiver)689   ObjCPropertyRefExpr(ObjCMethodDecl *Getter, ObjCMethodDecl *Setter,
690                       QualType T, ExprValueKind VK, ExprObjectKind OK,
691                       SourceLocation IdLoc, SourceLocation ReceiverLoc,
692                       ObjCInterfaceDecl *Receiver)
693       : Expr(ObjCPropertyRefExprClass, T, VK, OK),
694         PropertyOrGetter(Getter, true), SetterAndMethodRefFlags(Setter, 0),
695         IdLoc(IdLoc), ReceiverLoc(ReceiverLoc), Receiver(Receiver) {
696     assert(T->isSpecificPlaceholderType(BuiltinType::PseudoObject));
697     setDependence(computeDependence(this));
698   }
699 
ObjCPropertyRefExpr(EmptyShell Empty)700   explicit ObjCPropertyRefExpr(EmptyShell Empty)
701       : Expr(ObjCPropertyRefExprClass, Empty) {}
702 
isImplicitProperty()703   bool isImplicitProperty() const { return PropertyOrGetter.getInt(); }
isExplicitProperty()704   bool isExplicitProperty() const { return !PropertyOrGetter.getInt(); }
705 
getExplicitProperty()706   ObjCPropertyDecl *getExplicitProperty() const {
707     assert(!isImplicitProperty());
708     return cast<ObjCPropertyDecl>(PropertyOrGetter.getPointer());
709   }
710 
getImplicitPropertyGetter()711   ObjCMethodDecl *getImplicitPropertyGetter() const {
712     assert(isImplicitProperty());
713     return cast_or_null<ObjCMethodDecl>(PropertyOrGetter.getPointer());
714   }
715 
getImplicitPropertySetter()716   ObjCMethodDecl *getImplicitPropertySetter() const {
717     assert(isImplicitProperty());
718     return SetterAndMethodRefFlags.getPointer();
719   }
720 
getGetterSelector()721   Selector getGetterSelector() const {
722     if (isImplicitProperty())
723       return getImplicitPropertyGetter()->getSelector();
724     return getExplicitProperty()->getGetterName();
725   }
726 
getSetterSelector()727   Selector getSetterSelector() const {
728     if (isImplicitProperty())
729       return getImplicitPropertySetter()->getSelector();
730     return getExplicitProperty()->getSetterName();
731   }
732 
733   /// True if the property reference will result in a message to the
734   /// getter.
735   /// This applies to both implicit and explicit property references.
isMessagingGetter()736   bool isMessagingGetter() const {
737     return SetterAndMethodRefFlags.getInt() & MethodRef_Getter;
738   }
739 
740   /// True if the property reference will result in a message to the
741   /// setter.
742   /// This applies to both implicit and explicit property references.
isMessagingSetter()743   bool isMessagingSetter() const {
744     return SetterAndMethodRefFlags.getInt() & MethodRef_Setter;
745   }
746 
747   void setIsMessagingGetter(bool val = true) {
748     setMethodRefFlag(MethodRef_Getter, val);
749   }
750 
751   void setIsMessagingSetter(bool val = true) {
752     setMethodRefFlag(MethodRef_Setter, val);
753   }
754 
getBase()755   const Expr *getBase() const {
756     return cast<Expr>(Receiver.get<Stmt*>());
757   }
getBase()758   Expr *getBase() {
759     return cast<Expr>(Receiver.get<Stmt*>());
760   }
761 
getLocation()762   SourceLocation getLocation() const { return IdLoc; }
763 
getReceiverLocation()764   SourceLocation getReceiverLocation() const { return ReceiverLoc; }
765 
getSuperReceiverType()766   QualType getSuperReceiverType() const {
767     return QualType(Receiver.get<const Type*>(), 0);
768   }
769 
getClassReceiver()770   ObjCInterfaceDecl *getClassReceiver() const {
771     return Receiver.get<ObjCInterfaceDecl*>();
772   }
773 
isObjectReceiver()774   bool isObjectReceiver() const { return Receiver.is<Stmt*>(); }
isSuperReceiver()775   bool isSuperReceiver() const { return Receiver.is<const Type*>(); }
isClassReceiver()776   bool isClassReceiver() const { return Receiver.is<ObjCInterfaceDecl*>(); }
777 
778   /// Determine the type of the base, regardless of the kind of receiver.
779   QualType getReceiverType(const ASTContext &ctx) const;
780 
getBeginLoc()781   SourceLocation getBeginLoc() const LLVM_READONLY {
782     return isObjectReceiver() ? getBase()->getBeginLoc()
783                               : getReceiverLocation();
784   }
785 
getEndLoc()786   SourceLocation getEndLoc() const LLVM_READONLY { return IdLoc; }
787 
788   // Iterators
children()789   child_range children() {
790     if (Receiver.is<Stmt*>()) {
791       Stmt **begin = reinterpret_cast<Stmt**>(&Receiver); // hack!
792       return child_range(begin, begin+1);
793     }
794     return child_range(child_iterator(), child_iterator());
795   }
796 
children()797   const_child_range children() const {
798     auto Children = const_cast<ObjCPropertyRefExpr *>(this)->children();
799     return const_child_range(Children.begin(), Children.end());
800   }
801 
classof(const Stmt * T)802   static bool classof(const Stmt *T) {
803     return T->getStmtClass() == ObjCPropertyRefExprClass;
804   }
805 
806 private:
807   friend class ASTStmtReader;
808   friend class ASTStmtWriter;
809 
setExplicitProperty(ObjCPropertyDecl * D,unsigned methRefFlags)810   void setExplicitProperty(ObjCPropertyDecl *D, unsigned methRefFlags) {
811     PropertyOrGetter.setPointer(D);
812     PropertyOrGetter.setInt(false);
813     SetterAndMethodRefFlags.setPointer(nullptr);
814     SetterAndMethodRefFlags.setInt(methRefFlags);
815   }
816 
setImplicitProperty(ObjCMethodDecl * Getter,ObjCMethodDecl * Setter,unsigned methRefFlags)817   void setImplicitProperty(ObjCMethodDecl *Getter, ObjCMethodDecl *Setter,
818                            unsigned methRefFlags) {
819     PropertyOrGetter.setPointer(Getter);
820     PropertyOrGetter.setInt(true);
821     SetterAndMethodRefFlags.setPointer(Setter);
822     SetterAndMethodRefFlags.setInt(methRefFlags);
823   }
824 
setBase(Expr * Base)825   void setBase(Expr *Base) { Receiver = Base; }
setSuperReceiver(QualType T)826   void setSuperReceiver(QualType T) { Receiver = T.getTypePtr(); }
setClassReceiver(ObjCInterfaceDecl * D)827   void setClassReceiver(ObjCInterfaceDecl *D) { Receiver = D; }
828 
setLocation(SourceLocation L)829   void setLocation(SourceLocation L) { IdLoc = L; }
setReceiverLocation(SourceLocation Loc)830   void setReceiverLocation(SourceLocation Loc) { ReceiverLoc = Loc; }
831 
setMethodRefFlag(MethodRefFlags flag,bool val)832   void setMethodRefFlag(MethodRefFlags flag, bool val) {
833     unsigned f = SetterAndMethodRefFlags.getInt();
834     if (val)
835       f |= flag;
836     else
837       f &= ~flag;
838     SetterAndMethodRefFlags.setInt(f);
839   }
840 };
841 
842 /// ObjCSubscriptRefExpr - used for array and dictionary subscripting.
843 /// array[4] = array[3]; dictionary[key] = dictionary[alt_key];
844 class ObjCSubscriptRefExpr : public Expr {
845   // Location of ']' in an indexing expression.
846   SourceLocation RBracket;
847 
848   // array/dictionary base expression.
849   // for arrays, this is a numeric expression. For dictionaries, this is
850   // an objective-c object pointer expression.
851   enum { BASE, KEY, END_EXPR };
852   Stmt* SubExprs[END_EXPR];
853 
854   ObjCMethodDecl *GetAtIndexMethodDecl;
855 
856   // For immutable objects this is null. When ObjCSubscriptRefExpr is to read
857   // an indexed object this is null too.
858   ObjCMethodDecl *SetAtIndexMethodDecl;
859 
860 public:
ObjCSubscriptRefExpr(Expr * base,Expr * key,QualType T,ExprValueKind VK,ExprObjectKind OK,ObjCMethodDecl * getMethod,ObjCMethodDecl * setMethod,SourceLocation RB)861   ObjCSubscriptRefExpr(Expr *base, Expr *key, QualType T, ExprValueKind VK,
862                        ExprObjectKind OK, ObjCMethodDecl *getMethod,
863                        ObjCMethodDecl *setMethod, SourceLocation RB)
864       : Expr(ObjCSubscriptRefExprClass, T, VK, OK), RBracket(RB),
865         GetAtIndexMethodDecl(getMethod), SetAtIndexMethodDecl(setMethod) {
866     SubExprs[BASE] = base;
867     SubExprs[KEY] = key;
868     setDependence(computeDependence(this));
869   }
870 
ObjCSubscriptRefExpr(EmptyShell Empty)871   explicit ObjCSubscriptRefExpr(EmptyShell Empty)
872       : Expr(ObjCSubscriptRefExprClass, Empty) {}
873 
getRBracket()874   SourceLocation getRBracket() const { return RBracket; }
setRBracket(SourceLocation RB)875   void setRBracket(SourceLocation RB) { RBracket = RB; }
876 
getBeginLoc()877   SourceLocation getBeginLoc() const LLVM_READONLY {
878     return SubExprs[BASE]->getBeginLoc();
879   }
880 
getEndLoc()881   SourceLocation getEndLoc() const LLVM_READONLY { return RBracket; }
882 
getBaseExpr()883   Expr *getBaseExpr() const { return cast<Expr>(SubExprs[BASE]); }
setBaseExpr(Stmt * S)884   void setBaseExpr(Stmt *S) { SubExprs[BASE] = S; }
885 
getKeyExpr()886   Expr *getKeyExpr() const { return cast<Expr>(SubExprs[KEY]); }
setKeyExpr(Stmt * S)887   void setKeyExpr(Stmt *S) { SubExprs[KEY] = S; }
888 
getAtIndexMethodDecl()889   ObjCMethodDecl *getAtIndexMethodDecl() const {
890     return GetAtIndexMethodDecl;
891   }
892 
setAtIndexMethodDecl()893   ObjCMethodDecl *setAtIndexMethodDecl() const {
894     return SetAtIndexMethodDecl;
895   }
896 
isArraySubscriptRefExpr()897   bool isArraySubscriptRefExpr() const {
898     return getKeyExpr()->getType()->isIntegralOrEnumerationType();
899   }
900 
children()901   child_range children() {
902     return child_range(SubExprs, SubExprs+END_EXPR);
903   }
904 
children()905   const_child_range children() const {
906     return const_child_range(SubExprs, SubExprs + END_EXPR);
907   }
908 
classof(const Stmt * T)909   static bool classof(const Stmt *T) {
910     return T->getStmtClass() == ObjCSubscriptRefExprClass;
911   }
912 
913 private:
914   friend class ASTStmtReader;
915 };
916 
917 /// An expression that sends a message to the given Objective-C
918 /// object or class.
919 ///
920 /// The following contains two message send expressions:
921 ///
922 /// \code
923 ///   [[NSString alloc] initWithString:@"Hello"]
924 /// \endcode
925 ///
926 /// The innermost message send invokes the "alloc" class method on the
927 /// NSString class, while the outermost message send invokes the
928 /// "initWithString" instance method on the object returned from
929 /// NSString's "alloc". In all, an Objective-C message send can take
930 /// on four different (although related) forms:
931 ///
932 ///   1. Send to an object instance.
933 ///   2. Send to a class.
934 ///   3. Send to the superclass instance of the current class.
935 ///   4. Send to the superclass of the current class.
936 ///
937 /// All four kinds of message sends are modeled by the ObjCMessageExpr
938 /// class, and can be distinguished via \c getReceiverKind(). Example:
939 ///
940 /// The "void *" trailing objects are actually ONE void * (the
941 /// receiver pointer), and NumArgs Expr *. But due to the
942 /// implementation of children(), these must be together contiguously.
943 class ObjCMessageExpr final
944     : public Expr,
945       private llvm::TrailingObjects<ObjCMessageExpr, void *, SourceLocation> {
946 public:
947   /// The kind of receiver this message is sending to.
948   enum ReceiverKind {
949     /// The receiver is a class.
950     Class = 0,
951 
952     /// The receiver is an object instance.
953     Instance,
954 
955     /// The receiver is a superclass.
956     SuperClass,
957 
958     /// The receiver is the instance of the superclass object.
959     SuperInstance
960   };
961 
962 private:
963   /// Stores either the selector that this message is sending
964   /// to (when \c HasMethod is zero) or an \c ObjCMethodDecl pointer
965   /// referring to the method that we type-checked against.
966   uintptr_t SelectorOrMethod = 0;
967 
968   enum { NumArgsBitWidth = 16 };
969 
970   /// The number of arguments in the message send, not
971   /// including the receiver.
972   unsigned NumArgs : NumArgsBitWidth;
973 
974   /// The kind of message send this is, which is one of the
975   /// ReceiverKind values.
976   ///
977   /// We pad this out to a byte to avoid excessive masking and shifting.
978   LLVM_PREFERRED_TYPE(ReceiverKind)
979   unsigned Kind : 8;
980 
981   /// Whether we have an actual method prototype in \c
982   /// SelectorOrMethod.
983   ///
984   /// When non-zero, we have a method declaration; otherwise, we just
985   /// have a selector.
986   LLVM_PREFERRED_TYPE(bool)
987   unsigned HasMethod : 1;
988 
989   /// Whether this message send is a "delegate init call",
990   /// i.e. a call of an init method on self from within an init method.
991   LLVM_PREFERRED_TYPE(bool)
992   unsigned IsDelegateInitCall : 1;
993 
994   /// Whether this message send was implicitly generated by
995   /// the implementation rather than explicitly written by the user.
996   LLVM_PREFERRED_TYPE(bool)
997   unsigned IsImplicit : 1;
998 
999   /// Whether the locations of the selector identifiers are in a
1000   /// "standard" position, a enum SelectorLocationsKind.
1001   LLVM_PREFERRED_TYPE(SelectorLocationsKind)
1002   unsigned SelLocsKind : 2;
1003 
1004   /// When the message expression is a send to 'super', this is
1005   /// the location of the 'super' keyword.
1006   SourceLocation SuperLoc;
1007 
1008   /// The source locations of the open and close square
1009   /// brackets ('[' and ']', respectively).
1010   SourceLocation LBracLoc, RBracLoc;
1011 
ObjCMessageExpr(EmptyShell Empty,unsigned NumArgs)1012   ObjCMessageExpr(EmptyShell Empty, unsigned NumArgs)
1013       : Expr(ObjCMessageExprClass, Empty), Kind(0), HasMethod(false),
1014         IsDelegateInitCall(false), IsImplicit(false), SelLocsKind(0) {
1015     setNumArgs(NumArgs);
1016   }
1017 
1018   ObjCMessageExpr(QualType T, ExprValueKind VK,
1019                   SourceLocation LBracLoc,
1020                   SourceLocation SuperLoc,
1021                   bool IsInstanceSuper,
1022                   QualType SuperType,
1023                   Selector Sel,
1024                   ArrayRef<SourceLocation> SelLocs,
1025                   SelectorLocationsKind SelLocsK,
1026                   ObjCMethodDecl *Method,
1027                   ArrayRef<Expr *> Args,
1028                   SourceLocation RBracLoc,
1029                   bool isImplicit);
1030   ObjCMessageExpr(QualType T, ExprValueKind VK,
1031                   SourceLocation LBracLoc,
1032                   TypeSourceInfo *Receiver,
1033                   Selector Sel,
1034                   ArrayRef<SourceLocation> SelLocs,
1035                   SelectorLocationsKind SelLocsK,
1036                   ObjCMethodDecl *Method,
1037                   ArrayRef<Expr *> Args,
1038                   SourceLocation RBracLoc,
1039                   bool isImplicit);
1040   ObjCMessageExpr(QualType T, ExprValueKind VK,
1041                   SourceLocation LBracLoc,
1042                   Expr *Receiver,
1043                   Selector Sel,
1044                   ArrayRef<SourceLocation> SelLocs,
1045                   SelectorLocationsKind SelLocsK,
1046                   ObjCMethodDecl *Method,
1047                   ArrayRef<Expr *> Args,
1048                   SourceLocation RBracLoc,
1049                   bool isImplicit);
1050 
numTrailingObjects(OverloadToken<void * >)1051   size_t numTrailingObjects(OverloadToken<void *>) const { return NumArgs + 1; }
1052 
setNumArgs(unsigned Num)1053   void setNumArgs(unsigned Num) {
1054     assert((Num >> NumArgsBitWidth) == 0 && "Num of args is out of range!");
1055     NumArgs = Num;
1056   }
1057 
1058   void initArgsAndSelLocs(ArrayRef<Expr *> Args,
1059                           ArrayRef<SourceLocation> SelLocs,
1060                           SelectorLocationsKind SelLocsK);
1061 
1062   /// Retrieve the pointer value of the message receiver.
getReceiverPointer()1063   void *getReceiverPointer() const { return *getTrailingObjects<void *>(); }
1064 
1065   /// Set the pointer value of the message receiver.
setReceiverPointer(void * Value)1066   void setReceiverPointer(void *Value) {
1067     *getTrailingObjects<void *>() = Value;
1068   }
1069 
getSelLocsKind()1070   SelectorLocationsKind getSelLocsKind() const {
1071     return (SelectorLocationsKind)SelLocsKind;
1072   }
1073 
hasStandardSelLocs()1074   bool hasStandardSelLocs() const {
1075     return getSelLocsKind() != SelLoc_NonStandard;
1076   }
1077 
1078   /// Get a pointer to the stored selector identifiers locations array.
1079   /// No locations will be stored if HasStandardSelLocs is true.
getStoredSelLocs()1080   SourceLocation *getStoredSelLocs() {
1081     return getTrailingObjects<SourceLocation>();
1082   }
getStoredSelLocs()1083   const SourceLocation *getStoredSelLocs() const {
1084     return getTrailingObjects<SourceLocation>();
1085   }
1086 
1087   /// Get the number of stored selector identifiers locations.
1088   /// No locations will be stored if HasStandardSelLocs is true.
getNumStoredSelLocs()1089   unsigned getNumStoredSelLocs() const {
1090     if (hasStandardSelLocs())
1091       return 0;
1092     return getNumSelectorLocs();
1093   }
1094 
1095   static ObjCMessageExpr *alloc(const ASTContext &C,
1096                                 ArrayRef<Expr *> Args,
1097                                 SourceLocation RBraceLoc,
1098                                 ArrayRef<SourceLocation> SelLocs,
1099                                 Selector Sel,
1100                                 SelectorLocationsKind &SelLocsK);
1101   static ObjCMessageExpr *alloc(const ASTContext &C,
1102                                 unsigned NumArgs,
1103                                 unsigned NumStoredSelLocs);
1104 
1105 public:
1106   friend class ASTStmtReader;
1107   friend class ASTStmtWriter;
1108   friend TrailingObjects;
1109 
1110   /// Create a message send to super.
1111   ///
1112   /// \param Context The ASTContext in which this expression will be created.
1113   ///
1114   /// \param T The result type of this message.
1115   ///
1116   /// \param VK The value kind of this message.  A message returning
1117   /// a l-value or r-value reference will be an l-value or x-value,
1118   /// respectively.
1119   ///
1120   /// \param LBracLoc The location of the open square bracket '['.
1121   ///
1122   /// \param SuperLoc The location of the "super" keyword.
1123   ///
1124   /// \param IsInstanceSuper Whether this is an instance "super"
1125   /// message (otherwise, it's a class "super" message).
1126   ///
1127   /// \param Sel The selector used to determine which method gets called.
1128   ///
1129   /// \param Method The Objective-C method against which this message
1130   /// send was type-checked. May be nullptr.
1131   ///
1132   /// \param Args The message send arguments.
1133   ///
1134   /// \param RBracLoc The location of the closing square bracket ']'.
1135   static ObjCMessageExpr *Create(const ASTContext &Context, QualType T,
1136                                  ExprValueKind VK,
1137                                  SourceLocation LBracLoc,
1138                                  SourceLocation SuperLoc,
1139                                  bool IsInstanceSuper,
1140                                  QualType SuperType,
1141                                  Selector Sel,
1142                                  ArrayRef<SourceLocation> SelLocs,
1143                                  ObjCMethodDecl *Method,
1144                                  ArrayRef<Expr *> Args,
1145                                  SourceLocation RBracLoc,
1146                                  bool isImplicit);
1147 
1148   /// Create a class message send.
1149   ///
1150   /// \param Context The ASTContext in which this expression will be created.
1151   ///
1152   /// \param T The result type of this message.
1153   ///
1154   /// \param VK The value kind of this message.  A message returning
1155   /// a l-value or r-value reference will be an l-value or x-value,
1156   /// respectively.
1157   ///
1158   /// \param LBracLoc The location of the open square bracket '['.
1159   ///
1160   /// \param Receiver The type of the receiver, including
1161   /// source-location information.
1162   ///
1163   /// \param Sel The selector used to determine which method gets called.
1164   ///
1165   /// \param Method The Objective-C method against which this message
1166   /// send was type-checked. May be nullptr.
1167   ///
1168   /// \param Args The message send arguments.
1169   ///
1170   /// \param RBracLoc The location of the closing square bracket ']'.
1171   static ObjCMessageExpr *Create(const ASTContext &Context, QualType T,
1172                                  ExprValueKind VK,
1173                                  SourceLocation LBracLoc,
1174                                  TypeSourceInfo *Receiver,
1175                                  Selector Sel,
1176                                  ArrayRef<SourceLocation> SelLocs,
1177                                  ObjCMethodDecl *Method,
1178                                  ArrayRef<Expr *> Args,
1179                                  SourceLocation RBracLoc,
1180                                  bool isImplicit);
1181 
1182   /// Create an instance message send.
1183   ///
1184   /// \param Context The ASTContext in which this expression will be created.
1185   ///
1186   /// \param T The result type of this message.
1187   ///
1188   /// \param VK The value kind of this message.  A message returning
1189   /// a l-value or r-value reference will be an l-value or x-value,
1190   /// respectively.
1191   ///
1192   /// \param LBracLoc The location of the open square bracket '['.
1193   ///
1194   /// \param Receiver The expression used to produce the object that
1195   /// will receive this message.
1196   ///
1197   /// \param Sel The selector used to determine which method gets called.
1198   ///
1199   /// \param Method The Objective-C method against which this message
1200   /// send was type-checked. May be nullptr.
1201   ///
1202   /// \param Args The message send arguments.
1203   ///
1204   /// \param RBracLoc The location of the closing square bracket ']'.
1205   static ObjCMessageExpr *Create(const ASTContext &Context, QualType T,
1206                                  ExprValueKind VK,
1207                                  SourceLocation LBracLoc,
1208                                  Expr *Receiver,
1209                                  Selector Sel,
1210                                  ArrayRef<SourceLocation> SeLocs,
1211                                  ObjCMethodDecl *Method,
1212                                  ArrayRef<Expr *> Args,
1213                                  SourceLocation RBracLoc,
1214                                  bool isImplicit);
1215 
1216   /// Create an empty Objective-C message expression, to be
1217   /// filled in by subsequent calls.
1218   ///
1219   /// \param Context The context in which the message send will be created.
1220   ///
1221   /// \param NumArgs The number of message arguments, not including
1222   /// the receiver.
1223   static ObjCMessageExpr *CreateEmpty(const ASTContext &Context,
1224                                       unsigned NumArgs,
1225                                       unsigned NumStoredSelLocs);
1226 
1227   /// Indicates whether the message send was implicitly
1228   /// generated by the implementation. If false, it was written explicitly
1229   /// in the source code.
isImplicit()1230   bool isImplicit() const { return IsImplicit; }
1231 
1232   /// Determine the kind of receiver that this message is being
1233   /// sent to.
getReceiverKind()1234   ReceiverKind getReceiverKind() const { return (ReceiverKind)Kind; }
1235 
1236   /// \return the return type of the message being sent.
1237   /// This is not always the type of the message expression itself because
1238   /// of references (the expression would not have a reference type).
1239   /// It is also not always the declared return type of the method because
1240   /// of `instancetype` (in that case it's an expression type).
1241   QualType getCallReturnType(ASTContext &Ctx) const;
1242 
1243   /// Source range of the receiver.
1244   SourceRange getReceiverRange() const;
1245 
1246   /// Determine whether this is an instance message to either a
1247   /// computed object or to super.
isInstanceMessage()1248   bool isInstanceMessage() const {
1249     return getReceiverKind() == Instance || getReceiverKind() == SuperInstance;
1250   }
1251 
1252   /// Determine whether this is an class message to either a
1253   /// specified class or to super.
isClassMessage()1254   bool isClassMessage() const {
1255     return getReceiverKind() == Class || getReceiverKind() == SuperClass;
1256   }
1257 
1258   /// Returns the object expression (receiver) for an instance message,
1259   /// or null for a message that is not an instance message.
getInstanceReceiver()1260   Expr *getInstanceReceiver() {
1261     if (getReceiverKind() == Instance)
1262       return static_cast<Expr *>(getReceiverPointer());
1263 
1264     return nullptr;
1265   }
getInstanceReceiver()1266   const Expr *getInstanceReceiver() const {
1267     return const_cast<ObjCMessageExpr*>(this)->getInstanceReceiver();
1268   }
1269 
1270   /// Turn this message send into an instance message that
1271   /// computes the receiver object with the given expression.
setInstanceReceiver(Expr * rec)1272   void setInstanceReceiver(Expr *rec) {
1273     Kind = Instance;
1274     setReceiverPointer(rec);
1275   }
1276 
1277   /// Returns the type of a class message send, or NULL if the
1278   /// message is not a class message.
getClassReceiver()1279   QualType getClassReceiver() const {
1280     if (TypeSourceInfo *TSInfo = getClassReceiverTypeInfo())
1281       return TSInfo->getType();
1282 
1283     return {};
1284   }
1285 
1286   /// Returns a type-source information of a class message
1287   /// send, or nullptr if the message is not a class message.
getClassReceiverTypeInfo()1288   TypeSourceInfo *getClassReceiverTypeInfo() const {
1289     if (getReceiverKind() == Class)
1290       return reinterpret_cast<TypeSourceInfo *>(getReceiverPointer());
1291     return nullptr;
1292   }
1293 
setClassReceiver(TypeSourceInfo * TSInfo)1294   void setClassReceiver(TypeSourceInfo *TSInfo) {
1295     Kind = Class;
1296     setReceiverPointer(TSInfo);
1297   }
1298 
1299   /// Retrieve the location of the 'super' keyword for a class
1300   /// or instance message to 'super', otherwise an invalid source location.
getSuperLoc()1301   SourceLocation getSuperLoc() const {
1302     if (getReceiverKind() == SuperInstance || getReceiverKind() == SuperClass)
1303       return SuperLoc;
1304 
1305     return SourceLocation();
1306   }
1307 
1308   /// Retrieve the receiver type to which this message is being directed.
1309   ///
1310   /// This routine cross-cuts all of the different kinds of message
1311   /// sends to determine what the underlying (statically known) type
1312   /// of the receiver will be; use \c getReceiverKind() to determine
1313   /// whether the message is a class or an instance method, whether it
1314   /// is a send to super or not, etc.
1315   ///
1316   /// \returns The type of the receiver.
1317   QualType getReceiverType() const;
1318 
1319   /// Retrieve the Objective-C interface to which this message
1320   /// is being directed, if known.
1321   ///
1322   /// This routine cross-cuts all of the different kinds of message
1323   /// sends to determine what the underlying (statically known) type
1324   /// of the receiver will be; use \c getReceiverKind() to determine
1325   /// whether the message is a class or an instance method, whether it
1326   /// is a send to super or not, etc.
1327   ///
1328   /// \returns The Objective-C interface if known, otherwise nullptr.
1329   ObjCInterfaceDecl *getReceiverInterface() const;
1330 
1331   /// Retrieve the type referred to by 'super'.
1332   ///
1333   /// The returned type will either be an ObjCInterfaceType (for an
1334   /// class message to super) or an ObjCObjectPointerType that refers
1335   /// to a class (for an instance message to super);
getSuperType()1336   QualType getSuperType() const {
1337     if (getReceiverKind() == SuperInstance || getReceiverKind() == SuperClass)
1338       return QualType::getFromOpaquePtr(getReceiverPointer());
1339 
1340     return QualType();
1341   }
1342 
setSuper(SourceLocation Loc,QualType T,bool IsInstanceSuper)1343   void setSuper(SourceLocation Loc, QualType T, bool IsInstanceSuper) {
1344     Kind = IsInstanceSuper? SuperInstance : SuperClass;
1345     SuperLoc = Loc;
1346     setReceiverPointer(T.getAsOpaquePtr());
1347   }
1348 
1349   Selector getSelector() const;
1350 
setSelector(Selector S)1351   void setSelector(Selector S) {
1352     HasMethod = false;
1353     SelectorOrMethod = reinterpret_cast<uintptr_t>(S.getAsOpaquePtr());
1354   }
1355 
getMethodDecl()1356   const ObjCMethodDecl *getMethodDecl() const {
1357     if (HasMethod)
1358       return reinterpret_cast<const ObjCMethodDecl *>(SelectorOrMethod);
1359 
1360     return nullptr;
1361   }
1362 
getMethodDecl()1363   ObjCMethodDecl *getMethodDecl() {
1364     if (HasMethod)
1365       return reinterpret_cast<ObjCMethodDecl *>(SelectorOrMethod);
1366 
1367     return nullptr;
1368   }
1369 
setMethodDecl(ObjCMethodDecl * MD)1370   void setMethodDecl(ObjCMethodDecl *MD) {
1371     HasMethod = true;
1372     SelectorOrMethod = reinterpret_cast<uintptr_t>(MD);
1373   }
1374 
getMethodFamily()1375   ObjCMethodFamily getMethodFamily() const {
1376     if (HasMethod) return getMethodDecl()->getMethodFamily();
1377     return getSelector().getMethodFamily();
1378   }
1379 
1380   /// Return the number of actual arguments in this message,
1381   /// not counting the receiver.
getNumArgs()1382   unsigned getNumArgs() const { return NumArgs; }
1383 
1384   /// Retrieve the arguments to this message, not including the
1385   /// receiver.
getArgs()1386   Expr **getArgs() {
1387     return reinterpret_cast<Expr **>(getTrailingObjects<void *>() + 1);
1388   }
getArgs()1389   const Expr * const *getArgs() const {
1390     return reinterpret_cast<const Expr *const *>(getTrailingObjects<void *>() +
1391                                                  1);
1392   }
1393 
1394   /// getArg - Return the specified argument.
getArg(unsigned Arg)1395   Expr *getArg(unsigned Arg) {
1396     assert(Arg < NumArgs && "Arg access out of range!");
1397     return getArgs()[Arg];
1398   }
getArg(unsigned Arg)1399   const Expr *getArg(unsigned Arg) const {
1400     assert(Arg < NumArgs && "Arg access out of range!");
1401     return getArgs()[Arg];
1402   }
1403 
1404   /// setArg - Set the specified argument.
setArg(unsigned Arg,Expr * ArgExpr)1405   void setArg(unsigned Arg, Expr *ArgExpr) {
1406     assert(Arg < NumArgs && "Arg access out of range!");
1407     getArgs()[Arg] = ArgExpr;
1408   }
1409 
1410   /// isDelegateInitCall - Answers whether this message send has been
1411   /// tagged as a "delegate init call", i.e. a call to a method in the
1412   /// -init family on self from within an -init method implementation.
isDelegateInitCall()1413   bool isDelegateInitCall() const { return IsDelegateInitCall; }
setDelegateInitCall(bool isDelegate)1414   void setDelegateInitCall(bool isDelegate) { IsDelegateInitCall = isDelegate; }
1415 
getLeftLoc()1416   SourceLocation getLeftLoc() const { return LBracLoc; }
getRightLoc()1417   SourceLocation getRightLoc() const { return RBracLoc; }
1418 
getSelectorStartLoc()1419   SourceLocation getSelectorStartLoc() const {
1420     if (isImplicit())
1421       return getBeginLoc();
1422     return getSelectorLoc(0);
1423   }
1424 
getSelectorLoc(unsigned Index)1425   SourceLocation getSelectorLoc(unsigned Index) const {
1426     assert(Index < getNumSelectorLocs() && "Index out of range!");
1427     if (hasStandardSelLocs())
1428       return getStandardSelectorLoc(
1429           Index, getSelector(), getSelLocsKind() == SelLoc_StandardWithSpace,
1430           llvm::ArrayRef(const_cast<Expr **>(getArgs()), getNumArgs()),
1431           RBracLoc);
1432     return getStoredSelLocs()[Index];
1433   }
1434 
1435   void getSelectorLocs(SmallVectorImpl<SourceLocation> &SelLocs) const;
1436 
getNumSelectorLocs()1437   unsigned getNumSelectorLocs() const {
1438     if (isImplicit())
1439       return 0;
1440     Selector Sel = getSelector();
1441     if (Sel.isUnarySelector())
1442       return 1;
1443     return Sel.getNumArgs();
1444   }
1445 
setSourceRange(SourceRange R)1446   void setSourceRange(SourceRange R) {
1447     LBracLoc = R.getBegin();
1448     RBracLoc = R.getEnd();
1449   }
1450 
getBeginLoc()1451   SourceLocation getBeginLoc() const LLVM_READONLY { return LBracLoc; }
getEndLoc()1452   SourceLocation getEndLoc() const LLVM_READONLY { return RBracLoc; }
1453 
1454   // Iterators
1455   child_range children();
1456 
1457   const_child_range children() const;
1458 
1459   using arg_iterator = ExprIterator;
1460   using const_arg_iterator = ConstExprIterator;
1461 
arguments()1462   llvm::iterator_range<arg_iterator> arguments() {
1463     return llvm::make_range(arg_begin(), arg_end());
1464   }
1465 
arguments()1466   llvm::iterator_range<const_arg_iterator> arguments() const {
1467     return llvm::make_range(arg_begin(), arg_end());
1468   }
1469 
arg_begin()1470   arg_iterator arg_begin() { return reinterpret_cast<Stmt **>(getArgs()); }
1471 
arg_end()1472   arg_iterator arg_end()   {
1473     return reinterpret_cast<Stmt **>(getArgs() + NumArgs);
1474   }
1475 
arg_begin()1476   const_arg_iterator arg_begin() const {
1477     return reinterpret_cast<Stmt const * const*>(getArgs());
1478   }
1479 
arg_end()1480   const_arg_iterator arg_end() const {
1481     return reinterpret_cast<Stmt const * const*>(getArgs() + NumArgs);
1482   }
1483 
classof(const Stmt * T)1484   static bool classof(const Stmt *T) {
1485     return T->getStmtClass() == ObjCMessageExprClass;
1486   }
1487 };
1488 
1489 /// ObjCIsaExpr - Represent X->isa and X.isa when X is an ObjC 'id' type.
1490 /// (similar in spirit to MemberExpr).
1491 class ObjCIsaExpr : public Expr {
1492   /// Base - the expression for the base object pointer.
1493   Stmt *Base;
1494 
1495   /// IsaMemberLoc - This is the location of the 'isa'.
1496   SourceLocation IsaMemberLoc;
1497 
1498   /// OpLoc - This is the location of '.' or '->'
1499   SourceLocation OpLoc;
1500 
1501   /// IsArrow - True if this is "X->F", false if this is "X.F".
1502   bool IsArrow;
1503 
1504 public:
ObjCIsaExpr(Expr * base,bool isarrow,SourceLocation l,SourceLocation oploc,QualType ty)1505   ObjCIsaExpr(Expr *base, bool isarrow, SourceLocation l, SourceLocation oploc,
1506               QualType ty)
1507       : Expr(ObjCIsaExprClass, ty, VK_LValue, OK_Ordinary), Base(base),
1508         IsaMemberLoc(l), OpLoc(oploc), IsArrow(isarrow) {
1509     setDependence(computeDependence(this));
1510   }
1511 
1512   /// Build an empty expression.
ObjCIsaExpr(EmptyShell Empty)1513   explicit ObjCIsaExpr(EmptyShell Empty) : Expr(ObjCIsaExprClass, Empty) {}
1514 
setBase(Expr * E)1515   void setBase(Expr *E) { Base = E; }
getBase()1516   Expr *getBase() const { return cast<Expr>(Base); }
1517 
isArrow()1518   bool isArrow() const { return IsArrow; }
setArrow(bool A)1519   void setArrow(bool A) { IsArrow = A; }
1520 
1521   /// getMemberLoc - Return the location of the "member", in X->F, it is the
1522   /// location of 'F'.
getIsaMemberLoc()1523   SourceLocation getIsaMemberLoc() const { return IsaMemberLoc; }
setIsaMemberLoc(SourceLocation L)1524   void setIsaMemberLoc(SourceLocation L) { IsaMemberLoc = L; }
1525 
getOpLoc()1526   SourceLocation getOpLoc() const { return OpLoc; }
setOpLoc(SourceLocation L)1527   void setOpLoc(SourceLocation L) { OpLoc = L; }
1528 
getBeginLoc()1529   SourceLocation getBeginLoc() const LLVM_READONLY {
1530     return getBase()->getBeginLoc();
1531   }
1532 
getBaseLocEnd()1533   SourceLocation getBaseLocEnd() const LLVM_READONLY {
1534     return getBase()->getEndLoc();
1535   }
1536 
getEndLoc()1537   SourceLocation getEndLoc() const LLVM_READONLY { return IsaMemberLoc; }
1538 
getExprLoc()1539   SourceLocation getExprLoc() const LLVM_READONLY { return IsaMemberLoc; }
1540 
1541   // Iterators
children()1542   child_range children() { return child_range(&Base, &Base+1); }
1543 
children()1544   const_child_range children() const {
1545     return const_child_range(&Base, &Base + 1);
1546   }
1547 
classof(const Stmt * T)1548   static bool classof(const Stmt *T) {
1549     return T->getStmtClass() == ObjCIsaExprClass;
1550   }
1551 };
1552 
1553 /// ObjCIndirectCopyRestoreExpr - Represents the passing of a function
1554 /// argument by indirect copy-restore in ARC.  This is used to support
1555 /// passing indirect arguments with the wrong lifetime, e.g. when
1556 /// passing the address of a __strong local variable to an 'out'
1557 /// parameter.  This expression kind is only valid in an "argument"
1558 /// position to some sort of call expression.
1559 ///
1560 /// The parameter must have type 'pointer to T', and the argument must
1561 /// have type 'pointer to U', where T and U agree except possibly in
1562 /// qualification.  If the argument value is null, then a null pointer
1563 /// is passed;  otherwise it points to an object A, and:
1564 /// 1. A temporary object B of type T is initialized, either by
1565 ///    zero-initialization (used when initializing an 'out' parameter)
1566 ///    or copy-initialization (used when initializing an 'inout'
1567 ///    parameter).
1568 /// 2. The address of the temporary is passed to the function.
1569 /// 3. If the call completes normally, A is move-assigned from B.
1570 /// 4. Finally, A is destroyed immediately.
1571 ///
1572 /// Currently 'T' must be a retainable object lifetime and must be
1573 /// __autoreleasing;  this qualifier is ignored when initializing
1574 /// the value.
1575 class ObjCIndirectCopyRestoreExpr : public Expr {
1576   friend class ASTReader;
1577   friend class ASTStmtReader;
1578 
1579   Stmt *Operand;
1580 
1581   // unsigned ObjCIndirectCopyRestoreBits.ShouldCopy : 1;
1582 
ObjCIndirectCopyRestoreExpr(EmptyShell Empty)1583   explicit ObjCIndirectCopyRestoreExpr(EmptyShell Empty)
1584       : Expr(ObjCIndirectCopyRestoreExprClass, Empty) {}
1585 
setShouldCopy(bool shouldCopy)1586   void setShouldCopy(bool shouldCopy) {
1587     ObjCIndirectCopyRestoreExprBits.ShouldCopy = shouldCopy;
1588   }
1589 
1590 public:
ObjCIndirectCopyRestoreExpr(Expr * operand,QualType type,bool shouldCopy)1591   ObjCIndirectCopyRestoreExpr(Expr *operand, QualType type, bool shouldCopy)
1592       : Expr(ObjCIndirectCopyRestoreExprClass, type, VK_LValue, OK_Ordinary),
1593         Operand(operand) {
1594     setShouldCopy(shouldCopy);
1595     setDependence(computeDependence(this));
1596   }
1597 
getSubExpr()1598   Expr *getSubExpr() { return cast<Expr>(Operand); }
getSubExpr()1599   const Expr *getSubExpr() const { return cast<Expr>(Operand); }
1600 
1601   /// shouldCopy - True if we should do the 'copy' part of the
1602   /// copy-restore.  If false, the temporary will be zero-initialized.
shouldCopy()1603   bool shouldCopy() const { return ObjCIndirectCopyRestoreExprBits.ShouldCopy; }
1604 
children()1605   child_range children() { return child_range(&Operand, &Operand+1); }
1606 
children()1607   const_child_range children() const {
1608     return const_child_range(&Operand, &Operand + 1);
1609   }
1610 
1611   // Source locations are determined by the subexpression.
getBeginLoc()1612   SourceLocation getBeginLoc() const LLVM_READONLY {
1613     return Operand->getBeginLoc();
1614   }
getEndLoc()1615   SourceLocation getEndLoc() const LLVM_READONLY {
1616     return Operand->getEndLoc();
1617   }
1618 
getExprLoc()1619   SourceLocation getExprLoc() const LLVM_READONLY {
1620     return getSubExpr()->getExprLoc();
1621   }
1622 
classof(const Stmt * s)1623   static bool classof(const Stmt *s) {
1624     return s->getStmtClass() == ObjCIndirectCopyRestoreExprClass;
1625   }
1626 };
1627 
1628 /// An Objective-C "bridged" cast expression, which casts between
1629 /// Objective-C pointers and C pointers, transferring ownership in the process.
1630 ///
1631 /// \code
1632 /// NSString *str = (__bridge_transfer NSString *)CFCreateString();
1633 /// \endcode
1634 class ObjCBridgedCastExpr final
1635     : public ExplicitCastExpr,
1636       private llvm::TrailingObjects<ObjCBridgedCastExpr, CXXBaseSpecifier *> {
1637   friend class ASTStmtReader;
1638   friend class ASTStmtWriter;
1639   friend class CastExpr;
1640   friend TrailingObjects;
1641 
1642   SourceLocation LParenLoc;
1643   SourceLocation BridgeKeywordLoc;
LLVM_PREFERRED_TYPE(ObjCBridgeCastKind)1644   LLVM_PREFERRED_TYPE(ObjCBridgeCastKind)
1645   unsigned Kind : 2;
1646 
1647 public:
1648   ObjCBridgedCastExpr(SourceLocation LParenLoc, ObjCBridgeCastKind Kind,
1649                       CastKind CK, SourceLocation BridgeKeywordLoc,
1650                       TypeSourceInfo *TSInfo, Expr *Operand)
1651       : ExplicitCastExpr(ObjCBridgedCastExprClass, TSInfo->getType(),
1652                          VK_PRValue, CK, Operand, 0, false, TSInfo),
1653         LParenLoc(LParenLoc), BridgeKeywordLoc(BridgeKeywordLoc), Kind(Kind) {}
1654 
1655   /// Construct an empty Objective-C bridged cast.
ObjCBridgedCastExpr(EmptyShell Shell)1656   explicit ObjCBridgedCastExpr(EmptyShell Shell)
1657       : ExplicitCastExpr(ObjCBridgedCastExprClass, Shell, 0, false) {}
1658 
getLParenLoc()1659   SourceLocation getLParenLoc() const { return LParenLoc; }
1660 
1661   /// Determine which kind of bridge is being performed via this cast.
getBridgeKind()1662   ObjCBridgeCastKind getBridgeKind() const {
1663     return static_cast<ObjCBridgeCastKind>(Kind);
1664   }
1665 
1666   /// Retrieve the kind of bridge being performed as a string.
1667   StringRef getBridgeKindName() const;
1668 
1669   /// The location of the bridge keyword.
getBridgeKeywordLoc()1670   SourceLocation getBridgeKeywordLoc() const { return BridgeKeywordLoc; }
1671 
getBeginLoc()1672   SourceLocation getBeginLoc() const LLVM_READONLY { return LParenLoc; }
1673 
getEndLoc()1674   SourceLocation getEndLoc() const LLVM_READONLY {
1675     return getSubExpr()->getEndLoc();
1676   }
1677 
classof(const Stmt * T)1678   static bool classof(const Stmt *T) {
1679     return T->getStmtClass() == ObjCBridgedCastExprClass;
1680   }
1681 };
1682 
1683 /// A runtime availability query.
1684 ///
1685 /// There are 2 ways to spell this node:
1686 /// \code
1687 ///   @available(macos 10.10, ios 8, *); // Objective-C
1688 ///   __builtin_available(macos 10.10, ios 8, *); // C, C++, and Objective-C
1689 /// \endcode
1690 ///
1691 /// Note that we only need to keep track of one \c VersionTuple here, which is
1692 /// the one that corresponds to the current deployment target. This is meant to
1693 /// be used in the condition of an \c if, but it is also usable as top level
1694 /// expressions.
1695 ///
1696 class ObjCAvailabilityCheckExpr : public Expr {
1697   friend class ASTStmtReader;
1698 
1699   VersionTuple VersionToCheck;
1700   SourceLocation AtLoc, RParen;
1701 
1702 public:
ObjCAvailabilityCheckExpr(VersionTuple VersionToCheck,SourceLocation AtLoc,SourceLocation RParen,QualType Ty)1703   ObjCAvailabilityCheckExpr(VersionTuple VersionToCheck, SourceLocation AtLoc,
1704                             SourceLocation RParen, QualType Ty)
1705       : Expr(ObjCAvailabilityCheckExprClass, Ty, VK_PRValue, OK_Ordinary),
1706         VersionToCheck(VersionToCheck), AtLoc(AtLoc), RParen(RParen) {
1707     setDependence(ExprDependence::None);
1708   }
1709 
ObjCAvailabilityCheckExpr(EmptyShell Shell)1710   explicit ObjCAvailabilityCheckExpr(EmptyShell Shell)
1711       : Expr(ObjCAvailabilityCheckExprClass, Shell) {}
1712 
getBeginLoc()1713   SourceLocation getBeginLoc() const { return AtLoc; }
getEndLoc()1714   SourceLocation getEndLoc() const { return RParen; }
getSourceRange()1715   SourceRange getSourceRange() const { return {AtLoc, RParen}; }
1716 
1717   /// This may be '*', in which case this should fold to true.
hasVersion()1718   bool hasVersion() const { return !VersionToCheck.empty(); }
getVersion()1719   VersionTuple getVersion() const { return VersionToCheck; }
1720 
children()1721   child_range children() {
1722     return child_range(child_iterator(), child_iterator());
1723   }
1724 
children()1725   const_child_range children() const {
1726     return const_child_range(const_child_iterator(), const_child_iterator());
1727   }
1728 
classof(const Stmt * T)1729   static bool classof(const Stmt *T) {
1730     return T->getStmtClass() == ObjCAvailabilityCheckExprClass;
1731   }
1732 };
1733 
1734 } // namespace clang
1735 
1736 #endif // LLVM_CLANG_AST_EXPROBJC_H
1737