ARM-based hardware startup programming-initializing stacks

Source: Internet
Author: User

There are 7 operating states for ARM, and the stack pointer Register (SP) for each state is independent. So, for each processor pattern that needs to be used in the program, define a stack address for the SP. The process is to modify the status bits within the status register, so that the processor switches to the desired mode, and assigns a value to the SP. It is important to note that you do not switch to user mode for the stack setting in this mode, because you can no longer manipulate CPSR to return to other modes after entering user mode.

Define the value of the CPSR register m[4:0] for each mode, which determines which mode to enter and refer to the relevant data sheet.

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 was set (1), IRQ is disabled

F_bit EQU 0x40; When F bit was set (1), FIQ is disabled

Here is the code snippet that initializes the stack:

Initstack

MOV R0, LR

; /* Set the management mode stack */

MSR Cpsr_c, # (Mode_svc | I_bit | F_bit); 0xd3

LDR SP, Stacksvc

; /* Set break mode stack */

MSR Cpsr_c, # (MODE_IRQ | I_bit | F_bit); 0xd2

LDR SP, STACKIRQ

; /* Set fast interrupt mode stack */

MSR Cpsr_c, # (Mode_fiq | I_bit | F_bit); 0xd1

LDR SP, Stackfiq

; /* Set Abort mode stack */

MSR Cpsr_c, # (Mode_abt | I_bit | F_bit); 0xd7

LDR SP, Stackabt

; /* Set undefined schema stack */

MSR Cpsr_c, # (Mode_und | I_bit | F_bit); 0xdb

LDR SP, Stackund

; /* Set the system mode stack */

MSR Cpsr_c, # (Mode_sys | I_bit | F_bit); 0xDF

LDR SP, STACKUSR

MOV PC, R0

STACKUSR DCD Usrstackspace + (usr_stack_legth-1) * 4

Stacksvc DCD Svcstackspace + (svc_stack_legth-1) * 4

STACKIRQ DCD Irqstackspace + (irq_stack_legth-1) * 4

Stackfiq DCD Fiqstackspace + (fiq_stack_legth-1) * 4

Stackabt DCD Abtstackspace + (abt_stack_legth-1) * 4

Stackund DCD Undtstackspace + (und_stack_legth-1) * 4

; /* Allocate stack space */

Area mystacks, DATA, Noinit, align=2

Usrstackspace Space Usr_stack_legth * 4; User (System) mode stack spaces

Svcstackspace Space Svc_stack_legth * 4; management mode stack spaces

Irqstackspace Space Irq_stack_legth * 4; break mode stack spaces

Fiqstackspace Space Fiq_stack_legth * 4; quick break mode stack space

Abtstackspace Space Abt_stack_legth * 4; abort semantic mode stack spaces

Undtstackspace SPACE und_stack_legth * 4; no schema stack defined

Take the management mode stack space as an example to illustrate.

Svc_stack_legth is defined as 16, with the result of allocating 16 4-byte storage space, initializing the storage space to 0, and pointing the SP at the bottom of the stack (memory high).

From the above memory content can be seen above. The management mode stack has been allocated from 0x00008080~0x00008044 altogether 16*4 byte space. Where the 0x00008040 address memory is placed on the 0x00008080, which is the value of the pointer at the bottom of the stack.

That is, stacksvc DCD Svcstackspace + (svc_stack_legth-1) * 4 This 32-bit pseudo-instruction, after compiling, is placed on the 0x00008040 (stacksvc) address svcstacks Pace Address Value (0x00008080). That is, the 0x00008080 was assigned to SP.

Then look at the address 0x00008080~0x00008044 on the content, all is Andeq r0,r0,r0. Translated from the assembly instruction format, Andeq r0,r0,r0 was translated into 16 block code, just as 0x00000000.

Stack initialization parsing in startup code magicchip posted on 2007-7-23 20:10:00

2

Recommended

If you support this site, please click on this site ads, to express support for me.

In the startup code are:

; Define the size of the stack

Svc_stack_legth EQU 0

Fiq_stack_legth EQU 0

Irq_stack_legth EQU 128

Abt_stack_legth EQU 0

Und_stack_legth EQU 0

Reset

LDR PC, Resetaddr

LDR PC, Undefinedaddr

LDR PC, Swi_addr

LDR PC, Prefetchaddr

LDR PC, Dataabortaddr

DCD 0xb9205f80

