forked from mindspore-ai/mindquantum
-
Notifications
You must be signed in to change notification settings - Fork 0
/
build.sh
executable file
·435 lines (355 loc) · 14.8 KB
/
build.sh
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
#!/bin/bash
# Copyright 2021 Huawei Technologies Co., Ltd
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
# shellcheck disable=SC2154,SC2034
BASEPATH=$( cd -- "$( dirname -- "${BASH_SOURCE[0]:-$0}" )" &> /dev/null && pwd )
ROOTDIR="$BASEPATH"
PROGRAM=$(basename "${BASH_SOURCE[0]:-$0}")
echo "Called with: $*"
# Test for MindSpore CI
_IS_MINDSPORE_CI=0
if [[ "${JENKINS_URL:-0}" =~ https?://build.mindspore.cn && ! "${CI:-0}" =~ ^(false|0)$ ]]; then
echo "Detected MindSpore/MindQuantum CI"
_IS_MINDSPORE_CI=1
fi
if [[ "${DEVCLOUD_CI:-0}" == "1" ]]; then
echo "Detected MindSpore/MindQuantum CI"
_IS_MINDSPORE_CI=1
fi
# ==============================================================================
# Load common bash helper functions
. "$ROOTDIR/scripts/build/common_functions.sh"
check_for_verbose "$@"
# ------------------------------------------------------------------------------
# Default values for this particular script
python_extra_pkgs=('wheel-filename>1.2' 'build==0.9.0')
if [ "$(uname)" == "Linux" ]; then
LD_PATH_VAR=LD_LIBRARY_PATH
elif [ "$(uname)" == "Darwin" ]; then
LD_PATH_VAR=DYLD_LIBRARY_PATH
else
die "Unsupported platform (only Linux and macOS are supported"
fi
if [ "$_IS_MINDSPORE_CI" -eq 1 ]; then
for var in CUDA_HOME CUDA_PATH; do
if [ -n "${!var}" ]; then
echo "$var = ${!var}"
if [ ! -d "${!var}" ]; then
print_warning "$var is set, but location does not exist!"
else
echo "Adding $var/lib64 and $var/lib to LD_LIBRARY_PATH"
if [ -z "${!LD_PATH_VAR}" ]; then
export ${LD_PATH_VAR}="${!var}/lib64:${!var}/lib"
else
export ${LD_PATH_VAR}="${!LD_PATH_VAR}:${!var}/lib64:${!var}/lib"
fi
fi
fi
done
PY_EXEC="$(which python)"
echo '----------------------------------------'
echo 'Environment info'
echo "PATH = $PATH"
echo "${LD_PATH_VAR} = ${!LD_PATH_VAR}"
echo '----------------------------------------'
echo "PY_EXEC = $PY_EXEC"
echo '----------------------------------------'
echo 'System Python environment'
"$PY_EXEC" -m pip freeze
echo '----------------------------------------'
if [[ "$(uname)" == "Darwin" ]]; then
if [ -z "$MACOSX_DEPLOYMENT_TARGET" ]; then
MACOSX_DEPLOYMENT_TARGET=10.15
fi
export MACOSX_DEPLOYMENT_TARGET="$MACOSX_DEPLOYMENT_TARGET"
if [ -z "$_PYTHON_HOST_PLATFORM" ]; then
_PYTHON_HOST_PLATFORM="macosx-${MACOSX_DEPLOYMENT_TARGET}-$(uname -m)"
fi
export _PYTHON_HOST_PLATFORM="$_PYTHON_HOST_PLATFORM"
echo "MACOSX_DEPLOYMENT_TARGET = $MACOSX_DEPLOYMENT_TARGET"
echo "_PYTHON_HOST_PLATFORM = $_PYTHON_HOST_PLATFORM"
echo '----------------------------------------'
fi
verbose=1
set_var cmake_debug_mode true
set_var enable_gitee true
set_var enable_gpu true
mkdir -p ~/.config/pip
echo "[global]" > ~/.config/pip/pip.conf
echo "index-url = http://mirrors.aliyun.com/pypi/simple/" >> ~/.config/pip/pip.conf
echo "trusted-host = mirrors.aliyun.com" >> ~/.config/pip/pip.conf
fi
# ==============================================================================
function help_header() {
echo 'Build binary Python wheel for MindQunantum'
echo ''
echo 'This is mainly relevant for developers that want to deploy MindQuantum '
echo 'on machines other than their own.'
echo ''
echo 'This script will create a Python virtualenv in the MindQuantum root'
echo 'directory and then build a binary Python wheel of MindQuantum.'
}
function extra_help() {
echo 'Extra options:'
echo ' --(no-)build-isolation Pass --no-isolation to python3 -m build'
echo ' --(no-)delocate Delocate the binary wheels after build is finished'
echo ' (enabled by default; pass --no-delocate to disable)'
echo ' --(no-)fast-build If possible use an existing CMake directory to build the C++ Python extensions'
echo ' instead of using the normal Python bdist_wheel process. Assumes that '
echo ' IN_PLACE_BUILD=ON'
echo ' Use this with caution. CI build should not be using this.'
echo ' --fast-build-dir Specify build directory when performing a fast-build'
echo ' -o,--output=[dir] Output directory for built wheels'
echo ' -p,--plat-name=[dir] Platform name to use for wheel delocation'
echo ' (only effective if --delocate is used)'
echo -e '\nExample calls:'
echo "$PROGRAM"
echo "$PROGRAM --gpu"
echo "$PROGRAM --cxx --with-boost --without-gmp --venv=/tmp/venv"
}
# ==============================================================================
getopts_args_extra='o:p:'
function parse_extra_args() {
# input args: OPT OPTARG flag_value
case "$1" in
fast-build ) no_arg;
set_var fast_build "$3"
;;
fast-build-dir ) needs_arg;
set_var fast_build_dir "$2"
;;
delocate ) no_arg;
set_var delocate_wheel "$3"
;;
build-isolation ) no_arg;
set_var build_isolation "$3"
;;
o | output ) needs_arg;
set_var output_path "$2"
;;
p | plat-name ) needs_arg;
set_var platform_name "$2"
;;
??* ) return 2 # Delegate error handling to main argument parsing function
;;
esac
}
# NB: using the default values from parse_common_args.sh
. "$ROOTDIR/scripts/build/parse_common_args.sh"
# ------------------------------------------------------------------------------
# Locate python or python3
. "$ROOTDIR/scripts/build/locate_python3.sh"
# ==============================================================================
set -e
cd "${ROOTDIR}"
# ------------------------------------------------------------------------------
# NB: `created_venv` variable can be used to detect if a virtualenv was created or not
. "$ROOTDIR/scripts/build/python_virtualenv_activate.sh"
# ------------------------------------------------------------------------------
# Locate cmake or cmake3
# NB: `cmake_from_venv` variable is set by this script (and is used by python_virtualenv_update.sh)
. "$ROOTDIR/scripts/build/locate_cmake.sh"
# ------------------------------------------------------------------------------
# Locate ninja if needed
if [ "$cmake_generator" == "Ninja" ]; then
# NB: `ninja_from_venv` variable is set by this script (and is used by python_virtualenv_update.sh)
. "$ROOTDIR/scripts/build/locate_ninja.sh"
fi
# -----------------------------------------------------------------------------------------
# Locate patchelf
if [[ "$delocate_wheel" -eq 1 && "$(uname -s)" == "Linux" ]]; then
if ! command -v patchelf > /dev/null 2>&1; then
echo "Installing patchelf inside the Python virtual environment"
call_cmd "$PYTHON" -m pip install patchelf
fi
fi
# ------------------------------------------------------------------------------
# Update Python virtualenv (if requested/necessary)
. "$ROOTDIR/scripts/build/python_virtualenv_update.sh"
# ------------------------------------------------------------------------------
# Setup arguments for build
args=()
declare_AA cmake_option_names
set_AA cmake_option_names cmake_debug_mode ENABLE_CMAKE_DEBUG
set_AA cmake_option_names do_clean_3rdparty CLEAN_3RDPARTY_INSTALL_DIR
set_AA cmake_option_names enable_analyzer ENABLE_ANALYZER
set_AA cmake_option_names enable_gitee ENABLE_GITEE
set_AA cmake_option_names enable_gpu ENABLE_CUDA
set_AA cmake_option_names enable_logging ENABLE_LOGGING
set_AA cmake_option_names enable_tests BUILD_TESTING
set_AA cmake_option_names logging_enable_debug ENABLE_LOGGING_DEBUG_LEVEL
set_AA cmake_option_names logging_enable_trace ENABLE_LOGGING_TRACE_LEVEL
for var in $(get_AA_keys cmake_option_names); do
if [ "${!var}" -eq 1 ]; then
args+=(--set "$(get_AA_value cmake_option_names "$var")")
else
args+=(--unset "$(get_AA_value cmake_option_names "$var")")
fi
done
if [ "$_IS_MINDSPORE_CI" -eq 1 ]; then
args+=(--set MINDSPORE_CI)
fi
if [ "$cmake_make_silent" -eq 0 ]; then
args+=(--set USE_VERBOSE_MAKEFILE)
else
args+=(--unset USE_VERBOSE_MAKEFILE)
fi
if [ "$cmake_no_registry" -eq 1 ]; then
args+=(--unset CMAKE_FIND_USE_PACKAGE_REGISTRY)
args+=(--unset CMAKE_FIND_PACKAGE_NO_SYSTEM_PACKAGE_REGISTRY)
else
args+=(--set CMAKE_FIND_USE_PACKAGE_REGISTRY)
args+=(--set CMAKE_FIND_PACKAGE_NO_SYSTEM_PACKAGE_REGISTRY)
fi
if [ -n "$cmake_generator" ]; then
args+=(-G "${cmake_generator}")
fi
if [ "$fast_build" -eq 1 ]; then
args+=(bdist_wheel --fast-build)
if [ -n "$fast_build_dir" ]; then
args+=(bdist_wheel --fast-build-dir="$fast_build_dir")
fi
fi
if [ "$n_jobs" -ne -1 ]; then
args+=(--var JOBS "$n_jobs")
args+=(build_ext --jobs="$n_jobs")
fi
if [[ "$build_type" == 'Debug' ]]; then
args+=(build --debug)
fi
if [ "${_build_dir_was_set:-0}" -eq 1 ]; then
args+=(build_ext --build-dir "$build_dir")
fi
local_pkgs_str=$(join_by , "${local_pkgs[@]}")
if [[ "$force_local_pkgs" -eq 1 ]]; then
args+=(--var MQ_FORCE_LOCAL_PKGS all)
elif [ -n "$local_pkgs_str" ]; then
args+=(--var MQ_FORCE_LOCAL_PKGS "$local_pkgs_str")
fi
# --------------------------------------
if [[ "$enable_gpu" -eq 1 && -n "$cuda_arch" ]]; then
print_warning "--cuda-arch is unsupported (thus ignored) with $PROGRAM!"
fi
if [ "$enable_ccache" -eq 1 ]; then
ccache_exec=""
if command -v ccache > /dev/null 2>&1; then
ccache_exec=ccache
elif command -v sccache > /dev/null 2>&1; then
ccache_exec=sccache
fi
if [ -n "$ccache_exec" ]; then
ccache_exec=$(which "$ccache_exec")
args+=(--var CMAKE_C_COMPILER_LAUNCHER "$ccache_exec")
args+=(--var CMAKE_CXX_COMPILER_LAUNCHER "$ccache_exec")
if [ "$enable_gpu" -eq 1 ]; then
args+=(--var CMAKE_CUDA_COMPILER_LAUNCHER "$ccache_exec")
fi
fi
fi
# NB: CMake < 3.24 typically set CC, CXX during the first run, which basically overwrites the values in CC, CXX. In
# order to work around that, we explicitly set the compilers using the related CMake variables.
if [ -n "$CC" ]; then
args+=(--var CMAKE_C_COMPILER "$CC")
fi
if [ -n "$CXX" ]; then
args+=(--var CMAKE_CXX_COMPILER "$CXX")
fi
if [ -n "$CUDACXX" ]; then
args+=(--var CMAKE_CUDA_COMPILER "$CUDACXX")
fi
debug_print "Will be passing these arguments to setup.py:"
debug_print " ${args[*]}"
# ==============================================================================
if [ "$enable_gpu" -eq 1 ]; then
# Older CMake using find_package(CUDA) would rely on CUDA_HOME, but newer CMake only look at CUDACXX and CUDA_PATH
if [[ -n "$CUDA_HOME" && -z "$CUDA_PATH" ]]; then
echo 'CUDA_HOME is defined, but CUDA_PATH is not. Setting CUDA_PATH=CUDA_HOME'
export CUDA_PATH="$CUDA_HOME"
fi
debug_print "CUDA_PATH = $CUDA_PATH"
fi
# ==============================================================================
# Convert the CMake arguments for passing them using -C to python3 -m build
fixed_args=()
for arg in "${args[@]}"; do
fixed_args+=("-C--global-option=$arg")
done
args=("-w")
if [ "$build_isolation" -eq 0 ]; then
args+=("--no-isolation")
fi
# ------------------------------------------------------------------------------
# Clean build directory if requested and possible
temp_build_dir=$("$PYTHON" -m mindquantum_config --tempdir)
if [ "${_build_dir_was_set:-0}" -eq 1 ]; then
build_dir_for_cleaning="$build_dir"
elif [ -d "$temp_build_dir" ]; then
build_dir_for_cleaning="$temp_build_dir"
fi
if [ -n "$build_dir_for_cleaning" ]; then
if [ "$do_clean_build_dir" -eq 1 ]; then
echo "Deleting build folder: $build_dir_for_cleaning"
call_cmd rm -rf "$build_dir_for_cleaning"
elif [ "$do_clean_cache" -eq 1 ]; then
echo "Removing CMake cache at: $build_dir_for_cleaning/CMakeCache.txt"
call_cmd rm -f "$build_dir_for_cleaning/CMakeCache.txt"
echo "Removing CMake files at: $build_dir_for_cleaning/CMakeFiles"
call_cmd rm -rf "$build_dir_for_cleaning/CMakeFiles"
echo "Removing CMake files at: $build_dir_for_cleaning/cmake-ldtest*"
call_cmd rm -rf "$build_dir_for_cleaning/cmake-ldtest*"
fi
fi
# ------------------------------------------------------------------------------
# Build the wheels
env_vars=()
if [[ "$cmake_generator" == "Ninja" || "$cmake_generator" == "Ninja Multi-Config" ]]; then
env_vars+=(MQ_USE_NINJA=1)
fi
if [ "$delocate_wheel" -eq 1 ]; then
env_vars+=(MQ_DELOCATE_WHEEL=1
"${LD_PATH_VAR}=${!LD_PATH_VAR}")
if [[ "${_build_dir_was_set:-0}" -eq 1 || "${fast_build:-0}" -eq 1 ]]; then
build_dir_for_env="$build_dir"
elif [ "${_fast_build_dir_was_set:-0}" -eq 1 ]; then
build_dir_for_env="$fast_build_dir"
else
build_dir_for_env=$("$PYTHON" -m mindquantum_config --tempdir)
fi
if [ "$_IS_MINDSPORE_CI" -eq 1 ]; then
env_vars+=(MQ_LIB_PATHS="$ROOTDIR/ld_library_paths.txt")
else
env_vars+=(MQ_LIB_PATHS="$build_dir_for_env/ld_library_paths.txt")
fi
env_vars+=(MQ_BUILD_DIR="$build_dir_for_env")
if [ -n "$platform_name" ]; then
env_vars+=(MQ_DELOCATE_WHEEL_PLAT="$platform_name")
fi
fi
call_cmd env "${env_vars[@]}" "${PYTHON}" -m build "${args[@]}" "${fixed_args[@]}" "$@"
# ------------------------------------------------------------------------------
# Move the wheels to the output directory
if [[ -d "${output_path}" ]];then
call_cmd rm -rf "${output_path}"
fi
call_cmd mkdir -pv "${output_path}"
call_cmd mv -v "$ROOTDIR/dist/"*whl* "${output_path}"
if [[ "$_IS_MINDSPORE_CI" -eq 1 && "$(uname)" == 'Linux' ]]; then
suffix="-manylinux_2_27_$(uname -m)"
for ext in ".whl" ".whl.sha256"; do
for wheel in "${output_path}"/*"${suffix}${ext}"; do
call_cmd cp -v "$wheel" "${wheel%"${suffix}${ext}"}-linux_$(uname -m)${ext}"
done
done
fi
echo "------Successfully created mindquantum package------"