diff options
author | Ted Kremenek <kremenek@apple.com> | 2014-03-05 23:18:22 +0000 |
---|---|---|
committer | Ted Kremenek <kremenek@apple.com> | 2014-03-05 23:18:22 +0000 |
commit | d038ebe8f182ed6a54cff3c63747c2cda59dd9f3 (patch) | |
tree | 8e443de42f72bd506a75016c13b74d2e76134538 | |
parent | cfdb070d4dd0dcbcbbef854eb025693d5bd99cee (diff) | |
download | clang-d038ebe8f182ed6a54cff3c63747c2cda59dd9f3.tar.gz |
Fix recursion bug in logic to validate 'objc_protocol_requires_explicit_implementation' conformance.
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@203024 91177308-0d34-0410-b5e6-96231b3b80d8
-rw-r--r-- | lib/Sema/SemaDeclObjC.cpp | 17 | ||||
-rw-r--r-- | test/SemaObjC/protocols-suppress-conformance.m | 5 |
2 files changed, 16 insertions, 6 deletions
diff --git a/lib/Sema/SemaDeclObjC.cpp b/lib/Sema/SemaDeclObjC.cpp index 57f40aaca5..f71bd56a42 100644 --- a/lib/Sema/SemaDeclObjC.cpp +++ b/lib/Sema/SemaDeclObjC.cpp @@ -1635,6 +1635,17 @@ void Sema::WarnExactTypedMethods(ObjCMethodDecl *ImpMethodDecl, typedef llvm::DenseSet<IdentifierInfo*> ProtocolNameSet; typedef llvm::OwningPtr<ProtocolNameSet> LazyProtocolNameSet; + + +static void findProtocolsWithExplicitImpls(const ObjCProtocolDecl *PDecl, + ProtocolNameSet &PNS) { + if (PDecl->hasAttr<ObjCExplicitProtocolImplAttr>()) + PNS.insert(PDecl->getIdentifier()); + for (ObjCProtocolDecl::protocol_iterator PI = PDecl->protocol_begin(), + PE = PDecl->protocol_end(); PI != PE; ++PI) + findProtocolsWithExplicitImpls(*PI, PNS); +} + /// Recursively populates a set with all conformed protocols in a class /// hierarchy that have the 'objc_protocol_requires_explicit_implementation' /// attribute. @@ -1646,10 +1657,10 @@ static void findProtocolsWithExplicitImpls(const ObjCInterfaceDecl *Super, for (ObjCInterfaceDecl::all_protocol_iterator I = Super->all_referenced_protocol_begin(), E = Super->all_referenced_protocol_end(); I != E; ++I) { - const ObjCProtocolDecl *PDecl = *I; - if (PDecl->hasAttr<ObjCExplicitProtocolImplAttr>()) - PNS.insert(PDecl->getIdentifier()); + findProtocolsWithExplicitImpls(*I, PNS); } + + findProtocolsWithExplicitImpls(Super->getSuperClass(), PNS); } /// CheckProtocolMethodDefs - This routine checks unimplemented methods diff --git a/test/SemaObjC/protocols-suppress-conformance.m b/test/SemaObjC/protocols-suppress-conformance.m index 3bb892780c..299e44e807 100644 --- a/test/SemaObjC/protocols-suppress-conformance.m +++ b/test/SemaObjC/protocols-suppress-conformance.m @@ -178,7 +178,7 @@ __attribute__((objc_protocol_requires_explicit_implementation)) // expected-err __attribute__((objc_protocol_requires_explicit_implementation)) @protocol Ex2ProtocolA -- (void)methodB; // expected-note {{method 'methodB' declared here}} +- (void)methodB; @end __attribute__((objc_protocol_requires_explicit_implementation)) @@ -202,7 +202,6 @@ __attribute__((objc_protocol_requires_explicit_implementation)) // expected-err @interface Ex2ClassB : Ex2ClassA <Ex2ProtocolB> @end -@implementation Ex2ClassB // expected-warning {{method 'methodB' in protocol 'Ex2ProtocolA' not implemented}}\ - // expected-warning {{method 'methodA' in protocol 'Ex2ProtocolB' not implemented}} +@implementation Ex2ClassB // expected-warning {{method 'methodA' in protocol 'Ex2ProtocolB' not implemented}} @end |