TCC (tiny c compiler) for AVR

1 post / 0 new
Author
Message
#1
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Hi,

in my effort to find a suitable compiler for AVR reduced core, I had a look at tcc http://bellard.org/tcc/ .

I have created an "avr" target that emits pseudo-code (so I can see how tcc works).

To wrap it up: tcc is completely stack-based and the registers are assumed to have 32bits. I dont see any way to port this to a 8bit architecture - and dont even think about accessing the stack-variables with the reduced core instruction set :)

HOWEVER, I see little effort left in doing a 32bit-core avr-tcc.

Example:

char moin(char a, char b)
{ 
  char c = a + b;
  char d = c + b;
  return c + d;
}

char aaa=1;

void main()
{
  char c1=2;
  char c2=3;
  char c3;

  c3 = moin(c1,c2);

  aaa = aaa + (c3*2+1)*c2;
}

compiles to pseudo code

$avr-tcc -c ex6.c
gfunc_prolog
 arg at stack ptr 0
 arg at stack ptr 1
load r1 from value sv
 load stack ptr 0
 load byte from stack
load r2 from value sv
 load stack ptr 1
 load byte from stack
gen_opi r1 += fr 2
store register r1 in lvalue v
 load stack ptr -1
 store byte to stack
load r1 from value sv
 load stack ptr -1
 load byte from stack
load r2 from value sv
 load stack ptr 1
 load byte from stack
gen_opi r1 += fr 2
store register r1 in lvalue v
 load stack ptr -2
 store byte to stack
load r1 from value sv
 load stack ptr -1
 load byte from stack
load r2 from value sv
 load stack ptr -2
 load byte from stack
gen_opi r1 += fr 2
gen_opi r1 <<= 24
gen_opi r1 >>= 24
load r6 from value sv
 load r6 = r1
gjmp 0
gfunc_epilog
------------
gfunc_prolog
load r1 from value sv
 load VT_CONST r1 = 2
store register r1 in lvalue v
 load stack ptr -3
 store byte to stack
load r1 from value sv
 load VT_CONST r1 = 3
store register r1 in lvalue v
 load stack ptr -4
 store byte to stack
gfunc_call args 2
load r1 from value sv
 load stack ptr -4
 load byte from stack
 put reg r1 on stack
load r1 from value sv
 load stack ptr -3
 load byte from stack
 put reg r1 on stack
gcall 0
store register r6 in lvalue v
 load stack ptr -5
 store byte to stack
load r1 from value sv
 load stack ptr -5
 load byte from stack
gen_opi r1 <<= 1
gen_opi r1 += 1
load r2 from value sv
 load stack ptr -4
 load byte from stack
gen_opi r1 *= fr 2
load r2 from value sv
 load sym-ptr + 0
 load byte from ptr
gen_opi r2 += fr 1
store register r2 in lvalue v
 load sym-ptr + 0
 store byte r2 to ptr
gfunc_epilog

A) You can clearly see the structure of the stack-machine that tcc is based on. You just have to fill in the blanks with code...

B) You can see the 32bit-to-8bit casting with the generated "gen_opi r1 <<= 24, gen_opi r1 >>= 24" instructions.

Please find attached complete sources based on the current tcc 0.9.25. The new "avr"-backend is in avr-gen.c. Have a look at the c67 and the arm-backends to see how other backends work.

If anyone is interested in finishing this for a 32bit core, I can help a little bit. But please note that I am mainly interested in the reduced core.

Best,
PRosendahl

Attachment(s):