From: Fariborz Jahanian Date: Mon, 21 Sep 2009 18:54:29 +0000 (+0000) Subject: Miscellanous fixes in generatation of objc gc's write-barriers. X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=fd02ed702e754f8dd0b4c979325ba99c2234f270;p=clang Miscellanous fixes in generatation of objc gc's write-barriers. git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@82472 91177308-0d34-0410-b5e6-96231b3b80d8 --- diff --git a/lib/CodeGen/CGExpr.cpp b/lib/CodeGen/CGExpr.cpp index 43224bb424..157369d754 100644 --- a/lib/CodeGen/CGExpr.cpp +++ b/lib/CodeGen/CGExpr.cpp @@ -697,7 +697,7 @@ void setObjCGCLValueClass(const ASTContext &Ctx, const Expr *E, LValue &LV) { if (isa(E)) { LV.SetObjCIvar(LV, true); - LV.SetObjCIvarArray(LV, E->getType()->isArrayType()); + LV.SetObjCArray(LV, E->getType()->isArrayType()); return; } if (const DeclRefExpr *Exp = dyn_cast(E)) { @@ -706,6 +706,7 @@ void setObjCGCLValueClass(const ASTContext &Ctx, const Expr *E, LValue &LV) { VD->isFileVarDecl()) LV.SetGlobalObjCRef(LV, true); } + LV.SetObjCArray(LV, E->getType()->isArrayType()); } else if (const UnaryOperator *Exp = dyn_cast(E)) setObjCGCLValueClass(Ctx, Exp->getSubExpr(), LV); @@ -717,17 +718,20 @@ void setObjCGCLValueClass(const ASTContext &Ctx, const Expr *E, LValue &LV) { setObjCGCLValueClass(Ctx, Exp->getSubExpr(), LV); else if (const ArraySubscriptExpr *Exp = dyn_cast(E)) { setObjCGCLValueClass(Ctx, Exp->getBase(), LV); - if (LV.isObjCIvar() && !LV.isObjCIvarArray()) { + if (LV.isObjCIvar() && !LV.isObjCArray()) // Using array syntax to assigning to what an ivar points to is not // same as assigning to the ivar itself. {id *Names;} Names[i] = 0; LV.SetObjCIvar(LV, false); - } + else if (LV.isGlobalObjCRef() && !LV.isObjCArray()) + // Using array syntax to assigning to what global points to is not + // same as assigning to the global itself. {id *G;} G[i] = 0; + LV.SetGlobalObjCRef(LV, false); } else if (const MemberExpr *Exp = dyn_cast(E)) { setObjCGCLValueClass(Ctx, Exp->getBase(), LV); // We don't know if member is an 'ivar', but this flag is looked at // only in the context of LV.isObjCIvar(). - LV.SetObjCIvarArray(LV, E->getType()->isArrayType()); + LV.SetObjCArray(LV, E->getType()->isArrayType()); } } @@ -1130,19 +1134,11 @@ LValue CodeGenFunction::EmitLValueForField(llvm::Value* BaseValue, } if (Field->getType()->isReferenceType()) V = Builder.CreateLoad(V, "tmp"); - - QualType::GCAttrTypes attr = QualType::GCNone; - if (CGM.getLangOptions().ObjC1 && - CGM.getLangOptions().getGCMode() != LangOptions::NonGC) { - QualType Ty = Field->getType(); - attr = Ty.getObjCGCAttr(); - if (attr != QualType::GCNone) { - // __weak attribute on a field is ignored. - if (attr == QualType::Weak) - attr = QualType::GCNone; - } else if (Ty->isObjCObjectPointerType()) - attr = QualType::Strong; - } + QualType::GCAttrTypes attr = getContext().getObjCGCAttrKind(Field->getType()); + // __weak attribute on a field is ignored. + if (attr == QualType::Weak) + attr = QualType::GCNone; + LValue LV = LValue::MakeAddr(V, Field->getType().getCVRQualifiers()|CVRQualifiers, diff --git a/lib/CodeGen/CGValue.h b/lib/CodeGen/CGValue.h index af034a7ad5..d9dd94d4a6 100644 --- a/lib/CodeGen/CGValue.h +++ b/lib/CodeGen/CGValue.h @@ -154,7 +154,7 @@ class LValue { bool Ivar:1; // objective-c's ivar is an array - bool IvarArray:1; + bool ObjIsArray:1; // LValue is non-gc'able for any reason, including being a parameter or local // variable. @@ -176,7 +176,7 @@ private: // FIXME: Convenient place to set objc flags to 0. This should really be // done in a user-defined constructor instead. R.ObjCType = None; - R.Ivar = R.IvarArray = R.NonGC = R.GlobalObjCRef = false; + R.Ivar = R.ObjIsArray = R.NonGC = R.GlobalObjCRef = false; } public: @@ -195,7 +195,7 @@ public: } bool isObjCIvar() const { return Ivar; } - bool isObjCIvarArray() const { return IvarArray; } + bool isObjCArray() const { return ObjIsArray; } bool isNonGC () const { return NonGC; } bool isGlobalObjCRef() const { return GlobalObjCRef; } bool isObjCWeak() const { return ObjCType == Weak; } @@ -206,8 +206,8 @@ public: static void SetObjCIvar(LValue& R, bool iValue) { R.Ivar = iValue; } - static void SetObjCIvarArray(LValue& R, bool iValue) { - R.IvarArray = iValue; + static void SetObjCArray(LValue& R, bool iValue) { + R.ObjIsArray = iValue; } static void SetGlobalObjCRef(LValue& R, bool iValue) { R.GlobalObjCRef = iValue; diff --git a/test/CodeGenObjC/objc2-new-gc-api-strongcast.m b/test/CodeGenObjC/objc2-new-gc-api-strongcast.m new file mode 100644 index 0000000000..eb74317d8f --- /dev/null +++ b/test/CodeGenObjC/objc2-new-gc-api-strongcast.m @@ -0,0 +1,26 @@ +// RUN: clang-cc -triple x86_64-apple-darwin10 -fblocks -fnext-runtime -fobjc-gc -fobjc-newgc-api -emit-llvm -o %t %s && +// RUN: grep -F '@objc_assign_strongCast' %t | count 4 && +// RUN: true + +@interface DSATextSearch @end + +DSATextSearch **_uniqueIdToIdentifierArray = ((void *)0); +void foo (int _nextId) +{ + _uniqueIdToIdentifierArray[_nextId] = 0; // objc_assign_strongCast +} + +typedef struct { + unsigned long state; + id *itemsPtr; + void (^bp)(); + unsigned long *mutationsPtr; + unsigned long extra[5]; +} NSFastEnumerationState; + +void foo1 (NSFastEnumerationState * state) +{ + state->itemsPtr = 0; + state->bp = ^{}; +} +