当前位置:首页 > 单片机 > 单片机
[导读];/*****************************************************************************/;/* LPC2300.S: Startup file for Philips LPC2300 device series */;/******************************************************

;/*****************************************************************************/
;/* LPC2300.S: Startup file for Philips LPC2300 device series */
;/*****************************************************************************/
;/* <<< Use Configuration Wizard in Context Menu >>> */
;/*****************************************************************************/
;/* This file is part of the uVision/ARM development tools. */
;/* Copyright (c) 2007 Keil - An ARM Company. 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 LPC2300.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)
; * 0x40000000 when RAM_MODE is used
; *
; * RAM_MODE: when set the device is configured for code execution
; * from on-chip RAM starting at address 0x40000000.
; */
;/*
; 启动代码是在CPU复位后执行的
; 重映象:启动代码初始化寄存器,设置好CPU的端脚,中断向量
; 默认的地址 :0x00000000,不需要重新映象
; 当程序在RAM中运行时,地址位0x40000000
;
;
;*/

; Standard definitions of Mode bits and Interrupt (I & F) flags in PSRs

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

;堆栈大小设置(字节)
;// Stack Configuration (Stack Sizes in Bytes)
;// Undefined Mode <0x0-0xFFFFFFFF:8>
;// Supervisor Mode <0x0-0xFFFFFFFF:8>
;// Abort Mode <0x0-0xFFFFFFFF:8>
;// Fast Interrupt Mode <0x0-0xFFFFFFFF:8>
;// Interrupt Mode <0x0-0xFFFFFFFF:8>
;// User/System Mode <0x0-0xFFFFFFFF:8>
;//

;定义各种模式堆栈的空间大小
UND_Stack_Size EQU 0x00000000 ;定义未定义模式堆栈大小
SVC_Stack_Size EQU 0x00000008 ;定义管理模式堆栈大小
ABT_Stack_Size EQU 0x00000000 ;定义中止模式堆栈大小
FIQ_Stack_Size EQU 0x00000000 ;定义快速中断模式堆栈大小
IRQ_Stack_Size EQU 0x00000100 ;定义普通中断模式堆栈大小
USR_Stack_Size EQU 0x00000400 ;定义用户模式堆栈大小

; 将所有的堆栈大小进行相加,得到总堆栈大小
ISR_Stack_Size EQU (UND_Stack_Size + SVC_Stack_Size + ABT_Stack_Size +
FIQ_Stack_Size + IRQ_Stack_Size)

;开辟一个名为STACK的段,定义为可写可读,字节对齐

AREA STACK, NOINIT, READWRITE, ALIGN=3

;定义堆栈的空间,用户的在上面,ISR(中断处理)的在下面

Stack_Mem SPACE USR_Stack_Size ;申请堆栈内存空间

__initial_sp SPACE ISR_Stack_Size ;申请堆栈内存空间


Stack_Top ;在这里放个标号,用来获得堆栈顶部地址
;// Heap Configuration
;// Heap Size (in Bytes) <0x0-0xFFFFFFFF>
;//

Heap_Size EQU 0x00000000 ;(Heap)堆是C语言动态分配内存使用,是编译器自己设定,如果没

;有Printf ,New,Malloc之类的函数可以不设置

;开辟一个名为HEAP的段,定义为可写可读,字节对齐

AREA HEAP, NOINIT, READWRITE, ALIGN=3
__heap_base ;指定堆的开头
Heap_Mem SPACE Heap_Size
__heap_limit ;指定堆的结尾


; System Control Block (SCB) Module Definitions
SCB_BASE EQU 0xE01FC000 ; SCB Base Address
PLLCON_OFS EQU 0x80 ; PLL Control Offset
PLLCFG_OFS EQU 0x84 ; PLL Configuration Offset
PLLSTAT_OFS EQU 0x88 ; PLL Status Offset
PLLFEED_OFS EQU 0x8C ; PLL Feed Offset
CCLKCFG_OFS EQU 0x104 ; CPU Clock Divider Reg Offset
USBCLKCFG_OFS EQU 0x108 ; USB Clock Divider Reg Offset
CLKSRCSEL_OFS EQU 0x10C ; Clock Source Select Reg Offset
SCS_OFS EQU 0x1A0 ; System Control and Status Reg Offset
PCLKSEL0_OFS EQU 0x1A8 ; Peripheral Clock Select Reg 0 Offset
PCLKSEL1_OFS EQU 0x1AC ; Peripheral Clock Select Reg 1 Offset

