Commit | Line | Data |
---|---|---|
cb4cca12 KN |
1 | ;;; High-level compiler interface |
2 | ||
3 | ;; Copyright (C) 2001 Free Software Foundation, Inc. | |
4 | ||
5 | ;; This program is free software; you can redistribute it and/or modify | |
6 | ;; it under the terms of the GNU General Public License as published by | |
7 | ;; the Free Software Foundation; either version 2, or (at your option) | |
8 | ;; any later version. | |
9 | ;; | |
10 | ;; This program is distributed in the hope that it will be useful, | |
11 | ;; but WITHOUT ANY WARRANTY; without even the implied warranty of | |
12 | ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |
13 | ;; GNU General Public License for more details. | |
14 | ;; | |
15 | ;; You should have received a copy of the GNU General Public License | |
16 | ;; along with this program; see the file COPYING. If not, write to | |
17 | ;; the Free Software Foundation, Inc., 59 Temple Place - Suite 330, | |
18 | ;; Boston, MA 02111-1307, USA. | |
19 | ||
20 | ;;; Code: | |
21 | ||
22 | (define-module (system base compile) | |
8f5cfc81 | 23 | :use-syntax (system base syntax) |
cb4cca12 | 24 | :use-module (system base language) |
8f5cfc81 | 25 | :use-module (system il compile) |
ac99cb0c | 26 | :use-module (system il glil) |
49edef60 | 27 | :use-module ((system vm core) |
b6368dbb | 28 | #:select (the-vm vm-load objcode->u8vector)) |
8f5cfc81 KN |
29 | :use-module (system vm assemble) |
30 | :use-module (ice-9 regex)) | |
31 | ||
32 | ;;; | |
33 | ;;; Compiler environment | |
34 | ;;; | |
35 | ||
ac99cb0c | 36 | (define-record (<cenv> vm language module)) |
8f5cfc81 KN |
37 | |
38 | (define-public (make-cenv . rest) | |
ac99cb0c | 39 | (apply <cenv> rest)) |
8f5cfc81 KN |
40 | |
41 | (define-public (syntax-error loc msg exp) | |
42 | (throw 'syntax-error loc msg exp)) | |
43 | ||
44 | (define-public (call-with-compile-error-catch thunk) | |
d8eeb67c LC |
45 | (catch 'syntax-error |
46 | (thunk) | |
47 | (lambda (key loc msg exp) | |
48 | (format #t "~A:~A: ~A: ~A" (car loc) (cdr loc) msg exp)))) | |
8f5cfc81 KN |
49 | |
50 | \f | |
51 | ;;; | |
52 | ;;; Compiler | |
53 | ;;; | |
cb4cca12 KN |
54 | |
55 | (define scheme (lookup-language 'scheme)) | |
56 | ||
8f5cfc81 KN |
57 | (define-public (compile-file file . opts) |
58 | (let ((comp (compiled-file-name file))) | |
59 | (catch #t | |
60 | (lambda () | |
054599f1 LC |
61 | ; (call-with-compile-error-catch |
62 | ; (lambda () | |
cb4cca12 KN |
63 | (call-with-output-file comp |
64 | (lambda (port) | |
8f5cfc81 KN |
65 | (let* ((source (read-file-in file scheme)) |
66 | (objcode (apply compile-in source (current-module) | |
67 | scheme opts))) | |
ac99cb0c KN |
68 | (if (memq :c opts) |
69 | (pprint-glil objcode port) | |
054599f1 | 70 | (uniform-vector-write (objcode->u8vector objcode) port))))) |
b6368dbb | 71 | (format #t "wrote ~A\n" comp)) |
8f5cfc81 | 72 | (lambda (key . args) |
b6368dbb | 73 | (format #t "ERROR: during compilation of ~A:\n" file) |
8f5cfc81 | 74 | (display "ERROR: ") |
f21dfea6 | 75 | (apply format #t (cadr args) (caddr args)) |
8f5cfc81 | 76 | (newline) |
f21dfea6 | 77 | (format #t "ERROR: ~A ~A ~A\n" key (car args) (cadddr args)) |
8f5cfc81 KN |
78 | (delete-file comp))))) |
79 | ||
054599f1 LC |
80 | ; (let ((c-f compile-file)) |
81 | ; ;; XXX: Debugging output | |
82 | ; (set! compile-file | |
83 | ; (lambda (file . opts) | |
84 | ; (format #t "compile-file: ~a ~a~%" file opts) | |
85 | ; (let ((result (apply c-f (cons file opts)))) | |
86 | ; (format #t "compile-file: returned ~a~%" result) | |
87 | ; result)))) | |
88 | ||
8f5cfc81 KN |
89 | (define-public (load-source-file file . opts) |
90 | (let ((source (read-file-in file scheme))) | |
f21dfea6 | 91 | (apply compile-in source (current-module) scheme opts))) |
8f5cfc81 KN |
92 | |
93 | (define-public (load-file file . opts) | |
94 | (let ((comp (compiled-file-name file))) | |
95 | (if (file-exists? comp) | |
f21dfea6 | 96 | (load-objcode comp) |
8f5cfc81 KN |
97 | (apply load-source-file file opts)))) |
98 | ||
99 | (define-public (compiled-file-name file) | |
cb4cca12 KN |
100 | (let ((m (string-match "\\.[^.]*$" file))) |
101 | (string-append (if m (match:prefix m) file) ".go"))) | |
8f5cfc81 | 102 | |
7a0d0cee KN |
103 | (define-public (scheme-eval x e) |
104 | (vm-load (the-vm) (compile-in x e scheme))) | |
105 | ||
8f5cfc81 KN |
106 | \f |
107 | ;;; | |
108 | ;;; Scheme compiler interface | |
109 | ;;; | |
110 | ||
111 | (define-public (read-file-in file lang) | |
112 | (call-with-input-file file lang.read-file)) | |
113 | ||
114 | (define-public (compile-in x e lang . opts) | |
115 | (catch 'result | |
116 | (lambda () | |
117 | ;; expand | |
118 | (set! x (lang.expander x e)) | |
119 | (if (memq :e opts) (throw 'result x)) | |
120 | ;; translate | |
121 | (set! x (lang.translator x e)) | |
122 | (if (memq :t opts) (throw 'result x)) | |
123 | ;; compile | |
124 | (set! x (apply compile x e opts)) | |
125 | (if (memq :c opts) (throw 'result x)) | |
126 | ;; assemble | |
127 | (apply assemble x e opts)) | |
128 | (lambda (key val) val))) | |
129 | ||
130 | ;;; | |
b6368dbb | 131 | ;;; |
8f5cfc81 KN |
132 | ;;; |
133 | ||
134 | (define (compile-and-load file . opts) | |
135 | (let ((comp (object-file-name file))) | |
136 | (if (or (not (file-exists? comp)) | |
137 | (> (stat:mtime (stat file)) (stat:mtime (stat comp)))) | |
138 | (compile-file file)) | |
139 | (load-compiled-file comp))) | |
140 | ||
141 | (define (load/compile file . opts) | |
142 | (let* ((file (file-full-name file)) | |
143 | (compiled (object-file-name file))) | |
144 | (if (or (not (file-exists? compiled)) | |
145 | (> (stat:mtime (stat file)) (stat:mtime (stat compiled)))) | |
146 | (apply compile-file file #f opts)) | |
147 | (if (memq #:b opts) | |
148 | (apply vm-trace (the-vm) (load-objcode compiled) opts) | |
149 | ((the-vm) (load-objcode compiled))))) | |
150 | ||
151 | (define (file-full-name filename) | |
152 | (let* ((port (current-load-port)) | |
153 | (oldname (and port (port-filename port)))) | |
154 | (if (and oldname | |
155 | (> (string-length filename) 0) | |
156 | (not (char=? (string-ref filename 0) #\/)) | |
157 | (not (string=? (dirname oldname) "."))) | |
158 | (string-append (dirname oldname) "/" filename) | |
159 | filename))) |