mirror of
https://git.savannah.gnu.org/git/guile.git
synced 2025-06-16 16:50:21 +02:00
emacs-compatible lexical binding
* module/language/elisp/bindings.scm (global?): New function. * module/language/elisp/compile-tree-il.scm (lexical-binding): New variable. (bind-lexically?): If lexical binding is enabled, bind lexically unless a special binding exists. (compile-%set-lexical-binding-mode): New function. * module/language/elisp/lexer.scm (lexical-binding-regexp): New variable. (lex): Return a `set-lexical-binding-mode!' token if a comment is found while reading the first line. * module/language/elisp/parser.scm (get-expression): Add support for `set-lexical-binding-mode!' tokens. * module/language/elisp/runtime/function-slot.scm: Import and re-export the `%set-lexical-binding-mode' special form. * test-suite/tests/elisp-compiler.test ("Let and Let*")["lambda args inside lexical-let"]: Update.
This commit is contained in:
parent
d4cb18ad9c
commit
03e00c5c9d
6 changed files with 47 additions and 10 deletions
|
@ -252,7 +252,15 @@
|
|||
;;; Main lexer routine, which is given a port and does look for the next
|
||||
;;; token.
|
||||
|
||||
(define lexical-binding-regexp
|
||||
(make-regexp
|
||||
"-\\*-(|.*;)[ \t]*lexical-binding:[ \t]*([^;]*[^ \t;]).*-\\*-"))
|
||||
|
||||
(define (lex port)
|
||||
(define (lexical-binding-value string)
|
||||
(and=> (regexp-exec lexical-binding-regexp string)
|
||||
(lambda (match)
|
||||
(not (member (match:substring match 2) '("nil" "()"))))))
|
||||
(let ((return (let ((file (if (file-port? port)
|
||||
(port-filename port)
|
||||
#f))
|
||||
|
@ -283,11 +291,19 @@
|
|||
(case c
|
||||
;; A line comment, skip until end-of-line is found.
|
||||
((#\;)
|
||||
(let iterate ()
|
||||
(let ((cur (read-char port)))
|
||||
(if (or (eof-object? cur) (char=? cur #\newline))
|
||||
(lex port)
|
||||
(iterate)))))
|
||||
(if (= (port-line port) 0)
|
||||
(let iterate ((chars '()))
|
||||
(let ((cur (read-char port)))
|
||||
(if (or (eof-object? cur) (char=? cur #\newline))
|
||||
(let ((string (list->string (reverse chars))))
|
||||
(return 'set-lexical-binding-mode!
|
||||
(lexical-binding-value string)))
|
||||
(iterate (cons cur chars)))))
|
||||
(let iterate ()
|
||||
(let ((cur (read-char port)))
|
||||
(if (or (eof-object? cur) (char=? cur #\newline))
|
||||
(lex port)
|
||||
(iterate))))))
|
||||
;; A character literal.
|
||||
((#\?)
|
||||
(return 'character (get-character port #f)))
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue