2 ## (c) 2008 Utz-Uwe Haus <lisp@uuhaus.de>
5 ## This code is free software; you can redistribute it and/or modify
6 ## it under the terms of the version 2.1 of the GNU Lesser General
7 ## Public License as published by the Free Software Foundation, as
8 ## clarified by the lisp prequel found in LICENSE.
10 ## This code is distributed in the hope that it will be useful, but
11 ## without any warranty; without even the implied warranty of
12 ## merchantability or fitness for a particular purpose. See the GNU
13 ## Lesser General Public License for more details.
15 ## Version 2.1 of the GNU Lesser General Public License is in the file
16 ## LICENSE that was distributed with this file. If it is not
17 ## present, you can access it from
18 ## http://www.gnu.org/copyleft/lgpl.txt (until superseded by a
19 ## newer version) or write to the Free Software Foundation, Inc., 59
20 ## Temple Place, Suite 330, Boston, MA 02111-1307 USA
24 ## PEG syntax in PEG as in the original report
26 # Process this file with an existing PEG parser to bootstrap.
27 # The output needs to be adjusted by replacing the package OPOSSUM
28 # by OPOSSUM-SYSTEM if you want to use it as a replacement of
29 # the shipped pegparser-boot.lisp
31 # This file needs a cleanup wrt. linebreaks once we bootstrapped off
32 # the metapeg parser which is crippled.
35 PEG-Grammar <- Spacing Definition+ EndOfFile {
36 `((eval-when (:compile-toplevel :load-toplevel :execute)
37 (declaim (optimize (speed 0) (safety 3) (debug 3))))
38 (defun opossum-parser ()
39 (let ((*context* (make-instance 'context :start-index 0))) #'
40 (funcall (|PEG-Grammar|) 0)))
44 Definition <- Identifier LEFTARROW Expression {
45 `(,(opossum::make-name (first data)) #'(lambda () ,(third data))) ;'
48 Expression <- Sequence (SLASH Sequence)* { (if (null (second data))
50 (let ((tail (second (cadr data))))
51 (if (equal (first tail) 'seq)
52 `(seq ,(first data) ,@(rest tail))
53 `(seq ,(first data) ,tail)))) ;'
56 Sequence <- Prefix* { `(many ,(first data)) }
58 Prefix <- (AND Suffix) {
59 `(follow ,(second data))
61 `(negate ,(second data))
64 Suffix <- Primary QUESTION { `(optional ,(first data))
65 } / Primary STAR { `(many ,(first data))
66 } / Primary PLUS { `(many1 ,(first data)) }
68 Primary <- Identifier !LEFTARROW { (first data)
69 } / OPEN Expression CLOSE { (second data)
70 } / Literal { (first data)
71 } / Class { (first data)
72 } / DOT { `(match-any-char ,data) }
75 Identifier <- [a-zA-Z_] [a-zA-Z0-9_]* Spacing { (concatenate 'string (first data) (second data)) }
77 Literal <- ['] (!['] Char)* ['] Spacing {
79 } / ["] (!["] Char)* ["] Spacing {
82 Class <- "[" (!"]" Range)* "]" Spacing { (second data) }
84 Range <- Char "-" Char {
85 `(match-char-range ,(first data) ,(third data))
86 } / Char { (first data) }
87 # FIXME: needs to be repaired when metapeg traces are gone
88 Char <- "\\" [nrt'"] { data
92 } / "\\" [0-2] [0-7] [0-7] { `(match-octal-char-code ,(second data) ,(third data) ,(fourth data))
93 } / "\\" [0-7] [0-7]? {
95 `(match-octal-char-code 0 ,(second data) ,(third data))
96 `(match-octal-char-code 0 0 ,(second data)))
97 } / !"\\" . { (last data) }
100 LEFTARROW <- "<-" Spacing { (first data) }
101 SLASH <- "/" Spacing { (first data) }
102 AND <- "&" Spacing { (first data) }
103 NOT <- "!" Spacing { (first data) }
104 QUESTION <- "?" Spacing { (first data) }
105 STAR <- "*" Spacing { (first data) }
106 PLUS <- "+" Spacing { (first data) }
107 OPEN <- "(" Spacing { (first data) }
108 CLOSE <- ")" Spacing { (first data) }
109 DOT <- "." Spacing { (first data) }
110 Spacing <- (Space / Comment)*
111 Comment <- "#" (!EndOfLine .)* EndOfLine
112 Space <- " " / "\t" / EndOfLine
113 EndOfLine <- "\r\n" / "\n" / "\r"