Skip to content

Commit cef20cf

Browse files
committed
add ability to build a library with mock arduino headers
1 parent d9dee36 commit cef20cf

File tree

8 files changed

+104
-5
lines changed

8 files changed

+104
-5
lines changed

.gitignore

+3
Original file line numberDiff line numberDiff line change
@@ -11,3 +11,6 @@ vendor
1111

1212
# rspec failure tracking
1313
.rspec_status
14+
15+
# C++ stuff
16+
arduino_ci_built.bin

SampleProjects/DoSomething/do-something.cpp

+1
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,4 @@
1+
#include <Arduino.h>
12
#include <do-something.h>
23
int doSomething(void) {
34
millis(); // this line is only here to test that we're able to refer to the builtins

cpp/Arduino.h

+30
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,30 @@
1+
/*
2+
Mock Arduino.h library.
3+
4+
Where possible, variable names from the Arduino library are used to avoid conflicts
5+
6+
*/
7+
8+
9+
#ifndef ARDUINO_CI_ARDUINO
10+
11+
#include "math.h"
12+
#define ARDUINO_CI_ARDUINO
13+
14+
struct unit_test_state {
15+
unsigned long micros;
16+
};
17+
18+
struct unit_test_state godmode {
19+
0, // micros
20+
};
21+
22+
unsigned long millis() {
23+
return godmode.micros / 1000;
24+
}
25+
26+
unsigned long micros() {
27+
return godmode.micros;
28+
}
29+
30+
#endif

cpp/math.h

+41
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,41 @@
1+
//abs
2+
long abs(long x) { return x > 0 ? x : -x; }
3+
double fabs(double x) { return x > 0 ? x : -x; }
4+
5+
//max
6+
long max(long a, long b) { return a > b ? a : b; }
7+
double fmax(double a, double b) { return a > b ? a : b; }
8+
9+
//min
10+
long min(long a, long b) { return a < b ? a : b; }
11+
double fmin(double a, double b) { return a < b ? a : b; }
12+
13+
//constrain
14+
long constrain(long x, long a, long b) { return max(a, min(b, x)); }
15+
double constrain(double x, double a, double b) { return max(a, min(b, x)); }
16+
17+
//map
18+
long map(long x, long in_min, long in_max, long out_min, long out_max)
19+
{
20+
return (x - in_min) * (out_max - out_min) / (in_max - in_min) + out_min;
21+
}
22+
23+
double map(double x, double in_min, double in_max, double out_min, double out_max)
24+
{
25+
return (x - in_min) * (out_max - out_min) / (in_max - in_min) + out_min;
26+
}
27+
28+
//sq
29+
long sq(long x) { return x * x; }
30+
double sq(double x) { return x * x; }
31+
32+
// ??? too lazy to sort these now
33+
//pow
34+
//sqrt
35+
36+
// http://www.ganssle.com/approx.htm
37+
// http://www.ganssle.com/approx/sincos.cpp
38+
//cos
39+
//sin
40+
//tan
41+

exe/ci_system_check.rb

+5
Original file line numberDiff line numberDiff line change
@@ -47,6 +47,11 @@
4747
got_problem = true unless arduino_cmd.verify_sketch(simple_sketch)
4848

4949
library_path = File.join(File.dirname(File.dirname(__FILE__)), "SampleProjects", "DoSomething")
50+
51+
puts "verify a library with arduino mocks"
52+
cpp_library = ArduinoCI::CppLibrary.new(library_path)
53+
got_problem = true unless cpp_library.build(arduino_cmd)
54+
5055
puts "verify the examples of a library (#{library_path})..."
5156
puts " - Install the library"
5257
installed_library_path = arduino_cmd.install_local_library(library_path)

lib/arduino_ci/arduino_installation.rb

+7-5
Original file line numberDiff line numberDiff line change
@@ -49,26 +49,28 @@ def autolocate_osx
4949
]
5050
end
5151

52-
ret.gcc_cmd = [File.join(osx_root, "Java", "hardware", "tools", "avr", "bin", "avr-gcc")]
52+
hardware_dir = File.join(osx_root, "Java", "hardware")
53+
ret.gcc_cmd = [File.join(hardware_dir, "tools", "avr", "bin", "avr-gcc")]
5354
ret
5455
end
5556

5657
def autolocate_linux
58+
forced_avr = File.join(force_install_location, "hardware", "tools", "avr")
5759
if USE_BUILDER
5860
builder_name = "arduino-builder"
5961
cli_place = Host.which(builder_name)
6062
unless cli_place.nil?
6163
ret = ArduinoCmdLinuxBuilder.new
6264
ret.base_cmd = [cli_place]
63-
ret.gcc_cmd = Host.which("avr-gcc")
65+
ret.gcc_cmd = [Host.which("avr-gcc")]
6466
return ret
6567
end
6668

6769
forced_builder = File.join(force_install_location, builder_name)
6870
if File.exist?(forced_builder)
6971
ret = ArduinoCmdLinuxBuilder.new
7072
ret.base_cmd = [forced_builder]
71-
ret.gcc_cmd = [File.join(force_install_location, "hardware", "tools", "avr", "bin", "avr-gcc")]
73+
ret.gcc_cmd = [File.join(forced_avr, "bin", "avr-gcc")]
7274
return ret
7375
end
7476
end
@@ -78,15 +80,15 @@ def autolocate_linux
7880
unless gui_place.nil?
7981
ret = ArduinoCmdLinux.new
8082
ret.base_cmd = [gui_place]
81-
ret.gcc_cmd = Host.which("avr-gcc")
83+
ret.gcc_cmd = [Host.which("avr-gcc")]
8284
return ret
8385
end
8486

8587
forced_arduino = File.join(force_install_location, gui_name)
8688
if File.exist?(forced_arduino)
8789
ret = ArduinoCmdLinux.new
8890
ret.base_cmd = [forced_arduino]
89-
ret.gcc_cmd = [File.join(force_install_location, "hardware", "tools", "avr", "bin", "avr-gcc")]
91+
ret.gcc_cmd = [File.join(forced_avr, "bin", "avr-gcc")]
9092
return ret
9193
end
9294
nil

lib/arduino_ci/cpp_library.rb

+10
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@
33

44
HPP_EXTENSIONS = [".hpp", ".hh", ".h", ".hxx", ".h++"].freeze
55
CPP_EXTENSIONS = [".cpp", ".cc", ".c", ".cxx", ".c++"].freeze
6+
ARDUINO_HEADER_DIR = File.expand_path("../../../cpp", __FILE__)
67

78
module ArduinoCI
89

@@ -24,6 +25,15 @@ def header_dirs
2425
files.map { |path| File.dirname(path) }.uniq
2526
end
2627

28+
def build_args
29+
["-I#{ARDUINO_HEADER_DIR}"] + header_dirs.map { |d| "-I#{d}" } + cpp_files
30+
end
31+
32+
def build(arduino_cmd)
33+
args = ["-c", "-o", "arduino_ci_built.bin"] + build_args
34+
arduino_cmd.run_gcc(*args)
35+
end
36+
2737
end
2838

2939
end

spec/cpp_library_spec.rb

+7
Original file line numberDiff line numberDiff line change
@@ -21,4 +21,11 @@
2121
end
2222
end
2323

24+
context "build" do
25+
arduino_cmd = ArduinoCI::ArduinoInstallation.autolocate!
26+
it "builds libraries" do
27+
expect(cpp_library.build(arduino_cmd)).to be true
28+
end
29+
end
30+
2431
end

0 commit comments

Comments
 (0)