e29eb945f0e444397bf183d6707dd1c63af0bce0
[ghc-hetmet.git] / compiler / main / ParsePkgConf.y
1 {
2 module ParsePkgConf( loadPackageConfig ) where
3
4 #include "HsVersions.h"
5
6 import PackageConfig
7 import Lexer
8 import DynFlags
9 import FastString
10 import StringBuffer
11 import ErrUtils  ( mkLocMessage )
12 import SrcLoc
13 import Outputable
14 import Panic     ( GhcException(..) )
15 import Control.Exception ( throwDyn )
16
17 }
18
19 %token
20  '{'            { L _ ITocurly }
21  '}'            { L _ ITccurly }
22  '['            { L _ ITobrack }
23  ']'            { L _ ITcbrack }
24  ','            { L _ ITcomma }
25  '='            { L _ ITequal }
26  VARID          { L _ (ITvarid    $$) }
27  CONID          { L _ (ITconid    $$) }
28  STRING         { L _ (ITstring   $$) }
29  INT            { L _ (ITinteger  $$) }
30
31 %monad { P } { >>= } { return }
32 %lexer { lexer } { L _ ITeof }
33 %name parse
34 %tokentype { Located Token }
35 %%
36
37 pkgconf :: { [ PackageConfig ] }
38         : '[' ']'                       { [] }
39         | '[' pkgs ']'                  { reverse $2 }
40
41 pkgs    :: { [ PackageConfig ] }
42         : pkg                           { [ $1 ] }
43         | pkgs ',' pkg                  { $3 : $1 }
44
45 pkg     :: { PackageConfig }
46         : CONID '{' fields '}'          { $3 defaultPackageConfig }
47
48 fields  :: { PackageConfig -> PackageConfig }
49         : field                         { \p -> $1 p }
50         | fields ',' field              { \p -> $1 ($3 p) }
51
52 field   :: { PackageConfig -> PackageConfig }
53         : VARID '=' pkgid
54                 {% case unpackFS $1 of
55                         "package"     -> return (\p -> p{package = $3})
56                         _other        -> happyError
57                 }
58
59         | VARID '=' STRING              { id }
60                 -- we aren't interested in the string fields, they're all
61                 -- boring (copyright, maintainer etc.)
62                         
63         | VARID '=' CONID
64                 {% case unpackFS $1 of {
65                         "exposed" -> 
66                            case unpackFS $3 of {
67                                 "True"  -> return (\p -> p{exposed=True});
68                                 "False" -> return (\p -> p{exposed=False});
69                                 _       -> happyError };
70                         "license" -> return id; -- not interested
71                         _         -> happyError }
72                 }
73
74         | VARID '=' CONID STRING        { id }
75                 -- another case of license
76
77         | VARID '=' strlist             
78                 {\p -> case unpackFS $1 of
79                         "exposedModules"    -> p{exposedModules    = $3}
80                         "hiddenModules"     -> p{hiddenModules     = $3}
81                         "importDirs"        -> p{importDirs        = $3}
82                         "libraryDirs"       -> p{libraryDirs       = $3}
83                         "hsLibraries"       -> p{hsLibraries       = $3}
84                         "extraLibraries"    -> p{extraLibraries    = $3}
85                         "extraGHCiLibraries"-> p{extraGHCiLibraries= $3}
86                         "includeDirs"       -> p{includeDirs       = $3}
87                         "includes"          -> p{includes          = $3}
88                         "hugsOptions"       -> p{hugsOptions       = $3}
89                         "ccOptions"         -> p{ccOptions         = $3}
90                         "ldOptions"         -> p{ldOptions         = $3}
91                         "frameworkDirs"     -> p{frameworkDirs     = $3}
92                         "frameworks"        -> p{frameworks        = $3}
93                         "haddockInterfaces" -> p{haddockInterfaces = $3}
94                         "haddockHTMLs"      -> p{haddockHTMLs      = $3}
95                         "depends"           -> p{depends = []}
96                                 -- empty list only, non-empty handled below
97                         other -> p
98                 }
99
100         | VARID '=' pkgidlist
101                 {% case unpackFS $1 of
102                         "depends"     -> return (\p -> p{depends = $3})
103                         _other        -> happyError
104                 }
105
106 pkgid   :: { PackageIdentifier }
107         : CONID '{' VARID '=' STRING ',' VARID '=' version '}'
108                         { PackageIdentifier{ pkgName = unpackFS $5, 
109                                              pkgVersion = $9 } }
110
111 version :: { Version }
112         : CONID '{' VARID '=' intlist ',' VARID '=' strlist '}'
113                         { Version{ versionBranch=$5, versionTags=$9 } }
114
115 pkgidlist :: { [PackageIdentifier] }
116         : '[' pkgids ']'                { $2 }
117         -- empty list case is covered by strlist, to avoid conflicts
118
119 pkgids  :: { [PackageIdentifier] }
120         : pkgid                         { [ $1 ] }
121         | pkgid ',' pkgids              { $1 : $3 }
122
123 intlist :: { [Int] }
124         : '[' ']'                       { [] }
125         | '[' ints ']'                  { $2 }
126
127 ints    :: { [Int] }
128         : INT                           { [ fromIntegral $1 ] }
129         | INT ',' ints                  { fromIntegral $1 : $3 }
130
131 strlist :: { [String] }
132         : '[' ']'                       { [] }
133         | '[' strs ']'                  { $2 }
134
135 strs    :: { [String] }
136         : STRING                        { [ unpackFS $1 ] }
137         | STRING ',' strs               { unpackFS $1 : $3 }
138
139 {
140 happyError :: P a
141 happyError = srcParseFail
142
143 loadPackageConfig :: FilePath -> IO [PackageConfig]
144 loadPackageConfig conf_filename = do
145    buf <- hGetStringBuffer conf_filename
146    let loc  = mkSrcLoc (mkFastString conf_filename) 1 0
147    case unP parse (mkPState buf loc defaultDynFlags) of
148         PFailed span err -> 
149            throwDyn (InstallationError (showSDoc (mkLocMessage span err)))
150
151         POk _ pkg_details -> do
152             return pkg_details
153 }