【问题标题】:CMake: Embed ELF into executableCMake:将 ELF 嵌入到可执行文件中
【发布时间】:2014-05-24 21:34:44
【问题描述】:

我有一个项目需要访问嵌入到 special section 中的可执行文件中的 ELF 文件。

我之前在手工制作 Makefile,只是有一个 shell 脚本,我在其中使用 objcopy 将要嵌入的目标复制到 .o 文件中,然后在可执行文件中链接到该文件。

# Create a new section and copy the binary there ($1=input $2=output name)
objcopy --input-target binary --output-target elf64-x86-64 \
        --binary-architecture i386 $1 $2.o

现在我想摆脱自定义 Makefile 并使用 CMake 生成它们。但是,我看不到链接到此类文件的简单方法。我可以创建和添加这个文件,但不能链接它:

# Invoke script to package module as a library
add_custom_command(OUTPUT ${PACKAGED_FILE}
  COMMAND ./package.sh ${MODULE_FILE} ${PACKAGED_FILE}
  WORKING_DIRECTORY ${MODULE_DIR}
  DEPENDS ${MODULE_FILE}
  COMMENT packaging file into ELF object
  VERBATIM
)

add_custom_target(${PACKAGED_NAME} ALL DEPENDS ${PACKAGED_FILE})

我尝试添加:

target_link_libraries(binary ${PROJECT_BINARY_DIR}/${PACKAGED_FILE})

但是,这会失败,因为该文件尚不存在。会的,但 CMake 不知道。将目标名称添加为链接库也无济于事,因为找不到它。将其添加为依赖项也无济于事。有谁知道如何做到这一点?

【问题讨论】:

  • 您是否尝试过使用带有此签名的 add_custom_command:add_custom_command(TARGET binary PRE_LINK [your command here as usual]),它应该在链接之前立即调用您的命令(如果我理解 add_custom_command 的话)。

标签: c++ c makefile cmake elf


【解决方案1】:

你可以试试

add_custom_command(TARGET $(PROJECT_NAME).elf
    POST_BUILD
    COMMAND ${CMAKE_OBJCOPY} ARGS -O binary ${PROJECT_NAME}.elf \ 
${PROJECT_NAME}.bin)

把这个放在你的add_executable()之后。 POST_BUILD 表示构建后执行。

【讨论】:

    【解决方案2】:

    我们正在我们的项目中做类似的事情 - 我们CMakeLists.txt 的以下部分可以解决问题:

    set(PROJECT_EMBED_OBJ_FILES "")
    set(PROJECT_EMBED_FILES "file1.elf" "file2.elf")
    foreach(FILENAME ${PROJECT_EMBED_FILES})
        get_filename_component(FILENAME_ONLY ${FILENAME} NAME)
        get_filename_component(FILEPATH_ONLY ${FILENAME} PATH)
        add_custom_command(OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/${FILENAME_ONLY}.o 
                           WORKING_DIRECTORY ${PROJECT_SOURCE_DIR}/${FILEPATH_ONLY} 
                           COMMAND ${CMAKE_OBJCOPY} 
                           ARGS -I binary -O elf64-x86-64 -B i386 ${FILENAME_ONLY} ${CMAKE_CURRENT_BINARY_DIR}/${FILENAME_ONLY}.o )
        list(APPEND PROJECT_EMBED_OBJ_FILES ${CMAKE_CURRENT_BINARY_DIR}/${FILENAME_ONLY}.o)
        message(STATUS "Objcopy'ing ${FILENAME}")
    endforeach(FILENAME)
    

    然后在调用add_executable:

    add_executable(projectname ${PROJECT_SOURCES} ${PROJECT_EMBED_OBJ_FILES})
    

    【讨论】:

      猜你喜欢
      • 2011-02-23
      • 1970-01-01
      • 1970-01-01
      • 2011-11-09
      • 1970-01-01
      • 2011-04-19
      • 2015-09-10
      相关资源
      最近更新 更多