(define (parser pctx offset) (begin (define (parse_program) (let* ((parser (glyph-seq (many (lambda (ctx offset) (((parse_ws)) ctx offset))) (many1 (lambda (ctx offset) (((parse_rule)) ctx offset))) (list (quote glyphaction) (lambda (data) (quasiquote (define (parser pctx offset) (begin (unquote-splicing (second data)) (((parse_program)) pctx offset))))))))) (lambda () (lambda (ctx offset) (let* ((ctx2 (parser ctx offset))) (if (ctx-failed? ctx2) (fail) (succeed (clone-ctx ctx "program") (ctx-value ctx2) (ctx-start-index ctx2) (ctx-end-index ctx2)))))))) (define (parse_rule) (let* ((parser (glyph-seq (lambda (ctx offset) (((parse_id)) ctx offset)) (many (lambda (ctx offset) (((parse_ws)) ctx offset))) (match-string "<-") (many (lambda (ctx offset) (((parse_ws)) ctx offset))) (lambda (ctx offset) (((parse_ordered-expr-list)) ctx offset)) (many (lambda (ctx offset) (((parse_ws_or_nl)) ctx offset))) (list (quote glyphaction) (lambda (data) (quasiquote (define ((unquote (make-name (first data)))) (let* ((parser (unquote (fifth data)))) (lambda () (lambda (ctx offset) (let* ((ctx2 (parser ctx offset))) (if (ctx-failed? ctx2) (fail) (succeed (clone-ctx ctx (unquote (first data))) (ctx-value ctx2) (ctx-start-index ctx2) (ctx-end-index ctx2)))))))))))))) (lambda () (lambda (ctx offset) (let* ((ctx2 (parser ctx offset))) (if (ctx-failed? ctx2) (fail) (succeed (clone-ctx ctx "rule") (ctx-value ctx2) (ctx-start-index ctx2) (ctx-end-index ctx2)))))))) (define (parse_ordered-expr-list) (let* ((parser (either (glyph-seq (lambda (ctx offset) (((parse_expr-list)) ctx offset)) (many (lambda (ctx offset) (((parse_ws)) ctx offset))) (match-string "/") (many (lambda (ctx offset) (((parse_ws)) ctx offset))) (lambda (ctx offset) (((parse_ordered-expr-list)) ctx offset)) (list (quote glyphaction) (lambda (data) (let ((tail (fifth data))) (if (eq? (first tail) (quote either)) (quasiquote (either (unquote (first data)) (unquote-splicing (cdr tail)))) (quasiquote (either (unquote (first data)) (unquote (fifth data))))))))) (glyph-seq (lambda (ctx offset) (((parse_expr-list)) ctx offset)) (list (quote glyphaction) (lambda (data) (first data))))))) (lambda () (lambda (ctx offset) (let* ((ctx2 (parser ctx offset))) (if (ctx-failed? ctx2) (fail) (succeed (clone-ctx ctx "ordered-expr-list") (ctx-value ctx2) (ctx-start-index ctx2) (ctx-end-index ctx2)))))))) (define (parse_expr-list) (let* ((parser (glyph-seq (lambda (ctx offset) (((parse_expr)) ctx offset)) (many (glyph-seq (many1 (lambda (ctx offset) (((parse_ws)) ctx offset))) (lambda (ctx offset) (((parse_expr-list)) ctx offset)))) (list (quote glyphaction) (lambda (data) (if (or (null? (second data)) (and (not (pair? (second data))) (string=? (second data) ""))) (first data) (let ((tail (second (first (second data))))) (if (eq? (first tail) (quote glyph-seq)) (quasiquote (glyph-seq (unquote (first data)) (unquote-splicing (cdr tail)))) (quasiquote (glyph-seq (unquote (first data)) (unquote tail))))))))))) (lambda () (lambda (ctx offset) (let* ((ctx2 (parser ctx offset))) (if (ctx-failed? ctx2) (fail) (succeed (clone-ctx ctx "expr-list") (ctx-value ctx2) (ctx-start-index ctx2) (ctx-end-index ctx2)))))))) (define (parse_expr) (let* ((parser (either (glyph-seq (lambda (ctx offset) (((parse_simple-expr)) ctx offset)) (match-string "*") (list (quote glyphaction) (lambda (data) (quasiquote (many (unquote (first data))))))) (glyph-seq (lambda (ctx offset) (((parse_simple-expr)) ctx offset)) (match-string "+") (list (quote glyphaction) (lambda (data) (quasiquote (many1 (unquote (first data))))))) (glyph-seq (lambda (ctx offset) (((parse_simple-expr)) ctx offset)) (match-string "?") (list (quote glyphaction) (lambda (data) (quasiquote (optional (unquote (first data))))))) (glyph-seq (lambda (ctx offset) (((parse_simple-expr)) ctx offset)) (list (quote glyphaction) (lambda (data) (first data))))))) (lambda () (lambda (ctx offset) (let* ((ctx2 (parser ctx offset))) (if (ctx-failed? ctx2) (fail) (succeed (clone-ctx ctx "expr") (ctx-value ctx2) (ctx-start-index ctx2) (ctx-end-index ctx2)))))))) (define (parse_simple-expr) (let* ((parser (either (glyph-seq (lambda (ctx offset) (((parse_string)) ctx offset)) (list (quote glyphaction) (lambda (data) (first data)))) (lambda (ctx offset) (((parse_action)) ctx offset)) (glyph-seq (match-string "@") (lambda (ctx offset) (((parse_id)) ctx offset)) (list (quote glyphaction) (lambda (data) (printf "{}") (quasiquote (match (unquote (second data))))))) (glyph-seq (lambda (ctx offset) (((parse_id)) ctx offset)) (list (quote glyphaction) (lambda (data) (make-scheme-call-rule-closure2 (make-name (first data)))))) (glyph-seq (lambda (ctx offset) (((parse_bracketed-rule)) ctx offset)) (list (quote glyphaction) (lambda (data) (first data)))) (match-string "!.") (glyph-seq (match-string "!") (lambda (ctx offset) (((parse_expr)) ctx offset)) (list (quote glyphaction) (lambda (data) (quasiquote (negate (unquote (second data))))))) (glyph-seq (lambda (ctx offset) (((parse_character-class)) ctx offset)) (list (quote glyphaction) (lambda (data) (first data)))) (glyph-seq (match-string ".") (list (quote glyphaction) (lambda (data) (quasiquote (match-any-char (quote dummy))))))))) (lambda () (lambda (ctx offset) (let* ((ctx2 (parser ctx offset))) (if (ctx-failed? ctx2) (fail) (succeed (clone-ctx ctx "simple-expr") (ctx-value ctx2) (ctx-start-index ctx2) (ctx-end-index ctx2)))))))) (define (parse_bracketed-rule) (let* ((parser (either (match-string "()") (glyph-seq (match-string "(") (many (lambda (ctx offset) (((parse_ws)) ctx offset))) (lambda (ctx offset) (((parse_ordered-expr-list)) ctx offset)) (many (lambda (ctx offset) (((parse_ws)) ctx offset))) (match-string ")") (list (quote glyphaction) (lambda (data) (third data))))))) (lambda () (lambda (ctx offset) (let* ((ctx2 (parser ctx offset))) (if (ctx-failed? ctx2) (fail) (succeed (clone-ctx ctx "bracketed-rule") (ctx-value ctx2) (ctx-start-index ctx2) (ctx-end-index ctx2)))))))) (define (parse_id) (let* ((parser (glyph-seq (many1 (match-char (quote (#\0 #\1 #\2 #\3 #\4 #\5 #\6 #\7 #\8 #\9 #\A #\B #\C #\D #\E #\F #\G #\H #\I #\J #\K #\L #\M #\N #\O #\P #\Q #\R #\S #\T #\U #\V #\W #\X #\Y #\Z #\a #\b #\c #\d #\e #\f #\g #\h #\i #\j #\k #\l #\m #\n #\o #\p #\q #\r #\s #\t #\u #\v #\w #\x #\y #\z #\- #\_)))) (list (quote glyphaction) (lambda (data) (char-list-to-string (first data))))))) (lambda () (lambda (ctx offset) (let* ((ctx2 (parser ctx offset))) (if (ctx-failed? ctx2) (fail) (succeed (clone-ctx ctx "id") (ctx-value ctx2) (ctx-start-index ctx2) (ctx-end-index ctx2)))))))) (define (parse_character-class) (let* ((parser (glyph-seq (match-string "[") (many1 (glyph-seq (lambda (ctx offset) (((parse_not_right_bracket)) ctx offset)) (match-any-char (quote dummy)))) (match-string "]") (list (quote glyphaction) (lambda (data) (quasiquote (match-char (quote (unquote (fix-escapes2 (zip-second (second data)))))))))))) (lambda () (lambda (ctx offset) (let* ((ctx2 (parser ctx offset))) (if (ctx-failed? ctx2) (fail) (succeed (clone-ctx ctx "character-class") (ctx-value ctx2) (ctx-start-index ctx2) (ctx-end-index ctx2)))))))) (define (parse_string) (let* ((parser (glyph-seq (match-char (quote (#\"))) (many (glyph-seq (negate (match-char (quote (#\")))) (match-any-char (quote dummy)))) (match-char (quote (#\"))) (list (quote glyphaction) (lambda (data) (quasiquote (match-string (unquote (char-list-to-string (zip-second (second data))))))))))) (lambda () (lambda (ctx offset) (let* ((ctx2 (parser ctx offset))) (if (ctx-failed? ctx2) (fail) (succeed (clone-ctx ctx "string") (ctx-value ctx2) (ctx-start-index ctx2) (ctx-end-index ctx2)))))))) (define (parse_action) (let* ((parser (glyph-seq (match-char (quote (#\{))) (many (either (lambda (ctx offset) (((parse_escaped-char)) ctx offset)) (lambda (ctx offset) (((parse_non-escaped-char)) ctx offset)))) (match-char (quote (#\}))) (list (quote glyphaction) (lambda (data) (make-glyph-action2 (char-list-to-string (fix-escapes2 (second data))))))))) (lambda () (lambda (ctx offset) (let* ((ctx2 (parser ctx offset))) (if (ctx-failed? ctx2) (fail) (succeed (clone-ctx ctx "action") (ctx-value ctx2) (ctx-start-index ctx2) (ctx-end-index ctx2)))))))) (define (parse_escaped-char) (let* ((parser (glyph-seq (match-char (quote (#\\))) (match-char (quote (#\}))) (list (quote glyphaction) (lambda (data) (second data)))))) (lambda () (lambda (ctx offset) (let* ((ctx2 (parser ctx offset))) (if (ctx-failed? ctx2) (fail) (succeed (clone-ctx ctx "escaped-char") (ctx-value ctx2) (ctx-start-index ctx2) (ctx-end-index ctx2)))))))) (define (parse_non-escaped-char) (let* ((parser (glyph-seq (negate (match-char (quote (#\})))) (match-any-char (quote dummy)) (list (quote glyphaction) (lambda (data) (second data)))))) (lambda () (lambda (ctx offset) (let* ((ctx2 (parser ctx offset))) (if (ctx-failed? ctx2) (fail) (succeed (clone-ctx ctx "non-escaped-char") (ctx-value ctx2) (ctx-start-index ctx2) (ctx-end-index ctx2)))))))) (define (parse_not_right_bracket) (let* ((parser (negate (match-string "]")))) (lambda () (lambda (ctx offset) (let* ((ctx2 (parser ctx offset))) (if (ctx-failed? ctx2) (fail) (succeed (clone-ctx ctx "not_right_bracket") (ctx-value ctx2) (ctx-start-index ctx2) (ctx-end-index ctx2)))))))) (define (parse_ws) (let* ((parser (match-char (quote (#\space #\tab))))) (lambda () (lambda (ctx offset) (let* ((ctx2 (parser ctx offset))) (if (ctx-failed? ctx2) (fail) (succeed (clone-ctx ctx "ws") (ctx-value ctx2) (ctx-start-index ctx2) (ctx-end-index ctx2)))))))) (define (parse_nl) (let* ((parser (match-char (quote (#\newline))))) (lambda () (lambda (ctx offset) (let* ((ctx2 (parser ctx offset))) (if (ctx-failed? ctx2) (fail) (succeed (clone-ctx ctx "nl") (ctx-value ctx2) (ctx-start-index ctx2) (ctx-end-index ctx2)))))))) (define (parse_ws_or_nl) (let* ((parser (either (lambda (ctx offset) (((parse_ws)) ctx offset)) (lambda (ctx offset) (((parse_nl)) ctx offset))))) (lambda () (lambda (ctx offset) (let* ((ctx2 (parser ctx offset))) (if (ctx-failed? ctx2) (fail) (succeed (clone-ctx ctx "ws_or_nl") (ctx-value ctx2) (ctx-start-index ctx2) (ctx-end-index ctx2)))))))) (((parse_program)) pctx offset)))