-
Notifications
You must be signed in to change notification settings - Fork 16
/
binding.rkt
74 lines (62 loc) · 2.45 KB
/
binding.rkt
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
#lang racket/base
(require racket/contract/base)
(provide
wrapper-id
(contract-out
[wrapper-binding? (-> any/c boolean?)]
[wrapper-binding-type (-> wrapper-binding? wrapper-type?)]
[wrapper-binding-descriptor (-> wrapper-binding? identifier?)]
[wrapper-binding-predicate (-> wrapper-binding? identifier?)]
[wrapper-binding-constructor (-> wrapper-binding? identifier?)]
[wrapper-binding-accessor (-> wrapper-binding? identifier?)]))
(module+ private-constructor
(provide
(contract-out
[wrapper-binding
(-> #:type wrapper-type?
#:descriptor identifier?
#:predicate identifier?
#:constructor identifier?
#:accessor identifier?
#:pattern identifier?
#:macro (-> syntax? syntax?)
wrapper-binding?)])))
(require (for-template racket/base
racket/match)
racket/sequence
racket/syntax
rebellion/type/wrapper/base
syntax/parse)
;@------------------------------------------------------------------------------
(struct wrapper-binding
(type descriptor predicate constructor accessor pattern macro)
#:omit-define-syntaxes
#:constructor-name constructor:wrapper-binding
#:property prop:match-expander
(λ (this stx)
(define/with-syntax pattern (wrapper-binding-pattern this))
(syntax-parse stx #:track-literals
[(_ . body) (quasisyntax/loc stx (pattern . body))]))
#:property prop:procedure (λ (this stx) ((wrapper-binding-macro this) stx)))
(define (wrapper-binding
#:type type
#:descriptor descriptor
#:predicate predicate
#:constructor constructor
#:accessor accessor
#:pattern pattern
#:macro macro)
(constructor:wrapper-binding
type descriptor predicate constructor accessor pattern macro))
(define-syntax-class wrapper-id
#:attributes (type binding name descriptor predicate constructor accessor)
(pattern binding-id
#:declare binding-id
(static wrapper-binding? "a static wrapper-binding? value")
#:attr binding (attribute binding-id.value)
#:attr type (wrapper-binding-type (attribute binding))
#:with name #`'#,(wrapper-type-name (attribute type))
#:with descriptor (wrapper-binding-descriptor (attribute binding))
#:with predicate (wrapper-binding-predicate (attribute binding))
#:with constructor (wrapper-binding-constructor (attribute binding))
#:with accessor (wrapper-binding-accessor (attribute binding))))