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