Optimizations

cpik performs many optimizations, but not all possible optimizations. Optimizations can be performed during code analysis, intermediate code generation, asm code generation and suprisingly after the code generation.

  1. NOP removal

    Most expressions that have no effect are simply removed. For example i = i + 0 ; does not produce any code.

  2. Register value tracking

    Value of W register is tracked whenever possible, so it is not reloaded when it contains the proper value. This feature only concern the W register, but I plan to extend it to FSR1 register.

  3. Constant folding

    Most constant subexpressions are computed by the compiler, so complex expressions are often compiled as a single constant (eg: x= (1+2*4) « 1 ;). However, a lot of constant foldings are done by the peephole optimizer or the expression simplifier (eg: st.a.b.c = 34 ; is exactly compiled like x = 34 ;)

  4. Peephole optimization

    Intermediate code is analyzed by grouping instructions into slices of 2, 3 or 4 items. Each slice is compared against a library of possible simplifications or transformations. Then, the simplified code is simplified again, and so on. This kind of optimization may lead to 25% to 30% gain.

  5. Code generator optimization

    This is the only phase that depends on the target architecture. Bit operations are excellent candidates for optimization. For example, consider the following macro to reset a single bit:

    #define CLRBIT(var,bit) ((var) &= ~(1 << (bit)))
    
    so
    CLRBIT(i,3) ;
    
    is expanded as
    ((i) &= ~(1 << (3))) ;
    
    which is optimally translated as:
    	bcf INDF0,3,0
    

    This example is a combination of constant folding and code generator optimizations.

  6. Dead code removal

    cpik takes into account constants when testing boolean conditions. For example, instructions like

    if(0) { ... }
    
    or
    while(0) { ... }
    
    do not generate any code. In the same way,
    while(1) { .. }
    
    generates a genuine infinite loop with no test, exactly like for(;;) { .. } does.

    However cpik does not perform a global analysis of code, so common subexpression removal are out of scope at this time.

  7. Jumps optimization

    cpik contains a special optional9 optimizer that allows to use short jumps instead of long ones, whenever possible. This step is executed after the asm source code generation and can reduce the memory size by $ 20\%$.



Footnotes

... optional9
See section 10.3
Alain Gibaud 2015-07-09