From 28d6025a67a6b4c6ee038dd81ca89040406360c6 Mon Sep 17 00:00:00 2001 From: Case Duckworth Date: Tue, 16 May 2023 23:04:27 -0500 Subject: Initial commit (chicken version) --- fff.parse.ss | 125 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 125 insertions(+) create mode 100644 fff.parse.ss (limited to 'fff.parse.ss') diff --git a/fff.parse.ss b/fff.parse.ss new file mode 100644 index 0000000..0ff7806 --- /dev/null +++ b/fff.parse.ss @@ -0,0 +1,125 @@ +;;; Syntax +;; an fff document translates to a key-value object containing lists or other +;; objects. Nesting objects are accomplished using references, which start with @. + +;; # comments start with '#' and go to the end of the line. +;; fff-object:: +;; key: value +;; key2: value2 +;; key3: @reference # a reference refers to another defined object +;; +;; # lists are similar to objects, just without keys +;; fff-list:: +;; : item1 +;; : item2 +;; : item3 +;; +;; name: something # this is okay too + +(import (scheme base) + (scheme case-lambda) + (utf8) + (comparse) + (srfi 14)) + +(define anything + (in char-set:full)) + +(define nl+ws + (sequence* ((_ (is #\newline)) + (_ ws*)) + (result " "))) + +(define end + (any-of nl+ws + end-of-input)) + +(define end* + (any-of (one-or-more nl+ws) + end-of-input)) + +(define (escaped parser) + (preceded-by (is #\\) parser)) + +(define (unescaped parser) + (none-of* (escaped parser) + parser)) + +(define ws + (in char-set:blank)) + +(define ws* + (zero-or-more ws)) + +(define nonl + (in (char-set-delete char-set:full #\newline))) + +(define fff-val + (sequence* ((@? (maybe (escaped (is #\@)))) + (v (as-string + (zero-or-more + (any-of (escaped nl+ws) + (none-of* nl+ws item)))))) + (result (if @? + (string-append "@" v) + v)))) + +(define fff-key + (as-string + (one-or-more + (all-of (any-of (escaped (is #\:)) + (escaped nl+ws) + (none-of* (is #\:) nl+ws item)))))) + +(define fff-ref + (sequence* ((_ (unescaped (is #\@))) + (k fff-key)) + (result (cons 'ref k)))) + +(define fff-comment + (sequence* ((_ (one-or-more (is #\#))) + (_ ws*) + (c (as-string (zero-or-more nonl))) + (_ end*)) + (result (cons 'comment c)))) + +(define fff-comment+ + (bind (one-or-more fff-comment) + (lambda (xs) + (result (cons 'comment (map cdr xs)))))) + +(define fff-item + (sequence* ((k (maybe fff-key)) + (_ ws*) + (_ (is #\:)) + (_ ws*) + (v (any-of fff-ref fff-val)) + (_ end)) + (result (cons k v)))) + +(define fff-item* + (sequence* ((k fff-key) + (_ ws*) + (_ (is #\:)) + (_ ws*) + (v (any-of fff-ref fff-val)) + (_ end*)) + (result (cons k v)))) + +(define fff-object + (sequence* ((name fff-key) + (_ ws*) + (_ (sequence (is #\:) (is #\:) (is #\newline))) + (contents (one-or-more + (any-of fff-comment+ + fff-item))) + (_ end*)) + (result (cons name contents)))) + +(define fff-document + (zero-or-more (any-of fff-comment+ + fff-object + fff-item*))) + +(define (parse-fff x) + (parse fff-document x)) -- cgit 1.4.1-21-gabe81