https://gcc.gnu.org/bugzilla/show_bug.cgi?id=125304

            Bug ID: 125304
           Summary: -Wanalyzer-free-of-non-heap false positive with
                    std::string due to CAST_REG comparison bug
           Product: gcc
           Version: 17.0
            Status: UNCONFIRMED
          Keywords: false-positive
          Severity: normal
          Priority: P3
         Component: analyzer
          Assignee: dmalcolm at gcc dot gnu.org
          Reporter: dmalcolm at gcc dot gnu.org
            Blocks: 97110
  Target Milestone: ---

The analyzer reports a false positive when analyzing std::string's destructor.
It incorrectly warns about freeing stack memory (_M_local_buf) when the string
uses Small String Optimization (SSO).

I saw the following on a trivial use of an empty std::string:

// { dg-additional-options "-O2" }
// { dg-additional-options "-fno-analyzer-state-merge" }

#include "../../gcc.dg/analyzer/analyzer-decls.h"
#include <string>

void
test_ctor_empty ()
{
  std::string s;
  __analyzer_eval (s.length () == 0); // { dg-warning "TRUE" }
  __analyzer_eval (s.size () == 0); // { dg-warning "TRUE" }


with a snapshot of state of libstdc++ at r17-368-gb1cd9bd9908b0f in my working
copy (though not in Compiler Explorer).  

I captured the preprocessed source and reduced it.

It seems to be an instance of a more general issue.  I'm filing this now as a
checkpoint of where I've gotten up to.

How to reproduce:

See attached test case std-string-snapshot-1.C. 

Compile command:

$ g++ -fanalyzer -O2 -fno-analyzer-state-merge -S std-string-snapshot-1.C

Expected behavior:

Only the three TRUE warnings from __analyzer_eval should be emitted. No
warnings about freeing stack memory.

Actual behavior:

$ g++ -fanalyzer -O2 -fno-analyzer-state-merge -S std-string-snapshot-1.C
std-string-snapshot-1.C:129:18: warning: TRUE
std-string-snapshot-1.C:130:18: warning: TRUE
std-string-snapshot-1.C:131:18: warning: TRUE
std-string-snapshot-1.C:35:34: warning: 'delete' of '&
s.std::basic_string<char, std::char_traits<char>, std::allocator<char>
>::<anonymous>.std::basic_string<char, std::char_traits<char>,
std::allocator<char> >::<unnamed union>::_M_local_buf' which points to memory
on the stack [CWE-590] [-Wanalyzer-free-of-non-heap]

The false positive occurs at line 35 in allocator::deallocate.


Referenced Bugs:

https://gcc.gnu.org/bugzilla/show_bug.cgi?id=97110
[Bug 97110] [meta-bug] tracker bug for supporting C++ in -fanalyzer

Reply via email to