ExprObjC.h revision aa165f8458b51c546bebff947343e1a36f3594cb
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/Basic/IdentifierTable.h" 20 21namespace clang { 22 class IdentifierInfo; 23 class ASTContext; 24 25/// ObjCStringLiteral, used for Objective-C string literals 26/// i.e. @"foo". 27class ObjCStringLiteral : public Expr { 28 Stmt *String; 29 SourceLocation AtLoc; 30public: 31 ObjCStringLiteral(StringLiteral *SL, QualType T, SourceLocation L) 32 : Expr(ObjCStringLiteralClass, T, VK_RValue, OK_Ordinary, false, false, 33 false), 34 String(SL), AtLoc(L) {} 35 explicit ObjCStringLiteral(EmptyShell Empty) 36 : Expr(ObjCStringLiteralClass, Empty) {} 37 38 StringLiteral *getString() { return cast<StringLiteral>(String); } 39 const StringLiteral *getString() const { return cast<StringLiteral>(String); } 40 void setString(StringLiteral *S) { String = S; } 41 42 SourceLocation getAtLoc() const { return AtLoc; } 43 void setAtLoc(SourceLocation L) { AtLoc = L; } 44 45 virtual SourceRange getSourceRange() const { 46 return SourceRange(AtLoc, String->getLocEnd()); 47 } 48 49 static bool classof(const Stmt *T) { 50 return T->getStmtClass() == ObjCStringLiteralClass; 51 } 52 static bool classof(const ObjCStringLiteral *) { return true; } 53 54 // Iterators 55 virtual child_iterator child_begin(); 56 virtual child_iterator child_end(); 57}; 58 59/// ObjCEncodeExpr, used for @encode in Objective-C. @encode has the same type 60/// and behavior as StringLiteral except that the string initializer is obtained 61/// from ASTContext with the encoding type as an argument. 62class ObjCEncodeExpr : public Expr { 63 TypeSourceInfo *EncodedType; 64 SourceLocation AtLoc, RParenLoc; 65public: 66 ObjCEncodeExpr(QualType T, TypeSourceInfo *EncodedType, 67 SourceLocation at, SourceLocation rp) 68 : Expr(ObjCEncodeExprClass, T, VK_LValue, OK_Ordinary, 69 EncodedType->getType()->isDependentType(), 70 EncodedType->getType()->isDependentType(), 71 EncodedType->getType()->containsUnexpandedParameterPack()), 72 EncodedType(EncodedType), AtLoc(at), RParenLoc(rp) {} 73 74 explicit ObjCEncodeExpr(EmptyShell Empty) : Expr(ObjCEncodeExprClass, Empty){} 75 76 77 SourceLocation getAtLoc() const { return AtLoc; } 78 void setAtLoc(SourceLocation L) { AtLoc = L; } 79 SourceLocation getRParenLoc() const { return RParenLoc; } 80 void setRParenLoc(SourceLocation L) { RParenLoc = L; } 81 82 QualType getEncodedType() const { return EncodedType->getType(); } 83 84 TypeSourceInfo *getEncodedTypeSourceInfo() const { return EncodedType; } 85 void setEncodedTypeSourceInfo(TypeSourceInfo *EncType) { 86 EncodedType = EncType; 87 } 88 89 virtual SourceRange getSourceRange() const { 90 return SourceRange(AtLoc, RParenLoc); 91 } 92 93 static bool classof(const Stmt *T) { 94 return T->getStmtClass() == ObjCEncodeExprClass; 95 } 96 static bool classof(const ObjCEncodeExpr *) { return true; } 97 98 // Iterators 99 virtual child_iterator child_begin(); 100 virtual child_iterator child_end(); 101}; 102 103/// ObjCSelectorExpr used for @selector in Objective-C. 104class ObjCSelectorExpr : public Expr { 105 Selector SelName; 106 SourceLocation AtLoc, RParenLoc; 107public: 108 ObjCSelectorExpr(QualType T, Selector selInfo, 109 SourceLocation at, SourceLocation rp) 110 : Expr(ObjCSelectorExprClass, T, VK_RValue, OK_Ordinary, false, false, 111 false), 112 SelName(selInfo), AtLoc(at), RParenLoc(rp){} 113 explicit ObjCSelectorExpr(EmptyShell Empty) 114 : Expr(ObjCSelectorExprClass, Empty) {} 115 116 Selector getSelector() const { return SelName; } 117 void setSelector(Selector S) { SelName = S; } 118 119 SourceLocation getAtLoc() const { return AtLoc; } 120 SourceLocation getRParenLoc() const { return RParenLoc; } 121 void setAtLoc(SourceLocation L) { AtLoc = L; } 122 void setRParenLoc(SourceLocation L) { RParenLoc = L; } 123 124 virtual SourceRange getSourceRange() const { 125 return SourceRange(AtLoc, RParenLoc); 126 } 127 128 /// getNumArgs - Return the number of actual arguments to this call. 129 unsigned getNumArgs() const { return SelName.getNumArgs(); } 130 131 static bool classof(const Stmt *T) { 132 return T->getStmtClass() == ObjCSelectorExprClass; 133 } 134 static bool classof(const ObjCSelectorExpr *) { return true; } 135 136 // Iterators 137 virtual child_iterator child_begin(); 138 virtual child_iterator child_end(); 139}; 140 141/// ObjCProtocolExpr used for protocol expression in Objective-C. This is used 142/// as: @protocol(foo), as in: 143/// obj conformsToProtocol:@protocol(foo)] 144/// The return type is "Protocol*". 145class ObjCProtocolExpr : public Expr { 146 ObjCProtocolDecl *TheProtocol; 147 SourceLocation AtLoc, RParenLoc; 148public: 149 ObjCProtocolExpr(QualType T, ObjCProtocolDecl *protocol, 150 SourceLocation at, SourceLocation rp) 151 : Expr(ObjCProtocolExprClass, T, VK_RValue, OK_Ordinary, false, false, 152 false), 153 TheProtocol(protocol), AtLoc(at), RParenLoc(rp) {} 154 explicit ObjCProtocolExpr(EmptyShell Empty) 155 : Expr(ObjCProtocolExprClass, Empty) {} 156 157 ObjCProtocolDecl *getProtocol() const { return TheProtocol; } 158 void setProtocol(ObjCProtocolDecl *P) { TheProtocol = P; } 159 160 SourceLocation getAtLoc() const { return AtLoc; } 161 SourceLocation getRParenLoc() const { return RParenLoc; } 162 void setAtLoc(SourceLocation L) { AtLoc = L; } 163 void setRParenLoc(SourceLocation L) { RParenLoc = L; } 164 165 virtual SourceRange getSourceRange() const { 166 return SourceRange(AtLoc, RParenLoc); 167 } 168 169 static bool classof(const Stmt *T) { 170 return T->getStmtClass() == ObjCProtocolExprClass; 171 } 172 static bool classof(const ObjCProtocolExpr *) { return true; } 173 174 // Iterators 175 virtual child_iterator child_begin(); 176 virtual child_iterator child_end(); 177}; 178 179/// ObjCIvarRefExpr - A reference to an ObjC instance variable. 180class ObjCIvarRefExpr : public Expr { 181 class ObjCIvarDecl *D; 182 SourceLocation Loc; 183 Stmt *Base; 184 bool IsArrow:1; // True if this is "X->F", false if this is "X.F". 185 bool IsFreeIvar:1; // True if ivar reference has no base (self assumed). 186 187public: 188 ObjCIvarRefExpr(ObjCIvarDecl *d, QualType t, 189 SourceLocation l, Expr *base, 190 bool arrow = false, bool freeIvar = false) : 191 Expr(ObjCIvarRefExprClass, t, VK_LValue, OK_Ordinary, 192 /*TypeDependent=*/false, base->isValueDependent(), 193 base->containsUnexpandedParameterPack()), 194 D(d), Loc(l), Base(base), IsArrow(arrow), IsFreeIvar(freeIvar) {} 195 196 explicit ObjCIvarRefExpr(EmptyShell Empty) 197 : Expr(ObjCIvarRefExprClass, Empty) {} 198 199 ObjCIvarDecl *getDecl() { return D; } 200 const ObjCIvarDecl *getDecl() const { return D; } 201 void setDecl(ObjCIvarDecl *d) { D = d; } 202 203 const Expr *getBase() const { return cast<Expr>(Base); } 204 Expr *getBase() { return cast<Expr>(Base); } 205 void setBase(Expr * base) { Base = base; } 206 207 bool isArrow() const { return IsArrow; } 208 bool isFreeIvar() const { return IsFreeIvar; } 209 void setIsArrow(bool A) { IsArrow = A; } 210 void setIsFreeIvar(bool A) { IsFreeIvar = A; } 211 212 SourceLocation getLocation() const { return Loc; } 213 void setLocation(SourceLocation L) { Loc = L; } 214 215 virtual SourceRange getSourceRange() const { 216 return isFreeIvar() ? SourceRange(Loc) 217 : SourceRange(getBase()->getLocStart(), Loc); 218 } 219 220 static bool classof(const Stmt *T) { 221 return T->getStmtClass() == ObjCIvarRefExprClass; 222 } 223 static bool classof(const ObjCIvarRefExpr *) { return true; } 224 225 // Iterators 226 virtual child_iterator child_begin(); 227 virtual child_iterator child_end(); 228}; 229 230/// ObjCPropertyRefExpr - A dot-syntax expression to access an ObjC 231/// property. 232/// 233class ObjCPropertyRefExpr : public Expr { 234private: 235 /// If the bool is true, this is an implicit property reference; the 236 /// pointer is an (optional) ObjCMethodDecl and Setter may be set. 237 /// if the bool is false, this is an explicit property reference; 238 /// the pointer is an ObjCPropertyDecl and Setter is always null. 239 llvm::PointerIntPair<NamedDecl*, 1, bool> PropertyOrGetter; 240 ObjCMethodDecl *Setter; 241 242 SourceLocation IdLoc; 243 244 /// \brief When the receiver in property access is 'super', this is 245 /// the location of the 'super' keyword. When it's an interface, 246 /// this is that interface. 247 SourceLocation ReceiverLoc; 248 llvm::PointerUnion3<Stmt*, Type*, ObjCInterfaceDecl*> Receiver; 249 250public: 251 ObjCPropertyRefExpr(ObjCPropertyDecl *PD, QualType t, 252 ExprValueKind VK, ExprObjectKind OK, 253 SourceLocation l, Expr *base) 254 : Expr(ObjCPropertyRefExprClass, t, VK, OK, 255 /*TypeDependent=*/false, base->isValueDependent(), 256 base->containsUnexpandedParameterPack()), 257 PropertyOrGetter(PD, false), Setter(0), 258 IdLoc(l), ReceiverLoc(), Receiver(base) { 259 } 260 261 ObjCPropertyRefExpr(ObjCPropertyDecl *PD, QualType t, 262 ExprValueKind VK, ExprObjectKind OK, 263 SourceLocation l, SourceLocation sl, QualType st) 264 : Expr(ObjCPropertyRefExprClass, t, VK, OK, 265 /*TypeDependent=*/false, false, 266 st->containsUnexpandedParameterPack()), 267 PropertyOrGetter(PD, false), Setter(0), 268 IdLoc(l), ReceiverLoc(sl), Receiver(st.getTypePtr()) { 269 } 270 271 ObjCPropertyRefExpr(ObjCMethodDecl *Getter, ObjCMethodDecl *Setter, 272 QualType T, ExprValueKind VK, ExprObjectKind OK, 273 SourceLocation IdLoc, Expr *Base) 274 : Expr(ObjCPropertyRefExprClass, T, VK, OK, false, 275 Base->isValueDependent(), 276 Base->containsUnexpandedParameterPack()), 277 PropertyOrGetter(Getter, true), Setter(Setter), 278 IdLoc(IdLoc), ReceiverLoc(), Receiver(Base) { 279 } 280 281 ObjCPropertyRefExpr(ObjCMethodDecl *Getter, ObjCMethodDecl *Setter, 282 QualType T, ExprValueKind VK, ExprObjectKind OK, 283 SourceLocation IdLoc, 284 SourceLocation SuperLoc, QualType SuperTy) 285 : Expr(ObjCPropertyRefExprClass, T, VK, OK, false, false, false), 286 PropertyOrGetter(Getter, true), Setter(Setter), 287 IdLoc(IdLoc), ReceiverLoc(SuperLoc), Receiver(SuperTy.getTypePtr()) { 288 } 289 290 ObjCPropertyRefExpr(ObjCMethodDecl *Getter, ObjCMethodDecl *Setter, 291 QualType T, ExprValueKind VK, ExprObjectKind OK, 292 SourceLocation IdLoc, 293 SourceLocation ReceiverLoc, ObjCInterfaceDecl *Receiver) 294 : Expr(ObjCPropertyRefExprClass, T, VK, OK, false, false, false), 295 PropertyOrGetter(Getter, true), Setter(Setter), 296 IdLoc(IdLoc), ReceiverLoc(ReceiverLoc), Receiver(Receiver) { 297 } 298 299 explicit ObjCPropertyRefExpr(EmptyShell Empty) 300 : Expr(ObjCPropertyRefExprClass, Empty) {} 301 302 bool isImplicitProperty() const { return PropertyOrGetter.getInt(); } 303 bool isExplicitProperty() const { return !PropertyOrGetter.getInt(); } 304 305 ObjCPropertyDecl *getExplicitProperty() const { 306 assert(!isImplicitProperty()); 307 return cast<ObjCPropertyDecl>(PropertyOrGetter.getPointer()); 308 } 309 310 ObjCMethodDecl *getImplicitPropertyGetter() const { 311 assert(isImplicitProperty()); 312 return cast_or_null<ObjCMethodDecl>(PropertyOrGetter.getPointer()); 313 } 314 315 ObjCMethodDecl *getImplicitPropertySetter() const { 316 assert(isImplicitProperty()); 317 return Setter; 318 } 319 320 Selector getGetterSelector() const { 321 if (isImplicitProperty()) 322 return getImplicitPropertyGetter()->getSelector(); 323 return getExplicitProperty()->getGetterName(); 324 } 325 326 Selector getSetterSelector() const { 327 if (isImplicitProperty()) 328 return getImplicitPropertySetter()->getSelector(); 329 return getExplicitProperty()->getSetterName(); 330 } 331 332 const Expr *getBase() const { 333 return cast<Expr>(Receiver.get<Stmt*>()); 334 } 335 Expr *getBase() { 336 return cast<Expr>(Receiver.get<Stmt*>()); 337 } 338 339 SourceLocation getLocation() const { return IdLoc; } 340 341 SourceLocation getReceiverLocation() const { return ReceiverLoc; } 342 QualType getSuperReceiverType() const { 343 return QualType(Receiver.get<Type*>(), 0); 344 } 345 ObjCInterfaceDecl *getClassReceiver() const { 346 return Receiver.get<ObjCInterfaceDecl*>(); 347 } 348 bool isObjectReceiver() const { return Receiver.is<Stmt*>(); } 349 bool isSuperReceiver() const { return Receiver.is<Type*>(); } 350 bool isClassReceiver() const { return Receiver.is<ObjCInterfaceDecl*>(); } 351 352 virtual SourceRange getSourceRange() const { 353 return SourceRange((isObjectReceiver() ? getBase()->getLocStart() 354 : getReceiverLocation()), 355 IdLoc); 356 } 357 358 static bool classof(const Stmt *T) { 359 return T->getStmtClass() == ObjCPropertyRefExprClass; 360 } 361 static bool classof(const ObjCPropertyRefExpr *) { return true; } 362 363 // Iterators 364 virtual child_iterator child_begin(); 365 virtual child_iterator child_end(); 366private: 367 friend class ASTStmtReader; 368 void setExplicitProperty(ObjCPropertyDecl *D) { 369 PropertyOrGetter.setPointer(D); 370 PropertyOrGetter.setInt(false); 371 Setter = 0; 372 } 373 void setImplicitProperty(ObjCMethodDecl *Getter, ObjCMethodDecl *Setter) { 374 PropertyOrGetter.setPointer(Getter); 375 PropertyOrGetter.setInt(true); 376 this->Setter = Setter; 377 } 378 void setBase(Expr *Base) { Receiver = Base; } 379 void setSuperReceiver(QualType T) { Receiver = T.getTypePtr(); } 380 void setClassReceiver(ObjCInterfaceDecl *D) { Receiver = D; } 381 382 void setLocation(SourceLocation L) { IdLoc = L; } 383 void setReceiverLocation(SourceLocation Loc) { ReceiverLoc = Loc; } 384}; 385 386/// \brief An expression that sends a message to the given Objective-C 387/// object or class. 388/// 389/// The following contains two message send expressions: 390/// 391/// \code 392/// [[NSString alloc] initWithString:@"Hello"] 393/// \endcode 394/// 395/// The innermost message send invokes the "alloc" class method on the 396/// NSString class, while the outermost message send invokes the 397/// "initWithString" instance method on the object returned from 398/// NSString's "alloc". In all, an Objective-C message send can take 399/// on four different (although related) forms: 400/// 401/// 1. Send to an object instance. 402/// 2. Send to a class. 403/// 3. Send to the superclass instance of the current class. 404/// 4. Send to the superclass of the current class. 405/// 406/// All four kinds of message sends are modeled by the ObjCMessageExpr 407/// class, and can be distinguished via \c getReceiverKind(). Example: 408/// 409class ObjCMessageExpr : public Expr { 410 /// \brief The number of arguments in the message send, not 411 /// including the receiver. 412 unsigned NumArgs : 16; 413 414 /// \brief The kind of message send this is, which is one of the 415 /// ReceiverKind values. 416 /// 417 /// We pad this out to a byte to avoid excessive masking and shifting. 418 unsigned Kind : 8; 419 420 /// \brief Whether we have an actual method prototype in \c 421 /// SelectorOrMethod. 422 /// 423 /// When non-zero, we have a method declaration; otherwise, we just 424 /// have a selector. 425 unsigned HasMethod : 8; 426 427 /// \brief When the message expression is a send to 'super', this is 428 /// the location of the 'super' keyword. 429 SourceLocation SuperLoc; 430 431 /// \brief Stores either the selector that this message is sending 432 /// to (when \c HasMethod is zero) or an \c ObjCMethodDecl pointer 433 /// referring to the method that we type-checked against. 434 uintptr_t SelectorOrMethod; 435 436 /// \brief Location of the selector. 437 SourceLocation SelectorLoc; 438 439 /// \brief The source locations of the open and close square 440 /// brackets ('[' and ']', respectively). 441 SourceLocation LBracLoc, RBracLoc; 442 443 ObjCMessageExpr(EmptyShell Empty, unsigned NumArgs) 444 : Expr(ObjCMessageExprClass, Empty), NumArgs(NumArgs), Kind(0), 445 HasMethod(0), SelectorOrMethod(0) { } 446 447 ObjCMessageExpr(QualType T, ExprValueKind VK, 448 SourceLocation LBracLoc, 449 SourceLocation SuperLoc, 450 bool IsInstanceSuper, 451 QualType SuperType, 452 Selector Sel, 453 SourceLocation SelLoc, 454 ObjCMethodDecl *Method, 455 Expr **Args, unsigned NumArgs, 456 SourceLocation RBracLoc); 457 ObjCMessageExpr(QualType T, ExprValueKind VK, 458 SourceLocation LBracLoc, 459 TypeSourceInfo *Receiver, 460 Selector Sel, 461 SourceLocation SelLoc, 462 ObjCMethodDecl *Method, 463 Expr **Args, unsigned NumArgs, 464 SourceLocation RBracLoc); 465 ObjCMessageExpr(QualType T, ExprValueKind VK, 466 SourceLocation LBracLoc, 467 Expr *Receiver, 468 Selector Sel, 469 SourceLocation SelLoc, 470 ObjCMethodDecl *Method, 471 Expr **Args, unsigned NumArgs, 472 SourceLocation RBracLoc); 473 474 /// \brief Retrieve the pointer value of the message receiver. 475 void *getReceiverPointer() const { 476 return *const_cast<void **>( 477 reinterpret_cast<const void * const*>(this + 1)); 478 } 479 480 /// \brief Set the pointer value of the message receiver. 481 void setReceiverPointer(void *Value) { 482 *reinterpret_cast<void **>(this + 1) = Value; 483 } 484 485public: 486 /// \brief The kind of receiver this message is sending to. 487 enum ReceiverKind { 488 /// \brief The receiver is a class. 489 Class = 0, 490 /// \brief The receiver is an object instance. 491 Instance, 492 /// \brief The receiver is a superclass. 493 SuperClass, 494 /// \brief The receiver is the instance of the superclass object. 495 SuperInstance 496 }; 497 498 /// \brief Create a message send to super. 499 /// 500 /// \param Context The ASTContext in which this expression will be created. 501 /// 502 /// \param T The result type of this message. 503 /// 504 /// \param VK The value kind of this message. A message returning 505 /// a l-value or r-value reference will be an l-value or x-value, 506 /// respectively. 507 /// 508 /// \param LBrac The location of the open square bracket '['. 509 /// 510 /// \param SuperLoc The location of the "super" keyword. 511 /// 512 /// \param IsInstanceSuper Whether this is an instance "super" 513 /// message (otherwise, it's a class "super" message). 514 /// 515 /// \param Sel The selector used to determine which method gets called. 516 /// 517 /// \param Method The Objective-C method against which this message 518 /// send was type-checked. May be NULL. 519 /// 520 /// \param Args The message send arguments. 521 /// 522 /// \param NumArgs The number of arguments. 523 /// 524 /// \param RBracLoc The location of the closing square bracket ']'. 525 static ObjCMessageExpr *Create(ASTContext &Context, QualType T, 526 ExprValueKind VK, 527 SourceLocation LBracLoc, 528 SourceLocation SuperLoc, 529 bool IsInstanceSuper, 530 QualType SuperType, 531 Selector Sel, 532 SourceLocation SelLoc, 533 ObjCMethodDecl *Method, 534 Expr **Args, unsigned NumArgs, 535 SourceLocation RBracLoc); 536 537 /// \brief Create a class message send. 538 /// 539 /// \param Context The ASTContext in which this expression will be created. 540 /// 541 /// \param T The result type of this message. 542 /// 543 /// \param VK The value kind of this message. A message returning 544 /// a l-value or r-value reference will be an l-value or x-value, 545 /// respectively. 546 /// 547 /// \param LBrac The location of the open square bracket '['. 548 /// 549 /// \param Receiver The type of the receiver, including 550 /// source-location information. 551 /// 552 /// \param Sel The selector used to determine which method gets called. 553 /// 554 /// \param Method The Objective-C method against which this message 555 /// send was type-checked. May be NULL. 556 /// 557 /// \param Args The message send arguments. 558 /// 559 /// \param NumArgs The number of arguments. 560 /// 561 /// \param RBracLoc The location of the closing square bracket ']'. 562 static ObjCMessageExpr *Create(ASTContext &Context, QualType T, 563 ExprValueKind VK, 564 SourceLocation LBracLoc, 565 TypeSourceInfo *Receiver, 566 Selector Sel, 567 SourceLocation SelLoc, 568 ObjCMethodDecl *Method, 569 Expr **Args, unsigned NumArgs, 570 SourceLocation RBracLoc); 571 572 /// \brief Create an instance message send. 573 /// 574 /// \param Context The ASTContext in which this expression will be created. 575 /// 576 /// \param T The result type of this message. 577 /// 578 /// \param VK The value kind of this message. A message returning 579 /// a l-value or r-value reference will be an l-value or x-value, 580 /// respectively. 581 /// 582 /// \param LBrac The location of the open square bracket '['. 583 /// 584 /// \param Receiver The expression used to produce the object that 585 /// will receive this message. 586 /// 587 /// \param Sel The selector used to determine which method gets called. 588 /// 589 /// \param Method The Objective-C method against which this message 590 /// send was type-checked. May be NULL. 591 /// 592 /// \param Args The message send arguments. 593 /// 594 /// \param NumArgs The number of arguments. 595 /// 596 /// \param RBracLoc The location of the closing square bracket ']'. 597 static ObjCMessageExpr *Create(ASTContext &Context, QualType T, 598 ExprValueKind VK, 599 SourceLocation LBracLoc, 600 Expr *Receiver, 601 Selector Sel, 602 SourceLocation SelLoc, 603 ObjCMethodDecl *Method, 604 Expr **Args, unsigned NumArgs, 605 SourceLocation RBracLoc); 606 607 /// \brief Create an empty Objective-C message expression, to be 608 /// filled in by subsequent calls. 609 /// 610 /// \param Context The context in which the message send will be created. 611 /// 612 /// \param NumArgs The number of message arguments, not including 613 /// the receiver. 614 static ObjCMessageExpr *CreateEmpty(ASTContext &Context, unsigned NumArgs); 615 616 /// \brief Determine the kind of receiver that this message is being 617 /// sent to. 618 ReceiverKind getReceiverKind() const { return (ReceiverKind)Kind; } 619 620 /// \brief Source range of the receiver. 621 SourceRange getReceiverRange() const; 622 623 /// \brief Determine whether this is an instance message to either a 624 /// computed object or to super. 625 bool isInstanceMessage() const { 626 return getReceiverKind() == Instance || getReceiverKind() == SuperInstance; 627 } 628 629 /// \brief Determine whether this is an class message to either a 630 /// specified class or to super. 631 bool isClassMessage() const { 632 return getReceiverKind() == Class || getReceiverKind() == SuperClass; 633 } 634 635 /// \brief Returns the receiver of an instance message. 636 /// 637 /// \brief Returns the object expression for an instance message, or 638 /// NULL for a message that is not an instance message. 639 Expr *getInstanceReceiver() { 640 if (getReceiverKind() == Instance) 641 return static_cast<Expr *>(getReceiverPointer()); 642 643 return 0; 644 } 645 const Expr *getInstanceReceiver() const { 646 return const_cast<ObjCMessageExpr*>(this)->getInstanceReceiver(); 647 } 648 649 /// \brief Turn this message send into an instance message that 650 /// computes the receiver object with the given expression. 651 void setInstanceReceiver(Expr *rec) { 652 Kind = Instance; 653 setReceiverPointer(rec); 654 } 655 656 /// \brief Returns the type of a class message send, or NULL if the 657 /// message is not a class message. 658 QualType getClassReceiver() const { 659 if (TypeSourceInfo *TSInfo = getClassReceiverTypeInfo()) 660 return TSInfo->getType(); 661 662 return QualType(); 663 } 664 665 /// \brief Returns a type-source information of a class message 666 /// send, or NULL if the message is not a class message. 667 TypeSourceInfo *getClassReceiverTypeInfo() const { 668 if (getReceiverKind() == Class) 669 return reinterpret_cast<TypeSourceInfo *>(getReceiverPointer()); 670 return 0; 671 } 672 673 void setClassReceiver(TypeSourceInfo *TSInfo) { 674 Kind = Class; 675 setReceiverPointer(TSInfo); 676 } 677 678 /// \brief Retrieve the location of the 'super' keyword for a class 679 /// or instance message to 'super', otherwise an invalid source location. 680 SourceLocation getSuperLoc() const { 681 if (getReceiverKind() == SuperInstance || getReceiverKind() == SuperClass) 682 return SuperLoc; 683 684 return SourceLocation(); 685 } 686 687 /// \brief Retrieve the Objective-C interface to which this message 688 /// is being directed, if known. 689 /// 690 /// This routine cross-cuts all of the different kinds of message 691 /// sends to determine what the underlying (statically known) type 692 /// of the receiver will be; use \c getReceiverKind() to determine 693 /// whether the message is a class or an instance method, whether it 694 /// is a send to super or not, etc. 695 /// 696 /// \returns The Objective-C interface if known, otherwise NULL. 697 ObjCInterfaceDecl *getReceiverInterface() const; 698 699 /// \brief Retrieve the type referred to by 'super'. 700 /// 701 /// The returned type will either be an ObjCInterfaceType (for an 702 /// class message to super) or an ObjCObjectPointerType that refers 703 /// to a class (for an instance message to super); 704 QualType getSuperType() const { 705 if (getReceiverKind() == SuperInstance || getReceiverKind() == SuperClass) 706 return QualType::getFromOpaquePtr(getReceiverPointer()); 707 708 return QualType(); 709 } 710 711 void setSuper(SourceLocation Loc, QualType T, bool IsInstanceSuper) { 712 Kind = IsInstanceSuper? SuperInstance : SuperClass; 713 SuperLoc = Loc; 714 setReceiverPointer(T.getAsOpaquePtr()); 715 } 716 717 Selector getSelector() const; 718 719 void setSelector(Selector S) { 720 HasMethod = false; 721 SelectorOrMethod = reinterpret_cast<uintptr_t>(S.getAsOpaquePtr()); 722 } 723 724 const ObjCMethodDecl *getMethodDecl() const { 725 if (HasMethod) 726 return reinterpret_cast<const ObjCMethodDecl *>(SelectorOrMethod); 727 728 return 0; 729 } 730 731 ObjCMethodDecl *getMethodDecl() { 732 if (HasMethod) 733 return reinterpret_cast<ObjCMethodDecl *>(SelectorOrMethod); 734 735 return 0; 736 } 737 738 void setMethodDecl(ObjCMethodDecl *MD) { 739 HasMethod = true; 740 SelectorOrMethod = reinterpret_cast<uintptr_t>(MD); 741 } 742 743 /// \brief Return the number of actual arguments in this message, 744 /// not counting the receiver. 745 unsigned getNumArgs() const { return NumArgs; } 746 747 /// \brief Retrieve the arguments to this message, not including the 748 /// receiver. 749 Expr **getArgs() { 750 return reinterpret_cast<Expr **>(this + 1) + 1; 751 } 752 const Expr * const *getArgs() const { 753 return reinterpret_cast<const Expr * const *>(this + 1) + 1; 754 } 755 756 /// getArg - Return the specified argument. 757 Expr *getArg(unsigned Arg) { 758 assert(Arg < NumArgs && "Arg access out of range!"); 759 return cast<Expr>(getArgs()[Arg]); 760 } 761 const Expr *getArg(unsigned Arg) const { 762 assert(Arg < NumArgs && "Arg access out of range!"); 763 return cast<Expr>(getArgs()[Arg]); 764 } 765 /// setArg - Set the specified argument. 766 void setArg(unsigned Arg, Expr *ArgExpr) { 767 assert(Arg < NumArgs && "Arg access out of range!"); 768 getArgs()[Arg] = ArgExpr; 769 } 770 771 SourceLocation getLeftLoc() const { return LBracLoc; } 772 SourceLocation getRightLoc() const { return RBracLoc; } 773 SourceLocation getSelectorLoc() const { return SelectorLoc; } 774 775 void setSourceRange(SourceRange R) { 776 LBracLoc = R.getBegin(); 777 RBracLoc = R.getEnd(); 778 } 779 virtual SourceRange getSourceRange() const { 780 return SourceRange(LBracLoc, RBracLoc); 781 } 782 783 static bool classof(const Stmt *T) { 784 return T->getStmtClass() == ObjCMessageExprClass; 785 } 786 static bool classof(const ObjCMessageExpr *) { return true; } 787 788 // Iterators 789 virtual child_iterator child_begin(); 790 virtual child_iterator child_end(); 791 792 typedef ExprIterator arg_iterator; 793 typedef ConstExprIterator const_arg_iterator; 794 795 arg_iterator arg_begin() { return reinterpret_cast<Stmt **>(getArgs()); } 796 arg_iterator arg_end() { 797 return reinterpret_cast<Stmt **>(getArgs() + NumArgs); 798 } 799 const_arg_iterator arg_begin() const { 800 return reinterpret_cast<Stmt const * const*>(getArgs()); 801 } 802 const_arg_iterator arg_end() const { 803 return reinterpret_cast<Stmt const * const*>(getArgs() + NumArgs); 804 } 805 806 friend class ASTStmtReader; 807 friend class ASTStmtWriter; 808}; 809 810/// ObjCIsaExpr - Represent X->isa and X.isa when X is an ObjC 'id' type. 811/// (similiar in spirit to MemberExpr). 812class ObjCIsaExpr : public Expr { 813 /// Base - the expression for the base object pointer. 814 Stmt *Base; 815 816 /// IsaMemberLoc - This is the location of the 'isa'. 817 SourceLocation IsaMemberLoc; 818 819 /// IsArrow - True if this is "X->F", false if this is "X.F". 820 bool IsArrow; 821public: 822 ObjCIsaExpr(Expr *base, bool isarrow, SourceLocation l, QualType ty) 823 : Expr(ObjCIsaExprClass, ty, VK_LValue, OK_Ordinary, 824 /*TypeDependent=*/false, base->isValueDependent(), 825 /*ContainsUnexpandedParameterPack=*/false), 826 Base(base), IsaMemberLoc(l), IsArrow(isarrow) {} 827 828 /// \brief Build an empty expression. 829 explicit ObjCIsaExpr(EmptyShell Empty) : Expr(ObjCIsaExprClass, Empty) { } 830 831 void setBase(Expr *E) { Base = E; } 832 Expr *getBase() const { return cast<Expr>(Base); } 833 834 bool isArrow() const { return IsArrow; } 835 void setArrow(bool A) { IsArrow = A; } 836 837 /// getMemberLoc - Return the location of the "member", in X->F, it is the 838 /// location of 'F'. 839 SourceLocation getIsaMemberLoc() const { return IsaMemberLoc; } 840 void setIsaMemberLoc(SourceLocation L) { IsaMemberLoc = L; } 841 842 virtual SourceRange getSourceRange() const { 843 return SourceRange(getBase()->getLocStart(), IsaMemberLoc); 844 } 845 846 virtual SourceLocation getExprLoc() const { return IsaMemberLoc; } 847 848 static bool classof(const Stmt *T) { 849 return T->getStmtClass() == ObjCIsaExprClass; 850 } 851 static bool classof(const ObjCIsaExpr *) { return true; } 852 853 // Iterators 854 virtual child_iterator child_begin(); 855 virtual child_iterator child_end(); 856}; 857 858} // end namespace clang 859 860#endif 861