Skip to content
GitLab
Menu
Projects
Groups
Snippets
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Sign in
Toggle navigation
Menu
Open sidebar
Zwinkau
libfirm
Commits
94b02881
Commit
94b02881
authored
Mar 14, 2006
by
Daniel Grund
Browse files
Added star constraints with all needed helpers
parent
50361736
Changes
3
Hide whitespace changes
Inline
Side-by-side
ir/be/becopyilp2.c
View file @
94b02881
...
...
@@ -173,10 +173,176 @@ static void build_affinity_cstr(ilp_env_t *ienv) {
}
/**
*
* Helping stuff for build_clique_star_cstr
*/
typedef
struct
_edge_t
{
ir_node
*
n1
,
*
n2
;
}
edge_t
;
static
int
compare_edge_t
(
const
void
*
k1
,
const
void
*
k2
,
size_t
size
)
{
const
edge_t
*
e1
=
k1
;
const
edge_t
*
e2
=
k2
;
return
!
(
e1
->
n1
==
e2
->
n1
&&
e1
->
n2
==
e2
->
n2
);
}
#define HASH_EDGE(e) (HASH_PTR((e)->n1) ^ HASH_PTR((e)->n2))
static
INLINE
edge_t
*
add_edge
(
set
*
edges
,
ir_node
*
n1
,
ir_node
*
n2
,
int
*
counter
)
{
edge_t
new_edge
;
if
(
PTR_TO_INT
(
n1
)
<
PTR_TO_INT
(
n2
))
{
new_edge
.
n1
=
n1
;
new_edge
.
n2
=
n2
;
}
else
{
new_edge
.
n1
=
n2
;
new_edge
.
n2
=
n1
;
}
*
counter
++
;
return
set_insert
(
edges
,
&
new_edge
,
sizeof
(
new_edge
),
HASH_EDGE
(
&
new_edge
));
}
static
INLINE
edge_t
*
find_edge
(
set
*
edges
,
ir_node
*
n1
,
ir_node
*
n2
)
{
edge_t
new_edge
;
if
(
PTR_TO_INT
(
n1
)
<
PTR_TO_INT
(
n2
))
{
new_edge
.
n1
=
n1
;
new_edge
.
n2
=
n2
;
}
else
{
new_edge
.
n1
=
n2
;
new_edge
.
n2
=
n1
;
}
return
set_find
(
edges
,
&
new_edge
,
sizeof
(
new_edge
),
HASH_EDGE
(
&
new_edge
));
}
static
INLINE
void
remove_edge
(
set
*
edges
,
ir_node
*
n1
,
ir_node
*
n2
,
int
*
counter
)
{
edge_t
new_edge
,
*
e
;
if
(
PTR_TO_INT
(
n1
)
<
PTR_TO_INT
(
n2
))
{
new_edge
.
n1
=
n1
;
new_edge
.
n2
=
n2
;
}
else
{
new_edge
.
n1
=
n2
;
new_edge
.
n2
=
n1
;
}
e
=
set_find
(
edges
,
&
new_edge
,
sizeof
(
new_edge
),
HASH_EDGE
(
&
new_edge
));
if
(
e
)
{
e
->
n1
=
NULL
;
e
->
n2
=
NULL
;
*
counter
--
;
}
}
#define pset_foreach(pset, irn) for(irn=pset_first(pset); irn; irn=pset_next(pset))
/**
* Search for an interference clique and an external node
* with affinity edges to all nodes of the clique.
* At most 1 node of the clique can be colored equally with the external node.
*/
static
void
build_clique_star_cstr
(
ilp_env_t
*
ienv
)
{
node_t
*
node
;
/* for each node with affinity edges */
co_gs_foreach_node
(
ienv
->
co
,
node
)
{
struct
obstack
ob
;
neighb_t
*
nbr
;
ir_node
*
center
=
node
->
irn
;
ir_node
**
nodes
;
set
*
edges
;
int
i
,
o
,
n_nodes
,
n_edges
;
obstack_init
(
&
ob
);
edges
=
new_set
(
compare_edge_t
,
8
);
/* get all affinity neighbours */
n_nodes
=
0
;
co_gs_foreach_neighb
(
node
,
nbr
)
{
obstack_ptr_grow
(
&
ob
,
nbr
->
irn
);
++
n_nodes
;
}
nodes
=
obstack_finish
(
&
ob
);
/* get all interference edges between these */
n_edges
=
0
;
for
(
i
=
0
;
i
<
n_nodes
;
++
i
)
for
(
o
=
0
;
o
<
i
;
++
o
)
if
(
be_ifg_connected
(
ienv
->
co
->
cenv
->
ifg
,
nodes
[
i
],
nodes
[
o
]))
add_edge
(
edges
,
nodes
[
i
],
nodes
[
o
],
&
n_edges
);
/* cover all these interference edges with maximal cliques */
while
(
n_edges
)
{
edge_t
*
e
;
pset
*
clique
=
pset_new_ptr
(
8
);
int
growed
;
/* get 2 starting nodes to form a clique */
for
(
e
=
set_first
(
edges
);
!
e
->
n1
;
e
=
set_next
(
edges
))
/*nothing*/
;
remove_edge
(
edges
,
e
->
n1
,
e
->
n2
,
&
n_edges
);
pset_insert_ptr
(
clique
,
e
->
n1
);
pset_insert_ptr
(
clique
,
e
->
n2
);
/* while the clique is growing */
do
{
growed
=
0
;
/* search for a candidate to extend the clique */
for
(
i
=
0
;
i
<
n_nodes
;
++
i
)
{
ir_node
*
member
,
*
cand
=
nodes
[
i
];
int
is_cand
;
/* if its already in the clique try the next */
if
(
pset_find_ptr
(
clique
,
cand
))
continue
;
/* are there all necessary interferences? */
is_cand
=
1
;
pset_foreach
(
clique
,
member
)
{
if
(
!
find_edge
(
edges
,
cand
,
member
))
{
is_cand
=
0
;
pset_break
(
clique
);
break
;
}
}
/* now we know if we have a clique extender */
if
(
is_cand
)
{
/* first remove all covered edges */
pset_foreach
(
clique
,
member
)
remove_edge
(
edges
,
cand
,
member
,
&
n_edges
);
/* insert into clique */
pset_insert_ptr
(
clique
,
cand
);
growed
=
1
;
break
;
}
}
}
while
(
growed
);
/* now the clique is maximal. Finally add the constraint */
{
ir_node
*
member
;
int
var_idx
,
cst_idx
,
center_nr
,
member_nr
;
char
buf
[
16
];
cst_idx
=
lpp_add_cst
(
ienv
->
lp
,
NULL
,
lpp_greater
,
pset_count
(
clique
)
-
1
);
center_nr
=
get_irn_node_nr
(
center
);
pset_foreach
(
clique
,
member
)
{
member_nr
=
get_irn_node_nr
(
member
);
var_idx
=
lpp_get_var_idx
(
ienv
->
lp
,
name_cdd_sorted
(
buf
,
'y'
,
center_nr
,
member_nr
));
lpp_set_factor_fast
(
ienv
->
lp
,
cst_idx
,
var_idx
,
1
.
0
);
}
}
del_pset
(
clique
);
}
del_set
(
edges
);
obstack_free
(
&
ob
,
NULL
);
}
}
/**
...
...
ir/be/becopyopt.c
View file @
94b02881
...
...
@@ -506,8 +506,12 @@ void co_free_graph_structure(copy_opt_t *co) {
/* co_solve_ilp1() co_solve_ilp2() are implemented in becopyilpX.c */
int
co_gs_is_optimizable
(
copy_opt_t
*
co
,
ir_node
*
irn
)
{
node_t
new_node
;
node_t
new_node
,
*
n
;
new_node
.
irn
=
irn
;
return
(
int
)
set_find
(
co
->
nodes
,
new_node
.
irn
,
sizeof
(
new_node
),
HASH_PTR
(
new_node
.
irn
));
new_node
.
irn
=
irn
;
n
=
set_find
(
co
->
nodes
,
new_node
.
irn
,
sizeof
(
new_node
),
HASH_PTR
(
new_node
.
irn
));
if
(
n
)
{
return
(
n
->
count
>
0
);
}
else
return
0
;
}
ir/be/becopyopt_t.h
View file @
94b02881
...
...
@@ -69,13 +69,13 @@ struct _copy_opt_t {
typedef
struct
_unit_t
{
struct
list_head
units
;
/**< chain for all units */
copy_opt_t
*
co
;
/**< the copy
_
opt this unit belongs to */
copy_opt_t
*
co
;
/**< the copy
opt this unit belongs to */
int
node_count
;
/**< size of the nodes array */
ir_node
**
nodes
;
/**< [0] is the root-node, others are non interfering args of it. */
int
*
costs
;
/**< costs[i] are incurred, if nodes[i] has a different color */
int
inevitable_costs
;
/**< sum of costs of all args interfering with root */
int
all_nodes_costs
;
/**< sum of all costs[i] */
int
min_nodes_costs
;
/**< a lower bound for the costs in costs[], determined by a max indep
.
set */
int
min_nodes_costs
;
/**< a lower bound for the costs in costs[], determined by a max indep
endent
set */
int
sort_key
;
/**< maximum costs. controls the order of ou's in the struct list_head units. */
/* for heuristic */
...
...
@@ -96,6 +96,8 @@ typedef struct _unit_t {
******************************************************************************/
typedef
struct
_neighb_t
neighb_t
;
typedef
struct
_node_t
node_t
;
struct
_neighb_t
{
neighb_t
*
next
;
/** the next neighbour entry*/
...
...
@@ -103,11 +105,17 @@ struct _neighb_t {
int
costs
;
/** the costs of the edge (node_t->irn, neighb_t->irn) */
};
typedef
struct
_node_t
{
struct
_node_t
{
ir_node
*
irn
;
/** a node with affinity edges */
int
count
;
/** number of affinity edges in the linked list below */
neighb_t
*
neighbours
;
/** a linked list of all affinity neighbours */
}
node_t
;
};
#define co_gs_nodes_begin(co) set_first((co)->nodes)
#define co_gs_nodes_next(co) set_next((co)->nodes)
#define co_gs_nodes_break(co) set_break((co)->nodes)
#define co_gs_foreach_node(co, node) for (node = co_gs_nodes_begin(co); node; node = co_gs_nodes_next(co))
#define co_gs_foreach_neighb(node, neighb) for (neighb = node->neighbours; neighb; neighb = neighb->next)
#endif
Write
Preview
Supports
Markdown
0%
Try again
or
attach a new file
.
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment