Search code examples
c++embeddedstm32bare-metalobjdump

Cannot find value in objdump output


I created a dummy program just to take a look at the assembly for research purposes. At the end of the question, you can find both the linker script, the startup file and the makefile, as well as my code. My problem is that in my code, I want to set bits in a register at address 0x48000000, however, I simply cannot locate this value in the output of the objdump. From the assembly, it seems that the value is coming from address 0x20000088, which is the SRAM of the device (STM32F030F4). But when and how does it land there? My first guess would have been that it should be located in the .data section and copied into the RAM on startup, but the .data section does not contain this value. Maybe there is something wrong with my code, or something gets optimized to an extend where it is no longer clear where the value is coming from, but it must be stored somwhere at some point. Every bit of help is appreciated.

Code:

#include <cstdint>
#include <concepts>
#include <type_traits>

constexpr std::uint32_t ModeRegisterAddress = 0x48000000;

enum class gpio_modes : std::uint32_t {
    input  = 0b00,
    output = 0b01,
    analog = 0b10
};

enum class pin_numbers : std::uint32_t {
    pin_0 = 0,
    pin_1 = 1,
    pin_2 = 2,
    pin_3 = 3,
    pin_4 = 4,
    pin_5 = 5,
    pin_6 = 6,
    pin_7 = 7
};

class CRegister {
private:
    const std::uint32_t m_address;
public:
    CRegister (std::uint32_t address) : m_address(address) { }

    void set (std::uint32_t val) const {
        *(reinterpret_cast<volatile std::uint32_t *>(this->m_address)) = val;
    }

    std::uint32_t get () const {
        return *(reinterpret_cast<volatile std::uint32_t *>(this->m_address));
    }

    void set (std::uint32_t value, std::uint32_t bitmask) const {
        std::uint32_t tmp = this->get();
        tmp &= ~bitmask;
        tmp |= value;
        this->set(tmp);
    }
};

class CModeRegister {
private:
    static inline const CRegister m_register { ModeRegisterAddress };

    template <pin_numbers pin, gpio_modes mode>
    static consteval std::uint32_t calculate_value () {
        return static_cast<std::uint32_t>(mode) << static_cast<std::uint32_t>(pin);
    }

    template <pin_numbers pin, gpio_modes mode>
    static consteval std::uint32_t calculate_bitmask () {
        return static_cast<std::uint32_t>(0b11) << static_cast<std::uint32_t>(pin);
    }
public:
    template <pin_numbers pin, gpio_modes mode>
    static inline void set_mode () {
        m_register.set(calculate_value<pin, mode>(), calculate_bitmask<pin, mode>());
    }
};

int main (void) {
    CModeRegister::set_mode<pin_numbers::pin_6, gpio_modes::output>();

    while (true) { /* ... */ }
}

Linker script:

ENTRY(Reset_Handler)

_estack = ORIGIN(RAM) + LENGTH(RAM);

_Min_Heap_Size = 0x200 ;
_Min_Stack_Size = 0x400 ;

MEMORY
{
  RAM    (xrw)    : ORIGIN = 0x20000000,   LENGTH = 4K
  FLASH    (rx)    : ORIGIN = 0x8000000,   LENGTH = 16K
}

