Hi,
I'm working with the AT91SAM9260 controller - but I think it's a software problem.
I try to go to another c-function located at 0x200003A8 but the assembler code is very different
//c-code: status = function(pEmac); //both variables are defind as well as the function 0x2000052C E1800006 ORR R0, R0, R6 0x20000530 EBDFFF9C BL 0x1F8003A8 -> there is the error
the whole programm is running in the sdram. How could I get the information for this BL jump in the program?
best regards Stefan
A few questions: Does anything work at all? Any part of code? Does firmware upload work correctly? Does external memory work correctly? Is memory layout for linker configured correctly? Could you post longer snippets of disassembled code? It's difficult to match C and assembly code in the samples you posted.
The code is stored in a dataflash connected to NCS0. I use the bootloader programm from keil to start the programm from the dataflash in the SDRAM. The simple Blinky-program from Keil is working without problems.
I use this normal Blinky-programm to init the ethernet interface.
The whole programm is:
#include <AT91SAM9260.H> /* AT91SAM9260 definitions */ #include <lib_AT91SAM9260.h> /* Library function definitions */ #include "test.h" EMAC_pRX_descriptor p_rxBD = (EMAC_pRX_descriptor)AT91C_EMAC_TDLIST_BASE; char RxPacket[NB_ETH_RX_PACKETS*ETH_PACKET_SIZE]; void test2(AT91PS_EMAC pEmac) { return 0; } void test(void) { unsigned int status=0, i=0; AT91PS_EMAC pEmac = AT91C_BASE_EMACB; char *pRxPacket =(char *)RxPacket; // Disable TX & RX and more AT91C_BASE_EMACB->EMAC_NCR = 0; for(i=0; i< NB_ETH_RX_PACKETS; i++) { p_rxBD[i].RxBufAddr = ((unsigned int)(pRxPacket + (i * ETH_PACKET_SIZE))) & 0xFFFFFFFC; p_rxBD[i].RxBufStatus = 0; } //set wrap bit at the end of the list descriptor p_rxBD[NB_ETH_RX_PACKETS - 1].RxBufAddr |= EMAC_RXBUF_ADD_WRAP; AT91F_EMACB_CfgPMC(); AT91F_EMACB_CfgPIO(); //MDC clock AT91C_BASE_EMACB->EMAC_NCFGR = (AT91C_BASE_EMACB->EMAC_NCFGR & (~AT91C_EMAC_CLK))| AT91C_EMAC_CLK_HCLK_64; //init MDIO interface status = test2(pEmac); } int main(void) { test(); while(1); }
The BL jump error is at this position:
status = test2(pEmac);
If I shorten the programm, so that the test()-function has only test()-function call - everything seems to work. Therefore I'm not sure if the problem is in my own code. If I add a few more lines I got the same error as befor.
The dataflash is the AT45DB161D (528 byte pages and 10 addr lines) -> therefore I use the keil algorithm AT91SAM_528_CSO.
Could there be a problem with a small stack size in the internal SRAM? To start the second-bootloader programm I have to use one part (the first part from the internal RAM 0x00300000 to 0x00300E00 as ROM) and the second part (0x00300E00 to 0x003010000 as RAM).
3. what's the current mode while you jump and what's your jump range?
I use the user-mode which is also running. The programm loaded by the second-bootloader, is running in the SDRAM (0x20000000 start addr for the code, and 0x21000000 start addr for variables e.g.)
something which is very tricky is that the BL jump addr is nearly correct
0x1F8003BC FFFF07C0 ???
and the correct position of the function is
0x200003BC
But I don't know if that could be a hardware problem (communication problem with the sdram or whatever) because the first jump to the function test() is working and this jump has also the above addr lines 0x200.... best regards Stefan
Why not try to load the code in simulator and compare the disassembler output with that of real hardware? Or better yet, pull the contents of memory from target board and compare it with linker output. This way you can rule out memory corruption etc.
Or better yet, pull the contents of memory from target board and compare it with linker output.
Which file do you mean? I only know the map file (linker addr map), where I can check the positions for the global variables and the functions...
I also took a look into the memory window and I can see at the position 0x20000530 the value EBDFFF9C. But where could I see the label (0x1F8003A8)?
0x20000530 EBDFFF9C BL 0x1F8003A8
I mean compare the actual executable code produced by the linker with the contents of on-board memory. The way I would do this is like this: convert the ELF file from the linker into plain binary with fromelf.exe, pull contents of memory into a binary file, compare the two files with some sort of binary file compare tool.