2021-05-21 19:44:05 +00:00
|
|
|
#lang racket/base
|
|
|
|
|
|
|
|
(provide definition-unparser)
|
|
|
|
|
|
|
|
(require preserves)
|
|
|
|
(require racket/match)
|
|
|
|
(require (only-in racket/syntax format-symbol))
|
|
|
|
(require (only-in racket/list append-map))
|
|
|
|
|
|
|
|
(require "type.rkt")
|
2021-05-22 13:52:12 +00:00
|
|
|
(require "gen/schema.rkt")
|
2021-05-21 19:44:05 +00:00
|
|
|
|
|
|
|
(define (simple-pattern? p)
|
|
|
|
(match p
|
|
|
|
['any #t]
|
|
|
|
[(record 'atom _) #t]
|
|
|
|
[(record 'embedded _) #t]
|
|
|
|
[(record 'lit _) #t]
|
|
|
|
[(record 'ref _) #t]
|
|
|
|
[_ #f]))
|
|
|
|
|
|
|
|
(define (definition-unparser name def)
|
|
|
|
(define ty (definition-ty def))
|
|
|
|
`(define (,(format-symbol "~a->preserves" name) input)
|
|
|
|
,(match def
|
2021-05-22 13:47:13 +00:00
|
|
|
[(Definition-or p0 p1 pN)
|
2021-05-21 19:44:05 +00:00
|
|
|
`(match input
|
2021-05-22 13:47:13 +00:00
|
|
|
,@(for/list [(named-alt (in-list (list* p0 p1 pN)))
|
2021-05-21 19:44:05 +00:00
|
|
|
(alt-ty (in-list (map cadr (ty-union-variants ty))))]
|
2021-05-22 13:47:13 +00:00
|
|
|
(match-define (NamedAlternative variant-label-str pattern) named-alt)
|
2021-05-21 19:44:05 +00:00
|
|
|
`[,(deconstruct (format-symbol "~a-~a" name variant-label-str) #t alt-ty)
|
|
|
|
,(pattern->unparser pattern 'src)]))]
|
2021-05-22 13:47:13 +00:00
|
|
|
[(Definition-and p0 p1 pN)
|
2021-05-21 19:44:05 +00:00
|
|
|
`(match input
|
|
|
|
[,(deconstruct name #f ty)
|
|
|
|
(merge-preserves (lambda (a b) (if (equal? a b) a (error 'merge-preserves "Cannot merge")))
|
|
|
|
,@(append-map
|
|
|
|
(lambda (named-pat)
|
|
|
|
(if (simple-pattern? named-pat)
|
|
|
|
'()
|
|
|
|
(list (pattern->unparser named-pat 'src))))
|
2021-05-22 13:47:13 +00:00
|
|
|
(list* p0 p1 pN)))])]
|
|
|
|
[(Definition-Pattern pattern)
|
2021-05-21 19:44:05 +00:00
|
|
|
`(match input
|
|
|
|
[,(deconstruct name #f ty)
|
|
|
|
,(pattern->unparser pattern 'src)])])))
|
|
|
|
|
|
|
|
(define (deconstruct name wrap? ty)
|
|
|
|
(match ty
|
|
|
|
[(ty-record fields) `(,name ,@(map escape (map car fields)))]
|
|
|
|
[(ty-unit) (if wrap? `(,name) '(? void?))]
|
|
|
|
[_ (if wrap? `(,name src) 'src)]))
|
|
|
|
|
|
|
|
(define (pattern->unparser pattern src-stx)
|
2021-05-22 13:47:13 +00:00
|
|
|
(match (unwrap pattern)
|
|
|
|
[(NamedSimplePattern_ n p) (pattern->unparser p (escape n))]
|
|
|
|
[(SimplePattern-any) src-stx]
|
|
|
|
[(SimplePattern-atom _) src-stx]
|
|
|
|
[(SimplePattern-embedded) (error 'pattern-parser "Embedded not yet implemented")]
|
|
|
|
[(SimplePattern-lit v) `',v]
|
2021-05-24 08:09:17 +00:00
|
|
|
[(SimplePattern-seqof variable-pat)
|
2021-05-21 19:44:05 +00:00
|
|
|
`(for/list [(item (in-list ,src-stx))] ,(pattern->unparser variable-pat 'item))]
|
2021-05-24 08:09:17 +00:00
|
|
|
[(SimplePattern-setof pat)
|
2021-05-21 19:44:05 +00:00
|
|
|
`(for/set [(item (in-set ,src-stx))] ,(pattern->unparser pat 'item))]
|
2021-05-24 08:09:17 +00:00
|
|
|
[(SimplePattern-dictof key-pat value-pat)
|
2021-05-21 19:44:05 +00:00
|
|
|
`(for/hash [((key value) (in-dict ,src-stx))]
|
|
|
|
(values ,(pattern->unparser key-pat 'key)
|
|
|
|
,(pattern->unparser value-pat 'value)))]
|
2021-05-24 08:09:17 +00:00
|
|
|
[(SimplePattern-Ref (Ref '() name)) `(,(format-symbol "~a->preserves" name) ,src-stx)]
|
|
|
|
[(SimplePattern-Ref (Ref module-path name))
|
|
|
|
(error 'pattern-parser "Ref with non-empty module path not yet implemented")]
|
2021-05-22 13:47:13 +00:00
|
|
|
[(CompoundPattern-rec label-pat fields-pat)
|
2021-05-21 19:44:05 +00:00
|
|
|
`(record ,(pattern->unparser label-pat src-stx) ,(pattern->unparser fields-pat src-stx))]
|
2021-05-22 13:47:13 +00:00
|
|
|
[(CompoundPattern-tuple named-pats)
|
2021-05-21 19:44:05 +00:00
|
|
|
`(list ,@(for/list [(p (in-list named-pats))] (pattern->unparser p src-stx)))]
|
2021-05-24 08:09:17 +00:00
|
|
|
[(CompoundPattern-tuple* fixed-named-pats variable-named-pat)
|
2021-05-21 19:44:05 +00:00
|
|
|
`(list* ,@(for/list [(p (in-list fixed-named-pats))] (pattern->unparser p src-stx))
|
2021-05-24 08:09:17 +00:00
|
|
|
,(pattern->unparser variable-named-pat src-stx))]
|
2021-05-22 13:47:13 +00:00
|
|
|
[(CompoundPattern-dict (hash-table (keys pats) ...))
|
2021-05-21 19:44:05 +00:00
|
|
|
`(hash ,@(append-map (lambda (key pat)
|
|
|
|
(list `',key (pattern->unparser (add-name-if-absent key pat) src-stx)))
|
|
|
|
keys pats))]))
|