diff options
author | Fariborz Jahanian <fjahanian@apple.com> | 2010-10-14 16:04:05 +0000 |
---|---|---|
committer | Fariborz Jahanian <fjahanian@apple.com> | 2010-10-14 16:04:05 +0000 |
commit | 8ac2d449820fd0df00fcbde5bf82165c1f49854d (patch) | |
tree | e776d338a9bd913adb7265519b84826f371b897b | |
parent | 44270d6abff30415cdd873164823f48a45be7f8c (diff) |
Eliminate usage of ObjCSuperExpr used for
'super' as receiver of property or a setter/getter
methods. //rdar: //8525788
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@116483 91177308-0d34-0410-b5e6-96231b3b80d8
26 files changed, 273 insertions, 152 deletions
diff --git a/include/clang/AST/ExprObjC.h b/include/clang/AST/ExprObjC.h index 15b70075cb..407a64938b 100644 --- a/include/clang/AST/ExprObjC.h +++ b/include/clang/AST/ExprObjC.h @@ -229,13 +229,29 @@ class ObjCPropertyRefExpr : public Expr { private: ObjCPropertyDecl *AsProperty; SourceLocation IdLoc; - Stmt *Base; + + /// \brief When the receiver in property access is 'super', this is + /// the location of the 'super' keyword. + SourceLocation SuperLoc; + + /// \brief When the receiver in property access is 'super', this is + /// the type associated with 'super' keyword. A null type indicates + /// that this is not a 'super' receiver. + llvm::PointerUnion<Stmt*, Type*> BaseExprOrSuperType; + public: ObjCPropertyRefExpr(ObjCPropertyDecl *PD, QualType t, SourceLocation l, Expr *base) : Expr(ObjCPropertyRefExprClass, t, /*TypeDependent=*/false, base->isValueDependent()), - AsProperty(PD), IdLoc(l), Base(base) { + AsProperty(PD), IdLoc(l), BaseExprOrSuperType(base) { + } + + ObjCPropertyRefExpr(ObjCPropertyDecl *PD, QualType t, + SourceLocation l, SourceLocation sl, QualType st) + : Expr(ObjCPropertyRefExprClass, t, /*TypeDependent=*/false, false), + AsProperty(PD), IdLoc(l), SuperLoc(sl), + BaseExprOrSuperType(st.getTypePtr()) { } explicit ObjCPropertyRefExpr(EmptyShell Empty) @@ -243,13 +259,27 @@ public: ObjCPropertyDecl *getProperty() const { return AsProperty; } - const Expr *getBase() const { return cast<Expr>(Base); } - Expr *getBase() { return cast<Expr>(Base); } + const Expr *getBase() const { + return cast<Expr>(BaseExprOrSuperType.get<Stmt*>()); + } + Expr *getBase() { + return cast<Expr>(BaseExprOrSuperType.get<Stmt*>()); + } SourceLocation getLocation() const { return IdLoc; } + + SourceLocation getSuperLocation() const { return SuperLoc; } + QualType getSuperType() const { + Type *t = BaseExprOrSuperType.get<Type*>(); + return QualType(t, 0); + } + bool isSuperReceiver() const { return BaseExprOrSuperType.is<Type*>(); } virtual SourceRange getSourceRange() const { - return SourceRange(getBase()->getLocStart(), IdLoc); + return SourceRange( + (BaseExprOrSuperType.is<Stmt*>() ? getBase()->getLocStart() + : getSuperLocation()), + IdLoc); } static bool classof(const Stmt *T) { @@ -263,8 +293,10 @@ public: private: friend class ASTStmtReader; void setProperty(ObjCPropertyDecl *D) { AsProperty = D; } - void setBase(Expr *base) { Base = base; } + void setBase(Expr *base) { BaseExprOrSuperType = base; } void setLocation(SourceLocation L) { IdLoc = L; } + void setSuperLocation(SourceLocation Loc) { SuperLoc = Loc; } + void setSuperType(QualType T) { BaseExprOrSuperType = T.getTypePtr(); } }; /// ObjCImplicitSetterGetterRefExpr - A dot-syntax expression to access two @@ -292,10 +324,22 @@ class ObjCImplicitSetterGetterRefExpr : public Expr { // FIXME: Swizzle these into a single pointer. Stmt *Base; ObjCInterfaceDecl *InterfaceDecl; - /// Location of the receiver class in the dot syntax notation + /// \brief Location of the receiver class in the dot syntax notation /// used to call a class method setter/getter. SourceLocation ClassLoc; + /// \brief When the receiver in dot-syntax expression is 'super', + /// this is the location of the 'super' keyword. + SourceLocation SuperLoc; + + /// \brief When the receiver in dot-syntax expression is 'super', this is + /// the type associated with 'super' keyword. + QualType SuperTy; + + /// \brief When the receiver in dot-syntax expression is 'super', this is + /// set to true. + bool IsSuper:1; + public: ObjCImplicitSetterGetterRefExpr(ObjCMethodDecl *getter, QualType t, @@ -305,7 +349,22 @@ public: base->isValueDependent()), Setter(setter), Getter(getter), MemberLoc(l), Base(base), InterfaceDecl(0), ClassLoc(SourceLocation()) { + IsSuper = false; } + + ObjCImplicitSetterGetterRefExpr(ObjCMethodDecl *getter, + QualType t, + ObjCMethodDecl *setter, + SourceLocation l, + SourceLocation sl, + QualType st) + : Expr(ObjCImplicitSetterGetterRefExprClass, t, /*TypeDependent=*/false, + false), + Setter(setter), Getter(getter), MemberLoc(l), + InterfaceDecl(0), ClassLoc(SourceLocation()), + SuperLoc(sl), SuperTy(st), IsSuper(true) { + } + ObjCImplicitSetterGetterRefExpr(ObjCMethodDecl *getter, QualType t, ObjCMethodDecl *setter, @@ -313,6 +372,7 @@ public: : Expr(ObjCImplicitSetterGetterRefExprClass, t, false, false), Setter(setter), Getter(getter), MemberLoc(l), Base(0), InterfaceDecl(C), ClassLoc(CL) { + IsSuper = false; } explicit ObjCImplicitSetterGetterRefExpr(EmptyShell Empty) : Expr(ObjCImplicitSetterGetterRefExprClass, Empty){} @@ -325,6 +385,8 @@ public: void setInterfaceDecl(ObjCInterfaceDecl *D) { InterfaceDecl = D; } virtual SourceRange getSourceRange() const { + if (isSuperReceiver()) + return SourceRange(getSuperLocation(), MemberLoc); if (Base) return SourceRange(getBase()->getLocStart(), MemberLoc); return SourceRange(ClassLoc, MemberLoc); @@ -337,6 +399,10 @@ public: void setLocation(SourceLocation L) { MemberLoc = L; } SourceLocation getClassLoc() const { return ClassLoc; } void setClassLoc(SourceLocation L) { ClassLoc = L; } + + SourceLocation getSuperLocation() const { return SuperLoc; } + QualType getSuperType() const { return SuperTy; } + bool isSuperReceiver() const { return IsSuper; } static bool classof(const Stmt *T) { return T->getStmtClass() == ObjCImplicitSetterGetterRefExprClass; @@ -346,6 +412,12 @@ public: // Iterators virtual child_iterator child_begin(); virtual child_iterator child_end(); + +private: + friend class ASTStmtReader; + void setSuperLocation(SourceLocation Loc) { SuperLoc = Loc; } + void setSuperType(QualType T) { SuperTy = T; } + void setSuperReceiver(bool bv) { IsSuper = bv; } }; /// \brief An expression that sends a message to the given Objective-C @@ -738,33 +810,6 @@ public: const_arg_iterator arg_end() const { return getArgs() + NumArgs; } }; -/// ObjCSuperExpr - Represents the "super" expression in Objective-C, -/// which refers to the object on which the current method is executing. -/// -/// FIXME: This class is intended for removal, once its remaining -/// clients have been altered to represent "super" internally. -class ObjCSuperExpr : public Expr { - SourceLocation Loc; -public: - ObjCSuperExpr(SourceLocation L, QualType Type) - : Expr(ObjCSuperExprClass, Type, false, false), Loc(L) { } - explicit ObjCSuperExpr(EmptyShell Empty) : Expr(ObjCSuperExprClass, Empty) {} - - SourceLocation getLoc() const { return Loc; } - void setLoc(SourceLocation L) { Loc = L; } - - virtual SourceRange getSourceRange() const { return SourceRange(Loc); } - - static bool classof(const Stmt *T) { - return T->getStmtClass() == ObjCSuperExprClass; - } - static bool classof(const ObjCSuperExpr *) { return true; } - - // Iterators - virtual child_iterator child_begin(); - virtual child_iterator child_end(); -}; - /// ObjCIsaExpr - Represent X->isa and X.isa when X is an ObjC 'id' type. /// (similiar in spirit to MemberExpr). class ObjCIsaExpr : public Expr { diff --git a/include/clang/AST/RecursiveASTVisitor.h b/include/clang/AST/RecursiveASTVisitor.h index 83a3d145e2..cb617f14e0 100644 --- a/include/clang/AST/RecursiveASTVisitor.h +++ b/include/clang/AST/RecursiveASTVisitor.h @@ -1835,7 +1835,6 @@ DEF_TRAVERSE_STMT(ObjCMessageExpr, { }) DEF_TRAVERSE_STMT(ObjCPropertyRefExpr, { }) DEF_TRAVERSE_STMT(ObjCProtocolExpr, { }) DEF_TRAVERSE_STMT(ObjCSelectorExpr, { }) -DEF_TRAVERSE_STMT(ObjCSuperExpr, { }) DEF_TRAVERSE_STMT(ParenExpr, { }) DEF_TRAVERSE_STMT(ParenListExpr, { }) DEF_TRAVERSE_STMT(PredefinedExpr, { }) diff --git a/include/clang/Basic/StmtNodes.td b/include/clang/Basic/StmtNodes.td index 94702841d3..53beb98eea 100644 --- a/include/clang/Basic/StmtNodes.td +++ b/include/clang/Basic/StmtNodes.td @@ -121,7 +121,6 @@ def ObjCProtocolExpr : DStmt<Expr>; def ObjCIvarRefExpr : DStmt<Expr>; def ObjCPropertyRefExpr : DStmt<Expr>; def ObjCImplicitSetterGetterRefExpr : DStmt<Expr>; -def ObjCSuperExpr : DStmt<Expr>; def ObjCIsaExpr : DStmt<Expr>; // Clang Extensions. diff --git a/include/clang/Sema/Sema.h b/include/clang/Sema/Sema.h index b1cd5628a7..6021cf76a3 100644 --- a/include/clang/Sema/Sema.h +++ b/include/clang/Sema/Sema.h @@ -3786,7 +3786,9 @@ public: HandleExprPropertyRefExpr(const ObjCObjectPointerType *OPT, Expr *BaseExpr, DeclarationName MemberName, - SourceLocation MemberLoc); + SourceLocation MemberLoc, + SourceLocation SuperLoc, QualType SuperType, + bool Super); ExprResult ActOnClassPropertyRefExpr(IdentifierInfo &receiverName, diff --git a/include/clang/Serialization/ASTBitCodes.h b/include/clang/Serialization/ASTBitCodes.h index 8628d74ff1..6e9658bfff 100644 --- a/include/clang/Serialization/ASTBitCodes.h +++ b/include/clang/Serialization/ASTBitCodes.h @@ -830,8 +830,6 @@ namespace clang { EXPR_OBJC_KVC_REF_EXPR, /// \brief An ObjCMessageExpr record. EXPR_OBJC_MESSAGE_EXPR, - /// \brief An ObjCSuperExpr record. - EXPR_OBJC_SUPER_EXPR, /// \brief An ObjCIsa Expr record. EXPR_OBJC_ISA, diff --git a/lib/AST/Expr.cpp b/lib/AST/Expr.cpp index 708512ce46..98f0656ad1 100644 --- a/lib/AST/Expr.cpp +++ b/lib/AST/Expr.cpp @@ -2348,23 +2348,35 @@ Stmt::child_iterator ObjCIvarRefExpr::child_begin() { return &Base; } Stmt::child_iterator ObjCIvarRefExpr::child_end() { return &Base+1; } // ObjCPropertyRefExpr -Stmt::child_iterator ObjCPropertyRefExpr::child_begin() { return &Base; } -Stmt::child_iterator ObjCPropertyRefExpr::child_end() { return &Base+1; } +Stmt::child_iterator ObjCPropertyRefExpr::child_begin() +{ + if (BaseExprOrSuperType.is<Stmt*>()) { + // Hack alert! + return reinterpret_cast<Stmt**> (&BaseExprOrSuperType); + } + return child_iterator(); +} + +Stmt::child_iterator ObjCPropertyRefExpr::child_end() +{ return BaseExprOrSuperType.is<Stmt*>() ? + reinterpret_cast<Stmt**> (&BaseExprOrSuperType)+1 : + child_iterator(); +} // ObjCImplicitSetterGetterRefExpr Stmt::child_iterator ObjCImplicitSetterGetterRefExpr::child_begin() { - // If this is accessing a class member, skip that entry. - if (Base) return &Base; - return &Base+1; + // If this is accessing a class member or super, skip that entry. + // Technically, 2nd condition is sufficient. But I want to be verbose + if (isSuperReceiver() || !Base) + return child_iterator(); + return &Base; } Stmt::child_iterator ObjCImplicitSetterGetterRefExpr::child_end() { + if (isSuperReceiver() || !Base) + return child_iterator(); return &Base+1; } -// ObjCSuperExpr -Stmt::child_iterator ObjCSuperExpr::child_begin() { return child_iterator(); } -Stmt::child_iterator ObjCSuperExpr::child_end() { return child_iterator(); } - // ObjCIsaExpr Stmt::child_iterator ObjCIsaExpr::child_begin() { return &Base; } Stmt::child_iterator ObjCIsaExpr::child_end() { return &Base+1; } diff --git a/lib/AST/ExprClassification.cpp b/lib/AST/ExprClassification.cpp index c9069f8707..0ab1402fa8 100644 --- a/lib/AST/ExprClassification.cpp +++ b/lib/AST/ExprClassification.cpp @@ -109,7 +109,6 @@ static Cl::Kinds ClassifyInternal(ASTContext &Ctx, const Expr *E) { case Expr::CXXThrowExprClass: case Expr::ShuffleVectorExprClass: case Expr::IntegerLiteralClass: - case Expr::ObjCSuperExprClass: case Expr::CharacterLiteralClass: case Expr::AddrLabelExprClass: case Expr::CXXDeleteExprClass: diff --git a/lib/AST/ExprConstant.cpp b/lib/AST/ExprConstant.cpp index 69a008fdc5..715d30ead0 100644 --- a/lib/AST/ExprConstant.cpp +++ b/lib/AST/ExprConstant.cpp @@ -2468,7 +2468,6 @@ static ICEDiag CheckICE(const Expr* E, ASTContext &Ctx) { case Expr::ObjCIvarRefExprClass: case Expr::ObjCPropertyRefExprClass: case Expr::ObjCImplicitSetterGetterRefExprClass: - case Expr::ObjCSuperExprClass: case Expr::ObjCIsaExprClass: case Expr::ShuffleVectorExprClass: case Expr::BlockExprClass: diff --git a/lib/AST/StmtDumper.cpp b/lib/AST/StmtDumper.cpp index 5c236a45a6..8b3ad5a61f 100644 --- a/lib/AST/StmtDumper.cpp +++ b/lib/AST/StmtDumper.cpp @@ -159,7 +159,6 @@ namespace { void VisitObjCImplicitSetterGetterRefExpr( ObjCImplicitSetterGetterRefExpr *Node); void VisitObjCIvarRefExpr(ObjCIvarRefExpr *Node); - void VisitObjCSuperExpr(ObjCSuperExpr *Node); }; } @@ -606,8 +605,11 @@ void StmtDumper::VisitObjCProtocolExpr(ObjCProtocolExpr *Node) { void StmtDumper::VisitObjCPropertyRefExpr(ObjCPropertyRefExpr *Node) { DumpExpr(Node); - - OS << " Kind=PropertyRef Property=\"" << Node->getProperty() << '"'; + if (Node->isSuperReceiver()) + OS << " Kind=PropertyRef Property=\"" << Node->getProperty() << '"' + << " super"; + else + OS << " Kind=PropertyRef Property=\"" << Node->getProperty() << '"'; } void StmtDumper::VisitObjCImplicitSetterGetterRefExpr( @@ -624,11 +626,8 @@ void StmtDumper::VisitObjCImplicitSetterGetterRefExpr( else OS << "(null)"; OS << "\""; -} - -void StmtDumper::VisitObjCSuperExpr(ObjCSuperExpr *Node) { - DumpExpr(Node); - OS << " super"; + if (Node->isSuperReceiver()) + OS << " super"; } //===----------------------------------------------------------------------===// diff --git a/lib/AST/StmtPrinter.cpp b/lib/AST/StmtPrinter.cpp index 2fc08dabf8..51289b2273 100644 --- a/lib/AST/StmtPrinter.cpp +++ b/lib/AST/StmtPrinter.cpp @@ -509,16 +509,21 @@ void StmtPrinter::VisitObjCIvarRefExpr(ObjCIvarRefExpr *Node) { } void StmtPrinter::VisitObjCPropertyRefExpr(ObjCPropertyRefExpr *Node) { - if (Node->getBase()) { + if (Node->isSuperReceiver()) + OS << "super."; + else if (Node->getBase()) { PrintExpr(Node->getBase()); OS << "."; } + OS << Node->getProperty()->getName(); } void StmtPrinter::VisitObjCImplicitSetterGetterRefExpr( ObjCImplicitSetterGetterRefExpr *Node) { - if (Node->getBase()) { + if (Node->isSuperReceiver()) + OS << "super."; + else if (Node->getBase()) { PrintExpr(Node->getBase()); OS << "."; } @@ -1298,9 +1303,6 @@ void StmtPrinter::VisitObjCMessageExpr(ObjCMessageExpr *Mess) { OS << "]"; } -void StmtPrinter::VisitObjCSuperExpr(ObjCSuperExpr *) { - OS << "super"; -} void StmtPrinter::VisitBlockExpr(BlockExpr *Node) { BlockDecl *BD = Node->getBlockDecl(); diff --git a/lib/AST/StmtProfile.cpp b/lib/AST/StmtProfile.cpp index 607cf213db..3f17a2b471 100644 --- a/lib/AST/StmtProfile.cpp +++ b/lib/AST/StmtProfile.cpp @@ -863,6 +863,10 @@ void StmtProfiler::VisitObjCIvarRefExpr(ObjCIvarRefExpr *S) { void StmtProfiler::VisitObjCPropertyRefExpr(ObjCPropertyRefExpr *S) { VisitExpr(S); VisitDecl(S->getProperty()); + if (S->isSuperReceiver()) { + ID.AddBoolean(S->isSuperReceiver()); + VisitType(S->getSuperType()); + } } void StmtProfiler::VisitObjCImplicitSetterGetterRefExpr( @@ -871,6 +875,10 @@ void StmtProfiler::VisitObjCImplicitSetterGetterRefExpr( VisitDecl(S->getGetterMethod()); VisitDecl(S->getSetterMethod()); VisitDecl(S->getInterfaceDecl()); + if (S->isSuperReceiver()) { + ID.AddBoolean(S->isSuperReceiver()); + VisitType(S->getSuperType()); + } } void StmtProfiler::VisitObjCMessageExpr(ObjCMessageExpr *S) { @@ -879,10 +887,6 @@ void StmtProfiler::VisitObjCMessageExpr(ObjCMessageExpr *S) { VisitDecl(S->getMethodDecl()); } -void StmtProfiler::VisitObjCSuperExpr(ObjCSuperExpr *S) { - VisitExpr(S); -} - void StmtProfiler::VisitObjCIsaExpr(ObjCIsaExpr *S) { VisitExpr(S); ID.AddBoolean(S->isArrow()); diff --git a/lib/Checker/GRExprEngine.cpp b/lib/Checker/GRExprEngine.cpp index 0c3a7bbc15..babea205be 100644 --- a/lib/Checker/GRExprEngine.cpp +++ b/lib/Checker/GRExprEngine.cpp @@ -830,7 +830,6 @@ void GRExprEngine::Visit(const Stmt* S, ExplodedNode* Pred, case Stmt::ObjCProtocolExprClass: case Stmt::ObjCSelectorExprClass: case Stmt::ObjCStringLiteralClass: - case Stmt::ObjCSuperExprClass: case Stmt::ParenListExprClass: case Stmt::PredefinedExprClass: case Stmt::ShuffleVectorExprClass: diff --git a/lib/CodeGen/CGBlocks.cpp b/lib/CodeGen/CGBlocks.cpp index 35a2ada974..ca78781ec6 100644 --- a/lib/CodeGen/CGBlocks.cpp +++ b/lib/CodeGen/CGBlocks.cpp @@ -122,12 +122,19 @@ static void CollectBlockDeclRefInfo(const Stmt *S, CGBlockInfo &Info) { E->getReceiverKind() == ObjCMessageExpr::SuperInstance) Info.NeedsObjCSelf = true; } - - // Getter/setter uses may also cause implicit super references, - // which we can check for with: - else if (isa<ObjCSuperExpr>(S)) - Info.NeedsObjCSelf = true; - + else if (const ObjCPropertyRefExpr *PE = dyn_cast<ObjCPropertyRefExpr>(S)) { + // Getter/setter uses may also cause implicit super references, + // which we can check for with: + if (PE->isSuperReceiver()) + Info.NeedsObjCSelf = true; + } + else if (const ObjCImplicitSetterGetterRefExpr *IE = + dyn_cast<ObjCImplicitSetterGetterRefExpr>(S)) { + // Getter/setter uses may also cause implicit super references, + // which we can check for with: + if (IE->isSuperReceiver()) + Info.NeedsObjCSelf = true; + } else if (isa<CXXThisExpr>(S)) Info.CXXThisRef = cast<CXXThisExpr>(S); } diff --git a/lib/CodeGen/CGExpr.cpp b/lib/CodeGen/CGExpr.cpp index e4ed5d64d9..186c5ff428 100644 --- a/lib/CodeGen/CGExpr.cpp +++ b/lib/CodeGen/CGExpr.cpp @@ -552,9 +552,6 @@ LValue CodeGenFunction::EmitLValue(const Expr *E) { return EmitObjCPropertyRefLValue(cast<ObjCPropertyRefExpr>(E)); case Expr::ObjCImplicitSetterGetterRefExprClass: return EmitObjCKVCRefLValue(cast<ObjCImplicitSetterGetterRefExpr>(E)); - case Expr::ObjCSuperExprClass: - return EmitObjCSuperExprLValue(cast<ObjCSuperExpr>(E)); - case Expr::StmtExprClass: return EmitStmtExprLValue(cast<StmtExpr>(E)); case Expr::UnaryOperatorClass: @@ -2082,10 +2079,6 @@ LValue CodeGenFunction::EmitObjCKVCRefLValue( return LValue::MakeKVCRef(E, E->getType().getCVRQualifiers()); } -LValue CodeGenFunction::EmitObjCSuperExprLValue(const ObjCSuperExpr *E) { - return EmitUnsupportedLValue(E, "use of super"); -} - LValue CodeGenFunction::EmitStmtExprLValue(const StmtExpr *E) { // Can only get l-value for message expression returning aggregate type RValue RV = EmitAnyExprToTemp(E); diff --git a/lib/CodeGen/CGObjC.cpp b/lib/CodeGen/CGObjC.cpp index 8abcbea5d0..7c2dfe8b23 100644 --- a/lib/CodeGen/CGObjC.cpp +++ b/lib/CodeGen/CGObjC.cpp @@ -534,7 +534,7 @@ RValue CodeGenFunction::EmitObjCPropertyGet(const Expr *Exp, // FIXME: Split it into two separate routines. if (const ObjCPropertyRefExpr *E = dyn_cast<ObjCPropertyRefExpr>(Exp)) { Selector S = E->getProperty()->getGetterName(); - if (isa<ObjCSuperExpr>(E->getBase())) + if (E->isSuperReceiver()) return EmitObjCSuperPropertyGet(E, S, Return); return CGM.getObjCRuntime(). GenerateMessageSend(*this, Return, Exp->getType(), S, @@ -548,7 +548,7 @@ RValue CodeGenFunction::EmitObjCPropertyGet(const Expr *Exp, if (KE->getInterfaceDecl()) { const ObjCInterfaceDecl *OID = KE->getInterfaceDecl(); Receiver = CGM.getObjCRuntime().GetClass(Builder, OID); - } else if (isa<ObjCSuperExpr>(KE->getBase())) + } else if (KE->isSuperReceiver()) return EmitObjCSuperPropertyGet(KE, S, Return); else Receiver = EmitScalarExpr(KE->getBase()); @@ -586,7 +586,7 @@ void CodeGenFunction::EmitObjCPropertySet(const Expr *Exp, // FIXME: Split it into two separate routines. if (const ObjCPropertyRefExpr *E = dyn_cast<ObjCPropertyRefExpr>(Exp)) { Selector S = E->getProperty()->getSetterName(); - if (isa<ObjCSuperExpr>(E->getBase())) { + if (E->isSuperReceiver()) { EmitObjCSuperPropertySet(E, S, Src); return; } @@ -605,7 +605,7 @@ void CodeGenFunction::EmitObjCPropertySet(const Expr *Exp, if (E->getInterfaceDecl()) { const ObjCInterfaceDecl *OID = E->getInterfaceDecl(); Receiver = CGM.getObjCRuntime().GetClass(Builder, OID); - } else if (isa<ObjCSuperExpr>(E->getBase())) { + } else if (E->isSuperReceiver()) { EmitObjCSuperPropertySet(E, S, Src); return; } else diff --git a/lib/CodeGen/CodeGenFunction.h b/lib/CodeGen/CodeGenFunction.h index cb9274388e..4e64319ae5 100644 --- a/lib/CodeGen/CodeGenFunction.h +++ b/lib/CodeGen/CodeGenFunction.h @@ -1439,7 +1439,6 @@ public: LValue EmitObjCIvarRefLValue(const ObjCIvarRefExpr *E); LValue EmitObjCPropertyRefLValue(const ObjCPropertyRefExpr *E); LValue EmitObjCKVCRefLValue(const ObjCImplicitSetterGetterRefExpr *E); - LValue EmitObjCSuperExprLValue(const ObjCSuperExpr *E); LValue EmitStmtExprLValue(const StmtExpr *E); LValue EmitPointerToDataMemberBinaryExpr(const BinaryOperator *E); LValue EmitObjCSelectorLValue(const ObjCSelectorExpr *E); diff --git a/lib/CodeGen/Mangle.cpp b/lib/CodeGen/Mangle.cpp index 1cf3211b70..36c908b099 100644 --- a/lib/CodeGen/Mangle.cpp +++ b/lib/CodeGen/Mangle.cpp @@ -1610,7 +1610,6 @@ void CXXNameMangler::mangleExpression(const Expr *E, unsigned Arity) { case Expr::ObjCProtocolExprClass: case Expr::ObjCSelectorExprClass: case Expr::ObjCStringLiteralClass: - case Expr::ObjCSuperExprClass: case Expr::OffsetOfExprClass: case Expr::PredefinedExprClass: case Expr::ShuffleVectorExprClass: diff --git a/lib/Frontend/StmtXML.cpp b/lib/Frontend/StmtXML.cpp index b6607349d7..fdd40b15c9 100644 --- a/lib/Frontend/StmtXML.cpp +++ b/lib/Frontend/StmtXML.cpp @@ -150,7 +150,6 @@ namespace { void VisitObjCImplicitSetterGetterRefExpr( ObjCImplicitSetterGetterRefExpr *Node); void VisitObjCIvarRefExpr(ObjCIvarRefExpr *Node); - void VisitObjCSuperExpr(ObjCSuperExpr *Node); #endif }; } @@ -428,11 +427,6 @@ void StmtXML::VisitObjCImplicitSetterGetterRefExpr( Doc.addAttribute("Setter", Setter ? Setter->getSelector().getAsString().c_str() : "(null)"); } -void StmtXML::VisitObjCSuperExpr(ObjCSuperExpr *Node) { - DumpExpr(Node); - Doc.addAttribute("super", "1"); -} - void StmtXML::VisitObjCIvarRefExpr(ObjCIvarRefExpr *Node) { DumpExpr(Node); Doc.addAttribute("kind", Node->getDecl()->getDeclKindName()); diff --git a/lib/Rewrite/RewriteObjC.cpp b/lib/Rewrite/RewriteObjC.cpp index 339b7d1640..8532bc7f13 100644 --- a/lib/Rewrite/RewriteObjC.cpp +++ b/lib/Rewrite/RewriteObjC.cpp @@ -1209,6 +1209,9 @@ Stmt *RewriteObjC::RewritePropertyOrImplicitSetter(BinaryOperator *BinOp, Expr * QualType Ty; Selector Sel; Stmt *Receiver; + bool Super = false; + QualType SuperTy; + SourceLocation SuperLocation; // Synthesize a ObjCMessageExpr from a ObjCPropertyRefExpr or ObjCImplicitSetterGetterRefExpr. // This allows us to reuse all the fun and games in SynthMessageExpr(). if (ObjCPropertyRefExpr *PropRefExpr = dyn_cast<ObjCPropertyRefExpr>(BinOp->getLHS())) { @@ -1216,14 +1219,26 @@ Stmt *RewriteObjC::RewritePropertyOrImplicitSetter(BinaryOperator *BinOp, Expr * OMD = PDecl->getSetterMethodDecl(); Ty = PDecl->getType(); Sel = PDecl->getSetterName(); - Receiver = PropRefExpr->getBase(); + Super = PropRefExpr->isSuperReceiver(); + if (!Super) + Receiver = PropRefExpr->getBase(); + else { + SuperTy = PropRefExpr->getSuperType(); + SuperLocation = PropRefExpr->getSuperLocation(); + } } else if (ObjCImplicitSetterGetterRefExpr *ImplicitRefExpr = dyn_cast<ObjCImplicitSetterGetterRefExpr>(BinOp->getLHS())) { OMD = ImplicitRefExpr->getSetterMethod(); Sel = OMD->getSelector(); Ty = ImplicitRefExpr->getType(); - Receiver = ImplicitRefExpr->getBase(); + Super = ImplicitRefExpr->isSuperReceiver(); + if (!Super) + Receiver = ImplicitRefExpr->getBase(); + else { + SuperTy = ImplicitRefExpr->getSuperType(); + SuperLocation = ImplicitRefExpr->getSuperLocation(); + } } assert(OMD && "RewritePropertyOrImplicitSetter - null OMD"); @@ -1236,13 +1251,13 @@ Stmt *RewriteObjC::RewritePropertyOrImplicitSetter(BinaryOperator *BinOp, Expr * Receiver = PropGetters[Exp]; ObjCMessageExpr *MsgExpr; - if (isa<ObjCSuperExpr>(Receiver)) + if (Super) MsgExpr = ObjCMessageExpr::Create(*Context, Ty.getNonReferenceType(), /*FIXME?*/SourceLocation(), - Receiver->getLocStart(), + SuperLocation, /*IsInstanceSuper=*/true, - cast<Expr>(Receiver)->getType(), + SuperTy, Sel, OMD, &ExprVec[0], 1, /*FIXME:*/SourceLocation()); @@ -1272,20 +1287,35 @@ Stmt *RewriteObjC::RewritePropertyOrImplicitGetter(Expr *PropOrGetterRefExpr) { ObjCMethodDecl *OMD = 0; QualType Ty; Selector Sel; + bool Super = false; + QualType SuperTy; + SourceLocation SuperLocation; if (ObjCPropertyRefExpr *PropRefExpr = dyn_cast<ObjCPropertyRefExpr>(PropOrGetterRefExpr)) { ObjCPropertyDecl *PDecl = PropRefExpr->getProperty(); OMD = PDecl->getGetterMethodDecl(); - Receiver = PropRefExpr->getBase(); Ty = PDecl->getType(); Sel = PDecl->getGetterName(); + Super = PropRefExpr->isSuperReceiver(); + if (!Super) + Receiver = PropRefExpr->getBase(); + else { + SuperTy = PropRefExpr->getSuperType(); + SuperLocation = PropRefExpr->getSuperLocation(); + } } else if (ObjCImplicitSetterGetterRefExpr *ImplicitRefExpr = dyn_cast<ObjCImplicitSetterGetterRefExpr>(PropOrGetterRefExpr)) { OMD = ImplicitRefExpr->getGetterMethod(); - Receiver = ImplicitRefExpr->getBase(); Sel = OMD->getSelector(); Ty = ImplicitRefExpr->getType(); + Super = ImplicitRefExpr->isSuperReceiver(); + if (!Super) + Receiver = ImplicitRefExpr->getBase(); + else { + SuperTy = ImplicitRefExpr->getSuperType(); + SuperLocation = ImplicitRefExpr->getSuperLocation(); + } } assert (OMD && "RewritePropertyOrImplicitGetter - OMD is null"); @@ -1296,13 +1326,13 @@ Stmt *RewriteObjC::RewritePropertyOrImplicitGetter(Expr *PropOrGetterRefExpr) { Receiver = PropGetters[Exp]; ObjCMessageExpr *MsgExpr; - if (isa<ObjCSuperExpr>(Receiver)) + if (Super) MsgExpr = ObjCMessageExpr::Create(*Context, Ty.getNonReferenceType(), - /*FIXME:*/SourceLocation(), - Receiver->getLocStart(), + /*FIXME?*/SourceLocation(), + SuperLocation, /*IsInstanceSuper=*/true, - cast<Expr>(Receiver)->getType(), + SuperTy, Sel, OMD, 0, 0, /*FIXME:*/SourceLocation()); diff --git a/lib/Sema/SemaExpr.cpp b/lib/Sema/SemaExpr.cpp index 609465c505..10225b6138 100644 --- a/lib/Sema/SemaExpr.cpp +++ b/lib/Sema/SemaExpr.cpp @@ -3307,7 +3307,8 @@ Sema::LookupMemberExpr(LookupResult &R, Expr *&BaseExpr, return ExprError(); return Owned(new (Context) ObjCPropertyRefExpr(PD, PD->getType(), - |