Loop unrolling + fusion ?
Simon Marlow
marlowsd at gmail.com
Mon Mar 9 11:14:07 EDT 2009
Claus Reinke wrote:
>>> That was one of my questions in the optimization and rewrite rules
>>> thread: shouldn't -fvia-C be supported (as a non-default option)
>>> for at least as long as the alternative isn't a clear win in all cases?
>>
>> The trouble with supporting multiple backends is that the cost in
>> terms of testing and maintenance is high. And the registerised
>> -fvia-C backend is particularly nasty, coming as it does with
>> thousands of lines of Perl 4 that regularly get broken by new versions
>> of gcc.
>
> Yes, I can understand that you'd like to leave that part behind sometime
> before yesterday:-) I assume that this very complexity means that the
> -fvia-C route doesn't really get all the way to its most interesting
> promises (easy portability, and full backend optimizations inherited
> from gcc). And with that in mind, I can also understand that you don't
> want to put in any further work into trying to improve it, if that
> distracts from a better long-term solution.
> What I don't understand yet is the routemap for replacing -fvia-C. We've
> seen -fvia-C being demoted from default to backup (fine by me), we've
> seen a feature supported only by -fvia-C removed completely, instead of
> seeing support for it added to the -fasm route (macro-based APIs
> used to work with ffi, would now require a wrapper generator, which
> doesn't exist yet).
> Indications are that -fvia-C still tends to produce better code (even
> though it is not the best that ghc+gcc could produce) than -fasm (is
> that any better for the new backend?). And last, but not least, ghc has
> more limited resources than gcc, so how is ghc going to beat gcc at the
> portability and backend optimizations game while still making progress
> in its core competencies (ie, higher-level improvements; there's also
> the interesting side-issue of how the two stages of optimizations are
> going to interact in ghc, if there is a barrier that can only be crossed
> in one direction)?
Ok, thanks for bringing these points up. Hopefully I'll be able to lay
your fears to rest:
1. Performance.
-fvia-c currently produces code that is on average about 1% faster than -fasm:
http://www.cse.unsw.edu.au/~dons/nobench/x86_64/results.html
There's one notable exception: floating-point code on x86 (not x86_64) is
terrible with -fasm, because our native code generator has a particularly
simple/stupid implementation of the x87 instruction set. So we need to
make the SSE2 code generator in the x86_64 backend work for x86, too.
Having said that, the native backend has much more potential for generating
faster code than we can with gcc. Firstly, it can re-use fixed registers
(e.g. argument registers) within a basic block, whereas gcc can't. We
don't do this currently because the C-- lacks the liveness information on
jumps, but the new backend will be able to do it. I bet this alone will be
worth more than that 1%. Secondly we have a much better handle on aliasing
inside GHC than gcc does, and there's no good way to tell gcc what we know
about aliasing.
On x86, gcc has a grand total of 2 spare registers, which means it has
virtually no scope for generating good code. There's also not much room
for generating C that is more amenable to gcc's optimisations. The obvious
thing to do is to make recursive functions look like loops. We've tried it
(there's some experimental code in GHC to do it), IIRC it didn't buy very
much. The lack of registers, and the lack of knowledge about aliasing
(heap doesn't alias with stack) meant that gcc didn't do some
obvious-looking optimisations. Trying to do better here is a dead end.
2. Portability.
We haven't had a single new registerised port of GHC in many years now.
While the via-C backend seems at first glance to offer some portability
benefits, in practice porting the mangler is still a pain unless your
platform is very similar to an existing one (e.g. vanilla ELF).
The only C-only registerised port we had was Sparc, and thanks to Ben
Lippmeier we now have a native backend for that too. Dropping the C
backend won't harm any of our existing ports, and it doesn't seem like
people are making new ports of GHC this way either.
We'll still have the unregisterised porting route, whose only drawback is
performance. Still, lots of platforms are successfully using
unregisterised GHC ports (via Debian).
One day maybe we'll have an LLVM backend, or similar. My impression is
that right now we can't make an LLVM backend with as good performance as
our native backend, without changes in LLVM. Maybe that will change.
Nothing that we're doing now precludes adding an LLVM backend later, I believe.
3. Features.
This is a non-issue: -fvia-C vs. -fasm should not affect what programs
work. Up until 6.10.1 we had a bug whereby you could use -fvia-C to bind
to CPP-based C APIs, but that bug was removed in 6.10.1. Ok, I realise
that some people considered this to be a feature and its removal to be a
regression. However, I believe it's more important that we conform to the
FFI spec, and for -fasm to be consistent with -fvia-C.
It's a slight inconvenience to have to write the wrappers, but in return
you get more robust code. Of course we should have tool support to make
generating the wrappers easier.
Cheers,
Simon
More information about the Glasgow-haskell-users
mailing list