Bug hunting; Diagnose array index out of bounds when struct member is accessed
This commit is contained in:
parent
5e15a7fac7
commit
d12732adfb
|
@ -2011,12 +2011,12 @@ static ExprEngine::ValuePtr executeCast(const Token *tok, Data &data)
|
||||||
|
|
||||||
static ExprEngine::ValuePtr executeDot(const Token *tok, Data &data)
|
static ExprEngine::ValuePtr executeDot(const Token *tok, Data &data)
|
||||||
{
|
{
|
||||||
if (!tok->astOperand1() || !tok->astOperand1()->varId()) {
|
if (!tok->astOperand1()) {
|
||||||
auto v = getValueRangeFromValueType(tok->valueType(), data);
|
auto v = std::make_shared<ExprEngine::BailoutValue>();
|
||||||
call(data.callbacks, tok, v, &data);
|
call(data.callbacks, tok, v, &data);
|
||||||
return v;
|
return v;
|
||||||
}
|
}
|
||||||
std::shared_ptr<ExprEngine::StructValue> structValue = std::dynamic_pointer_cast<ExprEngine::StructValue>(data.getValue(tok->astOperand1()->varId(), nullptr, nullptr));
|
std::shared_ptr<ExprEngine::StructValue> structValue = std::dynamic_pointer_cast<ExprEngine::StructValue>(executeExpression(tok->astOperand1(), data));
|
||||||
if (!structValue) {
|
if (!structValue) {
|
||||||
if (tok->originalName() == "->") {
|
if (tok->originalName() == "->") {
|
||||||
std::shared_ptr<ExprEngine::ArrayValue> pointerValue = std::dynamic_pointer_cast<ExprEngine::ArrayValue>(data.getValue(tok->astOperand1()->varId(), nullptr, nullptr));
|
std::shared_ptr<ExprEngine::ArrayValue> pointerValue = std::dynamic_pointer_cast<ExprEngine::ArrayValue>(data.getValue(tok->astOperand1()->varId(), nullptr, nullptr));
|
||||||
|
|
|
@ -38,6 +38,7 @@ private:
|
||||||
TEST_CASE(checkAssignment);
|
TEST_CASE(checkAssignment);
|
||||||
TEST_CASE(arrayIndexOutOfBounds1);
|
TEST_CASE(arrayIndexOutOfBounds1);
|
||||||
TEST_CASE(arrayIndexOutOfBounds2);
|
TEST_CASE(arrayIndexOutOfBounds2);
|
||||||
|
TEST_CASE(arrayIndexOutOfBounds3);
|
||||||
TEST_CASE(bufferOverflowMemCmp1);
|
TEST_CASE(bufferOverflowMemCmp1);
|
||||||
TEST_CASE(bufferOverflowMemCmp2);
|
TEST_CASE(bufferOverflowMemCmp2);
|
||||||
TEST_CASE(bufferOverflowStrcpy1);
|
TEST_CASE(bufferOverflowStrcpy1);
|
||||||
|
@ -83,7 +84,7 @@ private:
|
||||||
errout.str());
|
errout.str());
|
||||||
}
|
}
|
||||||
|
|
||||||
void arrayIndexOutOfBounds2() {
|
void arrayIndexOutOfBounds2() { // loop
|
||||||
check("void foo(int n) {\n"
|
check("void foo(int n) {\n"
|
||||||
" int p[8];\n"
|
" int p[8];\n"
|
||||||
" for (int i = 0; i < n; i++)\n"
|
" for (int i = 0; i < n; i++)\n"
|
||||||
|
@ -106,6 +107,18 @@ private:
|
||||||
errout.str());
|
errout.str());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void arrayIndexOutOfBounds3() { // struct
|
||||||
|
check("struct S { int x; };\n"
|
||||||
|
"void foo(short i) {\n"
|
||||||
|
" S s[8];\n"
|
||||||
|
" if (s[i].x == 0) {}\n"
|
||||||
|
"}");
|
||||||
|
ASSERT_EQUALS("[test.cpp:4]: (error) Array index out of bounds, cannot determine that i is less than 8\n"
|
||||||
|
"[test.cpp:4]: (error) Array index out of bounds, cannot determine that i is not negative\n"
|
||||||
|
"[test.cpp:4]: (error) Cannot determine that 's[i]' is initialized\n",
|
||||||
|
errout.str());
|
||||||
|
}
|
||||||
|
|
||||||
void bufferOverflowMemCmp1() {
|
void bufferOverflowMemCmp1() {
|
||||||
// CVE-2020-24265
|
// CVE-2020-24265
|
||||||
check("void foo(const char *pktdata, int datalen) {\n"
|
check("void foo(const char *pktdata, int datalen) {\n"
|
||||||
|
|
Loading…
Reference in New Issue