Fix #10238: char* confused with char (#3484)

This commit is contained in:
chrchr-github 2021-10-05 18:04:48 +02:00 committed by GitHub
parent a2ea8654b0
commit f3e1f0d41b
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
3 changed files with 14 additions and 6 deletions

View File

@ -205,7 +205,7 @@ bool astIsUnknownSignChar(const Token *tok)
bool astIsGenericChar(const Token* tok)
{
return tok && tok->valueType() && (tok->valueType()->type == ValueType::Type::CHAR || tok->valueType()->type == ValueType::Type::WCHAR_T);
return !astIsPointer(tok) && tok && tok->valueType() && (tok->valueType()->type == ValueType::Type::CHAR || tok->valueType()->type == ValueType::Type::WCHAR_T);
}
bool astIsIntegral(const Token *tok, bool unknown)

View File

@ -7043,18 +7043,19 @@ static std::vector<ValueFlow::Value> getInitListSize(const Token* tok,
if (!args.empty() && container->stdStringLike) {
if (astIsGenericChar(args[0])) // init list of chars
return { makeContainerSizeValue(args.size(), known) };
if (astIsIntegral(args[0], false)) {
if (astIsIntegral(args[0], false)) { // { count, 'c' }
if (args.size() > 1)
return {makeContainerSizeValue(args[0], known)};
} else if (astIsPointer(args[0])) {
// TODO: Try to read size of string literal
if (args.size() == 2 && astIsIntegral(args[1], false))
// TODO: Try to read size of string literal { "abc" }
if (args.size() == 2 && astIsIntegral(args[1], false)) // { char*, count }
return {makeContainerSizeValue(args[1], known)};
} else if (astIsContainer(args[0])) {
if (args.size() == 1)
if (args.size() == 1) // copy constructor { str }
return getContainerValues(args[0]);
if (args.size() == 3)
if (args.size() == 3) // { str, pos, count }
return {makeContainerSizeValue(args[2], known)};
// TODO: { str, pos }, { ..., alloc }
}
return {};
} else if ((args.size() == 1 && astIsContainer(args[0]) && args[0]->valueType()->container == container) ||

View File

@ -5126,6 +5126,13 @@ private:
"}";
ASSERT_EQUALS("", isKnownContainerSizeValue(tokenValues(code, "s . size"), 3));
code = "void f(const char* p) {\n"
" if (p == nullptr) return;\n"
" std::string s { p };\n" // size of s is unknown
" s.front();\n"
"}";
ASSERT(tokenValues(code, "s . front").empty());
code = "void f() {\n"
" std::string s = { 'a', 'b', 'c' };\n" // size of s is 3
" s.size();\n"