<html>
  <head>
    <meta content="text/html; charset=utf-8" http-equiv="Content-Type">
  </head>
  <body bgcolor="#FFFFFF" text="#000000">
    <p><br>
    </p>
    <div class="moz-cite-prefix">On 07/07/2017 04:31 AM, Alexandre
      Isoard wrote:<br>
    </div>
    <blockquote
cite="mid:CANLM5Ldd0jDVirtCwadFR6ku7da_XdXGg+23az0Hk0RPoS_oyA@mail.gmail.com"
      type="cite">
      <meta http-equiv="Content-Type" content="text/html; charset=utf-8">
      <div dir="ltr">Hi,
        <div><br>
        </div>
        <div>Well, here is an example:</div>
        <div><br>
        </div>
        <div>preheader:</div>
        <div>  %skip = icmp slt i64 0, %n</div>
        <div>  br i1 %skip, label %exit, label %body</div>
        <div><br>
        </div>
        <div>body:</div>
        <div>  %i = phi i64 [ 0, %preheader ], [ %i.inc, %body ]</div>
        <div>  %<a moz-do-not-send="true" href="http://n.int"
            target="_blank">n.int</a> = trunc nsw i64 %n to i32<br>
        </div>
          %<a moz-do-not-send="true" href="http://i.int" target="_blank">i.int</a>
        = trunc nsw i64 %i to i32
        <div>  %test = icmp slt i32 %<a moz-do-not-send="true"
            href="http://i.int" target="_blank">i.int</a>, %<a
            moz-do-not-send="true" href="http://n.int" target="_blank">n.int</a></div>
        <div>  %i.inc = add nsw i64 %i, 1</div>
        <div>  br i1 %test, label %body, label %exit</div>
        <div><br>
        </div>
        <div>exit:</div>
        <div>  ...</div>
        <div><br>
        </div>
        <div>The original loop induction variable (%i) was 32 bit, as
          well as the loop boundary (%n).</div>
        <div>A pass decided to "upgrade" the induction variable
          arithmetic to 64 bits, and because the original increment was
          "add nsw" it is safe to do so. However, the loop exit
          condition is still a 32 bits comparison.</div>
      </div>
    </blockquote>
    <br>
    This is a good point. Especially right now, we widen induction
    variables early in the pipeline, and so we lose information (in
    practice at least) as a result. I'd prefer that we move widening to
    later in the pipeline, but perhaps it is still valuable regardless
    (because there are backend passes that depend on SCEV, etc.).<br>
    <br>
     -Hal<br>
    <br>
    <blockquote
