public inbox for gcc-bugs@sourceware.org
help / color / mirror / Atom feed
* [Bug c/22485] New: pointer +- integer is never NULL
@ 2005-07-14 13:10 mattias at virtutech dot se
  2005-07-14 13:14 ` [Bug c/22485] " mattias at virtutech dot se
                   ` (21 more replies)
  0 siblings, 22 replies; 25+ messages in thread
From: mattias at virtutech dot se @ 2005-07-14 13:10 UTC (permalink / raw)
  To: gcc-bugs

The code

void stuff(void);
void f(int *p, int x)
{
        int *q = p + x;
        if (!q)
                stuff();
}

should never call stuff() - the test is unnecessary since pointer +/- integer is
undefined when the pointer does not point to an object or just past the end of
one (6.5.6 paragraph 8). This is important in cases such as:

static inline struct foo *lookup(struct foo *table, int x)
{
    if (match(table, x))
        return table + x;
    else
        return NULL;
}
...
    struct foo *e = lookup(tbl, x);
    if (e) ...

The code that calls the above function ends up checking for NULL twice: once
inside the (inlined) function, and one after the call. Were Q = P +- I
recognised as implying that P != NULL, Q != NULL (as we are allowed to do
according to the Standard), then the extraneous NULL test could be eliminated.

-- 
           Summary: pointer +- integer is never NULL
           Product: gcc
           Version: unknown
            Status: UNCONFIRMED
          Severity: enhancement
          Priority: P2
         Component: c
        AssignedTo: unassigned at gcc dot gnu dot org
        ReportedBy: mattias at virtutech dot se
                CC: gcc-bugs at gcc dot gnu dot org


http://gcc.gnu.org/bugzilla/show_bug.cgi?id=22485


^ permalink raw reply	[flat|nested] 25+ messages in thread

* [Bug c/22485] pointer +- integer is never NULL
  2005-07-14 13:10 [Bug c/22485] New: pointer +- integer is never NULL mattias at virtutech dot se
  2005-07-14 13:14 ` [Bug c/22485] " mattias at virtutech dot se
@ 2005-07-14 13:14 ` pinskia at gcc dot gnu dot org
  2005-07-14 13:19 ` falk at debian dot org
                   ` (19 subsequent siblings)
  21 siblings, 0 replies; 25+ messages in thread
From: pinskia at gcc dot gnu dot org @ 2005-07-14 13:14 UTC (permalink / raw)
  To: gcc-bugs


------- Additional Comments From pinskia at gcc dot gnu dot org  2005-07-14 13:14 -------
This is invalid and here is why, if both p and x are NULL/0, then p+x will always be NULL so in this is 
invalid optimization.

-- 
           What    |Removed                     |Added
----------------------------------------------------------------------------
             Status|UNCONFIRMED                 |RESOLVED
         Resolution|                            |INVALID


http://gcc.gnu.org/bugzilla/show_bug.cgi?id=22485


^ permalink raw reply	[flat|nested] 25+ messages in thread

* [Bug c/22485] pointer +- integer is never NULL
  2005-07-14 13:10 [Bug c/22485] New: pointer +- integer is never NULL mattias at virtutech dot se
@ 2005-07-14 13:14 ` mattias at virtutech dot se
  2005-07-14 13:14 ` pinskia at gcc dot gnu dot org
                   ` (20 subsequent siblings)
  21 siblings, 0 replies; 25+ messages in thread
From: mattias at virtutech dot se @ 2005-07-14 13:14 UTC (permalink / raw)
  To: gcc-bugs


------- Additional Comments From mattias at virtutech dot se  2005-07-14 13:13 -------
I forgot to state the version (4.0.0), but I have not seen any gcc version
optimising this case.


-- 
           What    |Removed                     |Added
----------------------------------------------------------------------------
            Version|unknown                     |4.0.0


http://gcc.gnu.org/bugzilla/show_bug.cgi?id=22485


^ permalink raw reply	[flat|nested] 25+ messages in thread

* [Bug c/22485] pointer +- integer is never NULL
  2005-07-14 13:10 [Bug c/22485] New: pointer +- integer is never NULL mattias at virtutech dot se
  2005-07-14 13:14 ` [Bug c/22485] " mattias at virtutech dot se
  2005-07-14 13:14 ` pinskia at gcc dot gnu dot org
@ 2005-07-14 13:19 ` falk at debian dot org
  2005-07-14 13:45 ` dberlin at gcc dot gnu dot org
                   ` (18 subsequent siblings)
  21 siblings, 0 replies; 25+ messages in thread
From: falk at debian dot org @ 2005-07-14 13:19 UTC (permalink / raw)
  To: gcc-bugs


