From 49e300821f0dc185fb4d1dc378f4248f8536a010 Mon Sep 17 00:00:00 2001 From: chrchr-github Date: Fri, 2 Jan 2026 18:30:35 +0100 Subject: [PATCH 1/3] Partial fix for #12046 FN: containerOutOfBounds (temporary string passed to subfunction) --- lib/valueflow.cpp | 6 ++++-- test/teststl.cpp | 5 +++++ 2 files changed, 9 insertions(+), 2 deletions(-) diff --git a/lib/valueflow.cpp b/lib/valueflow.cpp index e649786fb8f..b803a49dc98 100644 --- a/lib/valueflow.cpp +++ b/lib/valueflow.cpp @@ -6707,13 +6707,15 @@ static void valueFlowContainerSize(const TokenList& tokenlist, for (const ValueFlow::Value& value : values) setTokenValue(tok, value, settings); } - else if (Token::Match(tok->previous(), ",|( {")) { + else if (Token::Match(tok->previous(), ",|( {|%str%")) { int nArg{}; if (const Token* funcTok = getTokenArgumentFunction(tok, nArg)) { if (const Function* func = funcTok->function()) { if (const Variable* var = func->getArgumentVar(nArg)) { if (var->valueType() && var->valueType()->container && var->valueType()->container->size_templateArgNo < 0) { - std::vector values = getInitListSize(tok, var->valueType(), settings, true); + auto values = tok->tokType() == Token::Type::eString ? + std::vector{makeContainerSizeValue(Token::getStrLength(tok))} : + getInitListSize(tok, var->valueType(), settings, true); ValueFlow::Value tokValue; tokValue.valueType = ValueFlow::Value::ValueType::TOK; tokValue.tokvalue = tok; diff --git a/test/teststl.cpp b/test/teststl.cpp index ec6f46148a8..2c4669dbeca 100644 --- a/test/teststl.cpp +++ b/test/teststl.cpp @@ -967,6 +967,11 @@ class TestStl : public TestFixture { "}\n"); ASSERT_EQUALS("[test.cpp:2:17]: error: Out of bounds access in expression 'v[0]' because 'v' is empty. [containerOutOfBounds]\n", errout_str()); + + checkNormal("bool f(const std::string_view s) { return s[500] == 'x'; }\n" // #12046 + "bool g() { return f(\" \"); }\n"); + ASSERT_EQUALS("[test.cpp:1:44]: error: Out of bounds access in 's[500]', if 's' size is 1 and '500' is 500 [containerOutOfBounds]\n", + errout_str()); } void outOfBoundsSymbolic() From 814566f5d79598b9f9768ba88ca17f1f1de5627c Mon Sep 17 00:00:00 2001 From: chrchr-github Date: Fri, 2 Jan 2026 20:01:22 +0100 Subject: [PATCH 2/3] Format --- lib/valueflow.cpp | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/lib/valueflow.cpp b/lib/valueflow.cpp index b803a49dc98..873d3d5facd 100644 --- a/lib/valueflow.cpp +++ b/lib/valueflow.cpp @@ -2594,7 +2594,7 @@ static void valueFlowLifetimeFunction(Token *tok, const TokenList &tokenlist, Er const Token* varTok = args[iArg - 1]; if (varTok->variable() && varTok->variable()->isLocal()) LifetimeStore{ varTok, "Passed to '" + tok->str() + "'.", ValueFlow::Value::LifetimeKind::Address }.byRef( - tok->next(), tokenlist, errorLogger, settings); + tok->next(), tokenlist, errorLogger, settings); } } } @@ -6713,9 +6713,9 @@ static void valueFlowContainerSize(const TokenList& tokenlist, if (const Function* func = funcTok->function()) { if (const Variable* var = func->getArgumentVar(nArg)) { if (var->valueType() && var->valueType()->container && var->valueType()->container->size_templateArgNo < 0) { - auto values = tok->tokType() == Token::Type::eString ? - std::vector{makeContainerSizeValue(Token::getStrLength(tok))} : - getInitListSize(tok, var->valueType(), settings, true); + auto values = tok->tokType() == Token::Type::eString + ? std::vector{makeContainerSizeValue(Token::getStrLength(tok))} + : getInitListSize(tok, var->valueType(), settings, true); ValueFlow::Value tokValue; tokValue.valueType = ValueFlow::Value::ValueType::TOK; tokValue.tokvalue = tok; From c3ea82045c766051b6f6d6d22795a1154353bfef Mon Sep 17 00:00:00 2001 From: chrchr-github <78114321+chrchr-github@users.noreply.github.com> Date: Sat, 3 Jan 2026 01:07:36 +0100 Subject: [PATCH 3/3] Update valueflow.cpp --- lib/valueflow.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/valueflow.cpp b/lib/valueflow.cpp index 873d3d5facd..f3df5a0c31f 100644 --- a/lib/valueflow.cpp +++ b/lib/valueflow.cpp @@ -2594,7 +2594,7 @@ static void valueFlowLifetimeFunction(Token *tok, const TokenList &tokenlist, Er const Token* varTok = args[iArg - 1]; if (varTok->variable() && varTok->variable()->isLocal()) LifetimeStore{ varTok, "Passed to '" + tok->str() + "'.", ValueFlow::Value::LifetimeKind::Address }.byRef( - tok->next(), tokenlist, errorLogger, settings); + tok->next(), tokenlist, errorLogger, settings); } } }