Skip to content

Commit

Permalink
makefiles: Add mechanism to build modules through Cargo
Browse files Browse the repository at this point in the history
... and to dissect the static libraries into invidial .o files to link
them the same way we link C.
  • Loading branch information
chrysn committed Dec 14, 2021
1 parent a2e1b92 commit 732c369
Show file tree
Hide file tree
Showing 4 changed files with 82 additions and 0 deletions.
4 changes: 4 additions & 0 deletions Makefile.include
Original file line number Diff line number Diff line change
Expand Up @@ -216,6 +216,8 @@ ifeq (,$(TOOLCHAIN))
override TOOLCHAIN := gnu
endif

include $(RIOTMAKE)/cargo-settings.inc.mk

GLOBAL_GOALS += buildtest \
buildtest-indocker \
info-boards-features-blacklisted \
Expand Down Expand Up @@ -1033,6 +1035,8 @@ endif

endif

include $(RIOTMAKE)/cargo-targets.inc.mk

# include RIOT_MAKEFILES_GLOBAL_POST configuration files
# allows setting user specific system wide configuration parsed after the body
# of $(RIOTBASE)/Makefile.include
Expand Down
43 changes: 43 additions & 0 deletions makefiles/cargo-settings.inc.mk
Original file line number Diff line number Diff line change
@@ -0,0 +1,43 @@
# Rust's own version of the target triple / quadruple.
#
# This does not have a sane default, and needs to be set in the architecture
# files.
# RUST_TARGET = ...

# Flags that need to be added to the RIOT_CFLAGS passed to cargo in order to
# make bindgen happy
CARGO_EXTRACFLAGS ?=

# Setting anything other than "debug" or "release" will necessitate additional
# -Z unstable-options as of 2021-03 nightlies.
CARGO_PROFILE ?= release

# The Rust version to use.
#
# As long as C2Rust and riot-wrappers require nightly, the only alternative
# here is to pick a particular nightly when something breaks.
#
# (Default is empty, because the riotbuild container picks a particular nightly
# and sets it as a default; users without a nightly default need to either
# override this here or in rustup)
CARGO_CHANNEL ?=

# Note that if we did not set this explicitly, CARGO_LIB would have to
# understand which value cargo uses in absence of CARGO_TARGET_DIR, which would
# be $(APPDIR)/target.
#
# For many cases, it would be beneficial to base this on BINDIRBASE rather than
# BINDIR, for that would allow different boards using the same CPU to share
# compiled code (unless they they build conditionally on environment variables,
# like riot-sys does). This is not done for two reasons:
#
# * Overriding BINDIR (like is done in Murdock) would not take effect,
# requiring additional overrides to enable out-of-tree building.
#
# * Switching back and forth between two boards of the same CPU requires
# riot-sys rebuilds. (On its own, this would be outweighed by the shared
# compilation of other modules).
CARGO_TARGET_DIR = $(BINDIR)/target

# The single Rust library to be built.
CARGO_LIB = $(CARGO_TARGET_DIR)/$(RUST_TARGET)/${CARGO_PROFILE}/lib$(APPLICATION_RUST_MODULE).a
34 changes: 34 additions & 0 deletions makefiles/cargo-targets.inc.mk
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
CARGO_COMPILE_COMMANDS = $(BINDIR)/cargo-compile-commands.json
CARGO_COMPILE_COMMANDS_FLAGS = --clang

# This is duplicating the compile-commands rule because unlike in the use case
# when a $(RIOTBASE)/compile_commands.json is built, we *want* this to be
# per-board and per-application. (The large mechanisms are shared anyway).
#
# Changes relative to the compile-commands rule: This uses lazysponge to keep
# Rust from rebuilding, and uses a custom output file and
# CARGO_COMPILE_COMMAND_FLAGS.
$(CARGO_COMPILE_COMMANDS): $(BUILDDEPS)
$(Q)DIRS="$(DIRS)" APPLICATION_BLOBS="$(BLOBS)" \
"$(MAKE)" -C $(APPDIR) -f $(RIOTMAKE)/application.inc.mk compile-commands
$(Q)$(RIOTTOOLS)/compile_commands/compile_commands.py $(CARGO_COMPILE_COMMANDS_FLAGS) $(BINDIR) \
| $(LAZYSPONGE) $@


$(CARGO_LIB): $(RIOTBUILD_CONFIG_HEADER_C) $(BUILDDEPS) $(CARGO_COMPILE_COMMANDS) FORCE
$(Q)[ x"${RUST_TARGET}" != x"" ] || (echo "Error: No RUST_TARGET was set for this platform. (Set FEATURES_REQUIRED+=rust_target to catch this earlier)."; exit 1)
$(Q)CC= CFLAGS= CPPFLAGS= CXXFLAGS= RIOT_COMPILE_COMMANDS_JSON="$(CARGO_COMPILE_COMMANDS)" RIOT_USEMODULE="$(USEMODULE)" cargo $(patsubst +,,+${CARGO_CHANNEL}) build --target $(RUST_TARGET) `if [ x$(CARGO_PROFILE) = xrelease ]; then echo --release; else if [ x$(CARGO_PROFILE) '!=' xdebug ]; then echo "--profile $(CARGO_PROFILE)"; fi; fi` $(CARGO_OPTIONS)

$(APPLICATION_RUST_MODULE).module: $(CARGO_LIB) FORCE
$(Q)# Ensure no old object files persist. These would lead to duplicate
$(Q)# symbols, or worse, lingering behaivor of XFA entries.
$(Q)rm -rf $(BINDIR)/$(APPLICATION_RUST_MODULE)/
$(Q)mkdir -p $(BINDIR)/$(APPLICATION_RUST_MODULE)/

$(Q)# On cortex-m0 boards like airfy-beacon, the archive contains a
$(Q)# bin/thumbv6m-none-eabi.o file; the directory must be present for
$(Q)# ar to unpack it...
$(Q)mkdir -p $(BINDIR)/$(APPLICATION_RUST_MODULE)/bin/
$(Q)cd $(BINDIR)/$(APPLICATION_RUST_MODULE)/ && $(AR) x $<
$(Q)# ... and move them back if any exist, careful to err if anything is duplicate
$(Q)rmdir $(BINDIR)/$(APPLICATION_RUST_MODULE)/bin/ || (mv -n $(BINDIR)/$(APPLICATION_RUST_MODULE)/bin/* $(BINDIR)/$(APPLICATION_RUST_MODULE)/ && rmdir $(BINDIR)/$(APPLICATION_RUST_MODULE)/bin/)
1 change: 1 addition & 0 deletions makefiles/vars.inc.mk
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,7 @@ export RIOTMAKE # Location of all supplemental Makefiles (such as t
export RIOTKCONFIG # Location of all supplemental Kconfig files
export BINDIRBASE # This is the folder where the application should be built in. For each BOARD a different subfolder is used.
export BINDIR # This is the folder where the application should be built in.
export CARGO_TARGET_DIR # This is the folder where Rust parts of the application should be built in.
export BUILD_DIR # This is the base folder to store common build files and artifacts, e.g. test results.
export APPDIR # The base folder containing the application
export PKGDIRBASE # The base folder for building packages
Expand Down

0 comments on commit 732c369

Please sign in to comment.