On Sat, Apr 18, 2020 at 9:29 PM Tadeus Prastowo <tadeus.prastowo@unitn.it> wrote:
On Sat, Apr 18, 2020 at 10:55 PM Andrew Schepler <aschepler@gmail.com> wrote:
>
> Got it. Linguistically, "the object will be or was located" is
> fairly vague, and it seems to me that the adverb clauses serve
> to specify the exact times meant by "will be" and "was". Using
> the definite article in "the object", rather than a phrase
> like "such an object", has to refer back to something recent,
> like the two phrases "an object" which are definitely modified
> by those time restrictions.

I interpret the "the object" in "any pointer that represents the
address of the storage location where the object will be or was
located" as an object that the pointer will point or already pointed.

In the sentence "After a stolen car is found on private property, any person who has an ownership stake or financial responsibility for the property may be questioned by the police" does not imply every owner of property may be questioned, even on an intentional misreading.
 
> And in your interpretation, the "before ..., or after ..."
> conditions modify only the main clause of that same sentence,
> i.e. "any pointer that ... may be used, but only in limited
> ways"?

Yes.

> Then what are those limited ways it may be used, or the
> limitations on its use?

It is elaborated in the immediately following sentence.  That sentence
in turn gives a forward reference to [class.cdtor].

Sentence-Y does not describe p. The object it pointed at is not "under construction or destruction". [class.cdtor]/1 does say no non-static member or base class of *p can be referred to. But none of the rest of [class.cdtor] can apply (except possibly paragraph 3, but its restrictions would always be weaker than paragraph 1 if both apply).

> Does any other clause in the Standard
> elaborate that case, if the following sentences and paragraphs
> don't?

See my previous answer.

> To be very specific, an example:
>
> #include <string>
> #include <new>
> union U {
>     int n;
>     std::string s;
>     U() {} // no member initialized
>     ~U() {}
> };
> void f() {
>     U u;
>     std::string* p = new((void*) &u.s) std::string("hello");

Why do you need the cast to `void *' for `&u.s' ?

It's a somewhat paranoid habit to protect against some other operator new definition which could be a better match than the one in <new>. The Standard describes a similar cast for the default behavior of std::allocator_traits<A>::construct. Of course if we take the example as a complete translation unit, that's not a concern.
 
>     p->~std::string();
>     // The lifetime of the object p pointed at has ended, but its storage has not been reused or released.

Yes.

>     // At this point, how can p be used and how may it not be used?

In accordance with Sentence-A, -B, and -C.

Wasn't that what you said applied to pb in the Standard example after the storage for the object it pointed at was reused? What is the difference in applicable Standard rules between pb and this p? Or what other normative effect, if any, does the word "reused" in Sentence-X have?
 
>     *p; // ok?

Yes.

> }

--
Best regards,
Tadeus