frank26080115
Member
On Teensy 3, there is 16 KB of RAM available total, according to the reference manual, the SRAM is split into SRAM_L and SRAM_U
The Teensy 3 linker script simply states that
I have a bit of code that will malloc a piece of memory, by sheer coincidence, this bit of memory will occupy a bit of both regions. The memory contains an array of a struct, actually a list of files
This is a sample of my debug output as I am using memcpy to populate the file's information
notice how the memcpy failed for 0x1FFFFFDE , near the edge of the boundary.
then, I replaced memcpy with my own version, a trick to get my compiler to force 8 bit writes instead of 32 bit writes, it then works fine
it works fine
so I then run this bit of code
bam! instant crash hard fault. this almost confirms my suspicion that the crash is caused by the boundary between SRAM_L and SRAM_U.
so my question is: is cross-boundary operations like this disallowed on K10 and K20 hardware?
how can I make sure that the compiler is aware of this? I am using GCC 4.7.2
(I have posted the exact same question to the Freescale forum as well)
The Teensy 3 linker script simply states that
Code:
RAM (rwx) : ORIGIN = 0x1FFFE000, LENGTH = 16K
I have a bit of code that will malloc a piece of memory, by sheer coincidence, this bit of memory will occupy a bit of both regions. The memory contains an array of a struct, actually a list of files
This is a sample of my debug output as I am using memcpy to populate the file's information
Code:
file 1960 memcpy 0 addr 0x1FFFFCC0...done
file 1970 memcpy 1 addr 0x1FFFFCE6...done
file 1980 memcpy 2 addr 0x1FFFFD0C...done
file misc2 memcpy 3 addr 0x1FFFFD32...done
file 1990 memcpy 4 addr 0x1FFFFD58...done
file ABC_YA~1 memcpy 5 addr 0x1FFFFD7E...done
file AMBSTR~1 memcpy 6 addr 0x1FFFFDA4...done
file amoeba memcpy 7 addr 0x1FFFFDCA...done
file commod64 memcpy 8 addr 0x1FFFFDF0...done
file CUBES_~1 memcpy 9 addr 0x1FFFFE16...done
file EXPRIBB memcpy 10 addr 0x1FFFFE3C...done
file finlshot memcpy 11 addr 0x1FFFFE62...done
file GRAF_4KS memcpy 12 addr 0x1FFFFE88...done
file haduken memcpy 13 addr 0x1FFFFEAE...done
file intro memcpy 14 addr 0x1FFFFED4...done
file kickstar memcpy 15 addr 0x1FFFFEFA...done
file KS_HAL~1 memcpy 16 addr 0x1FFFFF20...done
file KS_TOGET memcpy 17 addr 0x1FFFFF46...done
file KSFINA~1 memcpy 18 addr 0x1FFFFF6C...done
file KSHELLOS memcpy 19 addr 0x1FFFFF92...done
file KSNINT memcpy 20 addr 0x1FFFFFB8...done
file lavapixe memcpy 21 addr 0x1FFFFFDE...
Exception Handler, source: 1
r0: 0x00000000, r1: 0x1FFFFA80, r2: 0x20000002, r3: 0x00000000, r12: 0x20001D8F
LR: 0x0000482F, PC: 0x0000484C, PSR: 0x61000000,
notice how the memcpy failed for 0x1FFFFFDE , near the edge of the boundary.
then, I replaced memcpy with my own version, a trick to get my compiler to force 8 bit writes instead of 32 bit writes, it then works fine
Code:
_PTR memcpy_safe(void* dest, void* src, int cnt)
{
int start = (int)dest;
int end = start + cnt;
if (start <= 0x1FFFFFFF && end >= 0x20000000) // if memory lies over SRAM_L and SRAM_U boundary
{
volatile uint8_t useless = 0; // force 8 bit copy instead of optimized 32 bit copy
volatile uint8_t c;
volatile int i = 0;
volatile uint8_t* src_p = (uint8_t*)src;
volatile uint8_t* dest_p = (uint8_t*)dest;
for (i = 0; i < cnt && useless == 0; i++) {
c = src_p[i];
dest_p[i] = c;
}
}
else
{
return memcpy(dest, src, cnt);
}
}
it works fine
Code:
file KSFINA~1 memcpy 18 addr 0x1FFFFF6C...done
file KSHELLOS memcpy 19 addr 0x1FFFFF92...done
file KSNINT memcpy 20 addr 0x1FFFFFB8...done
file lavapixe memcpy 21 addr 0x1FFFFFDE...done
file leon memcpy 22 addr 0x20000004...done
file lilypad memcpy 23 addr 0x2000002A...done
file LOGOAN01 memcpy 24 addr 0x20000050...done
file LOGOAN02 memcpy 25 addr 0x20000076...done
so I then run this bit of code
Code:
volatile uint32_t* foo;
foo = (volatile uint32_t*)0x1FFFFFFF; // right at the boundary between SRAM_L and SRAM_U
*foo = 0x12345678; // perform a 32 bit write
bam! instant crash hard fault. this almost confirms my suspicion that the crash is caused by the boundary between SRAM_L and SRAM_U.
so my question is: is cross-boundary operations like this disallowed on K10 and K20 hardware?
how can I make sure that the compiler is aware of this? I am using GCC 4.7.2
(I have posted the exact same question to the Freescale forum as well)