ExprObjC.h revision c6c16af963eddc3e9b75b5d2614d069e1162fe27
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/Expr.h" 18#include "clang/Basic/IdentifierTable.h" 19 20namespace clang { 21 class IdentifierInfo; 22 class ASTContext; 23 class ObjCMethodDecl; 24 class ObjCPropertyDecl; 25 26/// ObjCStringLiteral, used for Objective-C string literals 27/// i.e. @"foo". 28class ObjCStringLiteral : public Expr { 29 Stmt *String; 30 SourceLocation AtLoc; 31public: 32 ObjCStringLiteral(StringLiteral *SL, QualType T, SourceLocation L) 33 : Expr(ObjCStringLiteralClass, T), String(SL), AtLoc(L) {} 34 35 StringLiteral* getString() { return cast<StringLiteral>(String); } 36 const StringLiteral* getString() const { return cast<StringLiteral>(String); } 37 38 SourceLocation getAtLoc() const { return AtLoc; } 39 40 virtual SourceRange getSourceRange() const { 41 return SourceRange(AtLoc, String->getLocEnd()); 42 } 43 44 static bool classof(const Stmt *T) { 45 return T->getStmtClass() == ObjCStringLiteralClass; 46 } 47 static bool classof(const ObjCStringLiteral *) { return true; } 48 49 // Iterators 50 virtual child_iterator child_begin(); 51 virtual child_iterator child_end(); 52 53 virtual void EmitImpl(llvm::Serializer& S) const; 54 static ObjCStringLiteral* CreateImpl(llvm::Deserializer& D, ASTContext& C); 55}; 56 57/// ObjCEncodeExpr, used for @encode in Objective-C. 58class ObjCEncodeExpr : public Expr { 59 QualType EncType; 60 SourceLocation AtLoc, RParenLoc; 61public: 62 ObjCEncodeExpr(QualType T, QualType ET, 63 SourceLocation at, SourceLocation rp) 64 : Expr(ObjCEncodeExprClass, T), EncType(ET), AtLoc(at), RParenLoc(rp) {} 65 66 SourceLocation getAtLoc() const { return AtLoc; } 67 SourceLocation getRParenLoc() const { return RParenLoc; } 68 69 virtual SourceRange getSourceRange() const { 70 return SourceRange(AtLoc, RParenLoc); 71 } 72 73 QualType getEncodedType() const { return EncType; } 74 75 static bool classof(const Stmt *T) { 76 return T->getStmtClass() == ObjCEncodeExprClass; 77 } 78 static bool classof(const ObjCEncodeExpr *) { return true; } 79 80 // Iterators 81 virtual child_iterator child_begin(); 82 virtual child_iterator child_end(); 83 84 virtual void EmitImpl(llvm::Serializer& S) const; 85 static ObjCEncodeExpr* CreateImpl(llvm::Deserializer& D, ASTContext& C); 86}; 87 88/// ObjCSelectorExpr used for @selector in Objective-C. 89class ObjCSelectorExpr : public Expr { 90 Selector SelName; 91 SourceLocation AtLoc, RParenLoc; 92public: 93 ObjCSelectorExpr(QualType T, Selector selInfo, 94 SourceLocation at, SourceLocation rp) 95 : Expr(ObjCSelectorExprClass, T), SelName(selInfo), 96 AtLoc(at), RParenLoc(rp) {} 97 98 Selector getSelector() const { return SelName; } 99 100 SourceLocation getAtLoc() const { return AtLoc; } 101 SourceLocation getRParenLoc() const { return RParenLoc; } 102 103 virtual SourceRange getSourceRange() const { 104 return SourceRange(AtLoc, RParenLoc); 105 } 106 107 /// getNumArgs - Return the number of actual arguments to this call. 108 unsigned getNumArgs() const { return SelName.getNumArgs(); } 109 110 static bool classof(const Stmt *T) { 111 return T->getStmtClass() == ObjCSelectorExprClass; 112 } 113 static bool classof(const ObjCSelectorExpr *) { return true; } 114 115 // Iterators 116 virtual child_iterator child_begin(); 117 virtual child_iterator child_end(); 118 119 virtual void EmitImpl(llvm::Serializer& S) const; 120 static ObjCSelectorExpr* CreateImpl(llvm::Deserializer& D, ASTContext& C); 121}; 122 123/// ObjCProtocolExpr used for protocol in Objective-C. 124class ObjCProtocolExpr : public Expr { 125 ObjCProtocolDecl *Protocol; 126 SourceLocation AtLoc, RParenLoc; 127public: 128 ObjCProtocolExpr(QualType T, ObjCProtocolDecl *protocol, 129 SourceLocation at, SourceLocation rp) 130 : Expr(ObjCProtocolExprClass, T), Protocol(protocol), 131 AtLoc(at), RParenLoc(rp) {} 132 133 ObjCProtocolDecl *getProtocol() const { return Protocol; } 134 135 SourceLocation getAtLoc() const { return AtLoc; } 136 SourceLocation getRParenLoc() const { return RParenLoc; } 137 138 virtual SourceRange getSourceRange() const { 139 return SourceRange(AtLoc, RParenLoc); 140 } 141 142 static bool classof(const Stmt *T) { 143 return T->getStmtClass() == ObjCProtocolExprClass; 144 } 145 static bool classof(const ObjCProtocolExpr *) { return true; } 146 147 // Iterators 148 virtual child_iterator child_begin(); 149 virtual child_iterator child_end(); 150 151 virtual void EmitImpl(llvm::Serializer& S) const; 152 static ObjCProtocolExpr* CreateImpl(llvm::Deserializer& D, ASTContext& C); 153}; 154 155/// ObjCIvarRefExpr - A reference to an ObjC instance variable. 156class ObjCIvarRefExpr : public Expr { 157 class ObjCIvarDecl *D; 158 SourceLocation Loc; 159 Stmt *Base; 160 bool IsArrow:1; // True if this is "X->F", false if this is "X.F". 161 bool IsFreeIvar:1; // True if ivar reference has no base (self assumed). 162 163public: 164 ObjCIvarRefExpr(ObjCIvarDecl *d, 165 QualType t, SourceLocation l, Expr *base=0, 166 bool arrow = false, bool freeIvar = false) : 167 Expr(ObjCIvarRefExprClass, t), D(d), 168 Loc(l), Base(base), IsArrow(arrow), 169 IsFreeIvar(freeIvar) {} 170 171 ObjCIvarDecl *getDecl() { return D; } 172 const ObjCIvarDecl *getDecl() const { return D; } 173 virtual SourceRange getSourceRange() const { 174 return isFreeIvar() ? SourceRange(Loc) 175 : SourceRange(getBase()->getLocStart(), Loc); 176 } 177 const Expr *getBase() const { return cast<Expr>(Base); } 178 Expr *getBase() { return cast<Expr>(Base); } 179 void setBase(Expr * base) { Base = base; } 180 bool isArrow() const { return IsArrow; } 181 bool isFreeIvar() const { return IsFreeIvar; } 182 183 SourceLocation getLocation() const { return Loc; } 184 185 static bool classof(const Stmt *T) { 186 return T->getStmtClass() == ObjCIvarRefExprClass; 187 } 188 static bool classof(const ObjCIvarRefExpr *) { return true; } 189 190 // Iterators 191 virtual child_iterator child_begin(); 192 virtual child_iterator child_end(); 193 194 virtual void EmitImpl(llvm::Serializer& S) const; 195 static ObjCIvarRefExpr* CreateImpl(llvm::Deserializer& D, ASTContext& C); 196}; 197 198/// ObjCPropertyRefExpr - A dot-syntax expression to access an ObjC 199/// property. 200/// 201class ObjCPropertyRefExpr : public Expr { 202private: 203 ObjCPropertyDecl *AsProperty; 204 SourceLocation IdLoc; 205 Stmt *Base; 206 207public: 208 ObjCPropertyRefExpr(ObjCPropertyDecl *PD, QualType t, 209 SourceLocation l, Expr *base) 210 : Expr(ObjCPropertyRefExprClass, t), AsProperty(PD), IdLoc(l), Base(base) { 211 } 212 ObjCPropertyDecl *getProperty() const { 213 return AsProperty; 214 } 215 216 virtual SourceRange getSourceRange() const { 217 return SourceRange(getBase()->getLocStart(), IdLoc); 218 } 219 const Expr *getBase() const { return cast<Expr>(Base); } 220 Expr *getBase() { return cast<Expr>(Base); } 221 void setBase(Expr * base) { Base = base; } 222 223 SourceLocation getLocation() const { return IdLoc; } 224 225 static bool classof(const Stmt *T) { 226 return T->getStmtClass() == ObjCPropertyRefExprClass; 227 } 228 static bool classof(const ObjCPropertyRefExpr *) { return true; } 229 230 // Iterators 231 virtual child_iterator child_begin(); 232 virtual child_iterator child_end(); 233 234 virtual void EmitImpl(llvm::Serializer& S) const; 235 static ObjCPropertyRefExpr* CreateImpl(llvm::Deserializer& D, ASTContext& C); 236}; 237 238/// ObjCKVCRefExpr - A dot-syntax expression to access "implicit" properties 239/// (i.e. methods following the property naming convention). KVC stands for 240/// Key Value Encoding, a generic concept for accessing or setting a 'Key' 241/// value for an object. 242/// 243 244class ObjCKVCRefExpr : public Expr { 245private: 246 247 ObjCMethodDecl *Setter; 248 ObjCMethodDecl *Getter; 249 SourceLocation Loc; 250 Stmt *Base; 251 252public: 253 ObjCKVCRefExpr(ObjCMethodDecl *getter, 254 QualType t, 255 ObjCMethodDecl *setter, 256 SourceLocation l, Expr *base) 257 : Expr(ObjCKVCRefExprClass, t), Setter(setter), 258 Getter(getter), Loc(l), Base(base) { 259 } 260 261 ObjCMethodDecl *getGetterMethod() const { 262 return Getter; 263 } 264 ObjCMethodDecl *getSetterMethod() const { 265 return Setter; 266 } 267 268 virtual SourceRange getSourceRange() const { 269 return SourceRange(getBase()->getLocStart(), Loc); 270 } 271 const Expr *getBase() const { return cast<Expr>(Base); } 272 Expr *getBase() { return cast<Expr>(Base); } 273 void setBase(Expr * base) { Base = base; } 274 275 SourceLocation getLocation() const { return Loc; } 276 277 static bool classof(const Stmt *T) { 278 return T->getStmtClass() == ObjCKVCRefExprClass; 279 } 280 static bool classof(const ObjCKVCRefExpr *) { return true; } 281 282 // Iterators 283 virtual child_iterator child_begin(); 284 virtual child_iterator child_end(); 285 286 virtual void EmitImpl(llvm::Serializer& S) const; 287 static ObjCKVCRefExpr* CreateImpl(llvm::Deserializer& D, ASTContext& C); 288}; 289 290class ObjCMessageExpr : public Expr { 291 // SubExprs - The receiver and arguments of the message expression. 292 Stmt **SubExprs; 293 294 // NumArgs - The number of arguments (not including the receiver) to the 295 // message expression. 296 unsigned NumArgs; 297 298 // A unigue name for this message. 299 Selector SelName; 300 301 // A method prototype for this message (optional). 302 // FIXME: Since method decls contain the selector, and most messages have a 303 // prototype, consider devising a scheme for unifying SelName/MethodProto. 304 ObjCMethodDecl *MethodProto; 305 306 SourceLocation LBracloc, RBracloc; 307 308 // Constants for indexing into SubExprs. 309 enum { RECEIVER=0, ARGS_START=1 }; 310 311 // Bit-swizziling flags. 312 enum { IsInstMeth=0, IsClsMethDeclUnknown, IsClsMethDeclKnown, Flags=0x3 }; 313 unsigned getFlag() const { return (uintptr_t) SubExprs[RECEIVER] & Flags; } 314 315 // constructor used during deserialization 316 ObjCMessageExpr(Selector selInfo, QualType retType, 317 SourceLocation LBrac, SourceLocation RBrac, 318 Stmt **subexprs, unsigned nargs) 319 : Expr(ObjCMessageExprClass, retType), SubExprs(subexprs), 320 NumArgs(nargs), SelName(selInfo), MethodProto(NULL), 321 LBracloc(LBrac), RBracloc(RBrac) {} 322 323public: 324 /// This constructor is used to represent class messages where the 325 /// ObjCInterfaceDecl* of the receiver is not known. 326 ObjCMessageExpr(IdentifierInfo *clsName, Selector selInfo, 327 QualType retType, ObjCMethodDecl *methDecl, 328 SourceLocation LBrac, SourceLocation RBrac, 329 Expr **ArgExprs, unsigned NumArgs); 330 331 /// This constructor is used to represent class messages where the 332 /// ObjCInterfaceDecl* of the receiver is known. 333 // FIXME: clsName should be typed to ObjCInterfaceType 334 ObjCMessageExpr(ObjCInterfaceDecl *cls, Selector selInfo, 335 QualType retType, ObjCMethodDecl *methDecl, 336 SourceLocation LBrac, SourceLocation RBrac, 337 Expr **ArgExprs, unsigned NumArgs); 338 339 // constructor for instance messages. 340 ObjCMessageExpr(Expr *receiver, Selector selInfo, 341 QualType retType, ObjCMethodDecl *methDecl, 342 SourceLocation LBrac, SourceLocation RBrac, 343 Expr **ArgExprs, unsigned NumArgs); 344 345 ~ObjCMessageExpr() { 346 delete [] SubExprs; 347 } 348 349 /// getReceiver - Returns the receiver of the message expression. 350 /// This can be NULL if the message is for class methods. For 351 /// class methods, use getClassName. 352 /// FIXME: need to handle/detect 'super' usage within a class method. 353 Expr *getReceiver() { 354 uintptr_t x = (uintptr_t) SubExprs[RECEIVER]; 355 return (x & Flags) == IsInstMeth ? (Expr*) x : 0; 356 } 357 const Expr *getReceiver() const { 358 return const_cast<ObjCMessageExpr*>(this)->getReceiver(); 359 } 360 361 Selector getSelector() const { return SelName; } 362 363 const ObjCMethodDecl *getMethodDecl() const { return MethodProto; } 364 ObjCMethodDecl *getMethodDecl() { return MethodProto; } 365 366 typedef std::pair<ObjCInterfaceDecl*, IdentifierInfo*> ClassInfo; 367 368 /// getClassInfo - For class methods, this returns both the ObjCInterfaceDecl* 369 /// and IdentifierInfo* of the invoked class. Both can be NULL if this 370 /// is an instance message, and the ObjCInterfaceDecl* can be NULL if none 371 /// was available when this ObjCMessageExpr object was constructed. 372 ClassInfo getClassInfo() const; 373 374 /// getClassName - For class methods, this returns the invoked class, 375 /// and returns NULL otherwise. For instance methods, use getReceiver. 376 IdentifierInfo *getClassName() const { 377 return getClassInfo().second; 378 } 379 380 381 /// getNumArgs - Return the number of actual arguments to this call. 382 unsigned getNumArgs() const { return NumArgs; } 383 384 /// getArg - Return the specified argument. 385 Expr *getArg(unsigned Arg) { 386 assert(Arg < NumArgs && "Arg access out of range!"); 387 return cast<Expr>(SubExprs[Arg+ARGS_START]); 388 } 389 const Expr *getArg(unsigned Arg) const { 390 assert(Arg < NumArgs && "Arg access out of range!"); 391 return cast<Expr>(SubExprs[Arg+ARGS_START]); 392 } 393 /// setArg - Set the specified argument. 394 void setArg(unsigned Arg, Expr *ArgExpr) { 395 assert(Arg < NumArgs && "Arg access out of range!"); 396 SubExprs[Arg+ARGS_START] = ArgExpr; 397 } 398 399 virtual SourceRange getSourceRange() const { 400 return SourceRange(LBracloc, RBracloc); 401 } 402 403 static bool classof(const Stmt *T) { 404 return T->getStmtClass() == ObjCMessageExprClass; 405 } 406 static bool classof(const ObjCMessageExpr *) { return true; } 407 408 // Iterators 409 virtual child_iterator child_begin(); 410 virtual child_iterator child_end(); 411 412 typedef ExprIterator arg_iterator; 413 typedef ConstExprIterator const_arg_iterator; 414 415 arg_iterator arg_begin() { return &SubExprs[ARGS_START]; } 416 arg_iterator arg_end() { return &SubExprs[ARGS_START] + NumArgs; } 417 const_arg_iterator arg_begin() const { return &SubExprs[ARGS_START]; } 418 const_arg_iterator arg_end() const { return &SubExprs[ARGS_START] + NumArgs; } 419 420 // Serialization. 421 virtual void EmitImpl(llvm::Serializer& S) const; 422 static ObjCMessageExpr* CreateImpl(llvm::Deserializer& D, ASTContext& C); 423}; 424 425/// ObjCSuperExpr - Represents the "super" expression in Objective-C, 426/// which refers to the object on which the current method is executing. 427class ObjCSuperExpr : public Expr { 428 SourceLocation Loc; 429 430public: 431 ObjCSuperExpr(SourceLocation L, QualType Type) 432 : Expr(ObjCSuperExprClass, Type), Loc(L) { } 433 434 virtual SourceRange getSourceRange() const { return SourceRange(Loc); } 435 436 static bool classof(const Stmt *T) { 437 return T->getStmtClass() == ObjCSuperExprClass; 438 } 439 static bool classof(const ObjCSuperExpr *) { return true; } 440 441 // Iterators 442 virtual child_iterator child_begin(); 443 virtual child_iterator child_end(); 444 445 virtual void EmitImpl(llvm::Serializer& S) const; 446 static ObjCSuperExpr* CreateImpl(llvm::Deserializer& D, ASTContext& C); 447}; 448 449} // end namespace clang 450 451#endif 452