Skip to content

Commit d63e081

Browse files
committed
fixed #13673 - fixed signedCharArrayIndex detection [skip ci]
1 parent 4aa87ff commit d63e081

File tree

3 files changed

+27
-1
lines changed

3 files changed

+27
-1
lines changed

lib/checkother.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2023,7 +2023,7 @@ void CheckOther::checkCharVariable()
20232023
if (!tok->variable()->isArray() && !tok->variable()->isPointer())
20242024
continue;
20252025
const Token *index = tok->next()->astOperand2();
2026-
if (warning && tok->variable()->isArray() && astIsSignedChar(index) && index->getValueGE(0x80, *mSettings))
2026+
if (warning && tok->variable()->isArray() && astIsSignedChar(index) && index->getValueLE(-1, *mSettings))
20272027
signedCharArrayIndexError(tok);
20282028
if (portability && astIsUnknownSignChar(index) && index->getValueGE(0x80, *mSettings))
20292029
unknownSignCharArrayIndexError(tok);

lib/token.cpp

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1922,6 +1922,7 @@ const ValueFlow::Value * Token::getValueLE(const MathLib::bigint val, const Sett
19221922
{
19231923
if (!mImpl->mValues)
19241924
return nullptr;
1925+
// TODO: assert the given value is actually possible - i.e. 0x80 for a signed char is not possible
19251926
return ValueFlow::findValue(*mImpl->mValues, settings, [&](const ValueFlow::Value& v) {
19261927
return !v.isImpossible() && v.isIntValue() && v.intvalue <= val;
19271928
});
@@ -1931,6 +1932,7 @@ const ValueFlow::Value * Token::getValueGE(const MathLib::bigint val, const Sett
19311932
{
19321933
if (!mImpl->mValues)
19331934
return nullptr;
1935+
// TODO: assert the given value is actually possible - i.e. 0x80 for a signed char is not possible
19341936
return ValueFlow::findValue(*mImpl->mValues, settings, [&](const ValueFlow::Value& v) {
19351937
return !v.isImpossible() && v.isIntValue() && v.intvalue >= val;
19361938
});
@@ -1940,6 +1942,7 @@ const ValueFlow::Value * Token::getValueNE(MathLib::bigint val) const
19401942
{
19411943
if (!mImpl->mValues)
19421944
return nullptr;
1945+
// TODO: assert the given value is actually possible - i.e. 0x80 for a signed char is not possible
19431946
const auto it = std::find_if(mImpl->mValues->cbegin(), mImpl->mValues->cend(), [=](const ValueFlow::Value& value) {
19441947
return value.isIntValue() && !value.isImpossible() && value.intvalue != val;
19451948
});

test/testcharvar.cpp

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -68,6 +68,14 @@ class TestCharVar : public TestFixture {
6868
"}");
6969
ASSERT_EQUALS("[test.cpp:5:5]: (portability) 'char' type used as array index. [unknownSignCharArrayIndex]\n", errout_str());
7070

71+
check("int buf[256];\n"
72+
"void foo()\n"
73+
"{\n"
74+
" signed char ch = 0x80;\n"
75+
" buf[ch] = 0;\n"
76+
"}");
77+
ASSERT_EQUALS("[test.cpp:5:5]: (warning) Signed 'char' type used as array index. [signedCharArrayIndex]\n", errout_str());
78+
7179
check("int buf[256];\n"
7280
"void foo()\n"
7381
"{\n"
@@ -92,6 +100,14 @@ class TestCharVar : public TestFixture {
92100
"}");
93101
ASSERT_EQUALS("[test.cpp:5:5]: (portability) 'char' type used as array index. [unknownSignCharArrayIndex]\n", errout_str());
94102

103+
check("int buf[256];\n"
104+
"void foo()\n"
105+
"{\n"
106+
" signed char ch = 0x80;\n"
107+
" buf[ch] = 0;\n"
108+
"}");
109+
ASSERT_EQUALS("[test.cpp:5:5]: (warning) Signed 'char' type used as array index. [signedCharArrayIndex]\n", errout_str());
110+
95111
check("int buf[256];\n"
96112
"void foo(signed char ch)\n"
97113
"{\n"
@@ -113,6 +129,13 @@ class TestCharVar : public TestFixture {
113129
"}");
114130
ASSERT_EQUALS("[test.cpp:3:24]: (portability) 'char' type used as array index. [unknownSignCharArrayIndex]\n", errout_str());
115131

132+
check("void foo(char* buf)\n"
133+
"{\n"
134+
" signed char ch = 0x80;"
135+
" buf[ch] = 0;\n"
136+
"}");
137+
ASSERT_EQUALS("[test.cpp:3:31]: (warning) Signed 'char' type used as array index. [signedCharArrayIndex]\n", errout_str());
138+
116139
check("void foo(char* buf)\n"
117140
"{\n"
118141
" char ch = 0;"

0 commit comments

Comments
 (0)