Strange behaviour of ldr [pc, #value]

后端 未结 1 659
情话喂你
情话喂你 2020-12-16 17:54

I was debugging some c++ code (WinCE 6 on ARM platform), and i find some behavior strange:

    4277220C    mov         r3, #0x93, 30
    42772210    str              


        
相关标签:
1条回答
  • 2020-12-16 18:39

    This is correct. When pc is used for reading there is an 8-byte offset in ARM mode and 4-byte offset in Thumb mode.

    From the ARM-ARM:

    When an instruction reads the PC, the value read depends on which instruction set it comes from:

    • For an ARM instruction, the value read is the address of the instruction plus 8 bytes. Bits [1:0] of this value are always zero, because ARM instructions are always word-aligned.
    • For a Thumb instruction, the value read is the address of the instruction plus 4 bytes. Bit [0] of this value is always zero, because Thumb instructions are always halfword-aligned.

    This way of reading the PC is primarily used for quick, position-independent addressing of nearby instructions and data, including position-independent branching within a program.

    There are 2 reasons for pc-relative addressing.

    1. Position-independent code, which is in your case.
    2. Get some complicated constants nearby which cannot be written in 1 simple instruction, e.g. mov r3, #0x12345678 is impossible to complete in 1 instruction, so the compiler may put this constant in the end of the function and use e.g. ldr r3, [pc, #0x50] to load it instead.

    I don't know what mov r3, #0x93, 30 means. Probably it is mov r3, #0x93, rol 30 (which gives 0xC0000024)?

    0 讨论(0)
提交回复
热议问题