[project @ 2000-10-24 08:40:09 by simonpj]
[ghc-hetmet.git] / ghc / compiler / rename / ParseIface.y
index 4062b55..a51631f 100644 (file)
@@ -1,3 +1,32 @@
+{-     Notes about the syntax of interface files
+       ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+The header
+~~~~~~~~~~
+  interface "edison" M 4 6 2 ! 406     Module M, version 4, from package 'edison',
+                                       Fixities version 6, rules version 2
+                                       Interface syntax version 406
+                                       ! means M contains orphans
+
+Import declarations
+~~~~~~~~~~~~~~~~~~~
+  import Foo ;                         To compile M I used nothing from Foo, but it's 
+                                       below me in the hierarchy
+
+  import Foo ! @ ;                     Ditto, but the ! means that Foo contains orphans
+                                       and        the @ means that Foo is a boot interface
+
+  import Foo :: 3 ;                    To compile M I used everything from Foo, which has 
+                                       module version 3
+
+  import Foo :: 3 2 6 a 1 b 3 c 7 ;    To compile M I used Foo.  It had 
+                                               module version 3
+                                               fixity version 2
+                                               rules  version 6
+                                       and some specific things besides.
+
+-}
+
+
 {
 module ParseIface ( parseIface, IfaceStuff(..) ) where
 
@@ -5,45 +34,40 @@ module ParseIface ( parseIface, IfaceStuff(..) ) where
 
 import HsSyn           -- quite a bit of stuff
 import RdrHsSyn                -- oodles of synonyms
-import HsTypes         ( mkHsForAllTy, mkHsUsForAllTy )
+import HsTypes         ( mkHsForAllTy, mkHsUsForAllTy, mkHsTupCon )
 import HsCore
+import Demand          ( mkStrictnessInfo )
 import Literal         ( Literal(..), mkMachInt, mkMachInt64, mkMachWord, mkMachWord64 )
 import BasicTypes      ( Fixity(..), FixityDirection(..), 
-                         NewOrData(..), Version
+                         NewOrData(..), Version, initialVersion, Boxity(..)
                        )
 import CostCentre       ( CostCentre(..), IsCafCC(..), IsDupdCC(..) )
 import CallConv         ( cCallConv )
-import HsPragmas       ( noDataPragmas, noClassPragmas )
-import Type            ( Kind, mkArrowKind, boxedTypeKind, openTypeKind, UsageAnn(..) )
-import IdInfo           ( ArityInfo, exactArity, CprInfo(..), InlinePragInfo(..) )
+import Type            ( Kind, mkArrowKind, boxedTypeKind, openTypeKind )
+import IdInfo           ( exactArity, InlinePragInfo(..) )
 import PrimOp           ( CCall(..), CCallTarget(..) )
 import Lex             
 
-import RnMonad         ( ImportVersion, LocalVersion, ParsedIface(..), WhatsImported(..),
-                         RdrNamePragma, ExportItem, RdrAvailInfo, GenAvailInfo(..), 
-                          WhetherHasOrphans, IsBootInterface
-                       ) 
-import Bag             ( emptyBag, unitBag, snocBag )
-import FiniteMap       ( emptyFM, unitFM, addToFM, plusFM, bagToFM, FiniteMap )
-import RdrName          ( RdrName, mkRdrUnqual, mkSysQual, mkSysUnqual, mkRdrNameWkr )
-import Name            ( OccName, Provenance )
+import RnMonad         ( ParsedIface(..), ExportItem, IfaceDeprecs ) 
+import HscTypes         ( WhetherHasOrphans, IsBootInterface, GenAvailInfo(..), 
+                          ImportVersion, WhatsImported(..),
+                          RdrAvailInfo )
+
+import RdrName          ( RdrName, mkRdrUnqual, mkSysQual, mkSysUnqual )
+import Name            ( OccName )
 import OccName          ( mkSysOccFS,
                          tcName, varName, ipName, dataName, clsName, tvName, uvName,
                          EncodedFS 
                        )
-import Module           ( ModuleName, PackageName, mkSysModuleFS, mkModule )                   
-import PrelInfo         ( mkTupConRdrName, mkUbxTupConRdrName )
+import Module           ( ModuleName, PackageName, mkSysModuleNameFS, mkModule )
 import SrcLoc          ( SrcLoc )
 import CmdLineOpts     ( opt_InPackage )
-import Maybes
 import Outputable
+import List            ( insert )
+import Class            ( DefMeth (..) )
 
 import GlaExts
 import FastString      ( tailFS )
-
-#if __HASKELL1__ > 4
-import Ratio ( (%) )
-#endif
 }
 
 %name      parseIface
