GHC 6.8.1 SpecConstr

Simon Peyton-Jones simonpj at microsoft.com
Thu Nov 15 03:57:17 EST 2007


Urk.  Well spotted!

I omitted a prime (writing env instead of env') in a late fix, and as a result practically no top-level rules and specialisations are being applied.

What an egregious bug. The good news is that a one-character fix should make 6.8.2 perform quite a bit better than 6.8.1!

Simon


| -----Original Message-----
| From: glasgow-haskell-users-bounces at haskell.org [mailto:glasgow-haskell-users-bounces at haskell.org] On Behalf Of
| kenny lu
| Sent: 15 November 2007 06:49
| To: glasgow-haskell-users at haskell.org
| Subject: GHC 6.8.1 SpecConstr
|
| Hi,
|
| Recall the example from Simon's paper appearing in ICFP 2007.
|
| myLast :: [a] -> a
| myLast [] = error ""
| myLast [x] = x
| myLast (x:xs) = myLast xs
|
| which returns the last element in a list.
|
| Applying the idea in the paper, we should rewrite the function
| as follows,
|
| myLast :: [a] -> a
| myLast [] = error ""
| myLast (x:xs) = myLast' x xs
|     where myLast' x [] = x
|           myLast' x (y:ys) = myLast' y ys
|
| which avoids redundant pattern tests.
|
|
| We tried to compile the "unspecialized" version of myLast function
| with GHC 6.8.1
| with -O2 -ddump-simpl flags and observe the core code as follows,
|
| ==================== Tidy Core ====================
| lvl_r72 :: forall a_a5P. a_a5P
| [GlobalId]
| [Str: DmdType b]
| lvl_r72 = \ (@ a_a5P) -> GHC.Err.error @ a_a5P (GHC.Base.[] @ GHC.Base.Char)
|
| Rec {
| Last.$smyLast :: forall a_a5P. a_a5P -> [a_a5P] -> a_a5P
| [GlobalId]
| [Arity 2]
| Last.$smyLast =
|   \ (@ a_a5P) (ipv_s6i :: a_a5P) (ipv1_s6j :: [a_a5P]) ->
|     case ipv1_s6j of wild_X9 {
|       [] -> ipv_s6i; : ipv2_X6p ipv3_X6r -> Last.myLast @ a_a5P wild_X9
|     }
| Last.myLast :: forall a_a5B. [a_a5B] -> a_a5B
| [GlobalId]
| [Arity 1
|  Str: DmdType S]
| Last.myLast =
|   \ (@ a_a5P) (ds_d68 :: [a_a5P]) ->
|     case ds_d68 of wild_B1 {
|       [] -> lvl_r72 @ a_a5P;
|       : x_a5I ds1_d69 ->
|         case ds1_d69 of wild1_X9 {
|           [] -> x_a5I; : ipv_s6i ipv1_s6j -> Last.myLast @ a_a5P wild1_X9
|         }
|     }
| end Rec }
|
|
|
|
| ==================== Tidy Core Rules ====================
| "SC:Last.myLast0" [0]
|     forall {@ a_a5P ipv_s6i :: a_a5P ipv1_s6j :: [a_a5P]}
|       Last.myLast @ a_a5P (GHC.Base.: @ a_a5P ipv_s6i ipv1_s6j)
|       = Last.$smyLast @ a_a5P ipv_s6i ipv1_s6j
|
| It seems that $smyLast is the specialized version of myLast
| And the last tidy core rule says that we should replace the
| application  (myLast (x:xs))
| by  ($smyLast x xs).
|
| We are surprised by the development of the second pattern of $smyLast.
| In the second pattern, function myLast is applied to wild_X9 which is
| the reference of
| ipv_s6j.
|
| However, according to the running example,
| it seems to make more sense if this application is
| replaced by a recursive application ($smyLast ipv_3X6r) instead.
|
| Could you guys please enlighten me?
|
| Regards,
| Kenny
| _______________________________________________
| Glasgow-haskell-users mailing list
| Glasgow-haskell-users at haskell.org
| http://www.haskell.org/mailman/listinfo/glasgow-haskell-users


More information about the Glasgow-haskell-users mailing list