Author: djasper Date: Tue Oct 6 06:54:18 2015 New Revision: 249392 URL: http://llvm.org/viewvc/llvm-project?rev=249392&view=rev Log: clang-format: Make IncludeCategories configurable in .clang-format file.
This was made much easier by introducing an IncludeCategory struct to replace the previously used std::pair. Also, cleaned up documentation and added examples. Modified: cfe/trunk/docs/ClangFormatStyleOptions.rst cfe/trunk/docs/tools/dump_format_style.py cfe/trunk/include/clang/Format/Format.h cfe/trunk/lib/Format/Format.cpp cfe/trunk/unittests/Format/FormatTest.cpp Modified: cfe/trunk/docs/ClangFormatStyleOptions.rst URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/docs/ClangFormatStyleOptions.rst?rev=249392&r1=249391&r2=249392&view=diff ============================================================================== --- cfe/trunk/docs/ClangFormatStyleOptions.rst (original) +++ cfe/trunk/docs/ClangFormatStyleOptions.rst Tue Oct 6 06:54:18 2015 @@ -155,21 +155,29 @@ the configuration (without a prefix: ``A This applies to round brackets (parentheses), angle brackets and square brackets. This will result in formattings like - \code - someLongFunction(argument1, - argument2); - \endcode + .. code-block:: c++ + someLongFunction(argument1, + argument2); **AlignConsecutiveAssignments** (``bool``) If ``true``, aligns consecutive assignments. This will align the assignment operators of consecutive lines. This will result in formattings like - \code - int aaaa = 12; - int b = 23; - int ccc = 23; - \endcode + .. code-block:: c++ + int aaaa = 12; + int b = 23; + int ccc = 23; + +**AlignConsecutiveDeclarations** (``bool``) + If ``true``, aligns consecutive declarations. + + This will align the declaration names of consecutive lines. This + will result in formattings like + .. code-block:: c++ + int aaaa = 12; + float b = 23; + std::string ccc = 23; **AlignEscapedNewlinesLeft** (``bool``) If ``true``, aligns escaped newlines as far left as possible. @@ -381,14 +389,17 @@ the configuration (without a prefix: ``A instead of as function calls. These are expected to be macros of the form: - \code - FOREACH(<variable-declaration>, ...) - <loop-body> - \endcode + .. code-block:: c++ + FOREACH(<variable-declaration>, ...) + <loop-body> + + In the .clang-format configuration file, this can be configured like: + .. code-block:: c++ + ForEachMacros: ['RANGES_FOR', 'FOREACH'] For example: BOOST_FOREACH. -**IncludeCategories** (``std::vector<std::pair<std::string, unsigned>>``) +**IncludeCategories** (``std::vector<IncludeCategory>``) Regular expressions denoting the different #include categories used for ordering #includes. @@ -403,6 +414,16 @@ the configuration (without a prefix: ``A so that it is kept at the beginning of the #includes (http://llvm.org/docs/CodingStandards.html#include-style). + To configure this in the .clang-format file, use: + .. code-block:: c++ + IncludeCategories: + - Regex: '^"(llvm|llvm-c|clang|clang-c)/' + Priority: 2 + - Regex: '^(<|"(gtest|isl|json)/)' + Priority: 3 + - Regex: '.\*' + Priority: 1 + **IndentCaseLabels** (``bool``) Indent case labels one level from the switch statement. Modified: cfe/trunk/docs/tools/dump_format_style.py URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/docs/tools/dump_format_style.py?rev=249392&r1=249391&r2=249392&view=diff ============================================================================== --- cfe/trunk/docs/tools/dump_format_style.py (original) +++ cfe/trunk/docs/tools/dump_format_style.py Tue Oct 6 06:54:18 2015 @@ -86,7 +86,11 @@ class EnumValue: doxygen2rst(indent(self.comment, 2))) def clean_comment_line(line): - return line[3:].strip() + '\n' + if line == '/// \\code': + return '.. code-block:: c++\n' + if line == '/// \\endcode': + return '' + return line[4:] + '\n' def read_options(header): class State: @@ -139,8 +143,6 @@ def read_options(header): elif line == '};': state = State.InStruct nested_structs[nested_struct.name] = nested_struct - else: - raise Exception('Invalid format, expected struct field comment or };') elif state == State.InNestedFieldComent: if line.startswith('///'): comment += clean_comment_line(line) @@ -168,7 +170,7 @@ def read_options(header): for option in options: if not option.type in ['bool', 'unsigned', 'int', 'std::string', 'std::vector<std::string>', - 'std::vector<std::pair<std::string, unsigned>>']: + 'std::vector<IncludeCategory>']: if enums.has_key(option.type): option.enum = enums[option.type] elif nested_structs.has_key(option.type): Modified: cfe/trunk/include/clang/Format/Format.h URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Format/Format.h?rev=249392&r1=249391&r2=249392&view=diff ============================================================================== --- cfe/trunk/include/clang/Format/Format.h (original) +++ cfe/trunk/include/clang/Format/Format.h Tue Oct 6 06:54:18 2015 @@ -48,8 +48,8 @@ struct FormatStyle { /// This applies to round brackets (parentheses), angle brackets and square /// brackets. This will result in formattings like /// \code - /// someLongFunction(argument1, - /// argument2); + /// someLongFunction(argument1, + /// argument2); /// \endcode bool AlignAfterOpenBracket; @@ -58,9 +58,9 @@ struct FormatStyle { /// This will align the assignment operators of consecutive lines. This /// will result in formattings like /// \code - /// int aaaa = 12; - /// int b = 23; - /// int ccc = 23; + /// int aaaa = 12; + /// int b = 23; + /// int ccc = 23; /// \endcode bool AlignConsecutiveAssignments; @@ -69,9 +69,9 @@ struct FormatStyle { /// This will align the declaration names of consecutive lines. This /// will result in formattings like /// \code - /// int aaaa = 12; - /// float b = 23; - /// std::string ccc = 23; + /// int aaaa = 12; + /// float b = 23; + /// std::string ccc = 23; /// \endcode bool AlignConsecutiveDeclarations; @@ -297,13 +297,29 @@ struct FormatStyle { /// /// These are expected to be macros of the form: /// \code - /// FOREACH(<variable-declaration>, ...) - /// <loop-body> + /// FOREACH(<variable-declaration>, ...) + /// <loop-body> + /// \endcode + /// + /// In the .clang-format configuration file, this can be configured like: + /// \code + /// ForEachMacros: ['RANGES_FOR', 'FOREACH'] /// \endcode /// /// For example: BOOST_FOREACH. std::vector<std::string> ForEachMacros; + /// \brief See documentation of \c IncludeCategories. + struct IncludeCategory { + /// \brief The regular expression that this category matches. + std::string Regex; + /// \brief The priority to assign to this category. + unsigned Priority; + bool operator==(const IncludeCategory &Other) const { + return Regex == Other.Regex && Priority == Other.Priority; + } + }; + /// \brief Regular expressions denoting the different #include categories used /// for ordering #includes. /// @@ -317,7 +333,18 @@ struct FormatStyle { /// category. The main header for a source file automatically gets category 0, /// so that it is kept at the beginning of the #includes /// (http://llvm.org/docs/CodingStandards.html#include-style). - std::vector<std::pair<std::string, unsigned>> IncludeCategories; + /// + /// To configure this in the .clang-format file, use: + /// \code + /// IncludeCategories: + /// - Regex: '^"(llvm|llvm-c|clang|clang-c)/' + /// Priority: 2 + /// - Regex: '^(<|"(gtest|isl|json)/)' + /// Priority: 3 + /// - Regex: '.*' + /// Priority: 1 + /// \endcode + std::vector<IncludeCategory> IncludeCategories; /// \brief Indent case labels one level from the switch statement. /// @@ -546,6 +573,7 @@ struct FormatStyle { ExperimentalAutoDetectBinPacking == R.ExperimentalAutoDetectBinPacking && ForEachMacros == R.ForEachMacros && + IncludeCategories == R.IncludeCategories && IndentCaseLabels == R.IndentCaseLabels && IndentWidth == R.IndentWidth && Language == R.Language && IndentWrappedFunctionNames == R.IndentWrappedFunctionNames && Modified: cfe/trunk/lib/Format/Format.cpp URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Format/Format.cpp?rev=249392&r1=249391&r2=249392&view=diff ============================================================================== --- cfe/trunk/lib/Format/Format.cpp (original) +++ cfe/trunk/lib/Format/Format.cpp Tue Oct 6 06:54:18 2015 @@ -37,6 +37,7 @@ using clang::format::FormatStyle; LLVM_YAML_IS_FLOW_SEQUENCE_VECTOR(std::string) +LLVM_YAML_IS_SEQUENCE_VECTOR(clang::format::FormatStyle::IncludeCategory) namespace llvm { namespace yaml { @@ -247,6 +248,7 @@ template <> struct MappingTraits<FormatS IO.mapOptional("ExperimentalAutoDetectBinPacking", Style.ExperimentalAutoDetectBinPacking); IO.mapOptional("ForEachMacros", Style.ForEachMacros); + IO.mapOptional("IncludeCategories", Style.IncludeCategories); IO.mapOptional("IndentCaseLabels", Style.IndentCaseLabels); IO.mapOptional("IndentWidth", Style.IndentWidth); IO.mapOptional("IndentWrappedFunctionNames", @@ -307,6 +309,13 @@ template <> struct MappingTraits<FormatS } }; +template <> struct MappingTraits<FormatStyle::IncludeCategory> { + static void mapping(IO &IO, FormatStyle::IncludeCategory &Category) { + IO.mapOptional("Regex", Category.Regex); + IO.mapOptional("Priority", Category.Priority); + } +}; + // Allows to read vector<FormatStyle> while keeping default values. // IO.getContext() should contain a pointer to the FormatStyle structure, that // will be used to get default values for missing keys. @@ -1737,8 +1746,8 @@ tooling::Replacements sortIncludes(const // Create pre-compiled regular expressions for the #include categories. SmallVector<llvm::Regex, 4> CategoryRegexs; - for (const auto &IncludeBlock : Style.IncludeCategories) - CategoryRegexs.emplace_back(IncludeBlock.first); + for (const auto &Category : Style.IncludeCategories) + CategoryRegexs.emplace_back(Category.Regex); for (;;) { auto Pos = Code.find('\n', SearchFrom); @@ -1753,7 +1762,7 @@ tooling::Replacements sortIncludes(const Category = UINT_MAX; for (unsigned i = 0, e = CategoryRegexs.size(); i != e; ++i) { if (CategoryRegexs[i].match(Matches[1])) { - Category = Style.IncludeCategories[i].second; + Category = Style.IncludeCategories[i].Priority; break; } } Modified: cfe/trunk/unittests/Format/FormatTest.cpp URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/unittests/Format/FormatTest.cpp?rev=249392&r1=249391&r2=249392&view=diff ============================================================================== --- cfe/trunk/unittests/Format/FormatTest.cpp (original) +++ cfe/trunk/unittests/Format/FormatTest.cpp Tue Oct 6 06:54:18 2015 @@ -9646,6 +9646,8 @@ TEST_F(FormatTest, ParsesConfiguration) CHECK_PARSE("NamespaceIndentation: All", NamespaceIndentation, FormatStyle::NI_All); + // FIXME: This is required because parsing a configuration simply overwrites + // the first N elements of the list instead of resetting it. Style.ForEachMacros.clear(); std::vector<std::string> BoostForeach; BoostForeach.push_back("BOOST_FOREACH"); @@ -9655,6 +9657,16 @@ TEST_F(FormatTest, ParsesConfiguration) BoostAndQForeach.push_back("Q_FOREACH"); CHECK_PARSE("ForEachMacros: [BOOST_FOREACH, Q_FOREACH]", ForEachMacros, BoostAndQForeach); + + Style.IncludeCategories.clear(); + std::vector<FormatStyle::IncludeCategory> ExpectedCategories = {{"abc/.*", 2}, + {".*", 1}}; + CHECK_PARSE("IncludeCategories:\n" + " - Regex: abc/.*\n" + " Priority: 2\n" + " - Regex: .*\n" + " Priority: 1", + IncludeCategories, ExpectedCategories); } TEST_F(FormatTest, ParsesConfigurationWithLanguages) { _______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits