diff options
author | Alex Chiang <107899296+alexsifivetw@users.noreply.github.com> | 2023-06-05 19:11:37 +0800 |
---|---|---|
committer | GitHub <noreply@github.com> | 2023-06-05 19:11:37 +0800 |
commit | ce6d6ccc492bb17c375e6cac13510181c9afd084 (patch) | |
tree | 3f72fb8c3dba10759abf2489858f07d7d0d2dfd5 | |
parent | d1dfc7c18363f8993d0c800bf094f829d428347e (diff) | |
parent | 02a96780757db4d7c5579f017574a0f404a2ae20 (diff) | |
download | riscv-gnu-toolchain-ce6d6ccc492bb17c375e6cac13510181c9afd084.zip riscv-gnu-toolchain-ce6d6ccc492bb17c375e6cac13510181c9afd084.tar.gz riscv-gnu-toolchain-ce6d6ccc492bb17c375e6cac13510181c9afd084.tar.bz2 |
Merge pull request #1263 from alexsifivetw/alexc/riscv-llvm-qemu
Enable RISC-V LLVM & QEMU Build Flow
-rwxr-xr-x | .github/setup-apt.sh | 4 | ||||
-rw-r--r-- | .github/workflows/nightly-release.yaml | 15 | ||||
-rw-r--r-- | .gitmodules | 4 | ||||
-rw-r--r-- | Makefile.in | 57 | ||||
-rw-r--r-- | README.md | 44 | ||||
-rwxr-xr-x | configure | 78 | ||||
-rw-r--r-- | configure.ac | 19 | ||||
m--------- | llvm | 0 |
8 files changed, 196 insertions, 25 deletions
diff --git a/.github/setup-apt.sh b/.github/setup-apt.sh index 0ad82fb..49efd02 100755 --- a/.github/setup-apt.sh +++ b/.github/setup-apt.sh @@ -3,7 +3,7 @@ # install OS prerequisites dpkg --add-architecture i386 apt update -apt install -y autoconf automake autotools-dev curl python3 libmpc-dev libmpfr-dev \ +apt install -y autoconf automake autotools-dev curl python3 python3-pip libmpc-dev libmpfr-dev \ libgmp-dev gawk build-essential bison flex texinfo gperf libtool \ - patchutils bc zlib1g-dev libexpat-dev git ninja-build expect \ + patchutils bc zlib1g-dev libexpat-dev git ninja-build cmake libglib2.0-dev expect \ device-tree-compiler diff --git a/.github/workflows/nightly-release.yaml b/.github/workflows/nightly-release.yaml index 011b453..347c74e 100644 --- a/.github/workflows/nightly-release.yaml +++ b/.github/workflows/nightly-release.yaml @@ -68,8 +68,19 @@ jobs: - name: build toolchain run: | TARGET_TUPLE=($(echo ${{ matrix.target }} | tr "-" "\n")) - ./configure --prefix=/opt/riscv --with-arch=${TARGET_TUPLE[0]} --with-abi=${TARGET_TUPLE[1]} - sudo make -j $(nproc) ${{ matrix.mode }} + BUILD_TOOLCHAIN="./configure --prefix=/opt/riscv --with-arch=${TARGET_TUPLE[0]} --with-abi=${TARGET_TUPLE[1]}" + if [ "${{ matrix.mode }}" == "linux" ]; then # build toolchain with llvm + $BUILD_TOOLCHAIN --enable-llvm --enable-linux + sudo make -j $(nproc) all + else + $BUILD_TOOLCHAIN + sudo make -j $(nproc) ${{ matrix.mode }} + fi + + - name: build qemu + if: "${{ matrix.mode }}" == "linux" + run: | + make -j$(nproc) build-sim SIM=qemu - name: tarball build run: tar czvf riscv.tar.gz -C /opt/ riscv/ diff --git a/.gitmodules b/.gitmodules index 029be52..340189f 100644 --- a/.gitmodules +++ b/.gitmodules @@ -36,3 +36,7 @@ path = pk url = https://github.com/riscv-software-src/riscv-pk.git branch = master +[submodule "llvm"] + path = llvm + url = https://github.com/llvm/llvm-project.git + branch = release/15.x diff --git a/Makefile.in b/Makefile.in index 6c6e1d8..ab49a9f 100644 --- a/Makefile.in +++ b/Makefile.in @@ -12,8 +12,10 @@ GDB_SRCDIR := @with_gdb_src@ QEMU_SRCDIR := @with_qemu_src@ SPIKE_SRCDIR := @with_spike_src@ PK_SRCDIR := @with_pk_src@ +LLVM_SRCDIR := @with_llvm_src@ DEJAGNU_SRCDIR := @with_dejagnu_src@ DEBUG_INFO := @debug_info@ +DEJAGNU_SRCDIR := @with_dejagnu_src@ SIM ?= @WITH_SIM@ @@ -118,8 +120,16 @@ newlib: stamps/build-gdb-newlib linux: stamps/build-gdb-linux endif linux-native: stamps/build-gcc-linux-native +ifeq (@enable_llvm@,--enable-llvm) +all: stamps/build-llvm-@default_target@ +newlib: stamps/build-llvm-newlib +linux: stamps/build-llvm-linux +ifeq (@multilib_flags@,--enable-multilib) +$(error "Setting multilib flags for LLVM builds is not supported.") +endif +endif -.PHONY: build-binutils build-gdb build-gcc1 build-libc build-gcc2 build-qemu +.PHONY: build-binutils build-gdb build-gcc1 build-libc build-gcc2 build-qemu build-llvm build-binutils: stamps/build-binutils-@default_target@ build-gdb: stamps/build-gdb-@default_target@ build-gcc%: stamps/build-gcc-@default_target@-stage% @@ -130,6 +140,7 @@ build-libc: stamps/build-newlib stamps/build-newlib-nano \ stamps/merge-newlib-nano endif build-qemu: stamps/build-qemu +build-llvm: stamps/build-llvm-@default_target@ REGRESSION_TEST_LIST = gcc @@ -275,6 +286,12 @@ else SPIKE_SRC_GIT := endif +ifeq ($(findstring $(srcdir),$(LLVM_SRCDIR)),$(srcdir)) +LLVM_SRC_GIT := $(LLVM_SRCDIR)/.git +else +LLVM_SRC_GIT := +endif + ifeq ($(findstring $(srcdir),$(DEJAGNU_SRCDIR)),$(srcdir)) DEJAGNU_SRC_GIT := $(DEJAGNU_SRCDIR)/.git else @@ -890,6 +907,44 @@ stamps/build-qemu: $(QEMU_SRCDIR) $(QEMU_SRC_GIT) mkdir -p $(dir $@) date > $@ +stamps/build-llvm-linux: $(LLVM_SRCDIR) $(LLVM_SRC_GIT) \ + stamps/build-gcc-linux-stage2 + # We have the following situation: + # - sysroot directory: $(INSTALL_DIR)/sysroot + # - GCC install directory: $(INSTALL_DIR) + # However, LLVM does not allow to set a GCC install prefix + # (-DGCC_INSTALL_PREFIX) if a sysroot (-DDEFAULT_SYSROOT) is set + # (the GCC install prefix will be ignored silently). + # Without a proper sysroot path feature.h won't be found by clang. + # Without a proper GCC install directory libgcc won't be found. + # As a workaround we have to merge both paths: + mkdir -p $(SYSROOT)/lib/ + ln -s -f $(INSTALL_DIR)/lib/gcc $(SYSROOT)/lib/gcc + rm -rf $@ $(notdir $@) + mkdir $(notdir $@) + cd $(notdir $@) && ln -f -s $(SYSROOT) sysroot + cd $(notdir $@) && \ + cmake $(LLVM_SRCDIR)/llvm \ + -DCMAKE_INSTALL_PREFIX=$(INSTALL_DIR) \ + -DCMAKE_BUILD_TYPE=Release \ + -DLLVM_TARGETS_TO_BUILD="RISCV" \ + -DLLVM_ENABLE_PROJECTS="clang;lld" \ + -DLLVM_ENABLE_RUNTIMES="compiler-rt;libcxx;libcxxabi;libunwind" \ + -DLLVM_DEFAULT_TARGET_TRIPLE="$(LINUX_TUPLE)" \ + -DDEFAULT_SYSROOT="../sysroot" \ + -DLLVM_RUNTIME_TARGETS=$(call make_tuple,$(XLEN),linux-gnu) \ + -DLLVM_INSTALL_TOOLCHAIN_ONLY=On \ + -DLLVM_PARALLEL_LINK_JOBS=4 + $(MAKE) -C $(notdir $@) + $(MAKE) -C $(notdir $@) install + cp $(notdir $@)/lib/riscv$(XLEN)-unknown-linux-gnu/libc++* $(SYSROOT)/lib + cd $(INSTALL_DIR)/bin && ln -s clang $(LINUX_TUPLE)-clang + mkdir -p $(dir $@) && touch $@ + +stamps/build-llvm-newlib: + echo "Building LLVM is only supported in combination with a Linux toolchain." + exit 1 + stamps/build-dejagnu: $(DEJAGNU_SRCDIR) $(DEJAGNU_SRC_GIT) rm -rf $@ $(notdir $@) mkdir $(notdir $@) @@ -20,7 +20,7 @@ Several standard packages are needed to build the toolchain. On Ubuntu, executing the following command should suffice: - $ sudo apt-get install autoconf automake autotools-dev curl python3 libmpc-dev libmpfr-dev libgmp-dev gawk build-essential bison flex texinfo gperf libtool patchutils bc zlib1g-dev libexpat-dev ninja-build + $ sudo apt-get install autoconf automake autotools-dev curl python3 python3-pip libmpc-dev libmpfr-dev libgmp-dev gawk build-essential bison flex texinfo gperf libtool patchutils bc zlib1g-dev libexpat-dev ninja-build git cmake libglib2.0-dev On Fedora/CentOS/RHEL OS, executing the following command should suffice: @@ -246,6 +246,37 @@ The command below can be used to run the glibc tests: make check-glibc-linux +### LLVM / clang + +LLVM can be used in combination with the RISC-V GNU Compiler Toolchain +to build RISC-V applications. To build LLVM with C and C++ support the +configure flag `--enable-llvm` can be used. + +E.g. to build LLVM on top of a RV64 Linux toolchain the following commands +can be used: + + ./configure --prefix=$RISCV --enable-llvm --enable-linux + make + +Note, that a combination of `--enable-llvm` and multilib configuration flags +is not supported. +Also note, that building LLVM is only supported in combination with building +a Linux toolchain. + +Below is an example how to build a rv64gc Linux toolchain with LLVM support, +how to use it to build a C and a C++ application using clang, and how to +execute the generated binaries using QEMU: + + # Build rv64gc toolchain with LLVM + ./configure --prefix=$RISCV --enable-llvm --enable-linux --with-arch=rv64gc --with-abi=lp64d + make -j$(nproc) all build-sim SIM=qemu + # Build C application with clang + $RISCV/bin/clang -march=rv64imafdc -o hello_world hello_world.c + $RISCV/bin/qemu-riscv64 -L $RISCV/sysroot ./hello_world + # Build C++ application with clang + $RISCV/bin/clang++ -march=rv64imafdc -stdlib=libc++ -o hello_world_cpp hello_world_cpp.cxx + $RISCV/bin/qemu-riscv64 -L $RISCV/sysroot ./hello_world_cpp + ### Development This section is only for developer or advanced user, or you want to build @@ -296,13 +327,14 @@ For example you have a gcc in `$HOME/gcc`, use `--with-gcc-src` can specify that Here is the list of configure option for specify source tree: - --with-gcc-src --with-binutils-src - --with-newlib-src - --with-glibc-src - --with-musl-src + --with-gcc-src --with-gdb-src + --with-glibc-src --with-linux-headers-src + --with-llvm-src + --with-musl-src + --with-newlib-src + --with-pk-src --with-qemu-src --with-spike-src - --with-pk-src @@ -587,6 +587,10 @@ LIBOBJS qemu_targets enable_libsanitizer with_linux_headers_src +with_llvm_src +with_pk_src +with_dejagnu_src +with_pk_src with_dejagnu_src with_pk_src with_spike_src @@ -597,6 +601,7 @@ with_glibc_src with_newlib_src with_binutils_src with_gcc_src +enable_llvm enable_gdb with_guile with_system_zlib @@ -653,7 +658,6 @@ infodir docdir oldincludedir includedir -runstatedir localstatedir sharedstatedir sysconfdir @@ -693,6 +697,7 @@ with_host with_system_zlib with_guile enable_gdb +enable_llvm with_gcc_src with_binutils_src with_newlib_src @@ -702,6 +707,7 @@ with_gdb_src with_qemu_src with_spike_src with_pk_src +with_llvm_src with_dejagnu_src with_linux_headers_src enable_libsanitizer @@ -753,7 +759,6 @@ datadir='${datarootdir}' sysconfdir='${prefix}/etc' sharedstatedir='${prefix}/com' localstatedir='${prefix}/var' -runstatedir='${localstatedir}/run' includedir='${prefix}/include' oldincludedir='/usr/include' docdir='${datarootdir}/doc/${PACKAGE_TARNAME}' @@ -1006,15 +1011,6 @@ do | -silent | --silent | --silen | --sile | --sil) silent=yes ;; - -runstatedir | --runstatedir | --runstatedi | --runstated \ - | --runstate | --runstat | --runsta | --runst | --runs \ - | --run | --ru | --r) - ac_prev=runstatedir ;; - -runstatedir=* | --runstatedir=* | --runstatedi=* | --runstated=* \ - | --runstate=* | --runstat=* | --runsta=* | --runst=* | --runs=* \ - | --run=* | --ru=* | --r=*) - runstatedir=$ac_optarg ;; - -sbindir | --sbindir | --sbindi | --sbind | --sbin | --sbi | --sb) ac_prev=sbindir ;; -sbindir=* | --sbindir=* | --sbindi=* | --sbind=* | --sbin=* \ @@ -1152,7 +1148,7 @@ fi for ac_var in exec_prefix prefix bindir sbindir libexecdir datarootdir \ datadir sysconfdir sharedstatedir localstatedir includedir \ oldincludedir docdir infodir htmldir dvidir pdfdir psdir \ - libdir localedir mandir runstatedir + libdir localedir mandir do eval ac_val=\$$ac_var # Remove trailing slashes. @@ -1305,7 +1301,6 @@ Fine tuning of the installation directories: --sysconfdir=DIR read-only single-machine data [PREFIX/etc] --sharedstatedir=DIR modifiable architecture-independent data [PREFIX/com] --localstatedir=DIR modifiable single-machine data [PREFIX/var] - --runstatedir=DIR modifiable per-process data [LOCALSTATEDIR/run] --libdir=DIR object code libraries [EPREFIX/lib] --includedir=DIR C header files [PREFIX/include] --oldincludedir=DIR C header files for non-gcc [/usr/include] @@ -1339,12 +1334,14 @@ Optional Features: [--disable-linux] --enable-debug-info build glibc/musl/newlibc/libgcc with debug information + --disable-debug-info build glibc and musl without debug infromation --enable-multilib build both RV32 and RV64 runtime libraries (only RV64 for musl libc) [--disable-multilib] --enable-gcc-checking Enable gcc internal checking, it will make gcc very slow, only enable it when developing gcc [--disable-gcc-checking] --disable-gdb Don't build GDB, as it's not upstream + --enable-llvm Build LLVM (clang) --enable-libsanitizer Build libsanitizer, which only supports rv64 --enable-qemu-system Build qemu with system-mode emulation @@ -1382,6 +1379,7 @@ Optional Packages: --with-qemu-src Set qemu source path, use builtin source by default --with-spike-src Set spike source path, use builtin source by default --with-pk-src Set pk source path, use builtin source by default + --with-llvm-src Set llvm source path, use builtin source by default --with-dejagnu-src Set dejagnu source path, use builtin source by default --with-linux-headers-src @@ -3305,7 +3303,7 @@ if test "${enable_debug_info+set}" = set; then : enableval=$enable_debug_info; enable_debug_info=yes else enable_debug_info=no - + enableval=$enable_debug_info; disable_debug_info=yes fi @@ -3582,6 +3580,20 @@ else fi +# Check whether --enable-llvm was given. +if test "${enable_llvm+set}" = set; then : + enableval=$enable_llvm; enable_llvm=yes +fi + + +if test "x$enable_llvm" != xyes; then : + enable_llvm=--disable-llvm + +else + enable_llvm=--enable-llvm + +fi + { @@ -3757,6 +3769,44 @@ fi } { +# Check whether --with-llvm-src was given. +if test "${with_llvm_src+set}" = set; then : + withval=$with_llvm_src; +else + with_llvm_src=default + +fi + + if test "x$with_llvm_src" != xdefault; then : + with_llvm_src=$with_llvm_src + +else + with_llvm_src="\$(srcdir)/llvm" + +fi + + } +{ + +# Check whether --with-dejagnu-src was given. +if test "${with_dejagnu_src+set}" = set; then : + withval=$with_dejagnu_src; +else + with_dejagnu_src=default + +fi + + if test "x$with_dejagnu_src" != xdefault; then : + with_dejagnu_src=$with_dejagnu_src + +else + with_dejagnu_src="\$(srcdir)/dejagnu" + +fi + + } +{ + # Check whether --with-dejagnu-src was given. if test "${with_dejagnu_src+set}" = set; then : withval=$with_dejagnu_src; diff --git a/configure.ac b/configure.ac index 2c9c4dd..9e70bb2 100644 --- a/configure.ac +++ b/configure.ac @@ -58,6 +58,13 @@ AC_ARG_ENABLE(debug_info, ) AS_IF([test "x$enable_debug_info" != xyes], + [AS_HELP_STRING([--disable-debug-info], + [build glibc and musl without debug infromation])], + [disable_debug_info=yes], + [disable_debug_info=no] + ) + +AS_IF([test "x$enable_debug_info" != xyes], [AC_SUBST(debug_info, "")], [AC_SUBST(debug_info, "-g")]) @@ -232,6 +239,17 @@ AS_IF([test "x$enable_gdb" != xno], [AC_SUBST(enable_gdb, --enable-gdb)], [AC_SUBST(enable_gdb, --disable-gdb)]) +AC_ARG_ENABLE(llvm, + [AS_HELP_STRING([--enable-llvm], + [Build LLVM (clang)])], + [enable_llvm=yes], + [] + ) + +AS_IF([test "x$enable_llvm" != xyes], + [AC_SUBST(enable_llvm, --disable-llvm)], + [AC_SUBST(enable_llvm, --enable-llvm)]) + AC_DEFUN([AX_ARG_WITH_SRC], [{m4_pushdef([opt_name], with_$1_src) AC_ARG_WITH($1-src, @@ -255,6 +273,7 @@ AX_ARG_WITH_SRC(gdb, gdb) AX_ARG_WITH_SRC(qemu, qemu) AX_ARG_WITH_SRC(spike, spike) AX_ARG_WITH_SRC(pk, pk) +AX_ARG_WITH_SRC(llvm, llvm) AX_ARG_WITH_SRC(dejagnu, dejagnu) AC_ARG_WITH(linux-headers-src, diff --git a/llvm b/llvm new file mode 160000 +Subproject 185b81e034ba60081023b6e59504dfffb560f3e |