<div dir="ltr"><div class="gmail_extra"><div class="gmail_quote">On Fri, Feb 26, 2016 at 1:03 PM, Robert Haberlach <span dir="ltr">&lt;<a href="mailto:rh633@cam.ac.uk" target="_blank">rh633@cam.ac.uk</a>&gt;</span> wrote:<br><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">On 02/26/2016 02:26 PM, Hubert Tong wrote:<br>
<span class="">&gt; On Fri, Feb 26, 2016 at 7:12 AM, Robert Haberlach &lt;<a href="mailto:rh633@cam.ac.uk">rh633@cam.ac.uk</a> &lt;mailto:<a href="mailto:rh633@cam.ac.uk">rh633@cam.ac.uk</a>&gt;&gt; wrote:<br>
&gt;<br>
&gt;     I apologize in advance if this was discussed before; I didn&#39;t check the entire archive. Consider<br>
&gt;<br>
&gt;       static_assert(alignof(float) &gt;= alignof(int) &amp;&amp; sizeof(float) &gt;= sizeof(int));<br>
&gt;       int foo(float f) {<br>
&gt;         return *std::launder(reinterpret_cast&lt;int*&gt;(&amp;f)); }<br>
&gt;<br>
&gt;     As it stands, invocation of foo is undefined, as the argument to launder is not pointing to an object of type int (or similar) within its lifetime,<br>
&gt;     violating launder&#39;s requirement.<br>
&gt;<br>
&gt;     launder is designed to inhibit address propagation analysis, which is the only concerning optimization. Moreover, as long as all usual conditions are<br>
&gt;     met (alignment, size &amp; trap values), this should be fine on any implementation. If so, can we make the above formally well-defined?<br>
&gt;<br>
&gt; This is not fine. Type-based aliasing analysis (TBAA) is allowed to determine that the write to &quot;f&quot; and the read from the dereference is not related.<br>
&gt; Consider the effects of inlining:<br>
&gt; int main(void) { return !foo(0.5f); }<br>
&gt;<br>
&gt; becomes (loosely):<br>
&gt;<br>
&gt; int main(void) {<br>
&gt;   int __ret;<br>
&gt;   {<br>
&gt;     float __f = 0.5f;<br>
&gt;     __ret = *std::launder(reinterpret_cast&lt;int *&gt;(&amp;__f));<br>
&gt;   }<br>
&gt;   return !__ret;<br>
&gt; }<br>
&gt;<br>
&gt; The implementation is allowed to observe that there are no TBAA-compatible reads of the value of __f within its lifetime.<br>
<br>
</span>Isn&#39;t the whole idea that launder&#39;s definition is, to some extent, intransparent to optimizers? We&#39;re passing a pointer to f into launder. As long as<br>
the analyser is told to assume that calls to launder perform what not, it cannot elide the initialization, because launder could read.<br></blockquote><div>The definition of <span style="font-family:monospace,monospace">launder</span> is <i>not</i> opaque to optimizers. It is intended that <span style="font-family:monospace,monospace">launder</span> is well-known to not have side-effects.<br><br></div><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">
<br>
Perhaps launder isn&#39;t the right function to base such functionality on, anyway (I just had the impression it fitted the picture of an &quot;opaque&quot;<br>
identity function well). Then my question would rather be if it is sensible to provide some function (or language construct), e.g. taking a glvalue<br>
and returning one of a given type, s.t. aliasing via the returned glvalue can be well-defined. I don&#39;t think there would be great technical obstacles<br>
in adjusting aliasing analysers to treat such calls accordingly, but it would allow for a concise way of disabling strict aliasing for an operation<br>
while still benefiting from powerful optimization everywhere else.<br></blockquote><div>Assuming you mean to use that glvalue directly (as opposed to forming a pointer or reference binding) to perform said access, then such a construct makes some sense to me.<br></div><div> </div><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">
<br>
Robert<br>
<span class=""><br>
&gt; The likely result is that<br>
&gt; the initialization of __f would be optimized away.<br>
&gt;<br>
&gt; -- HT<br>
&gt;<br>
&gt;     Being able to use launder in such scenarios would render circumlocutions via memcpy superfluous.<br>
&gt;<br>
&gt;     Robert<br>
&gt;     _______________________________________________<br>
&gt;     ub mailing list<br>
</span>&gt;     <a href="mailto:ub@isocpp.open-std.org">ub@isocpp.open-std.org</a> &lt;mailto:<a href="mailto:ub@isocpp.open-std.org">ub@isocpp.open-std.org</a>&gt;<br>
&gt;     <a href="http://www.open-std.org/mailman/listinfo/ub" rel="noreferrer" target="_blank">http://www.open-std.org/mailman/listinfo/ub</a><br>
<div class="HOEnZb"><div class="h5">&gt;<br>
&gt;<br>
&gt;<br>
&gt;<br>
&gt; _______________________________________________<br>
&gt; ub mailing list<br>
&gt; <a href="mailto:ub@isocpp.open-std.org">ub@isocpp.open-std.org</a><br>
&gt; <a href="http://www.open-std.org/mailman/listinfo/ub" rel="noreferrer" target="_blank">http://www.open-std.org/mailman/listinfo/ub</a><br>
&gt;<br>
_______________________________________________<br>
ub mailing list<br>
<a href="mailto:ub@isocpp.open-std.org">ub@isocpp.open-std.org</a><br>
<a href="http://www.open-std.org/mailman/listinfo/ub" rel="noreferrer" target="_blank">http://www.open-std.org/mailman/listinfo/ub</a><br>
</div></div></blockquote></div><br></div></div>