This is the mail archive of the
mailing list for the GCC project.
Re: On-Demand range technology [2/5] - Major Components : How it works
- From: Marc Glisse <marc dot glisse at inria dot fr>
- To: Martin Sebor <msebor at gmail dot com>
- Cc: Andrew MacLeod <amacleod at redhat dot com>, Richard Biener <richard dot guenther at gmail dot com>, GCC <gcc at gcc dot gnu dot org>, Jeff Law <law at redhat dot com>, Aldy Hernandez <aldyh at redhat dot com>
- Date: Tue, 4 Jun 2019 22:21:25 +0200 (CEST)
- Subject: Re: On-Demand range technology [2/5] - Major Components : How it works
- References: <email@example.com> <CAFiYyc2a_h7AVa44G+wrAic=op+qbaGgLHbb+d8wGc3bFZdDaQ@mail.gmail.com> <firstname.lastname@example.org> <CAFiYyc3AGjzJpYJR4FFrN-J1yfa++aQ_9MJYiiZhJ4MS4Nw2qw@mail.gmail.com> <email@example.com> <CAFiYyc2Qvk2NJ0Akwakm8CEUz0ZdOFc4BbK1_xdQYpvdej=hgA@mail.gmail.com> <firstname.lastname@example.org> <email@example.com>
- Reply-to: gcc at gcc dot gnu dot org
On Tue, 4 Jun 2019, Martin Sebor wrote:
On 5/31/19 9:40 AM, Andrew MacLeod wrote:
On 5/29/19 7:15 AM, Richard Biener wrote:
On Tue, May 28, 2019 at 4:17 PM Andrew MacLeod <firstname.lastname@example.org>
On 5/27/19 9:02 AM, Richard Biener wrote:
On Fri, May 24, 2019 at 5:50 PM Andrew MacLeod <email@example.com>
The above suggests that iff this is done at all it is not in GORI
those are not conditional stmts or ranges from feeding those. The
machinery doing the use-def walking from stmt context also cannot
come along these so I have the suspicion that Ranger cannot handle
telling us that for the stmt following above, for example
if (_5 != 0)
that _5 is not zero?
Can you clarify?
So there are 2 aspects to this. the range-ops code for DIV_EXPR, if
asked for the range of op2 () would return ~[0,0] for _5.
But you are also correct in that the walk backwards would not find
This is similar functionality to how null_derefs are currently handled,
and in fact could probably be done simultaneously using the same code
base. I didn't bring null derefs up, but this is a good time :-)
There is a separate class used by the gori-cache which tracks the
non-nullness property at the block level. It has a single API:
non_null_deref_p (name, bb) which determines whether the is a
dereference in any BB for NAME, which indicates whether the range has
implicit ~[0,0] range in that basic block or not.
So when we then have
_1 = *_2; // after this _2 is non-NULL
_3 = _1 + 1; // _3 is non-NULL
_4 = *_3;
when a on-demand user asks whether _3 is non-NULL at the
point of _4 = *_3 we don't have this information? Since the
per-BB caching will only say _1 is non-NULL after the BB.
I'm also not sure whether _3 ever gets non-NULL during
non-NULL processing of the block since walking immediate uses
doesn't really help here?
presumably _3 is globally non-null due to the definition being (pointer
+ x) ... ie, _3 has a global range o f ~[0,0] ?
No, _3 is ~[0, 0] because it is derived from _1 which is ~[0, 0] and
you cannot arrive at NULL by pointer arithmetic from a non-NULL pointer.
_1 was loaded from _2 (thus asserting _2 is non-NULL). but we have no idea
what the range of _1 is, so how do you assert _1 is [~0,0] ?
The only way I see to determine _3 is non-NULL is through the _4 = *_3
In the first two statements from the above (where _1 is a pointer):
_1 = *_2;
_3 = _1 + 1;
_1 must be non-null because C/C++ define pointer addition only for
non-null pointers, and therefore so must _3.
(int*)0+0 is well-defined, so this uses the fact that 1 is non-null. This
is all well done in extract_range_from_binary_expr already, although it
seems to miss the (dangerous) optimization NULL + unknown == NULL.
Just in case, a quote:
"When an expression J that has integral type is added to or subtracted
from an expression P of pointer type, the result has the type of P.
(4.1) — If P evaluates to a null pointer value and J evaluates to 0, the
result is a null pointer value.
(4.2) — Otherwise, if P points to element x[i] of an array object x with
n elements, 80 the expressions P + J and J + P (where J has the value j)
point to the (possibly-hypothetical) element x[i + j] if 0 ≤ i + j ≤ n
and the expression P - J points to the (possibly-hypothetical) element
x[i − j] if 0 ≤ i − j ≤ n.
(4.3) — Otherwise, the behavior is undefined"
Or does the middle-end allow arithmetic on null pointers?
When people use -fno-delete-null-pointer-checks because their (embedded)
platform has important stuff at address 0, they also want to be able to do