[project @ 1996-06-05 06:44:31 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         SigConverter(..),
18         SrcFile(..),
19         SrcFun(..),
20         SrcLine(..),
21
22         readInteger
23     ) where
24
25 IMP_Ubiq()
26
27 import HsSyn
28 import RdrHsSyn
29 import Util             ( panic )
30
31 #ifdef REALLY_HASKELL_1_3
32 ord = fromEnum :: Char -> Int
33 #endif
34
35 type RdrId   = RdrName
36 type SrcLine = Int
37 type SrcFile = FAST_STRING
38 type SrcFun  = RdrName
39 \end{code}
40
41 \begin{code}
42 data RdrBinding
43   = RdrNullBind
44   | RdrAndBindings      RdrBinding RdrBinding
45
46   | RdrTyDecl           RdrNameTyDecl
47   | RdrFunctionBinding  SrcLine [RdrMatch]
48   | RdrPatternBinding   SrcLine [RdrMatch]
49   | RdrClassDecl        RdrNameClassDecl
50   | RdrInstDecl         RdrNameInstDecl
51   | RdrDefaultDecl      RdrNameDefaultDecl
52
53                         -- signatures are mysterious; we can't
54                         -- tell if its a Sig or a ClassOpSig,
55                         -- so we just save the pieces:
56   | RdrTySig            [RdrName]           -- vars getting sigs
57                         RdrNamePolyType     -- the type
58                         SrcLoc
59
60   -- user pragmas come in in a Sig-ish way/form...
61   | RdrSpecValSig       [RdrNameSig]
62   | RdrInlineValSig     RdrNameSig
63   | RdrDeforestSig      RdrNameSig
64   | RdrMagicUnfoldingSig RdrNameSig
65   | RdrSpecInstSig      RdrNameSpecInstSig
66   | RdrSpecDataSig      RdrNameSpecDataSig
67
68 type SigConverter = RdrBinding {- a Sig -} -> [RdrNameSig]
69 \end{code}
70
71 \begin{code}
72 data RdrMatch
73   = RdrMatch_NoGuard
74              SrcLine SrcFun
75              RdrNamePat
76              RdrNameHsExpr
77              RdrBinding
78
79   | RdrMatch_Guards
80              SrcLine SrcFun
81              RdrNamePat
82              [(RdrNameHsExpr, RdrNameHsExpr)]
83              -- (guard,         expr)
84              RdrBinding
85 \end{code}
86
87 Unscramble strings representing oct/dec/hex integer literals:
88 \begin{code}
89 readInteger :: String -> Integer
90
91 readInteger ('-' : xs)       = - (readInteger xs)
92 readInteger ('0' : 'o' : xs) = chk (stoo 0 xs)
93 readInteger ('0' : 'x' : xs) = chk (stox 0 xs)
94 readInteger ['0']            = 0    -- efficiency shortcut?
95 readInteger ['1']            = 1    -- ditto?
96 readInteger xs               = chk (stoi 0 xs)
97
98 chk (i, "")   = i
99 chk (i, junk) = panic ("readInteger: junk after reading:"++junk)
100
101 stoo, stoi, stox :: Integer -> String -> (Integer, String)
102
103 stoo a (c:cs) | is_oct c  = stoo (a*8 + ord_ c - ord_0) cs
104 stoo a cs                 = (a, cs)
105
106 stoi a (c:cs) | isDigit c = stoi (a*10 + ord_ c - ord_0) cs
107 stoi a cs                 = (a, cs)
108
109 stox a (c:cs) | isDigit c = stox (a_16_ord_c - ord_0)      cs
110               | is_hex  c = stox (a_16_ord_c - ord_a + 10) cs
111               | is_Hex  c = stox (a_16_ord_c - ord_A + 10) cs
112               where a_16_ord_c = a*16 + ord_ c
113 stox a cs = (a, cs)
114
115 is_oct c = c >= '0' && c <= '7'
116 is_hex c = c >= 'a' && c <= 'f'
117 is_Hex c = c >= 'A' && c <= 'F'
118
119 ord_ c = toInteger (ord c)
120
121 ord_0, ord_a, ord_A :: Integer
122 ord_0 = ord_ '0'; ord_a = ord_ 'a'; ord_A = ord_ 'A'
123 \end{code}