clang API Documentation
00001 //===--- RawCommentList.h - Classes for processing raw comments -*- C++ -*-===// 00002 // 00003 // The LLVM Compiler Infrastructure 00004 // 00005 // This file is distributed under the University of Illinois Open Source 00006 // License. See LICENSE.TXT for details. 00007 // 00008 //===----------------------------------------------------------------------===// 00009 00010 #ifndef LLVM_CLANG_AST_RAWCOMMENTLIST_H 00011 #define LLVM_CLANG_AST_RAWCOMMENTLIST_H 00012 00013 #include "clang/Basic/CommentOptions.h" 00014 #include "clang/Basic/SourceManager.h" 00015 #include "llvm/ADT/ArrayRef.h" 00016 00017 namespace clang { 00018 00019 class ASTContext; 00020 class ASTReader; 00021 class Decl; 00022 class Preprocessor; 00023 00024 namespace comments { 00025 class FullComment; 00026 } // end namespace comments 00027 00028 class RawComment { 00029 public: 00030 enum CommentKind { 00031 RCK_Invalid, ///< Invalid comment 00032 RCK_OrdinaryBCPL, ///< Any normal BCPL comments 00033 RCK_OrdinaryC, ///< Any normal C comment 00034 RCK_BCPLSlash, ///< \code /// stuff \endcode 00035 RCK_BCPLExcl, ///< \code //! stuff \endcode 00036 RCK_JavaDoc, ///< \code /** stuff */ \endcode 00037 RCK_Qt, ///< \code /*! stuff */ \endcode, also used by HeaderDoc 00038 RCK_Merged ///< Two or more documentation comments merged together 00039 }; 00040 00041 RawComment() : Kind(RCK_Invalid), IsAlmostTrailingComment(false) { } 00042 00043 RawComment(const SourceManager &SourceMgr, SourceRange SR, 00044 bool Merged, bool ParseAllComments); 00045 00046 CommentKind getKind() const LLVM_READONLY { 00047 return (CommentKind) Kind; 00048 } 00049 00050 bool isInvalid() const LLVM_READONLY { 00051 return Kind == RCK_Invalid; 00052 } 00053 00054 bool isMerged() const LLVM_READONLY { 00055 return Kind == RCK_Merged; 00056 } 00057 00058 /// Is this comment attached to any declaration? 00059 bool isAttached() const LLVM_READONLY { 00060 return IsAttached; 00061 } 00062 00063 void setAttached() { 00064 IsAttached = true; 00065 } 00066 00067 /// Returns true if it is a comment that should be put after a member: 00068 /// \code ///< stuff \endcode 00069 /// \code //!< stuff \endcode 00070 /// \code /**< stuff */ \endcode 00071 /// \code /*!< stuff */ \endcode 00072 bool isTrailingComment() const LLVM_READONLY { 00073 assert(isDocumentation()); 00074 return IsTrailingComment; 00075 } 00076 00077 /// Returns true if it is a probable typo: 00078 /// \code //< stuff \endcode 00079 /// \code /*< stuff */ \endcode 00080 bool isAlmostTrailingComment() const LLVM_READONLY { 00081 return IsAlmostTrailingComment; 00082 } 00083 00084 /// Returns true if this comment is not a documentation comment. 00085 bool isOrdinary() const LLVM_READONLY { 00086 return ((Kind == RCK_OrdinaryBCPL) || (Kind == RCK_OrdinaryC)) && 00087 !ParseAllComments; 00088 } 00089 00090 /// Returns true if this comment any kind of a documentation comment. 00091 bool isDocumentation() const LLVM_READONLY { 00092 return !isInvalid() && !isOrdinary(); 00093 } 00094 00095 /// Returns whether we are parsing all comments. 00096 bool isParseAllComments() const LLVM_READONLY { 00097 return ParseAllComments; 00098 } 00099 00100 /// Returns raw comment text with comment markers. 00101 StringRef getRawText(const SourceManager &SourceMgr) const { 00102 if (RawTextValid) 00103 return RawText; 00104 00105 RawText = getRawTextSlow(SourceMgr); 00106 RawTextValid = true; 00107 return RawText; 00108 } 00109 00110 SourceRange getSourceRange() const LLVM_READONLY { return Range; } 00111 SourceLocation getLocStart() const LLVM_READONLY { return Range.getBegin(); } 00112 SourceLocation getLocEnd() const LLVM_READONLY { return Range.getEnd(); } 00113 00114 const char *getBriefText(const ASTContext &Context) const { 00115 if (BriefTextValid) 00116 return BriefText; 00117 00118 return extractBriefText(Context); 00119 } 00120 00121 /// Parse the comment, assuming it is attached to decl \c D. 00122 comments::FullComment *parse(const ASTContext &Context, 00123 const Preprocessor *PP, const Decl *D) const; 00124 00125 private: 00126 SourceRange Range; 00127 00128 mutable StringRef RawText; 00129 mutable const char *BriefText; 00130 00131 mutable bool RawTextValid : 1; ///< True if RawText is valid 00132 mutable bool BriefTextValid : 1; ///< True if BriefText is valid 00133 00134 unsigned Kind : 3; 00135 00136 /// True if comment is attached to a declaration in ASTContext. 00137 bool IsAttached : 1; 00138 00139 bool IsTrailingComment : 1; 00140 bool IsAlmostTrailingComment : 1; 00141 00142 /// When true, ordinary comments starting with "//" and "/*" will be 00143 /// considered as documentation comments. 00144 bool ParseAllComments : 1; 00145 00146 /// \brief Constructor for AST deserialization. 00147 RawComment(SourceRange SR, CommentKind K, bool IsTrailingComment, 00148 bool IsAlmostTrailingComment, 00149 bool ParseAllComments) : 00150 Range(SR), RawTextValid(false), BriefTextValid(false), Kind(K), 00151 IsAttached(false), IsTrailingComment(IsTrailingComment), 00152 IsAlmostTrailingComment(IsAlmostTrailingComment), 00153 ParseAllComments(ParseAllComments) 00154 { } 00155 00156 StringRef getRawTextSlow(const SourceManager &SourceMgr) const; 00157 00158 const char *extractBriefText(const ASTContext &Context) const; 00159 00160 friend class ASTReader; 00161 }; 00162 00163 /// \brief Compare comments' source locations. 00164 template<> 00165 class BeforeThanCompare<RawComment> { 00166 const SourceManager &SM; 00167 00168 public: 00169 explicit BeforeThanCompare(const SourceManager &SM) : SM(SM) { } 00170 00171 bool operator()(const RawComment &LHS, const RawComment &RHS) { 00172 return SM.isBeforeInTranslationUnit(LHS.getLocStart(), RHS.getLocStart()); 00173 } 00174 00175 bool operator()(const RawComment *LHS, const RawComment *RHS) { 00176 return operator()(*LHS, *RHS); 00177 } 00178 }; 00179 00180 /// \brief This class represents all comments included in the translation unit, 00181 /// sorted in order of appearance in the translation unit. 00182 class RawCommentList { 00183 public: 00184 RawCommentList(SourceManager &SourceMgr) : SourceMgr(SourceMgr) {} 00185 00186 void addComment(const RawComment &RC, llvm::BumpPtrAllocator &Allocator); 00187 00188 ArrayRef<RawComment *> getComments() const { 00189 return Comments; 00190 } 00191 00192 private: 00193 SourceManager &SourceMgr; 00194 std::vector<RawComment *> Comments; 00195 00196 void addDeserializedComments(ArrayRef<RawComment *> DeserializedComments); 00197 00198 friend class ASTReader; 00199 }; 00200 00201 } // end namespace clang 00202 00203 #endif