SECTIONS
{
  .isr_vector :
  {
    . = ALIGN(4);
    KEEP(*(.isr_vector))
    . = ALIGN(4);
  } >FLASH

  .text :
  {
    . = ALIGN(4);
    *(.text)
    *(.text*)
    *(.glue_7)
    *(.glue_7t)
    *(.eh_frame)

    KEEP (*(.init))
    KEEP (*(.fini))

    . = ALIGN(4);
    _etext = .;
  } >FLASH

  .rodata :
  {
    . = ALIGN(4);
    *(.rodata)
    *(.rodata*)
    . = ALIGN(4);
  } >FLASH

  .ARM.extab   : {
    . = ALIGN(4);
    *(.ARM.extab* .gnu.linkonce.armextab.*)
    . = ALIGN(4);
  } >FLASH

  .ARM : {
    . = ALIGN(4);
    __exidx_start = .;
    *(.ARM.exidx*)
    __exidx_end = .;
    . = ALIGN(4);
  } >FLASH

  .preinit_array     :
  {
    . = ALIGN(4);
    PROVIDE_HIDDEN (__preinit_array_start = .);
    KEEP (*(.preinit_array*))
    PROVIDE_HIDDEN (__preinit_array_end = .);
    . = ALIGN(4);
  } >FLASH

  .init_array :
  {
    . = ALIGN(4);
    PROVIDE_HIDDEN (__init_array_start = .);
    KEEP (*(SORT(.init_array.*)))
    KEEP (*(.init_array*))
    PROVIDE_HIDDEN (__init_array_end = .);
    . = ALIGN(4);
  } >FLASH

  .fini_array :
  {
    . = ALIGN(4);
    PROVIDE_HIDDEN (__fini_array_start = .);
    KEEP (*(SORT(.fini_array.*)))
    KEEP (*(.fini_array*))
    PROVIDE_HIDDEN (__fini_array_end = .);
    . = ALIGN(4);
  } >FLASH

  _sidata = LOADADDR(.data);

  .data :
  {
    . = ALIGN(4);
    _sdata = .;
    *(.data)
    *(.data*)
    *(.RamFunc)
    *(.RamFunc*)

    . = ALIGN(4);
    _edata = .;

  } >RAM AT> FLASH

  . = ALIGN(4);
  .bss :
  {
    _sbss = .;
    __bss_start__ = _sbss;
    *(.bss)
    *(.bss*)
    *(COMMON)

    . = ALIGN(4);
    _ebss = .;
    __bss_end__ = _ebss;
  } >RAM

  ._user_heap_stack :
  {
    . = ALIGN(8);
    PROVIDE ( end = . );
    PROVIDE ( _end = . );
    . = . + _Min_Heap_Size;
    . = . + _Min_Stack_Size;
    . = ALIGN(8);
  } >RAM

  /DISCARD/ :
  {
    libc.a ( * )
    libm.a ( * )
    libgcc.a ( * )
  }

  .ARM.attributes 0 : { *(.ARM.attributes) }
}

Startup file:

.syntax unified
.cpu cortex-m0
.fpu softvfp
.thumb

.global g_pfnVectors
.global Default_Handler

.word _sidata
.word _sdata
.word _edata
.word _sbss
.word _ebss

.section .text.Reset_Handler
.weak Reset_Handler
.type Reset_Handler, %function

Reset_Handler:
    ldr   r0, =_estack
    mov   sp, r0
    ldr r0, =_sdata
    ldr r1, =_edata
    ldr r2, =_sidata
    movs r3, #0
    b LoopCopyDataInit

CopyDataInit:
    ldr r4, [r2, r3]
    str r4, [r0, r3]
    adds r3, r3, #4

LoopCopyDataInit:
    adds r4, r0, r3
    cmp r4, r1
    bcc CopyDataInit

    ldr r2, =_sbss
    ldr r4, =_ebss
    movs r3, #0
    b LoopFillZerobss

FillZerobss:
    str  r3, [r2]
    adds r2, r2, #4

LoopFillZerobss:
    cmp r2, r4
    bcc FillZerobss

    bl __libc_init_array
    bl main

LoopForever:
    b LoopForever

.size Reset_Handler, .-Reset_Handler



.section .text.Default_Handler,"ax",%progbits
Default_Handler:
Infinite_Loop:
    b Infinite_Loop
    .size Default_Handler, .-Default_Handler


.section .isr_vector,"a",%progbits
.type g_pfnVectors, %object
.size g_pfnVectors, .-g_pfnVectors

