Skip to content

Commit 1cd6f9a

Browse files
committed
improved testing of missing includes / made it possible to clear the include cache in simplecpp
1 parent 8cc3e0b commit 1cd6f9a

File tree

6 files changed

+131
-5
lines changed

6 files changed

+131
-5
lines changed

externals/simplecpp/simplecpp.cpp

Lines changed: 19 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -2796,6 +2796,11 @@ class NonExistingFilesCache {
27962796
m_pathSet.insert(path);
27972797
}
27982798

2799+
void clear() {
2800+
ScopedLock lock(m_criticalSection);
2801+
m_pathSet.clear();
2802+
}
2803+
27992804
private:
28002805
std::set<std::string> m_pathSet;
28012806
CRITICAL_SECTION m_criticalSection;
@@ -2807,8 +2812,8 @@ static NonExistingFilesCache nonExistingFilesCache;
28072812

28082813
static std::string openHeader(std::ifstream &f, const std::string &path)
28092814
{
2810-
#ifdef SIMPLECPP_WINDOWS
28112815
std::string simplePath = simplecpp::simplifyPath(path);
2816+
#ifdef SIMPLECPP_WINDOWS
28122817
if (nonExistingFilesCache.contains(simplePath))
28132818
return ""; // file is known not to exist, skip expensive file open call
28142819

@@ -2820,8 +2825,8 @@ static std::string openHeader(std::ifstream &f, const std::string &path)
28202825
return "";
28212826
}
28222827
#else
2823-
f.open(path.c_str());
2824-
return f.is_open() ? simplecpp::simplifyPath(path) : "";
2828+
f.open(simplePath.c_str());
2829+
return f.is_open() ? simplePath : "";
28252830
#endif
28262831
}
28272832

