I recently started learning Common Lisp using SBCL. How can I compile my Lisp programs into a Windows binary?
Compiling Common Lisp to an executable
Asked Answered
There're several tools to do it. You can start with Buildapp. –
Armbruster
Making hello.exe:
* (defun main () (print "hello"))
MAIN
* (sb-ext:save-lisp-and-die "hello.exe" :toplevel #'main :executable t)
[undoing binding stack and other enclosing state... done]
[saving current Lisp image into hello.exe:
writing 3160 bytes from the read-only space at 0x22000000
writing 2592 bytes from the static space at 0x22100000
writing 30134272 bytes from the dynamic space at 0x22300000
done]
> dir hello.exe
31,457,304 hello.exe
> hello.exe
"hello"
31 MB executable file!
Using ASDF's UIOP:
https://quickref.common-lisp.net/uiop.html#index-dump_002dimage
This also works in other Lisps, including SBCL:
* (require "asdf")
("ASDF" "asdf" "UIOP" "uiop")
* (defun main () (print "hello"))
MAIN
* (setq uiop:*image-entry-point* #'main)
#<FUNCTION MAIN>
* (uiop:dump-image "hello.exe" :executable t)
[undoing binding stack and other enclosing state... done]
[performing final GC... done]
[defragmenting immobile space... (inst,fdefn,code,sym)=828+16731+18346+26762... done]
[saving current Lisp image into hello.exe:
writing 1936 bytes from the static space at 0000000020020000
writing 18743296 bytes from the dynamic space at 0000001000000000
writing 6786336 bytes from the read-only space at 0000000fff980000
writing 1937408 bytes from the fixedobj space at 0000000020120000
writing 11816960 bytes from the text space at 0000000021a20000
done]
> dir hello.exe
41,817,704 hello.exe
Thanks, this is a good example of what Anton was talking about. Two questions, how would you create an executable from an existing lisp file and is it possible to get the executable to a smaller size? –
Hessney
@JamesMcMahon: smaller sizes are possible with some other CL implementations. For example Clozure CL, CLISP, LispWorks, Allegro CL, MKCL. Really small programs can be created with the commercial 'mocl' compiler (though currently not for windows), which only supports a large subset of Common Lisp and which then does not support runtime code loading, runtime compilation, full runtime evaluation, etc. With mocl you get tiny applications, but which are static - similar to what you would expect from a C compiler. It actually compiles to C code. –
Uturn
You can just save an executable with no :toplevel , and then use that as your new “sbcl binary” to run scripts (with your dependencies already loaded). Just one big file, and instant startup on all scripts. –
Voltmer
Use SB-EXT:SAVE-LISP-AND-DIE
. See http://www.sbcl.org/manual/#Saving-a-Core-Image for details.
could you provide more info? This points in the right direction but there is a lot of information to digest there for a Lisp newbie. –
Hessney
(defun main ()
(format t "Hello, world!~%"))
(sb-ext:save-lisp-and-die "hello-world.exe"
:executable t
:toplevel 'main)
The correct method is:
(compile-file "file.lisp")
This is incorrect.
compile-file
compiles a source file into a form that can be loaded in the repl, but this is not an executable binary. –
Tamarau @adabsurdum For me, it produces an executable binary just fine. –
Externality
I am afraid that you are wrong about this.
compile-file
creates a file in an implementation-dependent format that is intended to work with load
. With SBCL the resulting files are only compatible with the SBCL version which created them. If you have a method for creating an executable using compile-file
, you need to present the complete method: a minimal source file, steps to compile to an executable, and method of running the executable. A binary executable should run with something like $ ./my-executable
. –
Tamarau © 2022 - 2024 — McMap. All rights reserved.