Commit e5df270e by Alexander Monakov Committed by Alexander Monakov

domwalk: optimize basic block sorting

	* domwalk.c (cmp_bb_postorder): Simplify.
	(sort_bbs_postorder): New function.  Use it...
	(dom_walker::walk): ...here to optimize common cases.

From-SVN: r250502
parent 4287b4e8
2017-07-25 Alexander Monakov <amonakov@ispras.ru>
* domwalk.c (cmp_bb_postorder): Simplify.
(sort_bbs_postorder): New function. Use it...
(dom_walker::walk): ...here to optimize common cases.
2017-07-25 Martin Liska <mliska@suse.cz> 2017-07-25 Martin Liska <mliska@suse.cz>
PR ipa/81520 PR ipa/81520
......
...@@ -128,19 +128,45 @@ along with GCC; see the file COPYING3. If not see ...@@ -128,19 +128,45 @@ along with GCC; see the file COPYING3. If not see
which is currently an abstraction over walking tree statements. Thus which is currently an abstraction over walking tree statements. Thus
the dominator walker is currently only useful for trees. */ the dominator walker is currently only useful for trees. */
/* Reverse postorder index of each basic block. */
static int *bb_postorder; static int *bb_postorder;
static int static int
cmp_bb_postorder (const void *a, const void *b) cmp_bb_postorder (const void *a, const void *b)
{ {
basic_block bb1 = *(basic_block *)const_cast<void *>(a); basic_block bb1 = *(const basic_block *)(a);
basic_block bb2 = *(basic_block *)const_cast<void *>(b); basic_block bb2 = *(const basic_block *)(b);
if (bb1->index == bb2->index)
return 0;
/* Place higher completion number first (pop off lower number first). */ /* Place higher completion number first (pop off lower number first). */
if (bb_postorder[bb1->index] > bb_postorder[bb2->index]) return bb_postorder[bb2->index] - bb_postorder[bb1->index];
return -1; }
return 1;
/* Permute array BBS of N basic blocks in postorder,
i.e. by descending number in BB_POSTORDER array. */
static void
sort_bbs_postorder (basic_block *bbs, int n)
{
if (__builtin_expect (n == 2, true))
{
basic_block bb0 = bbs[0], bb1 = bbs[1];
if (bb_postorder[bb0->index] < bb_postorder[bb1->index])
bbs[0] = bb1, bbs[1] = bb0;
}
else if (__builtin_expect (n == 3, true))
{
basic_block bb0 = bbs[0], bb1 = bbs[1], bb2 = bbs[2];
if (bb_postorder[bb0->index] < bb_postorder[bb1->index])
std::swap (bb0, bb1);
if (bb_postorder[bb1->index] < bb_postorder[bb2->index])
{
std::swap (bb1, bb2);
if (bb_postorder[bb0->index] < bb_postorder[bb1->index])
std::swap (bb0, bb1);
}
bbs[0] = bb0, bbs[1] = bb1, bbs[2] = bb2;
}
else
qsort (bbs, n, sizeof *bbs, cmp_bb_postorder);
} }
/* Constructor for a dom walker. /* Constructor for a dom walker.
...@@ -284,16 +310,8 @@ dom_walker::walk (basic_block bb) ...@@ -284,16 +310,8 @@ dom_walker::walk (basic_block bb)
for (dest = first_dom_son (m_dom_direction, bb); for (dest = first_dom_son (m_dom_direction, bb);
dest; dest = next_dom_son (m_dom_direction, dest)) dest; dest = next_dom_son (m_dom_direction, dest))
worklist[sp++] = dest; worklist[sp++] = dest;
if (m_dom_direction == CDI_DOMINATORS) if (sp - saved_sp > 1 && m_dom_direction == CDI_DOMINATORS)
switch (sp - saved_sp) sort_bbs_postorder (&worklist[saved_sp], sp - saved_sp);
{
case 0:
case 1:
break;
default:
qsort (&worklist[saved_sp], sp - saved_sp,
sizeof (basic_block), cmp_bb_postorder);
}
} }
/* NULL is used to mark pop operations in the recursion stack. */ /* NULL is used to mark pop operations in the recursion stack. */
while (sp > 0 && !worklist[sp - 1]) while (sp > 0 && !worklist[sp - 1])
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment