Christian Becker

Coldfire V1+ Inline Assembly (MCF51QM) for EMAC in Codewarrior V10.4

Discussion created by Christian Becker on Aug 6, 2013
Latest reply on Aug 6, 2013 by Jim Donelson

Hi everyone,

 

I´m trying to implement a assembly function which uses the EMAC Unit to multply over 2 32-bit Fields. I`ve started with a marcro described in CFLMOPM (EMAC / MAC Library) but it didnt work out of the box.

So I rewrite this macro to a Statement-level inline assembly according to 34.1.1.4.2 Statement-level in MCU_Coldfire_Compiler.pdf.

 

Unfortunately after calling the function the cpu traps in ISR(Cpu_ivViinstr).

 

My question is: Do I  maybe have to save and restore registers I`ve used in this inline assembly function? And if yes, how can I do this?

 

The original source was:

/* Save registers */\

        lea -60(a7),a7          

       movem.l d0-d7/a0-a5,(a7) 

 

and at the end

 

/* Restore registers */  \

     movem.l (a7),d0-d7/a0-a5 

     lea 60(a7),a7    

 

But I guess this won`t work anymore becaus of the register abi calling convention?!

 

Ive also tried different settings in coldfire compiler - processor -properties but it didnt help

     

 

 

Another question: Do I need the "rts" statement at the end?

 

 

 

Here`s my source code

 

 

void emac_mul (unsigned long * d,    unsigned long * s2,    unsigned long *s1, unsigned long n)

    {

     asm {

         

              /* Initialize MACSR register for unsigned operations */

            move.l #0x40,d0            ;

            move.l d0,MACSR            ;

            moveq.l %16,d0            ;

            /* Load function variables */

            move.l d,a0            ;

            move.l s1,a1            ;

            move.l s2,a2            ;

            move.l n,d1            ;

            /* Load counter */

            move.l d1,d2            ;

            /* Load in d1 number of 4 operations */

            asr.l %2,d1            ;

            beq *+72            ;

            /* Initialize eMAC accumulators */

            move.l #0,ACC0            ;

            move.l #0,ACC1            ;

            move.l #0,ACC2            ;

            move.l #0,ACC3            ;

            /* Perform 4 by 4 operations as MUL */

            movem.l (a1),d7/a3-a5        ;

            add.l d0,a1            ;

            movem.l (a2),d3-d6        ;

            macl.l d7,d3,(a1)+,d7,ACC0    ;

            macl.l a3,d4,(a1)+,a3,ACC1    ;

            macl.l a4,d5,(a1)+,a4,ACC2    ;

            macl.l a5,d6,(a1)+,a5,ACC3    ;

            /* Store results and clear accumulators */

            movclr.l ACC0,d3        ;

            movclr.l ACC1,d4        ;

            movclr.l ACC2,d5        ;

            movclr.l ACC3,d6        ;

            movem.l d3-d6,(a0)        ;

            add.l d0,a2            ;

            add.l d0,a0            ;

            subq.l %1,d1            ;

            bne *-38            ;

            /* Load in d2 number of operations Left */

            and.l %3,d2            ;

            beq *+16            ;

            sub.l d0,a1            ;

            /* Perform last operations as MUL */

            move.l (a6)+,d3            ;

            mulu.l (a1)+,d3            ;

            move.l d3,(a0)+            ;

            subq.l %1,d2            ;

            bne *-10            ;

            rts            ;

          }

    }

 

 

Maybe anyone has an idea or there`s a little hint to get this working.

 

Thanks for help

 

Christian

Outcomes