mirror of
https://github.com/Kitware/CMake.git
synced 2026-01-09 15:20:56 -06:00
Merge branch 'backport-fix-co-compile' into fix-co-compile
Resolve a logical conflict by replacing `cmArray{Begin,End}` from
the their side with `cm::{cbegin,cend}` from our side.
This commit is contained in:
137
Source/cmcmd.cxx
137
Source/cmcmd.cxx
@@ -33,16 +33,14 @@
|
||||
#include "cmsys/Process.h"
|
||||
#include "cmsys/Terminal.h"
|
||||
#include <algorithm>
|
||||
#include <functional>
|
||||
#include <iostream>
|
||||
#include <iterator>
|
||||
#include <map>
|
||||
#include <memory> // IWYU pragma: keep
|
||||
#include <sstream>
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <time.h>
|
||||
#include <utility>
|
||||
|
||||
class cmConnection;
|
||||
|
||||
@@ -161,7 +159,8 @@ static bool cmTarFilesFrom(std::string const& file,
|
||||
return true;
|
||||
}
|
||||
|
||||
int cmcmd::HandleIWYU(const std::string& runCmd, const std::string&,
|
||||
static int HandleIWYU(const std::string& runCmd,
|
||||
const std::string& /* sourceFile */,
|
||||
const std::vector<std::string>& orig_cmd)
|
||||
{
|
||||
// Construct the iwyu command line by taking what was given
|
||||
@@ -188,7 +187,7 @@ int cmcmd::HandleIWYU(const std::string& runCmd, const std::string&,
|
||||
return 0;
|
||||
}
|
||||
|
||||
int cmcmd::HandleTidy(const std::string& runCmd, const std::string& sourceFile,
|
||||
static int HandleTidy(const std::string& runCmd, const std::string& sourceFile,
|
||||
const std::vector<std::string>& orig_cmd)
|
||||
{
|
||||
// Construct the clang-tidy command line by taking what was given
|
||||
@@ -219,7 +218,8 @@ int cmcmd::HandleTidy(const std::string& runCmd, const std::string& sourceFile,
|
||||
return ret;
|
||||
}
|
||||
|
||||
int cmcmd::HandleLWYU(const std::string& runCmd, const std::string&,
|
||||
static int HandleLWYU(const std::string& runCmd,
|
||||
const std::string& /* sourceFile */,
|
||||
const std::vector<std::string>&)
|
||||
{
|
||||
// Construct the ldd -r -u (link what you use lwyu) command line
|
||||
@@ -251,7 +251,7 @@ int cmcmd::HandleLWYU(const std::string& runCmd, const std::string&,
|
||||
return 0;
|
||||
}
|
||||
|
||||
int cmcmd::HandleCppLint(const std::string& runCmd,
|
||||
static int HandleCppLint(const std::string& runCmd,
|
||||
const std::string& sourceFile,
|
||||
const std::vector<std::string>&)
|
||||
{
|
||||
@@ -275,7 +275,7 @@ int cmcmd::HandleCppLint(const std::string& runCmd,
|
||||
return ret;
|
||||
}
|
||||
|
||||
int cmcmd::HandleCppCheck(const std::string& runCmd,
|
||||
static int HandleCppCheck(const std::string& runCmd,
|
||||
const std::string& sourceFile,
|
||||
const std::vector<std::string>& orig_cmd)
|
||||
{
|
||||
@@ -327,60 +327,70 @@ int cmcmd::HandleCppCheck(const std::string& runCmd,
|
||||
return 0;
|
||||
}
|
||||
|
||||
typedef int (*CoCompileHandler)(const std::string&, const std::string&,
|
||||
const std::vector<std::string>&);
|
||||
|
||||
struct CoCompiler
|
||||
{
|
||||
const char* Option;
|
||||
CoCompileHandler Handler;
|
||||
bool NoOriginalCommand;
|
||||
};
|
||||
|
||||
static CoCompiler CoCompilers[] = { // Table of options and handlers.
|
||||
{ "--cppcheck=", HandleCppCheck, false },
|
||||
{ "--cpplint=", HandleCppLint, false },
|
||||
{ "--iwyu=", HandleIWYU, false },
|
||||
{ "--lwyu=", HandleLWYU, true },
|
||||
{ "--tidy=", HandleTidy, false }
|
||||
};
|
||||
|
||||
struct CoCompileJob
|
||||
{
|
||||
std::string Command;
|
||||
CoCompileHandler Handler;
|
||||
};
|
||||
|
||||
// called when args[0] == "__run_co_compile"
|
||||
int cmcmd::HandleCoCompileCommands(std::vector<std::string>& args)
|
||||
{
|
||||
// initialize a map from command option to handler function
|
||||
std::map<std::string,
|
||||
std::function<int(const std::string&, const std::string&,
|
||||
const std::vector<std::string>&)>>
|
||||
coCompileTypes;
|
||||
auto a1 = std::placeholders::_1;
|
||||
auto a2 = std::placeholders::_2;
|
||||
auto a3 = std::placeholders::_3;
|
||||
// create a map from option to handler function for option
|
||||
// if the option does not call the original command then it will need
|
||||
// to set runOriginalCmd to false later in this function
|
||||
coCompileTypes["--iwyu="] = std::bind(&cmcmd::HandleIWYU, a1, a2, a3);
|
||||
coCompileTypes["--tidy="] = std::bind(&cmcmd::HandleTidy, a1, a2, a3);
|
||||
coCompileTypes["--lwyu="] = std::bind(&cmcmd::HandleLWYU, a1, a2, a3);
|
||||
coCompileTypes["--cpplint="] = std::bind(&cmcmd::HandleCppLint, a1, a2, a3);
|
||||
coCompileTypes["--cppcheck="] =
|
||||
std::bind(&cmcmd::HandleCppCheck, a1, a2, a3);
|
||||
// copy the command options to a vector of strings
|
||||
std::vector<std::string> commandOptions;
|
||||
commandOptions.reserve(coCompileTypes.size());
|
||||
for (const auto& i : coCompileTypes) {
|
||||
commandOptions.push_back(i.first);
|
||||
}
|
||||
std::vector<CoCompileJob> jobs;
|
||||
std::string sourceFile; // store --source=
|
||||
|
||||
// Default is to run the original command found after -- if the option
|
||||
// does not need to do that, it should be specified here, currently only
|
||||
// lwyu does that.
|
||||
bool runOriginalCmd = true;
|
||||
|
||||
std::string runCmd; // command to be run from --thing=command
|
||||
std::string sourceFile; // store --source=
|
||||
std::string commandFound; // the command that was in the args list
|
||||
std::vector<std::string> orig_cmd;
|
||||
bool doing_options = true;
|
||||
for (std::string::size_type cc = 2; cc < args.size(); cc++) {
|
||||
std::string const& arg = args[cc];
|
||||
for (std::string::size_type i = 2; i < args.size(); ++i) {
|
||||
std::string const& arg = args[i];
|
||||
// if the arg is -- then the rest of the args after
|
||||
// go into orig_cmd
|
||||
if (arg == "--") {
|
||||
doing_options = false;
|
||||
} else if (doing_options) {
|
||||
bool optionFound = false;
|
||||
// check arg against all the commandOptions
|
||||
for (auto const& command : commandOptions) {
|
||||
if (arg.compare(0, command.size(), command) == 0) {
|
||||
for (CoCompiler const* cc = cm::cbegin(CoCompilers);
|
||||
cc != cm::cend(CoCompilers); ++cc) {
|
||||
size_t optionLen = strlen(cc->Option);
|
||||
if (arg.compare(0, optionLen, cc->Option) == 0) {
|
||||
optionFound = true;
|
||||
runCmd = arg.substr(command.size());
|
||||
commandFound = command;
|
||||
CoCompileJob job;
|
||||
job.Command = arg.substr(optionLen);
|
||||
job.Handler = cc->Handler;
|
||||
jobs.push_back(std::move(job));
|
||||
if (cc->NoOriginalCommand) {
|
||||
runOriginalCmd = false;
|
||||
}
|
||||
}
|
||||
}
|
||||
// check arg with --source=
|
||||
if (cmHasLiteralPrefix(arg, "--source=")) {
|
||||
sourceFile = arg.substr(9);
|
||||
optionFound = true;
|
||||
}
|
||||
// if it was not a commandOptions or --source then error
|
||||
// if it was not a co-compiler or --source then error
|
||||
if (!optionFound) {
|
||||
std::cerr << "__run_co_compile given unknown argument: " << arg
|
||||
<< "\n";
|
||||
@@ -390,39 +400,40 @@ int cmcmd::HandleCoCompileCommands(std::vector<std::string>& args)
|
||||
orig_cmd.push_back(arg);
|
||||
}
|
||||
}
|
||||
if (commandFound.empty()) {
|
||||
std::cerr << "__run_co_compile missing command to run. Looking for one of "
|
||||
"the following:\n";
|
||||
for (const auto& i : commandOptions) {
|
||||
std::cerr << i << "\n";
|
||||
if (jobs.empty()) {
|
||||
std::cerr << "__run_co_compile missing command to run. "
|
||||
"Looking for one or more of the following:\n";
|
||||
for (CoCompiler const* cc = cm::cbegin(CoCompilers);
|
||||
cc != cm::cend(CoCompilers); ++cc) {
|
||||
std::cerr << cc->Option << "\n";
|
||||
}
|
||||
return 1;
|
||||
}
|
||||
// Default is to run the original command found after -- if the option
|
||||
// does not need to do that, it should be specified here, currently only
|
||||
// lwyu does that.
|
||||
bool runOriginalCmd = true;
|
||||
if (commandFound == "--lwyu=") {
|
||||
runOriginalCmd = false;
|
||||
}
|
||||
|
||||
if (runOriginalCmd && orig_cmd.empty()) {
|
||||
std::cerr << "__run_co_compile missing compile command after --\n";
|
||||
return 1;
|
||||
}
|
||||
|
||||
// call the command handler here
|
||||
int ret = coCompileTypes[commandFound](runCmd, sourceFile, orig_cmd);
|
||||
// if the command returns non-zero then return and fail.
|
||||
// for commands that do not want to break the build, they should return
|
||||
// 0 no matter what.
|
||||
if (ret != 0) {
|
||||
return ret;
|
||||
for (CoCompileJob const& job : jobs) {
|
||||
// call the command handler here
|
||||
int ret = job.Handler(job.Command, sourceFile, orig_cmd);
|
||||
|
||||
// if the command returns non-zero then return and fail.
|
||||
// for commands that do not want to break the build, they should return
|
||||
// 0 no matter what.
|
||||
if (ret != 0) {
|
||||
return ret;
|
||||
}
|
||||
}
|
||||
|
||||
// if there is no original command to run return now
|
||||
if (!runOriginalCmd) {
|
||||
return ret;
|
||||
return 0;
|
||||
}
|
||||
|
||||
// Now run the real compiler command and return its result value
|
||||
int ret;
|
||||
if (!cmSystemTools::RunSingleCommand(orig_cmd, nullptr, nullptr, &ret,
|
||||
nullptr,
|
||||
cmSystemTools::OUTPUT_PASSTHROUGH)) {
|
||||
|
||||
@@ -18,24 +18,6 @@ public:
|
||||
*/
|
||||
static int ExecuteCMakeCommand(std::vector<std::string>&);
|
||||
|
||||
// define co-compile command handlers they must be public
|
||||
// because they are used in a std::function map
|
||||
static int HandleIWYU(const std::string& runCmd,
|
||||
const std::string& sourceFile,
|
||||
const std::vector<std::string>& orig_cmd);
|
||||
static int HandleTidy(const std::string& runCmd,
|
||||
const std::string& sourceFile,
|
||||
const std::vector<std::string>& orig_cmd);
|
||||
static int HandleLWYU(const std::string& runCmd,
|
||||
const std::string& sourceFile,
|
||||
const std::vector<std::string>& orig_cmd);
|
||||
static int HandleCppLint(const std::string& runCmd,
|
||||
const std::string& sourceFile,
|
||||
const std::vector<std::string>& orig_cmd);
|
||||
static int HandleCppCheck(const std::string& runCmd,
|
||||
const std::string& sourceFile,
|
||||
const std::vector<std::string>& orig_cmd);
|
||||
|
||||
protected:
|
||||
static int HandleCoCompileCommands(std::vector<std::string>& args);
|
||||
static int HashSumFile(std::vector<std::string>& args,
|
||||
|
||||
@@ -374,6 +374,12 @@ if("${CMAKE_GENERATOR}" MATCHES "Make|Ninja")
|
||||
add_RunCMake_test(IncludeWhatYouUse -DPSEUDO_IWYU=$<TARGET_FILE:pseudo_iwyu>)
|
||||
add_RunCMake_test(Cpplint -DPSEUDO_CPPLINT=$<TARGET_FILE:pseudo_cpplint>)
|
||||
add_RunCMake_test(Cppcheck -DPSEUDO_CPPCHECK=$<TARGET_FILE:pseudo_cppcheck>)
|
||||
add_RunCMake_test(MultiLint
|
||||
-DPSEUDO_TIDY=$<TARGET_FILE:pseudo_tidy>
|
||||
-DPSEUDO_IWYU=$<TARGET_FILE:pseudo_iwyu>
|
||||
-DPSEUDO_CPPLINT=$<TARGET_FILE:pseudo_cpplint>
|
||||
-DPSEUDO_CPPCHECK=$<TARGET_FILE:pseudo_cppcheck>
|
||||
)
|
||||
if(DEFINED CMake_TEST_CUDA)
|
||||
list(APPEND CompilerLauncher_ARGS -DCMake_TEST_CUDA=${CMake_TEST_CUDA})
|
||||
endif()
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
^__run_co_compile missing command to run. Looking for one of the following:
|
||||
.*--cppcheck=
|
||||
.*--cpplint=
|
||||
.*--iwyu=
|
||||
.*--tidy=
|
||||
^__run_co_compile missing command to run. Looking for one or more of the following:
|
||||
--cppcheck=
|
||||
--cpplint=
|
||||
--iwyu=
|
||||
--lwyu=
|
||||
--tidy=
|
||||
|
||||
8
Tests/RunCMake/MultiLint/C-Build-stdout.txt
Normal file
8
Tests/RunCMake/MultiLint/C-Build-stdout.txt
Normal file
@@ -0,0 +1,8 @@
|
||||
Warning: include-what-you-use reported diagnostics:
|
||||
should add these lines:
|
||||
*
|
||||
#include <\.\.\.>
|
||||
+
|
||||
.*Tests[/\]RunCMake[/\]MultiLint[/\]main\.c:0:0: warning: message \[checker\].*
|
||||
Total errors found: 0
|
||||
.*Warning: cppcheck reported diagnostics.*error.*warning.*style.*performance.*information.*
|
||||
8
Tests/RunCMake/MultiLint/C-launch-Build-stdout.txt
Normal file
8
Tests/RunCMake/MultiLint/C-launch-Build-stdout.txt
Normal file
@@ -0,0 +1,8 @@
|
||||
Warning: include-what-you-use reported diagnostics:
|
||||
should add these lines:
|
||||
*
|
||||
#include <\.\.\.>
|
||||
+
|
||||
.*Tests[/\]RunCMake[/\]MultiLint[/\]main\.c:0:0: warning: message \[checker\].*
|
||||
Total errors found: 0
|
||||
.*Warning: cppcheck reported diagnostics.*error.*warning.*style.*performance.*information.*
|
||||
3
Tests/RunCMake/MultiLint/C-launch.cmake
Normal file
3
Tests/RunCMake/MultiLint/C-launch.cmake
Normal file
@@ -0,0 +1,3 @@
|
||||
set(CTEST_USE_LAUNCHERS 1)
|
||||
include(CTestUseLaunchers)
|
||||
include(C.cmake)
|
||||
6
Tests/RunCMake/MultiLint/C.cmake
Normal file
6
Tests/RunCMake/MultiLint/C.cmake
Normal file
@@ -0,0 +1,6 @@
|
||||
enable_language(C)
|
||||
set(CMAKE_C_INCLUDE_WHAT_YOU_USE "${PSEUDO_IWYU}" -some -args)
|
||||
set(CMAKE_C_CLANG_TIDY "${PSEUDO_TIDY}" -some -args)
|
||||
set(CMAKE_C_CPPLINT "${PSEUDO_CPPLINT}" --verbose=0 --linelength=80)
|
||||
set(CMAKE_C_CPPCHECK "${PSEUDO_CPPCHECK}")
|
||||
add_executable(main main.c)
|
||||
3
Tests/RunCMake/MultiLint/CMakeLists.txt
Normal file
3
Tests/RunCMake/MultiLint/CMakeLists.txt
Normal file
@@ -0,0 +1,3 @@
|
||||
cmake_minimum_required(VERSION 3.10)
|
||||
project(${RunCMake_TEST} NONE)
|
||||
include(${RunCMake_TEST}.cmake)
|
||||
8
Tests/RunCMake/MultiLint/CXX-Build-stdout.txt
Normal file
8
Tests/RunCMake/MultiLint/CXX-Build-stdout.txt
Normal file
@@ -0,0 +1,8 @@
|
||||
Warning: include-what-you-use reported diagnostics:
|
||||
should add these lines:
|
||||
*
|
||||
#include <\.\.\.>
|
||||
+
|
||||
.*Tests[/\]RunCMake[/\]MultiLint[/\]main\.cxx:0:0: warning: message \[checker\].*
|
||||
Total errors found: 0
|
||||
.*Warning: cppcheck reported diagnostics.*error.*warning.*style.*performance.*information.*
|
||||
8
Tests/RunCMake/MultiLint/CXX-launch-Build-stdout.txt
Normal file
8
Tests/RunCMake/MultiLint/CXX-launch-Build-stdout.txt
Normal file
@@ -0,0 +1,8 @@
|
||||
Warning: include-what-you-use reported diagnostics:
|
||||
should add these lines:
|
||||
*
|
||||
#include <\.\.\.>
|
||||
+
|
||||
.*Tests[/\]RunCMake[/\]MultiLint[/\]main\.cxx:0:0: warning: message \[checker\].*
|
||||
Total errors found: 0
|
||||
.*Warning: cppcheck reported diagnostics.*error.*warning.*style.*performance.*information.*
|
||||
3
Tests/RunCMake/MultiLint/CXX-launch.cmake
Normal file
3
Tests/RunCMake/MultiLint/CXX-launch.cmake
Normal file
@@ -0,0 +1,3 @@
|
||||
set(CTEST_USE_LAUNCHERS 1)
|
||||
include(CTestUseLaunchers)
|
||||
include(CXX.cmake)
|
||||
6
Tests/RunCMake/MultiLint/CXX.cmake
Normal file
6
Tests/RunCMake/MultiLint/CXX.cmake
Normal file
@@ -0,0 +1,6 @@
|
||||
enable_language(CXX)
|
||||
set(CMAKE_CXX_INCLUDE_WHAT_YOU_USE "${PSEUDO_IWYU}" -some -args)
|
||||
set(CMAKE_CXX_CLANG_TIDY "${PSEUDO_TIDY}" -some -args)
|
||||
set(CMAKE_CXX_CPPLINT "${PSEUDO_CPPLINT}" --verbose=0 --linelength=80)
|
||||
set(CMAKE_CXX_CPPCHECK "${PSEUDO_CPPCHECK}")
|
||||
add_executable(main main.cxx)
|
||||
27
Tests/RunCMake/MultiLint/RunCMakeTest.cmake
Normal file
27
Tests/RunCMake/MultiLint/RunCMakeTest.cmake
Normal file
@@ -0,0 +1,27 @@
|
||||
include(RunCMake)
|
||||
|
||||
set(RunCMake_TEST_OPTIONS
|
||||
"-DPSEUDO_CPPCHECK=${PSEUDO_CPPCHECK}"
|
||||
"-DPSEUDO_CPPLINT=${PSEUDO_CPPLINT}"
|
||||
"-DPSEUDO_IWYU=${PSEUDO_IWYU}"
|
||||
"-DPSEUDO_TIDY=${PSEUDO_TIDY}"
|
||||
)
|
||||
|
||||
function(run_multilint lang)
|
||||
# Use a single build tree for tests without cleaning.
|
||||
set(RunCMake_TEST_BINARY_DIR "${RunCMake_BINARY_DIR}/${lang}-build")
|
||||
set(RunCMake_TEST_NO_CLEAN 1)
|
||||
file(REMOVE_RECURSE "${RunCMake_TEST_BINARY_DIR}")
|
||||
file(MAKE_DIRECTORY "${RunCMake_TEST_BINARY_DIR}")
|
||||
run_cmake(${lang})
|
||||
set(RunCMake_TEST_OUTPUT_MERGE 1)
|
||||
run_cmake_command(${lang}-Build ${CMAKE_COMMAND} --build .)
|
||||
endfunction()
|
||||
|
||||
run_multilint(C)
|
||||
run_multilint(CXX)
|
||||
|
||||
if(NOT RunCMake_GENERATOR STREQUAL "Watcom WMake")
|
||||
run_multilint(C-launch)
|
||||
run_multilint(CXX-launch)
|
||||
endif()
|
||||
4
Tests/RunCMake/MultiLint/main.c
Normal file
4
Tests/RunCMake/MultiLint/main.c
Normal file
@@ -0,0 +1,4 @@
|
||||
int main(void)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
4
Tests/RunCMake/MultiLint/main.cxx
Normal file
4
Tests/RunCMake/MultiLint/main.cxx
Normal file
@@ -0,0 +1,4 @@
|
||||
int main()
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
Reference in New Issue
Block a user