Skip to content

Commit 1c11d30

Browse files
Fix FP returnTempReference (#4793)
* Fix FP returnTempReference * Fix mismatch between token and variable ValueType * Format, clang-tidy * Add test * Format
1 parent f0ebaf9 commit 1c11d30

4 files changed

Lines changed: 70 additions & 1 deletion

File tree

lib/symboldatabase.cpp

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6037,7 +6037,12 @@ void SymbolDatabase::setValueType(Token* tok, const Variable& var, SourceLocatio
60376037
valuetype.setDebugPath(tok, loc);
60386038
if (var.nameToken())
60396039
valuetype.bits = var.nameToken()->bits();
6040-
valuetype.pointer = (var.valueType() && var.valueType()->container) ? 0 : var.dimensions().size();
6040+
6041+
valuetype.pointer = var.dimensions().size();
6042+
// HACK: don't set pointer for plain std::array
6043+
if (var.valueType() && var.valueType()->container && Token::simpleMatch(var.typeStartToken(), "std :: array") && !Token::simpleMatch(var.nameToken()->next(), "["))
6044+
valuetype.pointer = 0;
6045+
60416046
valuetype.typeScope = var.typeScope();
60426047
if (var.valueType()) {
60436048
valuetype.container = var.valueType()->container;

test/test64bit.cpp

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -67,6 +67,12 @@ class Test64BitPortability : public TestFixture {
6767
" CharArray foo = \"\";\n"
6868
"}");
6969
ASSERT_EQUALS("", errout.str());
70+
71+
check("struct T { std::vector<int>*a[2][2]; };\n" // #11560
72+
"void f(T& t, int i, int j) {\n"
73+
" t.a[i][j] = new std::vector<int>;\n"
74+
"}\n");
75+
ASSERT_EQUALS("", errout.str());
7076
}
7177

7278
void novardecl() {

test/testautovariables.cpp

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1714,6 +1714,13 @@ class TestAutoVariables : public TestFixture {
17141714
" return it->foo;\n"
17151715
"}");
17161716
ASSERT_EQUALS("", errout.str());
1717+
1718+
check("static std::vector<int> A[2];\n"
1719+
"static std::vector<int> B;\n"
1720+
"std::vector<int>& g(int i) {\n"
1721+
" return i ? A[i] : B;\n"
1722+
"}\n");
1723+
ASSERT_EQUALS("", errout.str());
17171724
}
17181725

17191726
void returnReferenceLiteral() {

test/testsymboldatabase.cpp

Lines changed: 51 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -130,6 +130,7 @@ class TestSymbolDatabase : public TestFixture {
130130
TEST_CASE(array_ptr);
131131
TEST_CASE(stlarray1);
132132
TEST_CASE(stlarray2);
133+
TEST_CASE(stlarray3);
133134

134135
TEST_CASE(test_isVariableDeclarationCanHandleNull);
135136
TEST_CASE(test_isVariableDeclarationIdentifiesSimpleDeclaration);
@@ -573,6 +574,56 @@ class TestSymbolDatabase : public TestFixture {
573574
ASSERT_EQUALS(20U, v->dimension(0));
574575
}
575576

577+
void stlarray3() {
578+
GET_SYMBOL_DB("std::array<int, 4> a;\n"
579+
"std::array<int, 4> b[2];\n"
580+
"const std::array<int, 4>& r = a;\n");
581+
ASSERT(db != nullptr);
582+
583+
ASSERT_EQUALS(4, db->variableList().size()); // the first one is not used
584+
auto it = db->variableList().begin() + 1;
585+
586+
ASSERT((*it)->isArray());
587+
ASSERT(!(*it)->isPointer());
588+
ASSERT(!(*it)->isReference());
589+
ASSERT_EQUALS(1U, (*it)->dimensions().size());
590+
ASSERT_EQUALS(4U, (*it)->dimension(0));
591+
const ValueType* vt = (*it)->valueType();
592+
ASSERT(vt && vt->container);
593+
ASSERT_EQUALS(vt->pointer, 0);
594+
const Token* tok = (*it)->nameToken();
595+
ASSERT(tok && (vt = tok->valueType()));
596+
ASSERT_EQUALS(vt->pointer, 0);
597+
598+
++it;
599+
ASSERT((*it)->isArray());
600+
ASSERT(!(*it)->isPointer());
601+
ASSERT(!(*it)->isReference());
602+
ASSERT_EQUALS(1U, (*it)->dimensions().size());
603+
ASSERT_EQUALS(4U, (*it)->dimension(0));
604+
vt = (*it)->valueType();
605+
ASSERT_EQUALS(vt->pointer, 0);
606+
tok = (*it)->nameToken();
607+
ASSERT(tok && (vt = tok->valueType()));
608+
ASSERT_EQUALS(vt->pointer, 1);
609+
610+
++it;
611+
ASSERT((*it)->isArray());
612+
ASSERT(!(*it)->isPointer());
613+
ASSERT((*it)->isReference());
614+
ASSERT((*it)->isConst());
615+
ASSERT_EQUALS(1U, (*it)->dimensions().size());
616+
ASSERT_EQUALS(4U, (*it)->dimension(0));
617+
vt = (*it)->valueType();
618+
ASSERT_EQUALS(vt->pointer, 0);
619+
ASSERT(vt->reference == Reference::LValue);
620+
tok = (*it)->nameToken();
621+
ASSERT(tok && (vt = tok->valueType()));
622+
ASSERT_EQUALS(vt->pointer, 0);
623+
ASSERT_EQUALS(vt->constness, 1);
624+
ASSERT(vt->reference == Reference::LValue);
625+
}
626+
576627
void test_isVariableDeclarationCanHandleNull() {
577628
reset();
578629
GET_SYMBOL_DB("void main(){}");

0 commit comments

Comments
 (0)