Created
October 31, 2009 07:59
-
-
Save hiredman/222974 to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
(defn shell [cmd] | |
(-> (Runtime/getRuntime) (.exec cmd))) | |
(defn is->string [is] | |
(let [sb (StringBuilder.)] | |
(loop [ch (.read is)] | |
(if (= (int ch) -1) | |
(.toString sb) | |
(do (.append sb (char ch)) | |
(recur (.read is))))))) | |
(defmulti clojurec (comp :tag meta)) | |
(defmethod clojurec :proc [p] | |
(let [[name- args & body] p | |
args (pr-str (into () args)) | |
return (name (:tag (meta name-))) | |
body (apply str (map clojurec body))] | |
(format "\n%s %s %s\n{\n%s\n}\n" return name- args body))) | |
(defmethod clojurec := [assn] | |
(let [type (name (:tag (meta (first assn)))) | |
name- (name (first assn)) | |
value (second assn)] | |
(format "%s %s = %s;\n" type name- value))) | |
(defmethod clojurec :call [call] | |
(let [name (first call) | |
args (rest call)] | |
(format "%s%s;" name args))) | |
(defmethod clojurec :c-program [prog] | |
(let [body (apply str (map clojurec prog)) | |
m (meta prog) | |
cmd (format "%s %s -o %s" (:compiler m) (:file-name m) (:binary-file m))] | |
(with-open [o (-> m :file-name java.io.File. java.io.FileWriter.)] | |
(.write o body)) | |
(shell cmd) | |
`(fn [] (shell (format "./%s" ~(:binary-file m)))))) | |
(defmacro cc [x] | |
(clojurec x)) | |
;; example | |
(cc | |
#^{:tag :c-program :compiler "gcc" :file-name "test.c" :binary-file "test"} | |
[#^:proc (#^:int main [] | |
#^:= (#^int x 1) | |
#^:call (printf "foo\n"))]) | |
;; at repl | |
user=> | |
(cc | |
#^{:tag :c-program :compiler "gcc" :file-name "test.c" :binary-file "test"} | |
[#^:proc (#^:int main [] | |
#^:= (#^int x 1) | |
#^:call (printf "foo\n"))]) | |
#<user$eval__759$fn__761 user$eval__759$fn__761@1b17d49> | |
user=> (-> *1 (apply nil) .getInputStream is->string) | |
"foo\n" | |
user=> | |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment