Question about ARM instruction: STMIA / STMEA

Hi,

When I read ARM Thumb2 instruction manual, I find a problem on STMIA / STMEA.

It said: "Store Multiple Increment After (Store Multiple Empty Ascending) stores multiple registers to consecutive memory locations using an address from a base register."

Does that mean STMIA is equivalent to STMEA?

Then, when I try to find the answer online, I have more questions on this topic. Below the dot line is from Keil website. Although it gives more explanation, I don't understand it, especially Table 4.5 and 4.6.

For example, on Table 4.5, there is one row has content:

FD (Full Descending stack) DB (Decrement Before) IA (Increment After)

I don't see the relationship between 'DB' and 'IA'. Could you explain it to me a little more?

Thanks in advance.

...............

formatting link

4.15 Stack implementation using LDM and STM You can use the LDM and STM instructions to implement pop and push operatio ns respectively. You use a suffix to indicate the stack type.

The load and store multiple instructions can update the base register. For stack operations, the base register is usually the stack pointer, SP. This means that you can use these instructions to implement push and pop operati ons for any number of registers in a single instruction. The load and store multiple instructions can be used with several types of stack: Descending or ascending The stack grows downwards, starting with a high address and progressing to a lower one (a descending stack), or upwards, starting from a low address a nd progressing to a higher address (an ascending stack). Full or empty The stack pointer can either point to the last item in the stack (a full st ack), or the next free space on the stack (an empty stack). To make it easier for the programmer, stack-oriented suffixes can be used i nstead of the increment or decrement, and before or after suffixes. The fol lowing table shows the stack-oriented suffixes and their equivalent address ing mode suffixes for load and store instructions: Table 4-5 Stack-oriented suffixes and equivalent addressing mode suffixes

Stack-oriented suffix For store or push instructions For load or pop instru ctions FD (Full Descending stack) DB (Decrement Before) IA (Increment After) FA (Full Ascending stack) IB (Increment Before) DA (Decrement After) ED (Empty Descending stack) DA (Decrement After) IB (Increment Before) EA (Empty Ascending stack) IA (Increment After) DB (Decrement Before) The following table shows the load and store multiple instructions with the stack-oriented suffixes for the various stack types: Table 4-6 Suffixes for load and store multiple instructions

Stack type Store Load Full descending STMFD (STMDB, Decrement Before) LDMFD (LDM, increment after ) Full ascending STMFA (STMIB, Increment Before) LDMFA (LDMDA, Decrement Afte r) Empty descending STMED (STMDA, Decrement After) LDMED (LDMIB, Increment Bef ore) Empty ascending STMEA (STM, increment after) LDMEA (LDMDB, Decrement Before ) For example: STMFD sp!, {r0-r5} ; Push onto a Full Descending Stack LDMFD sp!, {r0-r5} ; Pop from a Full Descending Stack

Reply to
Robert Willy
Loading thread data ...

I don't use ascending stacks, or the *EA instruction variants, so you need to check this yourself with objdump (or the equivalent tool in your toolchain) but I suspect you will find they generate the same opcode.

You use the first one (STMDB) to push onto the stack and you use the second one (LDMIA) to pop from the stack.

Read the section you quoted again, but thinking about how the address of the next available slot on the stack varies depending depending on the stack model in use and then you will realise they complement each other.

If it helps, draw out on paper how the stack contents (and stack pointer) change after each instruction variant and think about how this allows you to store data to, and recover data from, the stack.

Simon.

--
Simon Clubley, clubley@remove_me.eisner.decus.org-Earth.UFP 
Microsoft: Bringing you 1980s technology to a 21st century world
Reply to
Simon Clubley

They will, it's simply assembler sugar: STMEA = STMIA LDMEA = LDMDB STMFD = STMDB LDMFD = LDMIA

and so on. It's just two different notations, one for stacks (where you go 'forwards' and 'backwards') and one for normal loads/stores (where there's usually only 'forwards' - most data structures start at a low address and grow towards a higher address).

Theo

Reply to
Theo Markettos

Yes.