; Constants
OSCRANGE EQU (1<<4) ; Oscillator Range Select
OSCEN EQU (1<<5) ; Main oscillator Enable
OSCSTAT EQU (1<<6) ; Main Oscillator Status
PLLCON_PLLE EQU (1<<0) ; PLL Enable
PLLCON_PLLC EQU (1<<1) ; PLL Connect
PLLSTAT_M EQU (0x7FFF<<0) ; PLL M Value
PLLSTAT_N EQU (0xFF<<16) ; PLL N Value
PLLSTAT_PLOCK EQU (1<<26) ; PLL Lock Status

;时钟的建立
;// Clock Setup
;// System Controls and Status Register (SCS) ;系统控制和状态寄存器
;// OSCRANGE: Main Oscillator Range Select ;主晶振的范围选择
;// <0=> 1 MHz to 20 MHz
;// <1=> 15 MHz to 24 MHz
;// OSCEN: Main Oscillator Enable ;主晶振使能
;//

;//

;时钟源选择
;//
;// Clock Source Select Register (CLKSRCSEL) ;PLL时钟源选择
;// CLKSRC: PLL Clock Source Selection
;// <0=> Internal RC oscillator ;内部RC
;// <1=> Main oscillator;主晶振
;// <1=> RTC oscillator ;实时时钟晶振
;//

;PLL的配置
;//
;// PLL Configuration Register (PLLCFG)
;// PLL_clk = (2* M * PLL_clk_src) / N
;// MSEL: PLL Multiplier Selection;PLL倍频
;// <1-32768><#-1>
;// M Value
;// NSEL: PLL Divider Selection ;PLL分频
;// <1-256><#-1>
;// N Value
;//

;CPU时钟配置
;//
;// CPU Clock Configuration Register (CCLKCFG)
;// CCLKSEL: Divide Value for CPU Clock from PLL ;系统的频率,由PLL分频得到
;// <1-256><#-1>
;//

;USB时钟配置
;//
;// USB Clock Configuration Register (USBCLKCFG)
;// USBSEL: Divide Value for USB Clock from PLL ;USB的频率,由PLL分频得到
;// <1-16><#-1>
;//

;外设时钟选择
;//
;// Peripheral Clock Selection Register 0 (PCLKSEL0)
;// PCLK_WDT: Peripheral Clock Selection for WDT ;WDT的外设时钟
;// <0=> Pclk = Cclk / 4 ;系统时钟/4
;// <1=> Pclk = Cclk ;系统时钟
;// <2=> Pclk = Cclk / 2 ;系统时钟/2
;// <3=> Pclk = Hclk / 8 ;AHB总线时钟/2

