From ebca094b50d4885866cc1c3c3f3d6e2ed600aeac Mon Sep 17 00:00:00 2001 From: Andy Wingo Date: Fri, 9 Jan 2015 19:10:51 +0100 Subject: [PATCH] Statically compute offsets for slots of in Scheme * module/oop/goops.scm (macro-fold-left): New helper. (define-class-index): Define class-index-FOO for each slot FOO. (fold--slots): Make the slots list have the marks of the "visit" macro. --- module/oop/goops.scm | 69 ++++++++++++++++++++++++++++++++------------ 1 file changed, 50 insertions(+), 19 deletions(-) diff --git a/module/oop/goops.scm b/module/oop/goops.scm index 7ebe0c053..d00ce670e 100644 --- a/module/oop/goops.scm +++ b/module/oop/goops.scm @@ -207,31 +207,62 @@ (define (compute-cpl class) (compute-std-cpl class class-direct-supers)) +(define-syntax macro-fold-left + (syntax-rules () + ((_ folder seed ()) seed) + ((_ folder seed (head . tail)) + (macro-fold-left folder (folder head seed) tail)))) + (define-syntax macro-fold-right (syntax-rules () ((_ folder seed ()) seed) ((_ folder seed (head . tail)) (folder head (macro-fold-right folder seed tail))))) -(define-syntax-rule (fold--slots fold visit seed) - (fold visit seed - ((layout ) - (flags ) - (self ) - (instance-finalizer ) - (print) - (name ) - (reserved-0 ) - (reserved-1 ) - (redefined) - (direct-supers) - (direct-slots) - (direct-subclasses) - (direct-methods) - (cpl) - (slots) - (getters-n-setters) - (nfields)))) +(define-syntax fold--slots + (lambda (x) + (define slots + '((layout ) + (flags ) + (self ) + (instance-finalizer ) + (print) + (name ) + (reserved-0 ) + (reserved-1 ) + (redefined) + (direct-supers) + (direct-slots) + (direct-subclasses) + (direct-methods) + (cpl) + (slots) + (getters-n-setters) + (nfields))) + (syntax-case x () + ((_ fold visit seed) + ;; The datum->syntax makes it as if the identifiers in `slots' + ;; were present in the initial form, which allows them to be used + ;; as (components of) introduced identifiers. + #`(fold visit seed #,(datum->syntax #'visit slots)))))) + +;; Define class-index-layout to 0, class-index-flags to 1, and so on. +(let-syntax ((define-class-index + (lambda (x) + (define (id-append ctx a b) + (datum->syntax ctx (symbol-append (syntax->datum a) + (syntax->datum b)))) + (define (tail-length tail) + (syntax-case tail () + ((begin) 0) + ((visit head tail) (1+ (tail-length #'tail))))) + (syntax-case x () + ((_ (name . _) tail) + #`(begin + (define #,(id-append #'name #'class-index- #'name) + #,(tail-length #'tail)) + tail)))))) + (fold--slots macro-fold-left define-class-index (begin))) (define (build-slots-list dslots cpl) (define (check-cpl slots class-slots)