Hi,
I am about to implement some rtl procedures in avr - assembler, and of course register usage and calling conventions are important for that.
The fpc wiki says concerning avr, "It uses the GCC AVR tool chain and will be compatible with GCC regarding calling conventions etc.". That would be passing arguments in registers r25 - r8 downwards (first argument in r24, r25 if 16 byte, 2nd below that etc.). High bytes are in high and low bytes in low register no.
Function results are returned in r22 - r25 (32byte), r24-r25 (16 byte). According to GCC documentation, R0, R18-R27, R30, R31 are call used, R 2-R17, R28 and R29 are call saved. R1 has always to be 0.
Actual code produced by the compiler looks different. It is the same sequence of arguments (first in highest registers, second below that ...), but the byte order is reversed, lowest byte in highest register no.
After noting this discrepancy, I am of course unsure about the whole matter. Could somebody tell me what convention is actually used by the compiler?
A word to register R1: it shall be 0 at all times according to GCC specs. In some occasions, the compiler uses this to set other registers to 0, by MOV reg, R0. On other occasions the compiler uses the CLR Reg instruction (which is actually a pseudo opcode that translates to EOR reg, reg). On the other hand, R0 and R1 are used by the MUL / MULS / MULSU instructions to return the multiplication result. Forgetting to clear R0 again after a multiplication (i.e. in an assembler routine) will thus lead to errors at some later time.
As long as the MOV is not used because it does not change any status flags, It might be a good idea if the compiler always used the CLR instruction.
Thanks in advance for some info on the register stuff,
Georg
