You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

基于QEMU通过GDB调试树莓派3的技术问题咨询

Troubleshooting Raspberry Pi 3 Bare-Metal Debugging with gdb-multiarch: Code Not Loading to Memory

Hey there, let’s tackle this frustrating bare-metal debugging issue you’re hitting with Raspberry Pi 3 and gdb-multiarch. I’ve seen this exact problem pop up when folks mix up Pi 3’s bootloader behavior with older Pi models, so let’s break it down step by step.

First, Understand Pi 3’s Boot Process (The Root of the Issue)

  • Raspberry Pi 3 uses the GPU to handle initial boot: it runs bootcode.bin, then start.elf, which is responsible for loading your bare-metal program into memory.
  • Critical note: Unlike older Pi models (which used 0x10000), Pi 3’s start.elf loads kernel.img (your bare-metal binary) to 0x8000 by default.
  • The 0x0 address you’re seeing initially is the GPU’s ROM, not your program’s memory. The CPU starts here because it’s in reset, but the GPU will eventually jump to your program’s entry point at 0x8000. That random jump to 0x10000? It’s likely leftover behavior from outdated config or link scripts targeting older Pis.

Your link script is pointing to the wrong memory addresses. Here’s a minimal working example tailored for Pi 3:

ENTRY(_start)  # Make sure this matches your assembly entry point label
SECTIONS {
    . = 0x8000;  # Align all sections to Pi 3's default load address
    .text : { *(.text) }  # Code section
    .data : { *(.data) }  # Initialized data
    .bss : { *(.bss) }    # Uninitialized data (zeroed at boot)
}
  • Compile with this script using -T link.ld to ensure your program is linked to the correct memory space.
  • Always generate a kernel.img binary (using objcopy)—this is the only filename the Pi’s bootloader will look for by default.

Fix 2: Proper GDB-Multiarch Setup

For QEMU Simulation (Easier Debugging)

  1. Start QEMU with Pi 3 emulation, waiting for GDB to connect:
    qemu-system-aarch64 -machine raspi3 -kernel kernel.img -s -S
    
  2. In a separate terminal, launch gdb-multiarch and connect correctly:
    gdb-multiarch kernel.elf  # Load your ELF symbols first
    (gdb) target remote localhost:1234  # Connect to QEMU's debug port
    (gdb) b *0x8000  # Set breakpoint at your program's entry point (not 0x0!)
    (gdb) c  # Continue execution—this will stop at your _start function
    
  • Why not break at 0x0? That’s GPU ROM code, not your program. You’ll just follow the GPU’s boot sequence instead of your code.
  • Ensure your debug probe is correctly mapping Pi 3’s memory space.
  • After connecting to the target, load your ELF symbols with file kernel.elf, then set a breakpoint at 0x8000 before resuming execution.
  • If you’re still seeing a jump to 0x10000, check your SD card’s config.txt for an outdated kernel_address=0x10000 line—remove it or set it to 0x8000.

Verify Your Program Is Loaded

To confirm your code is in memory, use GDB’s memory inspection command:

(gdb) x/16x 0x8000  # Dump 16 bytes at the load address
  • If you see your program’s machine code (match it to your assembly _start function), it’s loaded correctly. If you see all zeros or garbage, double-check:
    • Is kernel.img in the SD card’s FAT32 boot partition?
    • Did you compile with the correct link script?
    • Is your config.txt overriding the default load address?

If You Really Need 0x10000

If you have a specific reason to use 0x10000 instead of 0x8000:

  1. Update your link script to set . = 0x10000;
  2. Add kernel_address=0x10000 to your SD card’s config.txt
  3. Set your GDB breakpoint at 0x10000 instead of 0x8000

内容的提问来源于stack exchange,提问作者Flayneorange

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.21 08:28:32