;// PCLK_TIMER0: Peripheral Clock Selection for TIMER0 ;TIMER0时钟选择
;// <0=> Pclk = Cclk / 4
;// <1=> Pclk = Cclk
;// <2=> Pclk = Cclk / 2
;// <3=> Pclk = Hclk / 8
;// PCLK_TIMER1: Peripheral Clock Selection for TIMER1 ;TIMER0时钟选择
;// <0=> Pclk = Cclk / 4
;// <1=> Pclk = Cclk
;// <2=> Pclk = Cclk / 2
;// <3=> Pclk = Hclk / 8
;// PCLK_UART0: Peripheral Clock Selection for UART0 ;UART0时钟选择
;// <0=> Pclk = Cclk / 4
;// <1=> Pclk = Cclk
;// <2=> Pclk = Cclk / 2
;// <3=> Pclk = Hclk / 8
;// PCLK_UART1: Peripheral Clock Selection for UART1 ;UART1时钟选择
;// <0=> Pclk = Cclk / 4
;// <1=> Pclk = Cclk
;// <2=> Pclk = Cclk / 2
;// <3=> Pclk = Hclk / 8
;// PCLK_PWM0: Peripheral Clock Selection for PWM0 ;PWM0时钟选择
;// <0=> Pclk = Cclk / 4
;// <1=> Pclk = Cclk
;// <2=> Pclk = Cclk / 2
;// <3=> Pclk = Hclk / 8
;// PCLK_PWM1: Peripheral Clock Selection for PWM1 ;PWM1时钟选择
;// <0=> Pclk = Cclk / 4
;// <1=> Pclk = Cclk
;// <2=> Pclk = Cclk / 2
;// <3=> Pclk = Hclk / 8
;// PCLK_I2C0: Peripheral Clock Selection for I2C0 ;I2C0时钟选择
;// <0=> Pclk = Cclk / 4
;// <1=> Pclk = Cclk
;// <2=> Pclk = Cclk / 2
;// <3=> Pclk = Hclk / 8
;// PCLK_SPI: Peripheral Clock Selection for SPI ;SPI时钟选择
;// <0=> Pclk = Cclk / 4
;// <1=> Pclk = Cclk
;// <2=> Pclk = Cclk / 2
;// <3=> Pclk = Hclk / 8
;// PCLK_RTC: Peripheral Clock Selection for RTC ;RTC 时钟选择
;// <0=> Pclk = Cclk / 4
;// <1=> Pclk = Cclk
;// <2=> Pclk = Cclk / 2
;// <3=> Pclk = Hclk / 8
;// PCLK_SSP1: Peripheral Clock Selection for SSP1 ;SSP1时钟选择
;// <0=> Pclk = Cclk / 4
;// <1=> Pclk = Cclk
;// <2=> Pclk = Cclk / 2
;// <3=> Pclk = Hclk / 8
;// PCLK_DAC: Peripheral Clock Selection for DAC ;DAC时钟选择
;// <0=> Pclk = Cclk / 4
;// <1=> Pclk = Cclk
;// <2=> Pclk = Cclk / 2
;// <3=> Pclk = Hclk / 8
;// PCLK_ADC: Peripheral Clock Selection for ADC ;ADC时钟选择
;// <0=> Pclk = Cclk / 4
;// <1=> Pclk = Cclk
;// <2=> Pclk = Cclk / 2
;// <3=> Pclk = Hclk / 8
;// PCLK_CAN1: Peripheral Clock Selection for CAN1;CAN总线1时钟选择
;// <0=> Pclk = Cclk / 4
;// <1=> Pclk = Cclk
;// <2=> Pclk = Cclk / 2
;// <3=> Pclk = Hclk / 6
;// PCLK_CAN2: Peripheral Clock Selection for CAN2 ;CAN总线2时钟选择
;// <0=> Pclk = Cclk / 4
;// <1=> Pclk = Cclk
;// <2=> Pclk = Cclk / 2
;// <3=> Pclk = Hclk / 6
;// PCLK_ACF: Peripheral Clock Selection for ACF ;高级通讯时钟选择
;// <0=> Pclk = Cclk / 4 ;在这为以太网
;// <1=> Pclk = Cclk
;// <2=> Pclk = Cclk / 2
;// <3=> Pclk = Hclk / 6
;//