@@ -104,6 +128,7 @@ import Ratio ( (%) )
  '__word64'    { ITword64_lit }
  '__rational'  { ITrational_lit }
  '__addr'      { ITaddr_lit }
+ '__label'     { ITlabel_lit }
  '__litlit'    { ITlit_lit }
  '__string'    { ITstring_lit }
  '__ccall'     { ITccall $$ }
@@ -139,6 +164,8 @@ import Ratio ( (%) )
 
  '{'           { ITocurly }                    -- special symbols
  '}'           { ITccurly }
+ '{|'          { ITocurlybar }                         -- special symbols
+ '|}'          { ITccurlybar }                         -- special symbols
  '['           { ITobrack }
  ']'           { ITcbrack }
  '('           { IToparen }
@@ -179,41 +206,45 @@ iface_stuff :: { IfaceStuff }
 iface_stuff : iface            { PIface   $1 }
            | type              { PType    $1 }
            | id_info           { PIdInfo  $1 }
-           | '__R' rules       { PRules   $2 }
-           | '__D' deprecs     { PDeprecs $2 }
-
+           | rules_and_deprecs { PRulesAndDeprecs $1 }
 
 iface          :: { ParsedIface }
-iface          : '__interface' package mod_name INTEGER orphans checkVersion 'where'
+iface          : '__interface' package mod_name 
+                       version sub_versions
+                       orphans checkVersion 'where'
                  exports_part
                   import_part
+                 fix_decl_part
                  instance_decl_part
                  decls_part
-                 rules_and_deprecs
+                 rules_and_deprecs_part
                  { ParsedIface {
                        pi_mod  = mkModule $3 $2,       -- Module itself
-                       pi_vers = fromInteger $4,       -- Module version
-                       pi_orphan  = $5,
-                       pi_exports = $8,        -- Exports
-                       pi_usages  = $9,        -- Usages
-                       pi_insts   = $10,       -- Local instances
-                       pi_decls   = $11,       -- Decls
-                       pi_rules   = fst $12,   -- Rules 
-                       pi_deprecs = snd $12    -- Deprecations 
-                     } }
+                       pi_vers = $4,                   -- Module version
+                       pi_orphan  = $6,
+                       pi_exports = (fst $5, $9),      -- Exports
+                       pi_usages  = $10,               -- Usages
+                       pi_fixity  = $11,               -- Fixies
+                       pi_insts   = $12,               -- Local instances
+                       pi_decls   = $13,               -- Decls
+                       pi_rules   = (snd $5,fst $14),  -- Rules 
+                       pi_deprecs = snd $14            -- Deprecations 
+                  } }
+
+-- Versions for exports and rules (optional)
+sub_versions :: { (Version,Version) }
+       : '[' version version ']'               { ($2,$3) }
+       | {- empty -}                           { (initialVersion, initialVersion) }
 
 --------------------------------------------------------------------------
 
 import_part :: { [ImportVersion OccName] }
 import_part :                                            { [] }
-           |  import_part import_decl                    { $2 : $1 }
+           |  import_decl import_part                    { $1 : $2 }
            
 import_decl :: { ImportVersion OccName }
-import_decl : 'import' mod_name INTEGER orphans is_boot whats_imported ';'
-                       { (mkSysModuleFS $2, fromInteger $3, $4, $5, $6) }
-       -- import Foo 3 :: a 1 b 3 c 7 ;        means import a,b,c from Foo
-       -- import Foo 3 ;                       means import all of Foo
-       -- import Foo 3 ! :: ...stuff... ;      the ! means that Foo contains orphans
+import_decl : 'import' mod_name orphans is_boot whats_imported ';'
+                       { ({-mkSysModuleNameFS-} $2, $3, $4, $5) }
 
 orphans                    :: { WhetherHasOrphans }
 orphans                    :                                           { False }
@@ -224,34 +255,39 @@ is_boot               :                                           { False }
                    | '@'                                       { True }
 
 whats_imported      :: { WhatsImported OccName }
-whats_imported      :                                           { Everything }
-                    | '::' name_version_pairs                  { Specifically $2 }
+whats_imported      :                                                  { NothingAtAll }
+                   | '::' version                                      { Everything $2 }
+                    | '::' version version name_version_pairs version  { Specifically $2 (Just $3) $4 $5 }
 
