FindCMSIS.cmake 7.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190
  1. if(NOT CMSIS_FIND_COMPONENTS)
  2. set(CMSIS_FIND_COMPONENTS
  3. STM32F0 STM32F1 STM32F2 STM32F3 STM32F4 STM32F7
  4. STM32G0 STM32G4
  5. STM32H7_M7 STM32H7_M4
  6. STM32L0 STM32L1 STM32L4
  7. )
  8. endif()
  9. if(STM32H7 IN_LIST CMSIS_FIND_COMPONENTS)
  10. list(REMOVE_ITEM CMSIS_FIND_COMPONENTS STM32H7)
  11. list(APPEND CMSIS_FIND_COMPONENTS STM32H7_M7 STM32H7_M4)
  12. endif()
  13. list(REMOVE_DUPLICATES CMSIS_FIND_COMPONENTS)
  14. include(stm32/devices)
  15. function(cmsis_generate_default_linker_script FAMILY DEVICE CORE)
  16. if(CORE)
  17. set(CORE_C "::${CORE}")
  18. set(CORE_U "_${CORE}")
  19. endif()
  20. set(OUTPUT_LD_FILE "${CMAKE_CURRENT_BINARY_DIR}/${DEVICE}${CORE_U}.ld")
  21. stm32_get_memory_info(FAMILY ${FAMILY} DEVICE ${DEVICE} CORE ${CORE} FLASH SIZE FLASH_SIZE ORIGIN FLASH_ORIGIN)
  22. stm32_get_memory_info(FAMILY ${FAMILY} DEVICE ${DEVICE} CORE ${CORE} RAM SIZE RAM_SIZE ORIGIN RAM_ORIGIN)
  23. stm32_get_memory_info(FAMILY ${FAMILY} DEVICE ${DEVICE} CORE ${CORE} CCRAM SIZE CCRAM_SIZE ORIGIN CCRAM_ORIGIN)
  24. stm32_get_memory_info(FAMILY ${FAMILY} DEVICE ${DEVICE} CORE ${CORE} HEAP SIZE HEAP_SIZE)
  25. stm32_get_memory_info(FAMILY ${FAMILY} DEVICE ${DEVICE} CORE ${CORE} STACK SIZE STACK_SIZE)
  26. add_custom_command(OUTPUT "${OUTPUT_LD_FILE}"
  27. COMMAND ${CMAKE_COMMAND}
  28. -DFLASH_ORIGIN="${FLASH_ORIGIN}"
  29. -DRAM_ORIGIN="${RAM_ORIGIN}"
  30. -DCCRAM_ORIGIN="${CCRAM_ORIGIN}"
  31. -DFLASH_SIZE="${FLASH_SIZE}"
  32. -DRAM_SIZE="${RAM_SIZE}"
  33. -DCCRAM_SIZE="${CCRAM_SIZE}"
  34. -DSTACK_SIZE="${STACK_SIZE}"
  35. -DHEAP_SIZE="${HEAP_SIZE}"
  36. -DLINKER_SCRIPT="${OUTPUT_LD_FILE}"
  37. -P "${STM32_CMAKE_DIR}/stm32/linker_ld.cmake"
  38. )
  39. add_custom_target(CMSIS_LD_${DEVICE}${CORE_U} DEPENDS "${OUTPUT_LD_FILE}")
  40. add_dependencies(CMSIS::STM32::${DEVICE}${CORE_C} CMSIS_LD_${DEVICE}${CORE_U})
  41. stm32_add_linker_script(CMSIS::STM32::${DEVICE}${CORE_C} INTERFACE "${OUTPUT_LD_FILE}")
  42. endfunction()
  43. foreach(COMP ${CMSIS_FIND_COMPONENTS})
  44. string(TOLOWER ${COMP} COMP_L)
  45. string(TOUPPER ${COMP} COMP)
  46. string(REGEX MATCH "^STM32([A-Z][0-9])([0-9A-Z][0-9][A-Z][0-9A-Z])?_?(M[47])?.*$" COMP ${COMP})
  47. if((NOT CMAKE_MATCH_1) AND (NOT CMAKE_MATCH_2))
  48. message(FATAL_ERROR "Unknown CMSIS component: ${COMP}")
  49. endif()
  50. if(CMAKE_MATCH_2)
  51. set(FAMILY ${CMAKE_MATCH_1})
  52. set(DEVICES "${CMAKE_MATCH_1}${CMAKE_MATCH_2}")
  53. else()
  54. set(FAMILY ${CMAKE_MATCH_1})
  55. stm32_get_devices_by_family(DEVICES FAMILY ${FAMILY} CORE ${CORE})
  56. endif()
  57. if(CMAKE_MATCH_3)
  58. set(CORE ${CMAKE_MATCH_3})
  59. set(CORE_C "::${CORE}")
  60. set(CORE_U "_${CORE}")
  61. else()
  62. unset(CORE)
  63. unset(CORE_C)
  64. unset(CORE_U)
  65. endif()
  66. string(TOLOWER ${FAMILY} FAMILY_L)
  67. if((NOT STM32_CMSIS_${FAMILY}_PATH) AND (NOT STM32_CUBE_${FAMILY}_PATH))
  68. set(STM32_CUBE_${FAMILY}_PATH /opt/STM32Cube${FAMILY} CACHE PATH "Path to STM32Cube${FAMILY}")
  69. message(STATUS "Neither STM32_CUBE_${FAMILY}_PATH nor STM32_CMSIS_${FAMILY}_PATH specified using default STM32_CUBE_${FAMILY}_PATH: ${STM32_CUBE_${FAMILY}_PATH}")
  70. endif()
  71. find_path(CMSIS_${FAMILY}${CORE_U}_CORE_PATH
  72. NAMES Include/cmsis_gcc.h
  73. PATHS "${STM32_CMSIS_PATH}" "${STM32_CUBE_${FAMILY}_PATH}/Drivers/CMSIS"
  74. NO_DEFAULT_PATH
  75. )
  76. if (NOT CMSIS_${FAMILY}${CORE_U}_CORE_PATH)
  77. continue()
  78. endif()
  79. find_path(CMSIS_${FAMILY}${CORE_U}_PATH
  80. NAMES Include/stm32${FAMILY_L}xx.h
  81. PATHS "${STM32_CMSIS_${FAMILY}_PATH}" "${STM32_CUBE_${FAMILY}_PATH}/Drivers/CMSIS/Device/ST/STM32${FAMILY}xx"
  82. NO_DEFAULT_PATH
  83. )
  84. if (NOT CMSIS_${FAMILY}${CORE_U}_PATH)
  85. continue()
  86. endif()
  87. list(APPEND CMSIS_INCLUDE_DIRS "${CMSIS_${FAMILY}${CORE_U}_CORE_PATH}/Include" "${CMSIS_${FAMILY}${CORE_U}_PATH}/Include")
  88. if(NOT CMSIS_${FAMILY}${CORE_U}_VERSION)
  89. find_file(CMSIS_${FAMILY}${CORE_U}_PDSC
  90. NAMES ARM.CMSIS.pdsc
  91. PATHS "${CMSIS_${FAMILY}${CORE_U}_CORE_PATH}"
  92. NO_DEFAULT_PATH
  93. )
  94. if (NOT CMSIS_${FAMILY}${CORE_U}_PDSC)
  95. set(CMSIS_${FAMILY}${CORE_U}_VERSION "0.0.0")
  96. else()
  97. file(STRINGS "${CMSIS_${FAMILY}${CORE_U}_PDSC}" VERSION_STRINGS REGEX "<release version=\"([0-9]*\\.[0-9]*\\.[0-9]*)\" date=\"[0-9]+\\-[0-9]+\\-[0-9]+\">")
  98. list(GET VERSION_STRINGS 0 STR)
  99. string(REGEX MATCH "<release version=\"([0-9]*)\\.([0-9]*)\\.([0-9]*)\" date=\"[0-9]+\\-[0-9]+\\-[0-9]+\">" MATCHED ${STR})
  100. set(CMSIS_${FAMILY}${CORE_U}_VERSION "${CMAKE_MATCH_1}.${CMAKE_MATCH_2}.${CMAKE_MATCH_3}" CACHE INTERNAL "CMSIS STM32${FAMILY}${CORE_U} version")
  101. endif()
  102. endif()
  103. set(CMSIS_${COMP}_VERSION ${CMSIS_${FAMILY}${CORE_U}_VERSION})
  104. set(CMSIS_VERSION ${CMSIS_${COMP}_VERSION})
  105. find_file(CMSIS_${FAMILY}${CORE_U}_SOURCE
  106. NAMES system_stm32${FAMILY_L}xx.c
  107. PATHS "${CMSIS_${FAMILY}${CORE_U}_PATH}/Source/Templates"
  108. NO_DEFAULT_PATH
  109. )
  110. list(APPEND CMSIS_SOURCES "${CMSIS_${FAMILY}${CORE_U}_SOURCE}")
  111. if (NOT CMSIS_${FAMILY}${CORE_U}_SOURCE)
  112. continue()
  113. endif()
  114. if(NOT (TARGET CMSIS::STM32::${FAMILY}${CORE_C}))
  115. add_library(CMSIS::STM32::${FAMILY}${CORE_C} INTERFACE IMPORTED)
  116. target_link_libraries(CMSIS::STM32::${FAMILY}${CORE_C} INTERFACE STM32::${FAMILY}${CORE_C})
  117. target_include_directories(CMSIS::STM32::${FAMILY}${CORE_C} INTERFACE "${CMSIS_${FAMILY}${CORE_U}_CORE_PATH}/Include")
  118. target_include_directories(CMSIS::STM32::${FAMILY}${CORE_C} INTERFACE "${CMSIS_${FAMILY}${CORE_U}_PATH}/Include")
  119. target_sources(CMSIS::STM32::${FAMILY}${CORE_C} INTERFACE "${CMSIS_${FAMILY}${CORE_U}_SOURCE}")
  120. endif()
  121. set(DEVICES_FOUND TRUE)
  122. foreach(DEVICE ${DEVICES})
  123. stm32_get_cores(DEV_CORES FAMILY ${FAMILY} DEVICE ${DEVICE})
  124. if(CORE AND (NOT ${CORE} IN_LIST DEV_CORES))
  125. continue()
  126. endif()
  127. stm32_get_chip_type(${FAMILY} ${DEVICE} TYPE)
  128. string(TOLOWER ${DEVICE} DEVICE_L)
  129. string(TOLOWER ${TYPE} TYPE_L)
  130. find_file(CMSIS_${FAMILY}${CORE_U}_${TYPE}_STARTUP
  131. NAMES startup_stm32${TYPE_L}.s
  132. PATHS "${CMSIS_${FAMILY}${CORE_U}_PATH}/Source/Templates/gcc"
  133. NO_DEFAULT_PATH
  134. )
  135. list(APPEND CMSIS_SOURCES "${CMSIS_${FAMILY}${CORE_U}_${TYPE}_STARTUP}")
  136. if(NOT CMSIS_${FAMILY}${CORE_U}_${TYPE}_STARTUP)
  137. set(DEVICES_FOUND FALSE)
  138. break()
  139. endif()
  140. if(NOT (TARGET CMSIS::STM32::${TYPE}${CORE_C}))
  141. add_library(CMSIS::STM32::${TYPE}${CORE_C} INTERFACE IMPORTED)
  142. target_link_libraries(CMSIS::STM32::${TYPE}${CORE_C} INTERFACE CMSIS::STM32::${FAMILY}${CORE_C} STM32::${TYPE}${CORE_C})
  143. target_sources(CMSIS::STM32::${TYPE}${CORE_C} INTERFACE "${CMSIS_${FAMILY}${CORE_U}_${TYPE}_STARTUP}")
  144. endif()
  145. add_library(CMSIS::STM32::${DEVICE}${CORE_C} INTERFACE IMPORTED)
  146. target_link_libraries(CMSIS::STM32::${DEVICE}${CORE_C} INTERFACE CMSIS::STM32::${TYPE}${CORE_C})
  147. cmsis_generate_default_linker_script(${FAMILY} ${DEVICE} "${CORE}")
  148. endforeach()
  149. if(DEVICES_FOUND)
  150. set(CMSIS_${COMP}_FOUND TRUE)
  151. else()
  152. set(CMSIS_${COMP}_FOUND FALSE)
  153. endif()
  154. list(REMOVE_DUPLICATES CMSIS_INCLUDE_DIRS)
  155. list(REMOVE_DUPLICATES CMSIS_SOURCES)
  156. endforeach()
  157. include(FindPackageHandleStandardArgs)
  158. find_package_handle_standard_args(CMSIS
  159. REQUIRED_VARS CMSIS_INCLUDE_DIRS CMSIS_SOURCES
  160. FOUND_VAR CMSIS_FOUND
  161. VERSION_VAR CMSIS_VERSION
  162. HANDLE_COMPONENTS
  163. )