From: David Malcolm Date: Tue, 10 Mar 2020 23:03:37 +0000 (-0400) Subject: analyzer: handle NOP_EXPR in get_lvalue [PR94099,PR94105] X-Git-Url: https://git.libre-soc.org/?a=commitdiff_plain;h=5c048755ec98645f8436b630df3f9294ca9cbc2a;p=gcc.git analyzer: handle NOP_EXPR in get_lvalue [PR94099,PR94105] PR analyzer/94099 and PR analyzer/94105 both report ICEs relating to calling region_model::get_lvalue on a NOP_EXPR. PR analyzer/94099's ICE happens when generating a checker_path when encountering an unhandled tree code (NOP_EXPR) in get_lvalue with a NULL context (from for_each_state_change). PR analyzer/94105 ICE happens when handling an ARRAY_REF where the first operand is a NOP_EXPR: the unhandled tree code gives us a symbolic_region, but the case for ARRAY_REF assumes we have an array_region. This patch fixes the ICEs by handling NOP_EXPR within region_model::get_lvalue, and bulletproofs both of the above sources of failure. gcc/analyzer/ChangeLog: PR analyzer/94099 PR analyzer/94105 * diagnostic-manager.cc (for_each_state_change): Bulletproof against errors in get_rvalue by passing a tentative_region_model_context and rejecting if there's an error. * region-model.cc (region_model::get_lvalue_1): When handling ARRAY_REF, handle results of error-handling. Handle NOP_EXPR. gcc/testsuite/ChangeLog: PR analyzer/94099 PR analyzer/94105 * gcc.dg/analyzer/pr94099.c: New test. * gcc.dg/analyzer/pr94105.c: New test. --- diff --git a/gcc/analyzer/ChangeLog b/gcc/analyzer/ChangeLog index e51a1cdf56a..8fc5dc4448f 100644 --- a/gcc/analyzer/ChangeLog +++ b/gcc/analyzer/ChangeLog @@ -1,3 +1,13 @@ +2020-03-13 David Malcolm + + PR analyzer/94099 + PR analyzer/94105 + * diagnostic-manager.cc (for_each_state_change): Bulletproof + against errors in get_rvalue by passing a + tentative_region_model_context and rejecting if there's an error. + * region-model.cc (region_model::get_lvalue_1): When handling + ARRAY_REF, handle results of error-handling. Handle NOP_EXPR. + 2020-03-06 David Malcolm * analyzer.h (class array_region): New forward decl. diff --git a/gcc/analyzer/diagnostic-manager.cc b/gcc/analyzer/diagnostic-manager.cc index 1b2c3ce68fa..bea566da9fc 100644 --- a/gcc/analyzer/diagnostic-manager.cc +++ b/gcc/analyzer/diagnostic-manager.cc @@ -768,9 +768,10 @@ for_each_state_change (const program_state &src_state, if (dst_pv->m_stack_depth >= src_state.m_region_model->get_stack_depth ()) continue; + tentative_region_model_context ctxt; svalue_id src_sid - = src_state.m_region_model->get_rvalue (*dst_pv, NULL); - if (src_sid.null_p ()) + = src_state.m_region_model->get_rvalue (*dst_pv, &ctxt); + if (src_sid.null_p () || ctxt.had_errors_p ()) continue; state_machine::state_t src_sm_val = src_smap.get_state (src_sid); if (dst_sm_val != src_sm_val) diff --git a/gcc/analyzer/region-model.cc b/gcc/analyzer/region-model.cc index 87980e7c8cd..45a190299ea 100644 --- a/gcc/analyzer/region-model.cc +++ b/gcc/analyzer/region-model.cc @@ -4749,7 +4749,18 @@ region_model::get_lvalue_1 (path_var pv, region_model_context *ctxt) region_id array_rid = get_lvalue (array, ctxt); svalue_id index_sid = get_rvalue (index, ctxt); - array_region *array_reg = get_region (array_rid); + region *base_array_reg = get_region (array_rid); + array_region *array_reg = base_array_reg->dyn_cast_array_region (); + if (!array_reg) + { + /* Normally, array_rid ought to refer to an array_region, since + array's type will be ARRAY_TYPE. However, if we have an + unexpected tree code for array, we could have a + symbolic_region here. If so, we're in error-handling. */ + gcc_assert (base_array_reg->get_type () == NULL_TREE); + return make_region_for_unexpected_tree_code (ctxt, expr, + dump_location_t ()); + } return array_reg->get_element (this, array_rid, index_sid, ctxt); } break; @@ -4849,6 +4860,7 @@ region_model::get_lvalue_1 (path_var pv, region_model_context *ctxt) } break; + case NOP_EXPR: case VIEW_CONVERT_EXPR: { tree obj = TREE_OPERAND (expr, 0); diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index 296ea8f0011..75d6041ba90 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,10 @@ +2020-03-13 David Malcolm + + PR analyzer/94099 + PR analyzer/94105 + * gcc.dg/analyzer/pr94099.c: New test. + * gcc.dg/analyzer/pr94105.c: New test. + 2020-03-13 Vasee Vinayagamoorthy * gcc.target/aarch64/advsimd-intrinsics/bfcvt-nosimd.c: Fix DejaGnu diff --git a/gcc/testsuite/gcc.dg/analyzer/pr94099.c b/gcc/testsuite/gcc.dg/analyzer/pr94099.c new file mode 100644 index 00000000000..0a34f561821 --- /dev/null +++ b/gcc/testsuite/gcc.dg/analyzer/pr94099.c @@ -0,0 +1,27 @@ +/* { dg-additional-options "-O1" } */ + +struct cg { + int hk; + int *bg; +}; + +union vb { + struct cg gk; +}; + +void +l3 (union vb *); + +void +pl (void) +{ + union vb th = { 0, }; + int sc; + + for (sc = 0; sc < 1; ++sc) + { + th.gk.hk = 0; + th.gk.bg[sc] = 0; /* { dg-warning "uninitialized" } */ + l3 (&th); + } +} diff --git a/gcc/testsuite/gcc.dg/analyzer/pr94105.c b/gcc/testsuite/gcc.dg/analyzer/pr94105.c new file mode 100644 index 00000000000..8220723bf6c --- /dev/null +++ b/gcc/testsuite/gcc.dg/analyzer/pr94105.c @@ -0,0 +1,3 @@ +/* { dg-do compile } */ + +#include "../../c-c++-common/torture/pr58794-1.c"