<div dir="ltr">Thanks for your reply Andreas.<div><br></div><div>Just some further thoughts, perhaps we don't even require inline.</div><div><br></div><div>Correct me if I'm wrong, but couldn't we compile even functions with levity polymorphic arguments by just boxing all the arguments?</div><div><br></div><div>This would also mean the caller would have to box arguments before passing. </div><div><br></div><div>You'd also need to box any working variables inside the function with levity other than `Type`. </div><div><br></div><div>This to a certain extent defeats the purpose of levity polymorphism when it's intended as an optimisation to avoid boxed types, but it does give a fallback we can always use. </div><div><br></div><div>Yes, if you inline you can get code bloat. But that's a risk when you inline any function. </div><div><br></div><div>Cheers,</div><div>Clinton</div></div><br><div class="gmail_quote"><div dir="ltr" class="gmail_attr">On Fri, Oct 8, 2021 at 11:39 PM Andreas Klebinger <<a href="mailto:klebinger.andreas@gmx.at">klebinger.andreas@gmx.at</a>> wrote:<br></div><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left:1px solid rgb(204,204,204);padding-left:1ex">
  
    
  
  <div>
    <p>Hey Clinton,<br>
      <br>
      I think the state of things is best summarised it's in principle
      possible to implement. But it's unclear how best to do so<br>
      or even if it's worth having this feature at all.<br>
    </p>
    <p>The biggest issue being code bloat.</p>
    <p>As you say a caller could create it's own version of the function
      with the right kind of argument type.<br>
      But that means duplicating the function for every use site
      (although some might be able to be commoned up). Potentially
      causing a lot of code<br>
      bloat and compile time overhead.<br>
    </p>
    <p>In a similar fashion we could create each potential version we
      need from the get go to avoid duplicating the same function.<br>
      But that runs the risk of generating far more code than what is
      actually used.<br>
      <br>
      Last but not least GHC currently doesn't always load unfoldings.
      In particular if you compile a module with optimizations disabled
      the RHS is currently *not*<br>
      available to the compiler when looking at the use site. There
      already is a mechanism to bypass this in GHC where a function
      *must* be inlined (compulsory unfoldings).<br>
      But it's currently reserved for built in functions. We could just
      make INLINE bindings compulsory if they have levity-polymorphic
      arguments sure. But again it's not clear<br>
      this is really desireable.<br>
    </p>
    <p>I don't think this has to mean we couldn't change how things work
      to accomodate levity-polymorphic arguments. It just seems it's
      unclear what a good design<br>
      would look like and if it's worth having.</p>
    <p>Cheers<br>
      Andreas<br>
    </p>
    <div>Am 08/10/2021 um 01:36 schrieb Clinton
      Mead:<br>
    </div>
    <blockquote type="cite">
      
      <div dir="ltr">
        <div>Hi All</div>
        <div><br>
        </div>
        <div>Not sure if this belongs in ghc-users or ghc-devs, but it
          seemed devy enough to put it here. </div>
        <div><br>
        </div>
        <div><a href="https://downloads.haskell.org/~ghc/9.0.1/docs/html/users_guide/exts/levity_polymorphism.html" target="_blank">Section 6.4.12.1</a> of the GHC user
          manual points out, if we allowed levity polymorphic arguments,
          then we would have no way to compile these functions, because
          the code required for different levites is different. </div>
        <div><br>
        </div>
        <div>However, if such a function is <font face="monospace">{-#
            INLINE #-}</font> or<font face="monospace"> {-# INLINABLE
            #-}</font> there's no need to compile it as it's full
          definition is in the interface file. Callers can just compile
          it themselves with the levity they require. Indeed callers of
          inline functions already compile their own versions even
          without levity polymorphism (for example, presumably inlining
          function calls that are known at compile time).</div>
        <div><br>
        </div>
        <div>The only sticking point to this that I could find was that <a href="https://downloads.haskell.org/ghc/9.0.1/docs/html/users_guide/exts/pragmas.html#inline-pragma" target="_blank">GHC will only inline the function if
            it is fully applied</a>, which suggests that the possibility
          of partial application means we can't inline and hence need a
          compiled version of the code. But this seems like a silly
          restriction, as we have the full RHS of the definition in the
          interface file. The caller can easily create and compile it's
          own partially applied version. It should be able to do this
          regardless of levity. </div>
        <div><br>
        </div>
        <div>It seems to me we're okay as long as the following three
          things aren't true simultaneously:</div>
        <div><br>
        </div>
        <div>1. Blah has levity polymorphic arguments</div>
        <div>2. Blah is exported</div>
        <div>3. Blah is not inline</div>
        <div><br>
        </div>
        <div>If a function "Blah" is not exported, we shouldn't care
          about levity polymorphic arguments, because we have it's RHS
          on hand in the current module and compile it as appropriate.
          And if it's inline, we're exposing it's full RHS to other
          callers so we're still fine also. Only when these three
          conditions combine should we give an error, say like:</div>
        <div><br>
        </div>
        <div>"Blah has levity polymorphic arguments, is exported, and is
          not inline. Please either remove levity polymorphic arguments,
          not export it or add an  <font face="monospace">{-# INLINE #-}</font> or<font face="monospace"> {-# INLINABLE #-}</font> pragma.</div>
        <div><br>
        </div>
        <div>I presume however there are some added complications that I
          don't understand, and I'm very interested in what they are as
          I presume they'll be quite interesting. </div>
        <div><br>
        </div>
        <div>Thanks,<br>
          Clinton</div>
        <div><br>
        </div>
      </div>
      <br>
      <fieldset></fieldset>
      <pre>_______________________________________________
ghc-devs mailing list
<a href="mailto:ghc-devs@haskell.org" target="_blank">ghc-devs@haskell.org</a>
<a href="http://mail.haskell.org/cgi-bin/mailman/listinfo/ghc-devs" target="_blank">http://mail.haskell.org/cgi-bin/mailman/listinfo/ghc-devs</a>
</pre>
    </blockquote>
  </div>

</blockquote></div>