Make tc-app code match using label phase.
This commit is contained in:
parent
e8c65ff759
commit
3d0cadf0a8
|
@ -8,10 +8,7 @@
|
||||||
(types abbrev utils)
|
(types abbrev utils)
|
||||||
(rep type-rep)
|
(rep type-rep)
|
||||||
|
|
||||||
;; fixme - don't need to be bound in this phase - only to make tests work
|
(for-label
|
||||||
(only-in '#%kernel [apply k:apply])
|
|
||||||
;; end fixme
|
|
||||||
(for-template
|
|
||||||
racket/base
|
racket/base
|
||||||
(only-in '#%kernel [apply k:apply])))
|
(only-in '#%kernel [apply k:apply])))
|
||||||
|
|
||||||
|
@ -19,8 +16,12 @@
|
||||||
(import tc-expr^ tc-apply^)
|
(import tc-expr^ tc-apply^)
|
||||||
(export tc-app-apply^)
|
(export tc-app-apply^)
|
||||||
|
|
||||||
|
(define-literal-set apply-literals
|
||||||
|
#:for-label
|
||||||
|
(k:apply apply values))
|
||||||
|
|
||||||
(define-tc/app-syntax-class (tc/app-apply expected)
|
(define-tc/app-syntax-class (tc/app-apply expected)
|
||||||
#:literals (k:apply apply values)
|
#:literal-sets (apply-literals)
|
||||||
(pattern ((~or apply k:apply) values e)
|
(pattern ((~or apply k:apply) values e)
|
||||||
(match (single-value #'e)
|
(match (single-value #'e)
|
||||||
[(tc-result1: (ListDots: dty dbound))
|
[(tc-result1: (ListDots: dty dbound))
|
||||||
|
|
|
@ -8,21 +8,20 @@
|
||||||
(types abbrev union utils)
|
(types abbrev union utils)
|
||||||
(rep type-rep)
|
(rep type-rep)
|
||||||
|
|
||||||
;; fixme - don't need to be bound in this phase - only to make tests work
|
(for-label racket/base racket/bool))
|
||||||
racket/bool
|
|
||||||
;; end fixme
|
|
||||||
|
|
||||||
(for-template racket/base racket/bool))
|
|
||||||
|
|
||||||
(import tc-expr^)
|
(import tc-expr^)
|
||||||
(export tc-app-eq^)
|
(export tc-app-eq^)
|
||||||
|
|
||||||
|
(define-literal-set eq-literals
|
||||||
|
#:for-label
|
||||||
|
(eq? equal? eqv? string=? symbol=? memq member memv))
|
||||||
|
|
||||||
;; comparators that inform the type system
|
;; comparators that inform the type system
|
||||||
;; `=' is not included. Its type is more useful than this typing rule.
|
;; `=' is not included. Its type is more useful than this typing rule.
|
||||||
(define-syntax-class comparator
|
(define-syntax-class comparator
|
||||||
#:literals (eq? equal? eqv? string=? symbol=? memq member memv)
|
#:literal-sets (eq-literals)
|
||||||
(pattern eq?) (pattern equal?) (pattern eqv?) (pattern string=?) (pattern symbol=?)
|
(pattern (~or eq? equal? eqv? string=? symbol=? member memq memv)))
|
||||||
(pattern member) (pattern memq) (pattern memv))
|
|
||||||
|
|
||||||
|
|
||||||
(define-tc/app-syntax-class (tc/app-eq expected)
|
(define-tc/app-syntax-class (tc/app-eq expected)
|
||||||
|
@ -42,9 +41,12 @@
|
||||||
(define (eq?-able e) (or (boolean? e) (keyword? e) (symbol? e) (eof-object? e)))
|
(define (eq?-able e) (or (boolean? e) (keyword? e) (symbol? e) (eof-object? e)))
|
||||||
(define (eqv?-able e) (or (eq?-able e) (number? e) (char? e)))
|
(define (eqv?-able e) (or (eq?-able e) (number? e) (char? e)))
|
||||||
(define (equal?-able e) #t)
|
(define (equal?-able e) #t)
|
||||||
|
(define (id=? a b)
|
||||||
|
(free-identifier=? a b #f (syntax-local-phase-level)))
|
||||||
(define (ok? val)
|
(define (ok? val)
|
||||||
(define-syntax-rule (alt nm pred ...)
|
(define-syntax-rule (alt nm pred ...)
|
||||||
(and (free-identifier=? #'nm comparator) (or (pred val) ...)))
|
(and (id=? #'nm comparator)
|
||||||
|
(or (pred val) ...)))
|
||||||
(or (alt symbol=? symbol?)
|
(or (alt symbol=? symbol?)
|
||||||
(alt string=? string?)
|
(alt string=? string?)
|
||||||
(alt eq? eq?-able)
|
(alt eq? eq?-able)
|
||||||
|
@ -60,11 +62,11 @@
|
||||||
(-FS (-filter-at (-val val) o)
|
(-FS (-filter-at (-val val) o)
|
||||||
(-not-filter-at (-val val) o)))]
|
(-not-filter-at (-val val) o)))]
|
||||||
[((tc-result1: t _ o)
|
[((tc-result1: t _ o)
|
||||||
(or (and (? (lambda _ (free-identifier=? #'member comparator)))
|
(or (and (? (lambda _ (id=? #'member comparator)))
|
||||||
(tc-result1: (app untuple (list (and ts (Value: _)) ...))))
|
(tc-result1: (app untuple (list (and ts (Value: _)) ...))))
|
||||||
(and (? (lambda _ (free-identifier=? #'memv comparator)))
|
(and (? (lambda _ (id=? #'memv comparator)))
|
||||||
(tc-result1: (app untuple (list (and ts (Value: (? eqv?-able))) ...))))
|
(tc-result1: (app untuple (list (and ts (Value: (? eqv?-able))) ...))))
|
||||||
(and (? (lambda _ (free-identifier=? #'memq comparator)))
|
(and (? (lambda _ (id=? #'memq comparator)))
|
||||||
(tc-result1: (app untuple (list (and ts (Value: (? eq?-able))) ...))))))
|
(tc-result1: (app untuple (list (and ts (Value: (? eq?-able))) ...))))))
|
||||||
(let ([ty (apply Un ts)])
|
(let ([ty (apply Un ts)])
|
||||||
(ret (Un (-val #f) t)
|
(ret (Un (-val #f) t)
|
||||||
|
|
|
@ -4,22 +4,26 @@
|
||||||
syntax/parse syntax/stx racket/match unstable/sequence unstable/syntax
|
syntax/parse syntax/stx racket/match unstable/sequence unstable/syntax
|
||||||
"signatures.rkt"
|
"signatures.rkt"
|
||||||
"utils.rkt"
|
"utils.rkt"
|
||||||
;; fixme - don't need to be bound in this phase - only to make tests work
|
|
||||||
racket/unsafe/ops
|
|
||||||
;; end fixme
|
|
||||||
(types utils abbrev numeric-tower union resolve type-table generalize)
|
(types utils abbrev numeric-tower union resolve type-table generalize)
|
||||||
(typecheck signatures check-below)
|
(typecheck signatures check-below)
|
||||||
(rep type-rep rep-utils)
|
(rep type-rep rep-utils)
|
||||||
(for-template racket/unsafe/ops racket/base))
|
(for-label racket/unsafe/ops racket/base))
|
||||||
|
|
||||||
(import tc-expr^ tc-app^ tc-literal^)
|
(import tc-expr^ tc-app^ tc-literal^)
|
||||||
(export tc-app-hetero^)
|
(export tc-app-hetero^)
|
||||||
|
|
||||||
|
(define-literal-set hetero-literals
|
||||||
|
#:for-label
|
||||||
|
(vector-ref unsafe-vector-ref unsafe-vector*-ref
|
||||||
|
vector-set! unsafe-vector-set! unsafe-vector*-set!
|
||||||
|
unsafe-struct-ref unsafe-struct*-ref
|
||||||
|
unsafe-struct-set! unsafe-struct*-set!
|
||||||
|
vector-immutable vector))
|
||||||
|
|
||||||
(define (tc/index expr)
|
(define (tc/index expr)
|
||||||
(syntax-parse expr
|
(syntax-parse expr
|
||||||
[((~literal quote) i:number)
|
#:literal-sets (kernel-literals)
|
||||||
|
[(quote i:number)
|
||||||
(let ((type (tc-literal #'i)))
|
(let ((type (tc-literal #'i)))
|
||||||
(add-typeof-expr expr (ret type))
|
(add-typeof-expr expr (ret type))
|
||||||
(syntax-e #'i))]
|
(syntax-e #'i))]
|
||||||
|
@ -73,11 +77,7 @@
|
||||||
(index-error i-val i-bound i-e vec-t expected name)]))
|
(index-error i-val i-bound i-e vec-t expected name)]))
|
||||||
|
|
||||||
(define-tc/app-syntax-class (tc/app-hetero expected)
|
(define-tc/app-syntax-class (tc/app-hetero expected)
|
||||||
#:literals (vector-ref unsafe-vector-ref unsafe-vector*-ref
|
#:literal-sets (hetero-literals)
|
||||||
vector-set! unsafe-vector-set! unsafe-vector*-set!
|
|
||||||
unsafe-struct-ref unsafe-struct*-ref
|
|
||||||
unsafe-struct-set! unsafe-struct*-set!
|
|
||||||
vector-immutable vector)
|
|
||||||
(pattern (~and form ((~or unsafe-struct-ref unsafe-struct*-ref) struct:expr index:expr))
|
(pattern (~and form ((~or unsafe-struct-ref unsafe-struct*-ref) struct:expr index:expr))
|
||||||
(match (single-value #'struct)
|
(match (single-value #'struct)
|
||||||
[(tc-result1: (and struct-t (app resolve (Struct: _ _ (list (fld: flds _ _) ...) _ _ _))))
|
[(tc-result1: (and struct-t (app resolve (Struct: _ _ (list (fld: flds _ _) ...) _ _ _))))
|
||||||
|
|
|
@ -10,15 +10,16 @@
|
||||||
(rep type-rep)
|
(rep type-rep)
|
||||||
(utils tc-utils)
|
(utils tc-utils)
|
||||||
(r:infer infer)
|
(r:infer infer)
|
||||||
|
(for-label racket/base))
|
||||||
(for-template racket/base))
|
|
||||||
|
|
||||||
|
|
||||||
(import tc-expr^)
|
(import tc-expr^)
|
||||||
(export tc-app-keywords^)
|
(export tc-app-keywords^)
|
||||||
|
|
||||||
|
(define-literal-set keyword-literals #:for-label (list))
|
||||||
|
|
||||||
(define-tc/app-syntax-class (tc/app-keywords expected)
|
(define-tc/app-syntax-class (tc/app-keywords expected)
|
||||||
#:literals (#%plain-app list)
|
#:literal-sets (kernel-literals keyword-literals)
|
||||||
(pattern (~and form
|
(pattern (~and form
|
||||||
((#%plain-app cpce s-kp fn kpe kws num)
|
((#%plain-app cpce s-kp fn kpe kws num)
|
||||||
kw-list
|
kw-list
|
||||||
|
|
|
@ -8,33 +8,38 @@
|
||||||
(typecheck signatures find-annotation)
|
(typecheck signatures find-annotation)
|
||||||
(types abbrev utils generalize type-table)
|
(types abbrev utils generalize type-table)
|
||||||
(private type-annotation)
|
(private type-annotation)
|
||||||
|
;; Needed to construct args to tc/let-values
|
||||||
(for-template racket/base))
|
(for-template racket/base)
|
||||||
|
(for-label racket/base))
|
||||||
|
|
||||||
|
|
||||||
(import tc-expr^ tc-let^ tc-lambda^)
|
(import tc-expr^ tc-let^ tc-lambda^)
|
||||||
(export tc-app-lambda^)
|
(export tc-app-lambda^)
|
||||||
|
|
||||||
|
(define-literal-set lambda-literals
|
||||||
|
#:for-label
|
||||||
|
(null? pair? null))
|
||||||
|
|
||||||
(define-tc/app-syntax-class (tc/app-lambda expected)
|
(define-tc/app-syntax-class (tc/app-lambda expected)
|
||||||
#:literals (#%plain-app #%plain-lambda letrec-values)
|
#:literal-sets (kernel-literals)
|
||||||
;; let loop
|
;; let loop
|
||||||
(pattern ((letrec-values ([(lp) (~and lam (#%plain-lambda (args ...) . body))]) lp*) . actuals)
|
(pattern ((letrec-values ([(lp) (~and lam (#%plain-lambda (args ...) . body))]) lp*) . actuals)
|
||||||
#:fail-unless expected #f
|
#:when expected
|
||||||
#:fail-unless (not (andmap type-annotation (syntax->list #'(lp args ...)))) #f
|
#:when (not (andmap type-annotation (syntax->list #'(lp args ...))))
|
||||||
#:fail-unless (free-identifier=? #'lp #'lp*) #f
|
#:when (free-identifier=? #'lp #'lp*)
|
||||||
(let-loop-check #'lam #'lp #'actuals #'(args ...) #'body expected))
|
(let-loop-check #'lam #'lp #'actuals #'(args ...) #'body expected))
|
||||||
;; inference for ((lambda
|
;; inference for ((lambda
|
||||||
(pattern ((#%plain-lambda (x ...) . body) args ...)
|
(pattern ((#%plain-lambda (x ...) . body) args ...)
|
||||||
#:fail-unless (= (syntax-length #'(x ...))
|
#:when (= (syntax-length #'(x ...))
|
||||||
(syntax-length #'(args ...))) #f
|
(syntax-length #'(args ...)))
|
||||||
#:fail-when (andmap type-annotation (syntax->list #'(x ...))) #f
|
#:fail-when (andmap type-annotation (syntax->list #'(x ...))) #f
|
||||||
(tc/let-values #'((x) ...) #'(args ...) #'body
|
(tc/let-values #'((x) ...) #'(args ...) #'body
|
||||||
#'(let-values ([(x) args] ...) . body)
|
#'(let-values ([(x) args] ...) . body)
|
||||||
expected))
|
expected))
|
||||||
;; inference for ((lambda with dotted rest
|
;; inference for ((lambda with dotted rest
|
||||||
(pattern ((#%plain-lambda (x ... . rst:id) . body) args ...)
|
(pattern ((#%plain-lambda (x ... . rst:id) . body) args ...)
|
||||||
#:fail-unless (<= (syntax-length #'(x ...))
|
#:when (<= (syntax-length #'(x ...))
|
||||||
(syntax-length #'(args ...))) #f
|
(syntax-length #'(args ...)))
|
||||||
;; FIXME - remove this restriction - doesn't work because the annotation
|
;; FIXME - remove this restriction - doesn't work because the annotation
|
||||||
;; on rst is not a normal annotation, may have * or ...
|
;; on rst is not a normal annotation, may have * or ...
|
||||||
#:fail-when (type-annotation #'rst) #f
|
#:fail-when (type-annotation #'rst) #f
|
||||||
|
@ -50,7 +55,7 @@
|
||||||
|
|
||||||
(define (let-loop-check lam lp actuals args body expected)
|
(define (let-loop-check lam lp actuals args body expected)
|
||||||
(syntax-parse #`(#,args #,body #,actuals)
|
(syntax-parse #`(#,args #,body #,actuals)
|
||||||
#:literals (#%plain-app if null? pair? null)
|
#:literal-sets (kernel-literals lambda-literals)
|
||||||
[((val acc ...)
|
[((val acc ...)
|
||||||
((~and inner-body (if (#%plain-app (~or pair? null?) val*) thn els)))
|
((~and inner-body (if (#%plain-app (~or pair? null?) val*) thn els)))
|
||||||
(actual actuals ...))
|
(actual actuals ...))
|
||||||
|
|
|
@ -10,11 +10,7 @@
|
||||||
(rep type-rep)
|
(rep type-rep)
|
||||||
(env tvar-env)
|
(env tvar-env)
|
||||||
|
|
||||||
;; fixme - don't need to be bound in this phase - only to make tests work
|
(for-label
|
||||||
(only-in '#%kernel [reverse k:reverse])
|
|
||||||
;; end fixme
|
|
||||||
|
|
||||||
(for-template
|
|
||||||
racket/base
|
racket/base
|
||||||
(only-in '#%kernel [reverse k:reverse])))
|
(only-in '#%kernel [reverse k:reverse])))
|
||||||
|
|
||||||
|
@ -22,10 +18,12 @@
|
||||||
(import tc-expr^ tc-app^)
|
(import tc-expr^ tc-app^)
|
||||||
(export tc-app-list^)
|
(export tc-app-list^)
|
||||||
|
|
||||||
|
(define-literal-set list-literals
|
||||||
|
#:for-label
|
||||||
|
(reverse k:reverse list list* cons map andmap ormap))
|
||||||
|
|
||||||
(define-tc/app-syntax-class (tc/app-list expected)
|
(define-tc/app-syntax-class (tc/app-list expected)
|
||||||
#:literals (reverse k:reverse list list*
|
#:literal-sets (list-literals)
|
||||||
cons map andmap ormap)
|
|
||||||
(pattern (~and form (map f arg0 arg ...))
|
(pattern (~and form (map f arg0 arg ...))
|
||||||
(match* ((single-value #'arg0) (stx-map single-value #'(arg ...)))
|
(match* ((single-value #'arg0) (stx-map single-value #'(arg ...)))
|
||||||
;; if the argument is a ListDots
|
;; if the argument is a ListDots
|
||||||
|
@ -97,7 +95,7 @@
|
||||||
(match-let* ([(list tys ... last) (stx-map tc-expr/t #'args)])
|
(match-let* ([(list tys ... last) (stx-map tc-expr/t #'args)])
|
||||||
(ret (foldr -pair last tys))))
|
(ret (foldr -pair last tys))))
|
||||||
;; special case for `reverse' to propagate expected type info
|
;; special case for `reverse' to propagate expected type info
|
||||||
(pattern ((~or reverse k:reverse) arg)
|
(pattern ((~and fun (~or reverse k:reverse)) arg)
|
||||||
(match expected
|
(match expected
|
||||||
[(tc-result1: (Listof: _))
|
[(tc-result1: (Listof: _))
|
||||||
(tc-expr/check #'arg expected)]
|
(tc-expr/check #'arg expected)]
|
||||||
|
@ -109,4 +107,4 @@
|
||||||
[(tc-result1: (List: ts))
|
[(tc-result1: (List: ts))
|
||||||
(ret (-Tuple (reverse ts)))]
|
(ret (-Tuple (reverse ts)))]
|
||||||
[arg-ty
|
[arg-ty
|
||||||
(tc/funapp #'reverse #'(arg) (single-value #'reverse) (list arg-ty) expected)])])))
|
(tc/funapp #'fun #'(arg) (single-value #'fun) (list arg-ty) expected)])])))
|
||||||
|
|
|
@ -10,15 +10,17 @@
|
||||||
(rep type-rep)
|
(rep type-rep)
|
||||||
(utils tc-utils)
|
(utils tc-utils)
|
||||||
|
|
||||||
(for-template racket/base))
|
(for-label racket/base))
|
||||||
|
|
||||||
|
|
||||||
(import tc-expr^)
|
(import tc-expr^)
|
||||||
(export tc-app-objects^)
|
(export tc-app-objects^)
|
||||||
|
|
||||||
|
(define-literal-set object-literals #:for-label (list cons))
|
||||||
|
|
||||||
|
|
||||||
(define-tc/app-syntax-class (tc/app-objects expected)
|
(define-tc/app-syntax-class (tc/app-objects expected)
|
||||||
#:literals (#%plain-app list cons quote)
|
#:literal-sets (kernel-literals object-literals)
|
||||||
(pattern (dmo b cl
|
(pattern (dmo b cl
|
||||||
(#%plain-app list . pos-args)
|
(#%plain-app list . pos-args)
|
||||||
(#%plain-app list (#%plain-app cons (quote names) named-args) ...))
|
(#%plain-app list (#%plain-app cons (quote names) named-args) ...))
|
||||||
|
|
|
@ -11,20 +11,17 @@
|
||||||
(rep type-rep filter-rep)
|
(rep type-rep filter-rep)
|
||||||
(utils tc-utils)
|
(utils tc-utils)
|
||||||
|
|
||||||
;; fixme - don't need to be bound in this phase - only to make tests work
|
(for-label racket/base racket/bool '#%paramz))
|
||||||
racket/bool
|
|
||||||
'#%paramz
|
|
||||||
;; end fixme
|
|
||||||
|
|
||||||
(for-template racket/base racket/bool '#%paramz))
|
|
||||||
|
|
||||||
|
|
||||||
(import tc-expr^)
|
(import tc-expr^)
|
||||||
(export tc-app-special^)
|
(export tc-app-special^)
|
||||||
|
|
||||||
|
(define-literal-set special-literals #:for-label
|
||||||
|
(extend-parameterization false? not call-with-values list))
|
||||||
|
|
||||||
(define-tc/app-syntax-class (tc/app-special expected)
|
(define-tc/app-syntax-class (tc/app-special expected)
|
||||||
#:literals (#%plain-app #%plain-lambda extend-parameterization quote
|
#:literal-sets (kernel-literals special-literals)
|
||||||
false? not call-with-values list)
|
|
||||||
;; parameterize
|
;; parameterize
|
||||||
(pattern (extend-parameterization pmz args ...)
|
(pattern (extend-parameterization pmz args ...)
|
||||||
(let loop ([args (syntax->list #'(args ...))])
|
(let loop ([args (syntax->list #'(args ...))])
|
||||||
|
|
|
@ -7,14 +7,16 @@
|
||||||
(typecheck signatures tc-funapp)
|
(typecheck signatures tc-funapp)
|
||||||
(types utils)
|
(types utils)
|
||||||
|
|
||||||
(for-template racket/base))
|
(for-label racket/base))
|
||||||
|
|
||||||
|
|
||||||
(import tc-expr^ tc-app^)
|
(import tc-expr^ tc-app^)
|
||||||
(export tc-app-values^)
|
(export tc-app-values^)
|
||||||
|
|
||||||
|
(define-literal-set values-literals #:for-label (values call-with-values))
|
||||||
|
|
||||||
(define-tc/app-syntax-class (tc/app-values expected)
|
(define-tc/app-syntax-class (tc/app-values expected)
|
||||||
#:literals (values call-with-values)
|
#:literal-sets (values-literals)
|
||||||
;; call-with-values
|
;; call-with-values
|
||||||
(pattern (call-with-values prod con)
|
(pattern (call-with-values prod con)
|
||||||
(match (tc/funapp #'prod #'() (single-value #'prod) null #f)
|
(match (tc/funapp #'prod #'() (single-value #'prod) null #f)
|
||||||
|
|
Loading…
Reference in New Issue
Block a user