[project @ 1996-03-19 08:58:34 by partain]
[ghc-hetmet.git] / ghc / compiler / reader / PrefixSyn.lhs
1 %
2 % (c) The GRASP/AQUA Project, Glasgow University, 1992-1996
3 %
4 \section[PrefixSyn]{``Prefix-form'' syntax}
5
6 This module contains an algebraic data type into which a prefix form
7 string from the current Haskell parser is converted.  Given in an
8 order that follows the \tr{Prefix_Form} document.
9
10 \begin{code}
11 #include "HsVersions.h"
12
13 module PrefixSyn (
14         RdrBinding(..),
15         RdrId(..),
16         RdrMatch(..),
17         RdrTySigPragmas(..),
18         SigConverter(..),
19         SrcFile(..),
20         SrcFun(..),
21         SrcLine(..),
22
23         readInteger
24     ) where
25
26 import Ubiq{-uitous-}
27
28 import HsSyn
29 import RdrHsSyn
30 import Util             ( panic )
31
32 type RdrId   = ProtoName
33 type SrcLine = Int
34 type SrcFile = FAST_STRING
35 type SrcFun  = ProtoName
36 \end{code}
37
38 \begin{code}
39 data RdrBinding
40   = RdrNullBind
41   | RdrAndBindings      RdrBinding RdrBinding
42
43   | RdrTyDecl           ProtoNameTyDecl
44   | RdrFunctionBinding  SrcLine [RdrMatch]
45   | RdrPatternBinding   SrcLine [RdrMatch]
46   | RdrClassDecl        ProtoNameClassDecl
47   | RdrInstDecl         ProtoNameInstDecl
48   | RdrDefaultDecl      ProtoNameDefaultDecl
49   | RdrIfaceImportDecl  (IfaceImportDecl ProtoName)
50   | RdrIfaceFixities    [ProtoNameFixityDecl]
51
52                         -- signatures are mysterious; we can't
53                         -- tell if its a Sig or a ClassOpSig,
54                         -- so we just save the pieces:
55   | RdrTySig            [ProtoName]         -- vars getting sigs
56                         ProtoNamePolyType   -- the type
57                         RdrTySigPragmas     -- val/class-op pragmas
58                         SrcLoc
59
60   -- user pragmas come in in a Sig-ish way/form...
61   | RdrSpecValSig       [ProtoNameSig]
62   | RdrInlineValSig     ProtoNameSig
63   | RdrDeforestSig      ProtoNameSig
64   | RdrMagicUnfoldingSig ProtoNameSig
65   | RdrSpecInstSig      ProtoNameSpecInstSig
66   | RdrSpecDataSig      ProtoNameSpecDataSig
67
68 data RdrTySigPragmas
69   = RdrNoPragma
70   | RdrGenPragmas       ProtoNameGenPragmas
71   | RdrClassOpPragmas   ProtoNameClassOpPragmas
72
73 type SigConverter = RdrBinding {- a RdrTySig... -} -> [ProtoNameSig]
74 \end{code}
75
76 \begin{code}
77 data RdrMatch
78   = RdrMatch_NoGuard
79              SrcLine SrcFun
80              ProtoNamePat
81              ProtoNameHsExpr
82              RdrBinding
83
84   | RdrMatch_Guards
85              SrcLine SrcFun
86              ProtoNamePat
87              [(ProtoNameHsExpr, ProtoNameHsExpr)]
88              -- (guard,         expr)
89              RdrBinding
90 \end{code}
91
92 Unscramble strings representing oct/dec/hex integer literals:
93 \begin{code}
94 readInteger :: String -> Integer
95
96 readInteger ('-' : xs)       = - (readInteger xs)
97 readInteger ('0' : 'o' : xs) = chk (stoo 0 xs)
98 readInteger ('0' : 'x' : xs) = chk (stox 0 xs)
99 readInteger ['0']            = 0    -- efficiency shortcut?
100 readInteger ['1']            = 1    -- ditto?
101 readInteger xs               = chk (stoi 0 xs)
102
103 chk (i, "")   = i
104 chk (i, junk) = panic ("readInteger: junk after reading:"++junk)
105
106 stoo, stoi, stox :: Integer -> String -> (Integer, String)
107
108 stoo a (c:cs) | is_oct c  = stoo (a*8 + ord_ c - ord_0) cs
109 stoo a cs                 = (a, cs)
110
111 stoi a (c:cs) | isDigit c = stoi (a*10 + ord_ c - ord_0) cs
112 stoi a cs                 = (a, cs)
113
114 stox a (c:cs) | isDigit c = stox (a_16_ord_c - ord_0)      cs
115               | is_hex  c = stox (a_16_ord_c - ord_a + 10) cs
116               | is_Hex  c = stox (a_16_ord_c - ord_A + 10) cs
117               where a_16_ord_c = a*16 + ord_ c
118 stox a cs = (a, cs)
119
120 is_oct c = c >= '0' && c <= '7'
121 is_hex c = c >= 'a' && c <= 'f'
122 is_Hex c = c >= 'A' && c <= 'F'
123
124 ord_ c = toInteger (ord c)
125
126 ord_0, ord_a, ord_A :: Integer
127 ord_0 = ord_ '0'; ord_a = ord_ 'a'; ord_A = ord_ 'A'
128 \end{code}