@@ -2907,6 +2912,11 @@ static bool hasFile(const std::map<std::string, simplecpp::TokenList *> &filedat
29072912

29082913
std::map<std::string, simplecpp::TokenList*> simplecpp::load(const simplecpp::TokenList &rawtokens, std::vector<std::string> &filenames, const simplecpp::DUI &dui, simplecpp::OutputList *outputList)
29092914
{
2915+
#ifdef SIMPLECPP_WINDOWS
2916+
if (dui.clearIncludeCache)
2917+
nonExistingFilesCache .clear();
2918+
#endif
2919+
29102920
std::map<std::string, simplecpp::TokenList*> ret;
29112921

29122922
std::list<const Token *> filelist;
@@ -3032,6 +3042,11 @@ static std::string getTimeDefine(struct tm *timep)
30323042

30333043
void simplecpp::preprocess(simplecpp::TokenList &output, const simplecpp::TokenList &rawtokens, std::vector<std::string> &files, std::map<std::string, simplecpp::TokenList *> &filedata, const simplecpp::DUI &dui, simplecpp::OutputList *outputList, std::list<simplecpp::MacroUsage> *macroUsage, std::list<simplecpp::IfCond> *ifCond)
30343044
{
3045+
#ifdef SIMPLECPP_WINDOWS
3046+
if (dui.clearIncludeCache)
3047+
nonExistingFilesCache.clear();
3048+
#endif
3049+
30353050
std::map<std::string, std::size_t> sizeOfType(rawtokens.sizeOfType);
30363051
sizeOfType.insert(std::make_pair("char", sizeof(char)));
30373052
sizeOfType.insert(std::make_pair("short", sizeof(short)));
@@ -3223,7 +3238,7 @@ void simplecpp::preprocess(simplecpp::TokenList &output, const simplecpp::TokenL
32233238

32243239
const Token * const inctok = inc2.cfront();
32253240

3226-
const bool systemheader = (inctok->op == '<');
3241+
const bool systemheader = inctok->str()[0] == '<';
32273242
const std::string header(realFilename(inctok->str().substr(1U, inctok->str().size() - 2U)));
32283243
std::string header2 = getFileName(filedata, rawtok->location.file(), header, dui, systemheader);
32293244
if (header2.empty()) {

externals/simplecpp/simplecpp.h

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -314,12 +314,13 @@ namespace simplecpp {
314314
* On the command line these are configured by -D, -U, -I, --include, -std
315315
*/
316316
struct SIMPLECPP_LIB DUI {
317-
DUI() {}
317+
DUI() : clearIncludeCache(false) {}
318318
std::list<std::string> defines;
319319
std::set<std::string> undefined;
320320
std::list<std::string> includePaths;
321321
std::list<std::string> includes;
322322
std::string std;
323+
bool clearIncludeCache;
323324
};
324325

325326
SIMPLECPP_LIB long long characterLiteralToLL(const std::string& str);

lib/preprocessor.cpp

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -626,6 +626,7 @@ static simplecpp::DUI createDUI(const Settings &mSettings, const std::string &cf
626626
dui.std = mSettings.standards.getCPP();
627627
else
628628
dui.std = mSettings.standards.getC();
629+
dui.clearIncludeCache = mSettings.clearIncludeCache;
629630
return dui;
630631
}
631632

lib/settings.cpp

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -44,6 +44,7 @@ Settings::Settings()
4444
clang(false),
4545
clangExecutable("clang"),
4646
clangTidy(false),
47+
clearIncludeCache(false),
4748
daca(false),
4849
debugnormal(false),
4950
debugSimplified(false),

lib/settings.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -143,6 +143,9 @@ class CPPCHECKLIB Settings : public cppcheck::Platform {
143143
/** Use clang-tidy */
144144
bool clangTidy;
145145

146+
/** Internal: Clear the simplecpp non-existing include cache */
147+
bool clearIncludeCache;
148+
146149
/** @brief include paths excluded from checking the configuration */
147150
std::set<std::string> configExcludePaths;
148151

test/testpreprocessor.cpp

Lines changed: 105 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -259,6 +259,10 @@ class TestPreprocessor : public TestFixture {
259259
TEST_CASE(testDirectiveIncludeComments);
260260

261261
TEST_CASE(testMissingInclude);
262+
TEST_CASE(testMissingInclude2);
263+
TEST_CASE(testMissingSystemInclude);
264+
TEST_CASE(testMissingSystemInclude2);
265+
TEST_CASE(testMissingIncludeMixed);
262266
TEST_CASE(testMissingIncludeCheckConfig);
263267
}
264268

@@ -2432,11 +2436,111 @@ class TestPreprocessor : public TestFixture {
24322436
ASSERT_EQUALS(dumpdata, ostr.str());
24332437
}
24342438

2439+
// TODO: test with absolute path
2440+
// TODO: test with include path
2441+
24352442
void testMissingInclude() {
24362443
Preprocessor::missingIncludeFlag = false;
24372444
Preprocessor::missingSystemIncludeFlag = false;
24382445

24392446
Settings settings;
2447+
settings.clearIncludeCache = true;
2448+
settings.severity.clear();
2449+
settings.checks.enable(Checks::missingInclude);
2450+
Preprocessor preprocessor(settings, this);
2451+
2452+
ScopedFile header("header.h", "");
2453+
2454+
std::string code("#include \"header.h\"");
2455+
errout.str("");
2456+
preprocessor.getcode(code, "", "test.c");
2457+
ASSERT_EQUALS(false, Preprocessor::missingIncludeFlag);
2458+
ASSERT_EQUALS(false, Preprocessor::missingSystemIncludeFlag);
2459+
2460+
// the expected messages are emitted outside of the Preprocessor
2461+
ASSERT_EQUALS("", errout.str());
2462+
2463+
Preprocessor::missingIncludeFlag = false;
2464+
Preprocessor::missingSystemIncludeFlag = false;
2465+
}
2466+
2467+
void testMissingInclude2() {
2468+
Preprocessor::missingIncludeFlag = false;
2469+
Preprocessor::missingSystemIncludeFlag = false;
2470+
2471+
Settings settings;
2472+
settings.clearIncludeCache = true;
2473+
settings.severity.clear();
2474+
settings.checks.enable(Checks::missingInclude);
2475+
Preprocessor preprocessor(settings, this);
2476+
2477+
std::string code("#include \"header.h\"");
2478+
errout.str("");
2479+
preprocessor.getcode(code, "", "test.c");
2480+
ASSERT_EQUALS(true, Preprocessor::missingIncludeFlag);
2481+
ASSERT_EQUALS(false, Preprocessor::missingSystemIncludeFlag);
2482+
2483+
// the expected messages are emitted outside of the Preprocessor
2484+
ASSERT_EQUALS("", errout.str());
2485+
2486+
Preprocessor::missingIncludeFlag = false;
2487+
Preprocessor::missingSystemIncludeFlag = false;
2488+
}
2489+
2490+
void testMissingSystemInclude() {
2491+
Preprocessor::missingIncludeFlag = false;
2492+
Preprocessor::missingSystemIncludeFlag = false;
2493+
2494+
Settings settings;
2495+
settings.clearIncludeCache = true;
2496+
settings.severity.clear();
2497+
settings.checks.enable(Checks::missingInclude);
2498+
Preprocessor preprocessor(settings, this);
2499+
2500+
ScopedFile header("header.h", "");
2501+
2502+
std::string code("#include <header.h>");
2503+
errout.str("");
2504+
preprocessor.getcode(code, "", "test.c");
2505+
ASSERT_EQUALS(false, Preprocessor::missingIncludeFlag);
2506+
ASSERT_EQUALS(false, Preprocessor::missingSystemIncludeFlag);
2507+
2508+
// the expected messages are emitted outside of the Preprocessor
2509+
ASSERT_EQUALS("", errout.str());
2510+
2511+
Preprocessor::missingIncludeFlag = false;
2512+
Preprocessor::missingSystemIncludeFlag = false;
2513+
}
2514+
2515+
void testMissingSystemInclude2() {
2516+
Preprocessor::missingIncludeFlag = false;
2517+
Preprocessor::missingSystemIncludeFlag = false;
2518+
2519+
Settings settings;
2520+
settings.clearIncludeCache = true;
2521+
settings.severity.clear();
2522+
settings.checks.enable(Checks::missingInclude);
2523+
Preprocessor preprocessor(settings, this);
2524+
2525+
std::string code("#include <header.h>");
2526+
errout.str("");
2527+
preprocessor.getcode(code, "", "test.c");
2528+
ASSERT_EQUALS(false, Preprocessor::missingIncludeFlag);
2529+
ASSERT_EQUALS(true, Preprocessor::missingSystemIncludeFlag);
2530+
2531+
// the expected messages are emitted outside of the Preprocessor
2532+
ASSERT_EQUALS("", errout.str());
2533+
2534+
Preprocessor::missingIncludeFlag = false;
2535+
Preprocessor::missingSystemIncludeFlag = false;
2536+
}
2537+
2538+
void testMissingIncludeMixed() {
2539+
Preprocessor::missingIncludeFlag = false;
2540+
Preprocessor::missingSystemIncludeFlag = false;
2541+
2542+
Settings settings;
2543+
settings.clearIncludeCache = true;
24402544
settings.severity.clear();
24412545
settings.checks.enable(Checks::missingInclude);
24422546
Preprocessor preprocessor(settings, this);
@@ -2465,6 +2569,7 @@ class TestPreprocessor : public TestFixture {
24652569
Preprocessor::missingSystemIncludeFlag = false;
24662570

24672571
Settings settings;
2572+
settings.clearIncludeCache = true;
24682573
settings.checkConfiguration = true;
24692574
settings.severity.clear();
24702575
// needs to be reported regardless of enabled checks

0 commit comments

Comments
 (0)