From: Fariborz Jahanian Date: Sun, 22 Feb 2009 18:40:18 +0000 (+0000) Subject: More objc gc work. Match gcc's treatment of ivar access X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=44baa8abba2a1552b6b50bf750a8750ab9da9f76;p=clang More objc gc work. Match gcc's treatment of ivar access true a local pointer to objective-c object in generating write barriers. git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@65290 91177308-0d34-0410-b5e6-96231b3b80d8 --- diff --git a/include/clang/AST/Expr.h b/include/clang/AST/Expr.h index 3745866f75..cfd13b2fbb 100644 --- a/include/clang/AST/Expr.h +++ b/include/clang/AST/Expr.h @@ -238,6 +238,10 @@ public: /// duration. This means that the address of this expression is a link-time /// constant. bool hasGlobalStorage() const; + + /// isOBJCGCCandidate - Return true if this expression may be used in a read/ + /// write barrier. + bool isOBJCGCCandidate() const; /// IgnoreParens - Ignore parentheses. If this Expr is a ParenExpr, return /// its subexpression. If that subexpression is also a ParenExpr, diff --git a/lib/AST/Expr.cpp b/lib/AST/Expr.cpp index f27419c0a2..a621119dae 100644 --- a/lib/AST/Expr.cpp +++ b/lib/AST/Expr.cpp @@ -745,6 +745,33 @@ bool Expr::hasGlobalStorage() const { } } +/// isOBJCGCCandidate - Check if an expression is objc gc'able. +/// +bool Expr::isOBJCGCCandidate() const { + switch (getStmtClass()) { + default: + return false; + case ObjCIvarRefExprClass: + return true; + case ParenExprClass: + return cast(this)->getSubExpr()->isOBJCGCCandidate(); + case ImplicitCastExprClass: + return cast(this)->getSubExpr()->isOBJCGCCandidate(); + case DeclRefExprClass: + case QualifiedDeclRefExprClass: { + const Decl *D = cast(this)->getDecl(); + if (const VarDecl *VD = dyn_cast(D)) + return VD->hasGlobalStorage(); + return false; + } + case MemberExprClass: { + const MemberExpr *M = cast(this); + return !M->isArrow() && M->getBase()->isOBJCGCCandidate(); + } + case ArraySubscriptExprClass: + return cast(this)->getBase()->isOBJCGCCandidate(); + } +} Expr* Expr::IgnoreParens() { Expr* E = this; while (ParenExpr* P = dyn_cast(E)) diff --git a/lib/CodeGen/CGExpr.cpp b/lib/CodeGen/CGExpr.cpp index 2348a11f7b..c96265242a 100644 --- a/lib/CodeGen/CGExpr.cpp +++ b/lib/CodeGen/CGExpr.cpp @@ -782,7 +782,7 @@ LValue CodeGenFunction::EmitArraySubscriptExpr(const ArraySubscriptExpr *E) { getContext().getObjCGCAttrKind(T)); if (getContext().getLangOptions().ObjC1 && getContext().getLangOptions().getGCMode() != LangOptions::NonGC) - LValue::SetObjCNonGC(LV, !E->hasGlobalStorage()); + LValue::SetObjCNonGC(LV, !E->isOBJCGCCandidate()); return LV; }