aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorSteve Naroff <snaroff@apple.com>2009-07-20 17:56:53 +0000
committerSteve Naroff <snaroff@apple.com>2009-07-20 17:56:53 +0000
commit67ef8eaea8a0a2073147a8d863f0e3f30d525802 (patch)
treee69453c4480792194458bc049fe3a75af6c5a28b
parentd33c868d386ef47c2942e2dbff0d9955a8591fa9 (diff)
5 cleanups to ObjCObjectPointerType work:
- Remove Sema::CheckPointeeTypesForAssignment(), a temporary API I added to ease migration to ObjCObjectPointerType. Convert Sema::CheckAssignmentConstraints() to no longer depend on the temporary API. - Sema::ConvertDeclSpecToType(): Replace a couple FIXME's with an important comment/example. - Sema::GetTypeForDeclarator(): Get the protocol's from the interface, NOT the declspec (to support the following C typedef idiom: "typedef C<P> T; T *obj"). - Sema::ObjCQualifiedIdTypesAreCompatible(): Removed some dead code. - ASTContext::getObjCEncodingForTypeImpl(): Some minor cleanups. git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@76443 91177308-0d34-0410-b5e6-96231b3b80d8
-rw-r--r--lib/AST/ASTContext.cpp13
-rw-r--r--lib/Sema/Sema.h2
-rw-r--r--lib/Sema/SemaExpr.cpp40
-rw-r--r--lib/Sema/SemaExprObjC.cpp28
-rw-r--r--lib/Sema/SemaType.cpp20
5 files changed, 35 insertions, 68 deletions
diff --git a/lib/AST/ASTContext.cpp b/lib/AST/ASTContext.cpp
index 680ec24eff..05627b47eb 100644
--- a/lib/AST/ASTContext.cpp
+++ b/lib/AST/ASTContext.cpp
@@ -2758,10 +2758,9 @@ void ASTContext::getObjCEncodingForTypeImpl(QualType T, std::string& S,
if (FD || EncodingProperty) {
// Note that we do extended encoding of protocol qualifer list
// Only when doing ivar or property encoding.
- const ObjCObjectPointerType *QIDT = T->getAsObjCQualifiedIdType();
S += '"';
- for (ObjCObjectPointerType::qual_iterator I = QIDT->qual_begin(),
- E = QIDT->qual_end(); I != E; ++I) {
+ for (ObjCObjectPointerType::qual_iterator I = OPT->qual_begin(),
+ E = OPT->qual_end(); I != E; ++I) {
S += '<';
S += (*I)->getNameAsString();
S += '>';
@@ -2786,12 +2785,10 @@ void ASTContext::getObjCEncodingForTypeImpl(QualType T, std::string& S,
S += '@';
if (FD || EncodingProperty) {
- const ObjCInterfaceType *OIT = OPT->getInterfaceType();
- ObjCInterfaceDecl *OI = OIT->getDecl();
S += '"';
- S += OI->getNameAsCString();
- for (ObjCInterfaceType::qual_iterator I = OIT->qual_begin(),
- E = OIT->qual_end(); I != E; ++I) {
+ S += OPT->getInterfaceDecl()->getNameAsCString();
+ for (ObjCObjectPointerType::qual_iterator I = OPT->qual_begin(),
+ E = OPT->qual_end(); I != E; ++I) {
S += '<';
S += (*I)->getNameAsString();
S += '>';
diff --git a/lib/Sema/Sema.h b/lib/Sema/Sema.h
index 82a8a087d9..837b2c8fec 100644
--- a/lib/Sema/Sema.h
+++ b/lib/Sema/Sema.h
@@ -3033,8 +3033,6 @@ public:
// Helper function for CheckAssignmentConstraints (C99 6.5.16.1p1)
AssignConvertType CheckPointerTypesForAssignment(QualType lhsType,
QualType rhsType);
- AssignConvertType CheckPointeeTypesForAssignment(QualType lhsType,
- QualType rhsType);
// Helper function for CheckAssignmentConstraints involving two
// block pointer types.
diff --git a/lib/Sema/SemaExpr.cpp b/lib/Sema/SemaExpr.cpp
index 35c0ddb06d..7aa66f9b62 100644
--- a/lib/Sema/SemaExpr.cpp
+++ b/lib/Sema/SemaExpr.cpp
@@ -2398,8 +2398,8 @@ Sema::ActOnMemberReferenceExpr(Scope *S, ExprArg Base, SourceLocation OpLoc,
MemberLoc, BaseExpr));
}
// Check protocols on qualified interfaces.
- for (ObjCObjectPointerType::qual_iterator I = IFaceT->qual_begin(),
- E = IFaceT->qual_end(); I != E; ++I)
+ for (ObjCObjectPointerType::qual_iterator I = OPT->qual_begin(),
+ E = OPT->qual_end(); I != E; ++I)
if (ObjCPropertyDecl *PD = (*I)->FindPropertyDeclaration(&Member)) {
// Check whether we can reference this property.
if (DiagnoseUseOfDecl(PD, MemberLoc))
@@ -3303,7 +3303,6 @@ Action::OwningExprResult Sema::ActOnConditionalOp(SourceLocation QuestionLoc,
RHSExpr, result));
}
-
// CheckPointerTypesForAssignment - This is a very tricky routine (despite
// being closely modeled after the C99 spec:-). The odd characteristic of this
// routine is it effectively iqnores the qualifiers on the top level pointee.
@@ -3317,11 +3316,6 @@ Sema::CheckPointerTypesForAssignment(QualType lhsType, QualType rhsType) {
lhptee = lhsType->getAsPointerType()->getPointeeType();
rhptee = rhsType->getAsPointerType()->getPointeeType();
- return CheckPointeeTypesForAssignment(lhptee, rhptee);
-}
-
-Sema::AssignConvertType
-Sema::CheckPointeeTypesForAssignment(QualType lhptee, QualType rhptee) {
// make sure we operate on the canonical type
lhptee = Context.getCanonicalType(lhptee);
rhptee = Context.getCanonicalType(rhptee);
@@ -3495,12 +3489,12 @@ Sema::CheckAssignmentConstraints(QualType lhsType, QualType rhsType) {
if (isa<PointerType>(rhsType))
return CheckPointerTypesForAssignment(lhsType, rhsType);
+ // In general, C pointers are not compatible with ObjC object pointers.
if (isa<ObjCObjectPointerType>(rhsType)) {
- QualType rhptee = rhsType->getAsObjCObjectPointerType()->getPointeeType();
- QualType lhptee = lhsType->getAsPointerType()->getPointeeType();
- return CheckPointeeTypesForAssignment(lhptee, rhptee);
+ if (lhsType->isVoidPointerType()) // an exception to the rule.
+ return Compatible;
+ return IncompatiblePointer;
}
-
if (rhsType->getAsBlockPointerType()) {
if (lhsType->getAsPointerType()->getPointeeType()->isVoidType())
return Compatible;
@@ -3533,18 +3527,19 @@ Sema::CheckAssignmentConstraints(QualType lhsType, QualType rhsType) {
if (isa<ObjCObjectPointerType>(lhsType)) {
if (rhsType->isIntegerType())
return IntToPointer;
-
+
+ // In general, C pointers are not compatible with ObjC object pointers.
if (isa<PointerType>(rhsType)) {
- QualType lhptee = lhsType->getAsObjCObjectPointerType()->getPointeeType();
- QualType rhptee = rhsType->getAsPointerType()->getPointeeType();
- return CheckPointeeTypesForAssignment(lhptee, rhptee);
+ if (rhsType->isVoidPointerType()) // an exception to the rule.
+ return Compatible;
+ return IncompatiblePointer;
}
if (rhsType->isObjCObjectPointerType()) {
if (lhsType->isObjCBuiltinType() || rhsType->isObjCBuiltinType())
return Compatible;
- QualType lhptee = lhsType->getAsObjCObjectPointerType()->getPointeeType();
- QualType rhptee = rhsType->getAsObjCObjectPointerType()->getPointeeType();
- return CheckPointeeTypesForAssignment(lhptee, rhptee);
+ if (Context.typesAreCompatible(lhsType, rhsType))
+ return Compatible;
+ return IncompatiblePointer;
}
if (const PointerType *RHSPT = rhsType->getAsPointerType()) {
if (RHSPT->getPointeeType()->isVoidType())
@@ -3579,10 +3574,11 @@ Sema::CheckAssignmentConstraints(QualType lhsType, QualType rhsType) {
if (lhsType->isIntegerType())
return PointerToInt;
+ // In general, C pointers are not compatible with ObjC object pointers.
if (isa<PointerType>(lhsType)) {
- QualType rhptee = lhsType->getAsObjCObjectPointerType()->getPointeeType();
- QualType lhptee = rhsType->getAsPointerType()->getPointeeType();
- return CheckPointeeTypesForAssignment(lhptee, rhptee);
+ if (lhsType->isVoidPointerType()) // an exception to the rule.
+ return Compatible;
+ return IncompatiblePointer;
}
if (isa<BlockPointerType>(lhsType) &&
rhsType->getAsPointerType()->getPointeeType()->isVoidType())
diff --git a/lib/Sema/SemaExprObjC.cpp b/lib/Sema/SemaExprObjC.cpp
index 1d995b53e6..66e1beb983 100644
--- a/lib/Sema/SemaExprObjC.cpp
+++ b/lib/Sema/SemaExprObjC.cpp
@@ -854,34 +854,6 @@ bool Sema::ObjCQualifiedIdTypesAreCompatible(QualType lhs, QualType rhs,
}
return true;
}
- // FIXME: The code below will be removed when ObjCQualifiedInterfaceType is
- // removed.
- if (!lhs->isPointerType())
- return false;
-
- QualType ltype = lhs->getAsPointerType()->getPointeeType();
- if (const ObjCInterfaceType *lhsQI =
- ltype->getAsObjCQualifiedInterfaceType()) {
- ObjCObjectPointerType::qual_iterator LHSProtoI = lhsQI->qual_begin();
- ObjCObjectPointerType::qual_iterator LHSProtoE = lhsQI->qual_end();
- for (; LHSProtoI != LHSProtoE; ++LHSProtoI) {
- bool match = false;
- ObjCProtocolDecl *lhsProto = *LHSProtoI;
- for (ObjCObjectPointerType::qual_iterator I = rhsQID->qual_begin(),
- E = rhsQID->qual_end(); I != E; ++I) {
- ObjCProtocolDecl *rhsProto = *I;
- if (ProtocolCompatibleWithProtocol(lhsProto, rhsProto) ||
- (compare && ProtocolCompatibleWithProtocol(rhsProto, lhsProto))) {
- match = true;
- break;
- }
- }
- if (!match)
- return false;
- }
- return true;
- }
-
return false;
}
diff --git a/lib/Sema/SemaType.cpp b/lib/Sema/SemaType.cpp
index 57989a021b..5fbc8e813b 100644
--- a/lib/Sema/SemaType.cpp
+++ b/lib/Sema/SemaType.cpp
@@ -205,12 +205,16 @@ QualType Sema::ConvertDeclSpecToType(const DeclSpec &DS,
Result = QualType::getFromOpaquePtr(DS.getTypeRep());
if (DeclSpec::ProtocolQualifierListTy PQ = DS.getProtocolQualifiers()) {
- // FIXME: Adding a TST_objcInterface clause doesn't seem ideal, so we have
- // this "hack" for now...
if (const ObjCInterfaceType *Interface = Result->getAsObjCInterfaceType())
- // FIXME: Investigate removing the protocol list in ObjCInterfaceType.
- // To simply this, Sema::GetTypeForDeclarator() uses the declspec
- // protocol list, not the list we are storing here.
+ // It would be nice if protocol qualifiers were only stored with the
+ // ObjCObjectPointerType. Unfortunately, this isn't possible due
+ // to the following typedef idiom (which is uncommon, but allowed):
+ //
+ // typedef Foo<P> T;
+ // static void func() {
+ // Foo<P> *yy;
+ // T *zz;
+ // }
Result = Context.getObjCInterfaceType(Interface->getDecl(),
(ObjCProtocolDecl**)PQ,
DS.getNumProtocolQualifiers());
@@ -901,10 +905,10 @@ QualType Sema::GetTypeForDeclarator(Declarator &D, Scope *S, unsigned Skip,
// Build the type anyway.
}
if (getLangOptions().ObjC1 && T->isObjCInterfaceType()) {
- const DeclSpec &DS = D.getDeclSpec();
+ const ObjCInterfaceType *OIT = T->getAsObjCInterfaceType();
T = Context.getObjCObjectPointerType(T,
- (ObjCProtocolDecl **)DS.getProtocolQualifiers(),
- DS.getNumProtocolQualifiers());
+ (ObjCProtocolDecl **)OIT->qual_begin(),
+ OIT->getNumProtocols());
break;
}
T = BuildPointerType(T, DeclType.Ptr.TypeQuals, DeclType.Loc, Name);