-name_version_pairs  :: { [LocalVersion OccName] }
+name_version_pairs  :: { [(OccName, Version)] }
 name_version_pairs  :                                                  { [] }
                    |  name_version_pair name_version_pairs     { $1 : $2 }
 
-name_version_pair   :: { LocalVersion OccName }
-name_version_pair   :  var_occ INTEGER                         { ($1, fromInteger $2) }
-                    |  tc_occ  INTEGER                          { ($1, fromInteger $2) }
+name_version_pair   :: { (OccName, Version) }
+name_version_pair   :  var_occ version                         { ($1, $2) }
+                    |  tc_occ  version                          { ($1, $2) }
 
 
 --------------------------------------------------------------------------
 
 exports_part   :: { [ExportItem] }
 exports_part   :                                       { [] }
-               | exports_part '__export' 
-                 mod_name entities ';'                 { (mkSysModuleFS $3, $4) : $1 }
+               | '__export' mod_name entities ';'
+                       exports_part                    { ({-mkSysModuleNameFS-} $2, $3) : $5 }
 
 entities       :: { [RdrAvailInfo] }
 entities       :                                       { [] }
                |  entity entities                      { $1 : $2 }
 
 entity         :: { RdrAvailInfo }
-entity         :  tc_occ                               { AvailTC $1 [$1] }
-               |  var_occ                              { Avail $1 }
-               |  tc_occ stuff_inside                  { AvailTC $1 ($1:$2) }
+entity         :  var_occ                              { Avail $1 }
+               |  tc_occ                               { AvailTC $1 [$1] }
                |  tc_occ '|' stuff_inside              { AvailTC $1 $3 }
+               |  tc_occ stuff_inside                  { AvailTC $1 (insert $1 $2) }
+               -- The 'insert' is important.  The stuff_inside is sorted, and
+               -- insert keeps it that way.  This is important when comparing 
+               -- against the new interface file, which has the stuff in sorted order
+               -- If they differ, we'll bump the module number when it's unnecessary
 
 stuff_inside   :: { [OccName] }
 stuff_inside   :  '{' val_occs '}'                     { $2 }
@@ -267,14 +303,24 @@ val_occs  :: { [OccName] }
 
 --------------------------------------------------------------------------
 
+fix_decl_part :: { [RdrNameFixitySig] }
+fix_decl_part : {- empty -}                            { [] }
+             | fix_decls ';'                           { $1 }
+
+fix_decls     :: { [RdrNameFixitySig] }
+fix_decls     :                                        { [] }
+             | fix_decl fix_decls                      { $1 : $2 }
+
+fix_decl :: { RdrNameFixitySig }
+fix_decl : src_loc fixity prec var_or_data_name                { FixitySig $4 (Fixity $3 $2) $1 }
+
 fixity      :: { FixityDirection }
 fixity      : 'infixl'                                  { InfixL }
             | 'infixr'                                  { InfixR }
             | 'infix'                                   { InfixN }
    
-mb_fix      :: { Int }
-mb_fix     : {-nothing-}                               { 9 }
-           | INTEGER                                   { (fromInteger $1) }
+prec        :: { Int }
+prec       : INTEGER                                   { fromInteger $1 }
 
 -----------------------------------------------------------------------------
 
@@ -283,12 +329,14 @@ csigs             :                               { [] }
                | 'where' '{' csigs1 '}'        { $3 }
 
 csigs1         :: { [RdrNameSig] }
-csigs1         : csig                          { [$1] }
+csigs1         :                               { [] }
                | csig ';' csigs1               { $1 : $3 }
 
 csig           :: { RdrNameSig }
-csig           :  src_loc var_name '::' type           { mkClassOpSig False $2 $4 $1 }
-               |  src_loc var_name '=' '::' type       { mkClassOpSig True  $2 $5 $1 }
+csig           :  src_loc var_name '::' type           { mkClassOpSig NoDefMeth $2 $4 $1 }
+               |  src_loc var_name '=' '::' type       { mkClassOpSig (DefMeth (error "DefMeth") )
+                                                               $2 $5 $1 }
+               |  src_loc var_name ';' '::' type       { mkClassOpSig GenDefMeth  $2 $5 $1 }           
 
 --------------------------------------------------------------------------
 
@@ -301,7 +349,7 @@ inst_decl   :  src_loc 'instance' type '=' var_name ';'
                        { InstDecl $3
                                   EmptyMonoBinds       {- No bindings -}
                                   []                   {- No user pragmas -}
-                                  $5                   {- Dfun id -}
+                                  (Just $5)            {- Dfun id -}
                                   $1
                        }
 
