From 6a99fbd79f47a61bfb4ce0bd7439b0ad6993905e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?IOhannes=20m=20zm=C3=B6lnig?= Date: Mon, 9 Mar 2020 13:14:41 +0100 Subject: [PATCH 1/7] first stab at building android externals compiles on dockcross/android-arm and dockcross/android-arm64 not runtime tests have been performed yet (as i only have a cross-compilation environment) Related: https://github.com/pure-data/pd-lib-builder/issues/60 --- Makefile.pdlibbuilder | 28 ++++++++++++++++++++++++++++ 1 file changed, 28 insertions(+) diff --git a/Makefile.pdlibbuilder b/Makefile.pdlibbuilder index 3cd379f..601d0c4 100644 --- a/Makefile.pdlibbuilder +++ b/Makefile.pdlibbuilder @@ -410,6 +410,9 @@ target.triplet := $(subst -, ,$(shell $(CC) -dumpmachine)) ifneq ($(filter linux gnu% kfreebsd, $(target.triplet)),) system = Linux endif +ifneq ($(filter android%, $(target.triplet)),) + system = Android +endif ifneq ($(filter darwin%, $(target.triplet)),) system = Darwin @@ -497,6 +500,27 @@ ifeq ($(system), Linux) endif +#=== flags and paths for Android =============================================== +ifeq ($(system), Android) + prefix = /usr/local + libdir := $(prefix)/lib + pkglibdir = $(libdir)/pd-externals + pdincludepath := $(wildcard /usr/include/pd) + extension = so + cpp.flags := -DUNIX + c.flags := + c.ldflags := -rdynamic -shared -Wl,-rpath,"\$$ORIGIN",--enable-new-dtags + c.ldlibs := -lc -lm + cxx.flags := -fcheck-new + cxx.ldflags := -rdynamic -shared -Wl,-rpath,"\$$ORIGIN",--enable-new-dtags + cxx.ldlibs := -lc -lm -lstdc++ + shared.extension = so + shared.ldflags := -rdynamic -shared -Wl,-soname,$(shared.lib) +endif + + + + #=== flags and paths for Darwin ================================================ @@ -721,7 +745,11 @@ all.objects = $(classes.objects) $(common.objects) $(shared.objects) \ # construct class executable names from class names +ifeq ($(system), Android) +classes.executables := $(addprefix lib, $(addsuffix .$(extension), $(patsubst %~,%_tilde,$(classes)))) +else classes.executables := $(addsuffix .$(extension), $(classes)) +endif # Construct shared lib executable name if shared sources are defined. If # extension and shared extension are not identical, use both to facilitate co- From 4e1724f358d1c7bf6bc15c7f399b3718bf80c812 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?IOhannes=20m=20zm=C3=B6lnig?= Date: Tue, 10 Mar 2020 11:06:56 +0100 Subject: [PATCH 2/7] Drop the Android output filename mangling - it doesn't work. --- Makefile.pdlibbuilder | 4 ---- 1 file changed, 4 deletions(-) diff --git a/Makefile.pdlibbuilder b/Makefile.pdlibbuilder index 601d0c4..0a3379e 100644 --- a/Makefile.pdlibbuilder +++ b/Makefile.pdlibbuilder @@ -745,11 +745,7 @@ all.objects = $(classes.objects) $(common.objects) $(shared.objects) \ # construct class executable names from class names -ifeq ($(system), Android) -classes.executables := $(addprefix lib, $(addsuffix .$(extension), $(patsubst %~,%_tilde,$(classes)))) -else classes.executables := $(addsuffix .$(extension), $(classes)) -endif # Construct shared lib executable name if shared sources are defined. If # extension and shared extension are not identical, use both to facilitate co- From e676c6f5a2e793e63c9cbb05e879375a97607086 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?IOhannes=20m=20zm=C3=B6lnig?= Date: Tue, 10 Mar 2020 11:15:09 +0100 Subject: [PATCH 3/7] Add an optional mangler for classnames --- Makefile.pdlibbuilder | 23 ++++++++++++++++++++++- 1 file changed, 22 insertions(+), 1 deletion(-) diff --git a/Makefile.pdlibbuilder b/Makefile.pdlibbuilder index 0a3379e..af7cbde 100644 --- a/Makefile.pdlibbuilder +++ b/Makefile.pdlibbuilder @@ -719,8 +719,29 @@ endef $(foreach v, $(class.sources), $(eval $(add-class-source))) +# Mangle the names of the classes +# If a function 'classname-mangler' is defined, it is applied to all output files +# effectively renaming the filename for the externals +# This is necessary for building externals for Android, which requires dlopen()ed +# files to have a specific name. +# the 'classname-mangler' function takes a single argument (the classname, +# e.g. 'foo~'), and returns a mangled version (e.g. 'libfoo_tilde'). +# file extensions are handled separately via the 'extension' variable. +define eval-classname-mangler = + $(call classname-mangler,$1).class.sources := $$($(1).class.sources) + undefine $(1).class.sources + sourcevariables += $(call classname-mangler,$1).class.sources +endef + +# only mangle the names if a 'classname-mangler' function is defined +ifdef classname-mangler + sourcevariables := + $(foreach v, $(filter %.class.sources, $(.VARIABLES)), $(eval $(call eval-classname-mangler,$(basename $(basename $v))))) +else + sourcevariables := $(filter %.class.sources, $(.VARIABLES)) +endif + # derive class names from .class.sources variables -sourcevariables := $(filter %.class.sources, $(.VARIABLES)) classes := $(basename $(basename $(sourcevariables))) # accumulate all source files specified in makefile From dd586d4cf37572ed4cdcbf4a5b431de868d618af Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?IOhannes=20m=20zm=C3=B6lnig?= Date: Tue, 10 Mar 2020 11:15:58 +0100 Subject: [PATCH 4/7] mangle the classnames on Android to adhere to their special conditions --- Makefile.pdlibbuilder | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/Makefile.pdlibbuilder b/Makefile.pdlibbuilder index af7cbde..885d3cd 100644 --- a/Makefile.pdlibbuilder +++ b/Makefile.pdlibbuilder @@ -516,6 +516,10 @@ ifeq ($(system), Android) cxx.ldlibs := -lc -lm -lstdc++ shared.extension = so shared.ldflags := -rdynamic -shared -Wl,-soname,$(shared.lib) + # on Android, dlopen()ed files must have the form 'lib.so'. + # also, the name must not include a '~', so Pd replaces it with a '_tilde' + # when searching for a library. + classname-mangler = $(addprefix lib, $(patsubst %~,%_tilde,$1)) endif @@ -727,6 +731,7 @@ $(foreach v, $(class.sources), $(eval $(add-class-source))) # the 'classname-mangler' function takes a single argument (the classname, # e.g. 'foo~'), and returns a mangled version (e.g. 'libfoo_tilde'). # file extensions are handled separately via the 'extension' variable. +# See the 'system==Android' section for an example. define eval-classname-mangler = $(call classname-mangler,$1).class.sources := $$($(1).class.sources) undefine $(1).class.sources From 2e6840adfd65e6e810d5d3b6e7133b61691e7bb2 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?IOhannes=20m=20zm=C3=B6lnig?= Date: Tue, 10 Mar 2020 12:56:06 +0100 Subject: [PATCH 5/7] adjust build/installchecks to Android-specifics --- tests/_template_/Makefile | 7 +++++-- tests/multifor/Makefile | 14 ++++++++++---- tests/multilib/Makefile | 7 +++++-- tests/multiple/Makefile | 11 +++++++---- tests/multiplexx/Makefile | 11 +++++++---- tests/multishared/Makefile | 11 +++++++---- tests/single/Makefile | 7 +++++-- tests/subdir/Makefile | 14 ++++++++++---- 8 files changed, 56 insertions(+), 26 deletions(-) diff --git a/tests/_template_/Makefile b/tests/_template_/Makefile index ea5fd4f..4565005 100644 --- a/tests/_template_/Makefile +++ b/tests/_template_/Makefile @@ -18,7 +18,10 @@ PDLIBBUILDER_DIR=../.. include $(PDLIBBUILDER_DIR)/Makefile.pdlibbuilder # simplistic tests whether all expected files have been produced/installed +ifeq ($(system), Android) + classprefix=lib +endif buildcheck: all - test -e _template_.$(extension) + test -e $(classprefix)_template_.$(extension) installcheck: install - test -e $(installpath)/_template_.$(extension) + test -e $(installpath)/$(classprefix)_template_.$(extension) diff --git a/tests/multifor/Makefile b/tests/multifor/Makefile index 48950f2..f3d8b5f 100644 --- a/tests/multifor/Makefile +++ b/tests/multifor/Makefile @@ -18,6 +18,9 @@ endef define forWindows class.sources += multiforB.c endef +define forAndroid + class.sources += multiforB.c +endef # all extra files to be included in binary distribution of the library datafiles = multifor-help.pd multifor-meta.pd @@ -29,11 +32,14 @@ PDLIBBUILDER_DIR=../.. include $(PDLIBBUILDER_DIR)/Makefile.pdlibbuilder # simplistic tests whether all expected files have been produced/installed +ifeq ($(system), Android) + classprefix=lib +endif buildcheck: all - test -e multiforA.$(extension) - test -e multiforB.$(extension) + test -e $(classprefix)multiforA.$(extension) + test -e $(classprefix)multiforB.$(extension) installcheck: install - test -e $(installpath)/multiforA.$(extension) - test -e $(installpath)/multiforB.$(extension) + test -e $(installpath)/$(classprefix)multiforA.$(extension) + test -e $(installpath)/$(classprefix)multiforB.$(extension) test -e $(installpath)/multifor-help.pd test -e $(installpath)/multifor-meta.pd diff --git a/tests/multilib/Makefile b/tests/multilib/Makefile index 00f20dc..17167e9 100644 --- a/tests/multilib/Makefile +++ b/tests/multilib/Makefile @@ -24,9 +24,12 @@ include $(PDLIBBUILDER_DIR)/Makefile.pdlibbuilder # simplistic tests whether all expected files have been produced/installed +ifeq ($(system), Android) + classprefix=lib +endif buildcheck: all - test -e multilib.$(extension) + test -e $(classprefix)multilib.$(extension) installcheck: install - test -e $(installpath)/multilib.$(extension) + test -e $(installpath)/$(classprefix)multilib.$(extension) test -e $(installpath)/multilib-help.pd test -e $(installpath)/multilib-meta.pd diff --git a/tests/multiple/Makefile b/tests/multiple/Makefile index eac1412..78d7660 100644 --- a/tests/multiple/Makefile +++ b/tests/multiple/Makefile @@ -18,11 +18,14 @@ PDLIBBUILDER_DIR=../.. include $(PDLIBBUILDER_DIR)/Makefile.pdlibbuilder # simplistic tests whether all expected files have been produced/installed +ifeq ($(system), Android) + classprefix=lib +endif buildcheck: all - test -e multipleA.$(extension) - test -e multipleB.$(extension) + test -e $(classprefix)multipleA.$(extension) + test -e $(classprefix)multipleB.$(extension) installcheck: install - test -e $(installpath)/multipleA.$(extension) - test -e $(installpath)/multipleB.$(extension) + test -e $(installpath)/$(classprefix)multipleA.$(extension) + test -e $(installpath)/$(classprefix)multipleB.$(extension) test -e $(installpath)/multiple-help.pd test -e $(installpath)/multiple-meta.pd diff --git a/tests/multiplexx/Makefile b/tests/multiplexx/Makefile index 7438f0a..99e0a94 100644 --- a/tests/multiplexx/Makefile +++ b/tests/multiplexx/Makefile @@ -18,11 +18,14 @@ PDLIBBUILDER_DIR=../.. include $(PDLIBBUILDER_DIR)/Makefile.pdlibbuilder # simplistic tests whether all expected files have been produced/installed +ifeq ($(system), Android) + classprefix=lib +endif buildcheck: all - test -e multiplexxA.$(extension) - test -e multiplexxB.$(extension) + test -e $(classprefix)multiplexxA.$(extension) + test -e $(classprefix)multiplexxB.$(extension) installcheck: install - test -e $(installpath)/multiplexxA.$(extension) - test -e $(installpath)/multiplexxB.$(extension) + test -e $(installpath)/$(classprefix)multiplexxA.$(extension) + test -e $(installpath)/$(classprefix)multiplexxB.$(extension) test -e $(installpath)/multiplexx-help.pd test -e $(installpath)/multiplexx-meta.pd diff --git a/tests/multishared/Makefile b/tests/multishared/Makefile index 9ccb169..a6bba3e 100644 --- a/tests/multishared/Makefile +++ b/tests/multishared/Makefile @@ -21,21 +21,24 @@ PDLIBBUILDER_DIR=../.. include $(PDLIBBUILDER_DIR)/Makefile.pdlibbuilder # simplistic tests whether all expected files have been produced/installed +ifeq ($(system), Android) + classprefix=lib +endif buildcheck: all ifeq ($(shared.extension), $(extension)) test -e lib$(lib.name).$(shared.extension) else test -e lib$(lib.name).$(extension).$(shared.extension) endif - test -e multisharedA.$(extension) - test -e multisharedB.$(extension) + test -e $(classprefix)multisharedA.$(extension) + test -e $(classprefix)multisharedB.$(extension) installcheck: install ifeq ($(shared.extension), $(extension)) test -e $(installpath)/lib$(lib.name).$(shared.extension) else test -e $(installpath)/lib$(lib.name).$(extension).$(shared.extension) endif - test -e $(installpath)/multisharedA.$(extension) - test -e $(installpath)/multisharedB.$(extension) + test -e $(installpath)/$(classprefix)multisharedA.$(extension) + test -e $(installpath)/$(classprefix)multisharedB.$(extension) test -e $(installpath)/multishared-help.pd test -e $(installpath)/multishared-meta.pd diff --git a/tests/single/Makefile b/tests/single/Makefile index 0d36005..b1453ff 100644 --- a/tests/single/Makefile +++ b/tests/single/Makefile @@ -18,7 +18,10 @@ PDLIBBUILDER_DIR=../.. include $(PDLIBBUILDER_DIR)/Makefile.pdlibbuilder # simplistic tests whether all expected files have been produced/installed +ifeq ($(system), Android) + classprefix=lib +endif buildcheck: all - test -e single.$(extension) + test -e $(classprefix)single.$(extension) installcheck: install - test -e $(installpath)/single.$(extension) + test -e $(installpath)/$(classprefix)single.$(extension) diff --git a/tests/subdir/Makefile b/tests/subdir/Makefile index ac68c2a..4fd89cf 100644 --- a/tests/subdir/Makefile +++ b/tests/subdir/Makefile @@ -19,9 +19,15 @@ PDLIBBUILDER_DIR=../.. include $(PDLIBBUILDER_DIR)/Makefile.pdlibbuilder # simplistic tests whether all expected files have been produced/installed +ifeq ($(system), Android) + classprefix=lib + tilde=_tilde +else + tilde=~ +endif buildcheck: all - test -e subdir.$(extension) - test -e subdir~.$(extension) + test -e $(classprefix)subdir.$(extension) + test -e $(classprefix)subdir$(tilde).$(extension) installcheck: install - test -e $(installpath)/subdir.$(extension) - test -e $(installpath)/subdir~.$(extension) + test -e $(installpath)/$(classprefix)subdir.$(extension) + test -e $(installpath)/$(classprefix)subdir$(tilde).$(extension) From 1e7cc657b9a88641182b4cb0b97431cfb007611d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?IOhannes=20m=20zm=C3=B6lnig?= Date: Tue, 10 Mar 2020 13:27:06 +0100 Subject: [PATCH 6/7] Introduce 'lib.executable' to allow mangling the name of multi-object libraries --- Makefile.pdlibbuilder | 15 +++++++++------ 1 file changed, 9 insertions(+), 6 deletions(-) diff --git a/Makefile.pdlibbuilder b/Makefile.pdlibbuilder index 885d3cd..641040f 100644 --- a/Makefile.pdlibbuilder +++ b/Makefile.pdlibbuilder @@ -742,8 +742,11 @@ endef ifdef classname-mangler sourcevariables := $(foreach v, $(filter %.class.sources, $(.VARIABLES)), $(eval $(call eval-classname-mangler,$(basename $(basename $v))))) + lib.executable = $(call classname-mangler,$(lib.name)).$(extension) else sourcevariables := $(filter %.class.sources, $(.VARIABLES)) + classname-mangler = $1 + lib.executable = $(lib.name).$(extension) endif # derive class names from .class.sources variables @@ -868,7 +871,7 @@ $(if $(filter install install-lib, $(goals)), $(info ++++ info: \ ifeq ($(make-lib-executable),yes) $(if $(lib.setup.sources), ,\ $(error Can not build library blob because lib.setup.sources is undefined)) - executables := $(lib.name).$(extension) + executables := $(lib.executable) else executables := $(classes.executables) $(shared.lib) endif @@ -941,22 +944,22 @@ endef # build all classes into single executable -build-lib: $(lib.name).$(extension) - $(info ++++ info: library blob $(lib.name).$(extension) completed) +build-lib: $(lib.executable) + $(info ++++ info: library blob $(lib.executable) completed) # recipe for linking objects in lib executable # argument $1 = compiler type (c or cxx) define link-lib $(compile-$1) \ $($1.ldflags) $(lib.ldflags) \ - -o $(lib.name).$(extension) $(all.objects) \ + -o $(lib.executable) $(all.objects) \ $($1.ldlibs) $(lib.ldlibs) endef # rule for linking objects in lib executable # declared conditionally to avoid name clashes ifeq ($(make-lib-executable),yes) -$(lib.name).$(extension): $(all.objects) +$(lib.executable): $(all.objects) $(if $(filter %.cc %.cpp, $(all.sources)), \ $(call link-lib,cxx), \ $(call link-lib,c)) @@ -1236,7 +1239,7 @@ $(DISTDIR): # delete build products from build tree clean: rm -f $(all.objects) - rm -f $(classes.executables) $(lib.name).$(extension) $(shared.lib) + rm -f $(classes.executables) $(lib.executable) $(shared.lib) rm -f *.pre *.lst # remove distribution directories and tarballs from build tree From ffc96459e8b3df1ac213ab8c4961c182a57c98c0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?IOhannes=20m=20zm=C3=B6lnig?= Date: Wed, 11 Mar 2020 20:57:38 +0100 Subject: [PATCH 7/7] use deferred expansion for Android's shared.ldflags --- Makefile.pdlibbuilder | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Makefile.pdlibbuilder b/Makefile.pdlibbuilder index dc7ef2b..51c1733 100644 --- a/Makefile.pdlibbuilder +++ b/Makefile.pdlibbuilder @@ -515,7 +515,7 @@ ifeq ($(system), Android) cxx.ldflags := -rdynamic -shared -Wl,-rpath,"\$$ORIGIN",--enable-new-dtags cxx.ldlibs := -lc -lm -lstdc++ shared.extension = so - shared.ldflags := -rdynamic -shared -Wl,-soname,$(shared.lib) + shared.ldflags = -rdynamic -shared -Wl,-soname,$(shared.lib) # on Android, dlopen()ed files must have the form 'lib.so'. # also, the name must not include a '~', so Pd replaces it with a '_tilde' # when searching for a library.