aboutsummaryrefslogtreecommitdiff
path: root/gcc
diff options
context:
space:
mode:
authorDavid Malcolm <dmalcolm@redhat.com>2020-09-16 17:21:32 -0400
committerDavid Malcolm <dmalcolm@redhat.com>2020-09-18 17:38:34 -0400
commitc89956cba9d1a5fbf059f7880ff49418718a2965 (patch)
treea4c2d0c4f393dd43f96f9e9060488debff8e2caf /gcc
parente1a1808cd19afd93fc4134fbd8376346d05bdba8 (diff)
downloadgcc-c89956cba9d1a5fbf059f7880ff49418718a2965.zip
gcc-c89956cba9d1a5fbf059f7880ff49418718a2965.tar.gz
gcc-c89956cba9d1a5fbf059f7880ff49418718a2965.tar.bz2
analyzer: handle strdup and strndup
gcc/analyzer/ChangeLog: * sm-malloc.cc (malloc_state_machine::on_stmt): Handle strdup and strndup as being malloc-like allocators. gcc/testsuite/ChangeLog: * gcc.dg/analyzer/strdup-1.c: New test. * gcc.dg/analyzer/strndup-1.c: New test.
Diffstat (limited to 'gcc')
-rw-r--r--gcc/analyzer/sm-malloc.cc4
-rw-r--r--gcc/testsuite/gcc.dg/analyzer/strdup-1.c21
-rw-r--r--gcc/testsuite/gcc.dg/analyzer/strndup-1.c21
3 files changed, 45 insertions, 1 deletions
diff --git a/gcc/analyzer/sm-malloc.cc b/gcc/analyzer/sm-malloc.cc
index 2b5a870..90d1da1 100644
--- a/gcc/analyzer/sm-malloc.cc
+++ b/gcc/analyzer/sm-malloc.cc
@@ -984,7 +984,9 @@ malloc_state_machine::on_stmt (sm_context *sm_ctxt,
|| is_std_named_call_p (callee_fndecl, "malloc", call, 1)
|| is_std_named_call_p (callee_fndecl, "calloc", call, 2)
|| is_named_call_p (callee_fndecl, "__builtin_malloc", call, 1)
- || is_named_call_p (callee_fndecl, "__builtin_calloc", call, 2))
+ || is_named_call_p (callee_fndecl, "__builtin_calloc", call, 2)
+ || is_named_call_p (callee_fndecl, "strdup", call, 1)
+ || is_named_call_p (callee_fndecl, "strndup", call, 2))
{
on_allocator_call (sm_ctxt, call, m_malloc);
return true;
diff --git a/gcc/testsuite/gcc.dg/analyzer/strdup-1.c b/gcc/testsuite/gcc.dg/analyzer/strdup-1.c
new file mode 100644
index 0000000..6b950ca
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/analyzer/strdup-1.c
@@ -0,0 +1,21 @@
+#include <string.h>
+#include <stdlib.h>
+
+extern void requires_nonnull (void *ptr)
+ __attribute__((nonnull));
+
+void test_1 (const char *s)
+{
+ char *p = strdup (s); /* { dg-message "allocated here" } */
+} /* { dg-warning "leak of 'p'" } */
+
+void test_2 (const char *s)
+{
+ char *p = strdup (s);
+ free (p);
+}
+void test_3 (const char *s)
+{
+ char *p = strdup (s); /* { dg-message "this call could return NULL" } */
+ requires_nonnull (p); /* { dg-warning "use of possibly-NULL 'p'" } */
+}
diff --git a/gcc/testsuite/gcc.dg/analyzer/strndup-1.c b/gcc/testsuite/gcc.dg/analyzer/strndup-1.c
new file mode 100644
index 0000000..23d9b60
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/analyzer/strndup-1.c
@@ -0,0 +1,21 @@
+#include <string.h>
+#include <stdlib.h>
+
+extern void requires_nonnull (void *ptr)
+ __attribute__((nonnull));
+
+void test_1 (const char *s)
+{
+ char *p = strndup (s, 42); /* { dg-message "allocated here" } */
+} /* { dg-warning "leak of 'p'" } */
+
+void test_2 (const char *s)
+{
+ char *p = strndup (s, 42);
+ free (p);
+}
+void test_3 (const char *s)
+{
+ char *p = strndup (s, 42); /* { dg-message "this call could return NULL" } */
+ requires_nonnull (p); /* { dg-warning "use of possibly-NULL 'p'" } */
+}