[Buildroot] [PATCH 2/2] rust: new package
Thomas Petazzoni
thomas.petazzoni at free-electrons.com
Wed Jun 15 22:09:33 UTC 2016
Hello,
Thanks Eric for working on Rust. Below a preliminary review with lots
of questions/comments.
On Sun, 24 Apr 2016 16:39:49 +0200, Eric Le Bihan wrote:
> This new package provides the compiler for the Rust programming language.
>
> Currently, only the host variant is built.
>
> The build process is as follows:
>
> 1. a snapshot of the Rust compiler matching the host architecture is
> downloaded. This is rustc-stage0.
OK, this one is downloaded pre-compiled. So your package should have a
dependency on the host architecture, since the pre-compiled rust
compilers are only available on x86 and x86_64 it seems. So you
probably want something like:
depends on BR2_HOSTARCH = "x86_64" || BR2_HOSTARCH = "x86"
> 2. rustc-stage0 is used to build rustc-stage1, which will build the
> final Rust compiler (rust-stage2) and the standard library for the
> host architecture.
Is this all happening inside the rust build process? Because from what
I can see in your package, you're downloading and extracting
rustc-stage0, and then directly building rust.
> 3. the standard library for the target architecture is build.
>
> The Rust compiler uses LLVM as its backend, compiled with support for
> x86, ARM, PowerPC and MIPS architectures.
>
> To properly build the standard library for the target, two files are
> needed:
>
> - the target configuration: a Makefile fragment telling the build system
> about the cross-compiler and such.
> - the target specification: a JSON file describing the target
> architecture to the LLVM backend.
>
> These files are generated with a Python script which takes info from the
> Buildroot configuration: `rust-target-gen`.
It is not entirely clear to me if a separate Python script is needed,
or if they could be generated from rust.mk directly.
> When compiling Rust code with this compiler, the generated program only
> depends on the target C library, as it is statically linked to the Rust
> standard library.
So where does the glibc dependency comes from?
> diff --git a/package/rust/0001-Harmonize-use-of-CROSS_PREFIX_-in-mk-cfg-.mk.patch b/package/rust/0001-Harmonize-use-of-CROSS_PREFIX_-in-mk-cfg-.mk.patch
> new file mode 100644
> index 0000000..a8dc151
> --- /dev/null
> +++ b/package/rust/0001-Harmonize-use-of-CROSS_PREFIX_-in-mk-cfg-.mk.patch
> @@ -0,0 +1,53 @@
> +From 23d9dbfb3ad4a8d5d5997738e8b1436d076898e9 Mon Sep 17 00:00:00 2001
> +From: Eric Le Bihan <eric.le.bihan.dev at free.fr>
> +Date: Tue, 19 Apr 2016 10:49:20 +0200
> +Subject: [PATCH 1/3] Harmonize use of CROSS_PREFIX_* in mk/cfg/*.mk
> +
> +Use CROSS_PREFIX_ in Makefile fragments for cross-compiling on Linux
> +wherever possible.
> +
> +Signed-off-by: Eric Le Bihan <eric.le.bihan.dev at free.fr>
> +---
> + mk/cfg/mips-unknown-linux-gnu.mk | 9 +++++----
> + mk/cfg/mipsel-unknown-linux-gnu.mk | 9 +++++----
> + 2 files changed, 10 insertions(+), 8 deletions(-)
Aren't those files generated by your Python script? If so, why are you
patching the existing ones?
> diff --git a/package/rust/Config.in.host b/package/rust/Config.in.host
> new file mode 100644
> index 0000000..b9bbe0b
> --- /dev/null
> +++ b/package/rust/Config.in.host
> @@ -0,0 +1,24 @@
> +config BR2_PACKAGE_RUST_ARCH_SUPPORTS
> + bool
> + default y
> + depends on BR2_arm || BR2_aarch64 || BR2_i386 \
> + || BR2_mips || BR2_mipsel || BR2_x86_64
> + depends on !BR2_ARM_CPU_ARMV4 && !BR2_ARM_CPU_ARMV5
> +
> +config BR2_PACKAGE_HOST_RUST
> + bool "host rust"
Normally, we wouldn't add visible Config.in options for such host
packages, they should just be used as dependencies of target packages.
Like we did for the host-go package recently.
> diff --git a/package/rust/rust.hash b/package/rust/rust.hash
> new file mode 100644
> index 0000000..552a5fc
> --- /dev/null
> +++ b/package/rust/rust.hash
> @@ -0,0 +1,5 @@
> +# Locally calculated
> +sha256 af4466147e8d4db4de2a46e07494d2dc2d96313c5b37da34237f511c905f7449 rustc-1.8.0-src.tar.gz
> +sha1 d29b7607d13d64078b6324aec82926fb493f59ba rust-stage0-2016-02-17-4d3eebf-linux-x86_64-d29b7607d13d64078b6324aec82926fb493f59ba.tar.bz2
> +sha1 5f194aa7628c0703f0fd48adc4ec7f3cc64b98c7 rust-stage0-2016-02-17-4d3eebf-linux-i386-5f194aa7628c0703f0fd48adc4ec7f3cc64b98c7.tar.bz2
> +
Unneeded empty line. If you're locally calculating the hashes, why not
use sha256 for all of them?
> diff --git a/package/rust/rust.mk b/package/rust/rust.mk
> new file mode 100644
> index 0000000..90c9e2b
> --- /dev/null
> +++ b/package/rust/rust.mk
> @@ -0,0 +1,90 @@
> +################################################################################
> +#
> +# rust
> +#
> +################################################################################
> +
> +RUST_VERSION = 1.8.0
> +RUST_SOURCE = rustc-$(RUST_VERSION)-src.tar.gz
> +RUST_SITE = https://static.rust-lang.org/dist
> +RUST_LICENSE = Apache-2.0, MIT
> +RUST_LICENSE_FILES = LICENSE-APACHE LICENSE-MIT
> +
> +HOST_RUST_DEPENDENCIES = host-python
> +
> +# Taken from src/snapshots.txt
> +HOST_RUST_SNAP_SITE = https://static.rust-lang.org/stage0-snapshots
> +HOST_RUST_SNAP_DATE = 2016-02-17
> +HOST_RUST_SNAP_REV = 4d3eebf
> +
> +ifeq ($(HOSTARCH),x86_64)
> +HOST_RUST_SNAP_HASH = d29b7607d13d64078b6324aec82926fb493f59ba
> +else
> +HOST_RUST_SNAP_HASH = 5f194aa7628c0703f0fd48adc4ec7f3cc64b98c7
> +endif
> +
> +HOST_RUST_SNAP_SOURCE = \
> + rust-stage0-$(HOST_RUST_SNAP_DATE)-$(HOST_RUST_SNAP_REV)-linux-$(HOSTARCH)-$(HOST_RUST_SNAP_HASH).tar.bz2
> +
> +HOST_RUST_EXTRA_DOWNLOADS = \
> + $(HOST_RUST_SNAP_SITE)/$(HOST_RUST_SNAP_SOURCE)
> +
> +define HOST_RUST_SNAP_EXTRACT
> + $(call suitable-extractor,$(HOST_RUST_SNAP_SOURCE)) $(DL_DIR)/$(HOST_RUST_SNAP_SOURCE) | \
> + $(TAR) -C $(@D) $(TAR_OPTIONS) -
> +endef
> +
> +HOST_RUST_POST_EXTRACT_HOOKS += HOST_RUST_SNAP_EXTRACT
Alternatively, downloading and installing the rustc-stage0 compiler
could be done in a separate package, perhaps?
> +
> +define HOST_RUST_GEN_CONF
> + package/rust/rust-target-gen \
> + --mode conf \
> + --prefix=$(notdir $(TARGET_CROSS)) \
> + --input $(@D) \
> + --output $(@D)/mk/cfg/$(GNU_TARGET_NAME).mk \
> + $(GNU_TARGET_NAME)
> +endef
> +
> +define HOST_RUST_GEN_SPEC
> + package/rust/rust-target-gen \
> + --mode spec \
> + --input $(@D) \
> + --output $(HOST_DIR)/etc/rustc/$(GNU_TARGET_NAME).json \
> + $(GNU_TARGET_NAME)
> +endef
> +
> +HOST_RUST_PRE_CONFIGURE_HOOKS += \
> + HOST_RUST_GEN_CONF \
> + HOST_RUST_GEN_SPEC
> +
> +HOST_RUST_MAKE_ENV = RUST_TARGET_PATH=$(HOST_DIR)/etc/rustc
> +HOST_RUST_MAKE_OPTS = VERBOSE=1
> +
> +define HOST_RUST_CONFIGURE_CMDS
> + (cd $(@D); $(HOST_CONFIGURE_OPTS) \
> + ./configure \
> + --host=$(GNU_HOST_NAME) \
> + --build=$(GNU_HOST_NAME) \
> + --target=$(GNU_TARGET_NAME) \
> + --prefix="$(HOST_DIR)/usr" \
> + --enable-local-rust \
> + --local-rust-root="$(@D)/rust-stage0" \
> + --disable-docs \
> + --disable-manage-submodules \
> + --sysconfdir="$(HOST_DIR)/etc" \
> + --localstatedir="$(HOST_DIR)/var/lib" \
> + --datadir="$(HOST_DIR)/usr/share" \
> + --infodir="$(HOST_DIR)/usr/share/info")
It's probably good to explain somewhere that the configure script is
not an autoconf-generated configure script.
In any case, I applied your patches, and tried to build the following
defconfig:
BR2_arm=y
BR2_cortex_a8=y
BR2_TOOLCHAIN_EXTERNAL=y
BR2_INIT_NONE=y
BR2_SYSTEM_BIN_SH_NONE=y
# BR2_PACKAGE_BUSYBOX is not set
# BR2_TARGET_ROOTFS_TAR is not set
BR2_PACKAGE_HOST_RUST=y
and it fails to build with:
>>> host-rust 1.8.0 Configuring
package/rust/rust-target-gen --mode conf --prefix=arm-linux-gnueabihf- --input /home/thomas/projets/buildroot/output/build/host-rust-1.8.0 --output /home/thomas/projets/buildroot/output/build/host-rust-1.8.0/mk/cfg/arm-buildroot-linux-gnueabihf.mk arm-buildroot-linux-gnueabihf
package/rust/rust-target-gen --mode spec --input /home/thomas/projets/buildroot/output/build/host-rust-1.8.0 --output /home/thomas/projets/buildroot/output/host/etc/rustc/arm-buildroot-linux-gnueabihf.json arm-buildroot-linux-gnueabihf
(cd /home/thomas/projets/buildroot/output/build/host-rust-1.8.0; PATH="/home/thomas/projets/buildroot/output/host/bin:/home/thomas/projets/buildroot/output/host/sbin:/home/thomas/projets/buildroot/output/host/usr/bin:/home/thomas/projets/buildroot/output/host/usr/sbin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games:/snap/bin:/home/thomas/sys/bin:/home/thomas/.gem/ruby/2.1.0/bin" AR="/usr/bin/ar" AS="/usr/bin/as" LD="/usr/bin/ld" NM="/usr/bin/nm" CC="/usr/bin/gcc" GCC="/usr/bin/gcc" CXX="/usr/bin/g++" CPP="/usr/bin/cpp" OBJCOPY="/usr/bin/objcopy" RANLIB="/usr/bin/ranlib" CPPFLAGS="-I/home/thomas/projets/buildroot/output/host/usr/include" CFLAGS="-O2 -I/home/thomas/projets/buildroot/output/host/usr/include" CXXFLAGS="-O2 -I/home/thomas/projets/buildroot/output/host/usr/include" LDFLAGS="-L/home/thomas/projets/buildroot/output/host/lib -L/home/thomas/projets/buildroot/output/host/usr/lib -Wl,-rpath,/home/thomas/projets/buildroot/output/ho
st/usr/l
ib" PKG_CONFIG_ALLOW_SYSTEM_CFLAGS=1 PKG_CONFIG_ALLOW_SYSTEM_LIBS=1 PKG_CONFIG="/home/thomas/projets/buildroot/output/host/usr/bin/pkg-config" PKG_CONFIG_SYSROOT_DIR="/" PKG_CONFIG_LIBDIR="/home/thomas/projets/buildroot/output/host/usr/lib/pkgconfig:/home/thomas/projets/buildroot/output/host/usr/share/pkgconfig" INTLTOOL_PERL=/usr/bin/perl ./configure --host=x86_64-pc-linux-gnu --build=x86_64-pc-linux-gnu --target=arm-buildroot-linux-gnueabihf --prefix="/home/thomas/projets/buildroot/output/host/usr" --enable-local-rust --local-rust-root="/home/thomas/projets/buildroot/output/build/host-rust-1.8.0/rust-stage0" --disable-docs --disable-manage-submodules --sysconfdir="/home/thomas/projets/buildroot/output/host/etc" --localstatedir="/home/thomas/projets/buildroot/output/host/var/lib" --datadir="/home/thomas/projets/buildroot/output/host/usr/share" --infodir="/home/thomas/projets/buildroot/output/host/usr/share/info")
configure: looking for configure programs
configure: found program 'cmp'
configure: found program 'mkdir'
configure: found program 'printf'
configure: found program 'cut'
configure: found program 'head'
configure: found program 'grep'
configure: found program 'xargs'
configure: found program 'cp'
configure: found program 'find'
configure: found program 'uname'
configure: found program 'date'
configure: found program 'tr'
configure: found program 'sed'
configure: found program 'file'
configure: found program 'make'
configure: inspecting environment
configure: recreating config.tmp
configure:
configure: processing ./configure args
configure:
configure: CFG_DISABLE_DOCS := 1
configure: CFG_ENABLE_LOCAL_RUST := 1
configure: CFG_LOCALSTATEDIR := /home/thomas/projets/buildroot/outp ...
configure: CFG_SYSCONFDIR := /home/thomas/projets/buildroot/outp ...
configure: CFG_DATADIR := /home/thomas/projets/buildroot/outp ...
configure: CFG_INFODIR := /home/thomas/projets/buildroot/outp ...
configure: CFG_LLVM_ROOT :=
configure: CFG_PYTHON :=
configure: CFG_JEMALLOC_ROOT :=
configure: CFG_BUILD := x86_64-pc-linux-gnu
configure: CFG_ANDROID_CROSS_PATH :=
configure: CFG_I686_LINUX_ANDROID_NDK :=
configure: CFG_ARM_LINUX_ANDROIDEABI_NDK :=
configure: CFG_AARCH64_LINUX_ANDROID_NDK :=
configure: CFG_NACL_CROSS_PATH :=
configure: CFG_RELEASE_CHANNEL := dev
configure: CFG_MUSL_ROOT := /usr/local
configure: CFG_EXTRA_FILENAME :=
configure: CFG_DEFAULT_LINKER := cc
configure: CFG_DEFAULT_AR := ar
configure: CFG_LIBDIR := /home/thomas/projets/buildroot/outp ...
configure:
configure: validating ./configure args
configure:
configure: CFG_BOOTSTRAP_KEY := 23:44:24
configure:
configure: looking for build programs
configure:
configure: CFG_CURLORWGET := /usr/bin/curl (7.47.0)
configure: CFG_PYTHON := /home/thomas/projets/buildroot/outp ...
configure: CFG_GIT := /usr/bin/git (2.7.4)
configure: git: no git directory. disabling submodules
configure: CFG_MD5 :=
configure: CFG_MD5SUM := /usr/bin/md5sum (8.25)
configure: CFG_HASH_COMMAND := /usr/bin/md5sum | cut -c 1-8
configure: CFG_CLANG :=
configure: CFG_CCACHE :=
configure: CFG_GCC := /usr/bin/gcc (5.3.1-14ubuntu2.1)
configure: CFG_LD := /usr/bin/ld (2.26)
configure: CFG_VALGRIND :=
configure: CFG_PERF :=
configure: CFG_ISCC :=
configure: CFG_ANTLR4 :=
configure: CFG_GRUN :=
configure: CFG_FLEX := /usr/bin/flex (2.6.0)
configure: CFG_BISON := /usr/bin/bison (3.0.4)
configure: CFG_GDB := /usr/bin/gdb (7.11-0ubuntu1)
configure: CFG_LLDB :=
configure: CFG_DISABLE_VALGRIND_RPASS := 1
configure: CFG_GDB_VERSION := GNU gdb (Ubuntu 7.11-0ubuntu1) 7.11
configure:
configure: looking for target specific programs
configure:
configure: CFG_ADB := /usr/bin/adb
configure:
configure: using rustc at: /home/thomas/projets/buildroot/output/build/host-rust-1.8.0/rust-stage0 with version: rustc 1.8.0-dev (4d3eebff9 2016-02-17)
configure:
configure: CFG_LOCAL_RUST_ROOT := /home/thomas/projets/buildroot/outp ...
configure: skipping compiler inference steps; using provided CC=/usr/bin/gcc
configure: CFG_CC := /usr/bin/gcc
configure: CFG_CXX := /usr/bin/g++
configure: CFG_CPP := /usr/bin/cpp
configure: CFG_CFLAGS := -O2 -I/home/thomas/projets/buildroo ...
configure: CFG_CXXFLAGS := -O2 -I/home/thomas/projets/buildroo ...
configure: CFG_LDFLAGS := -L/home/thomas/projets/buildroot/ou ...
configure: CFG_STDCPP_NAME := stdc++
configure: error: unsupported target triples "x86_64-pc-linux-gnu" found
package/pkg-generic.mk:185: recipe for target '/home/thomas/projets/buildroot/output/build/host-rust-1.8.0/.stamp_configured' failed
make[1]: *** [/home/thomas/projets/buildroot/output/build/host-rust-1.8.0/.stamp_configured] Error 1
Makefile:36: recipe for target '_all' failed
make: *** [_all] Error 2
Is this expected?
Thanks!
Thomas
--
Thomas Petazzoni, CTO, Free Electrons
Embedded Linux, Kernel and Android engineering
http://free-electrons.com
More information about the buildroot
mailing list