Do we do this for typedefs (and C++11 'using' type-aliases) as well? I ran into a case yesterday where it seemed not to be working.
Jordan On Apr 26, 2013, at 13:55 , Fariborz Jahanian <[email protected]> wrote: > Author: fjahanian > Date: Fri Apr 26 15:55:38 2013 > New Revision: 180629 > > URL: http://llvm.org/viewvc/llvm-project?rev=180629&view=rev > Log: > document parsing. When a sub-class (c++ Objective-C) missing > a comment, grab the first comment found in its class > heirarchy. Also, when a category is mossing a comment, > grab comment of its primary class. // rdar://13647476 > > Added: > cfe/trunk/test/Misc/ast-dump-subclass-comment.mm > Modified: > cfe/trunk/lib/AST/ASTContext.cpp > > Modified: cfe/trunk/lib/AST/ASTContext.cpp > URL: > http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/ASTContext.cpp?rev=180629&r1=180628&r2=180629&view=diff > ============================================================================== > --- cfe/trunk/lib/AST/ASTContext.cpp (original) > +++ cfe/trunk/lib/AST/ASTContext.cpp Fri Apr 26 15:55:38 2013 > @@ -451,6 +451,51 @@ comments::FullComment *ASTContext::getCo > if (comments::FullComment *FC = getCommentForDecl(TD, PP)) > return cloneFullComment(FC, D); > } > + else if (const ObjCInterfaceDecl *IC = dyn_cast<ObjCInterfaceDecl>(D)) { > + while (IC->getSuperClass()) { > + IC = IC->getSuperClass(); > + if (comments::FullComment *FC = getCommentForDecl(IC, PP)) > + return cloneFullComment(FC, D); > + } > + } > + else if (const ObjCCategoryDecl *CD = dyn_cast<ObjCCategoryDecl>(D)) { > + if (const ObjCInterfaceDecl *IC = CD->getClassInterface()) > + if (comments::FullComment *FC = getCommentForDecl(IC, PP)) > + return cloneFullComment(FC, D); > + } > + else if (const CXXRecordDecl *RD = dyn_cast<CXXRecordDecl>(D)) { > + if (!(RD = RD->getDefinition())) > + return NULL; > + // Check non-virtual bases. > + for (CXXRecordDecl::base_class_const_iterator I = > + RD->bases_begin(), E = RD->bases_end(); I != E; ++I) { > + if (I->isVirtual()) > + continue; > + QualType Ty = I->getType(); > + if (Ty.isNull()) > + continue; > + if (const CXXRecordDecl *NonVirtualBase = Ty->getAsCXXRecordDecl()) { > + if (!(NonVirtualBase= NonVirtualBase->getDefinition())) > + continue; > + > + if (comments::FullComment *FC = > getCommentForDecl((NonVirtualBase), PP)) > + return cloneFullComment(FC, D); > + } > + } > + // Check virtual bases. > + for (CXXRecordDecl::base_class_const_iterator I = > + RD->vbases_begin(), E = RD->vbases_end(); I != E; ++I) { > + QualType Ty = I->getType(); > + if (Ty.isNull()) > + continue; > + if (const CXXRecordDecl *VirtualBase = Ty->getAsCXXRecordDecl()) { > + if (!(VirtualBase= VirtualBase->getDefinition())) > + continue; > + if (comments::FullComment *FC = getCommentForDecl((VirtualBase), > PP)) > + return cloneFullComment(FC, D); > + } > + } > + } > return NULL; > } > > > Added: cfe/trunk/test/Misc/ast-dump-subclass-comment.mm > URL: > http://llvm.org/viewvc/llvm-project/cfe/trunk/test/Misc/ast-dump-subclass-comment.mm?rev=180629&view=auto > ============================================================================== > --- cfe/trunk/test/Misc/ast-dump-subclass-comment.mm (added) > +++ cfe/trunk/test/Misc/ast-dump-subclass-comment.mm Fri Apr 26 15:55:38 2013 > @@ -0,0 +1,101 @@ > +// RUN: %clang_cc1 -x objective-c++ -Wdocumentation -ast-dump %s | FileCheck > %s > +// rdar://13647476 > + > +//! NSObject is root of all. > +@interface NSObject > +@end > +// CHECK: ObjCInterfaceDecl{{.*}}NSObject > +// CHECK-NEXT: FullComment 0x{{[^ ]*}} <line:[[@LINE-4]]:4, col:28> > +// CHECK-NEXT: ParagraphComment{{.*}} <col:4, col:28> > +// CHECK-NEXT: TextComment{{.*}} <col:4, col:28> Text=" NSObject is > root of all." > + > +//! An umbrella class for super classes. > +@interface SuperClass > +@end > +// CHECK: ObjCInterfaceDecl{{.*}}SuperClass > +// CHECK-NEXT: FullComment 0x{{[^ ]*}} <line:[[@LINE-4]]:4, col:40> > +// CHECK-NEXT: ParagraphComment{{.*}} <col:4, col:40> > +// CHECK-NEXT: TextComment{{.*}} <col:4, col:40> Text=" An umbrella > class for super classes." > + > +@interface SubClass : SuperClass > +@end > +// CHECK: ObjCInterfaceDecl 0x{{[^ ]*}} <line:[[@LINE-2]]:1, > line:[[@LINE-1]]:2> SubClass > +// CHECK-NEXT: ObjCInterface 0x{{[^ ]*}} 'SuperClass' > +// CHECK-NEXT: FullComment > +// CHECK-NEXT: ParagraphComment{{.*}} <col:4, col:40> > +// CHECK-NEXT: TextComment{{.*}} <col:4, col:40> Text=" An umbrella class > for super classes." > + > +@interface SubSubClass : SubClass > +@end > +// CHECK: ObjCInterfaceDecl 0x{{[^ ]*}} <line:[[@LINE-2]]:1, > line:[[@LINE-1]]:2> SubSubClass > +// CHECK-NEXT: ObjCInterface{{.*}} 'SubClass' > +// CHECK-NEXT: FullComment > +// CHECK-NEXT: ParagraphComment{{.*}} <col:4, col:40> > +// CHECK-NEXT: TextComment{{.*}} <col:4, col:40> Text=" An umbrella class > for super classes." > + > +@interface SubSubClass (Private) > +@end > +// CHECK: ObjCCategoryDecl 0x{{[^ ]*}} <line:[[@LINE-2]]:1, > line:[[@LINE-1]]:2> Private > +// CHECK-NEXT: ObjCInterface{{.*}} 'SubSubClass' > +// CHECK-NEXT: FullComment > +// CHECK-NEXT: ParagraphComment{{.*}} <col:4, col:40> > +// CHECK-TEXT: TextComment{{.*}} <col:4, col:40> Text=" An umbrella class > for super classes." > + > +//! Something valuable to the organization. > +class Asset { > + > +}; > +// CHECK: CXXRecordDecl 0x{{[^ ]*}} <line:[[@LINE-3]]:1, line:[[@LINE-1]]:1> > class Asset > +// CHECK-NEXT: FullComment > +// CHECK-NEXT: ParagraphComment{{.*}} <col:4, col:43> > +// CHECK-NEXT: TextComment{{.*}} <col:4, col:43> Text=" Something valuable > to the organization." > + > +//! An individual human or human individual. > +class Person : public Asset { > +}; > +// CHECK: CXXRecordDecl 0x{{[^ ]*}} <line:[[@LINE-2]]:1, > line:[[@LINE-1]]:1> class Person > +// CHECK-NEXT: public 'class Asset' > +// CHECK-NEXT: FullComment > +// CHECK-NEXT: ParagraphComment{{.*}} <col:4, col:44> > +// CHECK-NEXT: TextComment{{.*}} <col:4, col:44> Text=" An individual human > or human individual." > + > +class Student : public Person { > +}; > +// CHECK: CXXRecordDecl 0x{{[^ ]*}} <line:[[@LINE-2]]:1, line:[[@LINE-1]]:1> > class Student > +// CHECK-NEXT: public 'class Person' > +// CHECK-NEXT: FullComment > +// CHECK-NEXT: ParagraphComment{{.*}} <col:4, col:44> > +// CHECK-NEXT: TextComment{{.*}} <col:4, col:44> Text=" An individual human > or human individual." > + > +//! Every thing is a part > +class Parts { > +}; > +// CHECK: CXXRecordDecl 0x{{[^ ]*}} <line:[[@LINE-2]]:1, line:[[@LINE-1]]:1> > class Parts > +// CHECK-NEXT: FullComment > +// CHECK-NEXT: ParagraphComment{{.*}} <col:4, col:25> > +// CHECK-NEXT: TextComment{{.*}} <col:4, col:25> Text=" Every thing is a > part" > + > +class Window : virtual Parts { > +}; > +// CHECK: CXXRecordDecl 0x{{[^ ]*}} <line:[[@LINE-2]]:1, > line:[[@LINE-1]]:1> class Window > +// CHECK-NEXT: virtual private 'class Parts' > +// CHECK-NEXT: FullComment > +// CHECK-NEXT: ParagraphComment{{.*}} <col:4, col:25> > +// CHECK-NEXT: TextComment{{.*}} <col:4, col:25> Text=" Every thing is a > part" > + > +class Door : virtual Parts { > +}; > +// CHECK: CXXRecordDecl 0x{{[^ ]*}} <line:[[@LINE-2]]:1, > line:[[@LINE-1]]:1> class Door > +// CHECK-NEXT: virtual private 'class Parts' > +// CHECK-NEXT: FullComment > +// CHECK-NEXT: ParagraphComment{{.*}} <col:4, col:25> > +// CHECK-NEXT: TextComment{{.*}} <col:4, col:25> Text=" Every thing is a > part" > + > +class House : Window, Door { > +}; > +// CHECK: CXXRecordDecl 0x{{[^ ]*}} <line:[[@LINE-2]]:1, > line:[[@LINE-1]]:1> class House > +// CHECK-NEXT: private 'class Window' > +// CHECK-NEXT: private 'class Door' > +// CHECK-NEXT: FullComment > +// CHECK-NEXT: ParagraphComment{{.*}} <col:4, col:25> > +// CHECK-NEXT: TextComment{{.*}} <col:4, col:25> Text=" Every thing is a > part" > > > _______________________________________________ > cfe-commits mailing list > [email protected] > http://lists.cs.uiuc.edu/mailman/listinfo/cfe-commits _______________________________________________ cfe-commits mailing list [email protected] http://lists.cs.uiuc.edu/mailman/listinfo/cfe-commits
