<html>
  <head>
    <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
  </head>
  <body smarttemplateinserted="true">
    <div id="smartTemplate4-template">Hi,<br>
      <br>
      <p> </p>
      <blockquote type="cite">
        <div><br>
        </div>
        <div>
          <blockquote type="cite"> Procedure ManagedMove<T>(const
            source: T;var dest: T;count: SizeInt);</blockquote>
        </div>
        <br>
        <div dir="auto">In principle a good idea. However this is one of
          those cases where you'd definitely need to use constref
          instead of const.</div>
      </blockquote>
      <p><br>
      </p>
      <p>Or var, since the source might be cleared<br>
      </p>
      <p>
        <blockquote type="cite">
          <div dir="auto">
            <div class="gmail_quote">
              <blockquote class="gmail_quote" style="margin:0 0 0
                .8ex;border-left:1px #ccc solid;padding-left:1ex">
                <div>
                  <div>
                    <p>And perhaps there could be a special attribute to
                      mark which kind of moving is needed, e.g..<br>
                    </p>
                      type [moveable] TA = record<br>
                    <div>
                      <div> </div>
                    </div>
                      type [referencecounted] TA = record</div>
                  <div>   type [nonmoveable] TA = record<br>
                  </div>
                </div>
              </blockquote>
            </div>
          </div>
          <div dir="auto"><br>
          </div>
          <div dir="auto">No, thank you.</div>
          <div dir="auto"><br>
          </div>
        </blockquote>
         </p>
      <p>But it could help a lot with optimizations. For moveable types
        it could omit calling an assignment function and just do a
        memory copy; and for refcounted tyes it could that when the
        number of references does not change. <br>
      </p>
      <p><br>
      </p>
      <p><br>
      </p>
      <p>Like a simple swap function:</p>
      <p>procedure stringSwap(var a, b: string);<br>
        var t: string;<br>
        begin<br>
          t := a;<br>
          a := b;<br>
          b := t;<br>
        end;<br>
      </p>
      <p>A smart compiler could detect that it is a refcounted type and
        the number of references stays the same, and thus optimize it
        into:</p>
      <p>    mov    (%rdi),%rax<br>
            mov    (%rsi),%rdx<br>
            mov    %rdx,(%rdi)<br>
            mov    %rax,(%rsi)<br>
            retq   <br>
        <br>
      </p>
      <p>But FPC turns it into:</p>
      <p>    begin<br>
            push   %rbx<br>
            push   %r12<br>
            lea    -0x68(%rsp),%rsp<br>
            mov    %rdi,%rbx<br>
            mov    %rsi,%r12<br>
            movq   $0x0,(%rsp)<br>
            lea    0x8(%rsp),%rdx<br>
            lea    0x20(%rsp),%rsi<br>
            mov    $0x1,%edi<br>
            callq  0x4324c0 <fpc_pushexceptaddr><br>
            mov    %rax,%rdi<br>
            callq  0x41fba0 <fpc_setjmp><br>
            movslq %eax,%rdx<br>
            mov    %rdx,0x60(%rsp)<br>
            test   %eax,%eax<br>
            jne    0x469191 <STRINGSWAP+97><br>
            t := a;<br>
            mov    (%rbx),%rsi<br>
            mov    %rsp,%rdi<br>
            callq  0x428d00 <fpc_ansistr_assign><br>
            a := b;<br>
            mov    (%r12),%rsi<br>
            mov    %rbx,%rdi<br>
            callq  0x428d00 <fpc_ansistr_assign><br>
            b := t;<br>
            mov    (%rsp),%rsi<br>
            mov    %r12,%rdi<br>
            callq  0x428d00 <fpc_ansistr_assign><br>
            callq  0x432830 <fpc_popaddrstack><br>
            end;<br>
            mov    %rsp,%rdi<br>
            callq  0x428ca0 <fpc_ansistr_decr_ref><br>
            mov    0x60(%rsp),%rax<br>
            test   %rax,%rax<br>
            je     0x4691b8 <STRINGSWAP+136><br>
            callq  0x4329e0 <fpc_reraise><br>
            movq   $0x0,0x60(%rsp)<br>
            jmp    0x469191 <STRINGSWAP+97><br>
            lea    0x68(%rsp),%rsp<br>
            pop    %r12<br>
            pop    %rbx<br>
            retq   <br>
        <br>
      </p>
      <p><br>
      </p>
      <blockquote type="cite"><br>
        Then you want to simply use ismanagedtype and move().  Moving
        the move() to a separate generic procedure will only lead to
        many instantiations of what is basically a move() procedure. <br>
      </blockquote>
    </div>
    <div><br>
    </div>
    <div>The goal is to reduce instantiations. <br>
    </div>
    <div>If there are n generic (collection) classes, C1, C2, .., Cn,
      and k types used in the collections, T1, T2, .. Tk, there are n*k
      collection class instantiation C1<T1>, C1<T2>, ..
      C1<Tk>, C2<T1>, ... Cn<Tk></div>
    <div>If each collection class does its own
      Finalize-Loop/Move/Fillchar there are also n*k of these move
      implementations. So like 3*n*k calls.<br>
    </div>
    <div>When any collection can call the same ManagedMove, there should
      only be k ManagedMove instantiations and n*k calls to ManagedMove,
      which is only one call. So it is k + n*k calls,  which is around a
      third of 3*n*k<br>
    </div>
    <div> <br>
      Bye,<br>
      Benito </div>
    <div class="moz-cite-prefix">On 11.01.21 18:51, Sven Barth via
      fpc-pascal wrote:<br>
    </div>
    <blockquote type="cite"
