diff --git a/docs/UsersManual.rst b/docs/UsersManual.rst index 6cc836130f9bd608cb24de5be1f465281786e095..97784f1b1bc650e1ff20c6504b3b5545d0f24aec 100644 --- a/docs/UsersManual.rst +++ b/docs/UsersManual.rst @@ -1005,6 +1005,19 @@ below. If multiple flags are present, the last one is used. Generate complete debug info. +Comment Parsing Options +-------------------------- + +Clang parses Doxygen and non-Doxygen style documentation comments and attaches +them to the appropriate declaration nodes. By default, it only parses +Doxygen-style comments and ignores ordinary comments starting with ``//`` and +``/*``. + +.. option:: -fparse-all-comments + + Parse all comments as documentation comments (including ordinary comments + starting with ``//`` and ``/*``). + .. _c: C Language Features diff --git a/include/clang/AST/RawCommentList.h b/include/clang/AST/RawCommentList.h index 3a8b2183a557d218bd924f3c5fcab1ffd86e2efa..7e8bf044c1e0c1a556792ad747190080d18a6d0c 100644 --- a/include/clang/AST/RawCommentList.h +++ b/include/clang/AST/RawCommentList.h @@ -10,6 +10,7 @@ #ifndef LLVM_CLANG_AST_RAW_COMMENT_LIST_H #define LLVM_CLANG_AST_RAW_COMMENT_LIST_H +#include "clang/Basic/CommentOptions.h" #include "clang/Basic/SourceManager.h" #include "llvm/ADT/ArrayRef.h" @@ -40,7 +41,7 @@ public: RawComment() : Kind(RCK_Invalid), IsAlmostTrailingComment(false) { } RawComment(const SourceManager &SourceMgr, SourceRange SR, - bool Merged = false); + bool Merged, bool ParseAllComments); CommentKind getKind() const LLVM_READONLY { return (CommentKind) Kind; @@ -82,12 +83,18 @@ public: /// Returns true if this comment is not a documentation comment. bool isOrdinary() const LLVM_READONLY { - return (Kind == RCK_OrdinaryBCPL) || (Kind == RCK_OrdinaryC); + return ((Kind == RCK_OrdinaryBCPL) || (Kind == RCK_OrdinaryC)) && + !ParseAllComments; } /// Returns true if this comment any kind of a documentation comment. bool isDocumentation() const LLVM_READONLY { - return !isInvalid() && !isOrdinary(); + return !isInvalid() && (!isOrdinary() || ParseAllComments); + } + + /// Returns whether we are parsing all comments. + bool isParseAllComments() const LLVM_READONLY { + return ParseAllComments; } /// Returns raw comment text with comment markers. @@ -135,6 +142,10 @@ private: bool IsTrailingComment : 1; bool IsAlmostTrailingComment : 1; + /// When true, ordinary comments starting with "//" and "/*" will be + /// considered as documentation comments. + bool ParseAllComments : 1; + mutable bool BeginLineValid : 1; ///< True if BeginLine is valid mutable bool EndLineValid : 1; ///< True if EndLine is valid mutable unsigned BeginLine; ///< Cached line number @@ -142,10 +153,12 @@ private: /// \brief Constructor for AST deserialization. RawComment(SourceRange SR, CommentKind K, bool IsTrailingComment, - bool IsAlmostTrailingComment) : + bool IsAlmostTrailingComment, + bool ParseAllComments) : Range(SR), RawTextValid(false), BriefTextValid(false), Kind(K), IsAttached(false), IsTrailingComment(IsTrailingComment), IsAlmostTrailingComment(IsAlmostTrailingComment), + ParseAllComments(ParseAllComments), BeginLineValid(false), EndLineValid(false) { } @@ -207,4 +220,3 @@ private: } // end namespace clang #endif - diff --git a/include/clang/Basic/CommentOptions.h b/include/clang/Basic/CommentOptions.h index 79b9a6b88350cf5c4cb1a0531f6f99d8412e6a12..7991875838a47995bcbb9c5f9d36dc506ebf65ca 100644 --- a/include/clang/Basic/CommentOptions.h +++ b/include/clang/Basic/CommentOptions.h @@ -27,6 +27,11 @@ struct CommentOptions { /// \brief Command names to treat as block commands in comments. /// Should not include the leading backslash. BlockCommandNamesTy BlockCommandNames; + + /// \brief Treat ordinary comments as documentation comments. + bool ParseAllComments; + + CommentOptions() : ParseAllComments(false) { } }; } // end namespace clang diff --git a/include/clang/Driver/Options.td b/include/clang/Driver/Options.td index 112feb77b1c9dc94be80f43e20c5fcc459a7740e..b9cf026fee111a7f8d50109b0168fe5b526a8414 100644 --- a/include/clang/Driver/Options.td +++ b/include/clang/Driver/Options.td @@ -330,6 +330,7 @@ def fcolor_diagnostics : Flag<["-"], "fcolor-diagnostics">, Group<f_Group>, Flag def fcomment_block_commands : CommaJoined<["-"], "fcomment-block-commands=">, Group<f_clang_Group>, Flags<[CC1Option]>, HelpText<"Treat each comma separated argument in <arg> as a documentation comment block command">, MetaVarName<"<arg>">; +def fparse_all_comments : Flag<["-"], "fparse-all-comments">, Group<f_clang_Group>, Flags<[CC1Option]>; def fcommon : Flag<["-"], "fcommon">, Group<f_Group>; def fcompile_resource_EQ : Joined<["-"], "fcompile-resource=">, Group<f_Group>; def fconstant_cfstrings : Flag<["-"], "fconstant-cfstrings">, Group<f_Group>; diff --git a/lib/AST/ASTContext.cpp b/lib/AST/ASTContext.cpp index 7245c0316082972dcda84cf77e5b4eecd04ee5d4..170cc0298b3a716c368ce418d5516c54b87fb120 100644 --- a/lib/AST/ASTContext.cpp +++ b/lib/AST/ASTContext.cpp @@ -141,7 +141,9 @@ RawComment *ASTContext::getRawCommentForDeclNoCache(const Decl *D) const { // When searching for comments during parsing, the comment we are looking // for is usually among the last two comments we parsed -- check them // first. - RawComment CommentAtDeclLoc(SourceMgr, SourceRange(DeclLoc)); + RawComment CommentAtDeclLoc( + SourceMgr, SourceRange(DeclLoc), false, + LangOpts.CommentOpts.ParseAllComments); BeforeThanCompare<RawComment> Compare(SourceMgr); ArrayRef<RawComment *>::iterator MaybeBeforeDecl = RawComments.end() - 1; bool Found = Compare(*MaybeBeforeDecl, &CommentAtDeclLoc); diff --git a/lib/AST/RawCommentList.cpp b/lib/AST/RawCommentList.cpp index f2386a56fcc719fc5108ea3820f0be9b095ad98d..78164593806983bbe1c474ebb8b913cb89836f1a 100644 --- a/lib/AST/RawCommentList.cpp +++ b/lib/AST/RawCommentList.cpp @@ -63,9 +63,10 @@ bool mergedCommentIsTrailingComment(StringRef Comment) { } // unnamed namespace RawComment::RawComment(const SourceManager &SourceMgr, SourceRange SR, - bool Merged) : + bool Merged, bool ParseAllComments) : Range(SR), RawTextValid(false), BriefTextValid(false), IsAttached(false), IsAlmostTrailingComment(false), + ParseAllComments(ParseAllComments), BeginLineValid(false), EndLineValid(false) { // Extract raw comment text, if possible. if (SR.getBegin() == SR.getEnd() || getRawText(SourceMgr).empty()) { @@ -253,7 +254,8 @@ void RawCommentList::addComment(const RawComment &RC, if (C1EndLine + 1 == C2BeginLine || C1EndLine == C2BeginLine) { SourceRange MergedRange(C1.getSourceRange().getBegin(), C2.getSourceRange().getEnd()); - *Comments.back() = RawComment(SourceMgr, MergedRange, true); + *Comments.back() = RawComment(SourceMgr, MergedRange, true, + RC.isParseAllComments()); Merged = true; } } @@ -262,4 +264,3 @@ void RawCommentList::addComment(const RawComment &RC, OnlyWhitespaceSeen = true; } - diff --git a/lib/Driver/Tools.cpp b/lib/Driver/Tools.cpp index 02ebc0448fed3d7dd0e25ef417f63a53717e6df9..253c2dc7a1f9e31c6c852ddaf789006dfce9fffe 100644 --- a/lib/Driver/Tools.cpp +++ b/lib/Driver/Tools.cpp @@ -3294,6 +3294,8 @@ void Clang::ConstructJob(Compilation &C, const JobAction &JA, // Forward -fcomment-block-commands to -cc1. Args.AddAllArgs(CmdArgs, options::OPT_fcomment_block_commands); + // Forward -fparse-all-comments to -cc1. + Args.AddAllArgs(CmdArgs, options::OPT_fparse_all_comments); // Forward -Xclang arguments to -cc1, and -mllvm arguments to the LLVM option // parser. diff --git a/lib/Frontend/CompilerInvocation.cpp b/lib/Frontend/CompilerInvocation.cpp index 324b6e38306424e1a107027723b4987c1120331c..ed207e66fa97cbd276cc264d18d4bd51b09f6311 100644 --- a/lib/Frontend/CompilerInvocation.cpp +++ b/lib/Frontend/CompilerInvocation.cpp @@ -281,6 +281,7 @@ static bool ParseMigratorArgs(MigratorOptions &Opts, ArgList &Args) { static void ParseCommentArgs(CommentOptions &Opts, ArgList &Args) { Opts.BlockCommandNames = Args.getAllArgValues(OPT_fcomment_block_commands); + Opts.ParseAllComments = Args.hasArg(OPT_fparse_all_comments); } static bool ParseCodeGenArgs(CodeGenOptions &Opts, ArgList &Args, InputKind IK, diff --git a/lib/Sema/Sema.cpp b/lib/Sema/Sema.cpp index e271f78ed0c556ce5c9b470585a02adf338589a0..6425f34ff5fe723345fc5bda832bbb75fd1aaf9c 100644 --- a/lib/Sema/Sema.cpp +++ b/lib/Sema/Sema.cpp @@ -1077,7 +1077,8 @@ void Sema::ActOnComment(SourceRange Comment) { if (!LangOpts.RetainCommentsFromSystemHeaders && SourceMgr.isInSystemHeader(Comment.getBegin())) return; - RawComment RC(SourceMgr, Comment); + RawComment RC(SourceMgr, Comment, false, + LangOpts.CommentOpts.ParseAllComments); if (RC.isAlmostTrailingComment()) { SourceRange MagicMarkerRange(Comment.getBegin(), Comment.getBegin().getLocWithOffset(3)); diff --git a/lib/Serialization/ASTReader.cpp b/lib/Serialization/ASTReader.cpp index d9844152b7409af200572be8e771463f4227845e..c8b3e93a8706eb23cb9ba9058dca0a0e6e019ba7 100644 --- a/lib/Serialization/ASTReader.cpp +++ b/lib/Serialization/ASTReader.cpp @@ -3907,6 +3907,7 @@ bool ASTReader::ParseLanguageOptions(const RecordData &Record, LangOpts.CommentOpts.BlockCommandNames.push_back( ReadString(Record, Idx)); } + LangOpts.CommentOpts.ParseAllComments = Record[Idx++]; return Listener.ReadLanguageOptions(LangOpts, Complain); } @@ -7165,9 +7166,9 @@ void ASTReader::ReadComments() { (RawComment::CommentKind) Record[Idx++]; bool IsTrailingComment = Record[Idx++]; bool IsAlmostTrailingComment = Record[Idx++]; - Comments.push_back(new (Context) RawComment(SR, Kind, - IsTrailingComment, - IsAlmostTrailingComment)); + Comments.push_back(new (Context) RawComment( + SR, Kind, IsTrailingComment, IsAlmostTrailingComment, + Context.getLangOpts().CommentOpts.ParseAllComments)); break; } } diff --git a/lib/Serialization/ASTWriter.cpp b/lib/Serialization/ASTWriter.cpp index cf93d1cf01a7cf28d7915fd91690c16aa46cea85..03e33ad369aef430e344184edea9b26d8f6f409b 100644 --- a/lib/Serialization/ASTWriter.cpp +++ b/lib/Serialization/ASTWriter.cpp @@ -1069,6 +1069,7 @@ void ASTWriter::WriteControlBlock(Preprocessor &PP, ASTContext &Context, I != IEnd; ++I) { AddString(*I, Record); } + Record.push_back(LangOpts.CommentOpts.ParseAllComments); Stream.EmitRecord(LANGUAGE_OPTIONS, Record);