1 //===--- CommentSema.h - Doxygen comment semantic analysis ------*- C++ -*-===// 2 // 3 // The LLVM Compiler Infrastructure 4 // 5 // This file is distributed under the University of Illinois Open Source 6 // License. See LICENSE.TXT for details. 7 // 8 //===----------------------------------------------------------------------===// 9 // 10 // This file defines the semantic analysis class for Doxygen comments. 11 // 12 //===----------------------------------------------------------------------===// 13 14 #ifndef LLVM_CLANG_AST_COMMENT_SEMA_H 15 #define LLVM_CLANG_AST_COMMENT_SEMA_H 16 17 #include "clang/AST/Comment.h" 18 #include "clang/Basic/Diagnostic.h" 19 #include "clang/Basic/SourceLocation.h" 20 #include "llvm/ADT/ArrayRef.h" 21 #include "llvm/ADT/StringMap.h" 22 #include "llvm/ADT/StringRef.h" 23 #include "llvm/Support/Allocator.h" 24 25 namespace clang { 26 class Decl; 27 class SourceMgr; 28 class Preprocessor; 29 30 namespace comments { 31 class CommandTraits; 32 33 class Sema { 34 Sema(const Sema &) LLVM_DELETED_FUNCTION; 35 void operator=(const Sema &) LLVM_DELETED_FUNCTION; 36 37 /// Allocator for AST nodes. 38 llvm::BumpPtrAllocator &Allocator; 39 40 /// Source manager for the comment being parsed. 41 const SourceManager &SourceMgr; 42 43 DiagnosticsEngine &Diags; 44 45 CommandTraits &Traits; 46 47 const Preprocessor *PP; 48 49 /// Information about the declaration this comment is attached to. 50 DeclInfo *ThisDeclInfo; 51 52 /// Comment AST nodes that correspond to parameter names in 53 /// \c TemplateParameters. 54 /// 55 /// Contains a valid value if \c DeclInfo->IsFilled is true. 56 llvm::StringMap<TParamCommandComment *> TemplateParameterDocs; 57 58 /// AST node for the \\brief command and its aliases. 59 const BlockCommandComment *BriefCommand; 60 61 /// AST node for the \\returns command and its aliases. 62 const BlockCommandComment *ReturnsCommand; 63 64 /// AST node for the \\headerfile command. 65 const BlockCommandComment *HeaderfileCommand; 66 Diag(SourceLocation Loc,unsigned DiagID)67 DiagnosticBuilder Diag(SourceLocation Loc, unsigned DiagID) { 68 return Diags.Report(Loc, DiagID); 69 } 70 71 /// A stack of HTML tags that are currently open (not matched with closing 72 /// tags). 73 SmallVector<HTMLStartTagComment *, 8> HTMLOpenTags; 74 75 public: 76 Sema(llvm::BumpPtrAllocator &Allocator, const SourceManager &SourceMgr, 77 DiagnosticsEngine &Diags, CommandTraits &Traits, 78 const Preprocessor *PP); 79 80 void setDecl(const Decl *D); 81 82 /// Returns a copy of array, owned by Sema's allocator. 83 template<typename T> copyArray(ArrayRef<T> Source)84 ArrayRef<T> copyArray(ArrayRef<T> Source) { 85 size_t Size = Source.size(); 86 if (Size != 0) { 87 T *Mem = Allocator.Allocate<T>(Size); 88 std::uninitialized_copy(Source.begin(), Source.end(), Mem); 89 return llvm::makeArrayRef(Mem, Size); 90 } else 91 return llvm::makeArrayRef(static_cast<T *>(NULL), 0); 92 } 93 94 ParagraphComment *actOnParagraphComment( 95 ArrayRef<InlineContentComment *> Content); 96 97 BlockCommandComment *actOnBlockCommandStart(SourceLocation LocBegin, 98 SourceLocation LocEnd, 99 unsigned CommandID, 100 CommandMarkerKind CommandMarker); 101 102 void actOnBlockCommandArgs(BlockCommandComment *Command, 103 ArrayRef<BlockCommandComment::Argument> Args); 104 105 void actOnBlockCommandFinish(BlockCommandComment *Command, 106 ParagraphComment *Paragraph); 107 108 ParamCommandComment *actOnParamCommandStart(SourceLocation LocBegin, 109 SourceLocation LocEnd, 110 unsigned CommandID, 111 CommandMarkerKind CommandMarker); 112 113 void actOnParamCommandDirectionArg(ParamCommandComment *Command, 114 SourceLocation ArgLocBegin, 115 SourceLocation ArgLocEnd, 116 StringRef Arg); 117 118 void actOnParamCommandParamNameArg(ParamCommandComment *Command, 119 SourceLocation ArgLocBegin, 120 SourceLocation ArgLocEnd, 121 StringRef Arg); 122 123 void actOnParamCommandFinish(ParamCommandComment *Command, 124 ParagraphComment *Paragraph); 125 126 TParamCommandComment *actOnTParamCommandStart(SourceLocation LocBegin, 127 SourceLocation LocEnd, 128 unsigned CommandID, 129 CommandMarkerKind CommandMarker); 130 131 void actOnTParamCommandParamNameArg(TParamCommandComment *Command, 132 SourceLocation ArgLocBegin, 133 SourceLocation ArgLocEnd, 134 StringRef Arg); 135 136 void actOnTParamCommandFinish(TParamCommandComment *Command, 137 ParagraphComment *Paragraph); 138 139 InlineCommandComment *actOnInlineCommand(SourceLocation CommandLocBegin, 140 SourceLocation CommandLocEnd, 141 unsigned CommandID); 142 143 InlineCommandComment *actOnInlineCommand(SourceLocation CommandLocBegin, 144 SourceLocation CommandLocEnd, 145 unsigned CommandID, 146 SourceLocation ArgLocBegin, 147 SourceLocation ArgLocEnd, 148 StringRef Arg); 149 150 InlineContentComment *actOnUnknownCommand(SourceLocation LocBegin, 151 SourceLocation LocEnd, 152 StringRef CommandName); 153 154 InlineContentComment *actOnUnknownCommand(SourceLocation LocBegin, 155 SourceLocation LocEnd, 156 unsigned CommandID); 157 158 TextComment *actOnText(SourceLocation LocBegin, 159 SourceLocation LocEnd, 160 StringRef Text); 161 162 VerbatimBlockComment *actOnVerbatimBlockStart(SourceLocation Loc, 163 unsigned CommandID); 164 165 VerbatimBlockLineComment *actOnVerbatimBlockLine(SourceLocation Loc, 166 StringRef Text); 167 168 void actOnVerbatimBlockFinish(VerbatimBlockComment *Block, 169 SourceLocation CloseNameLocBegin, 170 StringRef CloseName, 171 ArrayRef<VerbatimBlockLineComment *> Lines); 172 173 VerbatimLineComment *actOnVerbatimLine(SourceLocation LocBegin, 174 unsigned CommandID, 175 SourceLocation TextBegin, 176 StringRef Text); 177 178 HTMLStartTagComment *actOnHTMLStartTagStart(SourceLocation LocBegin, 179 StringRef TagName); 180 181 void actOnHTMLStartTagFinish(HTMLStartTagComment *Tag, 182 ArrayRef<HTMLStartTagComment::Attribute> Attrs, 183 SourceLocation GreaterLoc, 184 bool IsSelfClosing); 185 186 HTMLEndTagComment *actOnHTMLEndTag(SourceLocation LocBegin, 187 SourceLocation LocEnd, 188 StringRef TagName); 189 190 FullComment *actOnFullComment(ArrayRef<BlockContentComment *> Blocks); 191 192 void checkBlockCommandEmptyParagraph(BlockCommandComment *Command); 193 194 void checkReturnsCommand(const BlockCommandComment *Command); 195 196 /// Emit diagnostics about duplicate block commands that should be 197 /// used only once per comment, e.g., \\brief and \\returns. 198 void checkBlockCommandDuplicate(const BlockCommandComment *Command); 199 200 void checkDeprecatedCommand(const BlockCommandComment *Comment); 201 202 void checkFunctionDeclVerbatimLine(const BlockCommandComment *Comment); 203 204 void checkContainerDeclVerbatimLine(const BlockCommandComment *Comment); 205 206 void checkContainerDecl(const BlockCommandComment *Comment); 207 208 /// Resolve parameter names to parameter indexes in function declaration. 209 /// Emit diagnostics about unknown parametrs. 210 void resolveParamCommandIndexes(const FullComment *FC); 211 212 bool isFunctionDecl(); 213 bool isAnyFunctionDecl(); 214 bool isFunctionPointerVarDecl(); 215 bool isObjCMethodDecl(); 216 bool isObjCPropertyDecl(); 217 bool isTemplateOrSpecialization(); 218 bool isRecordLikeDecl(); 219 bool isClassOrStructDecl(); 220 bool isUnionDecl(); 221 bool isObjCInterfaceDecl(); 222 bool isObjCProtocolDecl(); 223 224 ArrayRef<const ParmVarDecl *> getParamVars(); 225 226 /// Extract all important semantic information from 227 /// \c ThisDeclInfo->ThisDecl into \c ThisDeclInfo members. 228 void inspectThisDecl(); 229 230 /// Returns index of a function parameter with a given name. 231 unsigned resolveParmVarReference(StringRef Name, 232 ArrayRef<const ParmVarDecl *> ParamVars); 233 234 /// Returns index of a function parameter with the name closest to a given 235 /// typo. 236 unsigned correctTypoInParmVarReference(StringRef Typo, 237 ArrayRef<const ParmVarDecl *> ParamVars); 238 239 bool resolveTParamReference(StringRef Name, 240 const TemplateParameterList *TemplateParameters, 241 SmallVectorImpl<unsigned> *Position); 242 243 StringRef correctTypoInTParamReference( 244 StringRef Typo, 245 const TemplateParameterList *TemplateParameters); 246 247 InlineCommandComment::RenderKind 248 getInlineCommandRenderKind(StringRef Name) const; 249 }; 250 251 } // end namespace comments 252 } // end namespace clang 253 254 #endif 255 256