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

如何用GCC将C/C++代码编译为无冗余函数的PowerPC原始汇编

Alright, let's work through your problem step by step. You're trying to compile a small C++ snippet into clean, standalone PowerPC assembly (no helper functions, standard library baggage, or ELF headers) with perform_write as the entry point, but you're stuck with redundant inline function code, AT&T-style % prefixes, and extra cruft. Here's how to fix this without post-processing:

1. Force Inlining & Eliminate Redundant Code

The __attribute__((always_inline)) alone might not work if you're missing key optimizations or haven't restricted the function's scope. Here's the adjusted source code to guarantee inlining:

// Mark as static + always_inline to ensure GCC sees it as only usable in this translation unit
static inline __attribute__((always_inline)) auto get_address() {
    const auto value = *(int *) 0x1234; // Read from 0x1234
    return reinterpret_cast<int *>(value); // Cast to pointer
}

void perform_write() {
    const auto address = get_address();
    *address = 1; // Write 1 to the resolved address
}

Pair this with aggressive optimizations to strip out all unused code:

  • -O3: Enables highest optimization level, which aggressively inlines and eliminates dead code
  • -ffreestanding: Tells GCC we're not targeting a standard OS environment (disables standard library dependencies)
  • -fno-builtin: Prevents GCC from replacing your code with built-in helper functions
  • -fno-exceptions -fno-rtti: Disables C++ exception handling and RTTI (since you don't need them here)

2. Ditch AT&T-Style % Prefixes

GCC defaults to AT&T syntax for PowerPC, which adds % before register names. To switch to the cleaner register naming you want (e.g., r9 instead of %r9), add this compile option:

  • -masm=intel: Forces GCC to output Intel-style assembly for PowerPC, which omits the % prefix on registers

3. Generate Clean Assembly (No ELF Headers)

To output pure assembly code (not a compiled object file), use the -S flag. Combine all the above options, and your full GCC command (or Compiler Explorer settings) will look like this:

powerpc-linux-gnu-g++ -O3 -ffreestanding -fno-builtin -fno-exceptions -fno-rtti -masm=intel -S your_code.cpp

What You'll Get

The resulting .s file will contain only the perform_write entry point with no redundant get_address code, like this:

perform_write:
        li r9, 4660        ; Load 0x1234 (4660 in decimal) into r9
        lwz r9, 0(r9)      ; Read the value at address 0x1234 into r9
        li r0, 1           ; Load immediate value 1 into r0
        stw r0, 0(r9)      ; Write 1 to the address stored in r9
        blr                ; Return from function

Bonus: Generate Raw Binary (No ELF Headers)

If you want raw machine code instead of assembly, compile to an object file first, then strip all ELF headers with objcopy:

# Compile to object file
powerpc-linux-gnu-g++ -O3 -ffreestanding -fno-builtin -fno-exceptions -fno-rtti -c your_code.cpp -o output.o
# Extract raw binary
powerpc-linux-gnu-objcopy -O binary output.o output.bin

This output.bin will be pure PowerPC machine code starting with the perform_write instructions, no extra headers or cruft.

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.14 08:20:42