@@ -1,5 +1,47 @@
2014-10-24 David Malcolm <dmalcolm@redhat.com>
+ Introduce gimple_try
+
+ * coretypes.h (gimple_try): New typedef.
+ (const_gimple_try): New typedef.
+
+ * gimple-low.c (gimple_try_catch_may_fallthru): Require a
+ gimple_try rather than a plain gimple.
+ (gimple_stmt_may_fallthru): Add checked cast to gimple_try.
+
+ * gimple-pretty-print.c (dump_gimple_try): Require a gimple_try
+ rather than a plain gimple.
+ (pp_gimple_stmt_1): Add checked cast to gimple_try within
+ GIMPLE_TRY case of switch statement.
+
+ * tree-eh.c (finally_tree_node::parent): Strengthen field from
+ gimple to gimple_try.
+ (record_in_finally_tree): Require a gimple_try rather than a plain
+ gimple.
+ (collect_finally_tree): Likewise.
+ (collect_finally_tree_1): Likewise.
+ (struct leh_tf_state::try_finally_expr): Strengthen field from
+ gimple to gimple_try.
+ (struct leh_tf_state::top_p): Likewise.
+ (lower_eh_must_not_throw): Require a gimple_try rather than a
+ plain gimple.
+ (frob_into_branch_around): Likewise.
+ (lower_try_finally_dup_block): Strengthen local from gimple to
+ gimple_try.
+ (honor_protect_cleanup_actions): Split out uses of "x" into new
+ locals "eh_mnt" and "try_stmt" with stronger types.
+ (lower_try_finally): Require a gimple_try rather than a plain
+ gimple.
+ (lower_catch): Likewise.
+ (lower_eh_filter): Likewise.
+ (lower_eh_must_not_throw): Likewise.
+ (lower_cleanup): Likewise.
+ (lower_eh_constructs_2): Add checked cast to gimple_try within
+ GIMPLE_TRY case of switch statement, introducing new local
+ "try_stmt", using it for type-safety.
+
+2014-10-24 David Malcolm <dmalcolm@redhat.com>
+
Use subclasses of gimple in various places
* asan.c (insert_if_then_before_iter): Require a gimple cond
@@ -162,6 +162,10 @@ struct gimple_statement_phi;
typedef struct gimple_statement_phi *gimple_phi;
typedef const struct gimple_statement_phi *const_gimple_phi;
+struct gimple_statement_try;
+typedef struct gimple_statement_try *gimple_try;
+typedef const struct gimple_statement_try *const_gimple_try;
+
union section;
typedef union section section;
struct gcc_options;
@@ -499,7 +499,7 @@ lower_try_catch (gimple_stmt_iterator *gsi, struct lower_data *data)
This is a subroutine of gimple_stmt_may_fallthru. */
static bool
-gimple_try_catch_may_fallthru (gimple stmt)
+gimple_try_catch_may_fallthru (gimple_try stmt)
{
gimple_stmt_iterator i;
@@ -585,7 +585,7 @@ gimple_stmt_may_fallthru (gimple stmt)
case GIMPLE_TRY:
if (gimple_try_kind (stmt) == GIMPLE_TRY_CATCH)
- return gimple_try_catch_may_fallthru (stmt);
+ return gimple_try_catch_may_fallthru (as_a <gimple_try> (stmt));
/* It must be a GIMPLE_TRY_FINALLY. */
@@ -932,7 +932,7 @@ dump_gimple_bind (pretty_printer *buffer, gimple_bind gs, int spc, int flags)
dumpfile.h). */
static void
-dump_gimple_try (pretty_printer *buffer, gimple gs, int spc, int flags)
+dump_gimple_try (pretty_printer *buffer, gimple_try gs, int spc, int flags)
{
if (flags & TDF_RAW)
{
@@ -2128,7 +2128,7 @@ pp_gimple_stmt_1 (pretty_printer *buffer, gimple gs, int spc, int flags)
break;
case GIMPLE_TRY:
- dump_gimple_try (buffer, gs, spc, flags);
+ dump_gimple_try (buffer, as_a <gimple_try> (gs), spc, flags);
break;
case GIMPLE_PHI:
@@ -177,7 +177,7 @@ struct finally_tree_node
tree) leaves the TRY block, its necessary to record a tree in
this field. Thus a treemple is used. */
treemple child;
- gimple parent;
+ gimple_try parent;
};
/* Hashtable helpers. */
@@ -206,7 +206,7 @@ finally_tree_hasher::equal (const value_type *v, const compare_type *c)
static hash_table<finally_tree_hasher> *finally_tree;
static void
-record_in_finally_tree (treemple child, gimple parent)
+record_in_finally_tree (treemple child, gimple_try parent)
{
struct finally_tree_node *n;
finally_tree_node **slot;
@@ -221,13 +221,13 @@ record_in_finally_tree (treemple child, gimple parent)
}
static void
-collect_finally_tree (gimple stmt, gimple region);
+collect_finally_tree (gimple stmt, gimple_try region);
/* Go through the gimple sequence. Works with collect_finally_tree to
record all GIMPLE_LABEL and GIMPLE_TRY statements. */
static void
-collect_finally_tree_1 (gimple_seq seq, gimple region)
+collect_finally_tree_1 (gimple_seq seq, gimple_try region)
{
gimple_stmt_iterator gsi;
@@ -236,7 +236,7 @@ collect_finally_tree_1 (gimple_seq seq, gimple region)
}
static void
-collect_finally_tree (gimple stmt, gimple region)
+collect_finally_tree (gimple stmt, gimple_try region)
{
treemple temp;
@@ -252,7 +252,8 @@ collect_finally_tree (gimple stmt, gimple region)
{
temp.g = stmt;
record_in_finally_tree (temp, region);
- collect_finally_tree_1 (gimple_try_eval (stmt), stmt);
+ collect_finally_tree_1 (gimple_try_eval (stmt),
+ as_a <gimple_try> (stmt));
collect_finally_tree_1 (gimple_try_cleanup (stmt), region);
}
else if (gimple_try_kind (stmt) == GIMPLE_TRY_CATCH)
@@ -369,8 +370,8 @@ struct leh_tf_state
try_finally_expr is the original GIMPLE_TRY_FINALLY. We need to retain
this so that outside_finally_tree can reliably reference the tree used
in the collect_finally_tree data structures. */
- gimple try_finally_expr;
- gimple top_p;
+ gimple_try try_finally_expr;
+ gimple_try top_p;
/* While lowering a top_p usually it is expanded into multiple statements,
thus we need the following field to store them. */
@@ -410,7 +411,7 @@ struct leh_tf_state
bool may_throw;
};
-static gimple_seq lower_eh_must_not_throw (struct leh_state *, gimple);
+static gimple_seq lower_eh_must_not_throw (struct leh_state *, gimple_try);
/* Search for STMT in the goto queue. Return the replacement,
or null if the statement isn't in the queue. */
@@ -861,7 +862,7 @@ eh_region_may_contain_throw (eh_region r)
an existing label that should be put at the exit, or NULL. */
static gimple_seq
-frob_into_branch_around (gimple tp, eh_region region, tree over)
+frob_into_branch_around (gimple_try tp, eh_region region, tree over)
{
gimple x;
gimple_seq cleanup, result;
@@ -898,7 +899,7 @@ static gimple_seq
lower_try_finally_dup_block (gimple_seq seq, struct leh_state *outer_state,
location_t loc)
{
- gimple region = NULL;
+ gimple_try region = NULL;
gimple_seq new_seq;
gimple_stmt_iterator gsi;
@@ -990,6 +991,8 @@ honor_protect_cleanup_actions (struct leh_state *outer_state,
bool finally_may_fallthru;
gimple_seq finally;
gimple x;
+ gimple_eh_must_not_throw eh_mnt;
+ gimple_try try_stmt;
gimple_eh_else eh_else;
/* First check for nothing to do. */
@@ -1032,10 +1035,10 @@ honor_protect_cleanup_actions (struct leh_state *outer_state,
}
/* Wrap the block with protect_cleanup_actions as the action. */
- x = gimple_build_eh_must_not_throw (protect_cleanup_actions);
- x = gimple_build_try (finally, gimple_seq_alloc_with_stmt (x),
- GIMPLE_TRY_CATCH);
- finally = lower_eh_must_not_throw (outer_state, x);
+ eh_mnt = gimple_build_eh_must_not_throw (protect_cleanup_actions);
+ try_stmt = gimple_build_try (finally, gimple_seq_alloc_with_stmt (eh_mnt),
+ GIMPLE_TRY_CATCH);
+ finally = lower_eh_must_not_throw (outer_state, try_stmt);
/* Drop all of this into the exception sequence. */
emit_post_landing_pad (&eh_seq, tf->region);
@@ -1640,7 +1643,7 @@ cleanup_is_dead_in (eh_region reg)
arrange for the FINALLY block to be executed on all exits. */
static gimple_seq
-lower_try_finally (struct leh_state *state, gimple tp)
+lower_try_finally (struct leh_state *state, gimple_try tp)
{
struct leh_tf_state this_tf;
struct leh_state this_state;
@@ -1747,7 +1750,7 @@ lower_try_finally (struct leh_state *state, gimple tp)
exception region trees that records all the magic. */
static gimple_seq
-lower_catch (struct leh_state *state, gimple tp)
+lower_catch (struct leh_state *state, gimple_try tp)
{
eh_region try_region = NULL;
struct leh_state this_state = *state;
@@ -1819,7 +1822,7 @@ lower_catch (struct leh_state *state, gimple tp)
region trees that record all the magic. */
static gimple_seq
-lower_eh_filter (struct leh_state *state, gimple tp)
+lower_eh_filter (struct leh_state *state, gimple_try tp)
{
struct leh_state this_state = *state;
eh_region this_region = NULL;
@@ -1864,7 +1867,7 @@ lower_eh_filter (struct leh_state *state, gimple tp)
plus the exception region trees that record all the magic. */
static gimple_seq
-lower_eh_must_not_throw (struct leh_state *state, gimple tp)
+lower_eh_must_not_throw (struct leh_state *state, gimple_try tp)
{
struct leh_state this_state = *state;
@@ -1897,7 +1900,7 @@ lower_eh_must_not_throw (struct leh_state *state, gimple tp)
except that we only execute the cleanup block for exception edges. */
static gimple_seq
-lower_cleanup (struct leh_state *state, gimple tp)
+lower_cleanup (struct leh_state *state, gimple_try tp)
{
struct leh_state this_state = *state;
eh_region this_region = NULL;
@@ -2052,36 +2055,39 @@ lower_eh_constructs_2 (struct leh_state *state, gimple_stmt_iterator *gsi)
break;
case GIMPLE_TRY:
- if (gimple_try_kind (stmt) == GIMPLE_TRY_FINALLY)
- replace = lower_try_finally (state, stmt);
- else
- {
- x = gimple_seq_first_stmt (gimple_try_cleanup (stmt));
- if (!x)
- {
- replace = gimple_try_eval (stmt);
- lower_eh_constructs_1 (state, &replace);
- }
- else
- switch (gimple_code (x))
+ {
+ gimple_try try_stmt = as_a <gimple_try> (stmt);
+ if (gimple_try_kind (try_stmt) == GIMPLE_TRY_FINALLY)
+ replace = lower_try_finally (state, try_stmt);
+ else
+ {
+ x = gimple_seq_first_stmt (gimple_try_cleanup (try_stmt));
+ if (!x)
{
+ replace = gimple_try_eval (try_stmt);
+ lower_eh_constructs_1 (state, &replace);
+ }
+ else
+ switch (gimple_code (x))
+ {
case GIMPLE_CATCH:
- replace = lower_catch (state, stmt);
- break;
+ replace = lower_catch (state, try_stmt);
+ break;
case GIMPLE_EH_FILTER:
- replace = lower_eh_filter (state, stmt);
- break;
+ replace = lower_eh_filter (state, try_stmt);
+ break;
case GIMPLE_EH_MUST_NOT_THROW:
- replace = lower_eh_must_not_throw (state, stmt);
- break;
+ replace = lower_eh_must_not_throw (state, try_stmt);
+ break;
case GIMPLE_EH_ELSE:
- /* This code is only valid with GIMPLE_TRY_FINALLY. */
- gcc_unreachable ();
+ /* This code is only valid with GIMPLE_TRY_FINALLY. */
+ gcc_unreachable ();
default:
- replace = lower_cleanup (state, stmt);
- break;
- }
- }
+ replace = lower_cleanup (state, try_stmt);
+ break;
+ }
+ }
+ }
/* Remove the old stmt and insert the transformed sequence
instead. */
This corresponds to: [PATCH 32/89] Introduce gimple_try https://gcc.gnu.org/ml/gcc-patches/2014-04/msg01214.html from the original 89-patch kit That earlier patch was approved by Jeff: > OK once const and associated renaming stuff is fixed. in https://gcc.gnu.org/ml/gcc-patches/2014-05/msg00636.html gcc/ * coretypes.h (gimple_try): New typedef. (const_gimple_try): New typedef. * gimple-low.c (gimple_try_catch_may_fallthru): Require a gimple_try rather than a plain gimple. (gimple_stmt_may_fallthru): Add checked cast to gimple_try. * gimple-pretty-print.c (dump_gimple_try): Require a gimple_try rather than a plain gimple. (pp_gimple_stmt_1): Add checked cast to gimple_try within GIMPLE_TRY case of switch statement. * tree-eh.c (finally_tree_node::parent): Strengthen field from gimple to gimple_try. (record_in_finally_tree): Require a gimple_try rather than a plain gimple. (collect_finally_tree): Likewise. (collect_finally_tree_1): Likewise. (struct leh_tf_state::try_finally_expr): Strengthen field from gimple to gimple_try. (struct leh_tf_state::top_p): Likewise. (lower_eh_must_not_throw): Require a gimple_try rather than a plain gimple. (frob_into_branch_around): Likewise. (lower_try_finally_dup_block): Strengthen local from gimple to gimple_try. (honor_protect_cleanup_actions): Split out uses of "x" into new locals "eh_mnt" and "try_stmt" with stronger types. (lower_try_finally): Require a gimple_try rather than a plain gimple. (lower_catch): Likewise. (lower_eh_filter): Likewise. (lower_eh_must_not_throw): Likewise. (lower_cleanup): Likewise. (lower_eh_constructs_2): Add checked cast to gimple_try within GIMPLE_TRY case of switch statement, introducing new local "try_stmt", using it for type-safety. --- gcc/ChangeLog.gimple-classes | 42 ++++++++++++++++++++ gcc/coretypes.h | 4 ++ gcc/gimple-low.c | 4 +- gcc/gimple-pretty-print.c | 4 +- gcc/tree-eh.c | 94 +++++++++++++++++++++++--------------------- 5 files changed, 100 insertions(+), 48 deletions(-)