------- Additional Comments From falk at debian dot org  2005-07-14 13:19 -------
(In reply to comment #2)
> This is invalid and here is why, if both p and x are NULL/0, then p+x will
always be NULL so in this is 
> invalid optimization.

Huh? nullpointer + 0 is undefined, it doesn't matter what happens in that
case. Reopening.

-- 
           What    |Removed                     |Added
----------------------------------------------------------------------------
             Status|RESOLVED                    |UNCONFIRMED
         Resolution|INVALID                     |


http://gcc.gnu.org/bugzilla/show_bug.cgi?id=22485


^ permalink raw reply	[flat|nested] 25+ messages in thread

* [Bug c/22485] pointer +- integer is never NULL
  2005-07-14 13:10 [Bug c/22485] New: pointer +- integer is never NULL mattias at virtutech dot se
                   ` (2 preceding siblings ...)
  2005-07-14 13:19 ` falk at debian dot org
@ 2005-07-14 13:45 ` dberlin at gcc dot gnu dot org
  2005-07-14 13:46 ` falk at debian dot org
                   ` (17 subsequent siblings)
  21 siblings, 0 replies; 25+ messages in thread
From: dberlin at gcc dot gnu dot org @ 2005-07-14 13:45 UTC (permalink / raw)
  To: gcc-bugs


------- Additional Comments From dberlin at gcc dot gnu dot org  2005-07-14 13:38 -------
Hmmmm.
I swear we just had this discussion for VRP purposes, and that a bug was
recently fixed so that we don't assume that pointer + - integer is NULL. 

But if it's really undefined, maybe we should optimize it.
Diego?

-- 
           What    |Removed                     |Added
----------------------------------------------------------------------------
                 CC|                            |dnovillo at gcc dot gnu dot
                   |                            |org


http://gcc.gnu.org/bugzilla/show_bug.cgi?id=22485


^ permalink raw reply	[flat|nested] 25+ messages in thread

* [Bug c/22485] pointer +- integer is never NULL
  2005-07-14 13:10 [Bug c/22485] New: pointer +- integer is never NULL mattias at virtutech dot se
                   ` (3 preceding siblings ...)
  2005-07-14 13:45 ` dberlin at gcc dot gnu dot org
@ 2005-07-14 13:46 ` falk at debian dot org
  2005-07-14 15:19 ` gdr at integrable-solutions dot net
                   ` (16 subsequent siblings)
  21 siblings, 0 replies; 25+ messages in thread
From: falk at debian dot org @ 2005-07-14 13:46 UTC (permalink / raw)
  To: gcc-bugs


------- Additional Comments From falk at debian dot org  2005-07-14 13:45 -------
(In reply to comment #4)
> Hmmmm.
> I swear we just had this discussion for VRP purposes, and that a bug was
> recently fixed so that we don't assume that pointer + - integer is NULL. 

Well, I checked C99 and C++, and they explain a few cases, never mentioning
null pointers, and then say everything else is undefined. Maybe this was
different in C89? Seems unlikely, though...


-- 


http://gcc.gnu.org/bugzilla/show_bug.cgi?id=22485


^ permalink raw reply	[flat|nested] 25+ messages in thread

* [Bug c/22485] pointer +- integer is never NULL
  2005-07-14 13:10 [Bug c/22485] New: pointer +- integer is never NULL mattias at virtutech dot se
                   ` (4 preceding siblings ...)
  2005-07-14 13:46 ` falk at debian dot org
@ 2005-07-14 15:19 ` gdr at integrable-solutions dot net
  2005-07-14 15:21 ` gdr at integrable-solutions dot net
                   ` (15 subsequent siblings)
  21 siblings, 0 replies; 25+ messages in thread
From: gdr at integrable-solutions dot net @ 2005-07-14 15:19 UTC (permalink / raw)
  To: gcc-bugs


------- Additional Comments From gdr at integrable-solutions dot net  2005-07-14 15:17 -------
Subject: Re:  pointer +- integer is never NULL

"dberlin at gcc dot gnu dot org" <gcc-bugzilla@gcc.gnu.org> writes:

| Hmmmm.
| I swear we just had this discussion for VRP purposes, and that a bug was
| recently fixed so that we don't assume that pointer + - integer is NULL. 

Please notice that there still are implementation of the offset macros
out there, in one form of the other that relies on pointer arithmetic
and NULL.

| But if it's really undefined, maybe we should optimize it.

I would recommend caution.

-- Gaby


-- 


http://gcc.gnu.org/bugzilla/show_bug.cgi?id=22485


^ permalink raw reply	[flat|nested] 25+ messages in thread

* [Bug c/22485] pointer +- integer is never NULL
  2005-07-14 13:10 [Bug c/22485] New: pointer +- integer is never NULL mattias at virtutech dot se
                   ` (5 preceding siblings ...)
  2005-07-14 15:19 ` gdr at integrable-solutions dot net
@ 2005-07-14 15:21 ` gdr at integrable-solutions dot net
  2005-07-14 16:03 ` falk at debian dot org
                   ` (14 subsequent siblings)
  21 siblings, 0 replies; 25+ messages in thread
From: gdr at integrable-solutions dot net @ 2005-07-14 15:21 UTC (permalink / raw)
  To: gcc-bugs


------- Additional Comments From gdr at integrable-solutions dot net  2005-07-14 15:19 -------
Subject: Re:  pointer +- integer is never NULL

"falk at debian dot org" <gcc-bugzilla@gcc.gnu.org> writes:

| (In reply to comment #4)
| > Hmmmm.
| > I swear we just had this discussion for VRP purposes, and that a bug was
| > recently fixed so that we don't assume that pointer + - integer is NULL. 
| 
| Well, I checked C99 and C++, and they explain a few cases, never mentioning
| null pointers, and then say everything else is undefined. Maybe this was
| different in C89? Seems unlikely, though...

I'm failing to find anything in the C++ standard that suggests that the
following shall be undefined

   (reinterpret_cast<int*>(0) + 5) - 5

-- Gaby


-- 


http://gcc.gnu.org/bugzilla/show_bug.cgi?id=22485


^ permalink raw reply	[flat|nested] 25+ messages in thread

* [Bug c/22485] pointer +- integer is never NULL
  2005-07-14 13:10 [Bug c/22485] New: pointer +- integer is never NULL mattias at virtutech dot se
                   ` (6 preceding siblings ...)
  2005-07-14 15:21 ` gdr at integrable-solutions dot net
@ 2005-07-14 16:03 ` falk at debian dot org
  2005-07-14 19:38   ` Gabriel Dos Reis
  2005-07-14 19:40 ` gdr at integrable-solutions dot net
                   ` (13 subsequent siblings)
  21 siblings, 1 reply; 25+ messages in thread
From: falk at debian dot org @ 2005-07-14 16:03 UTC (permalink / raw)
  To: gcc-bugs


------- Additional Comments From falk at debian dot org  2005-07-14 15:37 -------
(In reply to comment #7)

> I'm failing to find anything in the C++ standard that suggests that the
> following shall be undefined
> 
>    (reinterpret_cast<int*>(0) + 5) - 5

If (reinterpret_cast<int*>(0) + 5) - 5 is not undefined, then neither is
reinterpret_cast<int*>(0) + 5. Then what is its result, by which paragraph
in the standard?


-- 


http://gcc.gnu.org/bugzilla/show_bug.cgi?id=22485


^ permalink raw reply	[flat|nested] 25+ messages in thread

* Re: [Bug c/22485] pointer +- integer is never NULL
  2005-07-14 16:03 ` falk at debian dot org
@ 2005-07-14 19:38   ` Gabriel Dos Reis
  2005-07-14 21:47     ` Falk Hueffner
  0 siblings, 1 reply; 25+ messages in thread
From: Gabriel Dos Reis @ 2005-07-14 19:38 UTC (permalink / raw)
  To: gcc-bugzilla; +Cc: gcc-bugs

"falk at debian dot org" <gcc-bugzilla@gcc.gnu.org> writes:

| ------- Additional Comments From falk at debian dot org  2005-07-14 15:37 -------
| (In reply to comment #7)
| 
| > I'm failing to find anything in the C++ standard that suggests that the
| > following shall be undefined
| > 
| >    (reinterpret_cast<int*>(0) + 5) - 5
| 
| If (reinterpret_cast<int*>(0) + 5) - 5 is not undefined, then neither is
| reinterpret_cast<int*>(0) + 5. Then what is its result, by which paragraph
| in the standard?

The standard says that the mapping used by reinterpret_cast to turn an
integer into a pointer is *implemented-defined*.  It is not undefined.
GCC uses the "obvious" mapping, which is reinterpret_cast<int*>(0) is
the null pointer.

-- Gaby


^ permalink raw reply	[flat|nested] 25+ messages in thread

* [Bug c/22485] pointer +- integer is never NULL
  2005-07-14 13:10 [Bug c/22485] New: pointer +- integer is never NULL mattias at virtutech dot se
                   ` (7 preceding siblings ...)
  2005-07-14 16:03 ` falk at debian dot org
@ 2005-07-14 19:40 ` gdr at integrable-solutions dot net
  2005-07-14 22:19 ` falk at debian dot org
                   ` (12 subsequent siblings)
  21 siblings, 0 replies; 25+ messages in thread
From: gdr at integrable-solutions dot net @ 2005-07-14 19:40 UTC (permalink / raw)
  To: gcc-bugs


------- Additional Comments From gdr at integrable-solutions dot net  2005-07-14 19:38 -------
Subject: Re:  pointer +- integer is never NULL

"falk at debian dot org" <gcc-bugzilla@gcc.gnu.org> writes:

| ------- Additional Comments From falk at debian dot org  2005-07-14 15:37 -------
| (In reply to comment #7)
| 
| > I'm failing to find anything in the C++ standard that suggests that the
| > following shall be undefined
| > 
| >    (reinterpret_cast<int*>(0) + 5) - 5
| 
| If (reinterpret_cast<int*>(0) + 5) - 5 is not undefined, then neither is
| reinterpret_cast<int*>(0) + 5. Then what is its result, by which paragraph
| in the standard?

The standard says that the mapping used by reinterpret_cast to turn an
integer into a pointer is *implemented-defined*.  It is not undefined.
GCC uses the "obvious" mapping, which is reinterpret_cast<int*>(0) is
the null pointer.

-- Gaby


-- 


http://gcc.gnu.org/bugzilla/show_bug.cgi?id=22485


^ permalink raw reply	[flat|nested] 25+ messages in thread

* Re: [Bug c/22485] pointer +- integer is never NULL
  2005-07-14 19:38   ` Gabriel Dos Reis
@ 2005-07-14 21:47     ` Falk Hueffner
  0 siblings, 0 replies; 25+ messages in thread
From: Falk Hueffner @ 2005-07-14 21:47 UTC (permalink / raw)
  To: Gabriel Dos Reis; +Cc: gcc-bugzilla, gcc-bugs

Gabriel Dos Reis <gdr@integrable-solutions.net> writes:

> "falk at debian dot org" <gcc-bugzilla@gcc.gnu.org> writes:
>
> | ------- Additional Comments From falk at debian dot org  2005-07-14 15:37 -------
> | (In reply to comment #7)
> | 
> | > I'm failing to find anything in the C++ standard that suggests that the
> | > following shall be undefined
> | > 
> | >    (reinterpret_cast<int*>(0) + 5) - 5
> | 
> | If (reinterpret_cast<int*>(0) + 5) - 5 is not undefined, then neither is
> | reinterpret_cast<int*>(0) + 5. Then what is its result, by which paragraph
> | in the standard?
>
> The standard says that the mapping used by reinterpret_cast to turn an
> integer into a pointer is *implemented-defined*.  It is not undefined.
> GCC uses the "obvious" mapping, which is reinterpret_cast<int*>(0) is
> the null pointer.

So your example boils down further to the question of whether
((int*)0) + 5 is undefined, but you didn't answer my question
yet. What is the result of ((int*)0) + 5, by which paragraph in the
standard?

-- 
	Falk


^ permalink raw reply	[flat|nested] 25+ messages in thread

* [Bug c/22485] pointer +- integer is never NULL
  2005-07-14 13:10 [Bug c/22485] New: pointer +- integer is never NULL mattias at virtutech dot se
                   ` (8 preceding siblings ...)
  2005-07-14 19:40 ` gdr at integrable-solutions dot net
@ 2005-07-14 22:19 ` falk at debian dot org
  2005-07-14 23:04 ` gdr at integrable-solutions dot net
                   ` (11 subsequent siblings)
  21 siblings, 0 replies; 25+ messages in thread
From: falk at debian dot org @ 2005-07-14 22:19 UTC (permalink / raw)
  To: gcc-bugs


------- Additional Comments From falk at debian dot org  2005-07-14 21:47 -------
Subject: Re:  pointer +- integer is never NULL

Gabriel Dos Reis <gdr@integrable-solutions.net> writes:

> "falk at debian dot org" <gcc-bugzilla@gcc.gnu.org> writes:
>
> | ------- Additional Comments From falk at debian dot org  2005-07-14 15:37 -------
> | (In reply to comment #7)
> | 
> | > I'm failing to find anything in the C++ standard that suggests that the
> | > following shall be undefined
> | > 
> | >    (reinterpret_cast<int*>(0) + 5) - 5
> | 
> | If (reinterpret_cast<int*>(0) + 5) - 5 is not undefined, then neither is
> | reinterpret_cast<int*>(0) + 5. Then what is its result, by which paragraph
> | in the standard?
>
> The standard says that the mapping used by reinterpret_cast to turn an
> integer into a pointer is *implemented-defined*.  It is not undefined.
> GCC uses the "obvious" mapping, which is reinterpret_cast<int*>(0) is
> the null pointer.

So your example boils down further to the question of whether
((int*)0) + 5 is undefined, but you didn't answer my question
yet. What is the result of ((int*)0) + 5, by which paragraph in the
standard?



-- 


http://gcc.gnu.org/bugzilla/show_bug.cgi?id=22485


^ permalink raw reply	[flat|nested] 25+ messages in thread

* [Bug c/22485] pointer +- integer is never NULL
  2005-07-14 13:10 [Bug c/22485] New: pointer +- integer is never NULL mattias at virtutech dot se
                   ` (9 preceding siblings ...)
  2005-07-14 22:19 ` falk at debian dot org
@ 2005-07-14 23:04 ` gdr at integrable-solutions dot net
  2005-07-15  7:51 ` falk at debian dot org
                   ` (10 subsequent siblings)
  21 siblings, 0 replies; 25+ messages in thread
From: gdr at integrable-solutions dot net @ 2005-07-14 23:04 UTC (permalink / raw)
  To: gcc-bugs


------- Additional Comments From gdr at integrable-solutions dot net  2005-07-14 23:03 -------
Subject: Re:  pointer +- integer is never NULL

"falk at debian dot org" <gcc-bugzilla@gcc.gnu.org> writes:

[...]

| > | (In reply to comment #7)
| > | 
| > | > I'm failing to find anything in the C++ standard that suggests that the
| > | > following shall be undefined
| > | > 
| > | >    (reinterpret_cast<int*>(0) + 5) - 5
| > | 
| > | If (reinterpret_cast<int*>(0) + 5) - 5 is not undefined, then neither is
| > | reinterpret_cast<int*>(0) + 5. Then what is its result, by which paragraph
| > | in the standard?
| >
| > The standard says that the mapping used by reinterpret_cast to turn an
| > integer into a pointer is *implemented-defined*.  It is not undefined.
| > GCC uses the "obvious" mapping, which is reinterpret_cast<int*>(0) is
| > the null pointer.
| 
| So your example boils down further to the question of whether
| ((int*)0) + 5 is undefined, but you didn't answer my question
| yet.

No.  I think I made an indirect observation.  

There is no requirement from the standard that (int *)0 is the same as
reinterpret_cast<int*>(0) -- yes, I do not know many of practical
compilers that do things differently, but it needs pointing out.
Therefore, you cannot directly reduce reinterpret_cast<int*>(0) + 5 to
(int *)0 + 5. 

However, for practical purposes, GCC uses the obvious mapping
following the standard intent 5.2.10/4 for reinterpret_cast:

  [...] [Note: it is intended to be unsurprising to those who know the 
  addressing structure of the underlying machine. ]

My indirect observation was that reinterpret_cast is intended for specific
needs that cannot adequately be expressed at the purely object type level.
The result is intended to be unsurprising to those who know the
addressing structure.  Consequently it takes a creative compiler to
make reinterpret_cast<int*>(0) + 5 undefined.  Furthermore, given the
mapping chosen by GCC, it takes even more creative compiler to make
(int *)0 + 5 also undefined. 

There still are reasonable codes for system programming out there
that needs the to go through the play with null pointer -- we, GCC,
even used to distribute such things in the past.

-- Gaby


-- 


http://gcc.gnu.org/bugzilla/show_bug.cgi?id=22485


^ permalink raw reply	[flat|nested] 25+ messages in thread

* [Bug c/22485] pointer +- integer is never NULL
  2005-07-14 13:10 [Bug c/22485] New: pointer +- integer is never NULL mattias at virtutech dot se
                   ` (10 preceding siblings ...)
  2005-07-14 23:04 ` gdr at integrable-solutions dot net
@ 2005-07-15  7:51 ` falk at debian dot org
  2005-07-15  8:26 ` gdr at integrable-solutions dot net
                   ` (9 subsequent siblings)
  21 siblings, 0 replies; 25+ messages in thread
From: falk at debian dot org @ 2005-07-15  7:51 UTC (permalink / raw)
  To: gcc-bugs


------- Additional Comments From falk at debian dot org  2005-07-15 06:41 -------
Subject: Re:  pointer +- integer is never NULL

"gdr at integrable-solutions dot net" <gcc-bugzilla@gcc.gnu.org> writes:

> My indirect observation was that reinterpret_cast is intended for
> specific needs that cannot adequately be expressed at the purely
> object type level.  The result is intended to be unsurprising to
> those who know the addressing structure.  Consequently it takes a
> creative compiler to make reinterpret_cast<int*>(0) + 5 undefined.

Sorry, I cannot follow you. I'd find it massively unsurprising if
reinterpret_cast<int*>(0) produces a null pointer, and if I then get
undefined behavior for doing something with it that is undefined for a
null pointer. In fact I'd find it very *surprising* if
reinterpret_cast<int*>(0) behaves different than a normally
constructed null pointer anywhere.

> Furthermore, given the mapping chosen by GCC, it takes even more
> creative compiler to make (int *)0 + 5 also undefined.

And I don't see how that follows, either.

As it seems, arguing with different levels of surprisingness seems to
be somewhat subjective, so I don't think this leads us anywhere.

> There still are reasonable codes for system programming out there
> that needs the to go through the play with null pointer -- we, GCC,
> even used to distribute such things in the past.

This is a more relevant point. I don't think this optimization would
break offsetof-like macros, since they'd use null pointer *constants*,
which we could easily avoid to tag as non-null.



-- 


http://gcc.gnu.org/bugzilla/show_bug.cgi?id=22485


^ permalink raw reply	[flat|nested] 25+ messages in thread

* [Bug c/22485] pointer +- integer is never NULL
  2005-07-14 13:10 [Bug c/22485] New: pointer +- integer is never NULL mattias at virtutech dot se
                   ` (11 preceding siblings ...)
  2005-07-15  7:51 ` falk at debian dot org
@ 2005-07-15  8:26 ` gdr at integrable-solutions dot net
  2005-07-15  9:27 ` mattias at virtutech dot se
                   ` (8 subsequent siblings)
  21 siblings, 0 replies; 25+ messages in thread
From: gdr at integrable-solutions dot net @ 2005-07-15  8:26 UTC (permalink / raw)
  To: gcc-bugs


------- Additional Comments From gdr at integrable-solutions dot net  2005-07-15 08:10 -------
Subject: Re:  pointer +- integer is never NULL

"falk at debian dot org" <gcc-bugzilla@gcc.gnu.org> writes:

| ------- Additional Comments From falk at debian dot org  2005-07-15 06:41 -------
| Subject: Re:  pointer +- integer is never NULL
| 
| "gdr at integrable-solutions dot net" <gcc-bugzilla@gcc.gnu.org> writes:
| 
| > My indirect observation was that reinterpret_cast is intended for
| > specific needs that cannot adequately be expressed at the purely
| > object type level.  The result is intended to be unsurprising to
| > those who know the addressing structure.  Consequently it takes a
| > creative compiler to make reinterpret_cast<int*>(0) + 5 undefined.
| 
| Sorry, I cannot follow you. I'd find it massively unsurprising if
| reinterpret_cast<int*>(0) produces a null pointer, and if I then get
| undefined behavior for doing something with it that is undefined for a
| null pointer.

But, if I used reinterpret_cast to turn an integer value 0 into a
pointer, there is no reason why the compiler would assume that I do not
know the underlying machine and what I'm doing with the pointer.

| In fact I'd find it very *surprising* if
| reinterpret_cast<int*>(0) behaves different than a normally
| constructed null pointer anywhere.

At least, you get that part of my indirect observation! :-)

| > Furthermore, given the mapping chosen by GCC, it takes even more
| > creative compiler to make (int *)0 + 5 also undefined.
| 
| And I don't see how that follows, either.

if follows from your surprise that reinterpret_cast<int*> does
something different from the null pointer constant (int*)0.

| As it seems, arguing with different levels of surprisingness seems to
| be somewhat subjective, so I don't think this leads us anywhere.

I'm not actually arguing on different level of surprisingness.  I'm
just looking at reinterpret_cast and its implication. 

| > There still are reasonable codes for system programming out there
| > that needs the to go through the play with null pointer -- we, GCC,
| > even used to distribute such things in the past.
| 
| This is a more relevant point. I don't think this optimization would
| break offsetof-like macros, since they'd use null pointer *constants*,
                                                            ^^^^^^^^^^^

For the offsetof *macro*, yes
But that is not the case for codes that uses
reinterpret_cat<int*>(expr), where expr is an integer expression with
value 0.  Scanning a region of memory starting from zero, is not
exactly the kind of thing never done in practice.

| which we could easily avoid to tag as non-null.

so you would have to pretend that a null pointer constant is not null?
That is even more bizarre arithmetic.

-- Gaby


-- 


http://gcc.gnu.org/bugzilla/show_bug.cgi?id=22485


^ permalink raw reply	[flat|nested] 25+ messages in thread

* [Bug c/22485] pointer +- integer is never NULL
  2005-07-14 13:10 [Bug c/22485] New: pointer +- integer is never NULL mattias at virtutech dot se
                   ` (12 preceding siblings ...)
  2005-07-15  8:26 ` gdr at integrable-solutions dot net
@ 2005-07-15  9:27 ` mattias at virtutech dot se
  2005-07-15 10:35 ` gdr at integrable-solutions dot net
                   ` (7 subsequent siblings)
  21 siblings, 0 replies; 25+ messages in thread
From: mattias at virtutech dot se @ 2005-07-15  9:27 UTC (permalink / raw)
  To: gcc-bugs


------- Additional Comments From mattias at virtutech dot se  2005-07-15 09:12 -------
It could be made an option so the user can tell GCC whether to make
standard-conforming code go as fast as possible or if arithmetic on null
pointers (as a gcc extension, say) is needed. -fnull-pointer-arith?

(In reply to comment #13)
> Scanning a region of memory starting from zero, is not
> exactly the kind of thing never done in practice.

True, but that sort of code is already in danger, since GCC assumes that in

      x = *p;
      if (!p) shout();

the condition is never true (even if it is possible to read from location 0).


-- 


http://gcc.gnu.org/bugzilla/show_bug.cgi?id=22485


^ permalink raw reply	[flat|nested] 25+ messages in thread

* [Bug c/22485] pointer +- integer is never NULL
  2005-07-14 13:10 [Bug c/22485] New: pointer +- integer is never NULL mattias at virtutech dot se
                   ` (13 preceding siblings ...)
  2005-07-15  9:27 ` mattias at virtutech dot se
@ 2005-07-15 10:35 ` gdr at integrable-solutions dot net
  2005-07-15 11:42 ` pluto at agmk dot net
                   ` (6 subsequent siblings)
  21 siblings, 0 replies; 25+ messages in thread
From: gdr at integrable-solutions dot net @ 2005-07-15 10:35 UTC (permalink / raw)
  To: gcc-bugs


------- Additional Comments From gdr at integrable-solutions dot net  2005-07-15 10:26 -------
Subject: Re:  pointer +- integer is never NULL

"mattias at virtutech dot se" <gcc-bugzilla@gcc.gnu.org> writes:

| ------- Additional Comments From mattias at virtutech dot se  2005-07-15 09:12 -------
| It could be made an option so the user can tell GCC whether to make
| standard-conforming code go as fast as possible or if arithmetic on null
| pointers (as a gcc extension, say) is needed. -fnull-pointer-arith?
| 
| (In reply to comment #13)
| > Scanning a region of memory starting from zero, is not
| > exactly the kind of thing never done in practice.
| 
| True, but that sort of code is already in danger, since GCC assumes that in
| 
|       x = *p;
|       if (!p) shout();
| 
| the condition is never true (even if it is possible to read from location 0).

True but that is not the kind of codes I'm talking about.

-- Gaby


-- 


http://gcc.gnu.org/bugzilla/show_bug.cgi?id=22485


^ permalink raw reply	[flat|nested] 25+ messages in thread

* [Bug c/22485] pointer +- integer is never NULL
  2005-07-14 13:10 [Bug c/22485] New: pointer +- integer is never NULL mattias at virtutech dot se
                   ` (14 preceding siblings ...)
  2005-07-15 10:35 ` gdr at integrable-solutions dot net
@ 2005-07-15 11:42 ` pluto at agmk dot net
  2005-07-15 14:25 ` falk at debian dot org
                   ` (5 subsequent siblings)
  21 siblings, 0 replies; 25+ messages in thread
From: pluto at agmk dot net @ 2005-07-15 11:42 UTC (permalink / raw)
  To: gcc-bugs


------- Additional Comments From pluto at agmk dot net  2005-07-15 10:35 -------
minor comment:
e.g. on ARM7 i can read data from address 0x00000000 (-> exception vector table).

int* p = (int*)0x00000004;
int d = -1;
int *m = *p + d;    // it's valid for ARM arch.


-- 


http://gcc.gnu.org/bugzilla/show_bug.cgi?id=22485


^ permalink raw reply	[flat|nested] 25+ messages in thread

* [Bug c/22485] pointer +- integer is never NULL
  2005-07-14 13:10 [Bug c/22485] New: pointer +- integer is never NULL mattias at virtutech dot se
                   ` (15 preceding siblings ...)
  2005-07-15 11:42 ` pluto at agmk dot net
@ 2005-07-15 14:25 ` falk at debian dot org
  2005-07-15 15:02 ` gdr at integrable-solutions dot net
                   ` (4 subsequent siblings)
  21 siblings, 0 replies; 25+ messages in thread
From: falk at debian dot org @ 2005-07-15 14:25 UTC (permalink / raw)
  To: gcc-bugs


------- Additional Comments From falk at debian dot org  2005-07-15 14:22 -------
(In reply to comment #13)
> Subject: Re:  pointer +- integer is never NULL
> 
> "falk at debian dot org" <gcc-bugzilla@gcc.gnu.org> writes:
> | Sorry, I cannot follow you. I'd find it massively unsurprising if
> | reinterpret_cast<int*>(0) produces a null pointer, and if I then get
> | undefined behavior for doing something with it that is undefined for a
> | null pointer.
> 
> But, if I used reinterpret_cast to turn an integer value 0 into a
> pointer, there is no reason why the compiler would assume that I do not
> know the underlying machine and what I'm doing with the pointer.

The note merely requires the result of the mapping to be unsurprising;
it does not say anything about further operations of this result. Therefore,
it is completely irrelevant here.

> | As it seems, arguing with different levels of surprisingness seems to
> | be somewhat subjective, so I don't think this leads us anywhere.
> 
> I'm not actually arguing on different level of surprisingness.  I'm
> just looking at reinterpret_cast and its implication. 

I don't see you bringing any argument here exept one based on a side note
about surprisingness, which IMHO doesn't even apply here. So I am still
convinced that nullpointer+0 is clearly undefined.

> | This is a more relevant point. I don't think this optimization would
> | break offsetof-like macros, since they'd use null pointer *constants*,
>                                                             ^^^^^^^^^^^
> 
> For the offsetof *macro*, yes
> But that is not the case for codes that uses
> reinterpret_cat<int*>(expr), where expr is an integer expression with
> value 0.  Scanning a region of memory starting from zero, is not
> exactly the kind of thing never done in practice.

Can you give a complete example where this optimization would fail, that you
would consider reasonable and realistic?

> | which we could easily avoid to tag as non-null.
> 
> so you would have to pretend that a null pointer constant is not null?
> That is even more bizarre arithmetic.

I have no trouble doing bizarre arithmetic when the user gives invalid input.


-- 


http://gcc.gnu.org/bugzilla/show_bug.cgi?id=22485


^ permalink raw reply	[flat|nested] 25+ messages in thread

* [Bug c/22485] pointer +- integer is never NULL
  2005-07-14 13:10 [Bug c/22485] New: pointer +- integer is never NULL mattias at virtutech dot se
                   ` (16 preceding siblings ...)
  2005-07-15 14:25 ` falk at debian dot org
@ 2005-07-15 15:02 ` gdr at integrable-solutions dot net
  2005-07-15 15:21 ` falk at debian dot org
                   ` (3 subsequent siblings)
  21 siblings, 0 replies; 25+ messages in thread
From: gdr at integrable-solutions dot net @ 2005-07-15 15:02 UTC (permalink / raw)
  To: gcc-bugs


------- Additional Comments From gdr at integrable-solutions dot net  2005-07-15 14:43 -------
Subject: Re:  pointer +- integer is never NULL

"falk at debian dot org" <gcc-bugzilla@gcc.gnu.org> writes:

| (In reply to comment #13)
| > Subject: Re:  pointer +- integer is never NULL
| > 
| > "falk at debian dot org" <gcc-bugzilla@gcc.gnu.org> writes:
| > | Sorry, I cannot follow you. I'd find it massively unsurprising if
| > | reinterpret_cast<int*>(0) produces a null pointer, and if I then get
| > | undefined behavior for doing something with it that is undefined for a
| > | null pointer.
| > 
| > But, if I used reinterpret_cast to turn an integer value 0 into a
| > pointer, there is no reason why the compiler would assume that I do not
| > know the underlying machine and what I'm doing with the pointer.
| 
| The note merely requires the result of the mapping to be unsurprising;
| it does not say anything about further operations of this result. Therefore,
| it is completely irrelevant here.

The "side" notes were written by people who know what they
intend. Therefore their inputs are completely relevant here.

-- Gaby


-- 


http://gcc.gnu.org/bugzilla/show_bug.cgi?id=22485


^ permalink raw reply	[flat|nested] 25+ messages in thread

* [Bug c/22485] pointer +- integer is never NULL
  2005-07-14 13:10 [Bug c/22485] New: pointer +- integer is never NULL mattias at virtutech dot se
                   ` (17 preceding siblings ...)
  2005-07-15 15:02 ` gdr at integrable-solutions dot net
@ 2005-07-15 15:21 ` falk at debian dot org
  2005-07-15 15:54 ` mattias at virtutech dot se
                   ` (2 subsequent siblings)
  21 siblings, 0 replies; 25+ messages in thread
From: falk at debian dot org @ 2005-07-15 15:21 UTC (permalink / raw)
  To: gcc-bugs


------- Additional Comments From falk at debian dot org  2005-07-15 15:05 -------
(In reply to comment #18)

> The "side" notes were written by people who know what they
> intend. Therefore their inputs are completely relevant here.

This is going nowhere. I give up.


-- 


http://gcc.gnu.org/bugzilla/show_bug.cgi?id=22485


^ permalink raw reply	[flat|nested] 25+ messages in thread

* [Bug c/22485] pointer +- integer is never NULL
  2005-07-14 13:10 [Bug c/22485] New: pointer +- integer is never NULL mattias at virtutech dot se
                   ` (18 preceding siblings ...)
  2005-07-15 15:21 ` falk at debian dot org
@ 2005-07-15 15:54 ` mattias at virtutech dot se
  2005-09-24  5:37 ` gdr at gcc dot gnu dot org
  2005-09-24  9:39 ` falk at debian dot org
  21 siblings, 0 replies; 25+ messages in thread
From: mattias at virtutech dot se @ 2005-07-15 15:54 UTC (permalink / raw)
  To: gcc-bugs


------- Additional Comments From mattias at virtutech dot se  2005-07-15 15:29 -------
(In reply to comment #18)
> The "side" notes were written by people who know what they
> intend. Therefore their inputs are completely relevant here.

Even if you could show that these optimisations would contradict the letter
and/or spirit of the C++ standard, this does not mean the same thing for C,
where this clearly (my judgement) is a missed optimisation opportunity for
standard-conforming code.

(It is really two related optimisations: that Q=P+I implies P!=NULL and that it
implies Q!=NULL.)


-- 


http://gcc.gnu.org/bugzilla/show_bug.cgi?id=22485


^ permalink raw reply	[flat|nested] 25+ messages in thread

* [Bug c/22485] pointer +- integer is never NULL
  2005-07-14 13:10 [Bug c/22485] New: pointer +- integer is never NULL mattias at virtutech dot se
                   ` (19 preceding siblings ...)
  2005-07-15 15:54 ` mattias at virtutech dot se
@ 2005-09-24  5:37 ` gdr at gcc dot gnu dot org
  2005-09-24  9:39 ` falk at debian dot org
  21 siblings, 0 replies; 25+ messages in thread
From: gdr at gcc dot gnu dot org @ 2005-09-24  5:37 UTC (permalink / raw)
  To: gcc-bugs


------- Additional Comments From gdr at gcc dot gnu dot org  2005-09-24 05:37 -------
(In reply to comment #0)
> The code
> 
> void stuff(void);
> void f(int *p, int x)
> {
>         int *q = p + x;
>         if (!q)
>                 stuff();
> }
> 
> should never call stuff() - the test is unnecessary since pointer +/- integer is
> undefined when the pointer does not point to an object or just past the end of
> one (6.5.6 paragraph 8). This is important in cases such as:
> 
> static inline struct foo *lookup(struct foo *table, int x)
> {
>     if (match(table, x))
>         return table + x;
>     else
>         return NULL;
> }
> ...
>     struct foo *e = lookup(tbl, x);
>     if (e) ...
> 
> The code that calls the above function ends up checking for NULL twice: once
> inside the (inlined) function, and one after the call. Were Q = P +- I
> recognised as implying that P != NULL, Q != NULL (as we are allowed to do
> according to the Standard), then the extraneous NULL test could be eliminated.


There have been lots of messages exchanged on this topic.  It was just
pointed to me that the C++ standard -- unlike the C99 standard -- has the
following wording 5.7/7:

   If the value 0 is added to or subtracted from a pointer value, the result
   compares equal to the original pointer value. If two pointers point to the
   same object or both point one past the end of the same array or both are
   null, and the two pointers are subtracted, the result compares equal to the
   value 0 converted to the type ptrdiff_t.
  
-- Gaby

  

   

-- 


http://gcc.gnu.org/bugzilla/show_bug.cgi?id=22485


^ permalink raw reply	[flat|nested] 25+ messages in thread

* [Bug c/22485] pointer +- integer is never NULL
  2005-07-14 13:10 [Bug c/22485] New: pointer +- integer is never NULL mattias at virtutech dot se
                   ` (20 preceding siblings ...)
  2005-09-24  5:37 ` gdr at gcc dot gnu dot org
@ 2005-09-24  9:39 ` falk at debian dot org
  21 siblings, 0 replies; 25+ messages in thread
From: falk at debian dot org @ 2005-09-24  9:39 UTC (permalink / raw)
  To: gcc-bugs


------- Additional Comments From falk at debian dot org  2005-09-24 09:39 -------
(In reply to comment #21)

> There have been lots of messages exchanged on this topic.  It was just
> pointed to me that the C++ standard -- unlike the C99 standard -- has the
> following wording 5.7/7:

Hmm, I missed that. So can we agree now the following implications are valid:

int *p, *q, x;

C99:
q = p +- x formed => p nonnull, q nonnull
x = p - q  formed => p nonnull, q nonnull

C++:
q = p +- x formed, p nonnull => q nonnull
q = p +- x formed, x nonnull => p nonnull, q nonnull
x = p - q  formed, p nonnull => q nonnull
x = p - q  formed, q nonnull => p nonnull

-- 


http://gcc.gnu.org/bugzilla/show_bug.cgi?id=22485


^ permalink raw reply	[flat|nested] 25+ messages in thread

end of thread, other threads:[~2005-09-24  9:39 UTC | newest]

Thread overview: 25+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2005-07-14 13:10 [Bug c/22485] New: pointer +- integer is never NULL mattias at virtutech dot se
2005-07-14 13:14 ` [Bug c/22485] " mattias at virtutech dot se
2005-07-14 13:14 ` pinskia at gcc dot gnu dot org
2005-07-14 13:19 ` falk at debian dot org
2005-07-14 13:45 ` dberlin at gcc dot gnu dot org
2005-07-14 13:46 ` falk at debian dot org
2005-07-14 15:19 ` gdr at integrable-solutions dot net
2005-07-14 15:21 ` gdr at integrable-solutions dot net
2005-07-14 16:03 ` falk at debian dot org
2005-07-14 19:38   ` Gabriel Dos Reis
2005-07-14 21:47     ` Falk Hueffner
2005-07-14 19:40 ` gdr at integrable-solutions dot net
2005-07-14 22:19 ` falk at debian dot org
2005-07-14 23:04 ` gdr at integrable-solutions dot net
2005-07-15  7:51 ` falk at debian dot org
2005-07-15  8:26 ` gdr at integrable-solutions dot net
2005-07-15  9:27 ` mattias at virtutech dot se
2005-07-15 10:35 ` gdr at integrable-solutions dot net
2005-07-15 11:42 ` pluto at agmk dot net
2005-07-15 14:25 ` falk at debian dot org
2005-07-15 15:02 ` gdr at integrable-solutions dot net
2005-07-15 15:21 ` falk at debian dot org
2005-07-15 15:54 ` mattias at virtutech dot se
2005-09-24  5:37 ` gdr at gcc dot gnu dot org
2005-09-24  9:39 ` falk at debian dot org

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).