From 5c56e639963165867b8081a1e2961e2249fde575 Mon Sep 17 00:00:00 2001 From: PKEuS Date: Tue, 27 Jan 2015 21:52:52 +0100 Subject: [PATCH] Fixed false positive #6452: Handle member functions in CheckIO::checkFileUsage() --- lib/checkio.cpp | 14 ++++++++++++++ test/testio.cpp | 48 ++++++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 62 insertions(+) diff --git a/lib/checkio.cpp b/lib/checkio.cpp index ca069354e..770580e49 100644 --- a/lib/checkio.cpp +++ b/lib/checkio.cpp @@ -222,6 +222,20 @@ void CheckIO::checkFileUsage() operation = Filepointer::UNIMPORTANT; } else if (!Token::Match(tok, "if|for|while|catch|switch") && _settings->library.functionpure.find(tok->str()) == _settings->library.functionpure.end()) { const Token* const end2 = tok->linkAt(1); + if (scope->functionOf && scope->functionOf->isClassOrStruct() && !scope->function->isStatic() && ((tok->strAt(-1) != "::" && tok->strAt(-1) != ".") || tok->strAt(-2) == "this")) { + if (!tok->function() || (tok->function()->nestedIn && tok->function()->nestedIn->isClassOrStruct())) { + for (std::map::iterator i = filepointers.begin(); i != filepointers.end(); ++i) { + const Variable* var = symbolDatabase->getVariableFromVarId(i->first); + if (!var || !(var->isLocal() || var->isGlobal() || var->isStatic())) { + i->second.mode = UNKNOWN_OM; + i->second.mode_indent = 0; + i->second.op_indent = indent; + i->second.lastOperation = Filepointer::UNKNOWN_OP; + } + } + continue; + } + } for (const Token* tok2 = tok->tokAt(2); tok2 != end2; tok2 = tok2->next()) { if (tok2->varId() && filepointers.find(tok2->varId()) != filepointers.end()) { fileTok = tok2; diff --git a/test/testio.cpp b/test/testio.cpp index 13b75a1c1..449e34d6b 100644 --- a/test/testio.cpp +++ b/test/testio.cpp @@ -554,6 +554,54 @@ private: " fwrite(buffer, 5, 6, f);\n" "}"); ASSERT_EQUALS("[test.cpp:4]: (error) Read and write operations without a call to a positioning function (fseek, fsetpos or rewind) or fflush in between result in undefined behaviour.\n", errout.str()); + + // #6452 - member functions + check("class FileStream {\n" + " void insert(const ByteVector &data, ulong start);\n" + " void seek(long offset, Position p);\n" + " FileStreamPrivate *d;\n" + "};\n" + "void FileStream::insert(const ByteVector &data, ulong start) {\n" + " int bytesRead = fread(aboutToOverwrite.data(), 1, bufferLength, d->file);\n" + " seek(writePosition);\n" + " fwrite(buffer.data(), sizeof(char), buffer.size(), d->file);\n" + "}"); + ASSERT_EQUALS("", errout.str()); + + check("class FileStream {\n" + " void insert(const ByteVector &data, ulong start);\n" + " FileStreamPrivate *d;\n" + "};\n" + "void FileStream::insert(const ByteVector &data, ulong start) {\n" + " int bytesRead = fread(aboutToOverwrite.data(), 1, bufferLength, d->file);\n" + " unknown(writePosition);\n" + " fwrite(buffer.data(), sizeof(char), buffer.size(), d->file);\n" + "}"); + ASSERT_EQUALS("", errout.str()); + + check("class FileStream {\n" + " void insert(const ByteVector &data, ulong start);\n" + " FileStreamPrivate *d;\n" + "};\n" + "void known(int);\n" + "void FileStream::insert(const ByteVector &data, ulong start) {\n" + " int bytesRead = fread(aboutToOverwrite.data(), 1, bufferLength, d->file);\n" + " known(writePosition);\n" + " fwrite(buffer.data(), sizeof(char), buffer.size(), d->file);\n" + "}"); + ASSERT_EQUALS("[test.cpp:9]: (error) Read and write operations without a call to a positioning function (fseek, fsetpos or rewind) or fflush in between result in undefined behaviour.\n", errout.str()); + + check("class FileStream {\n" + " void insert(const ByteVector &data, ulong start);\n" + " FileStreamPrivate *d;\n" + "};\n" + "void known(int);\n" + "void FileStream::insert(const ByteVector &data, ulong start) {\n" + " int bytesRead = fread(X::data(), 1, bufferLength, d->file);\n" + " known(writePosition);\n" + " fwrite(X::data(), sizeof(char), buffer.size(), d->file);\n" + "}"); + ASSERT_EQUALS("[test.cpp:9]: (error) Read and write operations without a call to a positioning function (fseek, fsetpos or rewind) or fflush in between result in undefined behaviour.\n", errout.str()); } void seekOnAppendedFile() {