Я пытаюсь создать и скомпилировать проект STM32 на базе ARM с помощью CMake.
CMakeLsts.txt - это следующее:
cmake_minimum_required(VERSION 3.7)
SET(CMAKE_SYSTEM_NAME Generic)
SET(CMAKE_SYSTEM_VERSION 1)
# Enable logging messages
#set(CMAKE_VERBOSE_MAKEFILE ON)
# Project name
set(PROJECT_NAME FixtureTACO)
PROJECT(${PROJECT_NAME} C CXX ASM)
SET(CMAKE_CXX_STANDARD 11)
###################### CHIP CONFIGURATION ##########################
SET(ROOT_PROJ ${CMAKE_CURRENT_SOURCE_DIR})
SET(CPU "cortex-m4")
SET(ARCH_NAME "arm")
SET(ARCH_VER "v7e-m")
SET(FAMILY "stm32f3")
SET(CHIP "STM32F303xC")
SET(ARCH "${ARCH_NAME}${ARCH_VER}")
####################################################################
# MCU Config
set(FPU "-mfpu=fpv4-sp-d16")
set(FLOAT_ABI "-mfloat-abi=hard")
# Toolchain path
set(TOOLCHAIN_PATH "")
set(ARM_LIB "/usr/lib/arm-none-eabi/lib/${ARCH}")
# Specify C, C++ and ASM compilers
SET(CMAKE_C_COMPILER ${TOOLCHAIN_PATH}arm-none-eabi-gcc)
SET(CMAKE_CXX_COMPILER ${TOOLCHAIN_PATH}arm-none-eabi-g++)
set(AS ${TOOLCHAIN_PATH}arm-none-eabi-as)
set(AR ${TOOLCHAIN_PATH}arm-none-eabi-ar)
set(OBJCOPY ${TOOLCHAIN_PATH}arm-none-eabi-objcopy)
set(OBJDUMP ${TOOLCHAIN_PATH}arm-none-eabi-objdump)
set(SIZE ${TOOLCHAIN_PATH}arm-none-eabi-size)
set(GDB ${TOOLCHAIN_PATH}arm-none-eabi-gdb)
set(SIZE ${TOOLCHAIN_PATH}arm-none-eabi-size)
# Definitions passed at compile time (#defines)
add_definitions(-DFAMILY=${FAMILY})
add_definitions(-DCHIP=${CHIP})
add_definitions(-D${CHIP})
add_definitions(-DUSE_FULL_LL_DRIVER)
add_definitions(-USE_HAL_DRIVER)
add_definitions(-DHSE_VALUE=8000000)
add_definitions(-DHSE_STARTUP_TIMEOUT=100)
add_definitions(-DLSE_STARTUP_TIMEOUT=5000)
add_definitions(-DLSE_VALUE=32768)
add_definitions(-DHSI_VALUE=8000000)
add_definitions(-DLSI_VALUE=40000)
add_definitions(-DDD_VALUE=3300)
add_definitions(-DPREFETCH_ENABLE=1)
# Compilation flags
add_compile_options(-mcpu=${CPU})
add_compile_options(-march=${ARCH})
add_compile_options(-mthumb)
add_compile_options(${FPU})
add_compile_options(${FLOAT_ABI})
add_compile_options(-Og)
add_compile_options(-Wall)
add_compile_options(-fdata-sections)
add_compile_options(-ffunction-sections)
# Only for debugging
add_compile_options(-g -gdwarf-2)
# Linker script path
file(GLOB_RECURSE LINKER_SCRIPT ${ROOT_PROJ}/platforms/${FAMILY}/Linker/*.ld)
# Variables initialized first time
SET(CMAKE_CXX_FLAGS_INIT "-std=c++11")
SET(CMAKE_C_FLAGS_INIT "-std=gnu99")
################################## Source code ###############################################################
# Retrieve all sources # "platforms/${FAMILY}/Startup/*.s"
file(GLOB SOURCES "platforms/${FAMILY}/Startup/*.s" "src/*.cpp" "src/*.c" "platforms/${FAMILY}/Hal/src/*.c" "platforms/${FAMILY}/Device/*.c")
#Retrieve all locations of headers
file(GLOB_RECURSE HEADERS "includes/*.h" "src/*.h" "platforms/${FAMILY}*.h")
set (INCLUDE_DIRS "")
foreach (_headerFile ${HEADERS})
get_filename_component(_dir ${_headerFile} PATH)
list (APPEND INCLUDE_DIRS ${_dir})
endforeach()
list(REMOVE_DUPLICATES INCLUDE_DIRS)
include_directories(${INCLUDE_DIRS})
link_directories(${ARM_LIB})
################################## Source code END ###########################################################
set(EXE_NAME "${PROJECT_NAME}_${CHIP}")
add_executable(${EXE_NAME}.elf ${SOURCES} ${LINKER_SCRIPT})
set(CMAKE_EXE_LINKER_FLAGS "-mcpu=${CPU} -mthumb ${FPU} ${FLOAT_ABI} --specs=nano.specs -T${LINKER_SCRIPT} -Wl,-Map=${PROJECT_BINARY_DIR}/${PROJECT_NAME}.map,--cref -Wl,--gc-sections")
# Libs and external dependencies
target_link_libraries(${EXE_NAME}.elf -lc -lm -lnosys)
# Outputs
set(ELF_FILE ${PROJECT_BINARY_DIR}/${EXE_NAME}.elf)
set(HEX_FILE ${PROJECT_BINARY_DIR}/${EXE_NAME}.hex)
set(BIN_FILE ${PROJECT_BINARY_DIR}/${EXE_NAME}.bin)
add_custom_command(TARGET "${EXE_NAME}.elf" POST_BUILD
# Build .hex and .bin files
COMMAND ${OBJCOPY} -Obinary ${ELF_FILE} ${BIN_FILE}
COMMAND ${OBJCOPY} -Oihex ${ELF_FILE} ${HEX_FILE}
COMMENT "Building ${PROJECT_NAME}.bin and ${PROJECT_NAME}.hex"
# Copy files to a custom build directory
COMMAND ${CMAKE_COMMAND} -E copy ${ELF_FILE} "${ROOT_PROJ}/builds/${CHIP}/${EXE_NAME}.elf"
COMMAND ${CMAKE_COMMAND} -E copy ${HEX_FILE} "${ROOT_PROJ}/builds/${CHIP}/${EXE_NAME}.hex"
COMMAND ${CMAKE_COMMAND} -E copy ${BIN_FILE} "${ROOT_PROJ}/builds/${CHIP}/${EXE_NAME}.bin"
# Display sizes
COMMAND ${SIZE} --format=berkeley ${EXE_NAME}.elf ${EXE_NAME}.hex
COMMENT "Invoking: Cross ARM GNU Print Size"
)
add_custom_target(UPLOAD
${GDB} -iex "target remote tcp:127.0.0.1:3333"
-iex "monitor program ${EXE_NAME}.elf"
-iex "monitor reset init"
-iex "disconnect" -iex "quit ")
Когда я пытаюсь скомпилировать, я получаю следующие ошибки:
[ 82%] Building C object CMakeFiles/FixtureTACO_STM32F303xC.elf.dir/platforms/stm32f3/Hal/src/stm32f3xx_ll_utils.c.obj
[ 86%] Building ASM object CMakeFiles/FixtureTACO_STM32F303xC.elf.dir/platforms/stm32f3/Startup/startup_stm32f303xc.s.obj
cc: warning: ‘-mcpu=’ is deprecated; use ‘-mtune=’ or ‘-march=’ instead
cc: error: unrecognized command line option ‘-mthumb’; did you mean ‘-mtbm’?
cc: error: unrecognized command line option ‘-mfpu=fpv4-sp-d16’
cc: error: unrecognized command line option ‘-mfloat-abi=hard’
Ошибка возникает ТОЛЬКО, когда файл сборки (в данном случае startup.s) присутствует в исходных файлах и когда присутствуют флаги FPU и FLOAR_ABI. Как видите, ошибка возникает при компиляции startup_stm32f303xc.s.
Я подозреваю, что добавляю эти флаги не в том месте, но понятия не имею, куда их добавить, чтобы все заработало.
Позднее редактирование: я уже установил компилятор arm 7 в свою систему ubuntu. Я могу использовать его без указания пути, так как он уже присутствует в переменных среды. Я могу без проблем скомпилировать код ARM (из Makefiles) для других целей на машине. Моя проблема с cmake.
@Fred Я думаю, это как раз моя проблема. Не могли бы вы дать мне более подробную информацию?





Думаю, вы попробуете скомпилировать код для ARM с помощью компилятора x86. Она не будет работать. Вам необходимо загрузить набор инструментов ARM и использовать правильный компилятор.
-mcpu не используется в ветке x86, но не в ветке ARM.
других вариантов просто нет в компиляторе x86.
Да! Это была проблема. Только компилятор ASM был опущен, остальные были в порядке.
@caffeine отличный. Но сообщение было на самом деле очевидным.
В вашей строке set(TOOLCHAIN_PATH "") вы должны добавить путь к компилятору. Сначала получите бесплатный GCC ARM ToolChain. Загрузите для своей ОС. а затем просто скопируйте в свое любимое место. Если вы используете Linux, вы можете использовать мои конфигурации пути:
1.) Скопируйте gcc arm compirel в каталог / opt /:
sudo tar xjfv ~/Downloads/gcc-arm-none-eabi-7-2018-q2-update-linux.tar.bz2 -C /opt/
Для более «сексуального» пути можно сделать символическую ссылку:
sudo ln -s /opt/gcc-arm-none-eabi-7-2018-q2-update/ /opt/gcc-arm-none-eabi
После этого перейдите в свой CMakeLists.txt и перепишите команду set следующим образом:
set(TOOLCHAIN_PATH "/opt/gcc-arm-none-eabi/bin")
Но есть лучшее решение для создания вашего проекта для STM32, но с уже готовым проектом шаблона stm32-cmake, специально созданным для семейства STM32. Это намного легче сделать, если что-то работает. Вам также потребуются два предварительных требования: STM32CubeMX и снова GCC ARM ToolChain. Если вы хотите узнать, как использовать этот шаблон, просто напишите мне, и я дам вам краткое руководство.
Вы не «устанавливаете» инструментальную цепочку, вы просто копируете файлы в один каталог. Если у вас уже есть файлы toolchian, добавьте путь в свой код, добавьте set(TOOLCHAIN_PATH "path/to/your/toolchain/bin")
Хорошо, наконец-то я разобрался!
Мне пришлось заменить
set(AS ${TOOLCHAIN_PATH}arm-none-eabi-as)
с участием
set(CMAKE_ASM_COMPILER ${TOOLCHAIN_PATH}arm-none-eabi-gcc)
Это не ошибка, это компилятор gcc. Вы также можете добавить эти флаги: -x assembler-with-cpp.
CMake не знал о моем пользовательском компиляторе ASM, поэтому он использовал системный компилятор ASM по умолчанию, если я не заставлю его написать CMAKE_ASM_COMPILER. Сейчас проект строится и отлично работает на микроконтроллере.
Остальные ответы были нормальными, но у них была половина решения. Только файлы ASM были скомпилированы с неправильным компилятором.
Я предполагаю, что вам нужно использовать выражения генератора и $ <COMPILE_LANGUAGE: lang> только для добавления параметров C к компилятору C и параметров ASM к компилятору ASM. По сути, вы добавляете параметры в компилятор для обоих языков, и это то, что ломается при компиляции файла ASM.