1
Fork 0
mirror of https://git.savannah.gnu.org/git/guile.git synced 2025-06-15 08:10:17 +02:00

handle "this" in ecmascript

* module/language/ecmascript/base.scm:
* module/language/ecmascript/compile-ghil.scm:
* module/language/ecmascript/impl.scm:
* module/language/ecmascript/parse.scm: Compile "method calls" in such a
  way that "this" gets propagated correctly.
This commit is contained in:
Andy Wingo 2009-02-20 13:21:09 +01:00
parent e80ce73d20
commit 785fb107ef
4 changed files with 27 additions and 4 deletions

View file

@ -23,6 +23,7 @@
#:use-module (oop goops) #:use-module (oop goops)
#:export (*undefined* *this* #:export (*undefined* *this*
<js-object> *object-prototype* <js-object> *object-prototype*
js-prototype js-props js-prop-attrs js-value js-constructor js-class
pget prop-attrs prop-has-attr? pput has-property? pdel pget prop-attrs prop-has-attr? pput has-property? pdel
object->string object->number object->value/string object->string object->number object->value/string
@ -31,7 +32,7 @@
->primitive ->boolean ->number ->integer ->int32 ->uint32 ->primitive ->boolean ->number ->integer ->int32 ->uint32
->uint16 ->string ->object ->uint16 ->string ->object
call/this lambda/this define-js-method call/this* call/this lambda/this define-js-method
new-object)) new-object))
@ -82,8 +83,11 @@
(pput o p *undefined*) (pput o p *undefined*)
#t)))) #t))))
(define (call/this* this f)
(with-fluid* *this* this f))
(define-macro (call/this this f . args) (define-macro (call/this this f . args)
`(with-fluid* *this* ,this (lambda () (f . ,args)))) `(with-fluid* *this* ,this (lambda () (,f . ,args))))
(define-macro (lambda/this formals . body) (define-macro (lambda/this formals . body)
`(lambda ,formals (let ((this (fluid-ref *this*))) . ,body))) `(lambda ,formals (let ((this (fluid-ref *this*))) . ,body)))
(define-macro (define-js-method object name-and-args . body) (define-macro (define-js-method object name-and-args . body)

View file

@ -62,6 +62,8 @@
(make-ghil-quote e l num)) (make-ghil-quote e l num))
((string ,str) ((string ,str)
(make-ghil-quote e l str)) (make-ghil-quote e l str))
(this
(@impl e l get-this '()))
((+ ,a ,b) ((+ ,a ,b)
(make-ghil-inline e l 'add (list (comp a e) (comp b e)))) (make-ghil-inline e l 'add (list (comp a e) (comp b e))))
((- ,a ,b) ((- ,a ,b)
@ -95,6 +97,20 @@
(lambda (env vars) (lambda (env vars)
(make-ghil-lambda env l vars #t '() (make-ghil-lambda env l vars #t '()
(comp-body env l body formals '%args))))) (comp-body env l body formals '%args)))))
((call/this ,obj ,prop ,args)
(@impl e l call/this*
(list obj (make-ghil-lambda
e l '() #f '()
(make-ghil-call e l (@impl e l pget (list obj prop))
args)))))
((call (pref ,obj ,prop) ,args)
(comp `(call/this ,(comp obj e) ,(make-ghil-quote e l prop)
,(map (lambda (x) (comp x e)) args))
e))
((call (aref ,obj ,prop) ,args)
(comp `(call/this ,(comp obj e) ,(comp prop e)
,(map (lambda (x) (comp x e)) args))
e))
((call ,proc ,args) ((call ,proc ,args)
(make-ghil-call e l (comp proc e) (map (lambda (x) (comp x e)) args))) (make-ghil-call e l (comp proc e) (map (lambda (x) (comp x e)) args)))
((return ,expr) ((return ,expr)

View file

@ -24,9 +24,12 @@
#:use-module (language ecmascript base) #:use-module (language ecmascript base)
#:use-module (language ecmascript function) #:use-module (language ecmascript function)
#:use-module (language ecmascript array) #:use-module (language ecmascript array)
#:re-export (*undefined* *this* #:export (get-this)
#:re-export (*undefined* *this* call/this*
pget pput pdel pget pput pdel
new-object new-object
new new
new-array)) new-array))
(define (get-this)
(fluid-ref *this*))

View file

@ -173,7 +173,7 @@
;; as to get operator precedence right. ;; as to get operator precedence right.
;; ;;
(PrimaryExpression (this) -> '(this) (PrimaryExpression (this) -> 'this
(null) -> 'null (null) -> 'null
(true) -> #t (true) -> #t
(false) -> #f (false) -> #f