Skip to content


Subversion checkout URL

You can clone with
Download ZIP
Commits on Sep 23, 2011
  1. @simonpj

    Make a new type synonym CoreProgram = [CoreBind]

    simonpj authored
    and comment its invariants in Note [CoreProgram] in CoreSyn
    I'm not totally convinced that CoreProgram is the right name
    (perhaps CoreTopBinds might better), but it is useful to have
    a clue that you are looking at the top-level bindings.
    This is only a matter of a type synonym change; no deep
    refactoring here.
Commits on Sep 6, 2011
  1. @batterseapower

    Implement -XConstraintKind

    batterseapower authored
    Basically as documented in,
    this patch adds a new kind Constraint such that:
      Show :: * -> Constraint
      (?x::Int) :: Constraint
      (Int ~ a) :: Constraint
    And you can write *any* type with kind Constraint to the left of (=>):
    even if that type is a type synonym, type variable, indexed type or so on.
    The following (somewhat related) changes are also made:
     1. We now box equality evidence. This is required because we want
        to give (Int ~ a) the *lifted* kind Constraint
     2. For similar reasons, implicit parameters can now only be of
        a lifted kind. (?x::Int#) => ty is now ruled out
     3. Implicit parameter constraints are now allowed in superclasses
        and instance contexts (this just falls out as OK with the new
        constraint solver)
    Internally the following major changes were made:
     1. There is now no PredTy in the Type data type. Instead
        GHC checks the kind of a type to figure out if it is a predicate
     2. There is now no AClass TyThing: we represent classes as TyThings
        just as a ATyCon (classes had TyCons anyway)
     3. What used to be (~) is now pretty-printed as (~#). The box
        constructor EqBox :: (a ~# b) -> (a ~ b)
     4. The type LCoercion is used internally in the constraint solver
        and type checker to represent coercions with free variables
        of type (a ~ b) rather than (a ~# b)
Commits on Aug 3, 2011
  1. @simonpj

    Add Type.tyConAppTyCon_maybe and tyConAppArgs_maybe, and use them

    simonpj authored
    These turn out to be a useful special case of splitTyConApp_maybe.
    A refactoring only; no change in behaviour
Commits on Jul 15, 2011
  1. @simonpj

    Use varToCoreExpr rather than Var (fixes #5315)

    simonpj authored
    A coercion variable in a term must be wrapped in a coercion!
    (Led to lint errors.)
Commits on Apr 19, 2011
  1. @simonpj

    This BIG PATCH contains most of the work for the New Coercion Represe…

    simonpj authored
    See the paper "Practical aspects of evidence based compilation in System FC"
    * Coercion becomes a data type, distinct from Type
    * Coercions become value-level things, rather than type-level things,
      (although the value is zero bits wide, like the State token)
      A consequence is that a coerion abstraction increases the arity by 1
      (just like a dictionary abstraction)
    * There is a new constructor in CoreExpr, namely Coercion, to inject
      coercions into terms
Commits on Feb 14, 2011
  1. Better case-of-case transformation authored
    The ThunkSplitting idea in WorkWrap wasn't working at all,
    leading to Trac #4957.  The culprit is really the simplifier
    which was combining the wrong case continuations. See
    Note [Fusing case continuations] in Simplify.
Commits on Jan 28, 2011
  1. Fix an egregious strictness analyser bug (Trac #4924) authored
    The "virgin" flag was being threaded rather than treated
    like an environment.  As a result, the second and subsequent
    recursive definitions in a module were not getting a
    correctly-initialised fixpoint loop, causing much worse
    strictness analysis results.  Indeed the symptoms in
    Trac #4924 were quite bizarre.
    Anyway, it's easily fixed.  Merge to stable branch.
Commits on Jan 14, 2011
  1. Comments only authored
Commits on Nov 25, 2010
  1. Comment only authored
Commits on Oct 28, 2010
  1. Do w/w *recursive* things even if they are small authored
    A wibble to my previous change in WorkWrap, fixes simplrun010
Commits on Oct 27, 2010
  1. Don't worker-wrapper INLINABLE things authored
    See Note [Don't w/w INLINABLE things] in WorkWrap
    This fixes a bug that Milan found.
Commits on Oct 26, 2010
  1. Fix initialisation of strictness in the demand analyser authored
    Previously, the demand analyser assumed that every binder 
    starts off with no strictness info.  But now that we are
    preserving strictness on nesting bindings in interface files,
    that assumption is no longer correct, because an inlined function
    might have a nested binding with strictness set.
    So we need to know when we are in the initial sweep, so that we can
    set the strictness to 'bottom'. 
    See Note [Initialising strictness]
Commits on Sep 23, 2010
  1. Allow absent State# RealWorld arguments authored
  2. Rejig the absent-arg stuff for unlifted types authored
    This is what was giving the "absent entered" messages
    See Note [Absent errors] in WwLib.  We now return a 
    suitable literal for absent values of unlifted type.
Commits on Sep 15, 2010
  1. Implement INLINABLE pragma authored
    Implements Trac #4299.  Documentation to come.
Commits on Sep 14, 2010
  1. Make absent-arg wrappers work for unlifted types (fix Trac #4306) authored
    Previously we were simply passing arguments of unlifted
    type to a wrapper, even if they were absent, which was
    See Note [Absent error Id] in WwLib.
Commits on Sep 13, 2010
  1. Super-monster patch implementing the new typechecker -- at last authored
    This major patch implements the new OutsideIn constraint solving
    algorithm in the typecheker, following our JFP paper "Modular type
    inference with local assumptions".  
    Done with major help from Dimitrios Vytiniotis and Brent Yorgey.
Commits on May 5, 2010
  1. Make the demand analyser sdd demands for strict constructors authored
    This opportunity was spotted by Roman, and is documented in 
    Note [Add demands for strict constructors] in DmdAnal.
Commits on May 4, 2010
  1. Comments only authored
Commits on May 3, 2010
  1. @simonpj

    Make the demand analyser take account of lambda-bound unfoldings

    simonpj authored
    This is a long-standing lurking bug. See Note [Lamba-bound unfoldings]
    in DmdAnal.
    I'm still not really happy with this lambda-bound-unfolding stuff.
Commits on Jan 6, 2010
  1. Improve the handling of default methods authored
    See the long Note [INLINE and default methods].  
    This patch changes a couple of data types, with a knock-on effect on
    the format of interface files.  A lot of files get touched, but is a
    relatively minor change.  The main tiresome bit is the extra plumbing
    to communicate default methods between the type checker and the
Commits on Dec 18, 2009
  1. Move loop-breaker info from original function to worker in work/wrap authored
    When doing a w/w split, if the original function is a loop breaker
    then the worker (not the wrapper) becomes one instead.
    This isn't very important, because loop breaker information is
    recalculated afresh by the occurrence analyser, but it seems more
    kosher.  And Lint was bleating piteously about things with InlineRules
    that were loop breakers.
Commits on Dec 16, 2009
  1. Adjust Activations for specialise and work/wrap, and better simplify … authored
    …in InlineRules
    This patch does two main things:
    1. Adjusts the way we set the Activation for
       a) The wrappers generated by the strictness analyser
          See Note [Wrapper activation] in WorkWrap
       b) The RULEs generated by Specialise and SpecConstr
          See Note [Auto-specialisation and RULES] in Specialise
              Note [Transfer activation] in SpecConstr
    2. Refines how we set the phase when simplifying the right
       hand side of an InlineRule.  See
       Note [Simplifying inside InlineRules] in SimplUtils.
    Most of the extra lines are comments!  
    The merit of (2) is that a bit more stuff happens inside InlineRules,
    and that in turn allows better dead-code elimination.
Commits on Dec 11, 2009
  1. Improve strictness analysis for bottoming functions authored
    I found the following results from strictness analyis:
      f x = error (fst x)      -- Strictness U(SA)b
      g x = error ('y':fst x)  -- Strictness Tb
    Surely 'g' is no less strict on 'x' than 'f' is!  The fix turned out
    be to very nice and simple.  See Note [Bottom demands] in DmdAnal.
Commits on Dec 3, 2009
  1. @igfoo
Commits on Dec 2, 2009
  1. More work on the simplifier's inlining strategies authored
    This patch collects a small raft of related changes
    * Arrange that during 
         (a) rule matching and 
         (b) uses of exprIsConApp_maybe
      we "look through" unfoldings only if they are active
      in the phase. Doing this for (a) required a bit of 
      extra plumbing in the rule matching code, but I think
      it's worth it.
      One wrinkle is that even if inlining is off (in the 'gentle'
      phase of simplification) during rule matching we want to
      "look through" things with inlinings.  
       See SimplUtils.activeUnfInRule.
      This fixes a long-standing bug, where things that were
      supposed to be (say) NOINLINE, could still be poked into
      via exprIsConApp_maybe. 
    * In the above cases, also check for (non-rule) loop breakers; 
      we never look through these.  This fixes a bug that could make
      the simplifier diverge (and did for Roman).  
      Test = simplCore/should_compile/dfun-loop
    * Try harder not to choose a DFun as a loop breaker. This is 
      just a small adjustment in the OccurAnal scoring function
    * In the scoring function in OccurAnal, look at the InlineRule
      unfolding (if there is one) not the actual RHS, beause the
      former is what'll be inlined.  
    * Make the application of any function to dictionary arguments
      CONLIKE.  Thus (f d1 d2) is CONLIKE.  
      Encapsulated in CoreUtils.isExpandableApp
      Reason: see Note [Expandable overloadings] in CoreUtils
    * Make case expressions seem slightly smaller in CoreUnfold.
      This reverses an unexpected consequences of charging for
    * Signficantly refactor the data type for Unfolding (again). 
      The result is much nicer.  
    * Add type synonym BasicTypes.CompilerPhase = Int
      and use it
    Many of the files touched by this patch are simply knock-on
    consequences of these two refactorings.
Commits on Nov 26, 2009
  1. Comments only, esp about RecStmts authored
Commits on Nov 19, 2009
  1. Remove the (very) old strictness analyser authored
    I finally got tired of the #ifdef OLD_STRICTNESS stuff.  I had been
    keeping it around in the hope of doing old-to-new comparisions, but
    have failed to do so for many years, so I don't think it's going to
    happen.  This patch deletes the clutter.
Commits on Oct 29, 2009
  1. The Big INLINE Patch: totally reorganise way that INLINE pragmas work authored
    This patch has been a long time in gestation and has, as a
    result, accumulated some extra bits and bobs that are only
    loosely related.  I separated the bits that are easy to split
    off, but the rest comes as one big patch, I'm afraid.
    Note that:
     * It comes together with a patch to the 'base' library
     * Interface file formats change slightly, so you need to
       recompile all libraries
    The patch is mainly giant tidy-up, driven in part by the
    particular stresses of the Data Parallel Haskell project. I don't
    expect a big performance win for random programs.  Still, here are the
    nofib results, relative to the state of affairs without the patch
            Program           Size    Allocs   Runtime   Elapsed
                Min         -12.7%    -14.5%    -17.5%    -17.8%
                Max          +4.7%    +10.9%     +9.1%     +8.4%
     Geometric Mean          +0.9%     -0.1%     -5.6%     -7.3%
    The +10.9% allocation outlier is rewrite, which happens to have a
    very delicate optimisation opportunity involving an interaction
    of CSE and inlining (see nofib/Simon-nofib-notes). The fact that
    the 'before' case found the optimisation is somewhat accidental.
    Runtimes seem to go down, but I never kno wwhether to really trust
    this number.  Binary sizes wobble a bit, but nothing drastic.
    The Main Ideas are as follows.
    When you say 
          {-# INLINE f #-}
          f x = <rhs>
    you intend that calls (f e) are replaced by <rhs>[e/x] So we
    should capture (\x.<rhs>) in the Unfolding of 'f', and never meddle
    with it.  Meanwhile, we can optimise <rhs> to our heart's content,
    leaving the original unfolding intact in Unfolding of 'f'.
    So the representation of an Unfolding has changed quite a bit
    (see CoreSyn).  An INLINE pragma gives rise to an InlineRule 
    Moreover, it's only used when 'f' is applied to the
    specified number of arguments; that is, the number of argument on 
    the LHS of the '=' sign in the original source definition. 
    For example, (.) is now defined in the libraries like this
       {-# INLINE (.) #-}
       (.) f g = \x -> f (g x)
    so that it'll inline when applied to two arguments. If 'x' appeared
    on the left, thus
       (.) f g x = f (g x)
    it'd only inline when applied to three arguments.  This slightly-experimental
    change was requested by Roman, but it seems to make sense.
    Other associated changes
    * Moving the deck chairs in DsBinds, which processes the INLINE pragmas
    * In the old system an INLINE pragma made the RHS look like
       (Note InlineMe <rhs>)
      The Note switched off optimisation in <rhs>.  But it was quite
      fragile in corner cases. The new system is more robust, I believe.
      In any case, the InlineMe note has disappeared 
    * The workerInfo of an Id has also been combined into its Unfolding,
      so it's no longer a separate field of the IdInfo.
    * Many changes in CoreUnfold, esp in callSiteInline, which is the critical
      function that decides which function to inline.  Lots of comments added!
    * exprIsConApp_maybe has moved to CoreUnfold, since it's so strongly
      associated with "does this expression unfold to a constructor application".
      It can now do some limited beta reduction too, which Roman found 
      was an important.
    Instance declarations
    It's always been tricky to get the dfuns generated from instance
    declarations to work out well.  This is particularly important in 
    the Data Parallel Haskell project, and I'm now on my fourth attempt,
    more or less.
    There is a detailed description in TcInstDcls, particularly in
    Note [How instance declarations are translated].   Roughly speaking
    we now generate a top-level helper function for every method definition
    in an instance declaration, so that the dfun takes a particularly
    stylised form:
      dfun a d1 d2 = MkD (op1 a d1 d2) (op2 a d1 d2) ...etc...
    In fact, it's *so* stylised that we never need to unfold a dfun.
    Instead ClassOps have a special rewrite rule that allows us to
    short-cut dictionary selection.  Suppose dfun :: Ord a -> Ord [a]
                                                d :: Ord a
        compare (dfun a d)  -->   compare_list a d 
    in one rewrite, without first inlining the 'compare' selector
    and the body of the dfun.
    To support this
    a) ClassOps have a BuiltInRule (see MkId.dictSelRule)
    b) DFuns have a special form of unfolding (CoreSyn.DFunUnfolding)
       which is exploited in CoreUnfold.exprIsConApp_maybe
    Implmenting all this required a root-and-branch rework of TcInstDcls
    and bits of TcClassDcl.
    Default methods
    If you give an INLINE pragma to a default method, it should be just
    as if you'd written out that code in each instance declaration, including
    the INLINE pragma.  I think that it now *is* so.  As a result, library
    code can be simpler; less duplication.
    The CONLIKE pragma
    In the DPH project, Roman found cases where he had
       p n k = let x = replicate n k
               in ...(f x)...(g x)....
       {-# RULE f (replicate x) = f_rep x #-}
    Normally the RULE would not fire, because doing so involves 
    (in effect) duplicating the redex (replicate n k).  A new
    experimental modifier to the INLINE pragma, {-# INLINE CONLIKE
    replicate #-}, allows you to tell GHC to be prepared to duplicate
    a call of this function if it allows a RULE to fire.
    See Note [CONLIKE pragma] in BasicTypes
    Join points
    See Note [Case binders and join points] in Simplify
    Other refactoring
    * I moved endPass from CoreLint to CoreMonad, with associated jigglings
    * Better pretty-printing of Core
    * The top-level RULES (ones that are not rules for locally-defined things)
      are now substituted on every simplifier iteration.  I'm not sure how
      we got away without doing this before.  This entails a bit more plumbing
      in SimplCore.
    * The necessary stuff to serialise and deserialise the new
      info across interface files.
    * Something about bottoming floats in SetLevels
          Note [Bottoming floats]
    * substUnfolding has moved from SimplEnv to CoreSubs, where it belongs
            Program           Size    Allocs   Runtime   Elapsed
               anna          +2.4%     -0.5%      0.16      0.17
               ansi          +2.6%     -0.1%      0.00      0.00
               atom          -3.8%     -0.0%     -1.0%     -2.5%
             awards          +3.0%     +0.7%      0.00      0.00
             banner          +3.3%     -0.0%      0.00      0.00
         bernouilli          +2.7%     +0.0%     -4.6%     -6.9%
              boyer          +2.6%     +0.0%      0.06      0.07
             boyer2          +4.4%     +0.2%      0.01      0.01
               bspt          +3.2%     +9.6%      0.02      0.02
          cacheprof          +1.4%     -1.0%    -12.2%    -13.6%
           calendar          +2.7%     -1.7%      0.00      0.00
           cichelli          +3.7%     -0.0%      0.13      0.14
            circsim          +3.3%     +0.0%     -2.3%     -9.9%
           clausify          +2.7%     +0.0%      0.05      0.06
      comp_lab_zift          +2.6%     -0.3%     -7.2%     -7.9%
           compress          +3.3%     +0.0%     -8.5%     -9.6%
          compress2          +3.6%     +0.0%    -15.1%    -17.8%
        constraints          +2.7%     -0.6%    -10.0%    -10.7%
       cryptarithm1          +4.5%     +0.0%     -4.7%     -5.7%
       cryptarithm2          +4.3%    -14.5%      0.02      0.02
                cse          +4.4%     -0.0%      0.00      0.00
              eliza          +2.8%     -0.1%      0.00      0.00
              event          +2.6%     -0.0%     -4.9%     -4.4%
             exp3_8          +2.8%     +0.0%     -4.5%     -9.5%
             expert          +2.7%     +0.3%      0.00      0.00
                fem          -2.0%     +0.6%      0.04      0.04
                fft          -6.0%     +1.8%      0.05      0.06
               fft2          -4.8%     +2.7%      0.13      0.14
           fibheaps          +2.6%     -0.6%      0.05      0.05
               fish          +4.1%     +0.0%      0.03      0.04
              fluid          -2.1%     -0.2%      0.01      0.01
             fulsom          -4.8%     +9.2%     +9.1%     +8.4%
             gamteb          -7.1%     -1.3%      0.10      0.11
                gcd          +2.7%     +0.0%      0.05      0.05
        gen_regexps          +3.9%     -0.0%      0.00      0.00
             genfft          +2.7%     -0.1%      0.05      0.06
                 gg          -2.7%     -0.1%      0.02      0.02
               grep          +3.2%     -0.0%      0.00      0.00
             hidden          -0.5%     +0.0%    -11.9%    -13.3%
                hpg          -3.0%     -1.8%     +0.0%     -2.4%
                ida          +2.6%     -1.2%      0.17     -9.0%
              infer          +1.7%     -0.8%      0.08      0.09
            integer          +2.5%     -0.0%     -2.6%     -2.2%
          integrate          -5.0%     +0.0%     -1.3%     -2.9%
            knights          +4.3%     -1.5%      0.01      0.01
               lcss          +2.5%     -0.1%     -7.5%     -9.4%
               life          +4.2%     +0.0%     -3.1%     -3.3%
               lift          +2.4%     -3.2%      0.00      0.00
          listcompr          +4.0%     -1.6%      0.16      0.17
           listcopy          +4.0%     -1.4%      0.17      0.18
           maillist          +4.1%     +0.1%      0.09      0.14
             mandel          +2.9%     +0.0%      0.11      0.12
            mandel2          +4.7%     +0.0%      0.01      0.01
            minimax          +3.8%     -0.0%      0.00      0.00
            mkhprog          +3.2%     -4.2%      0.00      0.00
         multiplier          +2.5%     -0.4%     +0.7%     -1.3%
           nucleic2          -9.3%     +0.0%      0.10      0.10
               para          +2.9%     +0.1%     -0.7%     -1.2%
          paraffins         -10.4%     +0.0%      0.20     -1.9%
             parser          +3.1%     -0.0%      0.05      0.05
            parstof          +1.9%     -0.0%      0.00      0.01
                pic          -2.8%     -0.8%      0.01      0.02
              power          +2.1%     +0.1%     -8.5%     -9.0%
             pretty         -12.7%     +0.1%      0.00      0.00
             primes          +2.8%     +0.0%      0.11      0.11
          primetest          +2.5%     -0.0%     -2.1%     -3.1%
             prolog          +3.2%     -7.2%      0.00      0.00
             puzzle          +4.1%     +0.0%     -3.5%     -8.0%
             queens          +2.8%     +0.0%      0.03      0.03
            reptile          +2.2%     -2.2%      0.02      0.02
            rewrite          +3.1%    +10.9%      0.03      0.03
               rfib          -5.2%     +0.2%      0.03      0.03
                rsa          +2.6%     +0.0%      0.05      0.06
                scc          +4.6%     +0.4%      0.00      0.00
              sched          +2.7%     +0.1%      0.03      0.03
                scs          -2.6%     -0.9%     -9.6%    -11.6%
             simple          -4.0%     +0.4%    -14.6%    -14.9%
              solid          -5.6%     -0.6%     -9.3%    -14.3%
            sorting          +3.8%     +0.0%      0.00      0.00
             sphere          -3.6%     +8.5%      0.15      0.16
             symalg          -1.3%     +0.2%      0.03      0.03
                tak          +2.7%     +0.0%      0.02      0.02
          transform          +2.0%     -2.9%     -8.0%     -8.8%
           treejoin          +3.1%     +0.0%    -17.5%    -17.8%
          typecheck          +2.9%     -0.3%     -4.6%     -6.6%
            veritas          +3.9%     -0.3%      0.00      0.00
               wang          -6.2%     +0.0%      0.18     -9.8%
          wave4main         -10.3%     +2.6%     -2.1%     -2.3%
       wheel-sieve1          +2.7%     -0.0%     +0.3%     -0.6%
       wheel-sieve2          +2.7%     +0.0%     -3.7%     -7.5%
               x2n1          -4.1%     +0.1%      0.03      0.04
                Min         -12.7%    -14.5%    -17.5%    -17.8%
                Max          +4.7%    +10.9%     +9.1%     +8.4%
     Geometric Mean          +0.9%     -0.1%     -5.6%     -7.3%
Commits on Jul 7, 2009
  1. @igfoo

    Remove unused imports

    igfoo authored
Commits on May 29, 2009
  1. Fix Trac #3259: expose 'lazy' only after generating interface files authored
    This patch fixes an insidious and long-standing bug in the way that
    parallelism is handled in GHC.  See Note [lazyId magic] in MkId.
    Here's the diagnosis, copied from the Trac ticket.  par is defined 
    in GHC.Conc thus:
        {-# INLINE par  #-}
        par :: a -> b -> b
        par  x y = case (par# x) of { _ -> lazy y }
        -- The reason for the strange "lazy" call is that it fools the
        -- compiler into thinking that pseq and par are non-strict in
        -- their second argument (even if it inlines pseq/par at the call
        -- site).  If it thinks par is strict in "y", then it often
        -- evaluates "y" before "x", which is totally wrong.
    The function lazy is the identity function, but it is inlined only
    after strictness analysis, and (via some magic) pretends to be
    lazy. Hence par pretends to be lazy too.
    The trouble is that both par and lazy are inlined into your definition
    of parallelise, so that the unfolding for parallelise (exposed in
    Parallelise.hi) does not use lazy at all. Then when compiling Main,
    parallelise is in turn inlined (before strictness analysis), and so
    the strictness analyser sees too much.
    This was all sloppy thinking on my part. Inlining lazy after
    strictness analysis works fine for the current module, but not for
    importing modules.
    The fix implemented by this patch is to inline 'lazy' in CorePrep,
    not in WorkWrap. That way interface files never see the inlined version.
    The downside is that a little less optimisation may happen on programs
    that use 'lazy'.  And you'll only see this in the results -ddump-prep
    not in -ddump-simpl.  So KEEP AN EYE OUT (Simon and Satnam especially).
    Still, it should work properly now.  Certainly fixes #3259.
Commits on Apr 3, 2009
  1. Worker/wrapper should make INLINE if it doesn't w/w authored
    If worker/wrapper decides not to w/w something on the grounds that
    it's too small, it should add an INLINE pragma.  Otherwise, later
    in the day that small thing might now be big, and we'd wish we'd
    done the w/w after all.  This only made a difference in one nofib 
    program (bspt), but it's an easy change.
    See Note [Don't w/w inline things (a) and (b)]
Commits on Mar 18, 2009
  1. Add the notion of "constructor-like" Ids for rule-matching authored
    This patch adds an optional CONLIKE modifier to INLINE/NOINLINE pragmas, 
       {-# NOINLINE CONLIKE [1] f #-}
    The effect is to allow applications of 'f' to be expanded in a potential
    rule match.  Example
      {-# RULE "r/f" forall v. r (f v) = f (v+1) #-}
    Consider the term
         let x = f v in ..x...x...(r x)...
    Normally the (r x) would not match the rule, because GHC would be scared
    about duplicating the redex (f v). However the CONLIKE modifier says to
    treat 'f' like a constructor in this situation, and "look through" the
    unfolding for x.  So (r x) fires, yielding (f (v+1)).
    The main changes are:
      - Syntax
      - The inlinePragInfo field of an IdInfo has a RuleMatchInfo
        component, which records whether or not the Id is CONLIKE.
        Of course, this needs to be serialised in interface files too.
      - The occurrence analyser (OccAnal) and simplifier (Simplify) treat
        CONLIKE thing like constructors, by ANF-ing them
      - New function coreUtils.exprIsExpandable is like exprIsCheap, but
        additionally spots applications of CONLIKE functions
      - A CoreUnfolding has a field that caches exprIsExpandable
      - The rule matcher consults this field.  See 
        Note [Expanding variables] in Rules.lhs.
    On the way I fixed a lurking variable bug in the way variables are
    expanded.  See Note [Do not expand locally-bound variables] in
    Rule.lhs.  I also did a bit of reformatting and refactoring in
    Rules.lhs, so the module has more lines changed than are really
Commits on Jan 13, 2009
  1. Rewrite CorePrep and improve eta expansion authored
    This patch does two main things
    a) Rewrite most of CorePrep to be much easier to understand (I hope!).
       The invariants established by CorePrep are now written out, and
       the code is more perspicuous.  It is surpringly hard to get right,
       and the old code had become quite incomprehensible.
    b) Rewrite the eta-expander so that it does a bit of simplifying
       on-the-fly, and thereby guarantees to maintain the CorePrep
       invariants.  This make it much easier to use from CorePrep, and
       is a generally good thing anyway.
    A couple of pieces of re-structuring:
    *  I moved the eta-expander and arity analysis stuff into a new
       module coreSyn/CoreArity.
       Max will find that the type CoreArity.EtaInfo looks strangely 
    *  I moved a bunch of comments from Simplify to OccurAnal; that's
       why it looks as though there's a lot of lines changed in those
    On the way I fixed various things
      - Function arguments are eta expanded
           f (map g)  ===>  let s = \x. map g x in f s
      - Trac #2368
    The result is a modest performance gain, I think mainly due
    to the first of these changes:
            Program           Size    Allocs   Runtime   Elapsed
                Min          -1.0%    -17.4%    -19.1%    -46.4%
                Max          +0.3%     +0.5%     +5.4%    +53.8%
     Geometric Mean          -0.1%     -0.3%     -7.0%    -10.2%
Commits on Jan 2, 2009
  1. Make record selectors into ordinary functions authored
    This biggish patch addresses Trac #2670.  The main effect is to make
    record selectors into ordinary functions, whose unfoldings appear in
    interface files, in contrast to their previous existence as magic
    "implicit Ids".  This means that the usual machinery of optimisation,
    analysis, and inlining applies to them, which was failing before when
    the selector was somewhat complicated.  (Which it can be when
    strictness annotations, unboxing annotations, and GADTs are involved.)
    The change involves the following points
    * Changes in Var.lhs to the representation of Var.  Now a LocalId can
      have an IdDetails as well as a GlobalId.  In particular, the
      information that an Id is a record selector is kept in the
      IdDetails.  While compiling the current module, the record selector
      *must* be a LocalId, so that it participates properly in compilation
      (free variables etc).
      This led me to change the (hidden) representation of Var, so that there
      is now only one constructor for Id, not two.
    * The IdDetails is persisted into interface files, so that an
      importing module can see which Ids are records selectors.
    * In TcTyClDecls, we generate the record-selector bindings in renamed,
      but not typechecked form.  In this way, we can get the typechecker
      to add all the types and so on, which is jolly helpful especially
      when GADTs or type families are involved.  Just like derived
      instance declarations.
      This is the big new chunk of 180 lines of code (much of which is
      commentary).  A call to the same function, mkAuxBinds, is needed in
      TcInstDcls for associated types.
    * The typechecker therefore has to pin the correct IdDetails on to 
      the record selector, when it typechecks it.  There was a neat way
      to do this, by adding a new sort of signature to HsBinds.Sig, namely
      IdSig.  This contains an Id (with the correct Name, Type, and IdDetails);
      the type checker uses it as the binder for the final binding.  This
      worked out rather easily.
    * Record selectors are no longer "implicit ids", which entails changes to
      (These three functions must agree.)
    * MkId.mkRecordSelectorId is deleted entirely, some 300+ lines (incl
      comments) of very error prone code.  Happy days.
    * A TyCon no longer contains the list of record selectors: 
      algTcSelIds is gone
    The renamer is unaffected, including the way that import and export of
    record selectors is handled.
    Other small things
    * IfaceSyn.ifaceDeclSubBndrs had a fragile test for whether a data
      constructor had a wrapper.  I've replaced that with an explicit flag
      in the interface file. More robust I hope.
    * I renamed isIdVar to isId, which touched a few otherwise-unrelated files.
Something went wrong with that request. Please try again.