Fix doc path
[opentx.git] / radio / src / CMakeLists.txt
blob38be1e3508ee6175bc0ff64648b3642931b206fc
1 include(CMakeForceCompiler)
2 include(Bitmaps)
4 set(PCB_TYPES X7 XLITE X9D X9D+ X9E X10 X12S 9X 9XR 9X128 9XR128 9X2561 GRUVIN9X MEGA2560 SKY9X 9XRPRO AR9X)
5 set(GUI_LANGUAGES CZ DE EN ES FR IT PT SK SE PL HU NL)
6 set(TTS_LANGUAGES CZ DE EN ES FR IT PT SK SE PL HU NL RU)
8 set(PCB "X9D+" CACHE STRING "Radio type, one of: ${PCB_TYPES}")
9 set_property(CACHE PCB PROPERTY STRINGS ${PCB_TYPES})
10 set(TRANSLATIONS "EN" CACHE STRING "Radio language, one of: ${GUI_LANGUAGES}")
11 set_property(CACHE TRANSLATIONS PROPERTY STRINGS ${GUI_LANGUAGES})
12 set(SPLASH "DEFAULT" CACHE STRING "Splash (DEFAULT/OFF/FRSKY)")
13 set_property(CACHE SPLASH PROPERTY STRINGS DEFAULT OFF FRSKY)
14 set(PPM_UNIT "PERCENT_PREC1" CACHE STRING "PPM display unit (US/PERCENT_PREC1/PERCENT_PREC0)")
15 set_property(CACHE PPM_UNIT PROPERTY STRINGS US PERCENT_PREC1 PERCENT_PREC0)
16 set(DEFAULT_MODE "" CACHE STRING "Default sticks mode")
17 set(FONT "STD" CACHE STRING "Choose font : STD or SQT5")
18 set_property(CACHE FONT PROPERTY STRINGS SQT5)
20 option(HELI "Heli menu" ON)
21 option(FLIGHT_MODES "Flight Modes" ON)
22 option(CURVES "Curves" ON)
23 option(GVARS "Global variables" ON)
24 option(GUI "GUI enabled" ON)
25 option(PPM_CENTER_ADJUSTABLE "PPM center adjustable" ON)
26 option(PPM_LIMITS_SYMETRICAL "PPM limits symetrical" OFF)
27 option(OVERRIDE_CHANNEL_FUNCTION "OverrideChannel function available" ON)
28 option(DANGEROUS_MODULE_FUNCTIONS "Dangerous module functions (RangeCheck / Bind / Module OFF, etc.) available" OFF)
29 option(FAI "Competition mode (no telemetry)" OFF)
30 option(AUTOSOURCE "Automatic source detection in menus" ON)
31 option(AUTOSWITCH "Automatic switch detection in menus" ON)
32 option(SEMIHOSTING "Enable debugger semihosting" OFF)
33 option(JITTER_MEASURE "Enable ADC jitter measurement" OFF)
34 option(WATCHDOG_DISABLED "Disable hardware Watchdog" OFF)
35 if(SDL_FOUND)
36   option(SIMU_AUDIO "Enable simulator audio." ON)
37 endif()
38 option(LUA "Enable LUA support" ON)
39 option(SIMU_DISKIO "Enable disk IO simulation in simulator. Simulator will use FatFs module and simulated IO layer that  uses \"./sdcard.image\" file as image of SD card. This file must contain whole SD card from first to last sector" OFF)
40 option(SIMU_LUA_COMPILER "Pre-compile and save Lua scripts in simulator." ON)
41 option(FAS_PROTOTYPE "Support of old FAS prototypes (different resistors)" OFF)
42 option(RAS "RAS (SWR) enabled" ON)
43 option(TEMPLATES "Model templates menu" OFF)
44 option(TRACE_SIMPGMSPACE "Turn on traces in simpgmspace.cpp" ON)
45 option(TRACE_LUA_INTERNALS "Turn on traces for Lua internals" OFF)
46 option(FRSKY_STICKS "Reverse sticks for FrSky sticks" OFF)
47 option(NANO "Use nano newlib and binalloc")
48 option(NIGHTLY_BUILD_WARNING "Warn this is a nightly build" OFF)
49 option(MODULE_R9M_FLEX_FW "Add R9M options for non certified firmwwares" OFF)
51 # since we reset all default CMAKE compiler flags for firmware builds, provide an alternate way for user to specify additional flags.
52 set(FIRMWARE_C_FLAGS "" CACHE STRING "Additional flags for firmware target c compiler (note: all CMAKE_C_FLAGS[_*] are ignored for firmware/bootloader).")
53 set(FIRMWARE_C_FLAGS_DEBUG "-g" CACHE STRING "Additional flags for firmware target (Debug config) c compiler (note: CMAKE_C_FLAGS_DEBUG is ignored for firmware/bootloader).")
54 set(FIRMWARE_CXX_FLAGS "" CACHE STRING "Additional flags for firmware target c++ compiler (note: all CMAKE_CXX_FLAGS[_*] are ignored for firmware/bootloader).")
55 set(FIRMWARE_CXX_FLAGS_DEBUG "-g" CACHE STRING "Additional flags for firmware target (Debug config) c++ compiler (note: CMAKE_CXX_FLAGS_DEBUG is ignored for firmware/bootloader).")
57 set(THIRDPARTY_DIR thirdparty)
58 set(LUA_DIR ${THIRDPARTY_DIR}/Lua/src)
59 set(COOS_DIR ${THIRDPARTY_DIR}/CoOS)
60 set(FATFS_DIR ${THIRDPARTY_DIR}/FatFs)
61 set(RADIO_BIN_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR})
63 configure_file(stamp.h.in stamp.h @ONLY)
65 add_subdirectory(translations)
66 add_subdirectory(bitmaps)
67 add_subdirectory(fonts)
69 set(EEPROM_VARIANT  0)
70 set(GVARS_VARIANT   1)
71 set(FRSKY_VARIANT   2)
72 set(3POS_VARIANT    4)
73 set(MAVLINK_VARIANT 8)
74 set(M2561_VARIANT   16384)
75 set(M128_VARIANT    32768)
77 set(FIRMWARE_DEPENDENCIES firmware_translations)
79 set(FATFS_SRC
80   ${FATFS_DIR}/ff.c
81   ${FATFS_DIR}/fattime.c
82   ${FATFS_DIR}/option/ccsbcs.c
85 if(PCB STREQUAL X12S OR PCB STREQUAL X10)
86   include(targets/horus/CMakeLists.txt)
87 elseif(PCB STREQUAL X9E OR PCB STREQUAL X9D+ OR PCB STREQUAL X9D OR PCB STREQUAL X7 OR PCB STREQUAL XLITE)
88   include(targets/taranis/CMakeLists.txt)
89 elseif(PCB STREQUAL SKY9X OR PCB STREQUAL 9XRPRO OR PCB STREQUAL AR9X)
90   include(targets/sky9x/CMakeLists.txt)
91 elseif(PCB STREQUAL 9X OR PCB STREQUAL 9XR OR PCB STREQUAL 9X128 OR PCB STREQUAL 9XR128)
92   include(targets/9x/CMakeLists.txt)
93 elseif(PCB STREQUAL 9X2561)
94   set(ARCH AVR)
95   set(MCU atmega2561)
96   string(TOLOWER ${PCB} FLAVOUR)
97   set(EEPROM EEPROM_RLC)
98   set(SDCARD NO)
99   add_definitions(-DEEPROM_VARIANT=${M2561_VARIANT})
100   set(GUI_DIR 128x64)
101   set(TARGET_DIR 9x)
102   set(FIRMWARE_DEPENDENCIES ${FIRMWARE_DEPENDENCIES} 9x_bitmaps)
103   add_definitions(-DPCBSTD -DPCB${PCB} -DCPUM2561)
104   set(TARGET_SRC ${TARGET_SRC} board.cpp)
105   set(GUI_SRC
106     ${GUI_SRC}
107     model_inputs_mixes.cpp
108     radio_diagkeys.cpp
109     radio_diaganas.cpp)
110   if(SP22)
111     add_definitions(-DSP22)
112   endif()
113   if(PWM_BACKLIGHT)
114     add_definitions(-DPWM_BACKLIGHT)
115   endif()
116   set(FIRMWARE_TARGET_SRC ${FIRMWARE_TARGET_SRC} lcd_driver.cpp)
117 elseif(PCB STREQUAL GRUVIN9X)
118   include(targets/gruvin9x/CMakeLists.txt)
119 elseif(PCB STREQUAL MEGA2560)
120   include(targets/mega2560/CMakeLists.txt)
121 else()
122   message(FATAL_ERROR "Unknown PCB '${PCB}'")
123 endif()
125 if(NOT PCB STREQUAL 9XR AND NOT PCB STREQUAL 9XRPRO)
126   option(DBLKEYS "Double Keys" ON)
127   if(DBLKEYS)
128     add_definitions(-DDBLKEYS)
129   endif()
130 endif()
132 if(CPU_TYPE STREQUAL STM32F4)
133   include(targets/common/arm/stm32/f4/CMakeLists.txt)
134 endif()
136 if(CPU_TYPE STREQUAL STM32F2)
137   include(targets/common/arm/stm32/f2/CMakeLists.txt)
138 endif()
140 if(CPU_FAMILY STREQUAL STM32)
141   include(targets/common/arm/stm32/CMakeLists.txt)
142 endif()
144 if(ARCH STREQUAL ARM)
145   include(targets/common/arm/CMakeLists.txt)
146 else()
147   include(targets/common/avr/CMakeLists.txt)
148 endif()
150 include_directories(targets/${TARGET_DIR} ${THIRDPARTY_DIR})
152 foreach(LANGUAGE ${GUI_LANGUAGES})
153   if(TRANSLATIONS STREQUAL ${LANGUAGE})
154     add_definitions(-DTRANSLATIONS_${LANGUAGE} -DTRANSLATIONS="${LANGUAGE}")
155   endif()
156 endforeach()
158 set(SRC ${SRC} debug.cpp)
160 if(${EEPROM} STREQUAL SDCARD)
161   set(SRC ${SRC} storage/storage_common.cpp storage/sdcard_raw.cpp storage/modelslist.cpp)
162 elseif(${EEPROM} STREQUAL EEPROM_RLC)
163   set(SRC ${SRC} storage/storage_common.cpp storage/eeprom_common.cpp storage/eeprom_rlc.cpp)
164   add_definitions(-DEEPROM -DEEPROM_RLC)
165 else()
166   set(SRC ${SRC} storage/storage_common.cpp storage/eeprom_common.cpp storage/eeprom_raw.cpp)
167   add_definitions(-DEEPROM -DEEPROM_RAW)
168 endif()
170 if(ARCH STREQUAL ARM AND NOT PCB STREQUAL X12S AND NOT PCB STREQUAL X10 AND NOT PCB STREQUAL XLITE)
171   add_definitions(-DEEPROM_CONVERSIONS)
172   set(SRC ${SRC} storage/eeprom_conversions.cpp)
173 endif()
175 add_definitions(-DFLAVOUR="${FLAVOUR}")
177 include_directories(${CMAKE_CURRENT_SOURCE_DIR})
178 include_directories(${CMAKE_CURRENT_BINARY_DIR})
179 include_directories(${CMAKE_CURRENT_BINARY_DIR}/bitmaps/${GUI_DIR})
181 add_subdirectory(lua)
182 include(gui/CMakeLists.txt)
184 if(RAMBACKUP)
185   add_definitions(-DRAMBACKUP)
186   set(SRC ${SRC} storage/rambackup.cpp storage/rlc.cpp)
187 endif()
189 if(TEMPLATES)
190   add_definitions(-DTEMPLATES)
191   set(SRC ${SRC} templates.cpp)
192   set(GUI_SRC ${GUI_SRC} model_templates.cpp)
193 endif()
195 if(NOT LUA STREQUAL NO)
196   add_definitions(-DLUA)
197   if(LUA_COMPILER)
198     add_definitions(-DLUA_COMPILER)
199   endif()
200   if(LUA_ALLOCATOR_TRACER AND DEBUG)
201     add_definitions(-DLUA_ALLOCATOR_TRACER)
202   endif()
203   if(NOT "${LUA_SCRIPT_LOAD_MODE}" STREQUAL "")
204     add_definitions(-DLUA_SCRIPT_LOAD_MODE="${LUA_SCRIPT_LOAD_MODE}")
205   endif()
206   include_directories(${LUA_DIR})
207   set(FIRMWARE_DEPENDENCIES ${FIRMWARE_DEPENDENCIES} ${LUA_EXPORT})
208   if(LUA STREQUAL YES)
209     add_definitions(-DLUA_MODEL_SCRIPTS)
210     set(GUI_SRC ${GUI_SRC} model_custom_scripts.cpp)
211   endif()
212   set(SRC ${SRC} lua/interface.cpp lua/api_general.cpp lua/api_lcd.cpp lua/api_model.cpp)
213   if(PCB STREQUAL X12S OR PCB STREQUAL X10)
214     set(SRC ${SRC} lua/widgets.cpp)
215   endif()
216   set(LUA_SRC lapi.c lcode.c lctype.c ldebug.c ldo.c ldump.c lfunc.c lgc.c llex.c lmem.c lobject.c lopcodes.c lparser.c
217     lstate.c lstring.c ltable.c lrotable.c ltm.c lundump.c lvm.c lzio.c linit.c
218     lbaselib.c lmathlib.c lbitlib.c loadlib.c lauxlib.c ltablib.c lcorolib.c liolib.c lstrlib.c
219     )
220   foreach(FILE ${LUA_SRC})
221     set(SRC ${SRC} ${LUA_DIR}/${FILE})
222   endforeach()
223   if(MSVC)
224     # silence lots of warnings regarding "insecure" use of functions (sprintf, strcpy, etc) from Lua code
225     set(WARNING_FLAGS "${WARNING_FLAGS} /D_CRT_SECURE_NO_WARNINGS")
226   endif()
227 endif()
229 if(HELI)
230   add_definitions(-DHELI)
231 endif()
233 if(FLIGHT_MODES)
234   add_definitions(-DFLIGHT_MODES)
235   set(GUI_SRC ${GUI_SRC} model_flightmodes.cpp)
236 endif()
238 if(CURVES)
239   add_definitions(-DCURVES)
240   set(SRC ${SRC} curves.cpp)
241 endif()
243 if(GVARS)
244   add_definitions(-DGVARS)
245   set(SRC ${SRC} gvars.cpp)
246   math(EXPR EEPROM_VARIANT ${EEPROM_VARIANT}+${GVARS_VARIANT})
247 endif()
249 if(FAI STREQUAL YES)
250   add_definitions(-DFAI)
251 elseif(FAI STREQUAL CHOICE)
252   add_definitions(-DFAI_CHOICE)
253 endif()
255 if(NOT RAS)
256   add_definitions(-DNO_RAS)
257 endif()
259 if(FAS_PROTOTYPE)
260   add_definitions(-DFAS_PROTOTYPE)
261 endif()
263 if(AUTOSOURCE)
264   add_definitions(-DAUTOSOURCE)
265 endif()
267 if(AUTOSWITCH)
268   add_definitions(-DAUTOSWITCH)
269 endif()
271 if(JITTER_MEASURE)
272   add_definitions(-DJITTER_MEASURE)
273 endif()
275 if(WATCHDOG_DISABLED)
276   add_definitions(-DWATCHDOG_DISABLED)
277 endif()
279 if(SIMU_AUDIO)
280   add_definitions(-DSIMU_AUDIO)
281 endif()
283 if(SIMU_DISKIO)
284   add_definitions(-DSIMU_DISKIO)
285 endif()
287 if(SDCARD)
288   add_definitions(-DSDCARD)
289   include_directories(${FATFS_DIR} ${FATFS_DIR}/option)
290   set(SRC ${SRC} sdcard.cpp rtc.cpp logs.cpp)
291   set(FIRMWARE_SRC ${FIRMWARE_SRC} ${FATFS_SRC})
292 endif()
294 if(SHUTDOWN_CONFIRMATION)
295   add_definitions(-DSHUTDOWN_CONFIRMATION)
296 endif()
298 if(PPM_UNIT STREQUAL US)
299   add_definitions(-DPPM_UNIT_US)
300 elseif(PPM_UNIT STREQUAL PERCENT_PREC1)
301   add_definitions(-DPPM_UNIT_PERCENT_PREC1)
302 else()
303   add_definitions(-DPPM_UNIT_PERCENT_PREC0)
304 endif()
306 if(PPM_CENTER_ADJUSTABLE)
307   add_definitions(-DPPM_CENTER_ADJUSTABLE)
308 endif()
310 if(PPM_LIMITS_SYMETRICAL)
311   add_definitions(-DPPM_LIMITS_SYMETRICAL)
312 endif()
314 if(OVERRIDE_CHANNEL_FUNCTION)
315   add_definitions(-DOVERRIDE_CHANNEL_FUNCTION)
316 endif()
318 if(DANGEROUS_MODULE_FUNCTIONS)
319   add_definitions(-DDANGEROUS_MODULE_FUNCTIONS)
320 endif()
322 if(SPLASH STREQUAL FRSKY)
323   add_definitions(-DSPLASH -DSPLASH_FRSKY)
324 elseif(NOT SPLASH STREQUAL OFF)
325   add_definitions(-DSPLASH)
326 endif()
328 if(NOT DEFAULT_MODE STREQUAL "")
329   add_definitions(-DDEFAULT_MODE=${DEFAULT_MODE})
330 endif()
332 if(TRACE_SIMPGMSPACE)
333   add_definitions(-DTRACE_SIMPGMSPACE)
334 endif()
336 if(TRACE_LUA_INTERNALS)
337   add_definitions(-DTRACE_LUA_INTERNALS_ENABLED)
338 endif()
340 if(FRSKY_STICKS)
341   add_definitions(-DFRSKY_STICKS)
342 endif()
344 if(NOT FONT STREQUAL "")
345   add_definitions(-DFONT=${DEFAULT_MODE})
346 endif()
348 if(EEPROM_VARIANT_NEEDED)
349   add_definitions(-DEEPROM_VARIANT=${EEPROM_VARIANT})
350 endif()
352 if(NIGHTLY_BUILD_WARNING)
353   add_definitions(-DNIGHTLY_BUILD_WARNING)
354 endif(NIGHTLY_BUILD_WARNING)
356 if(MODULE_R9M_FLEX_FW)
357     add_definitions(-DMODULE_R9M_FLEX_FW)
358 endif()
360 set(SRC
361   ${SRC}
362   opentx.cpp
363   functions.cpp
364   strhelpers.cpp
365   switches.cpp
366   mixer.cpp
367   stamp.cpp
368   timers.cpp
369   trainer_input.cpp
370   )
372 if(GUI)
373   add_definitions(-DGUI)
374   set(SRC
375     ${SRC}
376     keys.cpp
377     maths.cpp
378     translations.cpp
379     gui/gui_common.cpp
380     )
381   foreach(FILE ${GUI_SRC})
382     set(SRC ${SRC} gui/${GUI_DIR}/${FILE})
383   endforeach()
384   if(ARCH STREQUAL ARM)
385     set(SRC
386       ${SRC}
387       gui/gui_common_arm.cpp
388       )
389   endif()
390 endif()
392 foreach(FILE ${TARGET_SRC})
393   set(SRC targets/${TARGET_DIR}/${FILE} ${SRC})
394 endforeach()
396 foreach(FILE ${FIRMWARE_TARGET_SRC})
397   set(FIRMWARE_SRC ${FIRMWARE_SRC} targets/${TARGET_DIR}/${FILE})
398 endforeach()
400 foreach(FILE ${PULSES_SRC})
401   set(SRC ${SRC} pulses/${FILE})
402 endforeach()
404 add_definitions(-DCORRECT_NEGATIVE_SHIFTS)
406 if(NOT MSVC)
407   set(WARNING_FLAGS "${WARNING_FLAGS} -Wall -Wno-strict-aliasing -Wformat -Wreturn-type -Wunused -Wuninitialized -Wunknown-pragmas -Wno-switch -Wtype-limits")
408   if(WARNINGS_AS_ERRORS)
409     set(WARNING_FLAGS "${WARNING_FLAGS} -Werror")
410   endif(WARNINGS_AS_ERRORS)
411 else()
412   add_definitions(-DHAVE_STRUCT_TIMESPEC)  # this is for pthread.h
413   if(WARNINGS_AS_ERRORS)
414     set(WARNING_FLAGS "${WARNING_FLAGS} /WX")
415   endif(WARNINGS_AS_ERRORS)
416 endif()
418 add_subdirectory(targets/simu)
419 if(NOT MSVC)
420   add_subdirectory(tests)
421 endif()
423 set(SRC ${SRC} ${FIRMWARE_SRC})
426 ##### firmware target #####
428 option(FIRMWARE_TARGET "Configure Firmware target (can be turned of for compiling Companion only)" ON)
429 if(NOT FIRMWARE_TARGET)
430   message(STATUS "firmware target disabled")
431   return()
432 endif()
434 set(CMAKE_EXECUTABLE_SUFFIX ".elf")
435 # trick to remove the -rdynamic and --out-implib issues
436 set(CMAKE_SHARED_LIBRARY_LINK_C_FLAGS "")
437 set(CMAKE_SHARED_LIBRARY_LINK_CXX_FLAGS "")
438 # similar for -mmacosx-version-min="
439 set(CMAKE_C_OSX_DEPLOYMENT_TARGET_FLAG "")
440 set(CMAKE_CXX_OSX_DEPLOYMENT_TARGET_FLAG "")
441 # reset some CMake default flags which assume optimization levels/etc
442 set(CMAKE_C_FLAGS "${FIRMWARE_C_FLAGS}")
443 set(CMAKE_C_FLAGS_DEBUG "${FIRMWARE_C_FLAGS_DEBUG}")
444 set(CMAKE_C_FLAGS_RELEASE "")
445 set(CMAKE_C_FLAGS_MINSIZEREL "")
446 set(CMAKE_C_FLAGS_RELWITHDEBINFO "")
447 set(CMAKE_CXX_FLAGS "${FIRMWARE_CXX_FLAGS}")
448 set(CMAKE_CXX_FLAGS_DEBUG "${FIRMWARE_CXX_FLAGS_DEBUG}")
449 set(CMAKE_CXX_FLAGS_RELEASE "")
450 set(CMAKE_CXX_FLAGS_MINSIZEREL "")
451 set(CMAKE_CXX_FLAGS_RELWITHDEBINFO "")
452 # customize linker command
453 set(CMAKE_EXE_LINKER_FLAGS "")
454 set(CMAKE_C_LINK_EXECUTABLE "<CMAKE_C_COMPILER> <FLAGS> <LINK_FLAGS> <OBJECTS>  -o <TARGET>")
455 set(CMAKE_CXX_LINK_EXECUTABLE "<CMAKE_CXX_COMPILER> <FLAGS> <LINK_FLAGS> <OBJECTS>  -o <TARGET>")
457 use_cxx11()  # ensure gnu++11 in CXX_FLAGS with CMake < 3.1
459 find_program(BASH bash HINTS "c:/cygwin/bin/" "c:/msys/bin/" DOC "bash shell for firmware size report (eg. c:/cygwin/bin/bash.exe on Windows).")
461 if(NOT MSVC)
462   set(OPT s)
464   if(ARCH STREQUAL ARM)
466     enable_language(ASM)
467     set(CMAKE_C_COMPILER arm-none-eabi-gcc)
468     set(CMAKE_CXX_COMPILER arm-none-eabi-g++)
469     set(CMAKE_ASM_COMPILER arm-none-eabi-as)
471     set(CMAKE_SYSTEM_NAME Generic)
472     set(CMAKE_SYSTEM_VERSION 1)
473     set(CMAKE_ASM_COMPILE_OBJECT "<CMAKE_ASM_COMPILER> -o <OBJECT> <SOURCE>")
475     set(COMMON_FLAGS "-mcpu=${MCU} -mthumb -fomit-frame-pointer -fverbose-asm -Wa,-ahlms=firmware.lst -O${OPT} -gdwarf-2 -DHSE_VALUE=${HSE_VALUE} -fno-exceptions -fdata-sections -ffunction-sections ${WARNING_FLAGS}")
476     set(COMMON_FLAGS "${COMMON_FLAGS} ${FPU_FLAGS}")
478     set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} ${COMMON_FLAGS} -Wimplicit")
479     set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${COMMON_FLAGS}")
481     # these are in addition to CMAKE_CXX_FLAGS
482     set(CMAKE_EXE_LINKER_FLAGS "-lm -T${RADIO_SRC_DIRECTORY}/${LINKER_SCRIPT} -Wl,-Map=firmware.map,--cref,--no-warn-mismatch,--gc-sections")
483     if(SEMIHOSTING)
484       add_definitions(-DSEMIHOSTING)
485       set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} --specs=rdimon.specs")
486     endif()
487     # Use newlib nano, which saves a few kilobytes.
488     if(NOT NANO STREQUAL NO)
489       set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} --specs=nano.specs")
490       if(NOT LUA STREQUAL NO)
491         # Lua needs %g and %f
492         set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} -u _printf_float -u _scanf_float")
493       endif()
494       # Nano's malloc does work well with lua, use our own
495       add_definitions(-DUSE_BIN_ALLOCATOR)
496       set(SRC ${SRC} bin_allocator.cpp)
497     endif()
500     if(PCB STREQUAL XLITE OR PCB STREQUAL X9D OR PCB STREQUAL X9D+ OR PCB STREQUAL X9E OR PCB STREQUAL X7 OR PCB STREQUAL X10 OR PCB STREQUAL X12S)
501       add_subdirectory(targets/common/arm/stm32/bootloader)
502       include_directories(${CMAKE_CURRENT_BINARY_DIR}/targets/common/arm/stm32/bootloader)
503       set(FIRMWARE_DEPENDENCIES ${FIRMWARE_DEPENDENCIES} bootloader)
504     elseif(OPENRC_BOOTLOADER)
505       # We fetch Mike's bootloader as it is not included inside OpenTX
506       message(STATUS "Downloading Mike's bootloader: https://github.com/MikeBland/OpenRcBootloader/releases/download/V1.9/${OPENRC_BOOTLOADER}")
507       file(DOWNLOAD https://github.com/MikeBland/OpenRcBootloader/releases/download/V1.9/${OPENRC_BOOTLOADER} ${CMAKE_CURRENT_BINARY_DIR}/bootloader.lbm STATUS status)
508       list(GET status 0 error_code)
509       if(error_code)
510         list(GET status 1 error_message)
511         message(FATAL_ERROR "Download failed: ${error_message}")
512       endif()
513     endif()
515     add_executable(firmware ${SRC} ${FIRMWARE_HEADERS})
516     link_libraries(firmware -lstdc++)
517     add_dependencies(firmware ${FIRMWARE_DEPENDENCIES})
519     add_custom_command(
520       TARGET firmware POST_BUILD
521       COMMAND arm-none-eabi-objcopy -O binary firmware.elf firmware.bin
522       WORKING_DIRECTORY ${CMAKE_BINARY_DIR}
523     )
525     find_program(GAWK gawk HINTS "c:/cygwin/bin/" "c:/msys/bin/" DOC "gawk for firmware size report.")  # OS X might only have "awk"
526     if (BASH AND GAWK)
527       add_custom_target(firmware-size
528         COMMAND ${BASH} -kc '${RADIO_DIRECTORY}/util/elf-size-report.sh --mcu=${CPU_TYPE_FULL} ${SIZE_TARGET_MEM_DEFINE} firmware.elf'
529         DEPENDS firmware
530         WORKING_DIRECTORY ${CMAKE_BINARY_DIR}
531         )
532     else()
533       add_custom_target(firmware-size
534         COMMAND arm-none-eabi-size -A firmware.elf
535         DEPENDS firmware
536         WORKING_DIRECTORY ${CMAKE_BINARY_DIR}
537         )
538     endif()
540   else()  # AVR
542     set(CMAKE_C_COMPILER avr-gcc)
543     set(CMAKE_CXX_COMPILER avr-gcc)
545     set(COMMON_FLAGS "-mmcu=${MCU} -DF_CPU=16000000UL -O${OPT} -gdwarf-2 -fno-exceptions -flto -fwhole-program -fno-inline-small-functions -mstrict-X ${WARNING_FLAGS}")
546     set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} ${COMMON_FLAGS}")
547     set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${COMMON_FLAGS}")
548     set(CMAKE_EXE_LINKER_FLAGS "-Wno-uninitialized")  # bogus "uninitialized" warnings from ld
550     include_directories(storage gui/${GUI_DIR})
552     set(ALLSRC ${PROJECT_BINARY_DIR}/allsrc.cpp)
553     if (BASH AND NOT WIN32)
554       add_custom_command(
555         OUTPUT ${ALLSRC}
556         COMMAND ${BASH} -kc 'rm -f ${ALLSRC}\; for f in ${SRC}\; do echo "\\# 1 \\\"$$f\\\"" >> ${ALLSRC}\; cat "$$f" >> ${ALLSRC}\; done'
557         WORKING_DIRECTORY ${RADIO_SRC_DIRECTORY}
558         DEPENDS ${SRC}
559         )
560     elseif(WIN32)
561       string(REPLACE "/" "\\" SRC_WIN "${SRC}")
562       string(REPLACE "/" "\\" ALLSRC_WIN "${ALLSRC}")
563       set(ALLSRC_BAT
564           "setlocal EnableDelayedExpansion"
565           "del \"${ALLSRC_WIN}\""
566           "for %%f in (${SRC_WIN}) do ("
567             "set p=\"%%f\""
568             "set p=!p:^\\=/! \necho \# 1 !p! >> \"${ALLSRC_WIN}\""
569             "type %%f >> \"${ALLSRC_WIN}\""
570           ")\n"
571         )
572       string(REPLACE ";" "\n" ALLSRC_BAT "${ALLSRC_BAT}")
573       file(WRITE "${ALLSRC}.bat" "${ALLSRC_BAT}")
574       add_custom_command(
575         OUTPUT ${ALLSRC}
576         COMMAND "${ALLSRC}.bat"
577         WORKING_DIRECTORY ${RADIO_SRC_DIRECTORY}
578         DEPENDS ${SRC}
579         )
580     else()
581       set(ALLSRC ${SRC})
582     endif()
583     add_executable(firmware ${ALLSRC})
585     add_dependencies(firmware ${FIRMWARE_DEPENDENCIES})
587     add_custom_command(
588       TARGET firmware POST_BUILD
589       COMMAND avr-objcopy -O ihex -R .eeprom firmware.elf firmware.hex
590       WORKING_DIRECTORY ${CMAKE_BINARY_DIR}
591       )
593     add_custom_target(firmware.lss
594       COMMAND avr-objdump -h -S firmware.elf > firmware.lss
595       DEPENDS firmware
596       WORKING_DIRECTORY ${CMAKE_BINARY_DIR}
597       )
599     add_custom_target(firmware-size
600       COMMAND avr-size --format=avr --mcu=${MCU} firmware.elf
601       DEPENDS firmware
602       WORKING_DIRECTORY ${CMAKE_BINARY_DIR}
603       )
605   endif()  # ARM or AVR
607   if(CPU_FAMILY STREQUAL STM32)
608     add_custom_target(flash
609       COMMAND dfu-util --alt 0 --dfuse-address 0x08000000:leave -d 0483:df11 -D firmware.bin
610       DEPENDS firmware
611       WORKING_DIRECTORY ${CMAKE_BINARY_DIR}
612     )
614     add_custom_target(jtag-flash
615       COMMAND st-flash --reset write firmware.bin 0x8000000
616       DEPENDS firmware
617       WORKING_DIRECTORY ${CMAKE_BINARY_DIR}
618       )
619   else()
620     add_custom_target(flash
621       COMMAND avrdude -c usbasp -p ${AVRDUDE_MCU} -U flash:w:firmware.hex:i
622       DEPENDS firmware
623       WORKING_DIRECTORY ${CMAKE_BINARY_DIR}
624       )
625   endif()
627   PrintTargetReport("firmware")
629 endif(NOT MSVC)