On Aug 22, 2013, at 2:28 PM, Gabriel Dos Reis <g...@integrable-solutions.net> 
wrote:
> On Thu, Aug 22, 2013 at 4:14 PM, Mike Stump <mikest...@comcast.net> wrote:
>> On Aug 22, 2013, at 9:45 AM, Gabriel Dos Reis 
>> <g...@integrable-solutions.net> wrote:
>>>> I.e. can I have something like
>>>> 
>>>> int a;
>>>> test()
>>>> {
>>>> int *b=new (int);
>>>> }
>>>> 
>>>> with custom implementation of new that returns &a?
>>> 
>>> If the user-supplied operator new returns &a, then it must
>>> also ensure that 'a' is not used anywhere else -- e.g. I you can't
>>> do lvalue-to-value conversion on 'a' to see what is written there.
>> 
>> This is wrong, in the c++97 standard there is no such limitation or 
>> restriction.
> 
> Please, elaborate.

Sure, there is no wording that limits as you describe.  There is a limit for 
polymorphic classes and classes with virtual bases (See [class.cdtor], but that 
is due to the vtable pointer lifetime and vbase pointer (offset) lifetime.  
Essentially, you can't use viable pointers or do vbase conversions before they 
are set, and they are only set at a particular time.  The standard keeps it 
simple and expands to non-POD, but I'd argue that from a QOI we should not make 
things that can work, not work.  See below on QOI issues.

I can't quote it, since the limitation doesn't exist.  I can quote the language 
that allows & on an object, that you can then cast this to be of a different 
type, and then dereference and use that type, if you want.  I can quote the 
object lifetime rules, that describe when it comes into existence, and when it 
goes away.  But, none of these are terribly surprising.  If you want to narrow 
done what part of the language you're interested in, I can quote just that part.

int a;

a exists before the program runs, and exists till after the program is finished 
running (See [basic.stc.static]).  That's the lifetime of it.  During it's 
lifetime, you can use it in the ways the standard lets you.  For example, ++a;. 
 In the below:

void foo() {
        char *cp = &a;

        [ … ]
}

cp's lifetime is from the declaration of it, til the }.  The character object 
that cp points to has a lifetime.  It's lifetime is from before the program 
runs, til after the program finishes.  (See [basic.life])  It can be used any 
way that a lvalue character can be used.  Since you can't use cp before it's 
lifetime, to use this character object outside of the lifetime of cp, you'd 
need another reference to it beyond just cp.  Again, this isn't suppose to be 
surprising.

Now, we do have wording like:

15If  a program attempts to access the stored value of an object through
  an lvalue of other than one of the following  types  the  behavior  is
  undefined48):

and we do have latitude to do things that uses that as a basis, but, once one 
ensures locking, say with atomics or volatile, to ensure the variable hits 
memory, I will argue that we can't make as much use of that from a quality of 
implementation viewpoint, despite the standard wording.  Now, even without 
volatile and locking, from a quality of implementation point of view, we don't 
actually want to make full use of undefined.  QOI still forces us to do the 
right thing.  undefined means, we get to kill the user.  QOI means, even though 
we can, we refrain from it, cause if we did, they would not like us.

For the case of a int, and a placement new on that int, of an int.  The 
behavior is mandated by the standard to work.  For a allocation function, they 
are free to play games with persistence (or unexec a la emacs), with allocated 
objects and this too has to work.  This means they can alias, and the standard 
says they can write this code and the standard mandates that it works.

Now, the user can use:

@item malloc
@cindex @code{malloc} attribute
The @code{malloc} attribute is used to tell the compiler that a function
may be treated as if any non-@code{NULL} pointer it returns cannot
alias any other pointer valid when the function returns and that the memory
has undefined content.
This often improves optimization.
Standard functions with this property include @code{malloc} and
@code{calloc}.  @code{realloc}-like functions do not have this
property as the memory pointed to does not have undefined content.

on their allocation functions, if they want.  And if they do, than what it says 
is true, by definition, but not by standard.  When this isn't true, the user 
will refrain from using this attribute.

Reply via email to