LDR pc, [pc, #-0xff0]

LDR PC, Fiq_addr

Resetaddr DCD Resetinit

Undefinedaddr DCD Undefined

Swi_addr DCD Softwareinterrupt

Prefetchaddr DCD Prefetchabort

Dataabortaddr DCD Dataabort

Nouse DCD 0

IRQ_ADDR DCD 0

Fiq_addr DCD Fiq_handler

; Directives not defined

Undefined

B Undefined

; Soft Interrupt

Softwareinterrupt

B Softwareinterrupt

Take command abort.

Prefetchabort

B Prefetchabort

Take data to abort

Dataabort

B Dataabort

; rapid interruption

Fiq_handler

B Fiq_handler

Stacksvc DCD Svcstackspace + (svc_stack_legth-1) * 4

STACKIRQ DCD Irqstackspace + (irq_stack_legth-1) * 4

Stackfiq DCD Fiqstackspace + (fiq_stack_legth-1) * 4

Stackabt DCD Abtstackspace + (abt_stack_legth-1) * 4

Stackund DCD Undtstackspace + (und_stack_legth-1) * 4

;/* Allocate stack space */

Area mystacks, DATA, Noinit, align=2

Svcstackspace Space Svc_stack_legth * 4; management mode stack spaces

Irqstackspace Space Irq_stack_legth * 4; break mode stack spaces

Fiqstackspace Space Fiq_stack_legth * 4; quick break mode stack space

Abtstackspace Space Abt_stack_legth * 4; abort semantic mode stack spaces

Undtstackspace SPACE und_stack_legth * 4; no schema stack defined

Among them, Irq_stack_legth is 128, according to

Irqstackspace Space Irq_stack_legth * 4; break mode stack spaces

Irqstackspace is the first address of a 128*4 byte space, and then the

STACKIRQ DCD Irqstackspace + (irq_stack_legth-1) * 4

, Irqstackspace + (irq_stack_legth-1) * 4 = 128*4 + (128-1) = (128+127), meaning the actual IRQ stack size is (128+127) * 4 bytes, is this true.

Answer 1: Is that so? STACKIRQ DCD Irqstackspace + (irq_stack_legth-1) * 4

The irqstackspace in the 128*4 is the first address of a contiguous byte, Irqstackspace + (irq_stack_legth-1) * 4 represents the offset of a base and a memory size, thus constituting 128*4 contiguous byte space.

Answer 2: But if that's the case, write it directly as

Stackirq DCD (irq_stack_legth) * 4

No, it's OK. Why do you use space statements?

Answer 3: Not as you say STACKIRQ DCD Irqstackspace + (irq_stack_legth-1) * 4

Here the STACKIRQ is written by Shelf, is a label, the essence is an address. The pseudo-directive is to place a value (Irqstackspace + (irq_stack_legth-1) * 4) on an address (STACKIRQ).

Irqstackspace SPACE Irq_stack_legth * 4

Is the space that is assigned a certain length (Irq_stack_legth * 4) starting from the location (address) of the irqstackspace.

The STACKIRQ actually points to the stack's top (the highest address of the stack).

Please refer to the common arm instruction set and compilation written by Wancheng, which contains explanations of these two instructions.

Answer 4:eyuge2 's right, Eyuge2 's right, Stakckirq. The stack top address of the vector interrupt stack

Answer 5:re I know where the problem is, I didn't understand the use of DCD and space properly.

It was wrong to follow the first post on my roof, and it was inappropriate to think so, because then there would be

(128+127) bytes as the stack space.

And in the third post that is sent later:

Is that so?

STACKIRQ DCD Irqstackspace + (irq_stack_legth-1) * 4

The irqstackspace in the 128*4 is the first address of a contiguous byte, Irqstackspace + (irq_stack_legth-1) * 4 represents a base add

The offset of the previous memory size makes up the 128*4 contiguous byte space.

is correct, but it confuses the functions of the DCD directive and the Space Command.

<label> DCD expr1 {, EXPR2}{,EXPR3} ...

The value of the expression is stored in the current address, this address is labeled as label, just EXPR1,EXPR2,EXPR3 ... Value is loaded in the label

At the beginning of the address, it is not possible to allocate expr1 consecutive bytes;

And space is used in the format

{Label} SPACE Expr

This command is the true allocation of expr a contiguous byte, and the first address of these contiguous bytes is a label,

So

In

STACKIRQ DCD Irqstackspace + (irq_stack_legth-1) * 4

, Irstackspace can be thought of as a base address, (IRQ_STACK_LEGTH-1) * 4 as an offset, both the and is the address of the most

High-end, this highest address is the stack STACKIRQ top. And the result of Irqstackspace + (irq_stack_legth-1) * 4 is after all a

Value, the value is stored in a DCD pseudo-instruction in the memory address labeled STACKIRQ, which reads the top of the stack when the STACKIRQ is accessed.

's address.

Just looked at the eyuge2 and autumn Maple Leaf replies to think so understanding should be, thank you two, thank you.

Answer 6: Yes, that's how you understand it!

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.