guile-user
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: Q on (language <lang> spec)


From: Nala Ginrut
Subject: Re: Q on (language <lang> spec)
Date: Mon, 19 Oct 2015 11:53:02 +0800

Nice work!
For more generic discussion about multi-lang, I could share some
opinions.

Most of the time, we just need to convert our AST/IR to tree-il. But I
saw old guile-lua frontend added something in the lower level. I haven't
learned it deeper.

There're two identical forms of tree-il, s-expr form and record form.
Personally, I like s-expr one, it's simple to use. But record form could
store the src meta info, which is considered better. 

And I'm grad that you write a new lexer generator (before it I only know
silex), it's great! Would you like to make the generated tokens
compatible with scm-lalr? If so, people may rewrite their lexer module
with your lexer generator, and no need to rewrite the parser. I saw the
token name is string rather than symbol, so I guess it's not compatible
with scm-lalr.

Happy hacking!




On Sun, 2015-10-18 at 13:00 -0700, Matt Wette wrote:
> > On Oct 17, 2015, at 12:02 PM, Matt Wette <address@hidden> wrote:
> > I am playing with the compiler tower and have been digging through the 
> > (system base language) module to try to get my hands around writing to the 
> > compiler tower.  .
> 
> Here is a simple calculator example that I have working with my own 
> intermediate (SXML based) language. 
> 
> scheme@(guile-user)> ,L calc
> Happy hacking with calc!  To switch back, type `,L scheme'.
> calc@(guile-user)> a = (2.5 + 4.5)/(9.3 - 1)
> calc@(guile-user)> ,L scheme
> Happy hacking with Scheme!  To switch back, type `,L calc'.
> scheme@(guile-user)> a
> $1 = 0.8433734939759036
> 
> The implementation consists of the files spec.scm, parser.scm and 
> compiler.scm which are listed below.
> 
> All files are:
> 
> ;;; Copyright (C) 2015 Matthew R. Wette
> ;;;
> ;;; This program is free software: you can redistribute it and/or modify
> ;;; it under the terms of the GNU General Public License as published by 
> ;;; the Free Software Foundation, either version 3 of the License, or 
> ;;; (at your option) any later version.
> 
> and to appear at https://savannah.nongnu.org/projects/nyacc 
> <https://savannah.nongnu.org/projects/nyacc>.
> 
> spec.scm:
> (define-module (language calc spec)
>   #:export (calc)
>   #:use-module (system base language)
>   #:use-module (nyacc lang calc parser)
>   #:use-module (nyacc lang calc compiler))
> 
> (define (calc-reader port env)
>   (let ((iport (current-input-port)))
>     (dynamic-wind
>         (lambda () (set-current-input-port port))
>         (lambda () (calc-parse #:debug #f))
>         (lambda () (set-current-input-port iport)))))
> 
> (define-language calc
>   #:title       "calc"
>   #:reader      calc-reader
>   #:compilers   `((tree-il . ,calc-sxml->tree-il))
>   #:printer     write)
> 
> 
> parser.scm:
> (define-module (nyacc lang calc parser)
>   #:export (calc-parse calc-spec calc-mach)
>   #:use-module (nyacc lalr)
>   #:use-module (nyacc lex)
>   #:use-module (nyacc parse)
>   )
> 
> (define calc-spec
>   (lalr-spec
>    (prec< (left "+" "-") (left "*" "/"))
>    (start stmt-list-proxy)
>    (grammar
> 
>     (stmt-list-proxy
>      (stmt-list "\n" ($$ (cons 'stmt-list (reverse $1)))))
> 
>     (stmt-list
>      (stmt ($$ (list $1)))
>      (stmt-list ";" stmt ($$ (cons $3 $1))))
> 
>     (stmt
>      (ident "=" expr ($$ `(assn-stmt ,$1 ,$3)))
>      (expr ($$ `(expr-stmt ,$1)))
>      ( ($$ '(empty-stmt))))
> 
>     (expr
>      (expr "+" expr ($$ `(add ,$1 ,$3)))
>      (expr "-" expr ($$ `(sub ,$1 ,$3)))
>      (expr "*" expr ($$ `(mul ,$1 ,$3)))
>      (expr "/" expr ($$ `(div ,$1 ,$3)))
>      ('$fixed ($$ `(fixed ,$1)))
>      ('$float ($$ `(float ,$1)))
>      ("(" expr ")" ($$ $2)))
> 
>     (ident ('$ident ($$ `(ident ,$1))))
>     )))
> 
> (define calc-mach
>   (compact-machine
>    (hashify-machine
>      (make-lalr-machine calc-spec))))
> 
> (define calc-parse
>   (let ((gen-lexer (make-lexer-generator (assq-ref calc-mach 'mtab)
>                                          #:space-chars " \t"))
>         (parser (make-lalr-ia-parser calc-mach)))
>     (lambda* (#:key (debug #f)) (parser (gen-lexer) #:debug debug))))
> 
> 
> compiler.scm:
> (define-module (nyacc lang calc compiler)
>   #:export (calc-sxml->tree-il)
>   #:use-module (sxml match)
>   #:use-module (sxml fold)
>   ;;#:use-module (system base language)
>   #:use-module (language tree-il))
> 
> (define (fup tree)
>   (sxml-match tree
>     ((fixed ,fx) `(const ,(string->number fx)))
>     ((float ,fl) `(const ,(string->number fl)))
>     ((ident ,id) `(toplevel ,(string->symbol id)))
>     ((add ,lt ,rt) `(apply (toplevel +) ,lt ,rt))
>     ((sub ,lt ,rt) `(apply (toplevel -) ,lt ,rt))
>     ((mul ,lt ,rt) `(apply (toplevel *) ,lt ,rt))
>     ((div ,lt ,rt) `(apply (toplevel /) ,lt ,rt))
>     ((assn-stmt (toplevel ,lhs) ,rhs) `(define ,lhs ,rhs))
>     ((empty-stmt) '(begin))
>     ((stmt-list ,items ...) `(begin ,items ...))
>     (,otherwise tree)))
> 
> (define (calc-sxml->tree-il exp env opts)
>   (let* ((tree (foldt fup identity exp))
>          (code (parse-tree-il tree)))
>     (values code env env)))
> 





reply via email to

[Prev in Thread] Current Thread [Next in Thread]