diff --git a/src/checkmemoryleak.cpp b/src/checkmemoryleak.cpp index 90ca2e1ea..b3d069ce3 100644 --- a/src/checkmemoryleak.cpp +++ b/src/checkmemoryleak.cpp @@ -23,6 +23,7 @@ #include #include +#include #include #include #include @@ -37,6 +38,28 @@ CheckMemoryLeakInClass instance2; CheckMemoryLeakStructMember instance3; } +// This list needs to be alphabetically sorted so we can run bsearch on it +static const char * const call_func_white_list[] = +{ + "atof", "atoi", "atol", "clearerr", "delete", "fchmod", "fcntl" + , "fdatasync", "feof", "ferror", "fflush", "fgetc", "fgetpos", "fgets" + , "flock", "for", "fprintf", "fputc", "fputs", "fread", "fseek" + , "fseeko", "fsetpos", "fstat", "fsync", "ftell", "ftello", "ftruncate" + , "fwrite", "getc", "if", "ioctl", "lockf", "lseek", "memchr", "memcpy" + , "memmove", "memset", "posix_fadvise", "posix_fallocate", "pread" + , "printf", "pwrite", "read", "readahead", "readdir", "readdir_r", "readv" + , "realloc", "return", "rewind", "rewinddir", "scandir", "seekdir" + , "setbuf", "setbuffer", "setlinebuf", "setvbuf", "sprintf", "strcasecmp" + , "strcat", "strchr", "strcmp", "strcpy", "stricmp", "strncat", "strncmp" + , "strncpy", "strrchr", "strstr", "strtod", "strtol", "strtoul", "switch" + , "sync_file_range", "telldir", "while", "write", "writev" +}; + +static int call_func_white_list_compare(const void *a, const void *b) +{ + return strcmp((const char *)a, *(const char **)b); +} + //--------------------------------------------------------------------------- bool CheckMemoryLeak::isclass(const Tokenizer *_tokenizer, const Token *tok) const @@ -407,35 +430,6 @@ CheckMemoryLeak::AllocType CheckMemoryLeak::functionReturnType(const Token *tok) return No; } - -void CheckMemoryLeakInFunction::init() -{ - static const char * const white_list[] = - { - "if", "for", "while", "return", "switch", "realloc", "delete" - , "strcpy", "strncpy", "strcat", "strncat", "strcmp", "strncmp" - , "strcasecmp", "stricmp", "sprintf", "strchr", "strrchr", "strstr" - , "memset", "memcpy", "memmove", "memchr", "fgets", "fgetc", "getc" - , "fputs", "fputc", "feof", "ferror", "clearerr", "printf", "fprintf" - , "fread", "fwrite", "fflush", "fseek", "fseeko", "ftell", "ftello" - , "fsetpos", "fgetpos", "setvbuf", "setbuf", "setbuffer", "setlinebuf" - , "rewind", "read", "readv", "pread", "readahead", "write", "writev" - , "pwrite", "lseek", "ioctl", "fchmod", "fcntl", "flock", "lockf" - , "ftruncate", "fsync", "fdatasync", "fstat", "sync_file_range" - , "posix_fallocate", "posix_fadvise", "readdir", "readdir_r" - , "rewinddir", "telldir", "seekdir", "scandir", "atoi", "atof", "atol" - , "strtol", "strtoul", "strtod" - , NULL - }; - - size_t i = 0; - while (white_list[i] != NULL) - { - call_func_white_list.insert(white_list[i]); - ++i; - } -} - bool CheckMemoryLeakInFunction::matchFunctionsThatReturnArg(const Token *tok, const unsigned int varid) const { return Token::Match(tok, "; %varid% = strcat|memcpy|memmove|strcpy ( %varid% ,", varid); @@ -480,7 +474,9 @@ static int countParameters(const Token *tok) const char * CheckMemoryLeakInFunction::call_func(const Token *tok, std::list callstack, const unsigned int varid, AllocType &alloctype, AllocType &dealloctype, bool &all, unsigned int sz) { - if (call_func_white_list.find(tok->str()) != call_func_white_list.end()) + if (bsearch(tok->str().c_str(), call_func_white_list, + sizeof(call_func_white_list) / sizeof(call_func_white_list[0]), + sizeof(call_func_white_list[0]), call_func_white_list_compare)) return 0; if (getAllocationType(tok, varid) != No || getReallocationType(tok, varid) != No || getDeallocationType(tok, varid) != No) diff --git a/src/checkmemoryleak.h b/src/checkmemoryleak.h index 0361014f5..f86ece3ab 100644 --- a/src/checkmemoryleak.h +++ b/src/checkmemoryleak.h @@ -145,16 +145,12 @@ class CheckMemoryLeakInFunction : private Check, private CheckMemoryLeak public: /** This constructor is used when registering this class */ CheckMemoryLeakInFunction() : Check(), CheckMemoryLeak(0, 0) - { - init(); - } + { } /** This constructor is used when running checks */ CheckMemoryLeakInFunction(const Tokenizer *tokenizer, const Settings *settings, ErrorLogger *errorLogger) : Check(tokenizer, settings, errorLogger), CheckMemoryLeak(tokenizer, errorLogger) - { - init(); - } + { } void runSimplifiedChecks(const Tokenizer *tokenizer, const Settings *settings, ErrorLogger *errorLogger) { @@ -272,13 +268,6 @@ private: { return "Is there any allocated memory when a function goes out of scope"; } - - // Keywords and function names which not allocating nor deallocating memory - // (used by call_func()) - std::set call_func_white_list; - - // Called in all constructors - void init(); }; diff --git a/src/token.cpp b/src/token.cpp index 6c1873259..a13806d18 100644 --- a/src/token.cpp +++ b/src/token.cpp @@ -488,21 +488,6 @@ bool Token::Match(const Token *tok, const char pattern[], unsigned int varid) return true; } -bool Token::isName() const -{ - return _isName; -} - -bool Token::isNumber() const -{ - return _isNumber; -} - -bool Token::isBoolean() const -{ - return _isBoolean; -} - bool Token::isStandardType() const { bool ret = false; @@ -524,36 +509,6 @@ const Token *Token::findmatch(const Token *tok, const char pattern[], unsigned i return 0; } -unsigned int Token::varId() const -{ - return _varId; -} - -void Token::varId(unsigned int id) -{ - _varId = id; -} - -Token *Token::next() const -{ - return _next; -} - -void Token::next(Token *next) -{ - _next = next; -} - -Token *Token::previous() const -{ - return _previous; -} - -void Token::previous(Token *previous) -{ - _previous = previous; -} - void Token::insertToken(const char str[]) { Token *newToken = new Token; @@ -581,36 +536,6 @@ void Token::eraseTokens(Token *begin, const Token *end) } } -unsigned int Token::fileIndex() const -{ - return _fileIndex; -} - -void Token::fileIndex(unsigned int fileIndex) -{ - _fileIndex = fileIndex; -} - -unsigned int Token::linenr() const -{ - return _linenr; -} - -void Token::linenr(unsigned int linenr) -{ - _linenr = linenr; -} - -void Token::link(Token *link) -{ - _link = link; -} - -Token *Token::link() const -{ - return _link; -} - void Token::createMutualLinks(Token *begin, Token *end) { assert(begin != NULL); diff --git a/src/token.h b/src/token.h index 9e2ba3df8..181f7dcd4 100644 --- a/src/token.h +++ b/src/token.h @@ -117,9 +117,9 @@ public: */ static bool Match(const Token *tok, const char pattern[], unsigned int varid = 0); - bool isName() const; - bool isNumber() const; - bool isBoolean() const; + bool isName() const { return _isName; } + bool isNumber() const { return _isNumber; } + bool isBoolean() const { return _isBoolean; } bool isStandardType() const; static const Token *findmatch(const Token *tok, const char pattern[], unsigned int varId = 0); @@ -139,13 +139,13 @@ public: */ static int multiCompare(const char *haystack, const char *needle); - unsigned int linenr() const; - void linenr(unsigned int linenr); + unsigned int linenr() const { return _linenr; } + void linenr(unsigned int linenr) { _linenr = linenr; } - unsigned int fileIndex() const; - void fileIndex(unsigned int fileIndex); + unsigned int fileIndex() const { return _fileIndex; } + void fileIndex(unsigned int fileIndex) { _fileIndex = fileIndex; } - Token *next() const; + Token *next() const { return _next; } /** @@ -164,11 +164,11 @@ public: */ void insertToken(const char str[]); - Token *previous() const; + Token *previous() const { return _previous; } - unsigned int varId() const; - void varId(unsigned int id); + unsigned int varId() const { return _varId; } + void varId(unsigned int id) { _varId = id; } /** * For debugging purposes, prints token and all tokens @@ -202,7 +202,7 @@ public: * @param link The token where this token should link * to. */ - void link(Token *link); + void link(Token *link) { _link = link; } /** * Return token where this token links to. @@ -211,7 +211,7 @@ public: * * @return The token where this token links to. */ - Token *link() const; + Token *link() const { return _link; } /** * Links two elements against each other. @@ -219,8 +219,8 @@ public: static void createMutualLinks(Token *begin, Token *end); private: - void next(Token *next); - void previous(Token *previous); + void next(Token *next) { _next = next; } + void previous(Token *previous) { _previous = previous; } /** * Works almost like strcmp() except returns only 0 or 1 and