"EA" means that the stack is

a) "empty", meaning that the stack pointer points to the first word beyond the end of the stack (i.e. where the next "pushed" word will be stored), and b) "ascending", meaning that the stack grows upward in memory, i.e. pushing increases the stack pointer while popping decreases it.

So to push a word onto an empty+ascending stack, you store the word at the current stack pointer then increment the stack pointer (increment after = IA).

To pop a word from an empty+ascending stack you first decrement the stack pointer (so that it points to the last word on the stack rather than the space after it) then read the word it now points to (decrement before = DB).

To summarise: STMEA = STMIA, LDMEA = LDMDB.

The Increment/Decrement Before/After syntax describes the operation in terms of what happens to the register and when (this is the conventional pre/post-increment/decrement terminology). It's more appropriate if you aren't manipulating a stack.

The Empty/Full Ascending/Descending syntax describes the nature of the stack (on the assumption that you are actually dealing with a stack).

With the former, load and store operations are asymmetric (or more accurately, anti-symmetric). Whichever suffixes are used for the store, the opposite suffixes must be used for the load, e.g. STMIALDMDB.

With the latter, load and store always use the same suffix, e.g. STMEALDMEA.

This is all syntactic sugar. The LDM/STM opcode format has a flag for Increment (set) or Decrement (clear) and another for Before (set) or After (clear). The assembler takes care of converting either syntax to the appropriate flags.

Load Incr Before Opcode 1 Opcode 2

0 0 0 STMDA STMED 0 0 1 STMDB STMFD 0 1 0 STMIA STMEA 0 1 1 STMIB STMFA 1 0 0 LDMDA LDMFA 1 0 1 LDMDB LDMEA 1 1 0 LDMIA LDMFD 1 1 1 LDMIB LDMED
Reply to
Nobody

ss

ions respectively. You use a suffix to indicate the stack type.

r stack operations, the base register is usually the stack pointer, SP. Thi s means that you can use these instructions to implement push and pop opera tions for any number of registers in a single instruction.

f stack:

o a lower one (a descending stack), or upwards, starting from a low address and progressing to a higher address (an ascending stack).

stack), or the next free space on the stack (an empty stack).

instead of the increment or decrement, and before or after suffixes. The f ollowing table shows the stack-oriented suffixes and their equivalent addre ssing mode suffixes for load and store instructions:

ructions

he stack-oriented suffixes for the various stack types:

er)

ter)

efore)

re)

After several trials, I find that the original STR type stack operations:

PUSH {LR} SUB SP, SP, #44

STR V1, [SP, #28] STR V2, [SP, #24] STR V3, [SP, #20] STR V4, [SP, #16] STR A4, [SP, #12] STR A3, [SP, #8] STR A2, [SP, #4] STR A1, [SP, #0]

can be replaced as:

PUSH {LR} SUB SP, SP, #44

STR A4, [SP, #12] STR A3, [SP, #8] STR A2, [SP, #4] STR A1, [SP, #0]

ADD A4, SP, #28+4 STMFD A4!, {V1-V4} LDR A4, [SP, #12]

That is, the original offset #28 is substituted as #32. The pop stack part LDR

LDR V4, [SP, #16] LDR V3, [SP, #20] LDR V2, [SP, #24] LDR V1, [SP, #28] ADD SP, SP, #44

is substituted as:

ADD A4, SP, #16 LDMFD A4!, {V1-V4} ADD SP, SP, #44

Number #16 is the same. The compiler makes the SP pointer to the full position, increasing to the small address direction with more data pushed in.

Although it works as the STR/LDR instructions, I have not figured out why it needs #4 more in the push operation yet.

Thanks for your views.

Reply to
Robert Willy

Because STMFD assumes that the stack pointer is pointing to an 'occupied' (i.e. 'Full') location, so it is decremented first before the

1st store, thus you need to computer the stack frame location one element farther than the first item.
Reply to
Richard Damon

ElectronDepot website is not affiliated with any of the manufacturers or service providers discussed here. All logos and trade names are the property of their respective owners.