arduino_sketch_builder 0.0.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (35) hide show
  1. checksums.yaml +7 -0
  2. data/.gitignore +23 -0
  3. data/.gitmodules +1 -0
  4. data/Gemfile +4 -0
  5. data/LICENSE.txt +22 -0
  6. data/README.md +71 -0
  7. data/Rakefile +5 -0
  8. data/arduino-cmake/cmake/ArduinoToolchain.cmake +75 -0
  9. data/arduino-cmake/cmake/Platform/Arduino.cmake +1846 -0
  10. data/arduino_sketch_builder.gemspec +22 -0
  11. data/lib/arduino_sketch_builder.rb +8 -0
  12. data/lib/arduino_sketch_builder/arduino_cmake_build.rb +52 -0
  13. data/lib/arduino_sketch_builder/c_make_lists_file_generator.rb +34 -0
  14. data/lib/arduino_sketch_builder/setup.rb +46 -0
  15. data/lib/arduino_sketch_builder/version.rb +3 -0
  16. data/lib/arduino_sketches/CMakeLists.txt +20 -0
  17. data/lib/arduino_sketches/src/BlinkCustomized/BlinkCustomized.ino +19 -0
  18. data/lib/arduino_sketches/src/CMakeLists.txt +14 -0
  19. data/spec/arduino_sketch_builder/arduino_cmake_build_spec.rb +105 -0
  20. data/spec/arduino_sketch_builder/c_make_lists_file_generator_spec.rb +35 -0
  21. data/spec/arduino_sketch_builder/setup_spec.rb +86 -0
  22. data/spec/arduino_sketches_fixture/CMakeLists.txt +20 -0
  23. data/spec/arduino_sketches_fixture/build/.gitkeep +0 -0
  24. data/spec/arduino_sketches_fixture/src/BlinkCustomizedForTest/BlinkCustomizedForTest.ino +19 -0
  25. data/spec/arduino_sketches_fixture/src/CMakeLists.txt +16 -0
  26. data/spec/fixtures/CMakeListsForTestSketch.txt +10 -0
  27. data/spec/fixtures/MainCMakeLists.txt +22 -0
  28. data/spec/spec_helper.rb +14 -0
  29. data/spec/temp/blink_customized_for_test/src/BlinkCustomizedForTest/BlinkCustomizedForTest.ino +19 -0
  30. data/spec/temp/blink_customized_for_test/src/CMakeLists.txt +10 -0
  31. data/templates/MainCMakeListsTemplate.txt.erb +22 -0
  32. data/templates/SourceCMakeListsTemplate.txt.erb +10 -0
  33. data/templates/gitkeep_template +0 -0
  34. data/templates/root_gitignore_template +2 -0
  35. metadata +117 -0
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: e29a1ee1ac0e35fdbb247b9acd642b26cfaf8db6
4
+ data.tar.gz: 838d0585f920ca96720d2b42dab900e1d794c116
5
+ SHA512:
6
+ metadata.gz: a64eb3e51947d7cf7327e961590fd1d95517531cab86e2cd7e41c46f980ff1e0d9f46260cd5d47f43e2796bde97946c557239a54f5af5ba8a57f699e31bd732e
7
+ data.tar.gz: 6a2771b672a28add2eef4db65546755bf8779066822f809f45a462ddabcfb2665619aa0aa0b2c28aa3334a62bfe39dc5f3b2ba001cb29bc1cc830906e8d77fcc
data/.gitignore ADDED
@@ -0,0 +1,23 @@
1
+ *.gem
2
+ *.rbc
3
+ .bundle
4
+ .config
5
+ .yardoc
6
+ Gemfile.lock
7
+ InstalledFiles
8
+ _yardoc
9
+ coverage
10
+ doc/
11
+ lib/bundler/man
12
+ pkg
13
+ rdoc
14
+ spec/reports
15
+ test/tmp
16
+ test/version_tmp
17
+ tmp
18
+ .rvmrc
19
+ .rspec
20
+ lib/arduino_sketches/build
21
+ spec/arduino_sketches_fixture/build/**/*.*
22
+ spec/temp/**/*.*
23
+ spec/temp/.*
data/.gitmodules ADDED
@@ -0,0 +1 @@
1
+
data/Gemfile ADDED
@@ -0,0 +1,4 @@
1
+ source 'https://rubygems.org'
2
+
3
+ # Specify your gem's dependencies in arduino_sketch_builder.gemspec
4
+ gemspec
data/LICENSE.txt ADDED
@@ -0,0 +1,22 @@
1
+ Copyright (c) 2013 Tadatoshi Takahashi
2
+
3
+ MIT License
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining
6
+ a copy of this software and associated documentation files (the
7
+ "Software"), to deal in the Software without restriction, including
8
+ without limitation the rights to use, copy, modify, merge, publish,
9
+ distribute, sublicense, and/or sell copies of the Software, and to
10
+ permit persons to whom the Software is furnished to do so, subject to
11
+ the following conditions:
12
+
13
+ The above copyright notice and this permission notice shall be
14
+ included in all copies or substantial portions of the Software.
15
+
16
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
17
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
18
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
19
+ NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
20
+ LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
21
+ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
22
+ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
data/README.md ADDED
@@ -0,0 +1,71 @@
1
+ # ArduinoSketchBuilder
2
+
3
+ Performs calling the code to compile Arduino sketch and upload it to Arduino
4
+ by Ruby, instead of using Arduino IDE.
5
+
6
+ ## Installation
7
+
8
+ Add this line to your application's Gemfile:
9
+
10
+ gem 'arduino_sketch_builder'
11
+
12
+ And then execute:
13
+
14
+ $ bundle
15
+
16
+ Or install it yourself as:
17
+
18
+ $ gem install arduino_sketch_builder
19
+
20
+ ## Requirements
21
+
22
+ Works with Ruby 1.9.3 and Ruby 2.0.0 (Tested with them).
23
+
24
+ Arduino SDK version 0.19 or higher.
25
+
26
+ ## Usage
27
+
28
+ ### Arduino CMake
29
+
30
+ This gem uses the code from **Arduino CMake** (https://github.com/queezythegreat/arduino-cmake).
31
+ Originally, **Arduino CMake** was included as GIT submodule in this gem.
32
+ But there was a problem so now the necessary **Arduino CMake** codes are copied in this gem (arduino-cmake directory).
33
+
34
+ ### Directory structure
35
+
36
+ The default directory structure is
37
+ The default directory structure is
38
+ (root directory)
39
+ |- cmake
40
+ | |- ArduinoToolchain.cmake
41
+ | |- Platform
42
+ | |- Arduino.cmake
43
+ |- (name of Arduino sketch underlined)
44
+ |--build
45
+ |--src
46
+ | |--(name of Arduino sketch)
47
+ | |--(Arduino sketch file)
48
+ | |--CMakeLists.txt
49
+ |--CMakeLists.txt
50
+
51
+ example:
52
+ ~/.arduino_sketches
53
+ |- cmake
54
+ | |- ArduinoToolchain.cmake
55
+ | |- Platform
56
+ | |- Arduino.cmake
57
+ |- blink_customized
58
+ |--build
59
+ |--src
60
+ | |--BlinkCustomized
61
+ | |--BlinkCustomized.ino
62
+ | |--CMakeLists.txt
63
+ |--CMakeLists.txt
64
+
65
+ ## Contributing
66
+
67
+ 1. Fork it
68
+ 2. Create your feature branch (`git checkout -b my-new-feature`)
69
+ 3. Commit your changes (`git commit -am 'Add some feature'`)
70
+ 4. Push to the branch (`git push origin my-new-feature`)
71
+ 5. Create new Pull Request
data/Rakefile ADDED
@@ -0,0 +1,5 @@
1
+ require "bundler/gem_tasks"
2
+ require 'rspec/core/rake_task'
3
+
4
+ RSpec::Core::RakeTask.new(:spec)
5
+ task default: :spec
@@ -0,0 +1,75 @@
1
+ #=============================================================================#
2
+ # Author: Tomasz Bogdal (QueezyTheGreat)
3
+ # Home: https://github.com/queezythegreat/arduino-cmake
4
+ #
5
+ # This Source Code Form is subject to the terms of the Mozilla Public
6
+ # License, v. 2.0. If a copy of the MPL was not distributed with this file,
7
+ # You can obtain one at http://mozilla.org/MPL/2.0/.
8
+ #=============================================================================#
9
+ set(CMAKE_SYSTEM_NAME Arduino)
10
+
11
+ set(CMAKE_C_COMPILER avr-gcc)
12
+ set(CMAKE_CXX_COMPILER avr-g++)
13
+
14
+ # Add current directory to CMake Module path automatically
15
+ if(EXISTS ${CMAKE_CURRENT_LIST_DIR}/Platform/Arduino.cmake)
16
+ set(CMAKE_MODULE_PATH ${CMAKE_MODULE_PATH} ${CMAKE_CURRENT_LIST_DIR})
17
+ endif()
18
+
19
+ #=============================================================================#
20
+ # System Paths #
21
+ #=============================================================================#
22
+ if(UNIX)
23
+ include(Platform/UnixPaths)
24
+ if(APPLE)
25
+ list(APPEND CMAKE_SYSTEM_PREFIX_PATH ~/Applications
26
+ /Applications
27
+ /Developer/Applications
28
+ /sw # Fink
29
+ /opt/local) # MacPorts
30
+ endif()
31
+ elseif(WIN32)
32
+ include(Platform/WindowsPaths)
33
+ endif()
34
+
35
+
36
+ #=============================================================================#
37
+ # Detect Arduino SDK #
38
+ #=============================================================================#
39
+ if(NOT ARDUINO_SDK_PATH)
40
+ set(ARDUINO_PATHS)
41
+
42
+ foreach(DETECT_VERSION_MAJOR 1)
43
+ foreach(DETECT_VERSION_MINOR RANGE 5 0)
44
+ list(APPEND ARDUINO_PATHS arduino-${DETECT_VERSION_MAJOR}.${DETECT_VERSION_MINOR})
45
+ foreach(DETECT_VERSION_PATCH RANGE 3 0)
46
+ list(APPEND ARDUINO_PATHS arduino-${DETECT_VERSION_MAJOR}.${DETECT_VERSION_MINOR}.${DETECT_VERSION_PATCH})
47
+ endforeach()
48
+ endforeach()
49
+ endforeach()
50
+
51
+ foreach(VERSION RANGE 23 19)
52
+ list(APPEND ARDUINO_PATHS arduino-00${VERSION})
53
+ endforeach()
54
+
55
+ file(GLOB SDK_PATH_HINTS /usr/share/arduino*
56
+ /opt/local/ardiuno*
57
+ /usr/local/share/arduino*)
58
+ list(SORT SDK_PATH_HINTS)
59
+ list(REVERSE SDK_PATH_HINTS)
60
+ endif()
61
+
62
+ find_path(ARDUINO_SDK_PATH
63
+ NAMES lib/version.txt
64
+ PATH_SUFFIXES share/arduino
65
+ Arduino.app/Contents/Resources/Java/
66
+ ${ARDUINO_PATHS}
67
+ HINTS ${SDK_PATH_HINTS}
68
+ DOC "Arduino SDK path.")
69
+
70
+ if(ARDUINO_SDK_PATH)
71
+ list(APPEND CMAKE_SYSTEM_PREFIX_PATH ${ARDUINO_SDK_PATH}/hardware/tools/avr/bin)
72
+ list(APPEND CMAKE_SYSTEM_PREFIX_PATH ${ARDUINO_SDK_PATH}/hardware/tools/avr/utils/bin)
73
+ else()
74
+ message(FATAL_ERROR "Could not find Arduino SDK (set ARDUINO_SDK_PATH)!")
75
+ endif()
@@ -0,0 +1,1846 @@
1
+ #=============================================================================#
2
+ # generate_arduino_firmware(name
3
+ # [BOARD board_id]
4
+ # [SKETCH sketch_path |
5
+ # SRCS src1 src2 ... srcN]
6
+ # [HDRS hdr1 hdr2 ... hdrN]
7
+ # [LIBS lib1 lib2 ... libN]
8
+ # [PORT port]
9
+ # [SERIAL serial_cmd]
10
+ # [PROGRAMMER programmer_id]
11
+ # [AFLAGS flags]
12
+ # [NO_AUTOLIBS]
13
+ # [MANUAL])
14
+ #=============================================================================#
15
+ #
16
+ # generaters firmware and libraries for Arduino devices
17
+ #
18
+ # The arguments are as follows:
19
+ #
20
+ # name # The name of the firmware target [REQUIRED]
21
+ # BOARD # Board name (such as uno, mega2560, ...) [REQUIRED]
22
+ # SKETCH # Arduino sketch [must have SRCS or SKETCH]
23
+ # SRCS # Sources [must have SRCS or SKETCH]
24
+ # HDRS # Headers
25
+ # LIBS # Libraries to link
26
+ # PORT # Serial port (enables upload support)
27
+ # SERIAL # Serial command for serial target
28
+ # PROGRAMMER # Programmer id (enables programmer support)
29
+ # AFLAGS # Avrdude flags for target
30
+ # NO_AUTOLIBS # Disables Arduino library detection
31
+ # MANUAL # (Advanced) Only use AVR Libc/Includes
32
+ #
33
+ # Here is a short example for a target named test:
34
+ #
35
+ # generate_arduino_firmware(
36
+ # NAME test
37
+ # SRCS test.cpp
38
+ # test2.cpp
39
+ # HDRS test.h test2.h
40
+ # BOARD uno)
41
+ #
42
+ # Alternatively you can specify the option by variables:
43
+ #
44
+ # set(test_SRCS test.cpp test2.cpp)
45
+ # set(test_HDRS test.h test2.h
46
+ # set(test_BOARD uno)
47
+ #
48
+ # generate_arduino_firmware(test)
49
+ #
50
+ # All variables need to be prefixed with the target name (${TARGET_NAME}_${OPTION}).
51
+ #
52
+ #=============================================================================#
53
+ # generate_arduino_library(name
54
+ # [BOARD board_id]
55
+ # [SRCS src1 src2 ... srcN]
56
+ # [HDRS hdr1 hdr2 ... hdrN]
57
+ # [LIBS lib1 lib2 ... libN]
58
+ # [NO_AUTOLIBS])
59
+ #=============================================================================#
60
+ # generaters firmware and libraries for Arduino devices
61
+ #
62
+ # The arguments are as follows:
63
+ #
64
+ # name # The name of the firmware target [REQUIRED]
65
+ # BOARD # Board name (such as uno, mega2560, ...) [REQUIRED]
66
+ # SRCS # Sources [REQUIRED]
67
+ # HDRS # Headers
68
+ # LIBS # Libraries to link
69
+ # NO_AUTOLIBS # Disables Arduino library detection
70
+ #
71
+ # Here is a short example for a target named test:
72
+ #
73
+ # generate_arduino_library(
74
+ # NAME test
75
+ # SRCS test.cpp
76
+ # test2.cpp
77
+ # HDRS test.h test2.h
78
+ # BOARD uno)
79
+ #
80
+ # Alternatively you can specify the option by variables:
81
+ #
82
+ # set(test_SRCS test.cpp test2.cpp)
83
+ # set(test_HDRS test.h test2.h
84
+ # set(test_BOARD uno)
85
+ #
86
+ # generate_arduino_library(test)
87
+ #
88
+ # All variables need to be prefixed with the target name (${TARGET_NAME}_${OPTION}).
89
+ #
90
+ #=============================================================================#
91
+ # generate_arduino_example(name
92
+ # LIBRARY library_name
93
+ # EXAMPLE example_name
94
+ # [BOARD board_id]
95
+ # [PORT port]
96
+ # [SERIAL serial command]
97
+ # [PORGRAMMER programmer_id]
98
+ # [AFLAGS avrdude_flags])
99
+ #=============================================================================#
100
+ #
101
+ # name - The name of the library example [REQUIRED]
102
+ # LIBRARY - Library name [REQUIRED]
103
+ # EXAMPLE - Example name [REQUIRED]
104
+ # BOARD - Board ID
105
+ # PORT - Serial port [optional]
106
+ # SERIAL - Serial command [optional]
107
+ # PROGRAMMER - Programmer id (enables programmer support)
108
+ # AFLAGS - Avrdude flags for target
109
+ #
110
+ # Creates a example from the specified library.
111
+ #
112
+ #
113
+ #=============================================================================#
114
+ # print_board_list()
115
+ #=============================================================================#
116
+ #
117
+ # Print list of detected Arduino Boards.
118
+ #
119
+ #=============================================================================#
120
+ # print_programmer_list()
121
+ #=============================================================================#
122
+ #
123
+ # Print list of detected Programmers.
124
+ #
125
+ #=============================================================================#
126
+ # print_programmer_settings(PROGRAMMER)
127
+ #=============================================================================#
128
+ #
129
+ # PROGRAMMER - programmer id
130
+ #
131
+ # Print the detected Programmer settings.
132
+ #
133
+ #=============================================================================#
134
+ # print_board_settings(ARDUINO_BOARD)
135
+ #=============================================================================#
136
+ #
137
+ # ARDUINO_BOARD - Board id
138
+ #
139
+ # Print the detected Arduino board settings.
140
+ #
141
+ #=============================================================================#
142
+ # Configuration Options
143
+ #=============================================================================#
144
+ #
145
+ # ARDUINO_SDK_PATH - Arduino SDK Path
146
+ # ARDUINO_AVRDUDE_PROGRAM - Full path to avrdude programmer
147
+ # ARDUINO_AVRDUDE_CONFIG_PATH - Full path to avrdude configuration file
148
+ #
149
+ # ARDUINO_C_FLAGS - C compiler flags
150
+ # ARDUINO_CXX_FLAGS - C++ compiler flags
151
+ # ARDUINO_LINKER_FLAGS - Linker flags
152
+ #
153
+ # ARDUINO_DEFAULT_BOARD - Default Arduino Board ID when not specified.
154
+ # ARDUINO_DEFAULT_PORT - Default Arduino port when not specified.
155
+ # ARDUINO_DEFAULT_SERIAL - Default Arduino Serial command when not specified.
156
+ # ARDUINO_DEFAULT_PROGRAMMER - Default Arduino Programmer ID when not specified.
157
+ #
158
+ #
159
+ # ARDUINO_FOUND - Set to True when the Arduino SDK is detected and configured.
160
+ # ARDUINO_SDK_VERSION - Set to the version of the detected Arduino SDK (ex: 1.0)
161
+
162
+ #=============================================================================#
163
+ # Author: Tomasz Bogdal (QueezyTheGreat)
164
+ # Home: https://github.com/queezythegreat/arduino-cmake
165
+ #
166
+ # This Source Code Form is subject to the terms of the Mozilla Public
167
+ # License, v. 2.0. If a copy of the MPL was not distributed with this file,
168
+ # You can obtain one at http://mozilla.org/MPL/2.0/.
169
+ #=============================================================================#
170
+ cmake_minimum_required(VERSION 2.8.5)
171
+ include(CMakeParseArguments)
172
+
173
+
174
+
175
+
176
+
177
+
178
+ #=============================================================================#
179
+ # User Functions
180
+ #=============================================================================#
181
+
182
+ #=============================================================================#
183
+ # [PUBLIC/USER]
184
+ #
185
+ # print_board_list()
186
+ #
187
+ # see documentation at top
188
+ #=============================================================================#
189
+ function(PRINT_BOARD_LIST)
190
+ message(STATUS "Arduino Boards:")
191
+ print_list(ARDUINO_BOARDS)
192
+ message(STATUS "")
193
+ endfunction()
194
+
195
+ #=============================================================================#
196
+ # [PUBLIC/USER]
197
+ #
198
+ # print_programmer_list()
199
+ #
200
+ # see documentation at top
201
+ #=============================================================================#
202
+ function(PRINT_PROGRAMMER_LIST)
203
+ message(STATUS "Arduino Programmers:")
204
+ print_list(ARDUINO_PROGRAMMERS)
205
+ message(STATUS "")
206
+ endfunction()
207
+
208
+ #=============================================================================#
209
+ # [PUBLIC/USER]
210
+ #
211
+ # print_programmer_settings(PROGRAMMER)
212
+ #
213
+ # see documentation at top
214
+ #=============================================================================#
215
+ function(PRINT_PROGRAMMER_SETTINGS PROGRAMMER)
216
+ if(${PROGRAMMER}.SETTINGS)
217
+ message(STATUS "Programmer ${PROGRAMMER} Settings:")
218
+ print_settings(${PROGRAMMER})
219
+ endif()
220
+ endfunction()
221
+
222
+ # [PUBLIC/USER]
223
+ #
224
+ # print_board_settings(ARDUINO_BOARD)
225
+ #
226
+ # see documentation at top
227
+ function(PRINT_BOARD_SETTINGS ARDUINO_BOARD)
228
+ if(${ARDUINO_BOARD}.SETTINGS)
229
+ message(STATUS "Arduino ${ARDUINO_BOARD} Board:")
230
+ print_settings(${ARDUINO_BOARD})
231
+ endif()
232
+ endfunction()
233
+
234
+ #=============================================================================#
235
+ # [PUBLIC/USER]
236
+ # see documentation at top
237
+ #=============================================================================#
238
+ function(GENERATE_ARDUINO_LIBRARY INPUT_NAME)
239
+ message(STATUS "Generating ${INPUT_NAME}")
240
+ parse_generator_arguments(${INPUT_NAME} INPUT
241
+ "NO_AUTOLIBS;MANUAL" # Options
242
+ "BOARD" # One Value Keywords
243
+ "SRCS;HDRS;LIBS" # Multi Value Keywords
244
+ ${ARGN})
245
+
246
+ if(NOT INPUT_BOARD)
247
+ set(INPUT_BOARD ${ARDUINO_DEFAULT_BOARD})
248
+ endif()
249
+ if(NOT INPUT_MANUAL)
250
+ set(INPUT_MANUAL FALSE)
251
+ endif()
252
+ required_variables(VARS INPUT_SRCS INPUT_BOARD MSG "must define for target ${INPUT_NAME}")
253
+
254
+ set(ALL_LIBS)
255
+ set(ALL_SRCS ${INPUT_SRCS} ${INPUT_HDRS})
256
+
257
+ if(NOT INPUT_MANUAL)
258
+ setup_arduino_core(CORE_LIB ${INPUT_BOARD})
259
+ endif()
260
+
261
+ find_arduino_libraries(TARGET_LIBS "${ALL_SRCS}")
262
+ set(LIB_DEP_INCLUDES)
263
+ foreach(LIB_DEP ${TARGET_LIBS})
264
+ set(LIB_DEP_INCLUDES "${LIB_DEP_INCLUDES} -I\"${LIB_DEP}\"")
265
+ endforeach()
266
+
267
+ if(NOT ${INPUT_NO_AUTOLIBS})
268
+ setup_arduino_libraries(ALL_LIBS ${INPUT_BOARD} "${ALL_SRCS}" "${LIB_DEP_INCLUDES}" "")
269
+ endif()
270
+
271
+ list(APPEND ALL_LIBS ${CORE_LIB} ${INPUT_LIBS})
272
+
273
+ add_library(${INPUT_NAME} ${ALL_SRCS})
274
+
275
+ get_arduino_flags(ARDUINO_COMPILE_FLAGS ARDUINO_LINK_FLAGS ${INPUT_BOARD} ${INPUT_MANUAL})
276
+
277
+ set_target_properties(${INPUT_NAME} PROPERTIES
278
+ COMPILE_FLAGS "${ARDUINO_COMPILE_FLAGS} ${COMPILE_FLAGS} ${LIB_DEP_INCLUDES}"
279
+ LINK_FLAGS "${ARDUINO_LINK_FLAGS} ${LINK_FLAGS}")
280
+
281
+ target_link_libraries(${INPUT_NAME} ${ALL_LIBS} "-lc -lm")
282
+ endfunction()
283
+
284
+ #=============================================================================#
285
+ # [PUBLIC/USER]
286
+ # see documentation at top
287
+ #=============================================================================#
288
+ function(GENERATE_ARDUINO_FIRMWARE INPUT_NAME)
289
+ message(STATUS "Generating ${INPUT_NAME}")
290
+ parse_generator_arguments(${INPUT_NAME} INPUT
291
+ "NO_AUTOLIBS;MANUAL" # Options
292
+ "BOARD;PORT;SKETCH;PROGRAMMER" # One Value Keywords
293
+ "SERIAL;SRCS;HDRS;LIBS;AFLAGS" # Multi Value Keywords
294
+ ${ARGN})
295
+
296
+ if(NOT INPUT_BOARD)
297
+ set(INPUT_BOARD ${ARDUINO_DEFAULT_BOARD})
298
+ endif()
299
+ if(NOT INPUT_PORT)
300
+ set(INPUT_PORT ${ARDUINO_DEFAULT_PORT})
301
+ endif()
302
+ if(NOT INPUT_SERIAL)
303
+ set(INPUT_SERIAL ${ARDUINO_DEFAULT_SERIAL})
304
+ endif()
305
+ if(NOT INPUT_PROGRAMMER)
306
+ set(INPUT_PROGRAMMER ${ARDUINO_DEFAULT_PROGRAMMER})
307
+ endif()
308
+ if(NOT INPUT_MANUAL)
309
+ set(INPUT_MANUAL FALSE)
310
+ endif()
311
+ required_variables(VARS INPUT_BOARD MSG "must define for target ${INPUT_NAME}")
312
+
313
+ set(ALL_LIBS)
314
+ set(ALL_SRCS ${INPUT_SRCS} ${INPUT_HDRS})
315
+ set(LIB_DEP_INCLUDES)
316
+
317
+ if(NOT INPUT_MANUAL)
318
+ setup_arduino_core(CORE_LIB ${INPUT_BOARD})
319
+ endif()
320
+
321
+ if(NOT "${INPUT_SKETCH}" STREQUAL "")
322
+ get_filename_component(INPUT_SKETCH "${INPUT_SKETCH}" ABSOLUTE)
323
+ setup_arduino_sketch(${INPUT_NAME} ${INPUT_SKETCH} ALL_SRCS)
324
+ if (IS_DIRECTORY "${INPUT_SKETCH}")
325
+ set(LIB_DEP_INCLUDES "${LIB_DEP_INCLUDES} -I\"${INPUT_SKETCH}\"")
326
+ else()
327
+ get_filename_component(INPUT_SKETCH_PATH "${INPUT_SKETCH}" PATH)
328
+ set(LIB_DEP_INCLUDES "${LIB_DEP_INCLUDES} -I\"${INPUT_SKETCH_PATH}\"")
329
+ endif()
330
+ endif()
331
+
332
+ required_variables(VARS ALL_SRCS MSG "must define SRCS or SKETCH for target ${INPUT_NAME}")
333
+
334
+ find_arduino_libraries(TARGET_LIBS "${ALL_SRCS}")
335
+ foreach(LIB_DEP ${TARGET_LIBS})
336
+ set(LIB_DEP_INCLUDES "${LIB_DEP_INCLUDES} -I\"${LIB_DEP}\"")
337
+ endforeach()
338
+
339
+ if(NOT INPUT_NO_AUTOLIBS)
340
+ setup_arduino_libraries(ALL_LIBS ${INPUT_BOARD} "${ALL_SRCS}" "${LIB_DEP_INCLUDES}" "")
341
+ endif()
342
+
343
+ list(APPEND ALL_LIBS ${CORE_LIB} ${INPUT_LIBS})
344
+
345
+ setup_arduino_target(${INPUT_NAME} ${INPUT_BOARD} "${ALL_SRCS}" "${ALL_LIBS}" "${LIB_DEP_INCLUDES}" "" "${INPUT_MANUAL}")
346
+
347
+ if(INPUT_PORT)
348
+ setup_arduino_upload(${INPUT_BOARD} ${INPUT_NAME} ${INPUT_PORT} "${INPUT_PROGRAMMER}" "${INPUT_AFLAGS}")
349
+ endif()
350
+
351
+ if(INPUT_SERIAL)
352
+ setup_serial_target(${INPUT_NAME} "${INPUT_SERIAL}" "${INPUT_PORT}")
353
+ endif()
354
+
355
+ endfunction()
356
+
357
+ #=============================================================================#
358
+ # [PUBLIC/USER]
359
+ # see documentation at top
360
+ #=============================================================================#
361
+ function(GENERATE_ARDUINO_EXAMPLE INPUT_NAME)
362
+ message(STATUS "Generating example ${LIBRARY_NAME}-${EXAMPLE_NAME}")
363
+ parse_generator_arguments(${INPUT_NAME} INPUT
364
+ "" # Options
365
+ "LIBRARY;EXAMPLE;BOARD;PORT;PROGRAMMER" # One Value Keywords
366
+ "SERIAL;AFLAGS" # Multi Value Keywords
367
+ ${ARGN})
368
+
369
+ if(NOT INPUT_BOARD)
370
+ set(INPUT_BOARD ${ARDUINO_DEFAULT_BOARD})
371
+ endif()
372
+ if(NOT INPUT_PORT)
373
+ set(INPUT_PORT ${ARDUINO_DEFAULT_PORT})
374
+ endif()
375
+ if(NOT INPUT_SERIAL)
376
+ set(INPUT_SERIAL ${ARDUINO_DEFAULT_SERIAL})
377
+ endif()
378
+ if(NOT INPUT_PROGRAMMER)
379
+ set(INPUT_PROGRAMMER ${ARDUINO_DEFAULT_PROGRAMMER})
380
+ endif()
381
+ required_variables(VARS INPUT_LIBRARY INPUT_EXAMPLE INPUT_BOARD
382
+ MSG "must define for target ${INPUT_NAME}")
383
+
384
+ set(ALL_LIBS)
385
+ set(ALL_SRCS)
386
+
387
+ setup_arduino_core(CORE_LIB ${INPUT_BOARD})
388
+
389
+ setup_arduino_example("${INPUT_NAME}" "${INPUT_LIBRARY}" "${INPUT_EXAMPLE}" ALL_SRCS)
390
+
391
+ if(NOT ALL_SRCS)
392
+ message(FATAL_ERROR "Missing sources for example, aborting!")
393
+ endif()
394
+
395
+ find_arduino_libraries(TARGET_LIBS "${ALL_SRCS}")
396
+ set(LIB_DEP_INCLUDES)
397
+ foreach(LIB_DEP ${TARGET_LIBS})
398
+ set(LIB_DEP_INCLUDES "${LIB_DEP_INCLUDES} -I\"${LIB_DEP}\"")
399
+ endforeach()
400
+
401
+ setup_arduino_libraries(ALL_LIBS ${INPUT_BOARD} "${ALL_SRCS}" "${LIB_DEP_INCLUDES}" "")
402
+
403
+ list(APPEND ALL_LIBS ${CORE_LIB} ${INPUT_LIBS})
404
+
405
+ setup_arduino_target(${INPUT_NAME} ${INPUT_BOARD} "${ALL_SRCS}" "${ALL_LIBS}" "${LIB_DEP_INCLUDES}" "" FALSE)
406
+
407
+ if(INPUT_PORT)
408
+ setup_arduino_upload(${INPUT_BOARD} ${INPUT_NAME} ${INPUT_PORT} "${INPUT_PROGRAMMER}" "${INPUT_AFLAGS}")
409
+ endif()
410
+
411
+ if(INPUT_SERIAL)
412
+ setup_serial_target(${INPUT_NAME} "${INPUT_SERIAL}" "${INPUT_PORT}")
413
+ endif()
414
+ endfunction()
415
+
416
+ #=============================================================================#
417
+ # Internal Functions
418
+ #=============================================================================#
419
+
420
+ #=============================================================================#
421
+ # [PRIVATE/INTERNAL]
422
+ #
423
+ # parse_generator_arguments(TARGET_NAME PREFIX OPTIONS ARGS MULTI_ARGS [ARG1 ARG2 .. ARGN])
424
+ #
425
+ # PREFIX - Parsed options prefix
426
+ # OPTIONS - List of options
427
+ # ARGS - List of one value keyword arguments
428
+ # MULTI_ARGS - List of multi value keyword arguments
429
+ # [ARG1 ARG2 .. ARGN] - command arguments [optional]
430
+ #
431
+ # Parses generator options from either variables or command arguments
432
+ #
433
+ #=============================================================================#
434
+ macro(PARSE_GENERATOR_ARGUMENTS TARGET_NAME PREFIX OPTIONS ARGS MULTI_ARGS)
435
+ cmake_parse_arguments(${PREFIX} "${OPTIONS}" "${ARGS}" "${MULTI_ARGS}" ${ARGN})
436
+ error_for_unparsed(${PREFIX})
437
+ load_generator_settings(${TARGET_NAME} ${PREFIX} ${OPTIONS} ${ARGS} ${MULTI_ARGS})
438
+ endmacro()
439
+
440
+ #=============================================================================#
441
+ # [PRIVATE/INTERNAL]
442
+ #
443
+ # load_board_settings()
444
+ #
445
+ # Load the Arduino SDK board settings from the boards.txt file.
446
+ #
447
+ #=============================================================================#
448
+ function(LOAD_BOARD_SETTINGS)
449
+ load_arduino_style_settings(ARDUINO_BOARDS "${ARDUINO_BOARDS_PATH}")
450
+ endfunction()
451
+
452
+ #=============================================================================#
453
+ # [PRIVATE/INTERNAL]
454
+ #
455
+ #=============================================================================#
456
+ function(LOAD_PROGRAMMERS_SETTINGS)
457
+ load_arduino_style_settings(ARDUINO_PROGRAMMERS "${ARDUINO_PROGRAMMERS_PATH}")
458
+ endfunction()
459
+
460
+ #=============================================================================#
461
+ # [PRIVATE/INTERNAL]
462
+ #
463
+ # load_generator_settings(TARGET_NAME PREFIX [SUFFIX_1 SUFFIX_2 .. SUFFIX_N])
464
+ #
465
+ # TARGET_NAME - The base name of the user settings
466
+ # PREFIX - The prefix name used for generator settings
467
+ # SUFFIX_XX - List of suffixes to load
468
+ #
469
+ # Loads a list of user settings into the generators scope. User settings have
470
+ # the following syntax:
471
+ #
472
+ # ${BASE_NAME}${SUFFIX}
473
+ #
474
+ # The BASE_NAME is the target name and the suffix is a specific generator settings.
475
+ #
476
+ # For every user setting found a generator setting is created of the follwoing fromat:
477
+ #
478
+ # ${PREFIX}${SUFFIX}
479
+ #
480
+ # The purpose of loading the settings into the generator is to not modify user settings
481
+ # and to have a generic naming of the settings within the generator.
482
+ #
483
+ #=============================================================================#
484
+ function(LOAD_GENERATOR_SETTINGS TARGET_NAME PREFIX)
485
+ foreach(GEN_SUFFIX ${ARGN})
486
+ if(${TARGET_NAME}_${GEN_SUFFIX} AND NOT ${PREFIX}_${GEN_SUFFIX})
487
+ set(${PREFIX}_${GEN_SUFFIX} ${${TARGET_NAME}_${GEN_SUFFIX}} PARENT_SCOPE)
488
+ endif()
489
+ endforeach()
490
+ endfunction()
491
+
492
+ #=============================================================================#
493
+ # [PRIVATE/INTERNAL]
494
+ #
495
+ # get_arduino_flags(COMPILE_FLAGS LINK_FLAGS BOARD_ID MANUAL)
496
+ #
497
+ # COMPILE_FLAGS_VAR -Variable holding compiler flags
498
+ # LINK_FLAGS_VAR - Variable holding linker flags
499
+ # BOARD_ID - The board id name
500
+ # MANUAL - (Advanced) Only use AVR Libc/Includes
501
+ #
502
+ # Configures the the build settings for the specified Arduino Board.
503
+ #
504
+ #=============================================================================#
505
+ function(get_arduino_flags COMPILE_FLAGS_VAR LINK_FLAGS_VAR BOARD_ID MANUAL)
506
+
507
+ set(BOARD_CORE ${${BOARD_ID}.build.core})
508
+ if(BOARD_CORE)
509
+ if(ARDUINO_SDK_VERSION MATCHES "([0-9]+)[.]([0-9]+)")
510
+ string(REPLACE "." "" ARDUINO_VERSION_DEFINE "${ARDUINO_SDK_VERSION}") # Normalize version (remove all periods)
511
+ set(ARDUINO_VERSION_DEFINE "")
512
+ if(CMAKE_MATCH_1 GREATER 0)
513
+ set(ARDUINO_VERSION_DEFINE "${CMAKE_MATCH_1}")
514
+ endif()
515
+ if(CMAKE_MATCH_2 GREATER 10)
516
+ set(ARDUINO_VERSION_DEFINE "${ARDUINO_VERSION_DEFINE}${CMAKE_MATCH_2}")
517
+ else()
518
+ set(ARDUINO_VERSION_DEFINE "${ARDUINO_VERSION_DEFINE}0${CMAKE_MATCH_2}")
519
+ endif()
520
+ else()
521
+ message("Invalid Arduino SDK Version (${ARDUINO_SDK_VERSION})")
522
+ endif()
523
+
524
+ # output
525
+ set(COMPILE_FLAGS "-DF_CPU=${${BOARD_ID}.build.f_cpu} -DARDUINO=${ARDUINO_VERSION_DEFINE} -mmcu=${${BOARD_ID}.build.mcu}")
526
+ if(DEFINED ${BOARD_ID}.build.vid)
527
+ set(COMPILE_FLAGS "${COMPILE_FLAGS} -DUSB_VID=${${BOARD_ID}.build.vid}")
528
+ endif()
529
+ if(DEFINED ${BOARD_ID}.build.pid)
530
+ set(COMPILE_FLAGS "${COMPILE_FLAGS} -DUSB_PID=${${BOARD_ID}.build.pid}")
531
+ endif()
532
+ if(NOT MANUAL)
533
+ set(COMPILE_FLAGS "${COMPILE_FLAGS} -I\"${ARDUINO_CORES_PATH}/${BOARD_CORE}\" -I\"${ARDUINO_LIBRARIES_PATH}\"")
534
+ endif()
535
+ set(LINK_FLAGS "-mmcu=${${BOARD_ID}.build.mcu}")
536
+ if(ARDUINO_SDK_VERSION VERSION_GREATER 1.0 OR ARDUINO_SDK_VERSION VERSION_EQUAL 1.0)
537
+ set(PIN_HEADER ${${BOARD_ID}.build.variant})
538
+ if(NOT MANUAL)
539
+ set(COMPILE_FLAGS "${COMPILE_FLAGS} -I\"${ARDUINO_VARIANTS_PATH}/${PIN_HEADER}\"")
540
+ endif()
541
+ endif()
542
+
543
+ # output
544
+ set(${COMPILE_FLAGS_VAR} "${COMPILE_FLAGS}" PARENT_SCOPE)
545
+ set(${LINK_FLAGS_VAR} "${LINK_FLAGS}" PARENT_SCOPE)
546
+
547
+ else()
548
+ message(FATAL_ERROR "Invalid Arduino board ID (${BOARD_ID}), aborting.")
549
+ endif()
550
+ endfunction()
551
+
552
+ #=============================================================================#
553
+ # [PRIVATE/INTERNAL]
554
+ #
555
+ # setup_arduino_core(VAR_NAME BOARD_ID)
556
+ #
557
+ # VAR_NAME - Variable name that will hold the generated library name
558
+ # BOARD_ID - Arduino board id
559
+ #
560
+ # Creates the Arduino Core library for the specified board,
561
+ # each board gets it's own version of the library.
562
+ #
563
+ #=============================================================================#
564
+ function(setup_arduino_core VAR_NAME BOARD_ID)
565
+ set(CORE_LIB_NAME ${BOARD_ID}_CORE)
566
+ set(BOARD_CORE ${${BOARD_ID}.build.core})
567
+ if(BOARD_CORE)
568
+ if(NOT TARGET ${CORE_LIB_NAME})
569
+ set(BOARD_CORE_PATH ${ARDUINO_CORES_PATH}/${BOARD_CORE})
570
+ find_sources(CORE_SRCS ${BOARD_CORE_PATH} True)
571
+ # Debian/Ubuntu fix
572
+ list(REMOVE_ITEM CORE_SRCS "${BOARD_CORE_PATH}/main.cxx")
573
+ add_library(${CORE_LIB_NAME} ${CORE_SRCS})
574
+ get_arduino_flags(ARDUINO_COMPILE_FLAGS ARDUINO_LINK_FLAGS ${BOARD_ID} FALSE)
575
+ set_target_properties(${CORE_LIB_NAME} PROPERTIES
576
+ COMPILE_FLAGS "${ARDUINO_COMPILE_FLAGS}"
577
+ LINK_FLAGS "${ARDUINO_LINK_FLAGS}")
578
+ endif()
579
+ set(${VAR_NAME} ${CORE_LIB_NAME} PARENT_SCOPE)
580
+ endif()
581
+ endfunction()
582
+
583
+ #=============================================================================#
584
+ # [PRIVATE/INTERNAL]
585
+ #
586
+ # find_arduino_libraries(VAR_NAME SRCS)
587
+ #
588
+ # VAR_NAME - Variable name which will hold the results
589
+ # SRCS - Sources that will be analized
590
+ #
591
+ # returns a list of paths to libraries found.
592
+ #
593
+ # Finds all Arduino type libraries included in sources. Available libraries
594
+ # are ${ARDUINO_SDK_PATH}/libraries and ${CMAKE_CURRENT_SOURCE_DIR}.
595
+ #
596
+ # A Arduino library is a folder that has the same name as the include header.
597
+ # For example, if we have a include "#include <LibraryName.h>" then the following
598
+ # directory structure is considered a Arduino library:
599
+ #
600
+ # LibraryName/
601
+ # |- LibraryName.h
602
+ # `- LibraryName.c
603
+ #
604
+ # If such a directory is found then all sources within that directory are considred
605
+ # to be part of that Arduino library.
606
+ #
607
+ #=============================================================================#
608
+ function(find_arduino_libraries VAR_NAME SRCS)
609
+ set(ARDUINO_LIBS )
610
+ foreach(SRC ${SRCS})
611
+ if(NOT (EXISTS ${SRC} OR
612
+ EXISTS ${CMAKE_CURRENT_SOURCE_DIR}/${SRC} OR
613
+ EXISTS ${CMAKE_CURRENT_BINARY_DIR}/${SRC}))
614
+ message(FATAL_ERROR "Invalid source file: ${SRC}")
615
+ endif()
616
+ file(STRINGS ${SRC} SRC_CONTENTS)
617
+ foreach(SRC_LINE ${SRC_CONTENTS})
618
+ if("${SRC_LINE}" MATCHES "^ *#include *[<\"](.*)[>\"]")
619
+ get_filename_component(INCLUDE_NAME ${CMAKE_MATCH_1} NAME_WE)
620
+ get_property(LIBRARY_SEARCH_PATH
621
+ DIRECTORY # Property Scope
622
+ PROPERTY LINK_DIRECTORIES)
623
+ foreach(LIB_SEARCH_PATH ${LIBRARY_SEARCH_PATH} ${ARDUINO_LIBRARIES_PATH} ${CMAKE_CURRENT_SOURCE_DIR} ${CMAKE_CURRENT_SOURCE_DIR}/libraries ${ARDUINO_EXTRA_LIBRARIES_PATH})
624
+ if(EXISTS ${LIB_SEARCH_PATH}/${INCLUDE_NAME}/${CMAKE_MATCH_1})
625
+ list(APPEND ARDUINO_LIBS ${LIB_SEARCH_PATH}/${INCLUDE_NAME})
626
+ break()
627
+ endif()
628
+ endforeach()
629
+ endif()
630
+ endforeach()
631
+ endforeach()
632
+ if(ARDUINO_LIBS)
633
+ list(REMOVE_DUPLICATES ARDUINO_LIBS)
634
+ endif()
635
+ set(${VAR_NAME} ${ARDUINO_LIBS} PARENT_SCOPE)
636
+ endfunction()
637
+
638
+ #=============================================================================#
639
+ # [PRIVATE/INTERNAL]
640
+ #
641
+ # setup_arduino_library(VAR_NAME BOARD_ID LIB_PATH COMPILE_FLAGS LINK_FLAGS)
642
+ #
643
+ # VAR_NAME - Vairable wich will hold the generated library names
644
+ # BOARD_ID - Board ID
645
+ # LIB_PATH - Path of the library
646
+ # COMPILE_FLAGS - Compile flags
647
+ # LINK_FLAGS - Link flags
648
+ #
649
+ # Creates an Arduino library, with all it's library dependencies.
650
+ #
651
+ # ${LIB_NAME}_RECURSE controls if the library will recurse
652
+ # when looking for source files.
653
+ #
654
+ #=============================================================================#
655
+
656
+ # For known libraries can list recurse here
657
+ set(Wire_RECURSE True)
658
+ set(Ethernet_RECURSE True)
659
+ set(SD_RECURSE True)
660
+ function(setup_arduino_library VAR_NAME BOARD_ID LIB_PATH COMPILE_FLAGS LINK_FLAGS)
661
+ set(LIB_TARGETS)
662
+
663
+ get_filename_component(LIB_NAME ${LIB_PATH} NAME)
664
+ set(TARGET_LIB_NAME ${BOARD_ID}_${LIB_NAME})
665
+ if(NOT TARGET ${TARGET_LIB_NAME})
666
+ string(REGEX REPLACE ".*/" "" LIB_SHORT_NAME ${LIB_NAME})
667
+
668
+ # Detect if recursion is needed
669
+ if (NOT DEFINED ${LIB_SHORT_NAME}_RECURSE)
670
+ set(${LIB_SHORT_NAME}_RECURSE False)
671
+ endif()
672
+
673
+ find_sources(LIB_SRCS ${LIB_PATH} ${${LIB_SHORT_NAME}_RECURSE})
674
+ if(LIB_SRCS)
675
+
676
+ arduino_debug_msg("Generating Arduino ${LIB_NAME} library")
677
+ add_library(${TARGET_LIB_NAME} STATIC ${LIB_SRCS})
678
+
679
+ get_arduino_flags(ARDUINO_COMPILE_FLAGS ARDUINO_LINK_FLAGS ${BOARD_ID} FALSE)
680
+
681
+ find_arduino_libraries(LIB_DEPS "${LIB_SRCS}")
682
+
683
+ foreach(LIB_DEP ${LIB_DEPS})
684
+ setup_arduino_library(DEP_LIB_SRCS ${BOARD_ID} ${LIB_DEP} "${COMPILE_FLAGS}" "${LINK_FLAGS}")
685
+ list(APPEND LIB_TARGETS ${DEP_LIB_SRCS})
686
+ endforeach()
687
+
688
+ set_target_properties(${TARGET_LIB_NAME} PROPERTIES
689
+ COMPILE_FLAGS "${ARDUINO_COMPILE_FLAGS} -I\"${LIB_PATH}\" -I\"${LIB_PATH}/utility\" ${COMPILE_FLAGS}"
690
+ LINK_FLAGS "${ARDUINO_LINK_FLAGS} ${LINK_FLAGS}")
691
+
692
+ target_link_libraries(${TARGET_LIB_NAME} ${BOARD_ID}_CORE ${LIB_TARGETS})
693
+ list(APPEND LIB_TARGETS ${TARGET_LIB_NAME})
694
+
695
+ endif()
696
+ else()
697
+ # Target already exists, skiping creating
698
+ list(APPEND LIB_TARGETS ${TARGET_LIB_NAME})
699
+ endif()
700
+ if(LIB_TARGETS)
701
+ list(REMOVE_DUPLICATES LIB_TARGETS)
702
+ endif()
703
+ set(${VAR_NAME} ${LIB_TARGETS} PARENT_SCOPE)
704
+ endfunction()
705
+
706
+ #=============================================================================#
707
+ # [PRIVATE/INTERNAL]
708
+ #
709
+ # setup_arduino_libraries(VAR_NAME BOARD_ID SRCS COMPILE_FLAGS LINK_FLAGS)
710
+ #
711
+ # VAR_NAME - Vairable wich will hold the generated library names
712
+ # BOARD_ID - Board ID
713
+ # SRCS - source files
714
+ # COMPILE_FLAGS - Compile flags
715
+ # LINK_FLAGS - Linker flags
716
+ #
717
+ # Finds and creates all dependency libraries based on sources.
718
+ #
719
+ #=============================================================================#
720
+ function(setup_arduino_libraries VAR_NAME BOARD_ID SRCS COMPILE_FLAGS LINK_FLAGS)
721
+ set(LIB_TARGETS)
722
+ find_arduino_libraries(TARGET_LIBS "${SRCS}")
723
+ foreach(TARGET_LIB ${TARGET_LIBS})
724
+ # Create static library instead of returning sources
725
+ setup_arduino_library(LIB_DEPS ${BOARD_ID} ${TARGET_LIB} "${COMPILE_FLAGS}" "${LINK_FLAGS}")
726
+ list(APPEND LIB_TARGETS ${LIB_DEPS})
727
+ endforeach()
728
+ set(${VAR_NAME} ${LIB_TARGETS} PARENT_SCOPE)
729
+ endfunction()
730
+
731
+
732
+ #=============================================================================#
733
+ # [PRIVATE/INTERNAL]
734
+ #
735
+ # setup_arduino_target(TARGET_NAME ALL_SRCS ALL_LIBS COMPILE_FLAGS LINK_FLAGS MANUAL)
736
+ #
737
+ # TARGET_NAME - Target name
738
+ # BOARD_ID - Arduino board ID
739
+ # ALL_SRCS - All sources
740
+ # ALL_LIBS - All libraries
741
+ # COMPILE_FLAGS - Compile flags
742
+ # LINK_FLAGS - Linker flags
743
+ # MANUAL - (Advanced) Only use AVR Libc/Includes
744
+ #
745
+ # Creates an Arduino firmware target.
746
+ #
747
+ #=============================================================================#
748
+ function(setup_arduino_target TARGET_NAME BOARD_ID ALL_SRCS ALL_LIBS COMPILE_FLAGS LINK_FLAGS MANUAL)
749
+
750
+ add_executable(${TARGET_NAME} ${ALL_SRCS})
751
+ set_target_properties(${TARGET_NAME} PROPERTIES SUFFIX ".elf")
752
+
753
+ get_arduino_flags(ARDUINO_COMPILE_FLAGS ARDUINO_LINK_FLAGS ${BOARD_ID} ${MANUAL})
754
+
755
+ set_target_properties(${TARGET_NAME} PROPERTIES
756
+ COMPILE_FLAGS "${ARDUINO_COMPILE_FLAGS} ${COMPILE_FLAGS}"
757
+ LINK_FLAGS "${ARDUINO_LINK_FLAGS} ${LINK_FLAGS}")
758
+ target_link_libraries(${TARGET_NAME} ${ALL_LIBS} "-lc -lm")
759
+
760
+ set(TARGET_PATH ${CMAKE_CURRENT_BINARY_DIR}/${TARGET_NAME})
761
+ add_custom_command(TARGET ${TARGET_NAME} POST_BUILD
762
+ COMMAND ${CMAKE_OBJCOPY}
763
+ ARGS ${ARDUINO_OBJCOPY_EEP_FLAGS}
764
+ ${TARGET_PATH}.elf
765
+ ${TARGET_PATH}.eep
766
+ COMMENT "Generating EEP image"
767
+ VERBATIM)
768
+
769
+ # Convert firmware image to ASCII HEX format
770
+ add_custom_command(TARGET ${TARGET_NAME} POST_BUILD
771
+ COMMAND ${CMAKE_OBJCOPY}
772
+ ARGS ${ARDUINO_OBJCOPY_HEX_FLAGS}
773
+ ${TARGET_PATH}.elf
774
+ ${TARGET_PATH}.hex
775
+ COMMENT "Generating HEX image"
776
+ VERBATIM)
777
+
778
+ # Display target size
779
+ add_custom_command(TARGET ${TARGET_NAME} POST_BUILD
780
+ COMMAND ${CMAKE_COMMAND}
781
+ ARGS -DFIRMWARE_IMAGE=${TARGET_PATH}.hex
782
+ -P ${ARDUINO_SIZE_SCRIPT}
783
+ COMMENT "Calculating image size"
784
+ VERBATIM)
785
+
786
+ # Create ${TARGET_NAME}-size target
787
+ add_custom_target(${TARGET_NAME}-size
788
+ COMMAND ${CMAKE_COMMAND}
789
+ -DFIRMWARE_IMAGE=${TARGET_PATH}.hex
790
+ -P ${ARDUINO_SIZE_SCRIPT}
791
+ DEPENDS ${TARGET_NAME}
792
+ COMMENT "Calculating ${TARGET_NAME} image size")
793
+ endfunction()
794
+
795
+ #=============================================================================#
796
+ # [PRIVATE/INTERNAL]
797
+ #
798
+ # setup_arduino_upload(BOARD_ID TARGET_NAME PORT)
799
+ #
800
+ # BOARD_ID - Arduino board id
801
+ # TARGET_NAME - Target name
802
+ # PORT - Serial port for upload
803
+ # PROGRAMMER_ID - Programmer ID
804
+ # AVRDUDE_FLAGS - avrdude flags
805
+ #
806
+ # Create an upload target (${TARGET_NAME}-upload) for the specified Arduino target.
807
+ #
808
+ #=============================================================================#
809
+ function(setup_arduino_upload BOARD_ID TARGET_NAME PORT PROGRAMMER_ID AVRDUDE_FLAGS)
810
+ setup_arduino_bootloader_upload(${TARGET_NAME} ${BOARD_ID} ${PORT} "${AVRDUDE_FLAGS}")
811
+
812
+ # Add programmer support if defined
813
+ if(PROGRAMMER_ID AND ${PROGRAMMER_ID}.protocol)
814
+ setup_arduino_programmer_burn(${TARGET_NAME} ${BOARD_ID} ${PROGRAMMER_ID} ${PORT} "${AVRDUDE_FLAGS}")
815
+ setup_arduino_bootloader_burn(${TARGET_NAME} ${BOARD_ID} ${PROGRAMMER_ID} ${PORT} "${AVRDUDE_FLAGS}")
816
+ endif()
817
+ endfunction()
818
+
819
+
820
+ #=============================================================================#
821
+ # [PRIVATE/INTERNAL]
822
+ #
823
+ # setup_arduino_bootloader_upload(TARGET_NAME BOARD_ID PORT)
824
+ #
825
+ # TARGET_NAME - target name
826
+ # BOARD_ID - board id
827
+ # PORT - serial port
828
+ # AVRDUDE_FLAGS - avrdude flags (override)
829
+ #
830
+ # Set up target for upload firmware via the bootloader.
831
+ #
832
+ # The target for uploading the firmware is ${TARGET_NAME}-upload .
833
+ #
834
+ #=============================================================================#
835
+ function(setup_arduino_bootloader_upload TARGET_NAME BOARD_ID PORT AVRDUDE_FLAGS)
836
+ set(UPLOAD_TARGET ${TARGET_NAME}-upload)
837
+ set(AVRDUDE_ARGS)
838
+
839
+ setup_arduino_bootloader_args(${BOARD_ID} ${TARGET_NAME} ${PORT} "${AVRDUDE_FLAGS}" AVRDUDE_ARGS)
840
+
841
+ if(NOT AVRDUDE_ARGS)
842
+ message("Could not generate default avrdude bootloader args, aborting!")
843
+ return()
844
+ endif()
845
+
846
+ list(APPEND AVRDUDE_ARGS "-Uflash:w:${TARGET_NAME}.hex")
847
+ add_custom_target(${UPLOAD_TARGET}
848
+ ${ARDUINO_AVRDUDE_PROGRAM}
849
+ ${AVRDUDE_ARGS}
850
+ DEPENDS ${TARGET_NAME})
851
+
852
+ # Global upload target
853
+ if(NOT TARGET upload)
854
+ add_custom_target(upload)
855
+ endif()
856
+
857
+ add_dependencies(upload ${UPLOAD_TARGET})
858
+ endfunction()
859
+
860
+ #=============================================================================#
861
+ # [PRIVATE/INTERNAL]
862
+ #
863
+ # setup_arduino_programmer_burn(TARGET_NAME BOARD_ID PROGRAMMER PORT AVRDUDE_FLAGS)
864
+ #
865
+ # TARGET_NAME - name of target to burn
866
+ # BOARD_ID - board id
867
+ # PROGRAMMER - programmer id
868
+ # PORT - serial port
869
+ # AVRDUDE_FLAGS - avrdude flags (override)
870
+ #
871
+ # Sets up target for burning firmware via a programmer.
872
+ #
873
+ # The target for burning the firmware is ${TARGET_NAME}-burn .
874
+ #
875
+ #=============================================================================#
876
+ function(setup_arduino_programmer_burn TARGET_NAME BOARD_ID PROGRAMMER PORT AVRDUDE_FLAGS)
877
+ set(PROGRAMMER_TARGET ${TARGET_NAME}-burn)
878
+
879
+ set(AVRDUDE_ARGS)
880
+
881
+ setup_arduino_programmer_args(${BOARD_ID} ${PROGRAMMER} ${TARGET_NAME} ${PORT} "${AVRDUDE_FLAGS}" AVRDUDE_ARGS)
882
+
883
+ if(NOT AVRDUDE_ARGS)
884
+ message("Could not generate default avrdude programmer args, aborting!")
885
+ return()
886
+ endif()
887
+
888
+ list(APPEND AVRDUDE_ARGS "-Uflash:w:${TARGET_NAME}.hex")
889
+
890
+ add_custom_target(${PROGRAMMER_TARGET}
891
+ ${ARDUINO_AVRDUDE_PROGRAM}
892
+ ${AVRDUDE_ARGS}
893
+ DEPENDS ${TARGET_NAME})
894
+ endfunction()
895
+
896
+ #=============================================================================#
897
+ # [PRIVATE/INTERNAL]
898
+ #
899
+ # setup_arduino_bootloader_burn(TARGET_NAME BOARD_ID PROGRAMMER PORT AVRDUDE_FLAGS)
900
+ #
901
+ # TARGET_NAME - name of target to burn
902
+ # BOARD_ID - board id
903
+ # PROGRAMMER - programmer id
904
+ # PORT - serial port
905
+ # AVRDUDE_FLAGS - avrdude flags (override)
906
+ #
907
+ # Create a target for burning a bootloader via a programmer.
908
+ #
909
+ # The target for burning the bootloader is ${TARGET_NAME}-burn-bootloader
910
+ #
911
+ #=============================================================================#
912
+ function(setup_arduino_bootloader_burn TARGET_NAME BOARD_ID PROGRAMMER PORT AVRDUDE_FLAGS)
913
+ set(BOOTLOADER_TARGET ${TARGET_NAME}-burn-bootloader)
914
+
915
+ set(AVRDUDE_ARGS)
916
+
917
+ setup_arduino_programmer_args(${BOARD_ID} ${PROGRAMMER} ${TARGET_NAME} ${PORT} "${AVRDUDE_FLAGS}" AVRDUDE_ARGS)
918
+
919
+ if(NOT AVRDUDE_ARGS)
920
+ message("Could not generate default avrdude programmer args, aborting!")
921
+ return()
922
+ endif()
923
+
924
+ foreach( ITEM unlock_bits high_fuses low_fuses path file)
925
+ if(NOT ${BOARD_ID}.bootloader.${ITEM})
926
+ message("Missing ${BOARD_ID}.bootloader.${ITEM}, not creating bootloader burn target ${BOOTLOADER_TARGET}.")
927
+ return()
928
+ endif()
929
+ endforeach()
930
+
931
+ if(NOT EXISTS "${ARDUINO_BOOTLOADERS_PATH}/${${BOARD_ID}.bootloader.path}/${${BOARD_ID}.bootloader.file}")
932
+ message("${ARDUINO_BOOTLOADERS_PATH}/${${BOARD_ID}.bootloader.path}/${${BOARD_ID}.bootloader.file}")
933
+ message("Missing bootloader image, not creating bootloader burn target ${BOOTLOADER_TARGET}.")
934
+ return()
935
+ endif()
936
+
937
+ # Erase the chip
938
+ list(APPEND AVRDUDE_ARGS "-e")
939
+
940
+ # Set unlock bits and fuses (because chip is going to be erased)
941
+ list(APPEND AVRDUDE_ARGS "-Ulock:w:${${BOARD_ID}.bootloader.unlock_bits}:m")
942
+ if(${BOARD_ID}.bootloader.extended_fuses)
943
+ list(APPEND AVRDUDE_ARGS "-Uefuse:w:${${BOARD_ID}.bootloader.extended_fuses}:m")
944
+ endif()
945
+ list(APPEND AVRDUDE_ARGS
946
+ "-Uhfuse:w:${${BOARD_ID}.bootloader.high_fuses}:m"
947
+ "-Ulfuse:w:${${BOARD_ID}.bootloader.low_fuses}:m")
948
+
949
+ # Set bootloader image
950
+ list(APPEND AVRDUDE_ARGS "-Uflash:w:${${BOARD_ID}.bootloader.file}:i")
951
+
952
+ # Set lockbits
953
+ list(APPEND AVRDUDE_ARGS "-Ulock:w:${${BOARD_ID}.bootloader.lock_bits}:m")
954
+
955
+ # Create burn bootloader target
956
+ add_custom_target(${BOOTLOADER_TARGET}
957
+ ${ARDUINO_AVRDUDE_PROGRAM}
958
+ ${AVRDUDE_ARGS}
959
+ WORKING_DIRECTORY ${ARDUINO_BOOTLOADERS_PATH}/${${BOARD_ID}.bootloader.path}
960
+ DEPENDS ${TARGET_NAME})
961
+ endfunction()
962
+
963
+ #=============================================================================#
964
+ # [PRIVATE/INTERNAL]
965
+ #
966
+ # setup_arduino_programmer_args(BOARD_ID PROGRAMMER TARGET_NAME PORT AVRDUDE_FLAGS OUTPUT_VAR)
967
+ #
968
+ # BOARD_ID - board id
969
+ # PROGRAMMER - programmer id
970
+ # TARGET_NAME - target name
971
+ # PORT - serial port
972
+ # AVRDUDE_FLAGS - avrdude flags (override)
973
+ # OUTPUT_VAR - name of output variable for result
974
+ #
975
+ # Sets up default avrdude settings for burning firmware via a programmer.
976
+ #=============================================================================#
977
+ function(setup_arduino_programmer_args BOARD_ID PROGRAMMER TARGET_NAME PORT AVRDUDE_FLAGS OUTPUT_VAR)
978
+ set(AVRDUDE_ARGS ${${OUTPUT_VAR}})
979
+
980
+ if(NOT AVRDUDE_FLAGS)
981
+ set(AVRDUDE_FLAGS ${ARDUINO_AVRDUDE_FLAGS})
982
+ endif()
983
+
984
+ list(APPEND AVRDUDE_ARGS "-C${ARDUINO_AVRDUDE_CONFIG_PATH}")
985
+
986
+ #TODO: Check mandatory settings before continuing
987
+ if(NOT ${PROGRAMMER}.protocol)
988
+ message(FATAL_ERROR "Missing ${PROGRAMMER}.protocol, aborting!")
989
+ endif()
990
+
991
+ list(APPEND AVRDUDE_ARGS "-c${${PROGRAMMER}.protocol}") # Set programmer
992
+
993
+ if(${PROGRAMMER}.communication STREQUAL "usb")
994
+ list(APPEND AVRDUDE_ARGS "-Pusb") # Set USB as port
995
+ elseif(${PROGRAMMER}.communication STREQUAL "serial")
996
+ list(APPEND AVRDUDE_ARGS "-P${PORT}") # Set port
997
+ if(${PROGRAMMER}.speed)
998
+ list(APPEND AVRDUDE_ARGS "-b${${PROGRAMMER}.speed}") # Set baud rate
999
+ endif()
1000
+ endif()
1001
+
1002
+ if(${PROGRAMMER}.force)
1003
+ list(APPEND AVRDUDE_ARGS "-F") # Set force
1004
+ endif()
1005
+
1006
+ if(${PROGRAMMER}.delay)
1007
+ list(APPEND AVRDUDE_ARGS "-i${${PROGRAMMER}.delay}") # Set delay
1008
+ endif()
1009
+
1010
+ list(APPEND AVRDUDE_ARGS "-p${${BOARD_ID}.build.mcu}") # MCU Type
1011
+
1012
+ list(APPEND AVRDUDE_ARGS ${AVRDUDE_FLAGS})
1013
+
1014
+ set(${OUTPUT_VAR} ${AVRDUDE_ARGS} PARENT_SCOPE)
1015
+ endfunction()
1016
+
1017
+ #=============================================================================#
1018
+ # [PRIVATE/INTERNAL]
1019
+ #
1020
+ # setup_arduino_bootloader_args(BOARD_ID TARGET_NAME PORT AVRDUDE_FLAGS OUTPUT_VAR)
1021
+ #
1022
+ # BOARD_ID - board id
1023
+ # TARGET_NAME - target name
1024
+ # PORT - serial port
1025
+ # AVRDUDE_FLAGS - avrdude flags (override)
1026
+ # OUTPUT_VAR - name of output variable for result
1027
+ #
1028
+ # Sets up default avrdude settings for uploading firmware via the bootloader.
1029
+ #=============================================================================#
1030
+ function(setup_arduino_bootloader_args BOARD_ID TARGET_NAME PORT AVRDUDE_FLAGS OUTPUT_VAR)
1031
+ set(AVRDUDE_ARGS ${${OUTPUT_VAR}})
1032
+
1033
+ if(NOT AVRDUDE_FLAGS)
1034
+ set(AVRDUDE_FLAGS ${ARDUINO_AVRDUDE_FLAGS})
1035
+ endif()
1036
+
1037
+ list(APPEND AVRDUDE_ARGS
1038
+ "-C${ARDUINO_AVRDUDE_CONFIG_PATH}" # avrdude config
1039
+ "-p${${BOARD_ID}.build.mcu}" # MCU Type
1040
+ )
1041
+
1042
+ # Programmer
1043
+ if(${BOARD_ID}.upload.protocol STREQUAL "stk500")
1044
+ list(APPEND AVRDUDE_ARGS "-cstk500v1")
1045
+ else()
1046
+ list(APPEND AVRDUDE_ARGS "-c${${BOARD_ID}.upload.protocol}")
1047
+ endif()
1048
+
1049
+ list(APPEND AVRDUDE_ARGS
1050
+ "-b${${BOARD_ID}.upload.speed}" # Baud rate
1051
+ "-P${PORT}" # Serial port
1052
+ "-D" # Dont erase
1053
+ )
1054
+
1055
+ list(APPEND AVRDUDE_ARGS ${AVRDUDE_FLAGS})
1056
+
1057
+ set(${OUTPUT_VAR} ${AVRDUDE_ARGS} PARENT_SCOPE)
1058
+ endfunction()
1059
+
1060
+ #=============================================================================#
1061
+ # [PRIVATE/INTERNAL]
1062
+ #
1063
+ # find_sources(VAR_NAME LIB_PATH RECURSE)
1064
+ #
1065
+ # VAR_NAME - Variable name that will hold the detected sources
1066
+ # LIB_PATH - The base path
1067
+ # RECURSE - Whether or not to recurse
1068
+ #
1069
+ # Finds all C/C++ sources located at the specified path.
1070
+ #
1071
+ #=============================================================================#
1072
+ function(find_sources VAR_NAME LIB_PATH RECURSE)
1073
+ set(FILE_SEARCH_LIST
1074
+ ${LIB_PATH}/*.cpp
1075
+ ${LIB_PATH}/*.c
1076
+ ${LIB_PATH}/*.cc
1077
+ ${LIB_PATH}/*.cxx
1078
+ ${LIB_PATH}/*.h
1079
+ ${LIB_PATH}/*.hh
1080
+ ${LIB_PATH}/*.hxx)
1081
+
1082
+ if(RECURSE)
1083
+ file(GLOB_RECURSE LIB_FILES ${FILE_SEARCH_LIST})
1084
+ else()
1085
+ file(GLOB LIB_FILES ${FILE_SEARCH_LIST})
1086
+ endif()
1087
+
1088
+ if(LIB_FILES)
1089
+ set(${VAR_NAME} ${LIB_FILES} PARENT_SCOPE)
1090
+ endif()
1091
+ endfunction()
1092
+
1093
+ #=============================================================================#
1094
+ # [PRIVATE/INTERNAL]
1095
+ #
1096
+ # setup_serial_target(TARGET_NAME CMD)
1097
+ #
1098
+ # TARGET_NAME - Target name
1099
+ # CMD - Serial terminal command
1100
+ #
1101
+ # Creates a target (${TARGET_NAME}-serial) for launching the serial termnial.
1102
+ #
1103
+ #=============================================================================#
1104
+ function(setup_serial_target TARGET_NAME CMD SERIAL_PORT)
1105
+ string(CONFIGURE "${CMD}" FULL_CMD @ONLY)
1106
+ add_custom_target(${TARGET_NAME}-serial
1107
+ COMMAND ${FULL_CMD})
1108
+ endfunction()
1109
+
1110
+
1111
+ #=============================================================================#
1112
+ # [PRIVATE/INTERNAL]
1113
+ #
1114
+ # detect_arduino_version(VAR_NAME)
1115
+ #
1116
+ # VAR_NAME - Variable name where the detected version will be saved
1117
+ #
1118
+ # Detects the Arduino SDK Version based on the revisions.txt file. The
1119
+ # following variables will be generated:
1120
+ #
1121
+ # ${VAR_NAME} -> the full version (major.minor.patch)
1122
+ # ${VAR_NAME}_MAJOR -> the major version
1123
+ # ${VAR_NAME}_MINOR -> the minor version
1124
+ # ${VAR_NAME}_PATCH -> the patch version
1125
+ #
1126
+ #=============================================================================#
1127
+ function(detect_arduino_version VAR_NAME)
1128
+ if(ARDUINO_VERSION_PATH)
1129
+ file(READ ${ARDUINO_VERSION_PATH} RAW_VERSION)
1130
+ if("${RAW_VERSION}" MATCHES " *[0]+([0-9]+)")
1131
+ set(PARSED_VERSION 0.${CMAKE_MATCH_1}.0)
1132
+ elseif("${RAW_VERSION}" MATCHES "[ ]*([0-9]+[.][0-9]+[.][0-9]+)")
1133
+ set(PARSED_VERSION ${CMAKE_MATCH_1})
1134
+ elseif("${RAW_VERSION}" MATCHES "[ ]*([0-9]+[.][0-9]+)")
1135
+ set(PARSED_VERSION ${CMAKE_MATCH_1}.0)
1136
+ endif()
1137
+
1138
+ if(NOT PARSED_VERSION STREQUAL "")
1139
+ string(REPLACE "." ";" SPLIT_VERSION ${PARSED_VERSION})
1140
+ list(GET SPLIT_VERSION 0 SPLIT_VERSION_MAJOR)
1141
+ list(GET SPLIT_VERSION 1 SPLIT_VERSION_MINOR)
1142
+ list(GET SPLIT_VERSION 2 SPLIT_VERSION_PATCH)
1143
+
1144
+ set(${VAR_NAME} "${PARSED_VERSION}" PARENT_SCOPE)
1145
+ set(${VAR_NAME}_MAJOR "${SPLIT_VERSION_MAJOR}" PARENT_SCOPE)
1146
+ set(${VAR_NAME}_MINOR "${SPLIT_VERSION_MINOR}" PARENT_SCOPE)
1147
+ set(${VAR_NAME}_PATCH "${SPLIT_VERSION_PATCH}" PARENT_SCOPE)
1148
+ endif()
1149
+ endif()
1150
+ endfunction()
1151
+
1152
+
1153
+ #=============================================================================#
1154
+ # [PRIVATE/INTERNAL]
1155
+ #
1156
+ # load_arduino_style_settings(SETTINGS_LIST SETTINGS_PATH)
1157
+ #
1158
+ # SETTINGS_LIST - Variable name of settings list
1159
+ # SETTINGS_PATH - File path of settings file to load.
1160
+ #
1161
+ # Load a Arduino style settings file into the cache.
1162
+ #
1163
+ # Examples of this type of settings file is the boards.txt and
1164
+ # programmers.txt files located in ${ARDUINO_SDK}/hardware/arduino.
1165
+ #
1166
+ # Settings have to following format:
1167
+ #
1168
+ # entry.setting[.subsetting] = value
1169
+ #
1170
+ # where [.subsetting] is optional
1171
+ #
1172
+ # For example, the following settings:
1173
+ #
1174
+ # uno.name=Arduino Uno
1175
+ # uno.upload.protocol=stk500
1176
+ # uno.upload.maximum_size=32256
1177
+ # uno.build.mcu=atmega328p
1178
+ # uno.build.core=arduino
1179
+ #
1180
+ # will generate the follwoing equivalent CMake variables:
1181
+ #
1182
+ # set(uno.name "Arduino Uno")
1183
+ # set(uno.upload.protocol "stk500")
1184
+ # set(uno.upload.maximum_size "32256")
1185
+ # set(uno.build.mcu "atmega328p")
1186
+ # set(uno.build.core "arduino")
1187
+ #
1188
+ # set(uno.SETTINGS name upload build) # List of settings for uno
1189
+ # set(uno.upload.SUBSETTINGS protocol maximum_size) # List of sub-settings for uno.upload
1190
+ # set(uno.build.SUBSETTINGS mcu core) # List of sub-settings for uno.build
1191
+ #
1192
+ # The ${ENTRY_NAME}.SETTINGS variable lists all settings for the entry, while
1193
+ # ${ENTRY_NAME}.SUBSETTINGS variables lists all settings for a sub-setting of
1194
+ # a entry setting pair.
1195
+ #
1196
+ # These variables are generated in order to be able to programatically traverse
1197
+ # all settings (for a example see print_board_settings() function).
1198
+ #
1199
+ #=============================================================================#
1200
+ function(LOAD_ARDUINO_STYLE_SETTINGS SETTINGS_LIST SETTINGS_PATH)
1201
+
1202
+ if(NOT ${SETTINGS_LIST} AND EXISTS ${SETTINGS_PATH})
1203
+ file(STRINGS ${SETTINGS_PATH} FILE_ENTRIES) # Settings file split into lines
1204
+
1205
+ foreach(FILE_ENTRY ${FILE_ENTRIES})
1206
+ if("${FILE_ENTRY}" MATCHES "^[^#]+=.*")
1207
+ string(REGEX MATCH "^[^=]+" SETTING_NAME ${FILE_ENTRY})
1208
+ string(REGEX MATCH "[^=]+$" SETTING_VALUE ${FILE_ENTRY})
1209
+ string(REPLACE "." ";" ENTRY_NAME_TOKENS ${SETTING_NAME})
1210
+ string(STRIP "${SETTING_VALUE}" SETTING_VALUE)
1211
+
1212
+ list(LENGTH ENTRY_NAME_TOKENS ENTRY_NAME_TOKENS_LEN)
1213
+
1214
+ # Add entry to settings list if it does not exist
1215
+ list(GET ENTRY_NAME_TOKENS 0 ENTRY_NAME)
1216
+ list(FIND ${SETTINGS_LIST} ${ENTRY_NAME} ENTRY_NAME_INDEX)
1217
+ if(ENTRY_NAME_INDEX LESS 0)
1218
+ # Add entry to main list
1219
+ list(APPEND ${SETTINGS_LIST} ${ENTRY_NAME})
1220
+ endif()
1221
+
1222
+ # Add entry setting to entry settings list if it does not exist
1223
+ set(ENTRY_SETTING_LIST ${ENTRY_NAME}.SETTINGS)
1224
+ list(GET ENTRY_NAME_TOKENS 1 ENTRY_SETTING)
1225
+ list(FIND ${ENTRY_SETTING_LIST} ${ENTRY_SETTING} ENTRY_SETTING_INDEX)
1226
+ if(ENTRY_SETTING_INDEX LESS 0)
1227
+ # Add setting to entry
1228
+ list(APPEND ${ENTRY_SETTING_LIST} ${ENTRY_SETTING})
1229
+ set(${ENTRY_SETTING_LIST} ${${ENTRY_SETTING_LIST}}
1230
+ CACHE INTERNAL "Arduino ${ENTRY_NAME} Board settings list")
1231
+ endif()
1232
+
1233
+ set(FULL_SETTING_NAME ${ENTRY_NAME}.${ENTRY_SETTING})
1234
+
1235
+ # Add entry sub-setting to entry sub-settings list if it does not exists
1236
+ if(ENTRY_NAME_TOKENS_LEN GREATER 2)
1237
+ set(ENTRY_SUBSETTING_LIST ${ENTRY_NAME}.${ENTRY_SETTING}.SUBSETTINGS)
1238
+ list(GET ENTRY_NAME_TOKENS 2 ENTRY_SUBSETTING)
1239
+ list(FIND ${ENTRY_SUBSETTING_LIST} ${ENTRY_SUBSETTING} ENTRY_SUBSETTING_INDEX)
1240
+ if(ENTRY_SUBSETTING_INDEX LESS 0)
1241
+ list(APPEND ${ENTRY_SUBSETTING_LIST} ${ENTRY_SUBSETTING})
1242
+ set(${ENTRY_SUBSETTING_LIST} ${${ENTRY_SUBSETTING_LIST}}
1243
+ CACHE INTERNAL "Arduino ${ENTRY_NAME} Board sub-settings list")
1244
+ endif()
1245
+ set(FULL_SETTING_NAME ${FULL_SETTING_NAME}.${ENTRY_SUBSETTING})
1246
+ endif()
1247
+
1248
+ # Save setting value
1249
+ set(${FULL_SETTING_NAME} ${SETTING_VALUE}
1250
+ CACHE INTERNAL "Arduino ${ENTRY_NAME} Board setting")
1251
+
1252
+
1253
+ endif()
1254
+ endforeach()
1255
+ set(${SETTINGS_LIST} ${${SETTINGS_LIST}}
1256
+ CACHE STRING "List of detected Arduino Board configurations")
1257
+ mark_as_advanced(${SETTINGS_LIST})
1258
+ endif()
1259
+ endfunction()
1260
+
1261
+ #=============================================================================#
1262
+ # print_settings(ENTRY_NAME)
1263
+ #
1264
+ # ENTRY_NAME - name of entry
1265
+ #
1266
+ # Print the entry settings (see load_arduino_syle_settings()).
1267
+ #
1268
+ #=============================================================================#
1269
+ function(PRINT_SETTINGS ENTRY_NAME)
1270
+ if(${ENTRY_NAME}.SETTINGS)
1271
+
1272
+ foreach(ENTRY_SETTING ${${ENTRY_NAME}.SETTINGS})
1273
+ if(${ENTRY_NAME}.${ENTRY_SETTING})
1274
+ message(STATUS " ${ENTRY_NAME}.${ENTRY_SETTING}=${${ENTRY_NAME}.${ENTRY_SETTING}}")
1275
+ endif()
1276
+ if(${ENTRY_NAME}.${ENTRY_SETTING}.SUBSETTINGS)
1277
+ foreach(ENTRY_SUBSETTING ${${ENTRY_NAME}.${ENTRY_SETTING}.SUBSETTINGS})
1278
+ if(${ENTRY_NAME}.${ENTRY_SETTING}.${ENTRY_SUBSETTING})
1279
+ message(STATUS " ${ENTRY_NAME}.${ENTRY_SETTING}.${ENTRY_SUBSETTING}=${${ENTRY_NAME}.${ENTRY_SETTING}.${ENTRY_SUBSETTING}}")
1280
+ endif()
1281
+ endforeach()
1282
+ endif()
1283
+ message(STATUS "")
1284
+ endforeach()
1285
+ endif()
1286
+ endfunction()
1287
+
1288
+ #=============================================================================#
1289
+ # [PRIVATE/INTERNAL]
1290
+ #
1291
+ # print_list(SETTINGS_LIST)
1292
+ #
1293
+ # SETTINGS_LIST - Variables name of settings list
1294
+ #
1295
+ # Print list settings and names (see load_arduino_syle_settings()).
1296
+ #=============================================================================#
1297
+ function(PRINT_LIST SETTINGS_LIST)
1298
+ if(${SETTINGS_LIST})
1299
+ set(MAX_LENGTH 0)
1300
+ foreach(ENTRY_NAME ${${SETTINGS_LIST}})
1301
+ string(LENGTH "${ENTRY_NAME}" CURRENT_LENGTH)
1302
+ if(CURRENT_LENGTH GREATER MAX_LENGTH)
1303
+ set(MAX_LENGTH ${CURRENT_LENGTH})
1304
+ endif()
1305
+ endforeach()
1306
+ foreach(ENTRY_NAME ${${SETTINGS_LIST}})
1307
+ string(LENGTH "${ENTRY_NAME}" CURRENT_LENGTH)
1308
+ math(EXPR PADDING_LENGTH "${MAX_LENGTH}-${CURRENT_LENGTH}")
1309
+ set(PADDING "")
1310
+ foreach(X RANGE ${PADDING_LENGTH})
1311
+ set(PADDING "${PADDING} ")
1312
+ endforeach()
1313
+ message(STATUS " ${PADDING}${ENTRY_NAME}: ${${ENTRY_NAME}.name}")
1314
+ endforeach()
1315
+ endif()
1316
+ endfunction()
1317
+
1318
+ #=============================================================================#
1319
+ # [PRIVATE/INTERNAL]
1320
+ #
1321
+ # setup_arduino_example(TARGET_NAME LIBRARY_NAME EXAMPLE_NAME OUTPUT_VAR)
1322
+ #
1323
+ # TARGET_NAME - Target name
1324
+ # LIBRARY_NAME - Library name
1325
+ # EXAMPLE_NAME - Example name
1326
+ # OUTPUT_VAR - Variable name to save sketch path.
1327
+ #
1328
+ # Creates a Arduino example from a the specified library.
1329
+ #=============================================================================#
1330
+ function(SETUP_ARDUINO_EXAMPLE TARGET_NAME LIBRARY_NAME EXAMPLE_NAME OUTPUT_VAR)
1331
+ set(EXAMPLE_SKETCH_PATH )
1332
+
1333
+ get_property(LIBRARY_SEARCH_PATH
1334
+ DIRECTORY # Property Scope
1335
+ PROPERTY LINK_DIRECTORIES)
1336
+ foreach(LIB_SEARCH_PATH ${LIBRARY_SEARCH_PATH} ${ARDUINO_LIBRARIES_PATH} ${CMAKE_CURRENT_SOURCE_DIR} ${CMAKE_CURRENT_SOURCE_DIR}/libraries)
1337
+ if(EXISTS "${LIB_SEARCH_PATH}/${LIBRARY_NAME}/examples/${EXAMPLE_NAME}")
1338
+ set(EXAMPLE_SKETCH_PATH "${LIB_SEARCH_PATH}/${LIBRARY_NAME}/examples/${EXAMPLE_NAME}")
1339
+ break()
1340
+ endif()
1341
+ endforeach()
1342
+
1343
+ if(EXAMPLE_SKETCH_PATH)
1344
+ setup_arduino_sketch(${TARGET_NAME} ${EXAMPLE_SKETCH_PATH} SKETCH_CPP)
1345
+ set("${OUTPUT_VAR}" ${${OUTPUT_VAR}} ${SKETCH_CPP} PARENT_SCOPE)
1346
+ else()
1347
+ message(FATAL_ERROR "Could not find example ${EXAMPLE_NAME} from library ${LIBRARY_NAME}")
1348
+ endif()
1349
+ endfunction()
1350
+
1351
+ #=============================================================================#
1352
+ # [PRIVATE/INTERNAL]
1353
+ #
1354
+ # setup_arduino_sketch(TARGET_NAME SKETCH_PATH OUTPUT_VAR)
1355
+ #
1356
+ # TARGET_NAME - Target name
1357
+ # SKETCH_PATH - Path to sketch directory
1358
+ # OUTPUT_VAR - Variable name where to save generated sketch source
1359
+ #
1360
+ # Generates C++ sources from Arduino Sketch.
1361
+ #=============================================================================#
1362
+ function(SETUP_ARDUINO_SKETCH TARGET_NAME SKETCH_PATH OUTPUT_VAR)
1363
+ get_filename_component(SKETCH_NAME "${SKETCH_PATH}" NAME)
1364
+ get_filename_component(SKETCH_PATH "${SKETCH_PATH}" ABSOLUTE)
1365
+
1366
+ if(EXISTS "${SKETCH_PATH}")
1367
+ set(SKETCH_CPP ${CMAKE_CURRENT_BINARY_DIR}/${TARGET_NAME}_${SKETCH_NAME}.cpp)
1368
+
1369
+ if (IS_DIRECTORY "${SKETCH_PATH}")
1370
+ # Sketch directory specified, try to find main sketch...
1371
+ set(MAIN_SKETCH ${SKETCH_PATH}/${SKETCH_NAME})
1372
+
1373
+ if(EXISTS "${MAIN_SKETCH}.pde")
1374
+ set(MAIN_SKETCH "${MAIN_SKETCH}.pde")
1375
+ elseif(EXISTS "${MAIN_SKETCH}.ino")
1376
+ set(MAIN_SKETCH "${MAIN_SKETCH}.ino")
1377
+ else()
1378
+ message(FATAL_ERROR "Could not find main sketch (${SKETCH_NAME}.pde or ${SKETCH_NAME}.ino) at ${SKETCH_PATH}! Please specify the main sketch file path instead of directory.")
1379
+ endif()
1380
+ else()
1381
+ # Sektch file specified, assuming parent directory as sketch directory
1382
+ set(MAIN_SKETCH ${SKETCH_PATH})
1383
+ get_filename_component(SKETCH_PATH "${SKETCH_PATH}" PATH)
1384
+ endif()
1385
+ arduino_debug_msg("sketch: ${MAIN_SKETCH}")
1386
+
1387
+ # Find all sketch files
1388
+ file(GLOB SKETCH_SOURCES ${SKETCH_PATH}/*.pde ${SKETCH_PATH}/*.ino)
1389
+ list(REMOVE_ITEM SKETCH_SOURCES ${MAIN_SKETCH})
1390
+ list(SORT SKETCH_SOURCES)
1391
+
1392
+ generate_cpp_from_sketch("${MAIN_SKETCH}" "${SKETCH_SOURCES}" "${SKETCH_CPP}")
1393
+
1394
+ # Regenerate build system if sketch changes
1395
+ add_custom_command(OUTPUT ${SKETCH_CPP}
1396
+ COMMAND ${CMAKE_COMMAND} ${CMAKE_SOURCE_DIR}
1397
+ WORKING_DIRECTORY ${CMAKE_BINARY_DIR}
1398
+ DEPENDS ${MAIN_SKETCH} ${SKETCH_SOURCES}
1399
+ COMMENT "Regnerating ${SKETCH_NAME} Sketch")
1400
+ set_source_files_properties(${SKETCH_CPP} PROPERTIES GENERATED TRUE)
1401
+
1402
+ set("${OUTPUT_VAR}" ${${OUTPUT_VAR}} ${SKETCH_CPP} PARENT_SCOPE)
1403
+ else()
1404
+ message(FATAL_ERROR "Sketch does not exist: ${SKETCH_PATH}")
1405
+ endif()
1406
+ endfunction()
1407
+
1408
+
1409
+ #=============================================================================#
1410
+ # [PRIVATE/INTERNAL]
1411
+ #
1412
+ # generate_cpp_from_sketch(MAIN_SKETCH_PATH SKETCH_SOURCES SKETCH_CPP)
1413
+ #
1414
+ # MAIN_SKETCH_PATH - Main sketch file path
1415
+ # SKETCH_SOURCES - Setch source paths
1416
+ # SKETCH_CPP - Name of file to generate
1417
+ #
1418
+ # Generate C++ source file from Arduino sketch files.
1419
+ #=============================================================================#
1420
+ function(GENERATE_CPP_FROM_SKETCH MAIN_SKETCH_PATH SKETCH_SOURCES SKETCH_CPP)
1421
+ file(WRITE ${SKETCH_CPP} "// automatically generated by arduino-cmake\n")
1422
+ file(READ ${MAIN_SKETCH_PATH} MAIN_SKETCH)
1423
+
1424
+ # remove comments
1425
+ remove_comments(MAIN_SKETCH MAIN_SKETCH_NO_COMMENTS)
1426
+
1427
+ # find first statement
1428
+ string(REGEX MATCH "[\n][_a-zA-Z0-9]+[^\n]*" FIRST_STATEMENT "${MAIN_SKETCH_NO_COMMENTS}")
1429
+ string(FIND "${MAIN_SKETCH}" "${FIRST_STATEMENT}" HEAD_LENGTH)
1430
+ if ("${HEAD_LENGTH}" STREQUAL "-1")
1431
+ set(HEAD_LENGTH 0)
1432
+ endif()
1433
+ #message(STATUS "FIRST STATEMENT: ${FIRST_STATEMENT}")
1434
+ #message(STATUS "FIRST STATEMENT POSITION: ${HEAD_LENGTH}")
1435
+ string(LENGTH "${MAIN_SKETCH}" MAIN_SKETCH_LENGTH)
1436
+
1437
+ string(SUBSTRING "${MAIN_SKETCH}" 0 ${HEAD_LENGTH} SKETCH_HEAD)
1438
+ #arduino_debug_msg("SKETCH_HEAD:\n${SKETCH_HEAD}")
1439
+
1440
+ # find the body of the main pde
1441
+ math(EXPR BODY_LENGTH "${MAIN_SKETCH_LENGTH}-${HEAD_LENGTH}")
1442
+ string(SUBSTRING "${MAIN_SKETCH}" "${HEAD_LENGTH}+1" "${BODY_LENGTH}-1" SKETCH_BODY)
1443
+ #arduino_debug_msg("BODY:\n${SKETCH_BODY}")
1444
+
1445
+ # write the file head
1446
+ file(APPEND ${SKETCH_CPP} "#line 1 \"${MAIN_SKETCH_PATH}\"\n${SKETCH_HEAD}")
1447
+
1448
+ # Count head line offset (for GCC error reporting)
1449
+ file(STRINGS ${SKETCH_CPP} SKETCH_HEAD_LINES)
1450
+ list(LENGTH SKETCH_HEAD_LINES SKETCH_HEAD_LINES_COUNT)
1451
+ math(EXPR SKETCH_HEAD_OFFSET "${SKETCH_HEAD_LINES_COUNT}+2")
1452
+
1453
+ # add arduino include header
1454
+ #file(APPEND ${SKETCH_CPP} "\n#line 1 \"autogenerated\"\n")
1455
+ file(APPEND ${SKETCH_CPP} "\n#line ${SKETCH_HEAD_OFFSET} \"${SKETCH_CPP}\"\n")
1456
+ if(ARDUINO_SDK_VERSION VERSION_LESS 1.0)
1457
+ file(APPEND ${SKETCH_CPP} "#include \"WProgram.h\"\n")
1458
+ else()
1459
+ file(APPEND ${SKETCH_CPP} "#include \"Arduino.h\"\n")
1460
+ endif()
1461
+
1462
+ # add function prototypes
1463
+ foreach(SKETCH_SOURCE_PATH ${SKETCH_SOURCES} ${MAIN_SKETCH_PATH})
1464
+ arduino_debug_msg("Sketch: ${SKETCH_SOURCE_PATH}")
1465
+ file(READ ${SKETCH_SOURCE_PATH} SKETCH_SOURCE)
1466
+ remove_comments(SKETCH_SOURCE SKETCH_SOURCE)
1467
+
1468
+ set(ALPHA "a-zA-Z")
1469
+ set(NUM "0-9")
1470
+ set(ALPHANUM "${ALPHA}${NUM}")
1471
+ set(WORD "_${ALPHANUM}")
1472
+ set(LINE_START "(^|[\n])")
1473
+ set(QUALIFIERS "[ \t]*([${ALPHA}]+[ ])*")
1474
+ set(TYPE "[${WORD}]+([ ]*[\n][\t]*|[ ])+")
1475
+ set(FNAME "[${WORD}]+[ ]?[\n]?[\t]*[ ]*")
1476
+ set(FARGS "[(]([\t]*[ ]*[*&]?[ ]?[${WORD}](\\[([${NUM}]+)?\\])*[,]?[ ]*[\n]?)*([,]?[ ]*[\n]?)?[)]")
1477
+ set(BODY_START "([ ]*[\n][\t]*|[ ]|[\n])*{")
1478
+ set(PROTOTYPE_PATTERN "${LINE_START}${QUALIFIERS}${TYPE}${FNAME}${FARGS}${BODY_START}")
1479
+
1480
+ string(REGEX MATCHALL "${PROTOTYPE_PATTERN}" SKETCH_PROTOTYPES "${SKETCH_SOURCE}")
1481
+
1482
+ # Write function prototypes
1483
+ file(APPEND ${SKETCH_CPP} "\n//=== START Forward: ${SKETCH_SOURCE_PATH}\n")
1484
+ foreach(SKETCH_PROTOTYPE ${SKETCH_PROTOTYPES})
1485
+ string(REPLACE "\n" " " SKETCH_PROTOTYPE "${SKETCH_PROTOTYPE}")
1486
+ string(REPLACE "{" "" SKETCH_PROTOTYPE "${SKETCH_PROTOTYPE}")
1487
+ arduino_debug_msg("\tprototype: ${SKETCH_PROTOTYPE};")
1488
+ # " else if(var == other) {" shoudn't be listed as prototype
1489
+ if(NOT SKETCH_PROTOTYPE MATCHES "(if[ ]?[\n]?[\t]*[ ]*[)])")
1490
+ file(APPEND ${SKETCH_CPP} "${SKETCH_PROTOTYPE};\n")
1491
+ else()
1492
+ arduino_debug_msg("\trejected prototype: ${SKETCH_PROTOTYPE};")
1493
+ endif()
1494
+ file(APPEND ${SKETCH_CPP} "${SKETCH_PROTOTYPE};\n")
1495
+ endforeach()
1496
+ file(APPEND ${SKETCH_CPP} "//=== END Forward: ${SKETCH_SOURCE_PATH}\n")
1497
+ endforeach()
1498
+
1499
+ # Write Sketch CPP source
1500
+ get_num_lines("${SKETCH_HEAD}" HEAD_NUM_LINES)
1501
+ file(APPEND ${SKETCH_CPP} "#line ${HEAD_NUM_LINES} \"${MAIN_SKETCH_PATH}\"\n")
1502
+ file(APPEND ${SKETCH_CPP} "\n${SKETCH_BODY}")
1503
+ foreach (SKETCH_SOURCE_PATH ${SKETCH_SOURCES})
1504
+ file(READ ${SKETCH_SOURCE_PATH} SKETCH_SOURCE)
1505
+ file(APPEND ${SKETCH_CPP} "\n//=== START : ${SKETCH_SOURCE_PATH}\n")
1506
+ file(APPEND ${SKETCH_CPP} "#line 1 \"${SKETCH_SOURCE_PATH}\"\n")
1507
+ file(APPEND ${SKETCH_CPP} "${SKETCH_SOURCE}")
1508
+ file(APPEND ${SKETCH_CPP} "\n//=== END : ${SKETCH_SOURCE_PATH}\n")
1509
+ endforeach()
1510
+ endfunction()
1511
+
1512
+ #=============================================================================#
1513
+ # [PRIVATE/INTERNAL]
1514
+ #
1515
+ # setup_arduino_size_script(OUTPUT_VAR)
1516
+ #
1517
+ # OUTPUT_VAR - Output variable that will contain the script path
1518
+ #
1519
+ # Generates script used to display the firmware size.
1520
+ #=============================================================================#
1521
+ function(SETUP_ARDUINO_SIZE_SCRIPT OUTPUT_VAR)
1522
+ set(ARDUINO_SIZE_SCRIPT_PATH ${CMAKE_BINARY_DIR}/CMakeFiles/FirmwareSize.cmake)
1523
+
1524
+ file(WRITE ${ARDUINO_SIZE_SCRIPT_PATH} "
1525
+ set(AVRSIZE_PROGRAM ${AVRSIZE_PROGRAM})
1526
+ set(AVRSIZE_FLAGS --target=ihex -d)
1527
+
1528
+ execute_process(COMMAND \${AVRSIZE_PROGRAM} \${AVRSIZE_FLAGS} \${FIRMWARE_IMAGE}
1529
+ OUTPUT_VARIABLE SIZE_OUTPUT)
1530
+
1531
+ string(STRIP \"\${SIZE_OUTPUT}\" SIZE_OUTPUT)
1532
+
1533
+ # Convert lines into a list
1534
+ string(REPLACE \"\\n\" \";\" SIZE_OUTPUT \"\${SIZE_OUTPUT}\")
1535
+
1536
+ list(GET SIZE_OUTPUT 1 SIZE_ROW)
1537
+
1538
+ if(SIZE_ROW MATCHES \"[ \\t]*[0-9]+[ \\t]*[0-9]+[ \\t]*[0-9]+[ \\t]*([0-9]+)[ \\t]*([0-9a-fA-F]+).*\")
1539
+ message(\"Total size \${CMAKE_MATCH_1} bytes\")
1540
+ endif()")
1541
+
1542
+ set(${OUTPUT_VAR} ${ARDUINO_SIZE_SCRIPT_PATH} PARENT_SCOPE)
1543
+ endfunction()
1544
+
1545
+ #=============================================================================#
1546
+ # [PRIVATE/INTERNAL]
1547
+ #
1548
+ # arduino_debug_on()
1549
+ #
1550
+ # Enables Arduino module debugging.
1551
+ #=============================================================================#
1552
+ function(ARDUINO_DEBUG_ON)
1553
+ set(ARDUINO_DEBUG True PARENT_SCOPE)
1554
+ endfunction()
1555
+
1556
+
1557
+ #=============================================================================#
1558
+ # [PRIVATE/INTERNAL]
1559
+ #
1560
+ # arduino_debug_off()
1561
+ #
1562
+ # Disables Arduino module debugging.
1563
+ #=============================================================================#
1564
+ function(ARDUINO_DEBUG_OFF)
1565
+ set(ARDUINO_DEBUG False PARENT_SCOPE)
1566
+ endfunction()
1567
+
1568
+
1569
+ #=============================================================================#
1570
+ # [PRIVATE/INTERNAL]
1571
+ #
1572
+ # arduino_debug_msg(MSG)
1573
+ #
1574
+ # MSG - Message to print
1575
+ #
1576
+ # Print Arduino debugging information. In order to enable printing
1577
+ # use arduino_debug_on() and to disable use arduino_debug_off().
1578
+ #=============================================================================#
1579
+ function(ARDUINO_DEBUG_MSG MSG)
1580
+ if(ARDUINO_DEBUG)
1581
+ message("## ${MSG}")
1582
+ endif()
1583
+ endfunction()
1584
+
1585
+ #=============================================================================#
1586
+ # [PRIVATE/INTERNAL]
1587
+ #
1588
+ # remove_comments(SRC_VAR OUT_VAR)
1589
+ #
1590
+ # SRC_VAR - variable holding sources
1591
+ # OUT_VAR - variable holding sources with no comments
1592
+ #
1593
+ # Removes all comments from the source code.
1594
+ #=============================================================================#
1595
+ function(REMOVE_COMMENTS SRC_VAR OUT_VAR)
1596
+ string(REGEX REPLACE "[\\./\\\\]" "_" FILE "${NAME}")
1597
+
1598
+ set(SRC ${${SRC_VAR}})
1599
+
1600
+ #message(STATUS "removing comments from: ${FILE}")
1601
+ #file(WRITE "${CMAKE_BINARY_DIR}/${FILE}_pre_remove_comments.txt" ${SRC})
1602
+ #message(STATUS "\n${SRC}")
1603
+
1604
+ # remove all comments
1605
+ string(REGEX REPLACE "([/][/][^\n]*)|([/][\\*]([^\\*]|([\\*]+[^/\\*]))*[\\*]+[/])" "" OUT "${SRC}")
1606
+
1607
+ #file(WRITE "${CMAKE_BINARY_DIR}/${FILE}_post_remove_comments.txt" ${SRC})
1608
+ #message(STATUS "\n${SRC}")
1609
+
1610
+ set(${OUT_VAR} ${OUT} PARENT_SCOPE)
1611
+
1612
+ endfunction()
1613
+
1614
+ #=============================================================================#
1615
+ # [PRIVATE/INTERNAL]
1616
+ #
1617
+ # get_num_lines(DOCUMENT OUTPUT_VAR)
1618
+ #
1619
+ # DOCUMENT - Document contents
1620
+ # OUTPUT_VAR - Variable which will hold the line number count
1621
+ #
1622
+ # Counts the line number of the document.
1623
+ #=============================================================================#
1624
+ function(GET_NUM_LINES DOCUMENT OUTPUT_VAR)
1625
+ string(REGEX MATCHALL "[\n]" MATCH_LIST "${DOCUMENT}")
1626
+ list(LENGTH MATCH_LIST NUM)
1627
+ set(${OUTPUT_VAR} ${NUM} PARENT_SCOPE)
1628
+ endfunction()
1629
+
1630
+ #=============================================================================#
1631
+ # [PRIVATE/INTERNAL]
1632
+ #
1633
+ # required_variables(MSG msg VARS var1 var2 .. varN)
1634
+ #
1635
+ # MSG - Message to be displayed in case of error
1636
+ # VARS - List of variables names to check
1637
+ #
1638
+ # Ensure the specified variables are not empty, otherwise a fatal error is emmited.
1639
+ #=============================================================================#
1640
+ function(REQUIRED_VARIABLES)
1641
+ cmake_parse_arguments(INPUT "" "MSG" "VARS" ${ARGN})
1642
+ error_for_unparsed(INPUT)
1643
+ foreach(VAR ${INPUT_VARS})
1644
+ if ("${${VAR}}" STREQUAL "")
1645
+ message(FATAL_ERROR "${VAR} not set: ${INPUT_MSG}")
1646
+ endif()
1647
+ endforeach()
1648
+ endfunction()
1649
+
1650
+ #=============================================================================#
1651
+ # [PRIVATE/INTERNAL]
1652
+ #
1653
+ # error_for_unparsed(PREFIX)
1654
+ #
1655
+ # PREFIX - Prefix name
1656
+ #
1657
+ # Emit fatal error if there are unparsed argument from cmake_parse_arguments().
1658
+ #=============================================================================#
1659
+ function(ERROR_FOR_UNPARSED PREFIX)
1660
+ set(ARGS "${${PREFIX}_UNPARSED_ARGUMENTS}")
1661
+ if (NOT ( "${ARGS}" STREQUAL "") )
1662
+ message(FATAL_ERROR "unparsed argument: ${ARGS}")
1663
+ endif()
1664
+ endfunction()
1665
+
1666
+
1667
+
1668
+
1669
+
1670
+
1671
+ #=============================================================================#
1672
+ # C Flags
1673
+ #=============================================================================#
1674
+ set(ARDUINO_C_FLAGS "-mcall-prologues -ffunction-sections -fdata-sections")
1675
+ set(CMAKE_C_FLAGS "-g -Os ${ARDUINO_C_FLAGS}" CACHE STRING "")
1676
+ set(CMAKE_C_FLAGS_DEBUG "-g ${ARDUINO_C_FLAGS}" CACHE STRING "")
1677
+ set(CMAKE_C_FLAGS_MINSIZEREL "-Os -DNDEBUG ${ARDUINO_C_FLAGS}" CACHE STRING "")
1678
+ set(CMAKE_C_FLAGS_RELEASE "-Os -DNDEBUG -w ${ARDUINO_C_FLAGS}" CACHE STRING "")
1679
+ set(CMAKE_C_FLAGS_RELWITHDEBINFO "-Os -g -w ${ARDUINO_C_FLAGS}" CACHE STRING "")
1680
+
1681
+ #=============================================================================#
1682
+ # C++ Flags
1683
+ #=============================================================================#
1684
+ set(ARDUINO_CXX_FLAGS "${ARDUINO_C_FLAGS} -fno-exceptions")
1685
+ set(CMAKE_CXX_FLAGS "-g -Os ${ARDUINO_CXX_FLAGS}" CACHE STRING "")
1686
+ set(CMAKE_CXX_FLAGS_DEBUG "-g ${ARDUINO_CXX_FLAGS}" CACHE STRING "")
1687
+ set(CMAKE_CXX_FLAGS_MINSIZEREL "-Os -DNDEBUG ${ARDUINO_CXX_FLAGS}" CACHE STRING "")
1688
+ set(CMAKE_CXX_FLAGS_RELEASE "-Os -DNDEBUG ${ARDUINO_CXX_FLAGS}" CACHE STRING "")
1689
+ set(CMAKE_CXX_FLAGS_RELWITHDEBINFO "-Os -g ${ARDUINO_CXX_FLAGS}" CACHE STRING "")
1690
+
1691
+ #=============================================================================#
1692
+ # Executable Linker Flags #
1693
+ #=============================================================================#
1694
+ set(ARDUINO_LINKER_FLAGS "-Wl,--gc-sections -lm")
1695
+ set(CMAKE_EXE_LINKER_FLAGS "${ARDUINO_LINKER_FLAGS}" CACHE STRING "")
1696
+ set(CMAKE_EXE_LINKER_FLAGS_DEBUG "${ARDUINO_LINKER_FLAGS}" CACHE STRING "")
1697
+ set(CMAKE_EXE_LINKER_FLAGS_MINSIZEREL "${ARDUINO_LINKER_FLAGS}" CACHE STRING "")
1698
+ set(CMAKE_EXE_LINKER_FLAGS_RELEASE "${ARDUINO_LINKER_FLAGS}" CACHE STRING "")
1699
+ set(CMAKE_EXE_LINKER_FLAGS_RELWITHDEBINFO "${ARDUINO_LINKER_FLAGS}" CACHE STRING "")
1700
+
1701
+ #=============================================================================#
1702
+ #=============================================================================#
1703
+ # Shared Lbrary Linker Flags #
1704
+ #=============================================================================#
1705
+ set(CMAKE_SHARED_LINKER_FLAGS "${ARDUINO_LINKER_FLAGS}" CACHE STRING "")
1706
+ set(CMAKE_SHARED_LINKER_FLAGS_DEBUG "${ARDUINO_LINKER_FLAGS}" CACHE STRING "")
1707
+ set(CMAKE_SHARED_LINKER_FLAGS_MINSIZEREL "${ARDUINO_LINKER_FLAGS}" CACHE STRING "")
1708
+ set(CMAKE_SHARED_LINKER_FLAGS_RELEASE "${ARDUINO_LINKER_FLAGS}" CACHE STRING "")
1709
+ set(CMAKE_SHARED_LINKER_FLAGS_RELWITHDEBINFO "${ARDUINO_LINKER_FLAGS}" CACHE STRING "")
1710
+
1711
+ set(CMAKE_MODULE_LINKER_FLAGS "${ARDUINO_LINKER_FLAGS}" CACHE STRING "")
1712
+ set(CMAKE_MODULE_LINKER_FLAGS_DEBUG "${ARDUINO_LINKER_FLAGS}" CACHE STRING "")
1713
+ set(CMAKE_MODULE_LINKER_FLAGS_MINSIZEREL "${ARDUINO_LINKER_FLAGS}" CACHE STRING "")
1714
+ set(CMAKE_MODULE_LINKER_FLAGS_RELEASE "${ARDUINO_LINKER_FLAGS}" CACHE STRING "")
1715
+ set(CMAKE_MODULE_LINKER_FLAGS_RELWITHDEBINFO "${ARDUINO_LINKER_FLAGS}" CACHE STRING "")
1716
+
1717
+
1718
+ #=============================================================================#
1719
+ # Arduino Settings
1720
+ #=============================================================================#
1721
+ set(ARDUINO_OBJCOPY_EEP_FLAGS -O ihex -j .eeprom --set-section-flags=.eeprom=alloc,load
1722
+ --no-change-warnings --change-section-lma .eeprom=0 CACHE STRING "")
1723
+ set(ARDUINO_OBJCOPY_HEX_FLAGS -O ihex -R .eeprom CACHE STRING "")
1724
+ set(ARDUINO_AVRDUDE_FLAGS -V CACHE STRING "")
1725
+
1726
+ #=============================================================================#
1727
+ # Initialization
1728
+ #=============================================================================#
1729
+ if(NOT ARDUINO_FOUND AND ARDUINO_SDK_PATH)
1730
+ find_file(ARDUINO_CORES_PATH
1731
+ NAMES cores
1732
+ PATHS ${ARDUINO_SDK_PATH}
1733
+ PATH_SUFFIXES hardware/arduino
1734
+ DOC "Path to directory containing the Arduino core sources.")
1735
+
1736
+ find_file(ARDUINO_VARIANTS_PATH
1737
+ NAMES variants
1738
+ PATHS ${ARDUINO_SDK_PATH}
1739
+ PATH_SUFFIXES hardware/arduino
1740
+ DOC "Path to directory containing the Arduino variant sources.")
1741
+
1742
+ find_file(ARDUINO_BOOTLOADERS_PATH
1743
+ NAMES bootloaders
1744
+ PATHS ${ARDUINO_SDK_PATH}
1745
+ PATH_SUFFIXES hardware/arduino
1746
+ DOC "Path to directory containing the Arduino bootloader images and sources.")
1747
+
1748
+ find_file(ARDUINO_LIBRARIES_PATH
1749
+ NAMES libraries
1750
+ PATHS ${ARDUINO_SDK_PATH}
1751
+ DOC "Path to directory containing the Arduino libraries.")
1752
+
1753
+ find_file(ARDUINO_BOARDS_PATH
1754
+ NAMES boards.txt
1755
+ PATHS ${ARDUINO_SDK_PATH}
1756
+ PATH_SUFFIXES hardware/arduino
1757
+ DOC "Path to Arduino boards definition file.")
1758
+
1759
+ find_file(ARDUINO_PROGRAMMERS_PATH
1760
+ NAMES programmers.txt
1761
+ PATHS ${ARDUINO_SDK_PATH}
1762
+ PATH_SUFFIXES hardware/arduino
1763
+ DOC "Path to Arduino programmers definition file.")
1764
+
1765
+ find_file(ARDUINO_VERSION_PATH
1766
+ NAMES lib/version.txt
1767
+ PATHS ${ARDUINO_SDK_PATH}
1768
+ DOC "Path to Arduino version file.")
1769
+
1770
+ find_program(ARDUINO_AVRDUDE_PROGRAM
1771
+ NAMES avrdude
1772
+ PATHS ${ARDUINO_SDK_PATH}
1773
+ PATH_SUFFIXES hardware/tools
1774
+ NO_DEFAULT_PATH)
1775
+
1776
+ find_program(ARDUINO_AVRDUDE_PROGRAM
1777
+ NAMES avrdude
1778
+ DOC "Path to avrdude programmer binary.")
1779
+
1780
+ find_program(AVRSIZE_PROGRAM
1781
+ NAMES avr-size)
1782
+
1783
+ find_file(ARDUINO_AVRDUDE_CONFIG_PATH
1784
+ NAMES avrdude.conf
1785
+ PATHS ${ARDUINO_SDK_PATH} /etc/avrdude
1786
+ PATH_SUFFIXES hardware/tools
1787
+ hardware/tools/avr/etc
1788
+ DOC "Path to avrdude programmer configuration file.")
1789
+
1790
+ set(ARDUINO_DEFAULT_BOARD uno CACHE STRING "Default Arduino Board ID when not specified.")
1791
+ set(ARDUINO_DEFAULT_PORT CACHE STRING "Default Arduino port when not specified.")
1792
+ set(ARDUINO_DEFAULT_SERIAL CACHE STRING "Default Arduino Serial command when not specified.")
1793
+ set(ARDUINO_DEFAULT_PROGRAMMER CACHE STRING "Default Arduino Programmer ID when not specified.")
1794
+
1795
+ # Ensure that all required paths are found
1796
+ required_variables(VARS
1797
+ ARDUINO_CORES_PATH
1798
+ ARDUINO_BOOTLOADERS_PATH
1799
+ ARDUINO_LIBRARIES_PATH
1800
+ ARDUINO_BOARDS_PATH
1801
+ ARDUINO_PROGRAMMERS_PATH
1802
+ ARDUINO_VERSION_PATH
1803
+ ARDUINO_AVRDUDE_FLAGS
1804
+ ARDUINO_AVRDUDE_PROGRAM
1805
+ ARDUINO_AVRDUDE_CONFIG_PATH
1806
+ AVRSIZE_PROGRAM
1807
+ MSG "Invalid Arduino SDK path (${ARDUINO_SDK_PATH}).\n")
1808
+
1809
+ detect_arduino_version(ARDUINO_SDK_VERSION)
1810
+ set(ARDUINO_SDK_VERSION ${ARDUINO_SDK_VERSION} CACHE STRING "Arduino SDK Version")
1811
+ set(ARDUINO_SDK_VERSION_MAJOR ${ARDUINO_SDK_VERSION_MAJOR} CACHE STRING "Arduino SDK Major Version")
1812
+ set(ARDUINO_SDK_VERSION_MINOR ${ARDUINO_SDK_VERSION_MINOR} CACHE STRING "Arduino SDK Minor Version")
1813
+ set(ARDUINO_SDK_VERSION_PATCH ${ARDUINO_SDK_VERSION_PATCH} CACHE STRING "Arduino SDK Patch Version")
1814
+
1815
+ if(ARDUINO_SDK_VERSION VERSION_LESS 0.19)
1816
+ message(FATAL_ERROR "Unsupported Arduino SDK (require verion 0.19 or higher)")
1817
+ endif()
1818
+
1819
+ message(STATUS "Arduino SDK version ${ARDUINO_SDK_VERSION}: ${ARDUINO_SDK_PATH}")
1820
+
1821
+ setup_arduino_size_script(ARDUINO_SIZE_SCRIPT)
1822
+ set(ARDUINO_SIZE_SCRIPT ${ARDUINO_SIZE_SCRIPT} CACHE INTERNAL "Arduino Size Script")
1823
+
1824
+ load_board_settings()
1825
+ load_programmers_settings()
1826
+
1827
+ #print_board_list()
1828
+ #print_programmer_list()
1829
+
1830
+ set(ARDUINO_FOUND True CACHE INTERNAL "Arduino Found")
1831
+ mark_as_advanced(
1832
+ ARDUINO_CORES_PATH
1833
+ ARDUINO_VARIANTS_PATH
1834
+ ARDUINO_BOOTLOADERS_PATH
1835
+ ARDUINO_LIBRARIES_PATH
1836
+ ARDUINO_BOARDS_PATH
1837
+ ARDUINO_PROGRAMMERS_PATH
1838
+ ARDUINO_VERSION_PATH
1839
+ ARDUINO_AVRDUDE_FLAGS
1840
+ ARDUINO_AVRDUDE_PROGRAM
1841
+ ARDUINO_AVRDUDE_CONFIG_PATH
1842
+ ARDUINO_OBJCOPY_EEP_FLAGS
1843
+ ARDUINO_OBJCOPY_HEX_FLAGS
1844
+ AVRSIZE_PROGRAM)
1845
+ endif()
1846
+