Kill the KVC l-value kind and calculate the base expression when emitting

the l-value.

llvm-svn: 120884
This commit is contained in:
John McCall 2010-12-04 02:32:38 +00:00
parent 7788e5fd64
commit f3eb96fccf
8 changed files with 62 additions and 140 deletions

View File

@ -195,11 +195,9 @@ EmitExprForReferenceBinding(CodeGenFunction &CGF, const Expr *E,
if (E->isLValue()) { if (E->isLValue()) {
// Emit the expression as an lvalue. // Emit the expression as an lvalue.
LValue LV = CGF.EmitLValue(E); LValue LV = CGF.EmitLValue(E);
if (LV.isPropertyRef() || LV.isKVCRef()) { if (LV.isPropertyRef()) {
QualType QT = E->getType(); QualType QT = E->getType();
RValue RV = RValue RV = CGF.EmitLoadOfPropertyRefLValue(LV);
LV.isPropertyRef() ? CGF.EmitLoadOfPropertyRefLValue(LV, QT)
: CGF.EmitLoadOfKVCRefLValue(LV, QT);
assert(RV.isScalar() && "EmitExprForReferenceBinding"); assert(RV.isScalar() && "EmitExprForReferenceBinding");
return RV.getScalarVal(); return RV.getScalarVal();
} }
@ -671,11 +669,8 @@ RValue CodeGenFunction::EmitLoadOfLValue(LValue LV, QualType ExprType) {
if (LV.isBitField()) if (LV.isBitField())
return EmitLoadOfBitfieldLValue(LV, ExprType); return EmitLoadOfBitfieldLValue(LV, ExprType);
if (LV.isPropertyRef()) assert(LV.isPropertyRef() && "Unknown LValue type!");
return EmitLoadOfPropertyRefLValue(LV, ExprType); return EmitLoadOfPropertyRefLValue(LV);
assert(LV.isKVCRef() && "Unknown LValue type!");
return EmitLoadOfKVCRefLValue(LV, ExprType);
} }
RValue CodeGenFunction::EmitLoadOfBitfieldLValue(LValue LV, RValue CodeGenFunction::EmitLoadOfBitfieldLValue(LValue LV,
@ -750,16 +745,6 @@ RValue CodeGenFunction::EmitLoadOfBitfieldLValue(LValue LV,
return RValue::get(Res); return RValue::get(Res);
} }
RValue CodeGenFunction::EmitLoadOfPropertyRefLValue(LValue LV,
QualType ExprType) {
return EmitObjCPropertyGet(LV.getPropertyRefExpr());
}
RValue CodeGenFunction::EmitLoadOfKVCRefLValue(LValue LV,
QualType ExprType) {
return EmitObjCPropertyGet(LV.getKVCRefExpr());
}
// If this is a reference to a subset of the elements of a vector, create an // If this is a reference to a subset of the elements of a vector, create an
// appropriate shufflevector. // appropriate shufflevector.
RValue CodeGenFunction::EmitLoadOfExtVectorElementLValue(LValue LV, RValue CodeGenFunction::EmitLoadOfExtVectorElementLValue(LValue LV,
@ -820,11 +805,8 @@ void CodeGenFunction::EmitStoreThroughLValue(RValue Src, LValue Dst,
if (Dst.isBitField()) if (Dst.isBitField())
return EmitStoreThroughBitfieldLValue(Src, Dst, Ty); return EmitStoreThroughBitfieldLValue(Src, Dst, Ty);
if (Dst.isPropertyRef()) assert(Dst.isPropertyRef() && "Unknown LValue type");
return EmitStoreThroughPropertyRefLValue(Src, Dst, Ty); return EmitStoreThroughPropertyRefLValue(Src, Dst);
assert(Dst.isKVCRef() && "Unknown LValue type");
return EmitStoreThroughKVCRefLValue(Src, Dst, Ty);
} }
if (Dst.isObjCWeak() && !Dst.isNonGC()) { if (Dst.isObjCWeak() && !Dst.isNonGC()) {
@ -969,18 +951,6 @@ void CodeGenFunction::EmitStoreThroughBitfieldLValue(RValue Src, LValue Dst,
} }
} }
void CodeGenFunction::EmitStoreThroughPropertyRefLValue(RValue Src,
LValue Dst,
QualType Ty) {
EmitObjCPropertySet(Dst.getPropertyRefExpr(), Src);
}
void CodeGenFunction::EmitStoreThroughKVCRefLValue(RValue Src,
LValue Dst,
QualType Ty) {
EmitObjCPropertySet(Dst.getKVCRefExpr(), Src);
}
void CodeGenFunction::EmitStoreThroughExtVectorComponentLValue(RValue Src, void CodeGenFunction::EmitStoreThroughExtVectorComponentLValue(RValue Src,
LValue Dst, LValue Dst,
QualType Ty) { QualType Ty) {
@ -1569,7 +1539,7 @@ LValue CodeGenFunction::EmitMemberExpr(const MemberExpr *E) {
BaseQuals = PTy->getPointeeType().getQualifiers(); BaseQuals = PTy->getPointeeType().getQualifiers();
} else if (ObjCPropertyRefExpr *PRE } else if (ObjCPropertyRefExpr *PRE
= dyn_cast<ObjCPropertyRefExpr>(BaseExpr->IgnoreParens())) { = dyn_cast<ObjCPropertyRefExpr>(BaseExpr->IgnoreParens())) {
RValue RV = EmitObjCPropertyGet(PRE); RValue RV = EmitLoadOfPropertyRefLValue(EmitObjCPropertyRefLValue(PRE));
BaseValue = RV.getAggregateAddr(); BaseValue = RV.getAggregateAddr();
BaseQuals = BaseExpr->getType().getQualifiers(); BaseQuals = BaseExpr->getType().getQualifiers();
} else { } else {
@ -1788,11 +1758,9 @@ LValue CodeGenFunction::EmitCastLValue(const CastExpr *E) {
case CK_NoOp: case CK_NoOp:
if (!E->getSubExpr()->isRValue() || E->getType()->isRecordType()) { if (!E->getSubExpr()->isRValue() || E->getType()->isRecordType()) {
LValue LV = EmitLValue(E->getSubExpr()); LValue LV = EmitLValue(E->getSubExpr());
if (LV.isPropertyRef() || LV.isKVCRef()) { if (LV.isPropertyRef()) {
QualType QT = E->getSubExpr()->getType(); QualType QT = E->getSubExpr()->getType();
RValue RV = RValue RV = EmitLoadOfPropertyRefLValue(LV);
LV.isPropertyRef() ? EmitLoadOfPropertyRefLValue(LV, QT)
: EmitLoadOfKVCRefLValue(LV, QT);
assert(RV.isAggregate()); assert(RV.isAggregate());
llvm::Value *V = RV.getAggregateAddr(); llvm::Value *V = RV.getAggregateAddr();
return MakeAddrLValue(V, QT); return MakeAddrLValue(V, QT);
@ -1861,11 +1829,9 @@ LValue CodeGenFunction::EmitCastLValue(const CastExpr *E) {
LValue LV = EmitLValue(E->getSubExpr()); LValue LV = EmitLValue(E->getSubExpr());
llvm::Value *This; llvm::Value *This;
if (LV.isPropertyRef() || LV.isKVCRef()) { if (LV.isPropertyRef()) {
QualType QT = E->getSubExpr()->getType(); QualType QT = E->getSubExpr()->getType();
RValue RV = RValue RV = EmitLoadOfPropertyRefLValue(LV);
LV.isPropertyRef() ? EmitLoadOfPropertyRefLValue(LV, QT)
: EmitLoadOfKVCRefLValue(LV, QT);
assert (!RV.isScalar() && "EmitCastLValue"); assert (!RV.isScalar() && "EmitCastLValue");
This = RV.getAggregateAddr(); This = RV.getAggregateAddr();
} }
@ -2107,9 +2073,15 @@ CodeGenFunction::EmitObjCPropertyRefLValue(const ObjCPropertyRefExpr *E) {
// This is a special l-value that just issues sends when we load or // This is a special l-value that just issues sends when we load or
// store through it. // store through it.
if (E->isImplicitProperty()) // For certain base kinds, we need to emit the base immediately.
return LValue::MakeKVCRef(E, E->getType().getCVRQualifiers()); llvm::Value *Base;
return LValue::MakePropertyRef(E, E->getType().getCVRQualifiers()); if (E->isSuperReceiver())
Base = 0;
else if (E->isClassReceiver())
Base = CGM.getObjCRuntime().GetClass(Builder, E->getClassReceiver());
else
Base = EmitScalarExpr(E->getBase());
return LValue::MakePropertyRef(E, Base);
} }
LValue CodeGenFunction::EmitStmtExprLValue(const StmtExpr *E) { LValue CodeGenFunction::EmitStmtExprLValue(const StmtExpr *E) {

View File

@ -349,7 +349,8 @@ void AggExprEmitter::VisitObjCMessageExpr(ObjCMessageExpr *E) {
} }
void AggExprEmitter::VisitObjCPropertyRefExpr(ObjCPropertyRefExpr *E) { void AggExprEmitter::VisitObjCPropertyRefExpr(ObjCPropertyRefExpr *E) {
RValue RV = CGF.EmitObjCPropertyGet(E, getReturnValueSlot()); RValue RV = CGF.EmitLoadOfPropertyRefLValue(CGF.EmitObjCPropertyRefLValue(E),
getReturnValueSlot());
EmitGCMove(E, RV); EmitGCMove(E, RV);
} }
@ -388,11 +389,7 @@ void AggExprEmitter::VisitBinAssign(const BinaryOperator *E) {
if (LHS.isPropertyRef()) { if (LHS.isPropertyRef()) {
AggValueSlot Slot = EnsureSlot(E->getRHS()->getType()); AggValueSlot Slot = EnsureSlot(E->getRHS()->getType());
CGF.EmitAggExpr(E->getRHS(), Slot); CGF.EmitAggExpr(E->getRHS(), Slot);
CGF.EmitObjCPropertySet(LHS.getPropertyRefExpr(), Slot.asRValue()); CGF.EmitStoreThroughPropertyRefLValue(Slot.asRValue(), LHS);
} else if (LHS.isKVCRef()) {
AggValueSlot Slot = EnsureSlot(E->getRHS()->getType());
CGF.EmitAggExpr(E->getRHS(), Slot);
CGF.EmitObjCPropertySet(LHS.getKVCRefExpr(), Slot.asRValue());
} else { } else {
bool GCollection = false; bool GCollection = false;
if (CGF.getContext().getLangOptions().getGCMode()) if (CGF.getContext().getLangOptions().getGCMode())

View File

@ -124,11 +124,9 @@ RValue CodeGenFunction::EmitCXXMemberCallExpr(const CXXMemberCallExpr *CE,
This = EmitScalarExpr(ME->getBase()); This = EmitScalarExpr(ME->getBase());
else { else {
LValue BaseLV = EmitLValue(ME->getBase()); LValue BaseLV = EmitLValue(ME->getBase());
if (BaseLV.isPropertyRef() || BaseLV.isKVCRef()) { if (BaseLV.isPropertyRef()) {
QualType QT = ME->getBase()->getType(); QualType QT = ME->getBase()->getType();
RValue RV = RValue RV = EmitLoadOfPropertyRefLValue(BaseLV);
BaseLV.isPropertyRef() ? EmitLoadOfPropertyRefLValue(BaseLV, QT)
: EmitLoadOfKVCRefLValue(BaseLV, QT);
This = RV.isScalar() ? RV.getScalarVal() : RV.getAggregateAddr(); This = RV.isScalar() ? RV.getScalarVal() : RV.getAggregateAddr();
} }
else else
@ -242,13 +240,10 @@ CodeGenFunction::EmitCXXOperatorMemberCallExpr(const CXXOperatorCallExpr *E,
"EmitCXXOperatorMemberCallExpr - user declared copy assignment"); "EmitCXXOperatorMemberCallExpr - user declared copy assignment");
LValue LV = EmitLValue(E->getArg(0)); LValue LV = EmitLValue(E->getArg(0));
llvm::Value *This; llvm::Value *This;
if (LV.isPropertyRef() || LV.isKVCRef()) { if (LV.isPropertyRef()) {
AggValueSlot Slot = CreateAggTemp(E->getArg(1)->getType()); AggValueSlot Slot = CreateAggTemp(E->getArg(1)->getType());
EmitAggExpr(E->getArg(1), Slot); EmitAggExpr(E->getArg(1), Slot);
if (LV.isPropertyRef()) EmitStoreThroughPropertyRefLValue(Slot.asRValue(), LV);
EmitObjCPropertySet(LV.getPropertyRefExpr(), Slot.asRValue());
else
EmitObjCPropertySet(LV.getKVCRefExpr(), Slot.asRValue());
return RValue::getAggregate(0, false); return RValue::getAggregate(0, false);
} }
else else
@ -267,11 +262,9 @@ CodeGenFunction::EmitCXXOperatorMemberCallExpr(const CXXOperatorCallExpr *E,
FPT->isVariadic()); FPT->isVariadic());
LValue LV = EmitLValue(E->getArg(0)); LValue LV = EmitLValue(E->getArg(0));
llvm::Value *This; llvm::Value *This;
if (LV.isPropertyRef() || LV.isKVCRef()) { if (LV.isPropertyRef()) {
QualType QT = E->getArg(0)->getType(); QualType QT = E->getArg(0)->getType();
RValue RV = RValue RV = EmitLoadOfPropertyRefLValue(LV);
LV.isPropertyRef() ? EmitLoadOfPropertyRefLValue(LV, QT)
: EmitLoadOfKVCRefLValue(LV, QT);
assert (!RV.isScalar() && "EmitCXXOperatorMemberCallExpr"); assert (!RV.isScalar() && "EmitCXXOperatorMemberCallExpr");
This = RV.getAggregateAddr(); This = RV.getAggregateAddr();
} }

View File

@ -64,11 +64,8 @@ public:
if (LV.isSimple()) if (LV.isSimple())
return EmitLoadOfComplex(LV.getAddress(), LV.isVolatileQualified()); return EmitLoadOfComplex(LV.getAddress(), LV.isVolatileQualified());
if (LV.isPropertyRef()) assert(LV.isPropertyRef() && "Unknown LValue type!");
return CGF.EmitObjCPropertyGet(LV.getPropertyRefExpr()).getComplexVal(); return CGF.EmitLoadOfPropertyRefLValue(LV).getComplexVal();
assert(LV.isKVCRef() && "Unknown LValue type!");
return CGF.EmitObjCPropertyGet(LV.getKVCRefExpr()).getComplexVal();
} }
/// EmitLoadOfComplex - Given a pointer to a complex value, emit code to load /// EmitLoadOfComplex - Given a pointer to a complex value, emit code to load
@ -531,11 +528,7 @@ EmitCompoundAssignLValue(const CompoundAssignOperator *E,
// We know the LHS is a complex lvalue. // We know the LHS is a complex lvalue.
ComplexPairTy LHSComplexPair; ComplexPairTy LHSComplexPair;
if (LHS.isPropertyRef()) if (LHS.isPropertyRef())
LHSComplexPair = LHSComplexPair = CGF.EmitLoadOfPropertyRefLValue(LHS).getComplexVal();
CGF.EmitObjCPropertyGet(LHS.getPropertyRefExpr()).getComplexVal();
else if (LHS.isKVCRef())
LHSComplexPair =
CGF.EmitObjCPropertyGet(LHS.getKVCRefExpr()).getComplexVal();
else else
LHSComplexPair = EmitLoadOfComplex(LHS.getAddress(), LHSComplexPair = EmitLoadOfComplex(LHS.getAddress(),
LHS.isVolatileQualified()); LHS.isVolatileQualified());
@ -551,10 +544,7 @@ EmitCompoundAssignLValue(const CompoundAssignOperator *E,
// Store the result value into the LHS lvalue. // Store the result value into the LHS lvalue.
if (LHS.isPropertyRef()) if (LHS.isPropertyRef())
CGF.EmitObjCPropertySet(LHS.getPropertyRefExpr(), CGF.EmitStoreThroughPropertyRefLValue(RValue::getComplex(Result), LHS);
RValue::getComplex(Result));
else if (LHS.isKVCRef())
CGF.EmitObjCPropertySet(LHS.getKVCRefExpr(), RValue::getComplex(Result));
else else
EmitStoreOfComplex(Result, LHS.getAddress(), LHS.isVolatileQualified()); EmitStoreOfComplex(Result, LHS.getAddress(), LHS.isVolatileQualified());
@ -573,7 +563,7 @@ EmitCompoundAssign(const CompoundAssignOperator *E,
return Val; return Val;
// Objective-C property assignment never reloads the value following a store. // Objective-C property assignment never reloads the value following a store.
if (LV.isPropertyRef() || LV.isKVCRef()) if (LV.isPropertyRef())
return Val; return Val;
// If the lvalue is non-volatile, return the computed value of the assignment. // If the lvalue is non-volatile, return the computed value of the assignment.
@ -599,9 +589,7 @@ LValue ComplexExprEmitter::EmitBinAssignLValue(const BinaryOperator *E,
// Store the result value into the LHS lvalue. // Store the result value into the LHS lvalue.
if (LHS.isPropertyRef()) if (LHS.isPropertyRef())
CGF.EmitObjCPropertySet(LHS.getPropertyRefExpr(), RValue::getComplex(Val)); CGF.EmitStoreThroughPropertyRefLValue(RValue::getComplex(Val), LHS);
else if (LHS.isKVCRef())
CGF.EmitObjCPropertySet(LHS.getKVCRefExpr(), RValue::getComplex(Val));
else else
EmitStoreOfComplex(Val, LHS.getAddress(), LHS.isVolatileQualified()); EmitStoreOfComplex(Val, LHS.getAddress(), LHS.isVolatileQualified());
@ -617,7 +605,7 @@ ComplexPairTy ComplexExprEmitter::VisitBinAssign(const BinaryOperator *E) {
return Val; return Val;
// Objective-C property assignment never reloads the value following a store. // Objective-C property assignment never reloads the value following a store.
if (LV.isPropertyRef() || LV.isKVCRef()) if (LV.isPropertyRef())
return Val; return Val;
// If the lvalue is non-volatile, return the computed value of the assignment. // If the lvalue is non-volatile, return the computed value of the assignment.

View File

@ -1127,9 +1127,7 @@ Value *ScalarExprEmitter::EmitCastExpr(CastExpr *CE) {
if (E->Classify(CGF.getContext()).isGLValue()) { if (E->Classify(CGF.getContext()).isGLValue()) {
LValue LV = CGF.EmitLValue(E); LValue LV = CGF.EmitLValue(E);
if (LV.isPropertyRef()) if (LV.isPropertyRef())
CGF.EmitLoadOfPropertyRefLValue(LV, E->getType()); CGF.EmitLoadOfPropertyRefLValue(LV);
else if (LV.isKVCRef())
CGF.EmitLoadOfKVCRefLValue(LV, E->getType());
} }
else else
CGF.EmitAnyExpr(E, AggValueSlot::ignored(), true); CGF.EmitAnyExpr(E, AggValueSlot::ignored(), true);
@ -1583,7 +1581,7 @@ Value *ScalarExprEmitter::EmitCompoundAssign(const CompoundAssignOperator *E,
return RHS; return RHS;
// Objective-C property assignment never reloads the value following a store. // Objective-C property assignment never reloads the value following a store.
if (LHS.isPropertyRef() || LHS.isKVCRef()) if (LHS.isPropertyRef())
return RHS; return RHS;
// If the lvalue is non-volatile, return the computed value of the assignment. // If the lvalue is non-volatile, return the computed value of the assignment.
@ -2183,7 +2181,7 @@ Value *ScalarExprEmitter::VisitBinAssign(const BinaryOperator *E) {
return RHS; return RHS;
// Objective-C property assignment never reloads the value following a store. // Objective-C property assignment never reloads the value following a store.
if (LHS.isPropertyRef() || LHS.isKVCRef()) if (LHS.isPropertyRef())
return RHS; return RHS;
// If the lvalue is non-volatile, return the computed value of the assignment. // If the lvalue is non-volatile, return the computed value of the assignment.

View File

@ -528,8 +528,9 @@ RValue CodeGenFunction::EmitObjCSuperPropertyGet(const Expr *Exp,
} }
RValue CodeGenFunction::EmitObjCPropertyGet(const ObjCPropertyRefExpr *E, RValue CodeGenFunction::EmitLoadOfPropertyRefLValue(LValue LV,
ReturnValueSlot Return) { ReturnValueSlot Return) {
const ObjCPropertyRefExpr *E = LV.getPropertyRefExpr();
QualType ResultType; QualType ResultType;
Selector S; Selector S;
if (E->isExplicitProperty()) { if (E->isExplicitProperty()) {
@ -545,14 +546,9 @@ RValue CodeGenFunction::EmitObjCPropertyGet(const ObjCPropertyRefExpr *E,
if (E->isSuperReceiver()) if (E->isSuperReceiver())
return EmitObjCSuperPropertyGet(E, S, Return); return EmitObjCSuperPropertyGet(E, S, Return);
llvm::Value *Receiver; llvm::Value *Receiver = LV.getPropertyRefBaseAddr();
const ObjCInterfaceDecl *ReceiverClass = 0; const ObjCInterfaceDecl *ReceiverClass
if (E->isClassReceiver()) { = (E->isClassReceiver() ? E->getClassReceiver() : 0);
ReceiverClass = E->getClassReceiver();
Receiver = CGM.getObjCRuntime().GetClass(Builder, ReceiverClass);
} else {
Receiver = EmitScalarExpr(E->getBase());
}
return CGM.getObjCRuntime(). return CGM.getObjCRuntime().
GenerateMessageSend(*this, Return, ResultType, S, GenerateMessageSend(*this, Return, ResultType, S,
Receiver, CallArgList(), ReceiverClass); Receiver, CallArgList(), ReceiverClass);
@ -579,8 +575,9 @@ void CodeGenFunction::EmitObjCSuperPropertySet(const Expr *Exp,
return; return;
} }
void CodeGenFunction::EmitObjCPropertySet(const ObjCPropertyRefExpr *E, void CodeGenFunction::EmitStoreThroughPropertyRefLValue(RValue Src,
RValue Src) { LValue Dst) {
const ObjCPropertyRefExpr *E = Dst.getPropertyRefExpr();
Selector S = E->getSetterSelector(); Selector S = E->getSetterSelector();
QualType ArgType; QualType ArgType;
if (E->isImplicitProperty()) { if (E->isImplicitProperty()) {
@ -596,14 +593,9 @@ void CodeGenFunction::EmitObjCPropertySet(const ObjCPropertyRefExpr *E,
return; return;
} }
const ObjCInterfaceDecl *ReceiverClass = 0; llvm::Value *Receiver = Dst.getPropertyRefBaseAddr();
llvm::Value *Receiver; const ObjCInterfaceDecl *ReceiverClass
if (E->isClassReceiver()) { = (E->isClassReceiver() ? E->getClassReceiver() : 0);
ReceiverClass = E->getClassReceiver();
Receiver = CGM.getObjCRuntime().GetClass(Builder, ReceiverClass);
} else {
Receiver = EmitScalarExpr(E->getBase());
}
CallArgList Args; CallArgList Args;
Args.push_back(std::make_pair(Src, ArgType)); Args.push_back(std::make_pair(Src, ArgType));

View File

@ -108,10 +108,8 @@ class LValue {
VectorElt, // This is a vector element l-value (V[i]), use getVector* VectorElt, // This is a vector element l-value (V[i]), use getVector*
BitField, // This is a bitfield l-value, use getBitfield*. BitField, // This is a bitfield l-value, use getBitfield*.
ExtVectorElt, // This is an extended vector subset, use getExtVectorComp ExtVectorElt, // This is an extended vector subset, use getExtVectorComp
PropertyRef, // This is an Objective-C property reference, use PropertyRef // This is an Objective-C property reference, use
// getPropertyRefExpr // getPropertyRefExpr
KVCRef // This is an objective-c 'implicit' property ref,
// use getKVCRefExpr
} LVType; } LVType;
llvm::Value *V; llvm::Value *V;
@ -177,7 +175,6 @@ public:
bool isBitField() const { return LVType == BitField; } bool isBitField() const { return LVType == BitField; }
bool isExtVectorElt() const { return LVType == ExtVectorElt; } bool isExtVectorElt() const { return LVType == ExtVectorElt; }
bool isPropertyRef() const { return LVType == PropertyRef; } bool isPropertyRef() const { return LVType == PropertyRef; }
bool isKVCRef() const { return LVType == KVCRef; }
bool isVolatileQualified() const { return Quals.hasVolatile(); } bool isVolatileQualified() const { return Quals.hasVolatile(); }
bool isRestrictQualified() const { return Quals.hasRestrict(); } bool isRestrictQualified() const { return Quals.hasRestrict(); }
@ -245,17 +242,15 @@ public:
} }
// property ref lvalue // property ref lvalue
llvm::Value *getPropertyRefBaseAddr() const {
assert(isPropertyRef());
return V;
}
const ObjCPropertyRefExpr *getPropertyRefExpr() const { const ObjCPropertyRefExpr *getPropertyRefExpr() const {
assert(isPropertyRef()); assert(isPropertyRef());
return PropertyRefExpr; return PropertyRefExpr;
} }
// 'implicit' property ref lvalue
const ObjCPropertyRefExpr *getKVCRefExpr() const {
assert(isKVCRef());
return PropertyRefExpr;
}
static LValue MakeAddr(llvm::Value *V, QualType T, unsigned Alignment, static LValue MakeAddr(llvm::Value *V, QualType T, unsigned Alignment,
ASTContext &Context, ASTContext &Context,
llvm::MDNode *TBAAInfo = 0) { llvm::MDNode *TBAAInfo = 0) {
@ -309,20 +304,12 @@ public:
// the lvalue. However, this complicates the code a bit, and I haven't figured // the lvalue. However, this complicates the code a bit, and I haven't figured
// out how to make it go wrong yet. // out how to make it go wrong yet.
static LValue MakePropertyRef(const ObjCPropertyRefExpr *E, static LValue MakePropertyRef(const ObjCPropertyRefExpr *E,
unsigned CVR) { llvm::Value *Base) {
LValue R; LValue R;
R.LVType = PropertyRef; R.LVType = PropertyRef;
R.V = Base;
R.PropertyRefExpr = E; R.PropertyRefExpr = E;
R.Initialize(Qualifiers::fromCVRMask(CVR)); R.Initialize(Qualifiers());
return R;
}
static LValue MakeKVCRef(const ObjCPropertyRefExpr *E,
unsigned CVR) {
LValue R;
R.LVType = KVCRef;
R.PropertyRefExpr = E;
R.Initialize(Qualifiers::fromCVRMask(CVR));
return R; return R;
} }
}; };

View File

@ -1382,9 +1382,8 @@ public:
RValue EmitLoadOfLValue(LValue V, QualType LVType); RValue EmitLoadOfLValue(LValue V, QualType LVType);
RValue EmitLoadOfExtVectorElementLValue(LValue V, QualType LVType); RValue EmitLoadOfExtVectorElementLValue(LValue V, QualType LVType);
RValue EmitLoadOfBitfieldLValue(LValue LV, QualType ExprType); RValue EmitLoadOfBitfieldLValue(LValue LV, QualType ExprType);
RValue EmitLoadOfPropertyRefLValue(LValue LV, QualType ExprType); RValue EmitLoadOfPropertyRefLValue(LValue LV,
RValue EmitLoadOfKVCRefLValue(LValue LV, QualType ExprType); ReturnValueSlot Return = ReturnValueSlot());
/// EmitStoreThroughLValue - Store the specified rvalue into the specified /// EmitStoreThroughLValue - Store the specified rvalue into the specified
/// lvalue, where both are guaranteed to the have the same type, and that type /// lvalue, where both are guaranteed to the have the same type, and that type
@ -1392,8 +1391,7 @@ public:
void EmitStoreThroughLValue(RValue Src, LValue Dst, QualType Ty); void EmitStoreThroughLValue(RValue Src, LValue Dst, QualType Ty);
void EmitStoreThroughExtVectorComponentLValue(RValue Src, LValue Dst, void EmitStoreThroughExtVectorComponentLValue(RValue Src, LValue Dst,
QualType Ty); QualType Ty);
void EmitStoreThroughPropertyRefLValue(RValue Src, LValue Dst, QualType Ty); void EmitStoreThroughPropertyRefLValue(RValue Src, LValue Dst);
void EmitStoreThroughKVCRefLValue(RValue Src, LValue Dst, QualType Ty);
/// EmitStoreThroughLValue - Store Src into Dst with same constraints as /// EmitStoreThroughLValue - Store Src into Dst with same constraints as
/// EmitStoreThroughLValue. /// EmitStoreThroughLValue.
@ -1544,11 +1542,8 @@ public:
llvm::Value *EmitObjCSelectorExpr(const ObjCSelectorExpr *E); llvm::Value *EmitObjCSelectorExpr(const ObjCSelectorExpr *E);
RValue EmitObjCMessageExpr(const ObjCMessageExpr *E, RValue EmitObjCMessageExpr(const ObjCMessageExpr *E,
ReturnValueSlot Return = ReturnValueSlot()); ReturnValueSlot Return = ReturnValueSlot());
RValue EmitObjCPropertyGet(const ObjCPropertyRefExpr *E,
ReturnValueSlot Return = ReturnValueSlot());
RValue EmitObjCSuperPropertyGet(const Expr *Exp, const Selector &S, RValue EmitObjCSuperPropertyGet(const Expr *Exp, const Selector &S,
ReturnValueSlot Return = ReturnValueSlot()); ReturnValueSlot Return = ReturnValueSlot());
void EmitObjCPropertySet(const ObjCPropertyRefExpr *E, RValue Src);
void EmitObjCSuperPropertySet(const Expr *E, const Selector &S, RValue Src); void EmitObjCSuperPropertySet(const Expr *E, const Selector &S, RValue Src);