cite="mid:CANLM5Ldd0jDVirtCwadFR6ku7da_XdXGg+23az0Hk0RPoS_oyA@mail.gmail.com"
      type="cite">
      <div dir="ltr">
        <div><br>
        </div>
        <div>A later pass could upgrade the loop exit condition to 64
          bits if it can prove that: « int64_t(i) < int64_t(n) ⇒
          int32_t(i) < int32_t(n) »</div>
        <div>Which is false in general, but true in this case, as the
          truncation is nsw.</div>
        <div><br>
        </div>
        <div>That being said, maybe the pass that upgraded the induction
          variable arithmetic should have finished the job and upgraded
          the loop condition. But that does provide some additional
          flexibility.</div>
        <div><br>
        </div>
        <div>Hopefully, I didn't mess up the example [I just made this
          up]. :-)</div>
        <div class="gmail_extra"><br>
          <div class="gmail_quote">On Fri, Jul 7, 2017 at 8:55 AM,
            Sanjoy Das <span dir="ltr"><<a moz-do-not-send="true"
                href="mailto:sanjoy@playingwithpointers.com"
                target="_blank">sanjoy@playingwithpointers.co<wbr>m</a>></span>
            wrote:<br>
            <blockquote class="gmail_quote" style="margin:0 0 0
              .8ex;border-left:1px #ccc solid;padding-left:1ex">Hi,<br>
              <br>
              Even if there are no ways in which a *frontend* can
              produce nsw<br>
              truncs, it may still be useful to have if optimization
              passes can<br>
              usefully attach nsw to truncates (after proving the
              truncates don't<br>
              "overflow").  For instance in<br>
              <br>
                %a = ashr i64 %v, i32 33<br>
                %t = trunc %a to i32<br>
              <br>
              the trunc can be marked nsw.<br>
              <br>
              However, the burden of proof here is to show that we can
              do some<br>
              useful optimization with nsw truncs that we can't do
              (unless we move<br>
              mountains) without them.<br>
              <br>
              Thanks!<br>
              -- Sanjoy<br>
              <br>
              <br>
              On Thu, Jul 6, 2017 at 5:46 PM, Hal Finkel via llvm-dev<br>
              <div
                class="m_7273905502421364517m_2468478144792101895HOEnZb">
                <div
                  class="m_7273905502421364517m_2468478144792101895h5"><<a
                    moz-do-not-send="true"
                    href="mailto:llvm-dev@lists.llvm.org"
                    target="_blank">llvm-dev@lists.llvm.org</a>>
                  wrote:<br>
                  ><br>
                  > On 07/06/2017 10:41 AM, Bruce Hoult wrote:<br>
                  ><br>
                  > According to <a moz-do-not-send="true"
                    href="http://6.3.1.3/3" rel="noreferrer"
                    target="_blank">6.3.1.3/3</a> of the C standard (I
                  didn't check C++):<br>
                  ><br>
                  > "3   Otherwise, the new type is signed and the
                  value cannot be represented<br>
                  > in it; either the result is
                  implementation-defined or an<br>
                  > implementation-defined signal is raised."<br>
                  ><br>
                  > I *think* that means that IF a signal is raised
                  then the signal raised could<br>
                  > be one that you can't guarantee to be able to
                  return from ("SIGFPE, SIGILL,<br>
                  > SIGSEGV, or any other implementation-defined
                  value corresponding to a<br>
                  > computational exception") and thus it is
                  implementation defined whether the<br>
                  > program will terminate.<br>
                  ><br>
                  > That provides pretty big scope to optimize around
                  :-)<br>
                  ><br>
                  ><br>
                  > That might be true, but C++ does not have the
                  implementation-defined signal<br>
                  > part. So whatever we did would need to be C
                  specific at this point.<br>
                  ><br>
                  >  -Hal<br>
                  ><br>
                  ><br>
                  ><br>
                  > Note also that while unsigned variables require
                  the implementation to act AS<br>
                  > IF running on a binary machine, signed variables
                  have no such requirement.<br>
                  > Most implementations do in fact truncate by
                  taking the remainder modulus the<br>
                  > number of values that can be represented in the
                  destination type, but that<br>
                  > might not be a power of two.<br>
                  ><br>
                  > I would guess there is very little code in the
                  wild that conforms to a<br>
                  > strict interpretation of all this.<br>
                  ><br>
                  > On Thu, Jul 6, 2017 at 5:24 PM, Alexandre Isoard
                  via llvm-dev<br>
                  > <<a moz-do-not-send="true"
                    href="mailto:llvm-dev@lists.llvm.org"
                    target="_blank">llvm-dev@lists.llvm.org</a>>
                  wrote:<br>
                  >><br>
                  >> Hi Hal,<br>
                  >><br>
                  >> I just want to check I understand correctly
                  the subtlety, in C++ an<br>
                  >> overflowing signed addition is an undefined
                  behavior (so Clang adds the nsw<br>
                  >> keyword to the sign add), while a signed cast
                  that overflow is "only"<br>
                  >> implementation defined (so Clang cant risk to
                  produce poison on trunc). Is<br>
                  >> that right?<br>
                  >><br>
                  >> If trunc produced undef instead of poison,
                  clang could use it, but then it<br>
                  >> is less useful and/or unwanted?<br>
                  >><br>
                  >> On Wed, Jul 5, 2017 at 10:30 PM, Hal Finkel
                  <<a moz-do-not-send="true"
                    href="mailto:hfinkel@anl.gov" target="_blank">hfinkel@anl.gov</a>>
                  wrote:<br>
                  >>><br>
                  >>><br>
                  >>> On 07/05/2017 03:10 PM, Alexandre Isoard
                  wrote:<br>
                  >>><br>
                  >>> Ah, ok. I read it wrong. In *neither*
                  case it is UB.<br>
                  >>><br>
                  >>> Hum, can an implementation define it as
                  UB? :-)<br>
                  >>><br>
                  >>><br>
                  >>> Nope :-)<br>
                  >>><br>
                  >>> The only case I've thought of where we
                  could add these for C++ would be<br>
                  >>> on conversions to (most) enums (because
                  they used signed underlying types<br>
                  >>> and the out-of-bounds mapping won't
                  generally be one of the allowed values<br>
                  >>> (or maybe we can define this to be the
                  case?)).<br>
                  >>><br>
                  >>>  -Hal<br>
                  >>><br>
                  >>><br>
                  >>><br>
                  >>> On Wed, Jul 5, 2017 at 9:09 PM, Alexandre
                  Isoard<br>
                  >>> <<a moz-do-not-send="true"
                    href="mailto:alexandre.isoard@gmail.com"
                    target="_blank">alexandre.isoard@gmail.com</a>>
                  wrote:<br>
                  >>>><br>
                  >>>><br>
                  >>>><br>
                  >>>> On Wed, Jul 5, 2017 at 3:59 PM, Hal
                  Finkel via llvm-dev<br>
                  >>>> <<a moz-do-not-send="true"
                    href="mailto:llvm-dev@lists.llvm.org"
                    target="_blank">llvm-dev@lists.llvm.org</a>>
                  wrote:<br>
                  >>>>><br>
                  >>>>><br>
                  >>>>> On 07/04/2017 01:41 AM, Dr.-Ing.
                  Christoph Cullmann via llvm-dev wrote:<br>
                  >>>>>><br>
                  >>>>>> Hi,<br>
                  >>>>>><br>
                  >>>>>>> Hi Alexandre,<br>
                  >>>>>>><br>
                  >>>>>>> LLVM currently doesn't
                  have trunc nsw/nuw, no.<br>
                  >>>>>>> Which frontend would emit
                  such instructions? Any application in mind?<br>
                  >>>>>>> Just asking because if no
                  frontend could emit those, then the<br>
                  >>>>>>> motivation to<br>
                  >>>>>>> add nsw/nuw support to
                  trunc would be very low I guess.<br>
                  >>>>>><br>
                  >>>>>> I think the clang frontend
                  could use that to allow better static<br>
                  >>>>>> analysis of integer overflows<br>
                  >>>>>> on the LLVM IR.<br>
                  >>>>>><br>
                  >>>>>> It might be interesting for
                  static analysis tools that want to know if<br>
                  >>>>>> you truncate something<br>
                  >>>>>> that is too large for the
                  target range but you need the sign to<br>
                  >>>>>> determine, e.g. the C/C++
                  frontend<br>
                  >>>>>> could use that flag for trunc
                  of signed/unsigned integers, then you<br>
                  >>>>>> could e.g. check if<br>
                  >>>>>><br>
                  >>>>>> (uint8_t)x<br>
                  >>>>>><br>
                  >>>>>> changes the values if x has
                  stuff out of the 0..255 range.<br>
                  >>>>>><br>
                  >>>>>> e.g. x as int with -100 =>
                  trunc nuw to 8 => bad<br>
                  >>>>>><br>
                  >>>>>> (int8_t)x<br>
                  >>>>>><br>
                  >>>>>>    => trunc nsw to 8 =>
                  ok<br>
                  >>>>><br>
                  >>>>><br>
                  >>>>> I'm not sure that a C/C++
                  frontend could add this flag. In C++, the<br>
                  >>>>> conversion for unsigned types is
                  specified and for signed types, it's<br>
                  >>>>> implementation defined, but in
                  neither case is it UB.<br>
                  >>>><br>
                  >>>><br>
                  >>>> Hmm, I don't get it.<br>
                  >>>><br>
                  >>>> Two questions:<br>
                  >>>> - if the conversion for unsigned
                  types is specified, how is it undefined<br>
                  >>>> behavior?<br>
                  >>>> - if the conversion for signed types
                  is UB, then this is a direct<br>
                  >>>> application of those flags, isn't it?<br>
                  >>>><br>
                  >>>>>  -Hal<br>
                  >>>>><br>
                  >>>>><br>
                  >>>>>><br>
                  >>>>>> Greetings<br>
                  >>>>>> Christoph<br>
                  >>>>>><br>
                  >>>>>>> Thanks,<br>
                  >>>>>>> Nuno<br>
                  >>>>>>><br>
                  >>>>>>> -----Original
                  Message-----<br>
                  >>>>>>> From: Alexandre Isoard
                  via llvm-dev<br>
                  >>>>>>> Sent: Monday, July 3,
                  2017 8:38 PM<br>
                  >>>>>>> To: llvm-dev<br>
                  >>>>>>> Subject: [llvm-dev] trunc
                  nsw/nuw?<br>
                  >>>>>>><br>
                  >>>>>>><br>
                  >>>>>>> Hello,<br>
                  >>>>>>><br>
                  >>>>>>>  From [1], trunc does not
                  seems to have a nsw/nuw attribute.<br>
                  >>>>>>> Is it possible to have
                  that? Or do we have that and it is not<br>
                  >>>>>>> up-to-date?<br>
                  >>>>>>><br>
                  >>>>>>> The definition would be:<br>
                  >>>>>>><br>
                  >>>>>>> If the nuw keyword is
                  present, the result value of the trunc is a<br>
                  >>>>>>> poison<br>
                  >>>>>>> value if the truncated
                  high order bits are non-zero. If the nsw<br>
                  >>>>>>> keyword is<br>
                  >>>>>>> present, the result value
                  of the trunc is a poison value if the<br>
                  >>>>>>> truncated<br>
                  >>>>>>> high order bits are not
                  all equal to the non-truncated bit of the<br>
                  >>>>>>> highest<br>
                  >>>>>>> order.<br>
                  >>>>>>><br>
                  >>>>>>> This allow to cancel out:<br>
                  >>>>>>> - sext with trunc nsw<br>
                  >>>>>>> - zext with trunc nuw<br>
                  >>>>>>><br>
                  >>>>>>> And probably to commute
                  with add/sub/mul/lshr/ashr/shl/urem<wbr>/udiv/udiv<br>
                  >>>>>>> (with<br>
                  >>>>>>> the correct flags).<br>
                  >>>>>>><br>
                  >>>>>>> [1]: <a
                    moz-do-not-send="true"
                    href="http://llvm.org/docs/LangRef.html#trunc-to-instruction"
                    rel="noreferrer" target="_blank">http://llvm.org/docs/LangRef.h<wbr>tml#trunc-to-instruction</a><br>
                  >>>>>>><br>
                  >>>>>>><br>
                  >>>>>>> --<br>
                  >>>>>>><br>
                  >>>>>>> Alexandre Isoard<br>
                  >>>>>>><br>
                  >>>>>>>
                  ______________________________<wbr>_________________<br>
                  >>>>>>> LLVM Developers mailing
                  list<br>
                  >>>>>>> <a
                    moz-do-not-send="true"
                    href="mailto:llvm-dev@lists.llvm.org"
                    target="_blank">llvm-dev@lists.llvm.org</a><br>
                  >>>>>>> <a
                    moz-do-not-send="true"
                    href="http://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-dev"
                    rel="noreferrer" target="_blank">http://lists.llvm.org/cgi-bin/<wbr>mailman/listinfo/llvm-dev</a><br>
                  >>>>><br>
                  >>>>><br>
                  >>>>> --<br>
                  >>>>> Hal Finkel<br>
                  >>>>> Lead, Compiler Technology and
                  Programming Languages<br>
                  >>>>> Leadership Computing Facility<br>
                  >>>>> Argonne National Laboratory<br>
                  >>>>><br>
                  >>>>><br>
                  >>>>> ______________________________<wbr>_________________<br>
                  >>>>> LLVM Developers mailing list<br>
                  >>>>> <a moz-do-not-send="true"
                    href="mailto:llvm-dev@lists.llvm.org"
                    target="_blank">llvm-dev@lists.llvm.org</a><br>
                  >>>>> <a moz-do-not-send="true"
                    href="http://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-dev"
                    rel="noreferrer" target="_blank">http://lists.llvm.org/cgi-bin/<wbr>mailman/listinfo/llvm-dev</a><br>
                  >>>><br>
                  >>>><br>
                  >>>><br>
                  >>>><br>
                  >>>> --<br>
                  >>>> Alexandre Isoard<br>
                  >>><br>
                  >>><br>
                  >>><br>
                  >>><br>
                  >>> --<br>
                  >>> Alexandre Isoard<br>
                  >>><br>
                  >>><br>
                  >>> --<br>
                  >>> Hal Finkel<br>
                  >>> Lead, Compiler Technology and Programming
                  Languages<br>
                  >>> Leadership Computing Facility<br>
                  >>> Argonne National Laboratory<br>
                  >><br>
                  >><br>
                  >><br>
                  >><br>
                  >> --<br>
                  >> Alexandre Isoard<br>
                  >><br>
                  >> ______________________________<wbr>_________________<br>
                  >> LLVM Developers mailing list<br>
                  >> <a moz-do-not-send="true"
                    href="mailto:llvm-dev@lists.llvm.org"
                    target="_blank">llvm-dev@lists.llvm.org</a><br>
                  >> <a moz-do-not-send="true"
                    href="http://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-dev"
                    rel="noreferrer" target="_blank">http://lists.llvm.org/cgi-bin/<wbr>mailman/listinfo/llvm-dev</a><br>
                  >><br>
                  ><br>
                  ><br>
                  > --<br>
                  > Hal Finkel<br>
                  > Lead, Compiler Technology and Programming
                  Languages<br>
                  > Leadership Computing Facility<br>
                  > Argonne National Laboratory<br>
                  ><br>
                  ><br>
                  > ______________________________<wbr>_________________<br>
                  > LLVM Developers mailing list<br>
                  > <a moz-do-not-send="true"
                    href="mailto:llvm-dev@lists.llvm.org"
                    target="_blank">llvm-dev@lists.llvm.org</a><br>
                  > <a moz-do-not-send="true"
                    href="http://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-dev"
                    rel="noreferrer" target="_blank">http://lists.llvm.org/cgi-bin/<wbr>mailman/listinfo/llvm-dev</a><br>
                  ><br>
                </div>
              </div>
            </blockquote>
          </div>
          <br>
          <br clear="all">
          <div><br>
          </div>
          -- <br>
          <div
            class="m_7273905502421364517m_2468478144792101895gmail_signature"
            data-smartmail="gmail_signature">
            <div dir="ltr"><b>Alexandre Isoard</b><br>
            </div>
          </div>
        </div>
      </div>
    </blockquote>
    <br>
    <pre class="moz-signature" cols="72">-- 
Hal Finkel
Lead, Compiler Technology and Programming Languages
Leadership Computing Facility
Argonne National Laboratory</pre>
  </body>
</html>