历史上的今天
今天是:2025年01月17日(星期五)
2019年01月17日 | 关于 keil mdk lpc2100 启动文件的思考
2019-01-17 来源:eefocus
;/*****************************************************************************/
;/* STARTUP.S: Startup file for Philips LPC2000 */
;/*****************************************************************************/
;/* <<< Use Configuration Wizard in Context Menu >>> */
;/*****************************************************************************/
;/* This file is part of the uVision/ARM development tools. */
;/* Copyright (c) 2005-2007 Keil Software. All rights reserved. */
;/* This software may only be used under the terms of a valid, current, */
;/* end user licence from KEIL for a compatible version of KEIL software */
;/* development tools. Nothing else gives you the right to use this software. */
;/*****************************************************************************/
;/*
; * The STARTUP.S code is executed after CPU Reset. This file may be
; * translated with the following SET symbols. In uVision these SET
; * symbols are entered under Options - ASM - Define.
; *
; * REMAP: when set the startup code initializes the register MEMMAP
; * which overwrites the settings of the CPU configuration pins. The
; * startup and interrupt vectors are remapped from:
; * 0x00000000 default setting (not remapped)
; * 0x80000000 when EXTMEM_MODE is used
; * 0x40000000 when RAM_MODE is used
; *
; * EXTMEM_MODE: when set the device is configured for code execution
; * from external memory starting at address 0x80000000.
; *
; * RAM_MODE: when set the device is configured for code execution
; * from on-chip RAM starting at address 0x40000000.
; *
; * EXTERNAL_MODE: when set the PIN2SEL values are written that enable
; * the external BUS at startup.
; */
; Standard definitions of Mode bits and Interrupt (I & F) flags in PSRs
; 七种模式,cpsr后8位
Mode_USR EQU 0x10
Mode_FIQ EQU 0x11
Mode_IRQ EQU 0x12
Mode_SVC EQU 0x13
Mode_ABT EQU 0x17
Mode_UND EQU 0x1B
Mode_SYS EQU 0x1F
I_Bit EQU 0x80 ; when I bit is set, IRQ is disabled
F_Bit EQU 0x40 ; when F bit is set, FIQ is disabled
;//
;//
;//
;//
;//
;//
;//
;//
UND_Stack_Size EQU 0x00000000
SVC_Stack_Size EQU 0x00000008
ABT_Stack_Size EQU 0x00000000
FIQ_Stack_Size EQU 0x00000000
IRQ_Stack_Size EQU 0x00000080
USR_Stack_Size EQU 0x00000400
;中断/异常服务程序栈 ,不要在\后面加注释
ISR_Stack_Size EQU (UND_Stack_Size + SVC_Stack_Size + ABT_Stack_Size + \
FIQ_Stack_Size + IRQ_Stack_Size)
;定义一个数据段,8字节对齐
AREA STACK, NOINIT, READWRITE, ALIGN=3
;space分配一块内存空间,并用0初始化,这段内存空间的首地址如何确定呢?首地址就是标号
Stack_Mem SPACE USR_Stack_Size
__initial_sp SPACE ISR_Stack_Size
Stack_Top ;此处说明栈顶为大地址,栈向下生长。
;//
;//
;//
;默认堆大小为0,程序运行时可以利用它动态申请内存吗?后文:如果定义了_Microlib,那么
;_heap_base 和_heap_limit可以被其他文件引用 。可以这样理解:如果定义_Microlib,那么
;就可以动态申请堆,并在启动文件中修改Heap_Size的大小,然后就可以用了,而默认是没有堆的
;你说呢?
Heap_Size EQU 0x00000000
AREA HEAP, NOINIT, READWRITE, ALIGN=3
__heap_base
Heap_Mem SPACE Heap_Size
__heap_limit
; VPBDIV definitions ;倍频,分频相关
VPBDIV EQU 0xE01FC100 ; VPBDIV Address
;//
;// Peripheral Bus Clock Rate
;//
;//
;//
;//
;//
;//
;//
;//
;//
VPBDIV_SETUP EQU 0
VPBDIV_Val EQU 0x00000000
; Phase Locked Loop (PLL) definitions
PLL_BASE EQU 0xE01FC080 ; PLL Base Address
PLLCON_OFS EQU 0x00 ; PLL Control Offset
PLLCFG_OFS EQU 0x04 ; PLL Configuration Offset
PLLSTAT_OFS EQU 0x08 ; PLL Status Offset
PLLFEED_OFS EQU 0x0C ; PLL Feed Offset
PLLCON_PLLE EQU (1<<0) ; PLL Enable
PLLCON_PLLC EQU (1<<1) ; PLL Connect
PLLCFG_MSEL EQU (0x1F<<0) ; PLL Multiplier
PLLCFG_PSEL EQU (0x03<<5) ; PLL Divider
PLLSTAT_PLOCK EQU (1<<10) ; PLL Lock Status
;//
;//
;// <1-32>
;// M Value
;//
;//
;// P Value
;//
PLL_SETUP EQU 0
PLLCFG_Val EQU 0x00000020
; Memory Accelerator Module (MAM) definitions
MAM_BASE EQU 0xE01FC000 ; MAM Base Address
MAMCR_OFS EQU 0x00 ; MAM Control Offset
MAMTIM_OFS EQU 0x04 ; MAM Timing Offset
;//
;//
;//
;//
;//
;// Mode
;//
;//
;//
;// Fetch Cycles
;//
MAM_SETUP EQU 0
MAMCR_Val EQU 0x00000002
MAMTIM_Val EQU 0x00000004
; External Memory Controller (EMC) definitions
EMC_BASE EQU 0xFFE00000 ; EMC Base Address
BCFG0_OFS EQU 0x00 ; BCFG0 Offset
BCFG1_OFS EQU 0x04 ; BCFG1 Offset
BCFG2_OFS EQU 0x08 ; BCFG2 Offset
BCFG3_OFS EQU 0x0C ; BCFG3 Offset
;//
EMC_SETUP EQU 0
;//
;//
;//
;//
;//
;//
;//
;//
;//
;//
BCFG0_SETUP EQU 0
BCFG0_Val EQU 0x0000FBEF
;//
;//
;//
;//
;//
;//
;//
;//
;//
;//
BCFG1_SETUP EQU 0
BCFG1_Val EQU 0x0000FBEF
;//
;//
;//
;//
;//
;//
;//
;//
;//
;//
BCFG2_SETUP EQU 0
BCFG2_Val EQU 0x0000FBEF
;//
;//
;//
;//
;//
;//
;//
;//
;//
;//
BCFG3_SETUP EQU 0
BCFG3_Val EQU 0x0000FBEF
;//End of EMC
; External Memory Pins definitions
PINSEL2 EQU 0xE002C014 ; PINSEL2 Address
PINSEL2_Val EQU 0x0E6149E4 ; CS0..3, OE, WE, BLS0..3,
; D0..31, A2..23, JTAG Pins
PRESERVE8
; Area Definition and Entry Point
; Startup Code must be linked first at Address at which it expects to run.
AREA RESET, CODE, READONLY
ARM
; Exception Vectors
; Mapped to Address 0.
; Absolute addressing mode must be used.
; Dummy Handlers are implemented as infinite loops which can be modified.
;传说中的中的中断向量表,程序从这里开始
Vectors LDR PC, Reset_Addr
LDR PC, Undef_Addr
LDR PC, SWI_Addr
LDR PC, PAbt_Addr
LDR PC, DAbt_Addr
NOP ; Reserved Vector
; LDR PC, IRQ_Addr
LDR PC, [PC, #-0x0FF0] ; Vector from VicVectAddr
LDR PC, FIQ_Addr
Reset_Addr DCD Reset_Handler
Undef_Addr DCD Undef_Handler
SWI_Addr DCD SWI_Handler
PAbt_Addr DCD PAbt_Handler
DAbt_Addr DCD DAbt_Handler
DCD 0 ; Reserved Address
IRQ_Addr DCD IRQ_Handler
FIQ_Addr DCD FIQ_Handler
Undef_Handler B Undef_Handler
SWI_Handler B SWI_Handler
PAbt_Handler B PAbt_Handler
DAbt_Handler B DAbt_Handler
IRQ_Handler B IRQ_Handler
FIQ_Handler B FIQ_Handler
; Reset Handler
EXPORT Reset_Handler
Reset_Handler
; Setup External Memory Pins
IF :DEF:EXTERNAL_MODE
LDR R0, =PINSEL2
LDR R1, =PINSEL2_Val
STR R1, [R0]
ENDIF
; Setup External Memory Controller
IF EMC_SETUP <> 0
LDR R0, =EMC_BASE
IF BCFG0_SETUP <> 0
LDR R1, =BCFG0_Val
STR R1, [R0, #BCFG0_OFS]
ENDIF
IF BCFG1_SETUP <> 0
LDR R1, =BCFG1_Val
STR R1, [R0, #BCFG1_OFS]
ENDIF
IF BCFG2_SETUP <> 0
LDR R1, =BCFG2_Val
STR R1, [R0, #BCFG2_OFS]
ENDIF
IF BCFG3_SETUP <> 0
LDR R1, =BCFG3_Val
STR R1, [R0, #BCFG3_OFS]
ENDIF
ENDIF ; EMC_SETUP
; Setup VPBDIV
IF VPBDIV_SETUP <> 0
LDR R0, =VPBDIV
LDR R1, =VPBDIV_Val
STR R1, [R0]
ENDIF
; Setup PLL
IF PLL_SETUP <> 0
LDR R0, =PLL_BASE
MOV R1, #0xAA
MOV R2, #0x55
; Configure and Enable PLL
MOV R3, #PLLCFG_Val
STR R3, [R0, #PLLCFG_OFS]
MOV R3, #PLLCON_PLLE
STR R3, [R0, #PLLCON_OFS]
STR R1, [R0, #PLLFEED_OFS]
STR R2, [R0, #PLLFEED_OFS]
; Wait until PLL Locked
PLL_Loop LDR R3, [R0, #PLLSTAT_OFS]
ANDS R3, R3, #PLLSTAT_PLOCK
BEQ PLL_Loop
; Switch to PLL Clock
MOV R3, #(PLLCON_PLLE:OR:PLLCON_PLLC)
STR R3, [R0, #PLLCON_OFS]
STR R1, [R0, #PLLFEED_OFS]
STR R2, [R0, #PLLFEED_OFS]
ENDIF ; PLL_SETUP
; Setup MAM
IF MAM_SETUP <> 0
LDR R0, =MAM_BASE
MOV R1, #MAMTIM_Val
STR R1, [R0, #MAMTIM_OFS]
MOV R1, #MAMCR_Val
STR R1, [R0, #MAMCR_OFS]
ENDIF ; MAM_SETUP
; Memory Mapping (when Interrupt Vectors are in RAM);中断向量重映射
MEMMAP EQU 0xE01FC040 ; Memory Mapping Control
IF :DEF:REMAP
LDR R0, =MEMMAP
IF :DEF:EXTMEM_MODE
MOV R1, #3
ELIF :DEF:RAM_MODE
MOV R1, #2
ELSE
MOV R1, #1
ENDIF
STR R1, [R0]
ENDIF
; Initialise Interrupt System
; ...
; Setup Stack for each mode ;除系统模式外的6种模式栈连续分布,系统模式的堆栈呢?
LDR R0, =Stack_Top
; Enter Undefined Instruction Mode and set its Stack Pointer
MSR CPSR_c, #Mode_UND:OR:I_Bit:OR:F_Bit
MOV SP, R0
SUB R0, R0, #UND_Stack_Size
; Enter Abort Mode and set its Stack Pointer
MSR CPSR_c, #Mode_ABT:OR:I_Bit:OR:F_Bit
MOV SP, R0
SUB R0, R0, #ABT_Stack_Size
; Enter FIQ Mode and set its Stack Pointer
MSR CPSR_c, #Mode_FIQ:OR:I_Bit:OR:F_Bit
MOV SP, R0
SUB R0, R0, #FIQ_Stack_Size
; Enter IRQ Mode and set its Stack Pointer
MSR CPSR_c, #Mode_IRQ:OR:I_Bit:OR:F_Bit
MOV SP, R0
SUB R0, R0, #IRQ_Stack_Size
; Enter Supervisor Mode and set its Stack Pointer ;栈向下生长
MSR CPSR_c, #Mode_SVC:OR:I_Bit:OR:F_Bit
MOV SP, R0
SUB R0, R0, #SVC_Stack_Size
; Enter User Mode and set its Stack Pointer
MSR CPSR_c, #Mode_USR
IF :DEF:__MICROLIB
EXPORT __initial_sp
ELSE
MOV SP, R0
SUB SL, SP, #USR_Stack_Size
ENDIF
; Enter the C code
IMPORT __main
LDR R0, =__main
BX R0 ;带状态切换的跳转 ,并不是跳到main(),与c/c++库函数有关,待详解;
IF :DEF:__MICROLIB
EXPORT __heap_base ;export声明一个符号可以被其他文件引用
EXPORT __heap_limit
ELSE
; User Initial Stack & Heap
; 这个程序段定义堆栈, c外部接口用于动态申请内存? 怎么用
;area定义出来的段名可以在scatter中用来指定区域
AREA |.text|, CODE, READONLY
IMPORT __use_two_region_memory ;调用外部:用两个存储区域?
EXPORT __user_initial_stackheap
__user_initial_stackheap ;
;放到寄存器中就完了,啥用呢?R0~R4用来传递参数,以供外部程序设置堆栈
;跟前面所定义用户模式的堆栈有啥区别?
LDR R0, = Heap_Mem
LDR R1, =(Stack_Mem + USR_Stack_Size)
LDR R2, = (Heap_Mem + Heap_Size)
LDR R3, = Stack_Mem
BX LR ;子程序返回
ENDIF
END
这个帖子类似于随笔,看了很多遍才基本把启动文件顺清楚,刚开始对汇编很排斥,虽说看了好多遍,完整看完的真没几遍,最近狠了下,发现汇编
也还是蛮清楚的,就那么几条。堆栈的划分还是有点疑惑,只能在以后的应用中慢慢体会了,到时再更新,欢迎一起讨论啊。
史海拾趣
|
本帖最后由 paulhyde 于 2014-9-15 09:41 编辑 当将模拟信号转换成方波脉冲后,再将脉冲信号送入单片机,那么单片机是怎样处理这个脉冲信号的? … 查看全部问答> |
|
note:usb address and data registers will not valid until usb clock is running 这是什么造成的呢?… 查看全部问答> |
|
技术在于积累! 第一次刚接触LED驱动是从一块DEMO板: DC输入,输出是低电流大致200MA的; 因为客户的需求,后来公司头一次想用SMD802开发一块非隔离的7*1w 450MA驱动板;那时候没买样板,也没找专门的IC厂商,要求技 ...… 查看全部问答> |
|
最近做了一个题目,使用蓝牙接收到的数据在LED点阵上显示出来,但是前提是不知道要接收的数据的内容。该如何实现接收到的数据用编程直接转换成LED点阵上能识别的二进制数。是该做一个字库还是有其他什么别的方法。请专业人士帮忙解决一下。谢谢。… 查看全部问答> |
|
windows ce stream driver wizard 搜遍了整个网络也没有找到windows ce stream driver wizard这个工具,哪位大哥大姐弟弟妹妹能够慷慨解囊,帮小弟一把,不胜感激。小弟的邮箱是:cougarz@somagic.com.cn… 查看全部问答> |
|
哪位达人用过《EVC高级编程及其应用开发》这本书上基础数据库的例子? 我在wince下试了这个程序,可是不好使阿,添加不了,也删除不了,请问是还需要安装什么程序还是本身实例程序有问题啊?… 查看全部问答> |
|
今天用Proteus仿真的ADC0809。。。但实际0809不工作啊。。。。 单片机的对应ST脚的P口接上0809时就被拉低了。Proteus仿真什么问题都没有。0809要注意什么问题么?有两个问题:1,我希望设定的是500K,用定时器方式2也是设成255。可从P口出来的就是50K 啊。2,ST脚被拉低,但不接0809时单片机P口是正常的 ...… 查看全部问答> |
|
我在使用msp430F149的JTAG模块下载时,一开始还能下载运行,试了有两三天,突然一天不能下载了,后来就再也不能下了,软件提示不能发现目标。然后又贴了一块板子,结果这块好了半天就又出现和前面一样的现象。很是郁闷 量了下载口各个引脚的电压 ...… 查看全部问答> |




