This wiki is being migrated to http://www.github.com/z88dk/z88dk/wiki

 

Optimization hints

  • Use the extra optimization flag
  zcc -O3 ....  program.c
  • When possible use global variables
  Access to local variables is slightly slower and the generated code
  gets slightly bigger.
  • Use the same data type where possible
  Limit the use of the 'char' datatypes.
  The type conversion adds extra code, expecially when unsigned and 
  unsigned datatypes are mixed.
  • Do not reinvent the wheel
  The z88dk function libraries are mostly written in assembly code; this
  helps saving a lot of memory and execution time; avoid using an equivalent
  C implementation of the existing functions, if any.
  • Split your libraries in modules
  The z80asm tool is able to link in code portions incrementally, 
  adding them only when they are really used, no matter if they were
  invoked already by the "header file" declarations or by the assembly
  code equivalents.
  • Use the _ _FASTCALL_ _ calling mode in functions needing a single parameter
  Most of the z88dk library is based on it to save memory and execution time.
  It could be worth to use the same technique in your projects.
  • Use the _ _CALLEE_ _ calling mode if possible
  Most of the z88dk library is usese the 'FASTCALL' or 'CALLEE' modes to save memory and execution time.
  This is a method for advanced users, though.  
    
    -- Calling methods as described by Alvin in the forum pages --
    
    To first approximation, the best way to get the best performance out of a C compiler for a small cpu
    is to make sure the libraries are hand coded in asm so that most cycles are spend in handcrafted code
    rather than compiler generated code.  The place that generated code for the z80 is now is still far
    from optimally hand coded stuff.   So a chunk of the effort in z88dk's dev has been in hand coded libraries.
    
    Further, the idea is to make sure z88dk is not just a C development environment but also an asm level dev
    environment.   This means the preference is to have these hand coded libraries efficiently accessible from
    both C and asm.
    
    For this kind of thing to be accessible from sdcc there has to be a convention for calling asm routines and
    passing parameters to them efficiently.
    
    Right now in z88dk there are three calling conventions:
    
       1. the smallc one with the left to right pushing of params on stack and the caller expected to clean
          up the stack after the function returns.  this is z88dk's equivalent of the right to left convention
          in sdcc.
          
          An example bit of generated code:
          
            extern int test(int a, b);
          
            ...
          
            ld hl,(_aloc)  ; push params
            push hl
            ld hl,(_bloc)
            push hl
            call _test
            pop bc    ; clean up stack
            pop bc
          
          
      2. fastcall where a single parameter is passed by register in (DE)HL.  this is meant for asm libraries or
         user supplied asm.
          
         An example bit of code generated by the caller might look like this:
          
            extern int __FASTCALL__ test(int d);
          
            ...
          
            ld hl,(paramlocation)
            call _test
          
          
      3. callee where the target function is expected to clean up the stack.  this is also meant for asm libraries
         or user supplied asm.  asm functions pop params off the stack as they read them, effectively cleaning up
         the stack.  this can lead to savings of hundreds of bytes in compiled programs since the compiler doesn't
         have to generate stack cleanup code each time the function is called.
          
         Example:
          
          
            extern int __CALLEE__ test(int a, int b);
          
            ...
          
            ld hl,(aloc)   ; push params
            push hl
            ld hl,(bloc)
            push hl
            call _test  ; stack cleanup performed at target function
          
          
    Three different linkage conventions can mess with calls through function pointers unless the compiler can
    determine what the linkage is.  z88dk is not strongly enough typed to do this.
          
    eg, you can do this:
          
          void *f;
          f = strcpy;
          (f)(d, s);
          
    No way can the compiler know if strcpy is called CALLEE or C convention.
    So in z88dk, now, all calls through function pointers are done with C linkage and every CALLEE function 
    has a second entry point associated with it using C linkage.  This second entry point does not get linked
    into the binary unless the program actually needs it.  Some cpp macro magic makes sure function pointer
    assignments like "f = strcpy" get the C linkage stub whereas stuff like "strcpy(d,s)" gets the CALLEE linkage.
 
optimization.txt · Last modified: 2012/10/08 07:16 by stefano
 
Recent changes RSS feed Donate Powered by PHP Valid XHTML 1.0 Valid CSS Driven by DokuWiki