[gambit-list] Strategies on decreasing executable size for Gambit-based software for client distribution

Marc Feeley feeley at iro.umontreal.ca
Sat Oct 4 09:40:10 EDT 2008


On 3-Oct-08, at 1:59 PM, Marc Feeley wrote:

> Currently there are only two (related) ways to get a smaller  
> executable:

Actually there is another one, which consists in eliminating the whole  
Gambit library, except for the "essentials" (lib/_kernel.scm and some  
of the C files in lib/ which implement the GC, C-interface,
initialization code, etc).

Using this technique (see trace below) I managed to build a 300 kB  
executable on MacOS X from the v4.2.9 tarball.  This could be reduced  
some more by removing some functionality.  Anyway, this is just a  
quick-and-dirty experiment.

The downside of course is that you have to implement yourself whatever  
you need in your application.  You only have very basic functionality  
(the inlinable primitives like ##fx+, ##cons, ##car).  This is like  
reinventing the wheel... but I'm sure some users will appreciate the  
hack value!

Marc

% tar zxf gambc-v4_2_9.tgz
% cd gambc-v4_2_9
% ./configure --enable-single-host
% make bootstrap
% ################ Now edit lib/makefile.in .
% diff lib/makefile.in lib/makefile.in-orig
< MODULES = _kernel
< MODULES_SCM = _kernel.scm
< MODULES_C = _kernel.c
< MODULES_O = _kernel at obj@
< MODULES_O_PLUS = +_kernel at obj@
< MODULES_O_COMMA = _kernel at obj@
---
 > MODULES = _kernel _system _num _std \
 > _eval _io _nonstd _thread _repl
 > MODULES_SCM = _kernel.scm _system.scm _num.scm _std.scm \
 > _eval.scm _io.scm _nonstd.scm _thread.scm _repl.scm
 > MODULES_C = _kernel.c _system.c _num.c _std.c \
 > _eval.c _io.c _nonstd.c _thread.c _repl.c
 > MODULES_O = _kernel at obj@ _system at obj@ _num at obj@ _std at obj@ \
 > _eval at obj@ _io at obj@ _nonstd at obj@ _thread at obj@ _repl at obj@
 > MODULES_O_PLUS = +_kernel at obj@ +_system at obj@ +_num at obj@ +_std at obj@ \
 > +_eval at obj@ +_io at obj@ +_nonstd at obj@ +_thread at obj@ +_repl at obj@
 > MODULES_O_COMMA = _kernel at obj@,_system at obj@,_num at obj@,_std at obj@,\
 > +_eval at obj@,_io at obj@,_nonstd at obj@,_thread at obj@,_repl at obj@
81c87,88
< MODULES_O_IN_COMPILE_ORDER = _kernel at obj@
---
 > MODULES_O_IN_COMPILE_ORDER = _io at obj@ _num at obj@ _std at obj@ \
 > _kernel at obj@ _nonstd at obj@ _repl at obj@ _eval at obj@ _thread at obj@  
_system at obj@
% make clean
% make
making all in include
...
making all in lib
...
../gsc-comp -:=.. -f -link -flat -o _gambc.c _kernel.c
*** WARNING -- "##*" is not defined,
***            referenced in: ("_kernel.c")
*** WARNING -- "##+" is not defined,
***            referenced in: ("_kernel.c")
*** WARNING -- "##map" is not defined,
***            referenced in: ("_kernel.c")
*** WARNING -- "##string->symbol" is not defined,
***            referenced in: ("_kernel.c")
% ################ Note that lib/_kernel.scm depends on some Gambit
% ################ library procedures that are not defined in
% ################ lib/_kernel.scm.  This will be fixed so that
% ################ lib/_kernel.scm is self contained, as it should.
% ################ Now create hw.scm .
% cat hw.scm
;; Make sure the compiler does not assume the standard library is
;; linked in.
(declare
   (block)
   (not inline)
   (not inline-primitives)
   (inlining-limit 0)
   (not run-time-bindings)
)

;; Supply the procedures lib/_kernel.scm needs (this dependency should
;; be removed since it is gratuitous).
(define (##map f lst) '()) ;; I'm lazy
(define (##string->symbol str) 'foo)
(define (##+ x y) 0)
(define (##* x y) 0)

;; The "hello world" program:

(c-declare "#include <stdio.h>")

(define puts (c-lambda (char-string) int "puts"))

(puts "hello world")
% ./gsc-comp -:=. -c hw.scm
% ./gsc-comp -:=. -link hw.c
% gcc -Iinclude -D___SINGLE_HOST hw_.c hw.c lib/libgambc.a -o hw
% strip hw
% ls -l hw
-rwxr-xr-x  1 feeley  feeley  300384 Oct  4 09:22 hw
% ./hw
hello world




More information about the Gambit-list mailing list