@@ -310,22 +358,19 @@ inst_decl :  src_loc 'instance' type '=' var_name ';'
 decls_part :: { [(Version, RdrNameHsDecl)] }
 decls_part 
        :  {- empty -}                          { [] }
-       |  decls_part version decl ';'          { ($2,$3):$1 }
+       |  opt_version decl ';' decls_part              { ($1,$2):$4 }
 
 decl   :: { RdrNameHsDecl }
 decl    : src_loc var_name '::' type maybe_idinfo
                         { SigD (IfaceSig $2 $4 ($5 $2) $1) }
        | src_loc 'type' tc_name tv_bndrs '=' type                     
                        { TyClD (TySynonym $3 $4 $6 $1) }
-       | src_loc 'data' decl_context tc_name tv_bndrs constrs         
-                       { TyClD (TyData DataType $3 $4 $5 $6 Nothing noDataPragmas $1) }
-       | src_loc 'newtype' decl_context tc_name tv_bndrs newtype_constr
-                       { TyClD (TyData NewType $3 $4 $5 $6 Nothing noDataPragmas $1) }
-       | src_loc 'class' decl_context tc_name tv_bndrs fds csigs
-                       { TyClD (mkClassDecl $3 $4 $5 $6 $7 EmptyMonoBinds 
-                                       noClassPragmas $1) }
-        | src_loc fixity mb_fix var_or_data_name
-                        { FixD (FixitySig $4 (Fixity $3 $2) $1) }
+       | src_loc 'data' opt_decl_context tc_name tv_bndrs constrs             
+                       { TyClD (mkTyData DataType $3 $4 $5 $6 (length $6) Nothing $1) }
+       | src_loc 'newtype' opt_decl_context tc_name tv_bndrs newtype_constr
+                       { TyClD (mkTyData NewType $3 $4 $5 $6 1 Nothing $1) }
+       | src_loc 'class' opt_decl_context tc_name tv_bndrs fds csigs
+                       { TyClD (mkClassDecl $3 $4 $5 $6 $7 EmptyMonoBinds $1) }
 
 maybe_idinfo  :: { RdrName -> [HsIdInfo RdrName] }
 maybe_idinfo  : {- empty -}    { \_ -> [] }
