AnsweredAssumed Answered

Math code in RAM issue - EWL library in RAM

Question asked by Cesare Masetti on Apr 23, 2014
Latest reply on Apr 29, 2014 by Cesare Masetti

Hi,

I am currently developing a project with CW 10.1 on a K60 MCU.

I have successfully managed to place my code in RAM but I have encountered some issues while performing math operations which call for library functions. Here follows some sample code:

 

main.c:

#include <stdio.h>

#include <math.h>

#include "derivative.h" /* include peripheral declarations */

 

#pragma define_section text ".text" ".text" ".text" far_abs RX

#pragma define_section RAMCode ".RAMCode" ".RAMCode" ".RAMCode" far_abs RX

 

__declspec(RAMCode) int myRAMfunction(int cnt);

 

int main(void)

{

  int counter = 0;

  for(;;) {  

    counter++;

    counter = myRAMfunction(counter);

  }

  return 0;

}

 

__declspec(RAMCode) int myRAMfunction(int cnt)

{

  cnt = __aeabi_idiv(cnt,3);

cnt = cnt /3;

  return cnt;

}

 

Linker command file:

MEMORY {

m_interrupts  (RX) : ORIGIN = 0x00000000, LENGTH = 0x000001E0

m_text        (RX) : ORIGIN = 0x00000800, LENGTH = 0x00080000-0x00000800

m_data        (RW) : ORIGIN = 0x1FFF0000, LENGTH = 0x00010000

m_RAMexec  (RX) : ORIGIN = 0x20000000, LENGTH = 0x00001000

m_cfmprotrom  (RX) : ORIGIN = 0x00000400, LENGTH = 0x00000010

}

......

.RAMexec:

{

  . = ALIGN (0x8);

    * (.RAMCode)

  . = ALIGN (0x8);

} > m_RAMexec

....

 

The first #pragma sets .text section as far_abs and allows to call flash stored functions, both user defined and (most) library ones, in myRAMfunction.

As I try to perform, for example, a division operation, the MCU generates an exception.

However, the code runs smoothly if I directly call the library function __aeabi_idiv which seems to be the function the compiler calls while performing a division.

Looking at the disassembly while debugging sheds a bit of light:

          myRAMfunction:

20000000:   push {r4,lr}

20000002:   cpy r4,r0

27         cnt = __aeabi_idiv(cnt,3);

20000004:   ldr r2,[pc,#0x1c]

20000008:   cpy r0,r4

2000000a:   movs r1,#3

2000000c:   blx r2

2000000e:   cpy r4,r0

28         cnt = cnt /3;

20000010:   cpy r0,r4

20000012:   movs r1,#3

20000014:   bl $Ven$lb$$__aeabi_idiv._s32_div_f.o    (0x20000028); 0x20000028

20000018:   cpy r4,r0

29         return cnt;

2000001a:   cpy r0,r4

30        }

2000001c:   ldm sp!,{r4,lr}

20000020:   bx lr

20000022:   nop

20000024:   lsrs r5,r5,#16

20000026:   movs r0,r0

20000028:   bx pc

It seems that the compiler carries out the second division with a branch link to $Ven$lb$$__aeabi_idiv._s32_div_f.o, which unfortunately points to nowhere (0x20000028), while the explicit call to __aeabi_idiv works fine, moving the PC back to the flash section where the integer division code is stored.

 

1. Does anybody know how to solve this issue?

2. Is there a smooth way to load the math EWL libraries in RAM?

Outcomes