@@ -1662,8 +1662,81 @@ static bool evalAssignment(ValueFlow::Value &lhsValue, const std::string &assign
16621662 return true ;
16631663}
16641664
1665+ template <class T >
1666+ struct SingleRange {
1667+ T* x;
1668+ T* begin () const {
1669+ return x;
1670+ }
1671+ T* end () const {
1672+ return x+1 ;
1673+ }
1674+ };
1675+
1676+ template <class T >
1677+ SingleRange<T> MakeSingleRange (T& x)
1678+ {
1679+ return {&x};
1680+ }
1681+
1682+ class SelectValueFromVarIdMapRange {
1683+ using M = std::unordered_map<nonneg int , ValueFlow::Value>;
1684+
1685+ struct Iterator {
1686+ using iterator_category = std::forward_iterator_tag;
1687+ using value_type = const ValueFlow::Value;
1688+ using pointer = value_type *;
1689+ using reference = value_type &;
1690+
1691+ explicit Iterator (const M::const_iterator &it)
1692+ : mIt(it) {
1693+ }
1694+
1695+ reference operator *() const {
1696+ return mIt ->second ;
1697+ }
1698+
1699+ pointer operator ->() {
1700+ return &mIt ->second ;
1701+ }
1702+
1703+ Iterator &operator ++() {
1704+ // cppcheck-suppress postfixOperator - forward iterator needs to perform post-increment
1705+ mIt ++;
1706+ return *this ;
1707+ }
1708+
1709+ friend bool operator ==(const Iterator &a, const Iterator &b) {
1710+ return a.mIt == b.mIt ;
1711+ }
1712+
1713+ friend bool operator !=(const Iterator &a, const Iterator &b) {
1714+ return a.mIt != b.mIt ;
1715+ }
1716+
1717+ private:
1718+ M::const_iterator mIt ;
1719+ };
1720+
1721+ public:
1722+ explicit SelectValueFromVarIdMapRange (const M *m)
1723+ : mMap(m) {
1724+ }
1725+
1726+ Iterator begin () const {
1727+ return Iterator (mMap ->begin ());
1728+ }
1729+ Iterator end () const {
1730+ return Iterator (mMap ->end ());
1731+ }
1732+
1733+ private:
1734+ const M *mMap ;
1735+ };
1736+
16651737// Check if its an alias of the variable or is being aliased to this variable
1666- static bool isAliasOf (const Variable * var, const Token *tok, nonneg int varid, const std::list<ValueFlow::Value>& values, bool * inconclusive = nullptr )
1738+ template <typename V>
1739+ static bool isAliasOf (const Variable * var, const Token *tok, nonneg int varid, const V& values, bool * inconclusive = nullptr )
16671740{
16681741 if (tok->varId () == varid)
16691742 return false ;
@@ -2101,7 +2174,7 @@ struct SingleValueFlowAnalyzer : ValueFlowAnalyzer {
21012174 const Variable* var = p.second ;
21022175 if (tok->varId () == varid)
21032176 return true ;
2104- if (isAliasOf (var, tok, varid, { value} , &inconclusive))
2177+ if (isAliasOf (var, tok, varid, MakeSingleRange ( value) , &inconclusive))
21052178 return true ;
21062179 }
21072180 }
@@ -4967,15 +5040,14 @@ struct MultiValueFlowAnalyzer : ValueFlowAnalyzer {
49675040 }
49685041
49695042 virtual bool isAlias (const Token* tok, bool & inconclusive) const OVERRIDE {
4970- std::list<ValueFlow::Value> vals;
4971- std::transform (values.begin (), values.end (), std::back_inserter (vals), SelectMapValues{});
5043+ const auto range = SelectValueFromVarIdMapRange (&values);
49725044
49735045 for (const auto & p:getVars ()) {
49745046 nonneg int varid = p.first ;
49755047 const Variable* var = p.second ;
49765048 if (tok->varId () == varid)
49775049 return true ;
4978- if (isAliasOf (var, tok, varid, vals , &inconclusive))
5050+ if (isAliasOf (var, tok, varid, range , &inconclusive))
49795051 return true ;
49805052 }
49815053 return false ;
0 commit comments