- introduce an "end-block" to the absgraph, so the irg_end_block is known in a
authorMatthias Braun <matze@braunis.de>
Thu, 4 Oct 2007 19:18:05 +0000 (19:18 +0000)
committerMatthias Braun <matze@braunis.de>
Thu, 4 Oct 2007 19:18:05 +0000 (19:18 +0000)
  dfs even if the program contains just an endless loop

[r16090]

include/libfirm/absgraph.h
ir/ana/absgraph.c
ir/ana/dfs.c
ir/ana/irlivechk.c

index 9b6a7d2..613cb9c 100644 (file)
@@ -38,6 +38,7 @@
 typedef struct _absgraph_t {
        void *(*get_root)(void *self);
        void (*grow_succs)(void *self, void *node, struct obstack *obst);
+       void *(*get_end)(void *self);
 } absgraph_t;
 
 extern const absgraph_t absgraph_irg_cfg_succ;
index 1d483e2..bc2c97f 100644 (file)
@@ -41,6 +41,12 @@ static void *irg_cfg_succ_get_root(void *self)
        return get_irg_start_block(irg);
 }
 
+static void *irg_cfg_succ_get_end(void *self)
+{
+       ir_graph *irg = self;
+       return get_irg_end_block(irg);
+}
+
 static void irg_cfg_succ_grow_succs(void *self, void *node, struct obstack *obst)
 {
        ir_node *bl = node;
@@ -54,12 +60,18 @@ static void irg_cfg_succ_grow_succs(void *self, void *node, struct obstack *obst
 
 const absgraph_t absgraph_irg_cfg_succ = {
        irg_cfg_succ_get_root,
-       irg_cfg_succ_grow_succs
+       irg_cfg_succ_grow_succs,
+       irg_cfg_succ_get_end
 };
 
 static void *irg_cfg_pred_get_root(void *self)
 {
-       return get_irg_end_block(self);
+       return get_irg_end_block((ir_graph*) self);
+}
+
+static void *irg_cfg_pred_get_end(void *self)
+{
+       return get_irg_start_block((ir_graph*) self);
 }
 
 static void irg_cfg_pred_grow_succs(void *self, void *node, struct obstack *obst)
@@ -74,5 +86,6 @@ static void irg_cfg_pred_grow_succs(void *self, void *node, struct obstack *obst
 
 const absgraph_t absgraph_irg_cfg_pred = {
        irg_cfg_pred_get_root,
-       irg_cfg_pred_grow_succs
+       irg_cfg_pred_grow_succs,
+       irg_cfg_pred_get_end
 };
index a85064a..ca080d4 100644 (file)
 #include "statev.h"
 #include "dfs_t.h"
 
-static const char *edge_names[] = {
-       "anc",
-       "fwd",
-       "cross",
-       "back"
-};
-
 static int cmp_edge(const void *a, const void *b, size_t sz)
 {
        const dfs_edge_t *p = a;
@@ -182,11 +175,28 @@ dfs_t *dfs_new(const absgraph_t *graph_impl, void *graph_self)
        obstack_init(&res->obst);
 
        dfs_perform(res, graph_impl->get_root(graph_self), NULL, 0);
+
+       /* make sure the end node (which might not be accessible) has a number */
+       node = get_node(res, graph_impl->get_end(graph_self));
+       if (!node->visited) {
+               node->visited     = 1;
+               node->node        = graph_impl->get_end(graph_self);
+               node->ancestor    = NULL;
+               node->pre_num     = res->pre_num++;
+               node->post_num    = res->post_num++;
+               node->max_pre_num = node->pre_num;
+               node->level       = 0;
+       }
+
        classify_edges(res);
 
+       assert(res->pre_num == res->post_num);
        res->pre_order = xmalloc(res->pre_num * sizeof(res->pre_order));
-       res->post_order = xmalloc(res->pre_num * sizeof(res->post_order));
+       res->post_order = xmalloc(res->post_num * sizeof(res->post_order));
        foreach_set (res->nodes, node) {
+               assert(node->pre_num < res->pre_num);
+               assert(node->post_num < res->post_num);
+
                res->pre_order[node->pre_num] = node;
                res->post_order[node->post_num] = node;
        }
index 4aa00d8..2d6e91a 100644 (file)
@@ -247,6 +247,10 @@ lv_chk_t *lv_chk_new(ir_graph *irg, const dfs_t *dfs)
        struct obstack *obst;
        int i;
 
+       edges_deactivate(irg);
+       edges_activate(irg);
+       compute_doms(irg);
+
        stat_ev_tim_push();
        phase_init(&res->ph, "liveness check", irg, PHASE_DEFAULT_GROWTH, init_block_data, NULL);
        obst = phase_obst(&res->ph);
@@ -258,6 +262,7 @@ lv_chk_t *lv_chk_new(ir_graph *irg, const dfs_t *dfs)
        res->back_edge_src = bitset_obstack_alloc(obst, res->n_blocks);
        res->back_edge_tgt = bitset_obstack_alloc(obst, res->n_blocks);
        res->map           = obstack_alloc(obst, res->n_blocks * sizeof(res->map[0]));
+       memset(res->map, 0, res->n_blocks * sizeof(res->map[0]));
 
 #if 0
        {
@@ -276,6 +281,8 @@ lv_chk_t *lv_chk_new(ir_graph *irg, const dfs_t *dfs)
        for (i = res->n_blocks - 1; i >= 0; --i) {
                ir_node *irn  = (ir_node *) dfs_get_pre_num_node(res->dfs, i);
                bl_info_t *bi = phase_get_or_set_irn_data(&res->ph, irn);
+               assert(bi->id < res->n_blocks);
+               assert(res->map[bi->id] == NULL);
                res->map[bi->id] = bi;
        }