;外设时钟选择
;//
;// Peripheral Clock Selection Register 1 (PCLKSEL1)
;// PCLK_BAT_RAM: Peripheral Clock Selection for the Battery Supported RAM ;电池RAM
;// <0=> Pclk = Cclk / 4
;// <1=> Pclk = Cclk
;// <2=> Pclk = Cclk / 2
;// <3=> Pclk = Hclk / 8
;// PCLK_GPIO: Peripheral Clock Selection for GPIOs ;GPIO 时钟
;// <0=> Pclk = Cclk / 4
;// <1=> Pclk = Cclk
;// <2=> Pclk = Cclk / 2
;// <3=> Pclk = Hclk / 8
;// PCLK_PCB: Peripheral Clock Selection for Pin Connect Block ;引脚连接模块时钟
;// <0=> Pclk = Cclk / 4
;// <1=> Pclk = Cclk
;// <2=> Pclk = Cclk / 2
;// <3=> Pclk = Hclk / 8
;// PCLK_I2C1: Peripheral Clock Selection for I2C1 ;I2C1时钟
;// <0=> Pclk = Cclk / 4
;// <1=> Pclk = Cclk
;// <2=> Pclk = Cclk / 2
;// <3=> Pclk = Hclk / 8 ;SSP1时钟
;// PCLK_SSP0: Peripheral Clock Selection for SSP0
;// <0=> Pclk = Cclk / 4
;// <1=> Pclk = Cclk
;// <2=> Pclk = Cclk / 2
;// <3=> Pclk = Hclk / 8
;// PCLK_TIMER2: Peripheral Clock Selection for TIMER2;TIMER2时钟
;// <0=> Pclk = Cclk / 4
;// <1=> Pclk = Cclk
;// <2=> Pclk = Cclk / 2
;// <3=> Pclk = Hclk / 8
;// PCLK_TIMER3: Peripheral Clock Selection for TIMER3 ;TIMER3时钟
;// <0=> Pclk = Cclk / 4
;// <1=> Pclk = Cclk
;// <2=> Pclk = Cclk / 2
;// <3=> Pclk = Hclk / 8
;// PCLK_UART2: Peripheral Clock Selection for UART2;UART2时钟
;// <0=> Pclk = Cclk / 4
;// <1=> Pclk = Cclk
;// <2=> Pclk = Cclk / 2
;// <3=> Pclk = Hclk / 8
;// PCLK_UART3: Peripheral Clock Selection for UART3 ;UART3时钟
;// <0=> Pclk = Cclk / 4
;// <1=> Pclk = Cclk
;// <2=> Pclk = Cclk / 2
;// <3=> Pclk = Hclk / 8;I2C2时钟
;// PCLK_I2C2: Peripheral Clock Selection for I2C2
;// <0=> Pclk = Cclk / 4
;// <1=> Pclk = Cclk
;// <2=> Pclk = Cclk / 2
;// <3=> Pclk = Hclk / 8
;// PCLK_I2S: Peripheral Clock Selection for I2S ;I2S(数字音频设备)时钟
;// <0=> Pclk = Cclk / 4
;// <1=> Pclk = Cclk
;// <2=> Pclk = Cclk / 2
;// <3=> Pclk = Hclk / 8
;// PCLK_MCI: Peripheral Clock Selection for MCI ;MCI(媒体控制接口)时钟
;// <0=> Pclk = Cclk / 4
;// <1=> Pclk = Cclk
;// <2=> Pclk = Cclk / 2
;// <3=> Pclk = Hclk / 8
;// PCLK_SYSCON: Peripheral Clock Selection for System Control Block;系统控制模块时钟
;// <0=> Pclk = Cclk / 4
;// <1=> Pclk = Cclk
;// <2=> Pclk = Cclk / 2
;// <3=> Pclk = Hclk / 8
;//

;//
CLOCK_SETUP EQU 1
SCS_Val EQU 0x00000020 ;使用外部晶振
CLKSRCSEL_Val EQU 0x00000001 ;选择主晶振的PLL输出
;Fcco(电流控制振荡器)的范围为275MHZ~550MHZ
;Fin 的范围为32k~50MHZ
;Fcco=(2*M*Fin)/N
;M,N在写入寄存器的时候减1

;Fcco=(2*12*12M)/1=288M,LPC2378的FCCO范围:275MHZ~550MHZ
PLLCFG_Val EQU 0x0000000B

;Fcclk=PLL/CCLKSEL=288M/4=72MHZ
CCLKCFG_Val EQU 0x00000003 ;CCLKCFG的值必须为0或者奇数,否则会引起器件的不正确操作

;USB时钟=PLL/USBSEL=288/6=48MHZ
USBCLKCFG_Val EQU 0x00000005

;外设时钟=CCLK/4=72MHZ/4=18MHZ
PCLKSEL0_Val EQU 0x00000000
PCLKSEL1_Val EQU 0x00000000

;内存加速模块
; 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

;内存加速模块控制
;// MAM Setup
;// MAM Control
;// <0=> Disabled ;全部禁止
;// <1=> Partially Enabled ;部分使能
;// <2=> Fully Enabled ;全部使能
;// Mode ;保留
;// MAM Timing
;// <0=> Reserved <1=> 1 <2=> 2 <3=> 3
;// <4=> 4 <5=> 5 <6=> 6 <7=> 7
;// Fetch Cycles
;//

