Skip to content

Commit 02382b2

Browse files
author
Ladislas
committed
add automatic library detection
1 parent 6053817 commit 02382b2

File tree

3 files changed

+128
-8
lines changed

3 files changed

+128
-8
lines changed

Arduino.mk

Lines changed: 37 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -736,7 +736,7 @@ ifeq ($(strip $(CHK_SOURCES)),)
736736
$(call show_config_info,No .pde or .ino files found. If you are compiling .c or .cpp files then you need to explicitly include Arduino header files)
737737
else
738738
#TODO: Support more than one file. https://github.com/sudar/Arduino-Makefile/issues/49
739-
$(error Need exactly one .pde or .ino file. This makefile doesn't support multiple .ino/.pde files yet)
739+
$(error Need exactly one .pde or .ino file. This makefile doesn\'t support multiple .ino/.pde files yet)
740740
endif
741741
endif
742742

@@ -763,6 +763,19 @@ else
763763
$(call show_config_info,NO_CORE set so core library will not be built,[MANUAL])
764764
endif
765765

766+
########################################################################
767+
# Automatically find the libraries needed to compile the sketch
768+
769+
ifndef SKETCH_LIBS
770+
SKETCH_LIBS := $(shell $(ARDMK_DIR)/bin/lib-detection $(USER_LIB_PATH) | \
771+
sed -ne 's/SKETCH_LIBS \(.*\) /\1/p')
772+
endif
773+
774+
ifndef SKETCH_LIBS_DEPS
775+
SKETCH_LIBS_DEPS := $(shell $(ARDMK_DIR)/bin/lib-detection $(USER_LIB_PATH) | \
776+
sed -ne 's/SKETCH_LIBS_DEPS \(.*\) /\1/p')
777+
endif
778+
766779
########################################################################
767780
# Determine ARDUINO_LIBS automatically
768781

@@ -772,8 +785,6 @@ ifndef ARDUINO_LIBS
772785
$(shell sed -ne "s/^ *\# *include *[<\"]\(.*\)\.h[>\"]/\1/p" $(LOCAL_SRCS)))
773786
ARDUINO_LIBS += $(filter $(notdir $(wildcard $(ARDUINO_SKETCHBOOK)/libraries/*)), \
774787
$(shell sed -ne "s/^ *\# *include *[<\"]\(.*\)\.h[>\"]/\1/p" $(LOCAL_SRCS)))
775-
ARDUINO_LIBS += $(filter $(notdir $(wildcard $(USER_LIB_PATH)/*)), \
776-
$(shell sed -ne "s/^ *\# *include *[<\"]\(.*\)\.h[>\"]/\1/p" $(LOCAL_SRCS)))
777788
endif
778789

779790
########################################################################
@@ -872,7 +883,10 @@ get_library_files = $(if $(and $(wildcard $(1)/src), $(wildcard $(1)/library.pr
872883
$(wildcard $(1)/*.$(2) $(1)/utility/*.$(2)))
873884

874885
# General arguments
875-
USER_LIBS := $(wildcard $(patsubst %,$(USER_LIB_PATH)/%,$(ARDUINO_LIBS)))
886+
USER_LIBS := $(wildcard $(patsubst %,$(USER_LIB_PATH)/%,$(ARDUINO_LIBS))) \
887+
$(wildcard $(patsubst %,$(USER_LIB_PATH)/%,$(SKETCH_LIBS))) \
888+
$(wildcard $(patsubst %,$(USER_LIB_PATH)/%,$(SKETCH_LIBS_DEPS)))
889+
876890
USER_LIB_NAMES := $(patsubst $(USER_LIB_PATH)/%,%,$(USER_LIBS))
877891

878892
# Let user libraries override system ones.
@@ -1032,17 +1046,32 @@ else
10321046
$(call show_config_info,Size utility: Basic (not AVR-aware),[AUTODETECTED])
10331047
endif
10341048

1035-
ifneq (,$(strip $(ARDUINO_LIBS)))
1049+
ifneq (,$(strip $(SKETCH_LIBS)))
1050+
$(call arduino_output,-)
1051+
$(call show_config_info,SKETCH_LIBS =)
1052+
endif
1053+
1054+
ifneq (,$(strip $(SKETCH_LIBS)))
1055+
$(foreach lib,$(SKETCH_LIBS),$(call show_config_info, $(lib),[USER]))
1056+
endif
1057+
1058+
ifneq (,$(strip $(SKETCH_LIBS_DEPS)))
10361059
$(call arduino_output,-)
1037-
$(call show_config_info,ARDUINO_LIBS =)
1060+
$(call show_config_info,SKETCH_LIBS_DEPS =)
10381061
endif
10391062

1040-
ifneq (,$(strip $(USER_LIB_NAMES)))
1041-
$(foreach lib,$(USER_LIB_NAMES),$(call show_config_info, $(lib),[USER]))
1063+
ifneq (,$(strip $(SKETCH_LIBS_DEPS)))
1064+
$(foreach lib,$(SKETCH_LIBS_DEPS),$(call show_config_info, $(lib),[USER]))
1065+
endif
1066+
1067+
ifneq (,$(strip $(SYS_LIB_NAMES) $(PLATFORM_LIB_NAMES)))
1068+
$(call arduino_output,-)
1069+
$(call show_config_info,SYSTEM_LIBS =)
10421070
endif
10431071

10441072
ifneq (,$(strip $(SYS_LIB_NAMES) $(PLATFORM_LIB_NAMES)))
10451073
$(foreach lib,$(SYS_LIB_NAMES),$(call show_config_info, $(lib),[SYSTEM]))
1074+
$(call arduino_output,-)
10461075
endif
10471076

10481077
# either calculate parent dir from arduino dir, or user-defined path

HISTORY.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -34,6 +34,7 @@ I tried to give credit whenever possible. If I have missed anyone, kindly add it
3434
- Fix: Changed IDE download URL *again* for Travis-CI. (https://github.com/sej7278)
3535
- Fix: Allow avrdude to erase the chip before programming during ispload (https://github.com/tchebb)
3636
- Fix: Fix speed regression. Thanks ladislas (Issue #280) (https://github.com/sej7278)
37+
- New: Add automatic library detection when compiling a sketch. (http://github.com/ladislas)
3738

3839
### 1.3.4 (2014-07-12)
3940
- Tweak: Allow spaces in "Serial.begin (....)". (Issue #190) (https://github.com/pdav)

bin/lib-detection

Lines changed: 90 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,90 @@
1+
#!/usr/bin/env python
2+
3+
import os
4+
import re
5+
import sys
6+
7+
8+
# Set variables
9+
USER_LIB_PATH = sys.argv[1]
10+
USER_LIBS = []
11+
12+
includeRegex = re.compile("(?<=^\#include\s\")(.*)(?=\.h\")", re.DOTALL|re.M)
13+
14+
SKETCH_SRCS = []
15+
SKETCH_LIBS = []
16+
17+
SKETCH_LIBS_DEPS = []
18+
SKETCH_LIBS_DEPS_STACK = []
19+
20+
21+
# Define functions
22+
def outputLibs(libArray):
23+
for lib in libArray:
24+
print(lib),
25+
print("")
26+
27+
28+
# Find local sources .ino, .c or .cpp
29+
FILE_END = (".c", ".cpp", ".ino")
30+
SKETCH_SRCS = [f for f in os.listdir(os.curdir) if f.endswith(FILE_END)]
31+
32+
# Find all USER_LIBS
33+
for path, dirs, files in os.walk(USER_LIB_PATH):
34+
for d in dirs:
35+
USER_LIBS.append(d)
36+
37+
# Find SKETCH_LIBS included in SKETCH_SRCS
38+
for src in SKETCH_SRCS:
39+
currentFile = open(src)
40+
41+
for line in currentFile:
42+
match = includeRegex.search(line)
43+
if match is not None:
44+
group = match.group(1)
45+
if group in USER_LIBS:
46+
SKETCH_LIBS.append(group)
47+
48+
SKETCH_LIBS = sorted(set(SKETCH_LIBS))
49+
50+
# Find SKETCH_LIBS_DEPS includes in SKETCH_LIBS
51+
for lib in SKETCH_LIBS:
52+
if lib in USER_LIBS:
53+
currentFile = open(os.path.join(USER_LIB_PATH, lib, lib + ".h"))
54+
55+
for line in currentFile:
56+
match = includeRegex.search(line)
57+
if match is not None:
58+
group = match.group(1)
59+
if group in USER_LIBS and group not in SKETCH_LIBS:
60+
SKETCH_LIBS_DEPS_STACK.append(group)
61+
62+
SKETCH_LIBS_DEPS_STACK = list(set(SKETCH_LIBS_DEPS_STACK))
63+
64+
# Recursively find all dependencies of every libraries in USER_LIB_PATH
65+
while len(SKETCH_LIBS_DEPS_STACK) > 0:
66+
for lib in SKETCH_LIBS_DEPS_STACK:
67+
if lib in USER_LIBS:
68+
currentFile = open(os.path.join(USER_LIB_PATH, lib, lib + ".h"))
69+
70+
for line in currentFile:
71+
match = includeRegex.search(line)
72+
if match is not None:
73+
group = match.group(1)
74+
if group in USER_LIBS and group not in SKETCH_LIBS_DEPS_STACK and group not in SKETCH_LIBS_DEPS and group not in SKETCH_LIBS:
75+
SKETCH_LIBS_DEPS_STACK.append(group)
76+
77+
else:
78+
if lib not in SKETCH_LIBS_DEPS:
79+
SKETCH_LIBS_DEPS.append(lib)
80+
if lib in SKETCH_LIBS_DEPS_STACK:
81+
SKETCH_LIBS_DEPS_STACK.remove(lib)
82+
83+
SKETCH_LIBS_DEPS.sort()
84+
85+
# Output libraries for the Makefile
86+
print("SKETCH_LIBS"),
87+
outputLibs(SKETCH_LIBS)
88+
89+
print("SKETCH_LIBS_DEPS"),
90+
outputLibs(SKETCH_LIBS_DEPS)

0 commit comments

Comments
 (0)