g_pfnVectors:
  .word  _estack
  .word  Reset_Handler
  .word  NMI_Handler
  .word  HardFault_Handler
  .word  0
  .word  0
  .word  0
  .word  0
  .word  0
  .word  0
  .word  0
  .word  SVC_Handler
  .word  0
  .word  0
  .word  PendSV_Handler
  .word  SysTick_Handler
  .word  WWDG_IRQHandler
  .word  0
  .word  RTC_IRQHandler
  .word  FLASH_IRQHandler
  .word  RCC_IRQHandler
  .word  EXTI0_1_IRQHandler
  .word  EXTI2_3_IRQHandler
  .word  EXTI4_15_IRQHandler
  .word  0
  .word  DMA1_Channel1_IRQHandler
  .word  DMA1_Channel2_3_IRQHandler
  .word  DMA1_Channel4_5_IRQHandler
  .word  ADC1_IRQHandler
  .word  TIM1_BRK_UP_TRG_COM_IRQHandler
  .word  TIM1_CC_IRQHandler
  .word  0
  .word  TIM3_IRQHandler
  .word  0
  .word  0
  .word  TIM14_IRQHandler
  .word  0
  .word  TIM16_IRQHandler
  .word  TIM17_IRQHandler
  .word  I2C1_IRQHandler
  .word  0
  .word  SPI1_IRQHandler
  .word  0
  .word  USART1_IRQHandler
  .word  0
  .word  0
  .word  0
  .word  0


  .weak      NMI_Handler
  .thumb_set NMI_Handler,Default_Handler

  .weak      HardFault_Handler
  .thumb_set HardFault_Handler,Default_Handler

  .weak      SVC_Handler
  .thumb_set SVC_Handler,Default_Handler

  .weak      PendSV_Handler
  .thumb_set PendSV_Handler,Default_Handler

  .weak      SysTick_Handler
  .thumb_set SysTick_Handler,Default_Handler

  .weak      WWDG_IRQHandler
  .thumb_set WWDG_IRQHandler,Default_Handler

  .weak      RTC_IRQHandler
  .thumb_set RTC_IRQHandler,Default_Handler

  .weak      FLASH_IRQHandler
  .thumb_set FLASH_IRQHandler,Default_Handler

  .weak      RCC_IRQHandler
  .thumb_set RCC_IRQHandler,Default_Handler

  .weak      EXTI0_1_IRQHandler
  .thumb_set EXTI0_1_IRQHandler,Default_Handler

  .weak      EXTI2_3_IRQHandler
  .thumb_set EXTI2_3_IRQHandler,Default_Handler

  .weak      EXTI4_15_IRQHandler
  .thumb_set EXTI4_15_IRQHandler,Default_Handler

  .weak      DMA1_Channel1_IRQHandler
  .thumb_set DMA1_Channel1_IRQHandler,Default_Handler

  .weak      DMA1_Channel2_3_IRQHandler
  .thumb_set DMA1_Channel2_3_IRQHandler,Default_Handler

  .weak      DMA1_Channel4_5_IRQHandler
  .thumb_set DMA1_Channel4_5_IRQHandler,Default_Handler

  .weak      ADC1_IRQHandler
  .thumb_set ADC1_IRQHandler,Default_Handler

  .weak      TIM1_BRK_UP_TRG_COM_IRQHandler
  .thumb_set TIM1_BRK_UP_TRG_COM_IRQHandler,Default_Handler

  .weak      TIM1_CC_IRQHandler
  .thumb_set TIM1_CC_IRQHandler,Default_Handler

  .weak      TIM3_IRQHandler
  .thumb_set TIM3_IRQHandler,Default_Handler

  .weak      TIM14_IRQHandler
  .thumb_set TIM14_IRQHandler,Default_Handler

  .weak      TIM16_IRQHandler
  .thumb_set TIM16_IRQHandler,Default_Handler

  .weak      TIM17_IRQHandler
  .thumb_set TIM17_IRQHandler,Default_Handler

  .weak      I2C1_IRQHandler
  .thumb_set I2C1_IRQHandler,Default_Handler

  .weak      SPI1_IRQHandler
  .thumb_set SPI1_IRQHandler,Default_Handler

  .weak      USART1_IRQHandler
  .thumb_set USART1_IRQHandler,Default_Handler

makefile:

all: prog

prog:
    arm-none-eabi-g++ -mcpu=cortex-m0 -c -specs=nano.specs -mfloat-abi=soft -mthumb -o startup.o startup.s
    arm-none-eabi-g++ -mcpu=cortex-m0 -c -std=c++20 -Os -ffunction-sections -fdata-sections -Wall --specs=nano.specs -mfloat-abi=soft -mthumb -o main.o main.cpp
    arm-none-eabi-g++ -mcpu=cortex-m0 -o main.elf main.o startup.o -T linker_script.ld --specs=nosys.specs --specs=nano.specs -mfloat-abi=soft -mthumb
    arm-none-eabi-objcopy -O binary main.elf main.bin

objdump:
    arm-none-eabi-objdump -h -S main.elf

size:
    arm-none-eabi-size main.elf

flash:
    st-flash write main.bin 0x08000000

reset:
    st-flash reset