MAM_SETUP EQU 1 ; MAM 设置程序判断标志
MAMCR_Val EQU 0x00000002 ; MAM全部使能
MAMTIM_Val EQU 0x00000004 ; MAM,4个CPU时钟访问一次内存


; Area Definition and Entry Point
; Startup Code must be linked first at Address at which it expects to run.

;程序入口点,每个ARM必须至少要有一个入口

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, #-0x0120] ;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;B为跳转指令,跳转到某个地方
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 Clock
IF CLOCK_SETUP != 0
LDR R0, =SCB_BASE
;使PLL配置寄存器有效
MOV R1, #0xAA
MOV R2, #0x55
;配置使能PLL
; Configure and Enable PLL
LDR R3, =SCS_Val ; Enable main oscillator
STR R3, [R0, #SCS_OFS] ;SCS<=SCS_Val ,主晶振使能,使用外部引脚的晶振

IF (SCS_Val:AND:OSCEN) != 0 ;晶振是否已经稳定,继续判断
OSC_Loop LDR R3, [R0, #SCS_OFS] ; Wait for main osc stabiliz 等待主晶振稳定
ANDS R3, R3, #OSCSTAT
BEQ OSC_Loop ;
ENDIF

LDR R3, =CLKSRCSEL_Val ; Select PLL source clock
STR R3, [R0, #CLKSRCSEL_OFS] ; CLKSRCSEL<=0x00000001 ,选择主晶振作为PLL时钟源

LDR R3, =PLLCFG_Val; PLLCFG <=0x0000000B,M,N赋值
STR R3, [R0, #PLLCFG_OFS]

STR R1, [R0, #PLLFEED_OFS]; PLLFEED <=0xAA
STR R2, [R0, #PLLFEED_OFS]; PLLFEED <=0x55

MOV R3, #PLLCON_PLLE; PLLCON <= 1<<0,PLL使能
STR R3, [R0, #PLLCON_OFS]

STR R1, [R0, #PLLFEED_OFS]; PLLFEED <=0xAA
STR R2, [R0, #PLLFEED_OFS]; PLLFEED <=0x55

;等待PLL锁存
; Wait until PLL Locked
PLL_Loop LDR R3, [R0, #PLLSTAT_OFS];;读PLLSTAT
ANDS R3, R3, #PLLSTAT_PLOCK ;是否PLL已经锁定
BEQ PLL_Loop

M_N_Lock LDR R3, [R0, #PLLSTAT_OFS] ;读PLLSTAT的状态
LDR R4, =(PLLSTAT_M:OR:PLLSTAT_N) ;读M,N的值
AND R3, R3, R4 ;R3=R3&&R4,M,N和锁存状态

LDR R4, =PLLCFG_Val ;R4<=M,N的值
EORS R3, R3, R4 ;M,N的设定值是否与读出值相等
BNE M_N_Lock

;设置CPU时钟
; Setup CPU clock divider
MOV R3, #CCLKCFG_Val;CPU时钟为PLL时钟/5
STR R3, [R0, #CCLKCFG_OFS]

;设置USB时钟
; Setup USB clock divider
LDR R3, =USBCLKCFG_Val ;USB时钟为PLL时钟/6
STR R3, [R0, #USBCLKCFG_OFS]

;设置外设时钟
; Setup Peripheral Clock
LDR R3, =PCLKSEL0_Val ;外设时钟=CPU时钟/4=57.6MHZ/4=14.4MHZ
STR R3, [R0, #PCLKSEL0_OFS]
LDR R3, =PCLKSEL1_Val
STR R3, [R0, #PCLKSEL1_OFS]

;开启PLL时钟
; Switch to PLL Clock
MOV R3, #(PLLCON_PLLE:OR:PLLCON_PLLC) ;PLL使能并连接
STR R3, [R0, #PLLCON_OFS]

STR R1, [R0, #PLLFEED_OFS] ;PLLFEED <=0xAA
STR R2, [R0, #PLLFEED_OFS] ;PLLFEED <=0x55
ENDIF ; CLOCK_SETUP

;设置MAM 存储器加速模块
; Setup MAM
IF MAM_SETUP != 0
LDR R0, =MAM_BASE
MOV R1, #MAMTIM_Val ;4个CPU时钟访问依次内存
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:RAM_MODE
MOV R1, #2
ELSE
MOV R1, #1
ENDIF
STR R1, [R0]
ENDIF

; 初始化中断堆栈系统
; Initialise Interrupt System
; ...


;设置每一个工作模式堆栈
; Setup Stack for each mode

LDR R0, =Stack_Top ;R0设置为堆栈的首地址

; 进入未定义模式,并设置堆栈指针
; 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

;进入C代码, __main前的下划线不要去,进入C代码库的初始化函数,再进入用户的函数
; Enter the C code

IMPORT __main
LDR R0, =__main
BX R0


IF :DEF:__MICROLIB

EXPORT __heap_base
EXPORT __heap_limit

ELSE

;用户设置堆栈程序(C外部接口:用于动态申请内存使用)
; User Initial Stack & Heap
AREA |.text|, CODE, READONLY

IMPORT __use_two_region_memory
EXPORT __user_initial_stackheap
__user_initial_stackheap

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


本站声明: 本文章由作者或相关机构授权发布,目的在于传递更多信息,并不代表本站赞同其观点,本站亦不保证或承诺内容真实性等。需要转载请联系该专栏作者,如若文章内容侵犯您的权益,请及时联系本站删除。
换一批
延伸阅读

LED驱动电源的输入包括高压工频交流(即市电)、低压直流、高压直流、低压高频交流(如电子变压器的输出)等。

关键字: 驱动电源

在工业自动化蓬勃发展的当下,工业电机作为核心动力设备,其驱动电源的性能直接关系到整个系统的稳定性和可靠性。其中,反电动势抑制与过流保护是驱动电源设计中至关重要的两个环节,集成化方案的设计成为提升电机驱动性能的关键。

关键字: 工业电机 驱动电源

LED 驱动电源作为 LED 照明系统的 “心脏”,其稳定性直接决定了整个照明设备的使用寿命。然而,在实际应用中,LED 驱动电源易损坏的问题却十分常见,不仅增加了维护成本,还影响了用户体验。要解决这一问题,需从设计、生...

关键字: 驱动电源 照明系统 散热

根据LED驱动电源的公式,电感内电流波动大小和电感值成反比,输出纹波和输出电容值成反比。所以加大电感值和输出电容值可以减小纹波。

关键字: LED 设计 驱动电源

电动汽车(EV)作为新能源汽车的重要代表,正逐渐成为全球汽车产业的重要发展方向。电动汽车的核心技术之一是电机驱动控制系统,而绝缘栅双极型晶体管(IGBT)作为电机驱动系统中的关键元件,其性能直接影响到电动汽车的动力性能和...

关键字: 电动汽车 新能源 驱动电源

在现代城市建设中,街道及停车场照明作为基础设施的重要组成部分,其质量和效率直接关系到城市的公共安全、居民生活质量和能源利用效率。随着科技的进步,高亮度白光发光二极管(LED)因其独特的优势逐渐取代传统光源,成为大功率区域...

关键字: 发光二极管 驱动电源 LED

LED通用照明设计工程师会遇到许多挑战,如功率密度、功率因数校正(PFC)、空间受限和可靠性等。

关键字: LED 驱动电源 功率因数校正

在LED照明技术日益普及的今天,LED驱动电源的电磁干扰(EMI)问题成为了一个不可忽视的挑战。电磁干扰不仅会影响LED灯具的正常工作,还可能对周围电子设备造成不利影响,甚至引发系统故障。因此,采取有效的硬件措施来解决L...

关键字: LED照明技术 电磁干扰 驱动电源

开关电源具有效率高的特性,而且开关电源的变压器体积比串联稳压型电源的要小得多,电源电路比较整洁,整机重量也有所下降,所以,现在的LED驱动电源

关键字: LED 驱动电源 开关电源

LED驱动电源是把电源供应转换为特定的电压电流以驱动LED发光的电压转换器,通常情况下:LED驱动电源的输入包括高压工频交流(即市电)、低压直流、高压直流、低压高频交流(如电子变压器的输出)等。

关键字: LED 隧道灯 驱动电源
关闭