This commit is contained in:
parent
aa7a1f25c1
commit
bd9f5231b8
|
@ -373,18 +373,31 @@ void CheckSizeof::suspiciousSizeofCalculation()
|
||||||
if (!mSettings->severity.isEnabled(Severity::warning) || !mSettings->certainty.isEnabled(Certainty::inconclusive))
|
if (!mSettings->severity.isEnabled(Severity::warning) || !mSettings->certainty.isEnabled(Certainty::inconclusive))
|
||||||
return;
|
return;
|
||||||
|
|
||||||
// TODO: Use AST here. This should be possible as soon as sizeof without brackets is correctly parsed
|
|
||||||
for (const Token *tok = mTokenizer->tokens(); tok; tok = tok->next()) {
|
for (const Token *tok = mTokenizer->tokens(); tok; tok = tok->next()) {
|
||||||
if (Token::simpleMatch(tok, "sizeof (")) {
|
if (Token::simpleMatch(tok, "sizeof (")) {
|
||||||
const Token* const end = tok->linkAt(1);
|
const Token* lPar = tok->astParent();
|
||||||
const Variable* var = end->previous()->variable();
|
if (lPar && lPar->str() == "(") {
|
||||||
if (end->strAt(-1) == "*" || (var && var->isPointer() && !var->isArray())) {
|
const Token* const rPar = lPar->link();
|
||||||
if (end->strAt(1) == "/")
|
const Token* varTok = rPar->previous();
|
||||||
|
while (varTok && varTok->str() == "]")
|
||||||
|
varTok = varTok->link()->previous();
|
||||||
|
if (lPar->astParent() && lPar->astParent()->str() == "/") {
|
||||||
|
const Variable* var = varTok ? varTok->variable() : nullptr;
|
||||||
|
if (var && var->isPointer() && !var->isArray() && !(lPar->astOperand2() && lPar->astOperand2()->str() == "*"))
|
||||||
divideSizeofError(tok);
|
divideSizeofError(tok);
|
||||||
} else if (Token::simpleMatch(end, ") * sizeof") && end->next()->astOperand1() == tok->next())
|
else if (varTok && varTok->str() == "*") {
|
||||||
|
const Token* arrTok = lPar->astParent()->astOperand1();
|
||||||
|
arrTok = arrTok ? arrTok->next() : nullptr;
|
||||||
|
var = arrTok ? arrTok->variable() : nullptr;
|
||||||
|
if (var && var->isPointer() && !var->isArray())
|
||||||
|
divideSizeofError(tok);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else if (Token::simpleMatch(rPar, ") * sizeof") && rPar->next()->astOperand1() == tok->next())
|
||||||
multiplySizeofError(tok);
|
multiplySizeofError(tok);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void CheckSizeof::multiplySizeofError(const Token *tok)
|
void CheckSizeof::multiplySizeofError(const Token *tok)
|
||||||
|
|
|
@ -427,6 +427,35 @@ private:
|
||||||
" return (end - source) / sizeof(encode_block_type) * sizeof(encode_block_type);\n"
|
" return (end - source) / sizeof(encode_block_type) * sizeof(encode_block_type);\n"
|
||||||
"}");
|
"}");
|
||||||
ASSERT_EQUALS("", errout.str());
|
ASSERT_EQUALS("", errout.str());
|
||||||
|
|
||||||
|
check("struct S { T* t; };\n" // #10179
|
||||||
|
"int f(S* s) {\n"
|
||||||
|
" return g(sizeof(*s->t) / 4);\n"
|
||||||
|
"}\n");
|
||||||
|
ASSERT_EQUALS("", errout.str());
|
||||||
|
|
||||||
|
check("void f() {\n"
|
||||||
|
" const char* a[N];\n"
|
||||||
|
" for (int i = 0; i < (int)(sizeof(a) / sizeof(char*)); i++) {}\n"
|
||||||
|
"}\n");
|
||||||
|
ASSERT_EQUALS("", errout.str());
|
||||||
|
|
||||||
|
check("int f(const S& s) {\n"
|
||||||
|
" int** p;\n"
|
||||||
|
" return sizeof(p[0]) / 4;\n"
|
||||||
|
"}\n");
|
||||||
|
ASSERT_EQUALS("[test.cpp:3]: (warning, inconclusive) Division of result of sizeof() on pointer type.\n", errout.str());
|
||||||
|
|
||||||
|
check("struct S {\n"
|
||||||
|
" unsigned char* s;\n"
|
||||||
|
"};\n"
|
||||||
|
"struct T {\n"
|
||||||
|
" S s[38];\n"
|
||||||
|
"};\n"
|
||||||
|
"void f(T* t) {\n"
|
||||||
|
" for (size_t i = 0; i < sizeof(t->s) / sizeof(t->s[0]); i++) {}\n"
|
||||||
|
"}\n");
|
||||||
|
ASSERT_EQUALS("", errout.str());
|
||||||
}
|
}
|
||||||
|
|
||||||
void checkPointerSizeof() {
|
void checkPointerSizeof() {
|
||||||
|
@ -722,7 +751,9 @@ private:
|
||||||
check("void foo(memoryMapEntry_t* entry, memoryMapEntry_t* memoryMapEnd) {\n"
|
check("void foo(memoryMapEntry_t* entry, memoryMapEntry_t* memoryMapEnd) {\n"
|
||||||
" memmove(entry, entry + 1, (memoryMapEnd - entry) / sizeof(entry));\n"
|
" memmove(entry, entry + 1, (memoryMapEnd - entry) / sizeof(entry));\n"
|
||||||
"}");
|
"}");
|
||||||
ASSERT_EQUALS("[test.cpp:2]: (warning) Division by result of sizeof(). memmove() expects a size in bytes, did you intend to multiply instead?\n", errout.str());
|
ASSERT_EQUALS("[test.cpp:2]: (warning, inconclusive) Division of result of sizeof() on pointer type.\n"
|
||||||
|
"[test.cpp:2]: (warning) Division by result of sizeof(). memmove() expects a size in bytes, did you intend to multiply instead?\n",
|
||||||
|
errout.str());
|
||||||
|
|
||||||
check("Foo* allocFoo(int num) {\n"
|
check("Foo* allocFoo(int num) {\n"
|
||||||
" return malloc(num / sizeof(Foo));\n"
|
" return malloc(num / sizeof(Foo));\n"
|
||||||
|
|
|
@ -125,6 +125,11 @@ def compile_version(cppcheck_path, jobs):
|
||||||
def compile_cppcheck(cppcheck_path, jobs):
|
def compile_cppcheck(cppcheck_path, jobs):
|
||||||
print('Compiling {}'.format(os.path.basename(cppcheck_path)))
|
print('Compiling {}'.format(os.path.basename(cppcheck_path)))
|
||||||
try:
|
try:
|
||||||
|
os.chdir(cppcheck_path)
|
||||||
|
if sys.platform == 'win32':
|
||||||
|
subprocess.call(['MSBuild.exe', cppcheck_path + '/cppcheck.sln', '/property:Configuration=Release', '/property:Platform=x64'])
|
||||||
|
subprocess.call([cppcheck_path + '/bin/cppcheck.exe', '--version'])
|
||||||
|
else:
|
||||||
subprocess.check_call(['make', jobs, 'MATCHCOMPILER=yes', 'CXXFLAGS=-O2 -g -w'], cwd=cppcheck_path)
|
subprocess.check_call(['make', jobs, 'MATCHCOMPILER=yes', 'CXXFLAGS=-O2 -g -w'], cwd=cppcheck_path)
|
||||||
subprocess.check_call([os.path.join(cppcheck_path, 'cppcheck'), '--version'], cwd=cppcheck_path)
|
subprocess.check_call([os.path.join(cppcheck_path, 'cppcheck'), '--version'], cwd=cppcheck_path)
|
||||||
except:
|
except:
|
||||||
|
@ -279,6 +284,9 @@ def __run_command(cmd, print_cmd=True):
|
||||||
print(cmd)
|
print(cmd)
|
||||||
start_time = time.time()
|
start_time = time.time()
|
||||||
comm = None
|
comm = None
|
||||||
|
if sys.platform == 'win32':
|
||||||
|
p = subprocess.Popen(shlex.split(cmd, comments=False, posix=False), stdout=subprocess.PIPE, stderr=subprocess.PIPE)
|
||||||
|
else:
|
||||||
p = subprocess.Popen(shlex.split(cmd), stdout=subprocess.PIPE, stderr=subprocess.PIPE, preexec_fn=os.setsid)
|
p = subprocess.Popen(shlex.split(cmd), stdout=subprocess.PIPE, stderr=subprocess.PIPE, preexec_fn=os.setsid)
|
||||||
try:
|
try:
|
||||||
comm = p.communicate(timeout=CPPCHECK_TIMEOUT)
|
comm = p.communicate(timeout=CPPCHECK_TIMEOUT)
|
||||||
|
@ -323,6 +331,10 @@ def scan_package(work_path, cppcheck_path, jobs, libraries, capture_callstack=Tr
|
||||||
options = libs + ' --showtime=top5 --check-library --inconclusive --enable=style,information --template=daca2'
|
options = libs + ' --showtime=top5 --check-library --inconclusive --enable=style,information --template=daca2'
|
||||||
options += ' -D__GNUC__ --platform=unix64'
|
options += ' -D__GNUC__ --platform=unix64'
|
||||||
options += ' -rp={}'.format(dir_to_scan)
|
options += ' -rp={}'.format(dir_to_scan)
|
||||||
|
if sys.platform == 'win32':
|
||||||
|
cppcheck_cmd = cppcheck_path + '/bin/cppcheck.exe ' + options
|
||||||
|
cmd = cppcheck_cmd + ' ' + jobs + ' ' + dir_to_scan
|
||||||
|
else:
|
||||||
cppcheck_cmd = os.path.join(cppcheck_path, 'cppcheck') + ' ' + options
|
cppcheck_cmd = os.path.join(cppcheck_path, 'cppcheck') + ' ' + options
|
||||||
cmd = 'nice ' + cppcheck_cmd + ' ' + jobs + ' ' + dir_to_scan
|
cmd = 'nice ' + cppcheck_cmd + ' ' + jobs + ' ' + dir_to_scan
|
||||||
returncode, stdout, stderr, elapsed_time = __run_command(cmd)
|
returncode, stdout, stderr, elapsed_time = __run_command(cmd)
|
||||||
|
|
|
@ -3,6 +3,7 @@
|
||||||
# Run this script from your branch with proposed Cppcheck patch to verify your
|
# Run this script from your branch with proposed Cppcheck patch to verify your
|
||||||
# patch against current main. It will compare output of testing a bunch of
|
# patch against current main. It will compare output of testing a bunch of
|
||||||
# opensource packages
|
# opensource packages
|
||||||
|
# If running on Windows, make sure that git.exe, wget.exe, and MSBuild.exe are available in PATH
|
||||||
|
|
||||||
import donate_cpu_lib as lib
|
import donate_cpu_lib as lib
|
||||||
import argparse
|
import argparse
|
||||||
|
|
Loading…
Reference in New Issue