On 12/2/21 11:02, Martin Liška wrote:
On 12/2/21 15:27, Andrew MacLeod wrote:
ranger->gori().outgoing_edge_range_p (irange &r, edge e, tree name,
*get_global_range_query ());
Thank you! It works for me!
Martin
btw, this applies to names not on the stmt as well. The function
returns TRUE if there is an outgoing range calculable, and false if
not. so:
a = b + 20
if (a > 40) <- returns TRUE for outgoing range of 'a' or 'b'
{
c = foo()
if (c > 60) <- returns false for 'a' or 'b'
{
if (b < 100) <- Also returns TRUE for 'a' or 'b'
The final block, from the EVRP dump:
<bb 4> :
if (b_4(D) <= 99)
goto <bb 5>; [INV]
else
goto <bb 6>; [INV]
4->5 (T) b_4(D) : unsigned int [21, 99]
4->5 (T) a_5 : unsigned int [41, 119]
4->6 (F) b_4(D) : unsigned int [100, 4294967275]
4->6 (F) a_5 : unsigned int [120, +INF]
Shows that it has a range for both 'a' and 'b'.
Just to point out that you can use this query on any conditional edge,
even if it isnt directly mentioned on the stmt. so if you are keying of
'a', you could simply ask if outgoing_edge_range_p ( , a,...) rather
than parsing the condition to see if 'a' is on it. if there is no
chance that 'a' is affected by the block, is just returns false.
When its called directly like this, it picks up no ranges from outside
the basic block you are querying, except via that range query you
provide. The listing shows the defaultwhic is whatever ranger knows.
So if you provided get_global_range_query, those ranges would instead be
something like:
4->5 (T) b_4(D) : unsigned int [0, 99]
4->5 (T) a_5 : unsigned int [21, 119]
4->6 (F) b_4(D) : unsigned int [100, +INF]
4->6 (F) a_5 : unsigned int [0,20] [120, +INF-20 ]
It may simplify things a little if you are unswitching on 'a', you can
just ask each block with a condition whether 'a's range can be modified....
Andrew.