Warning: file_get_contents(/data/phpspider/zhask/data//catemap/7/css/32.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Embedded 启动裸机ARM应用程序时出现问题_Embedded_Arm_Llvm_Bare Metal - Fatal编程技术网

Embedded 启动裸机ARM应用程序时出现问题

Embedded 启动裸机ARM应用程序时出现问题,embedded,arm,llvm,bare-metal,Embedded,Arm,Llvm,Bare Metal,我正在尝试使用LLVM生成裸臂CortexM4开发的代码。 IR的创建进行得很顺利,LLVM正在生成(在我看来)正确的手臂拇指ASM 我买了一个Arm开发工具包来做一些测试:一个Atmel SAM4L-EK 我创建了一个在开发板上打开黄色led的应用程序。 (我只是想从董事会得到一些东西) 我用Atmel Studio运行了一个附带的应用程序,LED工作正常。 但我的应用程序似乎什么都没做 根据手册,LED连接至PC10 在ATSAM4LC4C MCU的数据表中,说明GPIO端口的地址为0x4

我正在尝试使用LLVM生成裸臂CortexM4开发的代码。 IR的创建进行得很顺利,LLVM正在生成(在我看来)正确的手臂拇指ASM

我买了一个Arm开发工具包来做一些测试:一个Atmel SAM4L-EK

我创建了一个在开发板上打开黄色led的应用程序。 (我只是想从董事会得到一些东西) 我用Atmel Studio运行了一个附带的应用程序,LED工作正常。 但我的应用程序似乎什么都没做

根据手册,LED连接至PC10 在ATSAM4LC4C MCU的数据表中,说明GPIO端口的地址为0x400E1000, 一个端口占用0x0200字节的地址空间,因此端口C位于0x400E1000+0x0400上

这是我的程序输出(LLVM输出):

此代码将GPIOEnableRegister中的位10设置为1

然后将OutputDriverEnableRegister中的位10设置为1

然后将OutputValueRegister中的位10设置为1

此时LED应亮起

这是我使用的启动代码:

.section INTERRUPT_VECTOR, "x"
.global _Reset
_Reset:
B Reset_Handler /* Reset */
B . /* Undefined */
B . /* SWI */
B . /* Prefetch Abort */
B . /* Data Abort */
B . /* reserved */
B . /* IRQ */
B . /* FIQ */

Reset_Handler:
#mov    r0, stack_top
MOV sp,r0
BL main
B .
两个汇编程序文件都编译为如下所示的对象文件:

as -mcpu=cortex-m4 -g startup.s -o startup.o
ld -T linkerscript.ld armtest.o startup.o -o armtest.elf
使用GNU ARM汇编程序

这是我使用的链接器脚本:

ENTRY(_Reset)
OUTPUT_FORMAT("elf32-littlearm", "elf32-littlearm", "elf32-littlearm")
OUTPUT_ARCH(arm)
SEARCH_DIR(.)

/* Memory Spaces Definitions */
MEMORY
{
     rom (rx)  : ORIGIN = 0x00000000, LENGTH = 0x00040000 /* flash, 256K */
     ram (rwx) : ORIGIN = 0x20000000, LENGTH = 0x00008000 /* sram, 32K */
}

SECTIONS
{
 . = 0x0;
 .text : {
 startup.o (INTERRUPT_VECTOR)
 *(.text)
}
.data : { *(.data) }
.bss : { *(.bss COMMON) }
. = ALIGN(8);0
. = . + 0x1000; /* 4kB of stack memory */
stack_top = .;
}
然后将对象文件链接到ELF二进制文件,如下所示:

as -mcpu=cortex-m4 -g startup.s -o startup.o
ld -T linkerscript.ld armtest.o startup.o -o armtest.elf
使用GNU Arm链接器

然后,我使用Atmel Studio将ELF二进制文件上传到主板上

Bot无任何事情发生(重置后也不会发生)


任何见解都将不胜感激

cortex-m系列不像非cortex-m系列手臂那样启动。cortex-m采用(非arm)传统的中断向量表方法,而不是像全尺寸arms那样的指令表

/* vectors.s */
.thumb

.word   0x20020000  /* stack top address */
.word   _start      /* 1 Reset */
.word   hang        /* 2 NMI */
.word   hang        /* 3 HardFault */
.word   hang        /* 4 MemManage */
.word   hang        /* 5 BusFault */
.word   hang        /* 6 UsageFault */
.word   hang        /* 7 RESERVED */
.word   hang        /* 8 RESERVED */
.word   hang        /* 9 RESERVED*/
.word   hang        /* 10 RESERVED */
.word   hang        /* 11 SVCall */
.word   hang        /* 12 Debug Monitor */
.word   hang        /* 13 RESERVED */
.word   hang        /* 14 PendSV */
.word   hang        /* 15 SysTick */
.word   hang        /* 16 External Interrupt(0) */
.word   hang        /* 17 External Interrupt(1) */
.word   hang        /* 18 External Interrupt(2) */
.word   hang        /* 19 ...   */

.thumb_func
.global _start
_start:
    /*ldr r0,stacktop */
    /*mov sp,r0*/
    bl notmain
    b hang

.thumb_func
hang:   b .

您需要将堆栈顶部地址设置为特定于处理器的第一项。使用llvm,您可能需要在这里调整一些指令,上面是针对gnu的。

无论是谁投票认为这是“太本地化”的,请注意在接受的答案中指出的问题在家庭范围内的适用性!