clean:
    @if [ -f main.o ]; then rm main.o; fi
    @if [ -f main.s ]; then rm main.s; fi
    @if [ -f startup.o ]; then rm startup.o; fi
    @if [ -f main.elf ]; then rm main.elf; fi
    @if [ -f main.bin ]; then rm main.bin; fi

objdump output:

arm-none-eabi-objdump -h -S main.elf

main.elf:     file format elf32-littlearm

Sections:
Idx Name          Size      VMA       LMA       File off  Algn
  0 .isr_vector   000000c0  08000000  08000000  00010000  2**0
                  CONTENTS, ALLOC, LOAD, READONLY, DATA
  1 .text         00000208  080000c0  080000c0  000100c0  2**2
                  CONTENTS, ALLOC, LOAD, READONLY, CODE
  2 .rodata       0000004c  080002c8  080002c8  000102c8  2**2
                  CONTENTS, ALLOC, LOAD, READONLY, DATA
  3 .ARM.extab    00000000  08000314  08000314  00010314  2**0
                  CONTENTS, ALLOC, LOAD, READONLY, DATA
  4 .ARM          00000008  08000314  08000314  00010314  2**2
                  CONTENTS, ALLOC, LOAD, READONLY, DATA
  5 .preinit_array 00000000  0800031c  0800031c  00020068  2**0
                  CONTENTS, ALLOC, LOAD, DATA
  6 .init_array   00000008  0800031c  0800031c  0001031c  2**2
                  CONTENTS, ALLOC, LOAD, DATA
  7 .fini_array   00000004  08000324  08000324  00010324  2**2
                  CONTENTS, ALLOC, LOAD, DATA
  8 .data         00000068  20000000  08000328  00020000  2**2
                  CONTENTS, ALLOC, LOAD, DATA
  9 .bss          00000024  20000068  08000390  00020068  2**2
                  ALLOC
 10 ._user_heap_stack 00000604  2000008c  08000390  0002008c  2**0
                  ALLOC
 11 .ARM.attributes 00000028  00000000  00000000  00020068  2**0
                  CONTENTS, READONLY
 12 .comment      00000049  00000000  00000000  00020090  2**0
                  CONTENTS, READONLY
 13 .debug_frame  00000094  00000000  00000000  000200dc  2**2
                  CONTENTS, READONLY, DEBUGGING, OCTETS

Disassembly of section .text:

080000c0 <__do_global_dtors_aux>:
 80000c0:   b510        push    {r4, lr}
 80000c2:   4c06        ldr r4, [pc, #24]   ; (80000dc <__do_global_dtors_aux+0x1c>)
 80000c4:   7823        ldrb    r3, [r4, #0]
 80000c6:   2b00        cmp r3, #0
 80000c8:   d107        bne.n   80000da <__do_global_dtors_aux+0x1a>
 80000ca:   4b05        ldr r3, [pc, #20]   ; (80000e0 <__do_global_dtors_aux+0x20>)
 80000cc:   2b00        cmp r3, #0
 80000ce:   d002        beq.n   80000d6 <__do_global_dtors_aux+0x16>
 80000d0:   4804        ldr r0, [pc, #16]   ; (80000e4 <__do_global_dtors_aux+0x24>)
 80000d2:   e000        b.n 80000d6 <__do_global_dtors_aux+0x16>
 80000d4:   bf00        nop
 80000d6:   2301        movs    r3, #1
 80000d8:   7023        strb    r3, [r4, #0]
 80000da:   bd10        pop {r4, pc}
 80000dc:   20000068    .word   0x20000068
 80000e0:   00000000    .word   0x00000000
 80000e4:   080002ac    .word   0x080002ac

080000e8 <frame_dummy>:
 80000e8:   4b04        ldr r3, [pc, #16]   ; (80000fc <frame_dummy+0x14>)
 80000ea:   b510        push    {r4, lr}
 80000ec:   2b00        cmp r3, #0
 80000ee:   d003        beq.n   80000f8 <frame_dummy+0x10>
 80000f0:   4903        ldr r1, [pc, #12]   ; (8000100 <frame_dummy+0x18>)
 80000f2:   4804        ldr r0, [pc, #16]   ; (8000104 <frame_dummy+0x1c>)
 80000f4:   e000        b.n 80000f8 <frame_dummy+0x10>
 80000f6:   bf00        nop
 80000f8:   bd10        pop {r4, pc}
 80000fa:   46c0        nop         ; (mov r8, r8)
 80000fc:   00000000    .word   0x00000000
 8000100:   2000006c    .word   0x2000006c
 8000104:   080002ac    .word   0x080002ac

08000108 <_stack_init>:
 8000108:   2240        movs    r2, #64 ; 0x40
 800010a:   0292        lsls    r2, r2, #10
 800010c:   1a9a        subs    r2, r3, r2
 800010e:   4692        mov sl, r2
 8000110:   4770        bx  lr
 8000112:   46c0        nop         ; (mov r8, r8)

08000114 <_mainCRTStartup>:
 8000114:   4b17        ldr r3, [pc, #92]   ; (8000174 <_mainCRTStartup+0x60>)
 8000116:   2b00        cmp r3, #0
 8000118:   d100        bne.n   800011c <_mainCRTStartup+0x8>
 800011a:   4b13        ldr r3, [pc, #76]   ; (8000168 <_mainCRTStartup+0x54>)
 800011c:   469d        mov sp, r3
 800011e:   f7ff fff3   bl  8000108 <_stack_init>
 8000122:   2100        movs    r1, #0
 8000124:   468b        mov fp, r1
 8000126:   460f        mov r7, r1
 8000128:   4813        ldr r0, [pc, #76]   ; (8000178 <_mainCRTStartup+0x64>)
 800012a:   4a14        ldr r2, [pc, #80]   ; (800017c <_mainCRTStartup+0x68>)
 800012c:   1a12        subs    r2, r2, r0
 800012e:   f000 f8b3   bl  8000298 <memset>
 8000132:   4b0e        ldr r3, [pc, #56]   ; (800016c <_mainCRTStartup+0x58>)
 8000134:   2b00        cmp r3, #0
 8000136:   d000        beq.n   800013a <_mainCRTStartup+0x26>
 8000138:   4798        blx r3
 800013a:   4b0d        ldr r3, [pc, #52]   ; (8000170 <_mainCRTStartup+0x5c>)
 800013c:   2b00        cmp r3, #0
 800013e:   d000        beq.n   8000142 <_mainCRTStartup+0x2e>
 8000140:   4798        blx r3
 8000142:   2000        movs    r0, #0
 8000144:   2100        movs    r1, #0
 8000146:   0004        movs    r4, r0
 8000148:   000d        movs    r5, r1
 800014a:   480d        ldr r0, [pc, #52]   ; (8000180 <_mainCRTStartup+0x6c>)
 800014c:   2800        cmp r0, #0
 800014e:   d002        beq.n   8000156 <_mainCRTStartup+0x42>
 8000150:   480c        ldr r0, [pc, #48]   ; (8000184 <_mainCRTStartup+0x70>)
 8000152:   e000        b.n 8000156 <_mainCRTStartup+0x42>
 8000154:   bf00        nop
 8000156:   f000 f87b   bl  8000250 <__libc_init_array>
 800015a:   0020        movs    r0, r4
 800015c:   0029        movs    r1, r5
 800015e:   f000 f81d   bl  800019c <main>
 8000162:   f000 f85f   bl  8000224 <exit>
 8000166:   46c0        nop         ; (mov r8, r8)
 8000168:   00080000    .word   0x00080000
    ...
 8000178:   20000068    .word   0x20000068
 800017c:   2000008c    .word   0x2000008c
    ...
 8000188:   08000328    .word   0x08000328
 800018c:   20000000    .word   0x20000000
 8000190:   20000068    .word   0x20000068
 8000194:   20000068    .word   0x20000068
 8000198:   2000008c    .word   0x2000008c

0800019c <main>:
 800019c:   22c0        movs    r2, #192    ; 0xc0
 800019e:   4b04        ldr r3, [pc, #16]   ; (80001b0 <main+0x14>)
 80001a0:   6819        ldr r1, [r3, #0]
 80001a2:   680b        ldr r3, [r1, #0]
 80001a4:   4393        bics    r3, r2
 80001a6:   001a        movs    r2, r3
 80001a8:   2340        movs    r3, #64 ; 0x40
 80001aa:   4313        orrs    r3, r2
 80001ac:   600b        str r3, [r1, #0]
 80001ae:   e7fe        b.n 80001ae <main+0x12>
 80001b0:   20000088    .word   0x20000088

080001b4 <_GLOBAL__sub_I_main>:
 80001b4:   2201        movs    r2, #1
 80001b6:   4b05        ldr r3, [pc, #20]   ; (80001cc <_GLOBAL__sub_I_main+0x18>)
 80001b8:   6819        ldr r1, [r3, #0]
 80001ba:   4211        tst r1, r2
 80001bc:   d104        bne.n   80001c8 <_GLOBAL__sub_I_main+0x14>
 80001be:   601a        str r2, [r3, #0]
 80001c0:   2290        movs    r2, #144    ; 0x90
 80001c2:   4b03        ldr r3, [pc, #12]   ; (80001d0 <_GLOBAL__sub_I_main+0x1c>)
 80001c4:   05d2        lsls    r2, r2, #23
 80001c6:   601a        str r2, [r3, #0]
 80001c8:   4770        bx  lr
 80001ca:   46c0        nop         ; (mov r8, r8)
 80001cc:   20000084    .word   0x20000084
 80001d0:   20000088    .word   0x20000088

080001d4 <Reset_Handler>:
 80001d4:   480c        ldr r0, [pc, #48]   ; (8000208 <LoopForever+0x2>)
 80001d6:   4685        mov sp, r0
 80001d8:   480c        ldr r0, [pc, #48]   ; (800020c <LoopForever+0x6>)
 80001da:   490d        ldr r1, [pc, #52]   ; (8000210 <LoopForever+0xa>)
 80001dc:   4a0d        ldr r2, [pc, #52]   ; (8000214 <LoopForever+0xe>)
 80001de:   2300        movs    r3, #0
 80001e0:   e002        b.n 80001e8 <LoopCopyDataInit>

080001e2 <CopyDataInit>:
 80001e2:   58d4        ldr r4, [r2, r3]
 80001e4:   50c4        str r4, [r0, r3]
 80001e6:   3304        adds    r3, #4

080001e8 <LoopCopyDataInit>:
 80001e8:   18c4        adds    r4, r0, r3
 80001ea:   428c        cmp r4, r1
 80001ec:   d3f9        bcc.n   80001e2 <CopyDataInit>
 80001ee:   4a0a        ldr r2, [pc, #40]   ; (8000218 <LoopForever+0x12>)
 80001f0:   4c0a        ldr r4, [pc, #40]   ; (800021c <LoopForever+0x16>)
 80001f2:   2300        movs    r3, #0
 80001f4:   e001        b.n 80001fa <LoopFillZerobss>

080001f6 <FillZerobss>:
 80001f6:   6013        str r3, [r2, #0]
 80001f8:   3204        adds    r2, #4

080001fa <LoopFillZerobss>:
 80001fa:   42a2        cmp r2, r4
 80001fc:   d3fb        bcc.n   80001f6 <FillZerobss>
 80001fe:   f000 f827   bl  8000250 <__libc_init_array>
 8000202:   f7ff ffcb   bl  800019c <main>

08000206 <LoopForever>:
 8000206:   e7fe        b.n 8000206 <LoopForever>
 8000208:   20001000    .word   0x20001000
 800020c:   20000000    .word   0x20000000
 8000210:   20000068    .word   0x20000068
 8000214:   08000328    .word   0x08000328
 8000218:   20000068    .word   0x20000068
 800021c:   2000008c    .word   0x2000008c

08000220 <ADC1_IRQHandler>:
 8000220:   e7fe        b.n 8000220 <ADC1_IRQHandler>
    ...

08000224 <exit>:
 8000224:   4b08        ldr r3, [pc, #32]   ; (8000248 <exit+0x24>)
 8000226:   b510        push    {r4, lr}
 8000228:   0004        movs    r4, r0
 800022a:   2b00        cmp r3, #0
 800022c:   d002        beq.n   8000234 <exit+0x10>
 800022e:   2100        movs    r1, #0
 8000230:   e000        b.n 8000234 <exit+0x10>
 8000232:   bf00        nop
 8000234:   4b05        ldr r3, [pc, #20]   ; (800024c <exit+0x28>)
 8000236:   6818        ldr r0, [r3, #0]
 8000238:   6a83        ldr r3, [r0, #40]   ; 0x28
 800023a:   2b00        cmp r3, #0
 800023c:   d000        beq.n   8000240 <exit+0x1c>
 800023e:   4798        blx r3
 8000240:   0020        movs    r0, r4
 8000242:   f000 f831   bl  80002a8 <_exit>
 8000246:   46c0        nop         ; (mov r8, r8)
 8000248:   00000000    .word   0x00000000
 800024c:   08000310    .word   0x08000310

08000250 <__libc_init_array>:
 8000250:   b570        push    {r4, r5, r6, lr}
 8000252:   2600        movs    r6, #0
 8000254:   4d0c        ldr r5, [pc, #48]   ; (8000288 <__libc_init_array+0x38>)
 8000256:   4c0d        ldr r4, [pc, #52]   ; (800028c <__libc_init_array+0x3c>)
 8000258:   1b64        subs    r4, r4, r5
 800025a:   10a4        asrs    r4, r4, #2
 800025c:   42a6        cmp r6, r4
 800025e:   d109        bne.n   8000274 <__libc_init_array+0x24>
 8000260:   2600        movs    r6, #0
 8000262:   f000 f825   bl  80002b0 <_init>
 8000266:   4d0a        ldr r5, [pc, #40]   ; (8000290 <__libc_init_array+0x40>)
 8000268:   4c0a        ldr r4, [pc, #40]   ; (8000294 <__libc_init_array+0x44>)
 800026a:   1b64        subs    r4, r4, r5
 800026c:   10a4        asrs    r4, r4, #2
 800026e:   42a6        cmp r6, r4
 8000270:   d105        bne.n   800027e <__libc_init_array+0x2e>
 8000272:   bd70        pop {r4, r5, r6, pc}
 8000274:   00b3        lsls    r3, r6, #2
 8000276:   58eb        ldr r3, [r5, r3]
 8000278:   4798        blx r3
 800027a:   3601        adds    r6, #1
 800027c:   e7ee        b.n 800025c <__libc_init_array+0xc>
 800027e:   00b3        lsls    r3, r6, #2
 8000280:   58eb        ldr r3, [r5, r3]
 8000282:   4798        blx r3
 8000284:   3601        adds    r6, #1
 8000286:   e7f2        b.n 800026e <__libc_init_array+0x1e>
 8000288:   0800031c    .word   0x0800031c
 800028c:   0800031c    .word   0x0800031c
 8000290:   0800031c    .word   0x0800031c
 8000294:   08000324    .word   0x08000324

08000298 <memset>:
 8000298:   0003        movs    r3, r0
 800029a:   1882        adds    r2, r0, r2
 800029c:   4293        cmp r3, r2
 800029e:   d100        bne.n   80002a2 <memset+0xa>
 80002a0:   4770        bx  lr
 80002a2:   7019        strb    r1, [r3, #0]
 80002a4:   3301        adds    r3, #1
 80002a6:   e7f9        b.n 800029c <memset+0x4>

080002a8 <_exit>:
 80002a8:   e7fe        b.n 80002a8 <_exit>
 80002aa:   46c0        nop         ; (mov r8, r8)

080002ac <__EH_FRAME_BEGIN__>:
 80002ac:   0000 0000                                   ....

080002b0 <_init>:
 80002b0:   b5f8        push    {r3, r4, r5, r6, r7, lr}
 80002b2:   46c0        nop         ; (mov r8, r8)
 80002b4:   bcf8        pop {r3, r4, r5, r6, r7}
 80002b6:   bc08        pop {r3}
 80002b8:   469e        mov lr, r3
 80002ba:   4770        bx  lr

080002bc <_fini>:
 80002bc:   b5f8        push    {r3, r4, r5, r6, r7, lr}
 80002be:   46c0        nop         ; (mov r8, r8)
 80002c0:   bcf8        pop {r3, r4, r5, r6, r7}
 80002c2:   bc08        pop {r3}
 80002c4:   469e        mov lr, r3
 80002c6:   4770        bx  lr

Solution

  • These two instructions construct the value 0x48000000 (in r2):

    80001c0:   2290        movs    r2, #144    ; 0x90
    ...
    80001c4:   05d2        lsls    r2, r2, #23
    

    This shifts the value 0x90 left by 23 bits. You can check that this results in 0x48000000 with a small C example program:

    #include <stdio.h>
    #include <stdint.h>
    
    int main(void)
    {
      uint32_t v = 0x90u;
    
      v <<= 23;
    
      printf("%x\n", v);
      return 0;
    }
    

    Output:

    48000000