我正在尝试使用Bazel交叉编译nsync,并遇到this question中所述的完全相同错误,即:
.///platform/c++11/platform.h:29:17: fatal error: mutex: No such file or directory
发布该问题的人似乎与我在同一Bazel cross-build tutorial上工作,但是他们对根本原因得出了截然不同的结论(即,他们认为归因于错误的包含是用户错误)路径)。就我而言,所有路径都是正确的,但是它们被nsync的构建忽略/覆盖。我真的可以使用一些帮助来弄清楚需要哪些更改,以便使用Linaro工具链正确构建nsync。
这是一个小的脚本,可以在我的系统上100%地重现该问题:
#!/bin/bash
# File: repro-nsync-error.sh
set -euo pipefail
# Work in a temp folder
mkdir tempxxx && cd tempxxx
# Clone the bits
git clone https://github.com/bazelbuild/bazel.git
git clone https://github.com/google/nsync.git
# Copy custom toolchain example files from the Bazel toolchain tutorial into nsync project
cd nsync
cp -a ../bazel/src/test/shell/bazel/testdata/bazel_toolchain_test_data/compilers .
cp -a ../bazel/src/test/shell/bazel/testdata/bazel_toolchain_test_data/tools/arm_compiler ./tools
cat ../bazel/src/test/shell/bazel/testdata/bazel_toolchain_test_data/WORKSPACE.linaro >> ./WORKSPACE
# Set executable bit on wrapper scripts
chmod +x ./tools/arm_compiler/linaro_linux_gcc/arm-linux-gnueabihf-*
# Nix the `.linaro` extension that the Bazel project uses to 'hide' the
# example files during normal Bazel builds, otherwise Bazel won't 'see' them
for file in $(find -name "*.linaro"); do mv "${file}" "$(dirname ${file})/$(basename ${file%.*})"; done
# Attempt to build
bazel build --verbose_failures --crosstool_top=//tools/arm_compiler:toolchain --cpu=armeabi-v7a //:nsync_cpp
这是我运行它时得到的输出:
$ ./repro-nsync-error.sh
Cloning into 'bazel'...
remote: Counting objects: 305983, done.
remote: Compressing objects: 100% (184/184), done.
remote: Total 305983 (delta 127), reused 273 (delta 104), pack-reused 305624
Receiving objects: 100% (305983/305983), 457.28 MiB | 2.62 MiB/s, done.
Resolving deltas: 100% (188973/188973), done.
Checking connectivity... done.
Cloning into 'nsync'...
remote: Counting objects: 944, done.
remote: Compressing objects: 100% (24/24), done.
remote: Total 944 (delta 10), reused 23 (delta 7), pack-reused 910
Receiving objects: 100% (944/944), 316.81 KiB | 0 bytes/s, done.
Resolving deltas: 100% (496/496), done.
Checking connectivity... done.
WARNING: ignoring http_proxy in environment.
Starting local Bazel server and connecting to it...
.........
INFO: Analysed target //:nsync_cpp (10 packages loaded).
INFO: Found 1 target...
ERROR: /home/evadeflow/Desktop/tempxxx/nsync/BUILD:463:1: C++ compilation of rule '//:nsync_cpp' failed (Exit 1): arm-linux-gnueabihf-gcc failed: error executing command
(cd /home/evadeflow/.cache/bazel/_bazel_evadeflow/595bcf82ccc39f6a61512641b728b082/execroot/__main__ && \
exec env - \
PATH=/home/evadeflow/.virtualenvs/tfbootstrap/bin:/home/evadeflow/.local/bin:/home/evadeflow/.virtualenvs/tfbootstrap/bin:/home/evadeflow/.local/bin:/usr/lib64/qt-3.3/bin:/usr/lib64/ccache:/home/evadeflow/.local/bin:/usr/local/bin:/usr/bin:/home/evadeflow/bin:/usr/local/sbin:/usr/sbin:/home/evadeflow/bin:/home/evadeflow/bin:/home/evadeflow/bin:/home/evadeflow/bin \
PWD=/proc/self/cwd \
tools/arm_compiler/linaro_linux_gcc/arm-linux-gnueabihf-gcc '--sysroot=external/org_linaro_components_toolchain_gcc_5_3_1/arm-linux-gnueabihf/libc' '-mfloat-abi=hard' -nostdinc -isystem external/org_linaro_components_toolchain_gcc_5_3_1/lib/gcc/arm-linux-gnueabihf/5.3.1/include -isystem external/org_linaro_components_toolchain_gcc_5_3_1/arm-linux-gnueabihf/libc/usr/include -isystem external/org_linaro_components_toolchain_gcc_5_3_1/lib/gcc/arm-linux-gnueabihf/5.3.1/include-fixed -isystem external/org_linaro_components_toolchain_gcc_5_3_1/arm-linux-gnueabihf/libc/usr/include -U_FORTIFY_SOURCE -fstack-protector -fPIE '-fdiagnostics-color=always' -Wall -Wunused-but-set-parameter -Wno-free-nonheap-object -fno-omit-frame-pointer -MD -MF bazel-out/armeabi-v7a-fastbuild/bin/_objs/nsync_cpp/internal/dll.pic.d -fPIC -iquote . -iquote bazel-out/armeabi-v7a-fastbuild/genfiles -iquote external/bazel_tools -iquote bazel-out/armeabi-v7a-fastbuild/genfiles/external/bazel_tools -isystem public -isystem bazel-out/armeabi-v7a-fastbuild/genfiles/public -isystem bazel-out/armeabi-v7a-fastbuild/bin/public -x c++ '-std=c++11' -DNSYNC_ATOMIC_CPP11 -DNSYNC_USE_CPP11_TIMEPOINT -I.///platform/c++11 -I.///platform/gcc -I.///platform/arm -I.///public -I.///internal -I.///platform/posix '-D_POSIX_C_SOURCE=200809L' -pthread -no-canonical-prefixes -Wno-builtin-macro-redefined '-D__DATE__="redacted"' '-D__TIMESTAMP__="redacted"' '-D__TIME__="redacted"' -c internal/dll.c -o bazel-out/armeabi-v7a-fastbuild/bin/_objs/nsync_cpp/internal/dll.pic.o)
Use --sandbox_debug to see verbose messages from the sandbox
In file included from internal/dll.c:16:0:
.///platform/c++11/platform.h:29:17: fatal error: mutex: No such file or directory
compilation terminated.
Target //:nsync_cpp failed to build
INFO: Elapsed time: 15.023s, Critical Path: 6.77s
INFO: 0 processes.
FAILED: Build did NOT complete successfully
我怀疑用于nsync的Bazel构建文件根本无法与Bazel定制工具链教程中概述的交叉构建方法配合使用,但是...我对Bazel的经验不足,无法知道如何开始将它们冲压成形...
更新1 :我想出了一个难题。无法编译的文件似乎都带有.c
扩展名,这意味着它们应该是“直接的” C源代码。但是,它们最终会包含platform/c++11/platform.h
,其中包含以下行:
#include <mutex>
工具链的-isystem
标志将切换正确的包含路径-如果文件是使用g++
编译的。但是,它们具有.c
扩展名这一事实意味着使用了arm-linux-gnueabihf-gcc
而不是arm-linux-gnueabihf-g++
,因此没有应用C ++的-isystem
标志,我们最终得到了fatal error: mutex: No such file or directory
。
为了验证这一新兴假设,我编写了以下小脚本:
#!/bin/bash
# File: build.sh
set -euo pipefail
bazel build -s --verbose_failures --crosstool_top=//tools/arm_compiler:toolchain --cpu=armeabi-v7a \
--cxxopt="-isystem external/org_linaro_components_toolchain_gcc_5_3_1/arm-linux-gnueabihf/include/c++/5.3.1/arm-linux-gnueabihf" \
--cxxopt="-isystem external/org_linaro_components_toolchain_gcc_5_3_1/arm-linux-gnueabihf/include/c++/5.3.1" \
--cxxopt="-isystem external/org_linaro_components_toolchain_gcc_5_3_1/include/c++/5.3.1/arm-linux-gnueabihf" \
--cxxopt="-isystem external/org_linaro_components_toolchain_gcc_5_3_1/include/c++/5.3.1" \
//:nsync_cpp
运行此命令时,它失败并出现相同的错误,但是-如果我如下所示s/cxxopt/copt
和s/isystem /I
,则编译成功:
#!/bin/bash
# File: build.sh
set -euo pipefail
bazel build -s --verbose_failures --crosstool_top=//tools/arm_compiler:toolchain --cpu=armeabi-v7a \
--copt="-Iexternal/org_linaro_components_toolchain_gcc_5_3_1/arm-linux-gnueabihf/include/c++/5.3.1/arm-linux-gnueabihf" \
--copt="-Iexternal/org_linaro_components_toolchain_gcc_5_3_1/arm-linux-gnueabihf/include/c++/5.3.1" \
--copt="-Iexternal/org_linaro_components_toolchain_gcc_5_3_1/include/c++/5.3.1/arm-linux-gnueabihf" \
--copt="-Iexternal/org_linaro_components_toolchain_gcc_5_3_1/include/c++/5.3.1" \
//:nsync_cpp
所以...我绝对可以看到在哪里应用了“错误的”编译器标志。但是我不确定解决问题的“正确”方法是什么。以上似乎是一种“强力”方法,可能会有意想不到的副作用[?],因此我仍在寻找更清洁的解决方案。
答案 0 :(得分:3)
问题在于,在CROSSTOOL中,包含互斥标头的include目录仅添加到C ++命令行中。我可以看到这是怎么回事,互斥锁所在的目录是org_linaro_components_toolchain_gcc_5_3_1/arm-linux-gnueabihf/include/c++/5.3.1/mutex
,请注意c++
。如果您认为该目录对于C编译也是有效的,则原则上的解决方法是将CROSSTOOL中的cxx_flag
更改为compiler_flag
。
您是正确的,因为g ++与gcc不同。 https://github.com/bazelbuild/bazel/issues/4644出现问题。但这与您的问题并没有真正的关系,只是没有将cxx_flags放置到C编译命令行中,而不是gcc。还是我错过了什么?
我建议不要依赖Bazel测试数据交叉工具:)