#3607: index variable for array traversal worker function is not unboxed
-----------------------------------+----------------------------------------
Reporter: blarsen | Owner:
Type: bug | Status: closed
Priority: normal | Milestone:
Component: Compiler | Version: 6.10.4
Severity: normal | Resolution: worksforme
Keywords: unboxed array, Ord | Difficulty: Unknown
Testcase: | Os: Unknown/Multiple
Architecture: Unknown/Multiple |
-----------------------------------+----------------------------------------
Changes (by simonpj):
* status: new => closed
* difficulty: => Unknown
* resolution: => worksforme
Comment:
With HEAD the inner loop looks like this:
{{{
$wgo_sE2 [Occ=LoopBreaker]
:: GHC.Prim.Int# -> GHC.Ordering.Ordering
[LclId, Arity=1, Str=DmdType L]
$wgo_sE2 =
\ (ww6_sD3 :: GHC.Prim.Int#) ->
case GHC.Prim.==# ww6_sD3 ww5_sCY of _ {
GHC.Bool.False ->
let {
i_sE4 :: GHC.Types.Int
[LclId]
i_sE4 = GHC.Types.I# ww6_sD3 } in
case GHC.Classes.compare
@ e_aos
w1_sDx
(ww2_sDh @ i_aou w_sDw w2_sDy i_sE4)
(ww4_sDr @ i_aou w_sDw w3_sDz i_sE4)
of _ {
GHC.Ordering.LT -> GHC.Ordering.LT;
GHC.Ordering.EQ -> $wgo_sE2 (GHC.Prim.+# ww6_sD3
1);
GHC.Ordering.GT -> GHC.Ordering.GT
};
GHC.Bool.True -> GHC.Ordering.EQ
}}}
So the parameter is unboxed, but alas it's boxed every time, and
necessarily so, in order to pass it to the (higher-order) indexing
operations.
If you specialise to a particular type, say
{{{
{-# SPECIALISE cmpArrays :: Ord e => Array Int e -> Array Int e ->
Ordering #-}
}}}
the inner loop seems reasonable (no boxing):
{{{
letrec {
$wgo_sGY [Occ=LoopBreaker]
:: GHC.Prim.Int# -> GHC.Ordering.Ordering
[LclId, Arity=1, Str=DmdType L]
$wgo_sGY =
\ (ww8_sFl :: GHC.Prim.Int#) ->
case GHC.Prim.==# ww8_sFl ww2_sFz of _ {
GHC.Bool.False ->
case GHC.Classes.compare
@ e_aB3
w_sFr
(case GHC.Prim.indexArray# @ e_aB3
ww3_sFA ww8_sFl
of _ { (# e_aEf #) ->
e_aEf
})
(case GHC.Prim.indexArray# @ e_aB3
ww7_sFK ww8_sFl
of _ { (# e_aEf #) ->
e_aEf
})
of _ {
GHC.Ordering.LT -> GHC.Ordering.LT;
GHC.Ordering.EQ -> $wgo_sGY (GHC.Prim.+#
ww8_sFl 1);
GHC.Ordering.GT -> GHC.Ordering.GT
};
GHC.Bool.True -> GHC.Ordering.EQ
}; } in
$wgo_sGY 0
}}}
An INLINE pragma will do the same, albeit at every call site.
I'll close this ticket, but do re-open it if you think there's still an
issue.
(I have not checked 6.12, but I don't think we'll fix that anyway, even if
it doesn't generate as good code.)
Simon
--
Ticket URL: <http://hackage.haskell.org/trac/ghc/ticket/3607#comment:1>
GHC <http://www.haskell.org/ghc/>
The Glasgow Haskell Compiler_______________________________________________
Glasgow-haskell-bugs mailing list
[email protected]
http://www.haskell.org/mailman/listinfo/glasgow-haskell-bugs