| 1. What is Frown? |
Frown is an LALR(k) parser generator for Haskell 98 written in Haskell 98.
Its salient features are:
| 2. Documentation |
Frown comes with extensive documentation available in a variety of formats:
| 3. Download |
Source distribution of Frown:
cabal-get install FrownOS-specific distributions:
dev-haskell/frown).
You can install Frown with the command ACCEPT_KEYWORDS="~x86" emerge frown.
| 4. A toy example |
Here is a simple grammar that specifies a character-based parser for function applications (Examples/Call.lg). The grammar is enclosed in special curly braces; the rest is Haskell source.
> import Char
>
> data Expr = Ident Char
> | Apply Expr Expr
> deriving (Show)
>
> type Terminal = Char
>
> %{
>
> Terminal = guard {isAlpha} as "letter"
> | '('
> | ')';
>
> Nonterminal = expr {Expr};
>
> expr {Ident x} : "letter" {x};
> {Apply t u} | expr {t}, '(', expr {u}, ')';
>
> }%
>
> frown ts = fail "syntax error"
|
Given this grammar, Frown generates (frown --suffix Call.lg) the following parser (Haskell part omitted).
data Stack = Empty
| T_1_4 Stack Terminal
| T_1_2 Stack Expr
| T_2_3 Stack
| T_2_6 Stack
| T_5_6 Stack
| T_5_7 Stack
| T_6_4 Stack Terminal
| T_6_5 Stack Expr
data Nonterminal = Expr Expr
expr tr = parse_1 tr Empty >>= (\ (Expr v1) -> return (v1))
parse_1 (v1 : tr) st | isAlpha v1 = parse_4 tr (T_1_4 st v1)
parse_1 ts st = frown ts
parse_2 tr@[] st = parse_3 tr (T_2_3 st)
parse_2 ('(' : tr) st = parse_6 tr (T_2_6 st)
parse_2 ts st = frown ts
parse_3 ts (T_2_3 (T_1_2 st v1)) = return (Expr v1)
parse_4 ts (T_1_4 st x) = parse_2 ts (T_1_2 st (Ident x))
parse_4 ts (T_6_4 st x) = parse_5 ts (T_6_5 st (Ident x))
parse_5 ('(' : tr) st = parse_6 tr (T_5_6 st)
parse_5 (')' : tr) st = parse_7 tr (T_5_7 st)
parse_5 ts st = frown ts
parse_6 (v1 : tr) st | isAlpha v1 = parse_4 tr (T_6_4 st v1)
parse_6 ts st = frown ts
parse_7 ts (T_5_7 (T_6_5 (T_2_6 (T_1_2 st t)) u))
= parse_2 ts (T_1_2 st (Apply t u))
parse_7 ts (T_5_7 (T_6_5 (T_5_6 (T_6_5 st t)) u))
= parse_5 ts (T_6_5 st (Apply t u))
|
Readers familiar with LR parsing will possibly recognize the underlying LR(0) automaton: each state has become a function that takes the input and a stack of transitions as argument.
| 5. Changelog |
1 November 2005: initial release (0.6, beta quality)
15 December 2005: improved look-ahead computation (0.6.1, beta quality)