gcl-devel
[Top][All Lists]
Advanced

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

[Gcl-devel] Re: proclaim -- so important for GCL performance


From: Camm Maguire
Subject: [Gcl-devel] Re: proclaim -- so important for GCL performance
Date: 25 Mar 2006 12:16:53 -0500
User-agent: Gnus/5.09 (Gnus v5.9.0) Emacs/21.2

Greetings, and thanks for this discussion!

This brings up several topics, including an old one I'd meant to
address before -- mutual recursion.  The bottom line is that GCL makes
'fast-link' calls via a function pointer.  At load time, the pointer
is setup to a stub which makes the first call in the traditional slow
way, and then, if (si::use-fast-links t) is on (the default), will
replace the contents of the function pointer to refer directly to the
function in question.  A link array is maintained whereby one can
switch all the pointers back to the stubs for use in debugging if
desired.  Pretty slick IMHO.

We can do a little better, though, when the function called is in the
same file as the caller.  Calling the function by name rather than by
the pointer is order of magnitude faster in both compile and run
time.  Furthermore, it allows gcc to make mutually recursive function
calls which consume no stack space.  

In general then we have three options:

1) The current practice, all function calls via a pointer.

2) At each function call, check if the pointer refers to the name, and
   if so, call the name directly.  Advantages/disadvantages -- allows mutual
   recursion, much faster runtime, somewhat slower compile time, still
   allows debugging by turning off fast links.  I have this working now.

3) Call all functions in the same file by name only.
   Advantages/disadvantages -- allows mutual recursion, much faster in
   compile and execution time, though execution time is roughly the
   same as 2, no debugging support.  Furthermore, this will require
   some debugging work, as it appears the stubs need to be called at
   least once to setup the function before it is called directly.
   (pcl compilation segfaults).

Here are some sample times on your test file: (note I cannot quite
make sense of both Bob and Ray's times, they do not appear consistent
given the hardware ???)

=============================================================================

1) Current:

COMPILER>(time (load (compile-file "/tmp/qq.l" :c-file t)))

;; Compiling /tmp/qq.l.
;; End of Pass 1.  
;; End of Pass 2.  
;; OPTIMIZE levels: Safety=0 (No runtime error checking), Space=0, Speed=3, 
(Debug quality ignored)
;; Finished compiling /tmp/qq.o.
Loading /tmp/qq.o
start address -T 0x8aee650 Finished loading /tmp/qq.o
real time       :      0.730 secs
run-gbc time    :      0.090 secs
child run time  :      0.600 secs
gbc time        :      0.000 secs
7688

COMPILER>(time (test 1000000))

real time       :      4.030 secs
run-gbc time    :      4.020 secs
child run time  :      0.000 secs
gbc time        :      0.000 secs
NIL

2) Optional by name calling:

(time (load (compile-file "/tmp/qq.l" :c-file t)))

;; Compiling /tmp/qq.l.
;; End of Pass 1.  
;; End of Pass 2.  
;; OPTIMIZE levels: Safety=0 (No runtime error checking), Space=0, Speed=3, 
(Debug quality ignored)
;; Finished compiling /tmp/qq.o.
Loading /tmp/qq.o
start address -T 0x8aea690 Finished loading /tmp/qq.o
real time       :      4.470 secs
run-gbc time    :      0.100 secs
child run time  :      4.230 secs
gbc time        :      0.060 secs
16316

COMPILER>(time (test 1000000))

real time       :      0.160 secs
run-gbc time    :      0.150 secs
child run time  :      0.000 secs
gbc time        :      0.000 secs
NIL

3) Always by name calling:

COMPILER>(time (load (compile-file "/tmp/qq.l" :c-file t)))

;; Compiling /tmp/qq.l.
;; End of Pass 1.  
;; End of Pass 2.  
;; OPTIMIZE levels: Safety=0 (No runtime error checking), Space=0, Speed=3, 
(Debug quality ignored)
;; Finished compiling /tmp/qq.o.
Loading /tmp/qq.o
start address -T 0x8af0458 Finished loading /tmp/qq.o
real time       :      0.400 secs
run-gbc time    :      0.080 secs
child run time  :      0.180 secs
gbc time        :      0.070 secs
268

COMPILER>(time (test 1000000))

real time       :      0.070 secs
run-gbc time    :      0.060 secs
child run time  :      0.000 secs
gbc time        :      0.000 secs
NIL

COMPILER>

=============================================================================

With 2) consider this:

/tmp/ppq.l

(declaim (ftype (function (t) t) foo bar))
(defun foo (x) (bar x))
(defun bar (x) (foo x))

>(compile-file "/tmp/ppq.l")

;; Compiling /tmp/ppq.l.
;; End of Pass 1.  
;; End of Pass 2.  
;; OPTIMIZE levels: Safety=0 (No runtime error checking), Space=0, Speed=3, 
(Debug quality ignored)
;; Finished compiling /tmp/ppq.o.
#P"/tmp/ppq.o"
NIL
NIL

>(load "/tmp/ppq.o")

Loading /tmp/ppq.o
start address -T 0x8a0c180 Finished loading /tmp/ppq.o
160

>(foo 1)


Console interrupt.

Fast links are on: do (si::use-fast-links nil) for debugging
Broken at SYSTEM::CLCS-TERMINAL-INTERRUPT.  Type :H for Help.
 1 (Continue) Continues execution.
 2 Return to top level.
dbl:>>2

Top level.
>(si::use-fast-links nil)

NIL

>(foo 1)

Error in BAR [or a callee]: Invocation history stack overflow.

Broken at INVOKE-DEBUGGER.  Type :H for Help.
 1 (Continue) Return to top level.
dbl:>>

I might include 2) in the next commit just to test it out.

Advice suggestions always appreciated!

Take care,



Robert Boyer <address@hidden> writes:

> > Compile-times matter too. :-)
> 
> Amen.
> 
> gcc can take a while on large files or functions.  I dimly suspect it is
> quadratic.
> 
> On short files, the gcl compiler might be faster if it did not have to start
> gcc up every time by reading in 200,000 characters of header info.  However,
> it seems it may take some thinking to fix that.  I believe I have heard of at
> least one C compiler that can be "saved" in midstream, but I have no idea how
> to do that sort of thing.
> 
> Bob
> 
> P. S.  Note what a large percentage of the time is spent below in gcc, the
> "child" here, for this particularly long function, which was a stupid, very
> artificial hack du jour to help time function calling a little more
> accurately, maybe.  Benchmarking is so hard.
> 
> % xg
> GCL (GNU Common Lisp)  2.7.0 ANSI    Mar 23 2006 20:28:22
> 
> >(time (compile-file "foo.lisp"))
> 
> ;; Compiling foo.lisp.
> ;; End of Pass 1.  
> ;; End of Pass 2.  
> ;; OPTIMIZE levels: Safety=0 (No runtime error checking), Space=0, Speed=3, 
> (Debug quality ignored)
> ;; Finished compiling foo.o.
> real time       :      5.490 secs
> run-gbc time    :      0.020 secs
> child run time  :      4.920 secs
> gbc time        :      0.040 secs
> #P"/v/filer2/boyer/foo.o"
> NIL
> NIL
> 
> >
> 
> 
> 

-- 
Camm Maguire                                            address@hidden
==========================================================================
"The earth is but one country, and mankind its citizens."  --  Baha'u'llah




reply via email to

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