@@ -345,60 +390,67 @@ pragma    : src_loc PRAGMA        { parseIface $2 PState{ bol = 0#, atbol = 1#,
 
 -----------------------------------------------------------------------------
 
-rules_and_deprecs :: { ([RdrNameRuleDecl], [RdrNameDeprecation]) }
-rules_and_deprecs : {- empty -}        { ([], []) }
-                 | rules_and_deprecs rule_or_deprec
-                               { let
-                                    append2 (xs1,ys1) (xs2,ys2) =
-                                       (xs1 `app` xs2, ys1 `app` ys2)
-                                    xs `app` [] = xs -- performance paranoia
-                                    xs `app` ys = xs ++ ys
-                                 in append2 $1 $2
-                               }
+rules_and_deprecs_part :: { ([RdrNameRuleDecl], IfaceDeprecs) }
+rules_and_deprecs_part : {- empty -}   { ([], Nothing) }
+                      | pragma         { case $1 of
+                                            POk _ (PRulesAndDeprecs rds) -> rds
+                                            PFailed err -> pprPanic "Rules/Deprecations parse failed" err
+                                       }
 
-rule_or_deprec :: { ([RdrNameRuleDecl], [RdrNameDeprecation]) }
-rule_or_deprec : pragma        { case $1 of
-                            POk _ (PRules   rules)   -> (rules,[])
-                            POk _ (PDeprecs deprecs) -> ([],deprecs)
-                            PFailed err -> pprPanic "Rules/Deprecations parse failed" err
-                       }
+rules_and_deprecs :: { ([RdrNameRuleDecl], IfaceDeprecs) }
+rules_and_deprecs : rule_prag deprec_prag      { ($1, $2) }
 
 -----------------------------------------------------------------------------
 
+rule_prag :: { [RdrNameRuleDecl] }
+rule_prag : {- empty -}                        { [] }
+         | '__R' rules                 { $2 }
+
 rules     :: { [RdrNameRuleDecl] }
           : {- empty -}        { [] }
           | rule ';' rules     { $1:$3 }
 
 rule      :: { RdrNameRuleDecl }
 rule      : src_loc STRING rule_forall qvar_name 
-            core_args '=' core_expr    { IfaceRuleDecl $4 (UfRuleBody $2 $3 $5 $7) $1 } 
+            core_args '=' core_expr    { IfaceRule $2 $3 $4 $5 $7 $1 } 
 
 rule_forall    :: { [UfBinder RdrName] }
 rule_forall    : '__forall' '{' core_bndrs '}' { $3 }
                  
 -----------------------------------------------------------------------------
 
-deprecs        :: { [RdrNameDeprecation] }
-deprecs                : {- empty -}           { [] }
-               | deprecs deprec ';'    { $2 : $1 }
+deprec_prag    :: { IfaceDeprecs }
+deprec_prag    : {- empty -}           { Nothing }
+               | '__D' deprecs         { Just $2 } 
+
+deprecs        :: { Either DeprecTxt [(RdrName,DeprecTxt)] }
+deprecs                : STRING                { Left $1 }
+               | deprec_list           { Right $1 }
+
+deprec_list    :: { [(RdrName,DeprecTxt)] }
+deprec_list    : deprec                        { [$1] }
+               | deprec ';' deprec_list        { $1 : $3 }
 
-deprec         :: { RdrNameDeprecation }
-deprec         : STRING                { Deprecation (IEModuleContents undefined) $1 }
-               | deprec_name STRING    { Deprecation $1 $2 }
+deprec         :: { (RdrName,DeprecTxt) }
+deprec         : deprec_name STRING    { ($1, $2) }
 
--- SUP: TEMPORARY HACK
-deprec_name    :: { RdrNameIE }
-               : var_name              { IEVar      $1 }
-               | data_name             { IEThingAbs $1 }
+deprec_name    :: { RdrName }
+               : var_name              { $1 }
+               | tc_name               { $1 }
 
 -----------------------------------------------------------------------------
 
 version                :: { Version }
-version                :  INTEGER                              { fromInteger $1 }
+version                :  INTEGER                      { fromInteger $1 }
 
-decl_context   :: { RdrNameContext }
-decl_context   :                                       { [] }
-               | '{' context_list1 '}' '=>'    { $2 }
+opt_version    :: { Version }
+opt_version    : version                       { $1 }
+               | {- empty -}                   { initialVersion }
+       
+opt_decl_context  :: { RdrNameContext }
+opt_decl_context  :                            { [] }
+                 | context '=>'                { $1 }
 
 ----------------------------------------------------------------------------
 
@@ -415,15 +467,14 @@ constr            :  src_loc ex_stuff data_name batypes           { mk_con_decl $3 $2 (VanillaCon $
                |  src_loc ex_stuff data_name '{' fields1 '}'   { mk_con_decl $3 $2 (RecCon $5)     $1 }
                 -- We use "data_fs" so as to include ()
 
-newtype_constr :: { [RdrNameConDecl] {- Empty if handwritten abstract -} }
-newtype_constr :                                       { [] }
-               | src_loc '=' ex_stuff data_name atype  { [mk_con_decl $4 $3 (NewCon $5 Nothing) $1] }
+newtype_constr :: { [RdrNameConDecl] {- Not allowed to be empty -} }
+newtype_constr : src_loc '=' ex_stuff data_name atype  { [mk_con_decl $4 $3 (VanillaCon [Unbanged $5]) $1] }
                | src_loc '=' ex_stuff data_name '{' var_name '::' atype '}'
-                                                       { [mk_con_decl $4 $3 (NewCon $8 (Just $6)) $1] }
+                                                       { [mk_con_decl $4 $3 (RecCon [([$6], Unbanged $8)]) $1] }
 
-ex_stuff :: { ([HsTyVar RdrName], RdrNameContext) }
+ex_stuff :: { ([HsTyVarBndr RdrName], RdrNameContext) }
 ex_stuff       :                                       { ([],[]) }
-                | '__forall' forall context '=>'            { ($2,$3) }
+                | '__forall' tv_bndrs opt_context '=>'  { ($2,$3) }
 
 batypes                :: { [RdrNameBangType] }
 batypes                :                                       { [] }
@@ -446,20 +497,21 @@ field             :  var_names1 '::' type         { ($1, Unbanged $3) }
 
 type           :: { RdrNameHsType }
 type           : '__fuall'  fuall '=>' type    { mkHsUsForAllTy $2 $4 }
-                | '__forall' forall context '=>' type  
-                                               { mkHsForAllTy (Just $2) $3 $5 }
-               | btype '->' type               { MonoFunTy $1 $3 }
+                | '__forall' tv_bndrs 
+                       opt_context '=>' type   { mkHsForAllTy (Just $2) $3 $5 }
+               | btype '->' type               { HsFunTy $1 $3 }
                | btype                         { $1 }
 
 fuall          :: { [RdrName] }
 fuall          : '[' uv_bndrs ']'                      { $2 }
 
-forall         :: { [HsTyVar RdrName] }
-forall         : '[' tv_bndrs ']'                      { $2 }
+opt_context    :: { RdrNameContext }
+opt_context    :                                       { [] }
+               | context                               { $1 }
 
 context                :: { RdrNameContext }
-context                :                                       { [] }
-               | '{' context_list1 '}'                 { $2 }
+context                : '(' context_list1 ')'                 { $2 }
+               | '{' context_list1 '}'                 { $2 }  -- Backward compatibility
 
 context_list1  :: { RdrNameContext }
 context_list1  : class                                 { [$1] }
@@ -480,27 +532,25 @@ types2            :  type ',' type                        { [$1,$3] }
 
 btype          :: { RdrNameHsType }
 btype          :  atype                                { $1 }
-               |  btype atype                          { MonoTyApp $1 $2 }
-                |  '__u' usage atype                   { MonoUsgTy $2 $3 }
+               |  btype atype                          { HsAppTy $1 $2 }
+                |  '__u' usage atype                   { HsUsgTy $2 $3 }
 
-usage          :: { MonoUsageAnn RdrName }
-usage          : '-'                                   { MonoUsOnce }
-               | '!'                                   { MonoUsMany }
-               | uv_name                               { MonoUsVar $1 }
+usage          :: { HsUsageAnn RdrName }
+usage          : '-'                                   { HsUsOnce }
+               | '!'                                   { HsUsMany }
+               | uv_name                               { HsUsVar $1 }
 
 atype          :: { RdrNameHsType }
-atype          :  qtc_name                             { MonoTyVar $1 }
-               |  tv_name                              { MonoTyVar $1 }
-               |  '(' types2 ')'                       { MonoTupleTy $2 True{-boxed-} }
-               |  '(#' types0 '#)'                     { MonoTupleTy $2 False{-unboxed-} }
-               |  '[' type ']'                         { MonoListTy  $2 }
-               |  '{' qcls_name atypes '}'             { MonoDictTy $2 $3 }
-               |  '{' ipvar_name '::' type '}'         { MonoIParamTy $2 $4 }
+atype          :  qtc_name                             { HsTyVar $1 }
+               |  tv_name                              { HsTyVar $1 }
+               |  '(' ')'                              { HsTupleTy (mkHsTupCon tcName Boxed   []) [] }
+               |  '(' types2 ')'                       { HsTupleTy (mkHsTupCon tcName Boxed   $2) $2 }
+               |  '(#' types0 '#)'                     { HsTupleTy (mkHsTupCon tcName Unboxed $2) $2 }
+               |  '[' type ']'                         { HsListTy  $2 }
+               |  '{' qcls_name atypes '}'             { mkHsDictTy $2 $3 }
+               |  '{' ipvar_name '::' type '}'         { mkHsIParamTy $2 $4 }
                |  '(' type ')'                         { $2 }
 
--- This one is dealt with via qtc_name
---             |  '(' ')'                              { MonoTupleTy [] True }
-
 atypes         :: { [RdrNameHsType]    {-  Zero or more -} }
 atypes         :                                       { [] }
                |  atype atypes                         { $1 : $2 }
@@ -512,7 +562,7 @@ package             :: { PackageName }
                                                                -- Module loops are always within a package
 
 mod_name       :: { ModuleName }
-               :  CONID                { mkSysModuleFS $1 }
+               :  CONID                { mkSysModuleNameFS $1 }
 
 
 ---------------------------------------------------
@@ -580,10 +630,6 @@ qdata_name :: { RdrName }
 qdata_name     :  data_name            { $1 }
                |  qdata_fs             { mkSysQual dataName $1 }
                                
-qdata_names    :: { [RdrName] }
-qdata_names    :                               { [] }
-               | qdata_name qdata_names        { $1 : $2 }
-
 var_or_data_name :: { RdrName }
                   : var_name                    { $1 }
                   | data_name                   { $1 }
@@ -626,13 +672,17 @@ tv_name           :: { RdrName }
                :  VARID                { mkSysUnqual tvName $1 }
                |  VARSYM               { mkSysUnqual tvName $1 {- Allow t2 as a tyvar -} }
 
-tv_bndr                :: { HsTyVar RdrName }
+tv_bndr                :: { HsTyVarBndr RdrName }
                :  tv_name '::' akind   { IfaceTyVar $1 $3 }
                |  tv_name              { IfaceTyVar $1 boxedTypeKind }
 
-tv_bndrs       :: { [HsTyVar RdrName] }
+tv_bndrs       :: { [HsTyVarBndr RdrName] }
+tv_bndrs       : tv_bndrs1             { $1 }
+               | '[' tv_bndrs1 ']'     { $2 }  -- Backward compatibility
+
+tv_bndrs1      :: { [HsTyVarBndr RdrName] }
                :                       { [] }
-               | tv_bndr tv_bndrs      { $1 : $2 }
+               | tv_bndr tv_bndrs1     { $1 : $2 }
 
 ---------------------------------------------------
 fds :: { [([RdrName], [RdrName])] }
@@ -667,21 +717,28 @@ akind             :: { Kind }
 --------------------------------------------------------------------------
 
 id_info                :: { [HsIdInfo RdrName] }
-               :                               { [] }
+               : id_info_item                  { [$1] }
                | id_info_item id_info          { $1 : $2 }
 
 id_info_item   :: { HsIdInfo RdrName }
                : '__A' INTEGER                 { HsArity (exactArity (fromInteger $2)) }
                | '__U' inline_prag core_expr   { HsUnfold $2 $3 }
                | '__M'                         { HsCprInfo }
-               | '__S'                         { HsStrictness (HsStrictnessInfo $1) }
+               | '__S'                         { HsStrictness (mkStrictnessInfo $1) }
                | '__C'                         { HsNoCafRefs }
                | '__P' qvar_name               { HsWorker $2 }
 
 inline_prag     :: { InlinePragInfo }
                 :  {- empty -}                  { NoInlinePragInfo }
-                | '[' INTEGER ']'               { IMustNotBeINLINEd True  (Just (fromInteger $2)) } -- INLINE n
-                | '[' '!' INTEGER ']'           { IMustNotBeINLINEd False (Just (fromInteger $3)) } -- NOINLINE n
+               | '[' from_prag phase ']'       { IMustNotBeINLINEd $2 $3 }
+
+from_prag      :: { Bool }
+               : {- empty -}                   { True }
+               | '!'                           { False }
+
+phase          :: { Maybe Int }
+               : {- empty -}                   { Nothing }
+               | INTEGER                       { Just (fromInteger $1) }
 
 -------------------------------------------------------
 core_expr      :: { UfExpr RdrName }
@@ -696,14 +753,14 @@ core_expr : '\\' core_bndrs '->' core_expr        { foldr UfLam $4 $2 }
 
                 | '__litlit' STRING atype               { UfLitLit $2 $3 }
 
-                | '__inline_me' core_expr               { UfNote UfInlineMe $2 }
-                | '__inline_call' core_expr             { UfNote UfInlineCall $2 }
-                | '__coerce' atype core_expr            { UfNote (UfCoerce $2) $3 }
-               | scc core_expr                         { UfNote (UfSCC $1) $2  }
                | fexpr                                 { $1 }
 
 fexpr   :: { UfExpr RdrName }
 fexpr   : fexpr core_arg                               { UfApp $1 $2 }
+       | scc core_aexpr                                { UfNote (UfSCC $1) $2  }
+        | '__inline_me' core_aexpr                     { UfNote UfInlineMe $2 }
+        | '__inline_call' core_aexpr                   { UfNote UfInlineCall $2 }
+        | '__coerce' atype core_aexpr                  { UfNote (UfCoerce $2) $3 }
         | core_aexpr                                   { $1 }
 
 core_arg       :: { UfExpr RdrName }
@@ -717,25 +774,13 @@ core_args :: { [UfExpr RdrName] }
 core_aexpr      :: { UfExpr RdrName }              -- Atomic expressions
 core_aexpr      : qvar_name                                    { UfVar $1 }
                 | qdata_name                                    { UfVar $1 }
-                       -- This one means that e.g. "True" will parse as 
-                       -- (UfVar True_Id) rather than (UfCon True_Con []).
-                       -- No big deal; it'll be inlined in a jiffy.  I tried 
-                       -- parsing it to (Con con []) directly, but got bitten 
-                       -- when a real constructor Id showed up in an interface
-                       -- file.  As usual, a hack bites you in the end.
-                       -- If you want to get a UfCon, then use the
-                       -- curly-bracket notation (True {}).
-
--- This one is dealt with by qdata_name: see above comments
---             | '('  ')'               { UfTuple (mkTupConRdrName 0) [] }
 
                | core_lit               { UfLit $1 }
                | '(' core_expr ')'      { $2 }
 
-                       -- Tuple construtors are for the *worker* of the tuple
-                       -- Going direct saves needless messing about 
-               | '(' comma_exprs2 ')'   { UfTuple (mkRdrNameWkr (mkTupConRdrName (length $2))) $2 }
-               | '(#' comma_exprs0 '#)' { UfTuple (mkRdrNameWkr (mkUbxTupConRdrName (length $2))) $2 }
+               | '('  ')'               { UfTuple (mkHsTupCon dataName Boxed [])   [] }
+               | '(' comma_exprs2 ')'   { UfTuple (mkHsTupCon dataName Boxed $2)   $2 }
+               | '(#' comma_exprs0 '#)' { UfTuple (mkHsTupCon dataName Unboxed $2) $2 }
 
                 | '{' '__ccall' ccall_string type '}'       
                            { let
@@ -764,7 +809,7 @@ rec_binds   :: { [(UfBinder RdrName, UfExpr RdrName)] }
                | core_val_bndr '=' core_expr ';' rec_binds     { ($1,$3) : $5 }
 
 core_alts      :: { [UfAlt RdrName] }
-               : core_alt                                      { [$1] }
+               :                                               { [] }
                | core_alt ';' core_alts                        { $1 : $3 }
 
 core_alt        :: { UfAlt RdrName }
@@ -774,8 +819,9 @@ core_pat    :: { (UfConAlt RdrName, [RdrName]) }
 core_pat       : core_lit                      { (UfLitAlt  $1, []) }
                | '__litlit' STRING atype       { (UfLitLitAlt $2 $3, []) }
                | qdata_name core_pat_names     { (UfDataAlt $1, $2) }
-               | '(' comma_var_names1 ')'      { (UfDataAlt (mkTupConRdrName (length $2)), $2) }
-               | '(#' comma_var_names1 '#)'    { (UfDataAlt (mkUbxTupConRdrName (length $2)), $2) }
+               | '('  ')'                      { (UfTupleAlt (mkHsTupCon dataName Boxed []),   []) }
+               | '(' comma_var_names1 ')'      { (UfTupleAlt (mkHsTupCon dataName Boxed $2),   $2) }
+               | '(#' comma_var_names1 '#)'    { (UfTupleAlt (mkHsTupCon dataName Unboxed $2), $2) }
                | '__DEFAULT'                   { (UfDefault, []) }
                | '(' core_pat ')'              { $2 }
 
@@ -805,6 +851,7 @@ core_lit    : integer                       { mkMachInt $1 }
                | '__int64' integer             { mkMachInt64 $2 }
                | '__float' rational            { MachFloat $2 }
                | '__addr' integer              { MachAddr $2 }
+               | '__label' STRING              { MachLabel $2 }
 
 integer                :: { Integer }
                : INTEGER                       { $1 }
@@ -859,6 +906,9 @@ cc_caf  :: { IsCafCC }
 src_loc :: { SrcLoc }
 src_loc :                              {% getSrcLocP }
 
+-- Check the project version: this makes sure
+-- that the project version (e.g. 407) in the interface
+-- file is the same as that for the compiler that's reading it
 checkVersion :: { () }
           : {-empty-}                  {% checkVersion Nothing }
           | INTEGER                    {% checkVersion (Just (fromInteger $1)) }
@@ -870,11 +920,10 @@ checkVersion :: { () }
 happyError :: P a
 happyError buf PState{ loc = loc } = PFailed (ifaceParseErr buf loc)
 
-data IfaceStuff = PIface       ParsedIface
-               | PIdInfo       [HsIdInfo RdrName]
-               | PType         RdrNameHsType
-               | PRules        [RdrNameRuleDecl]
-               | PDeprecs      [RdrNameDeprecation]
+data IfaceStuff = PIface          ParsedIface
+               | PIdInfo          [HsIdInfo RdrName]
+               | PType            RdrNameHsType
+               | PRulesAndDeprecs ([RdrNameRuleDecl], IfaceDeprecs)
 
 mk_con_decl name (ex_tvs, ex_ctxt) details loc = mkConDecl name ex_tvs ex_ctxt details loc
 }