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