diff --git a/clang/lib/CodeGen/CGDebugInfo.cpp b/clang/lib/CodeGen/CGDebugInfo.cpp --- a/clang/lib/CodeGen/CGDebugInfo.cpp +++ b/clang/lib/CodeGen/CGDebugInfo.cpp @@ -292,13 +292,6 @@ } } else if (const auto *OCD = dyn_cast(DC)) { OS << OCD->getClassInterface()->getName() << '(' << OCD->getName() << ')'; - } else if (isa(DC)) { - // We can extract the type of the class from the self pointer. - if (ImplicitParamDecl *SelfDecl = OMD->getSelfDecl()) { - QualType ClassTy = - cast(SelfDecl->getType())->getPointeeType(); - ClassTy.print(OS, PrintingPolicy(LangOptions())); - } } OS << ' ' << OMD->getSelector().getAsString() << ']'; diff --git a/clang/lib/CodeGen/CGObjCMac.cpp b/clang/lib/CodeGen/CGObjCMac.cpp --- a/clang/lib/CodeGen/CGObjCMac.cpp +++ b/clang/lib/CodeGen/CGObjCMac.cpp @@ -4027,7 +4027,7 @@ llvm::Function * CGObjCCommonMac::GenerateDirectMethod(const ObjCMethodDecl *OMD, const ObjCContainerDecl *CD) { - auto I = DirectMethodDefinitions.find(OMD); + auto I = DirectMethodDefinitions.find(OMD->getCanonicalDecl()); if (I != DirectMethodDefinitions.end()) return I->second; @@ -4040,7 +4040,7 @@ llvm::Function *Method = llvm::Function::Create(MethodTy, llvm::GlobalValue::ExternalLinkage, Name.str(), &CGM.getModule()); - DirectMethodDefinitions.insert(std::make_pair(OMD, Method)); + DirectMethodDefinitions.insert(std::make_pair(OMD->getCanonicalDecl(), Method)); return Method; } diff --git a/clang/lib/Sema/SemaDeclObjC.cpp b/clang/lib/Sema/SemaDeclObjC.cpp --- a/clang/lib/Sema/SemaDeclObjC.cpp +++ b/clang/lib/Sema/SemaDeclObjC.cpp @@ -4869,6 +4869,9 @@ } } + // Insert the invisible arguments, self and _cmd! + ObjCMethod->createImplicitParams(Context, ObjCMethod->getClassInterface()); + ActOnDocumentableDecl(ObjCMethod); return ObjCMethod; diff --git a/clang/lib/Serialization/ASTReaderDecl.cpp b/clang/lib/Serialization/ASTReaderDecl.cpp --- a/clang/lib/Serialization/ASTReaderDecl.cpp +++ b/clang/lib/Serialization/ASTReaderDecl.cpp @@ -1017,9 +1017,9 @@ // definitions rarely show up in headers. Reader.PendingBodies[MD] = GetCurrentCursorOffset(); HasPendingBody = true; - MD->setSelfDecl(ReadDeclAs()); - MD->setCmdDecl(ReadDeclAs()); } + MD->setSelfDecl(ReadDeclAs()); + MD->setCmdDecl(ReadDeclAs()); MD->setInstanceMethod(Record.readInt()); MD->setVariadic(Record.readInt()); MD->setPropertyAccessor(Record.readInt()); diff --git a/clang/lib/Serialization/ASTWriterDecl.cpp b/clang/lib/Serialization/ASTWriterDecl.cpp --- a/clang/lib/Serialization/ASTWriterDecl.cpp +++ b/clang/lib/Serialization/ASTWriterDecl.cpp @@ -664,14 +664,13 @@ VisitNamedDecl(D); // FIXME: convert to LazyStmtPtr? // Unlike C/C++, method bodies will never be in header files. - bool HasBodyStuff = D->getBody() != nullptr || - D->getSelfDecl() != nullptr || D->getCmdDecl() != nullptr; + bool HasBodyStuff = D->getBody() != nullptr; Record.push_back(HasBodyStuff); if (HasBodyStuff) { Record.AddStmt(D->getBody()); - Record.AddDeclRef(D->getSelfDecl()); - Record.AddDeclRef(D->getCmdDecl()); } + Record.AddDeclRef(D->getSelfDecl()); + Record.AddDeclRef(D->getCmdDecl()); Record.push_back(D->isInstanceMethod()); Record.push_back(D->isVariadic()); Record.push_back(D->isPropertyAccessor()); diff --git a/clang/lib/StaticAnalyzer/Frontend/AnalysisConsumer.cpp b/clang/lib/StaticAnalyzer/Frontend/AnalysisConsumer.cpp --- a/clang/lib/StaticAnalyzer/Frontend/AnalysisConsumer.cpp +++ b/clang/lib/StaticAnalyzer/Frontend/AnalysisConsumer.cpp @@ -722,13 +722,6 @@ } else if (const auto *OCD = dyn_cast(DC)) { OS << OCD->getClassInterface()->getName() << '(' << OCD->getName() << ')'; - } else if (isa(DC)) { - // We can extract the type of the class from the self pointer. - if (ImplicitParamDecl *SelfDecl = OMD->getSelfDecl()) { - QualType ClassTy = - cast(SelfDecl->getType())->getPointeeType(); - ClassTy.print(OS, PrintingPolicy(LangOptions())); - } } OS << ' ' << OMD->getSelector().getAsString() << ']'; diff --git a/clang/test/CodeGenObjC/direct-method.m b/clang/test/CodeGenObjC/direct-method.m --- a/clang/test/CodeGenObjC/direct-method.m +++ b/clang/test/CodeGenObjC/direct-method.m @@ -11,9 +11,17 @@ __attribute__((objc_root_class)) @interface Root +- (int)getInt __attribute__((objc_direct)); +@property(direct, readonly) int intProperty; +@property(direct, readonly) int intProperty2; @end @implementation Root +// CHECK-LABEL: define hidden i32 @"\01-[Root intProperty2]" +- (int)intProperty2 { + return 42; +} + // CHECK-LABEL: define hidden i32 @"\01-[Root getInt]"( - (int)getInt __attribute__((objc_direct)) { // loading parameters @@ -152,6 +160,7 @@ } @end +// CHECK-LABEL: define hidden i32 @"\01-[Root intProperty]" @interface Foo : Root { id __strong _cause_cxx_destruct; @@ -173,3 +182,11 @@ // CHECK-LABEL: define hidden void @"\01-[Foo setGetDynamic_setDirect:]"( // CHECK-LABEL: define internal void @"\01-[Foo .cxx_destruct]"( @end + +int useRoot(Root *r) { + // CHECK-LABEL: define i32 @useRoot + // CHECK: %{{[^ ]*}} = call i32 bitcast {{.*}} @"\01-[Root getInt]" + // CHECK: %{{[^ ]*}} = call i32 bitcast {{.*}} @"\01-[Root intProperty]" + // CHECK: %{{[^ ]*}} = call i32 bitcast {{.*}} @"\01-[Root intProperty2]" + return [r getInt] + [r intProperty] + [r intProperty2]; +}