-j 0 causes indefinite hang. require >= 1 (#5326)

In cppcheck 2.11.1 (macOS), using `-j 0` actually causes cppcheck to do
nothing–it stalls indefinitely.

I could only find one place where `mSettings.jobs` was validated against
> 0 and it's simply an assert, so you wouldn't hit it in a release
build.

- Require -j >= 1 
- Cap -j at 1024, not 10000  (I don't even know what would happen if
you created 10,000 threads, but nothing good; likely exhaust virtual
memory or grind the process to a halt). 1024 is still obscene but there
may be some hypercomputers out there that have that many logical cores.
This commit is contained in:
Ryan M. Lederman 2023-08-14 03:55:32 -06:00 committed by GitHub
parent 693084470d
commit d064f9c243
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
2 changed files with 21 additions and 6 deletions

View File

@ -507,10 +507,17 @@ bool CmdLineParser::parseFromArgs(int argc, const char* const argv[])
printError("argument to '-j' is not valid - " + err + ".");
return false;
}
if (tmp > 10000) {
// This limit is here just to catch typos. If someone has
// need for more jobs, this value should be increased.
printError("argument for '-j' is allowed to be 10000 at max.");
if (tmp == 0) {
// TODO: implement get CPU logical core count and use that.
// Usually, -j 0 would mean "use all available cores," but
// if we get a 0, we just stall and don't do any work.
printError("argument for '-j' must be greater than 0.");
return false;
}
if (tmp > 1024) {
// Almost nobody has 1024 logical cores, but somebody out
// there does.
printError("argument for '-j' is allowed to be 1024 at max.");
return false;
}
mSettings.jobs = tmp;

View File

@ -142,6 +142,7 @@ private:
TEST_CASE(jobs2);
TEST_CASE(jobsMissingCount);
TEST_CASE(jobsInvalid);
TEST_CASE(jobsNoJobs);
TEST_CASE(jobsTooBig);
TEST_CASE(maxConfigs);
TEST_CASE(maxConfigsMissingCount);
@ -1010,11 +1011,18 @@ private:
ASSERT_EQUALS("cppcheck: error: argument to '-j' is not valid - not an integer.\n", GET_REDIRECT_OUTPUT);
}
void jobsNoJobs() {
REDIRECT;
const char * const argv[] = {"cppcheck", "-j0", "file.cpp"};
ASSERT(!parser->parseFromArgs(3, argv));
ASSERT_EQUALS("cppcheck: error: argument for '-j' must be greater than 0.\n", GET_REDIRECT_OUTPUT);
}
void jobsTooBig() {
REDIRECT;
const char * const argv[] = {"cppcheck", "-j10001", "file.cpp"};
const char * const argv[] = {"cppcheck", "-j1025", "file.cpp"};
ASSERT(!parser->parseFromArgs(3, argv));
ASSERT_EQUALS("cppcheck: error: argument for '-j' is allowed to be 10000 at max.\n", GET_REDIRECT_OUTPUT);
ASSERT_EQUALS("cppcheck: error: argument for '-j' is allowed to be 1024 at max.\n", GET_REDIRECT_OUTPUT);
}
void maxConfigs() {