cite="mid:CAFMUeB9mKSDANQnwUWOa-SRsBrBmHjYLxDXcH9QtZgVjOZy-1Q@mail.gmail.com">
      <meta http-equiv="content-type" content="text/html; charset=UTF-8">
      <div dir="auto">
        <div>
          <div class="gmail_quote">
            <div dir="ltr" class="gmail_attr">Benito van der Zander via
              fpc-pascal <<a
                href="mailto:fpc-pascal@lists.freepascal.org"
                moz-do-not-send="true">fpc-pascal@lists.freepascal.org</a>>
              schrieb am Mo., 11. Jan. 2021, 15:26:<br>
            </div>
            <blockquote class="gmail_quote" style="margin:0 0 0
              .8ex;border-left:1px #ccc solid;padding-left:1ex">
              <div>
                <div id="m_926231055581021927smartTemplate4-template">Hi,</div>
                <div><br>
                </div>
                <div>perhaps a  safe, generic function for this copying
                  could be added to the RTL. Like:<br>
                </div>
                <div><br>
                </div>
                <div> Procedure ManagedMove<T>(const source: T;var
                  dest: T;count: SizeInt);</div>
              </div>
            </blockquote>
          </div>
        </div>
        <div dir="auto"><br>
        </div>
        <div dir="auto">In principle a good idea. However this is one of
          those cases where you'd definitely need to use constref
          instead of const.</div>
        <div dir="auto"><br>
        </div>
        <div dir="auto">
          <div class="gmail_quote">
            <blockquote class="gmail_quote" style="margin:0 0 0
              .8ex;border-left:1px #ccc solid;padding-left:1ex">
              <div>
                <div>And when you use IsManagedType, it does not
                  distinguish standard strings with such weird managed
                  types.<br>
                </div>
              </div>
            </blockquote>
          </div>
        </div>
        <div dir="auto"><br>
        </div>
        <div dir="auto">You can additionally use GetTypeKind as well.
          Unlike TypeInfo it directly returns the TTypeKind (which for
          this case is enough) and is considered constant. </div>
        <div dir="auto"><br>
        </div>
        <div dir="auto">
          <div class="gmail_quote">
            <blockquote class="gmail_quote" style="margin:0 0 0
              .8ex;border-left:1px #ccc solid;padding-left:1ex">
              <div>
                <div>
                  <p>And perhaps there could be a special attribute to
                    mark which kind of moving is needed, e.g..<br>
                  </p>
                    type [moveable] TA = record<br>
                  <div>
                    <div> </div>
                  </div>
                    type [referencecounted] TA = record</div>
                <div>   type [nonmoveable] TA = record<br>
                </div>
              </div>
            </blockquote>
          </div>
        </div>
        <div dir="auto"><br>
        </div>
        <div dir="auto">No, thank you.</div>
        <div dir="auto"><br>
        </div>
        <div dir="auto">Regards, </div>
        <div dir="auto">Sven </div>
      </div>
      <br>
      <fieldset class="mimeAttachmentHeader"></fieldset>
      <pre class="moz-quote-pre" wrap="">_______________________________________________
fpc-pascal maillist  -  <a class="moz-txt-link-abbreviated" href="mailto:fpc-pascal@lists.freepascal.org">fpc-pascal@lists.freepascal.org</a>
<a class="moz-txt-link-freetext" href="https://lists.freepascal.org/cgi-bin/mailman/listinfo/fpc-pascal">https://lists.freepascal.org/cgi-bin/mailman/listinfo/fpc-pascal</a>
</pre>
    </blockquote>
  </body>
</html>