build.sh raw
1 #!/usr/bin/env bash
2 # Copyright (c) 2019-present The Bitcoin Core developers
3 # Distributed under the MIT software license, see the accompanying
4 # file COPYING or http://www.opensource.org/licenses/mit-license.php.
5 export LC_ALL=C
6 set -e -o pipefail
7
8 # shellcheck source=setup.sh
9 source "$(dirname "${BASH_SOURCE[0]}")/setup.sh"
10
11 # Set environment variables to point the NATIVE toolchain to the right
12 # includes/libs
13 NATIVE_GCC="$(store_path gcc-toolchain)"
14
15 # Set native toolchain
16 build_CC="${NATIVE_GCC}/bin/gcc -isystem ${NATIVE_GCC}/include"
17 build_CXX="${NATIVE_GCC}/bin/g++ -isystem ${NATIVE_GCC}/include/c++ -isystem ${NATIVE_GCC}/include"
18
19 case "$HOST" in
20 *darwin*) export LIBRARY_PATH="${NATIVE_GCC}/lib" ;; # Required for native packages
21 *mingw*) export LIBRARY_PATH="${NATIVE_GCC}/lib" ;;
22 *)
23 NATIVE_GCC_STATIC="$(store_path gcc-toolchain static)"
24 export LIBRARY_PATH="${NATIVE_GCC}/lib:${NATIVE_GCC_STATIC}/lib"
25 ;;
26 esac
27
28 # Set environment variables to point the CROSS toolchain to the right
29 # includes/libs for $HOST
30 case "$HOST" in
31 *mingw*)
32 # Determine output paths to use in CROSS_* environment variables
33 CROSS_GLIBC="$(store_path "mingw-w64-x86_64-winpthreads")"
34 CROSS_GCC="$(store_path "gcc-cross-${HOST}")"
35 CROSS_GCC_LIB_STORE="$(store_path "gcc-cross-${HOST}" lib)"
36 CROSS_GCC_LIBS=( "${CROSS_GCC_LIB_STORE}/lib/gcc/${HOST}"/* ) # This expands to an array of directories...
37 CROSS_GCC_LIB="${CROSS_GCC_LIBS[0]}" # ...we just want the first one (there should only be one)
38
39 # The search path ordering is generally:
40 # 1. gcc-related search paths
41 # 2. libc-related search paths
42 # 2. kernel-header-related search paths (not applicable to mingw-w64 hosts)
43 export CROSS_C_INCLUDE_PATH="${CROSS_GCC_LIB}/include:${CROSS_GCC_LIB}/include-fixed:${CROSS_GLIBC}/include"
44 export CROSS_CPLUS_INCLUDE_PATH="${CROSS_GCC}/include/c++:${CROSS_GCC}/include/c++/${HOST}:${CROSS_GCC}/include/c++/backward:${CROSS_C_INCLUDE_PATH}"
45 export CROSS_LIBRARY_PATH="${CROSS_GCC_LIB_STORE}/lib:${CROSS_GCC_LIB}:${CROSS_GLIBC}/lib"
46 ;;
47 *darwin*)
48 # The CROSS toolchain for darwin uses the SDK and ignores environment variables.
49 # See depends/hosts/darwin.mk for more details.
50 ;;
51 *linux*)
52 CROSS_GLIBC="$(store_path "glibc-cross-${HOST}")"
53 CROSS_GLIBC_STATIC="$(store_path "glibc-cross-${HOST}" static)"
54 CROSS_KERNEL="$(store_path "linux-libre-headers-cross-${HOST}")"
55 CROSS_GCC="$(store_path "gcc-cross-${HOST}")"
56 CROSS_GCC_LIB_STORE="$(store_path "gcc-cross-${HOST}" lib)"
57 CROSS_GCC_LIBS=( "${CROSS_GCC_LIB_STORE}/lib/gcc/${HOST}"/* ) # This expands to an array of directories...
58 CROSS_GCC_LIB="${CROSS_GCC_LIBS[0]}" # ...we just want the first one (there should only be one)
59
60 export CROSS_C_INCLUDE_PATH="${CROSS_GCC_LIB}/include:${CROSS_GCC_LIB}/include-fixed:${CROSS_GLIBC}/include:${CROSS_KERNEL}/include"
61 export CROSS_CPLUS_INCLUDE_PATH="${CROSS_GCC}/include/c++:${CROSS_GCC}/include/c++/${HOST}:${CROSS_GCC}/include/c++/backward:${CROSS_C_INCLUDE_PATH}"
62 export CROSS_LIBRARY_PATH="${CROSS_GCC_LIB_STORE}/lib:${CROSS_GCC_LIB}:${CROSS_GLIBC}/lib:${CROSS_GLIBC_STATIC}/lib"
63 ;;
64 *)
65 exit 1 ;;
66 esac
67
68 # Sanity check CROSS_*_PATH directories
69 IFS=':' read -ra PATHS <<< "${CROSS_C_INCLUDE_PATH}:${CROSS_CPLUS_INCLUDE_PATH}:${CROSS_LIBRARY_PATH}"
70 for p in "${PATHS[@]}"; do
71 if [ -n "$p" ] && [ ! -d "$p" ]; then
72 echo "'$p' doesn't exist or isn't a directory... Aborting..."
73 exit 1
74 fi
75 done
76
77 # Determine the correct value for -Wl,--dynamic-linker for the current $HOST
78 case "$HOST" in
79 *linux*)
80 glibc_dynamic_linker=$(
81 case "$HOST" in
82 x86_64-linux-gnu) echo /lib64/ld-linux-x86-64.so.2 ;;
83 arm-linux-gnueabihf) echo /lib/ld-linux-armhf.so.3 ;;
84 aarch64-linux-gnu) echo /lib/ld-linux-aarch64.so.1 ;;
85 riscv64-linux-gnu) echo /lib/ld-linux-riscv64-lp64d.so.1 ;;
86 powerpc64-linux-gnu) echo /lib64/ld64.so.1;;
87 powerpc64le-linux-gnu) echo /lib64/ld64.so.2;;
88 *) exit 1 ;;
89 esac
90 )
91 ;;
92 esac
93
94 ####################
95 # Depends Building #
96 ####################
97
98 # Build the depends tree, overriding variables that assume multilib gcc
99 make -C depends --jobs="$JOBS" HOST="$HOST" \
100 ${V:+V=1} \
101 ${SOURCES_PATH+SOURCES_PATH="$SOURCES_PATH"} \
102 ${BASE_CACHE+BASE_CACHE="$BASE_CACHE"} \
103 ${SDK_PATH+SDK_PATH="$SDK_PATH"} \
104 ${build_CC+build_CC="$build_CC"} \
105 ${build_CXX+build_CXX="$build_CXX"} \
106 x86_64_linux_CC=x86_64-linux-gnu-gcc \
107 x86_64_linux_CXX=x86_64-linux-gnu-g++ \
108 x86_64_linux_AR=x86_64-linux-gnu-gcc-ar \
109 x86_64_linux_RANLIB=x86_64-linux-gnu-gcc-ranlib \
110 x86_64_linux_NM=x86_64-linux-gnu-gcc-nm \
111 x86_64_linux_STRIP=x86_64-linux-gnu-strip
112
113 case "$HOST" in
114 *darwin*)
115 # Unset now that Qt is built
116 unset LIBRARY_PATH
117 ;;
118 esac
119
120 ###########################
121 # Binary Tarball Building #
122 ###########################
123
124 # CONFIGFLAGS
125 CONFIGFLAGS="-DREDUCE_EXPORTS=ON -DBUILD_BENCH=OFF -DBUILD_GUI_TESTS=OFF -DBUILD_FUZZ_BINARY=OFF -DCMAKE_SKIP_RPATH=TRUE"
126
127 # CFLAGS
128 HOST_CFLAGS="-O2 -g"
129 HOST_CFLAGS+=$(find /gnu/store -maxdepth 1 -mindepth 1 -type d -exec echo -n " -ffile-prefix-map={}=/usr" \;)
130 HOST_CFLAGS+=" -fdebug-prefix-map=${DISTSRC}/src=."
131 case "$HOST" in
132 *mingw*) HOST_CFLAGS+=" -fno-ident" ;;
133 *darwin*) unset HOST_CFLAGS ;;
134 esac
135
136 # CXXFLAGS
137 HOST_CXXFLAGS="$HOST_CFLAGS"
138
139 case "$HOST" in
140 arm-linux-gnueabihf) HOST_CXXFLAGS="${HOST_CXXFLAGS} -Wno-psabi" ;;
141 esac
142
143 # LDFLAGS
144 case "$HOST" in
145 *linux*) HOST_LDFLAGS="-Wl,--as-needed -Wl,--dynamic-linker=$glibc_dynamic_linker -Wl,-O2" ;;
146 *mingw*) HOST_LDFLAGS="-Wl,--no-insert-timestamp" ;;
147 esac
148
149 # EXE FLAGS
150 case "$HOST" in
151 *linux*) CMAKE_EXE_LINKER_FLAGS="-DCMAKE_EXE_LINKER_FLAGS=${HOST_LDFLAGS} -static-libstdc++ -static-libgcc" ;;
152 esac
153
154 mkdir -p "$DISTSRC"
155 (
156 cd "$DISTSRC"
157
158 # Extract the source tarball
159 tar --strip-components=1 -xf "${GIT_ARCHIVE}"
160
161 # Configure this DISTSRC for $HOST
162 # shellcheck disable=SC2086
163 env CFLAGS="${HOST_CFLAGS}" CXXFLAGS="${HOST_CXXFLAGS}" LDFLAGS="${HOST_LDFLAGS}" \
164 cmake -S . -B build \
165 --toolchain "${BASEPREFIX}/${HOST}/toolchain.cmake" \
166 -DWITH_CCACHE=OFF \
167 -Werror=dev \
168 ${CONFIGFLAGS} \
169 ${CMAKE_EXE_LINKER_FLAGS+"$CMAKE_EXE_LINKER_FLAGS"}
170
171 # Build Bitcoin Core
172 cmake --build build -j "$JOBS"
173
174 mkdir -p "$OUTDIR"
175
176 # Make the os-specific installers
177 case "$HOST" in
178 *mingw*)
179 cmake --build build -j "$JOBS" -t deploy
180 mv build/bitcoin-win64-setup.exe "${OUTDIR}/${DISTNAME}-win64-setup-unsigned.exe"
181 ;;
182 esac
183
184 # Setup the directory where our Bitcoin Core build for HOST will be
185 # installed. This directory will also later serve as the input for our
186 # binary tarballs.
187 mkdir -p "${INSTALLPATH}"
188 # Install built Bitcoin Core to $INSTALLPATH
189 case "$HOST" in
190 *darwin*)
191 cmake --install build --strip --prefix "${INSTALLPATH}"
192 ;;
193 *)
194 cmake --install build --prefix "${INSTALLPATH}"
195 ;;
196 esac
197
198 # Perform basic security checks on installed executables.
199 echo "Checking binary security on installed executables..."
200 python3 "${DISTSRC}/contrib/guix/security-check.py" "${INSTALLPATH}/bin/"* "${INSTALLPATH}/libexec/"*
201 # Check that executables only contain allowed version symbols.
202 echo "Running symbol and dynamic library checks on installed executables..."
203 python3 "${DISTSRC}/contrib/guix/symbol-check.py" "${INSTALLPATH}/bin/"* "${INSTALLPATH}/libexec/"*
204 ) # $DISTSRC
205
206 # shellcheck source=package.sh
207 source "$(dirname "${BASH_SOURCE[0]}")/package.sh"
208