From: Jakub Jelinek <jakub@redhat.com>
To: Jason Merrill <jason@redhat.com>
Cc: gcc-patches@gcc.gnu.org
Subject: [C++ PATCH] Fix -fsanitize={null,alignment} of references (PR c++/79572)
Date: Thu, 23 Mar 2017 20:39:00 -0000 [thread overview]
Message-ID: <20170323203705.GX11094@tucnak> (raw)
Hi!
Since late C++ folding has been committed, we don't sanitize some reference
bindings to NULL. Earlier we had always NOP_EXPR to REFERENCE_TYPE say from
INTEGER_CST or whatever else, but cp_fold can now turn that right into
INTEGER_CST with REFERENCE_TYPE. The following patch sanitizes even those.
Bootstrapped/regtested on x86_64-linux and i686-linux, ok for trunk?
2017-03-23 Jakub Jelinek <jakub@redhat.com>
PR c++/79572
* c-ubsan.h (ubsan_maybe_instrument_reference): Change argument to
tree *.
* c-ubsan.c (ubsan_maybe_instrument_reference): Likewise. Handle
not just NOP_EXPR to REFERENCE_TYPE, but also INTEGER_CST with
REFERENCE_TYPE.
* cp-gimplify.c (cp_genericize_r): Sanitize INTEGER_CSTs with
REFERENCE_TYPE. Adjust ubsan_maybe_instrument_reference caller
for NOP_EXPR to REFERENCE_TYPE.
* g++.dg/ubsan/null-8.C: New test.
--- gcc/c-family/c-ubsan.h.jj 2017-01-01 12:45:46.000000000 +0100
+++ gcc/c-family/c-ubsan.h 2017-03-23 09:13:16.287888726 +0100
@@ -28,7 +28,7 @@ extern tree ubsan_instrument_return (loc
extern tree ubsan_instrument_bounds (location_t, tree, tree *, bool);
extern bool ubsan_array_ref_instrumented_p (const_tree);
extern void ubsan_maybe_instrument_array_ref (tree *, bool);
-extern void ubsan_maybe_instrument_reference (tree);
+extern void ubsan_maybe_instrument_reference (tree *);
extern void ubsan_maybe_instrument_member_call (tree, bool);
/* Declare this here as well as in ubsan.h. */
--- gcc/c-family/c-ubsan.c.jj 2017-01-01 12:45:46.000000000 +0100
+++ gcc/c-family/c-ubsan.c 2017-03-23 09:18:51.775486699 +0100
@@ -458,17 +458,26 @@ ubsan_maybe_instrument_reference_or_call
return fold_build2 (COMPOUND_EXPR, TREE_TYPE (op), call, op);
}
-/* Instrument a NOP_EXPR to REFERENCE_TYPE if needed. */
+/* Instrument a NOP_EXPR to REFERENCE_TYPE or INTEGER_CST with REFERENCE_TYPE
+ type if needed. */
void
-ubsan_maybe_instrument_reference (tree stmt)
+ubsan_maybe_instrument_reference (tree *stmt_p)
{
- tree op = TREE_OPERAND (stmt, 0);
+ tree stmt = *stmt_p;
+ tree op = stmt;
+ if (TREE_CODE (stmt) == NOP_EXPR)
+ op = TREE_OPERAND (stmt, 0);
op = ubsan_maybe_instrument_reference_or_call (EXPR_LOCATION (stmt), op,
TREE_TYPE (stmt),
UBSAN_REF_BINDING);
if (op)
- TREE_OPERAND (stmt, 0) = op;
+ {
+ if (TREE_CODE (stmt) == NOP_EXPR)
+ TREE_OPERAND (stmt, 0) = op;
+ else
+ *stmt_p = op;
+ }
}
/* Instrument a CALL_EXPR to a method if needed. */
--- gcc/cp/cp-gimplify.c.jj 2017-03-03 13:23:58.000000000 +0100
+++ gcc/cp/cp-gimplify.c 2017-03-23 09:21:26.693460888 +0100
@@ -1130,6 +1130,19 @@ cp_genericize_r (tree *stmt_p, int *walk
}
}
+ if (TREE_CODE (stmt) == INTEGER_CST
+ && TREE_CODE (TREE_TYPE (stmt)) == REFERENCE_TYPE
+ && (flag_sanitize & (SANITIZE_NULL | SANITIZE_ALIGNMENT))
+ && !wtd->no_sanitize_p)
+ {
+ ubsan_maybe_instrument_reference (stmt_p);
+ if (*stmt_p != stmt)
+ {
+ *walk_subtrees = 0;
+ return NULL_TREE;
+ }
+ }
+
/* Other than invisiref parms, don't walk the same tree twice. */
if (p_set->contains (stmt))
{
@@ -1477,7 +1490,7 @@ cp_genericize_r (tree *stmt_p, int *walk
if ((flag_sanitize & (SANITIZE_NULL | SANITIZE_ALIGNMENT))
&& TREE_CODE (stmt) == NOP_EXPR
&& TREE_CODE (TREE_TYPE (stmt)) == REFERENCE_TYPE)
- ubsan_maybe_instrument_reference (stmt);
+ ubsan_maybe_instrument_reference (stmt_p);
else if (TREE_CODE (stmt) == CALL_EXPR)
{
tree fn = CALL_EXPR_FN (stmt);
--- gcc/testsuite/g++.dg/ubsan/null-8.C.jj 2017-03-23 09:42:31.664696676 +0100
+++ gcc/testsuite/g++.dg/ubsan/null-8.C 2017-03-23 09:43:31.501908802 +0100
@@ -0,0 +1,19 @@
+// PR c++/79572
+// { dg-do run }
+// { dg-options "-fsanitize=null -std=c++14" }
+// { dg-output "reference binding to null pointer of type 'const int'" }
+
+void
+foo (const int &iref)
+{
+ if (&iref)
+ __builtin_printf ("iref %d\n", iref);
+ else
+ __builtin_printf ("iref is NULL\n");
+}
+
+int
+main ()
+{
+ foo (*((int*) __null));
+}
Jakub
next reply other threads:[~2017-03-23 20:37 UTC|newest]
Thread overview: 4+ messages / expand[flat|nested] mbox.gz Atom feed top
2017-03-23 20:39 Jakub Jelinek [this message]
2017-11-24 14:52 ` Maxim Kuvyrkov
2017-11-24 14:58 ` Jakub Jelinek
2017-11-27 10:49 ` Jakub Jelinek
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20170323203705.GX11094@tucnak \
--to=jakub@redhat.com \
--cc=gcc-patches@gcc.gnu.org \
--cc=jason@redhat.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).