Clang Project

clang_source_code/include/clang/AST/RawCommentList.h
1//===--- RawCommentList.h - Classes for processing raw comments -*- C++ -*-===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8
9#ifndef LLVM_CLANG_AST_RAWCOMMENTLIST_H
10#define LLVM_CLANG_AST_RAWCOMMENTLIST_H
11
12#include "clang/Basic/CommentOptions.h"
13#include "clang/Basic/SourceManager.h"
14#include "llvm/ADT/ArrayRef.h"
15
16namespace clang {
17
18class ASTContext;
19class ASTReader;
20class Decl;
21class Preprocessor;
22
23namespace comments {
24  class FullComment;
25// end namespace comments
26
27class RawComment {
28public:
29  enum CommentKind {
30    RCK_Invalid,      ///< Invalid comment
31    RCK_OrdinaryBCPL///< Any normal BCPL comments
32    RCK_OrdinaryC,    ///< Any normal C comment
33    RCK_BCPLSlash,    ///< \code /// stuff \endcode
34    RCK_BCPLExcl,     ///< \code //! stuff \endcode
35    RCK_JavaDoc,      ///< \code /** stuff */ \endcode
36    RCK_Qt,           ///< \code /*! stuff */ \endcode, also used by HeaderDoc
37    RCK_Merged        ///< Two or more documentation comments merged together
38  };
39
40  RawComment() : Kind(RCK_Invalid), IsAlmostTrailingComment(false) { }
41
42  RawComment(const SourceManager &SourceMgrSourceRange SR,
43             const CommentOptions &CommentOptsbool Merged);
44
45  CommentKind getKind() const LLVM_READONLY {
46    return (CommentKind) Kind;
47  }
48
49  bool isInvalid() const LLVM_READONLY {
50    return Kind == RCK_Invalid;
51  }
52
53  bool isMerged() const LLVM_READONLY {
54    return Kind == RCK_Merged;
55  }
56
57  /// Is this comment attached to any declaration?
58  bool isAttached() const LLVM_READONLY {
59    return IsAttached;
60  }
61
62  void setAttached() {
63    IsAttached = true;
64  }
65
66  /// Returns true if it is a comment that should be put after a member:
67  /// \code ///< stuff \endcode
68  /// \code //!< stuff \endcode
69  /// \code /**< stuff */ \endcode
70  /// \code /*!< stuff */ \endcode
71  bool isTrailingComment() const LLVM_READONLY {
72    return IsTrailingComment;
73  }
74
75  /// Returns true if it is a probable typo:
76  /// \code //< stuff \endcode
77  /// \code /*< stuff */ \endcode
78  bool isAlmostTrailingComment() const LLVM_READONLY {
79    return IsAlmostTrailingComment;
80  }
81
82  /// Returns true if this comment is not a documentation comment.
83  bool isOrdinary() const LLVM_READONLY {
84    return ((Kind == RCK_OrdinaryBCPL) || (Kind == RCK_OrdinaryC));
85  }
86
87  /// Returns true if this comment any kind of a documentation comment.
88  bool isDocumentation() const LLVM_READONLY {
89    return !isInvalid() && !isOrdinary();
90  }
91
92  /// Returns raw comment text with comment markers.
93  StringRef getRawText(const SourceManager &SourceMgr) const {
94    if (RawTextValid)
95      return RawText;
96
97    RawText = getRawTextSlow(SourceMgr);
98    RawTextValid = true;
99    return RawText;
100  }
101
102  SourceRange getSourceRange() const LLVM_READONLY { return Range; }
103  SourceLocation getBeginLoc() const LLVM_READONLY { return Range.getBegin(); }
104  SourceLocation getEndLoc() const LLVM_READONLY { return Range.getEnd(); }
105
106  const char *getBriefText(const ASTContext &Context) const {
107    if (BriefTextValid)
108      return BriefText;
109
110    return extractBriefText(Context);
111  }
112
113  /// Returns sanitized comment text, suitable for presentation in editor UIs.
114  /// E.g. will transform:
115  ///     // This is a long multiline comment.
116  ///     //   Parts of it  might be indented.
117  ///     /* The comments styles might be mixed. */
118  ///  into
119  ///     "This is a long multiline comment.\n"
120  ///     "  Parts of it  might be indented.\n"
121  ///     "The comments styles might be mixed."
122  /// Also removes leading indentation and sanitizes some common cases:
123  ///     /* This is a first line.
124  ///      *   This is a second line. It is indented.
125  ///      * This is a third line. */
126  /// and
127  ///     /* This is a first line.
128  ///          This is a second line. It is indented.
129  ///     This is a third line. */
130  /// will both turn into:
131  ///     "This is a first line.\n"
132  ///     "  This is a second line. It is indented.\n"
133  ///     "This is a third line."
134  std::string getFormattedText(const SourceManager &SourceMgr,
135                               DiagnosticsEngine &Diags) const;
136
137  /// Parse the comment, assuming it is attached to decl \c D.
138  comments::FullComment *parse(const ASTContext &Context,
139                               const Preprocessor *PPconst Decl *Dconst;
140
141private:
142  SourceRange Range;
143
144  mutable StringRef RawText;
145  mutable const char *BriefText;
146
147  mutable bool RawTextValid : 1;   ///< True if RawText is valid
148  mutable bool BriefTextValid : 1///< True if BriefText is valid
149
150  unsigned Kind : 3;
151
152  /// True if comment is attached to a declaration in ASTContext.
153  bool IsAttached : 1;
154
155  bool IsTrailingComment : 1;
156  bool IsAlmostTrailingComment : 1;
157
158  /// Constructor for AST deserialization.
159  RawComment(SourceRange SRCommentKind Kbool IsTrailingComment,
160             bool IsAlmostTrailingComment) :
161    Range(SR), RawTextValid(false), BriefTextValid(false), Kind(K),
162    IsAttached(false), IsTrailingComment(IsTrailingComment),
163    IsAlmostTrailingComment(IsAlmostTrailingComment)
164  { }
165
166  StringRef getRawTextSlow(const SourceManager &SourceMgrconst;
167
168  const char *extractBriefText(const ASTContext &Contextconst;
169
170  friend class ASTReader;
171};
172
173/// Compare comments' source locations.
174template<>
175class BeforeThanCompare<RawComment> {
176  const SourceManager &SM;
177
178public:
179  explicit BeforeThanCompare(const SourceManager &SM) : SM(SM) { }
180
181  bool operator()(const RawComment &LHSconst RawComment &RHS) {
182    return SM.isBeforeInTranslationUnit(LHS.getBeginLoc(), RHS.getBeginLoc());
183  }
184
185  bool operator()(const RawComment *LHSconst RawComment *RHS) {
186    return operator()(*LHS, *RHS);
187  }
188};
189
190/// This class represents all comments included in the translation unit,
191/// sorted in order of appearance in the translation unit.
192class RawCommentList {
193public:
194  RawCommentList(SourceManager &SourceMgr) : SourceMgr(SourceMgr) {}
195
196  void addComment(const RawComment &RCconst CommentOptions &CommentOpts,
197                  llvm::BumpPtrAllocator &Allocator);
198
199  ArrayRef<RawComment *> getComments() const {
200    return Comments;
201  }
202
203private:
204  SourceManager &SourceMgr;
205  std::vector<RawComment *> Comments;
206
207  void addDeserializedComments(ArrayRef<RawComment *> DeserializedComments);
208
209  friend class ASTReader;
210};
211
212// end namespace clang
213
214#endif
215
clang::RawComment::CommentKind
clang::RawComment::getKind
clang::RawComment::parse
clang::RawComment::Range
clang::RawComment::RawText
clang::RawComment::BriefText
clang::RawComment::RawTextValid
clang::RawComment::BriefTextValid
clang::RawComment::Kind
clang::RawComment::IsAttached
clang::RawComment::IsTrailingComment
clang::RawComment::IsAlmostTrailingComment
clang::RawComment::getRawTextSlow
clang::RawComment::extractBriefText
clang::BeforeThanCompare::SM
clang::RawCommentList::addComment
clang::RawCommentList::getComments
clang::RawCommentList::SourceMgr
clang::RawCommentList::Comments
clang::RawCommentList::addDeserializedComments