ASSERT_EQUALS("[test.cpp:4]: (error) Possible null pointer dereference: tok\n",errout.str());
check("void foo()\n"
"{\n"
" for (const Token *tok = tokens; tok; tok = tok->next())\n"
" {\n"
" while (tok && tok->str() != \";\")\n"
" tok = tok->next();\n"
" }\n"
"}\n");
ASSERT_EQUALS("[test.cpp:3]: (error) Possible null pointer dereference: tok - otherwise it is redundant to check if tok is null at line 5\n",errout.str());
check("void foo(Token &tok)\n"
"{\n"
" for (int i = 0; i < tok.size(); i++ )\n"
" {\n"
" while (!tok)\n"
" char c = tok.read();\n"
" }\n"
"}\n");
ASSERT_EQUALS("",errout.str());
check("void foo()\n"
"{\n"
" for (const Token *tok = tokens; tok; tok = tok->next())\n"
" {\n"
" while (tok && tok->str() != \";\")\n"
" tok = tok->next();\n"
" if( !tok ) break;\n"
" }\n"
"}\n");
ASSERT_EQUALS("",errout.str());
check("void foo()\n"
"{\n"
" for (const Token *tok = tokens; tok; tok = tok ? tok->next() : NULL)\n"
" {\n"
" while (tok && tok->str() != \";\")\n"
" tok = tok->next();\n"
" }\n"
"}\n");
ASSERT_EQUALS("",errout.str());
check("void foo(A*a)\n"
"{\n"
" switch (a->b()) {\n"
" case 1:\n"
" while( a ){\n"
" a = a->next;\n"
" }\n"
" break;\n"
" case 2:\n"
" a->b();\n"
" break;\n"
" }\n"
"}\n");
ASSERT_EQUALS("",errout.str());
// ticket #1923 - no false positive when using else if
check("void f(A *a)\n"
"{\n"
" if (a->x == 1)\n"
" {\n"
" a = a->next;\n"
" }\n"
" else if (a->x == 2) { }\n"
" if (a) { }\n"
"}\n");
ASSERT_EQUALS("",errout.str());
// ticket #2134 - sizeof doesn't dereference
check("void f() {\n"
" int c = 1;\n"
" int *list = NULL;\n"
" sizeof(*list);\n"
" if (!list)\n"
" ;\n"
"}\n");
ASSERT_EQUALS("",errout.str());
}
voidnullpointer2()
{
// Null pointer dereference can only happen with pointers
check("void foo()\n"
"{\n"
" Fred fred;\n"
" while (fred);\n"
" fred.hello();\n"
"}\n");
ASSERT_EQUALS("",errout.str());
}
// Dereferencing a struct and then checking if it is null
ASSERT_EQUALS("[test.cpp:3]: (error) Possible null pointer dereference: abc - otherwise it is redundant to check if abc is null at line 4\n",errout.str());
check("void foo(struct ABC *abc)\n"
"{\n"
" bar(abc->a);\n"
" if (!abc)\n"
" ;\n"
"}\n");
ASSERT_EQUALS("[test.cpp:3]: (error) Possible null pointer dereference: abc - otherwise it is redundant to check if abc is null at line 4\n",errout.str());
// ok dereferencing in a condition
check("void foo(struct ABC *abc)\n"
"{\n"
" if (abc && abc->a);\n"
" if (!abc)\n"
" ;\n"
"}\n");
ASSERT_EQUALS("",errout.str());
// ok to use a linked list..
check("void foo(struct ABC *abc)\n"
"{\n"
" abc = abc->next;\n"
" if (!abc)\n"
" ;\n"
"}\n");
ASSERT_EQUALS("",errout.str());
// reassign struct..
check("void foo(struct ABC *abc)\n"
"{\n"
" int a = abc->a;\n"
" abc = abc->next;\n"
" if (!abc)\n"
" ;\n"
"}\n");
ASSERT_EQUALS("",errout.str());
check("void foo(struct ABC *abc)\n"
"{\n"
" int a = abc->a;\n"
" f(&abc);\n"
" if (!abc)\n"
" ;\n"
"}\n");
ASSERT_EQUALS("",errout.str());
// goto..
check("void foo(struct ABC *abc)\n"
"{\n"
" int a;\n"
" if (!abc)\n"
" goto out;"
" a = abc->a;\n"
" return;\n"
"out:\n"
" if (!abc)\n"
" ;\n"
"}\n");
ASSERT_EQUALS("",errout.str());
// loops..
check("void freeAbc(struct ABC *abc)\n"
"{\n"
" while (abc)\n"
" {\n"
" struct ABC *next = abc->next;\n"
" if (abc) delete abc;\n"
" abc = next;\n"
" }\n"
"}\n");
ASSERT_EQUALS("",errout.str());
check("void foo(struct ABC *abc)\n"
"{\n"
" int a = abc->a;"
" do\n"
" {\n"
" if (abc)\n"
" abc = abc->next;\n"
" --a;\n"
" }\n"
" while (a > 0);\n"
"}\n");
ASSERT_EQUALS("",errout.str());
check("void f()\n"
"{\n"
" for (const Token *tok = _tokenizer->tokens(); tok; tok = tok->next())\n"
" {\n"
" while (tok && tok->str() != \"{\")\n"
" tok = tok->next();\n"
" if (!tok)\n"
" return;\n"
" }\n"
"}\n");
ASSERT_EQUALS("",errout.str());
// dynamic_cast..
check("void foo(ABC *abc)\n"
"{\n"
" int a = abc->a;\n"
" if (!dynamic_cast<DEF *>(abc))\n"
" ;\n"
"}\n");
ASSERT_EQUALS("",errout.str());
}
// Dereferencing a pointer and then checking if it is null
ASSERT_EQUALS("[test.cpp:3]: (error) Possible null pointer dereference: p - otherwise it is redundant to check if p is null at line 4\n",errout.str());
check("void foo(int *p)\n"
"{\n"
" bar(*p);\n"
" if (!p)\n"
" ;\n"
"}\n");
ASSERT_EQUALS("[test.cpp:3]: (error) Possible null pointer dereference: p - otherwise it is redundant to check if p is null at line 4\n",errout.str());