Hi Dmitry,

I hope this is of interest to you.  I know I have the source, and could
fiddle things myself, but this is way beyond my knowledge.

I've been playing about with bitfields, and looking at the code generated by
gcc for various manipulations.  Normally I tend to use chars to hold flag
registers and #defines to specify different flags, but I thought I might try
bitfields since I now have a good debugger that can display them properly.
There are a couple of places where I have spotted sub-optimal code, even
with -O2 or -O3 with plenty of flags.  I doubt if there is any point in
making an effort to optomise these particular points - after all, they are
purely artificial test cases, which are unlikely to be the same in real
code.  But it may be that you can generalise from them.

I have a bitfield structure defined:

typedef struct { unsigned char a : 1; unsigned char b : 1; } t;
t Test(t x) {
    x.a = x.b;
    return x;
}

The code generated is:
    mov.b r15, r14
    clrc
    rrc.b r14
    and.b #llo(1), r14
    bic.b #llo(1), r15
    bis.b r15, r14
    mov.b r14, r15
    ret

As far as I can see, the final mov should be removed, and the bis.b should
be "bis.b r14, r15".  I think the clrc could also be eliminated.

I have noticed on several occasions a tendancy to over-use r15.  For
example, in a switch statement I have seen the switch variable calculated in
another register (such as r14), which is then mov'ed into r15 before doing
the compares.

Finally, doing a switch on bitfields generates a lot of extra code, some of
which should definitely have been removed by the peephole optomisers:

switch(y.b) { ...                // y is in r11 here
    mov.b r11, r13
    clrc
    rrcb r13
    mov.b r13, r15            // All this could have been mov.b r11, r15;
rrcb r15
    and.b #llo(1), r15
    and.b #-1, r15            // ???
    cmp #llo(0), r15, etc.



Also, is there any way to optomise tail calls (if that is the right word) ?
I am thinking of a function that ends with a call to another function, where
the "call #...; ret" pair is replaced with a "jmp ..." instruction.


I always like to examine generated assembly, and look for ideas to improve
the generated code.  I must say it has been extremly difficult to find such
cases with msp430-gcc !

mvh.

David



Reply via email to