最近,我正在使用 cmake 和llvm clang 使用 Visual Studio Code 使用 clang clang clang clang clang clang clang >每个确切的对象或库会生成或取决于需要明确指定以进行或链接的需求。设计的程序应具有较高的RAM效率,对于未使用的数据段引起的最小漏洞和交叉兼容的安全性。
话虽如此,架构的配置库,应用程序二进制接口(又称ABI),C和C ++标准的标准库功能以及可执行的二进制二进制二进制需求手册设置用于工具链程序以适当的方式处理。
好吧,我认为,用libc ++库的libstdc ++替换是一个很好的“切入点”,但绝对不是直截了当的,您可能已经从其他地方有足够的痛苦实践中学到了足够多的东西,并认为这是一个糟糕的主意。 。但很抱歉,这已成为我的痴迷。我非常感谢您的帮助,然后它使我在这里发疯。
无论如何,以下是有关我本地计算机的信息列表:
- ubuntu 20.04 @ v5.13.0-40基因内核,SMP,x86_64指令集
- CMake 3.23.1,由源
- GCC-10构建:AMD64
- Clang-12: AMD64
- LIBSTDC ++ -10-DEV:AMD64
- LIBC ++ -12-DEV:AMD64
Clang可以从命令返回:
jacob.nielson@ubuntu~jul:clang ++ -12 -V -C -xc/dev/null

尽可能出乎意料且无关紧要的问题,我将项目目录布局尽可能简单,在制作cmakelists.txt:
https://s3.bmp.ovh/imgs/2022/05/05/06/3ebb5a1a1a1a1a08fa08fa08fa0274.4.plgng首先,我在Cmake的文档中查找了有关编译(预处理)或链接选项的文档:
-"-nostdinc"
-"-nostdinc++"
-"-nobuiltininc"
-"-nostdlib"
-"-nolibc"
-"-nostdlib++"
-"-nodefaultlibs"
中提出了一些简单的线条。
cmake_minimum_required(VERSION 3.23.0)
project(program VERSION 0.0.1)
set(TARGET program)
add_compile_options(-std=c++17)
# I'm not sure about semantics of "-nostdinc++", "-nostdinc" and "-nobuiltininc".
# Should I add them all in case to substitute libstdc++ with libc++ or not in below?
add_compile_options($<$<COMPILE_LANG_AND_ID:CXX,Clang>:-nobuiltininc>)
add_compile_options($<$<COMPILE_LANG_AND_ID:CXX,Clang>:-nostdinc++>)
add_compile_options($<$<COMPILE_LANG_AND_ID:CXX,Clang>:-nostdinc>)
# Should I add path to system headers in "-isystem" option?
# Attention: cmake-generator-expression does not recognize white-space separated options group to be string. It is option "-isystem" where the path to directory as value follows without white-space in this example.
add_compile_options(
$<$<COMPILE_LANG_AND_ID:CXX,Clang>:-isystem/usr/include/x86_64-linux-gnu>
$<$<COMPILE_LANG_AND_ID:CXX,Clang>:-isystem-after/usr/include>
# "-cxx-isystem" option is legacy and is not appropriate for standard headers. Add path to the subdirectories where you put your own c++-only headers in your project.
$<$<COMPILE_LANG_AND_ID:CXX,Clang>:-cxx-isystem ${...}>
)
# If C or/and C++ standard library is turned off like in above, Should I add path to libc++ headers in "-stdlib++-isystem" option?
# Attention: cmake-generator-expression does not recognize white-space separated options group to be string. It is option "-stdlib++-isystem" where the path to directory as value follows without white-space in this example.
add_compile_options($<$<COMPILE_LANG_AND_ID:CXX,Clang>:-stdlib++-isystem/usr/lib/llvm-12/include/c++/v1>)
# Replace default C++ standard with libc++.
add_link_options(
$<$<LINK_LANG_AND_ID:CXX,Clang>:-stdlib=libc++>
)
add_executable(${TARGET} "${CMAKE_CURRENT_SOURCE_DIR}/source/${TARGET}.cpp")
target_link_libraries(${TARGET} PRIVATE
$<$<LINK_LANG_AND_ID:CXX,Clang>:c++>
$<$<LINK_LANG_AND_ID:CXX,Clang>:c++abi>
$<$<LINK_LANG_AND_ID:CXX,Clang>:unwind>
$<$<LINK_LANG_AND_ID:CXX,Clang>:ssl>
$<$<LINK_LANG_AND_ID:CXX,Clang>:crypto>
$<$<LINK_LANG_AND_ID:CXX,Clang>:pthread>
)
然后我
在CMakelists =“ https://s3.bmp.ovh/imgs/2022/05/06/4e169b31361de09a.png” rel =“ nofollow noreferrer”> 
CMake parsed successfully:
” > cmakeccompiler.cmake 和 cmakecxxcompiler.cmake
in ./ build> ./ build/cmakefiles/3.23.1/
临时文件夹,后来包含几行:
set(CMAKE_CXX_IMPLICIT_INCLUDE_DIRECTORIES "/usr/include/c++/10;/usr/include/x86_64-linux-gnu/c++/10;/usr/include/c++/10/backward;/usr/local/include;/usr/lib/llvm-12/lib/clang/12.0.0/include;/usr/include/x86_64-linux-gnu;/usr/include")
set(CMAKE_CXX_IMPLICIT_LINK_LIBRARIES "stdc++;m;gcc_s;gcc;c;gcc_s;gcc")
set(CMAKE_CXX_IMPLICIT_LINK_DIRECTORIES "/usr/lib/gcc/x86_64-linux-gnu/10;/usr/lib/x86_64-linux-gnu;/usr/lib64;/lib/x86_64-linux-gnu;/lib64;/usr/lib;/usr/lib/llvm-12/lib;/lib")
set(CMAKE_CXX_IMPLICIT_LINK_FRAMEWORK_DIRECTORIES "")
注意:clang:clang :clang:clang:clang使用启发式发现来搜索前端报告的目录中的标题。
这是不合适的,因为我只是不希望LIBSTDC ++的标题或库中隐式使用。
另外,它将编译命令导出到 compile_commands.json
如下:
/usr/bin/clang++-12 -DLIBCXXABI_USE_COMPILER_RT=YES -DLIBCXX_USE_COMPILER_RT=YES -I/data/solution/projects/program/include -std=c++17 -stdlib=libc++ -isystem /usr/include/x86_64-linux-gnu -stdlib++-isystem /usr/lib/llvm-12/include/c++/v1 -o CMakeFiles/program.dir/source/program.cpp.o -c /data/solution/projects/program/source/program.cpp
一切看起来都不错。但是当我使用LDD检查时:
jacob.nielson@ubuntu:/data/data/doady/projection/proginse/progress/build/debug $ ldd program
linux-vdso.so.1 (0x00007ffee7190000)
libc++.so.1 => /lib/x86_64-linux-gnu/libc++.so.1 (0x00007f69164a5000)
libc++abi.so.1 => /lib/x86_64-linux-gnu/libc++abi.so.1 (0x00007f691646d000)
libstdc++.so.6 => /lib/x86_64-linux-gnu/libstdc++.so.6 (0x00007f691628b000) /* LIBSTDC++ in here! */
libm.so.6 => /lib/x86_64-linux-gnu/libm.so.6 (0x00007f691613c000) /* LIBM in here */
libgcc_s.so.1 => /lib/x86_64-linux-gnu/libgcc_s.so.1 (0x00007f6916121000) /* gcc startup file in here! */
libc.so.6 => /lib/x86_64-linux-gnu/libc.so.6 (0x00007f6915f2f000) /* LIBC in here! */
libpthread.so.0 => /lib/x86_64-linux-gnu/libpthread.so.0 (0x00007f6915f0a000)
librt.so.1 => /lib/x86_64-linux-gnu/librt.so.1 (0x00007f6915f00000)
libatomic.so.1 => /lib/x86_64-linux-gnu/libatomic.so.1 (0x00007f6915ef6000)
/lib64/ld-linux-x86-64.so.2 (0x00007f691658d000)
看到所有libstdc ++,libc,libc,libm或libgcc_s仍然令人沮丧。我是否错过了静态链接它们的任何选择,例如gnu cc中的-Static -libc,还是我必须在此时早期放弃自己的野心?
Recently I'm configuring a new project in language C and C++ using both CMake and llvm Clang with Visual Studio Code for a program where EVERY exact object or library it generates or depends needs specifying explicitly to make or link against. The program by design should feature high RAM efficency, security for the least vulnerabilities induced by the unused data segments and cross-compilation.
That being said, the provision libraries for architecture, application binary interface (aka ABIs), standard libraries functions from C and C++ standard and executable binary need manual setup for toolchain program to process in appropriate manner.
Well, the libstdc++ substitution with libc++ library is what I think a good "entry point" to kick-off, but definitely not straight forward, which you might have learned enough from documented painful practices elsewhere and think of that as a bad idea...but I'm sorry, this has become my obsession. I really appreciate your help before it drives me nuts here.
Anyway, here is a list of information about my local machine in below:
- Ubuntu 20.04 @ v5.13.0-40-generic kernel, SMP, x86_64 instruction-set
- CMake 3.23.1, built from source
- gcc-10:amd64
- clang-12:amd64
- libstdc++-10-dev:amd64
- libc++-12-dev:amd64
Clang works fine to return from command:
jacob.nielson@ubuntu~$: clang++-12 -v -c -xc /dev/null

to keep the new project from any future unexpected and irrelevant issue as much as possible, I leave the project directory layout as simple as it could be before making a CMakeLists.txt:

To begin with, I looked up in CMake's document about either compiling (preprocessing) or linking options:
-"-nostdinc"
-"-nostdinc++"
-"-nobuiltininc"
-"-nostdlib"
-"-nolibc"
-"-nostdlib++"
-"-nodefaultlibs"
Then I come up with a few simple lines in the CMakeLists.txt:
cmake_minimum_required(VERSION 3.23.0)
project(program VERSION 0.0.1)
set(TARGET program)
add_compile_options(-std=c++17)
# I'm not sure about semantics of "-nostdinc++", "-nostdinc" and "-nobuiltininc".
# Should I add them all in case to substitute libstdc++ with libc++ or not in below?
add_compile_options(lt;lt;COMPILE_LANG_AND_ID:CXX,Clang>:-nobuiltininc>)
add_compile_options(lt;lt;COMPILE_LANG_AND_ID:CXX,Clang>:-nostdinc++>)
add_compile_options(lt;lt;COMPILE_LANG_AND_ID:CXX,Clang>:-nostdinc>)
# Should I add path to system headers in "-isystem" option?
# Attention: cmake-generator-expression does not recognize white-space separated options group to be string. It is option "-isystem" where the path to directory as value follows without white-space in this example.
add_compile_options(
lt;lt;COMPILE_LANG_AND_ID:CXX,Clang>:-isystem/usr/include/x86_64-linux-gnu>
lt;lt;COMPILE_LANG_AND_ID:CXX,Clang>:-isystem-after/usr/include>
# "-cxx-isystem" option is legacy and is not appropriate for standard headers. Add path to the subdirectories where you put your own c++-only headers in your project.
lt;lt;COMPILE_LANG_AND_ID:CXX,Clang>:-cxx-isystem ${...}>
)
# If C or/and C++ standard library is turned off like in above, Should I add path to libc++ headers in "-stdlib++-isystem" option?
# Attention: cmake-generator-expression does not recognize white-space separated options group to be string. It is option "-stdlib++-isystem" where the path to directory as value follows without white-space in this example.
add_compile_options(lt;lt;COMPILE_LANG_AND_ID:CXX,Clang>:-stdlib++-isystem/usr/lib/llvm-12/include/c++/v1>)
# Replace default C++ standard with libc++.
add_link_options(
lt;lt;LINK_LANG_AND_ID:CXX,Clang>:-stdlib=libc++>
)
add_executable(${TARGET} "${CMAKE_CURRENT_SOURCE_DIR}/source/${TARGET}.cpp")
target_link_libraries(${TARGET} PRIVATE
lt;lt;LINK_LANG_AND_ID:CXX,Clang>:c++>
lt;lt;LINK_LANG_AND_ID:CXX,Clang>:c++abi>
lt;lt;LINK_LANG_AND_ID:CXX,Clang>:unwind>
lt;lt;LINK_LANG_AND_ID:CXX,Clang>:ssl>
lt;lt;LINK_LANG_AND_ID:CXX,Clang>:crypto>
lt;lt;LINK_LANG_AND_ID:CXX,Clang>:pthread>
)
Next, I tried to generate "Unix Makefiles" for project:

CMake parsed successfully:

Meanwhile it generates CMakeCCompiler.cmake
and CMakeCXXCompiler.cmake
in ./build/CMakeFiles/3.23.1/
temporary folder, the later contains a few lines:
set(CMAKE_CXX_IMPLICIT_INCLUDE_DIRECTORIES "/usr/include/c++/10;/usr/include/x86_64-linux-gnu/c++/10;/usr/include/c++/10/backward;/usr/local/include;/usr/lib/llvm-12/lib/clang/12.0.0/include;/usr/include/x86_64-linux-gnu;/usr/include")
set(CMAKE_CXX_IMPLICIT_LINK_LIBRARIES "stdc++;m;gcc_s;gcc;c;gcc_s;gcc")
set(CMAKE_CXX_IMPLICIT_LINK_DIRECTORIES "/usr/lib/gcc/x86_64-linux-gnu/10;/usr/lib/x86_64-linux-gnu;/usr/lib64;/lib/x86_64-linux-gnu;/lib64;/usr/lib;/usr/lib/llvm-12/lib;/lib")
set(CMAKE_CXX_IMPLICIT_LINK_FRAMEWORK_DIRECTORIES "")
Note: Clang uses heuristic discovery to search headers in directories which are reported by front-end.
This is inappropriate because I just don't want either headers or libraries of libstdc++ to be implicitly used within the project.
Also, it exports compile commands into compile_commands.json
as below:
/usr/bin/clang++-12 -DLIBCXXABI_USE_COMPILER_RT=YES -DLIBCXX_USE_COMPILER_RT=YES -I/data/solution/projects/program/include -std=c++17 -stdlib=libc++ -isystem /usr/include/x86_64-linux-gnu -stdlib++-isystem /usr/lib/llvm-12/include/c++/v1 -o CMakeFiles/program.dir/source/program.cpp.o -c /data/solution/projects/program/source/program.cpp
It all looks good. But when I use ldd to check:
jacob.nielson@ubuntu:/data/solution/projects/program/build/debug$ ldd program
linux-vdso.so.1 (0x00007ffee7190000)
libc++.so.1 => /lib/x86_64-linux-gnu/libc++.so.1 (0x00007f69164a5000)
libc++abi.so.1 => /lib/x86_64-linux-gnu/libc++abi.so.1 (0x00007f691646d000)
libstdc++.so.6 => /lib/x86_64-linux-gnu/libstdc++.so.6 (0x00007f691628b000) /* LIBSTDC++ in here! */
libm.so.6 => /lib/x86_64-linux-gnu/libm.so.6 (0x00007f691613c000) /* LIBM in here */
libgcc_s.so.1 => /lib/x86_64-linux-gnu/libgcc_s.so.1 (0x00007f6916121000) /* gcc startup file in here! */
libc.so.6 => /lib/x86_64-linux-gnu/libc.so.6 (0x00007f6915f2f000) /* LIBC in here! */
libpthread.so.0 => /lib/x86_64-linux-gnu/libpthread.so.0 (0x00007f6915f0a000)
librt.so.1 => /lib/x86_64-linux-gnu/librt.so.1 (0x00007f6915f00000)
libatomic.so.1 => /lib/x86_64-linux-gnu/libatomic.so.1 (0x00007f6915ef6000)
/lib64/ld-linux-x86-64.so.2 (0x00007f691658d000)
It is frustrating to see all libstdc++, libc, libm or libgcc_s remain. Is there any option I missed to link them statically such like -static-libc in GNU CC or do I have to give up my ambition early at this point?
发布评论
评论(1)
特此指出了问题的答案。
关于缺少定义的错误,可以指示Clang使用
Compiler_rt
。一旦我添加到相关选项,就可以解决问题。为了用libc ++替换libstsdc ++,一个人不会忘记添加以下选项:
afak,上述定义有助于指示clang“不要链接默认库”,但也必须将它们与编译选项结合使用, libc ++”,尤其是 no“ -nostdlib” 以生效。文档的一部分涵盖以下内容:
但是,我还不清楚这里指的是什么是指的是什么,以及如何告诉编译器对于给定目标是主导的。
The answer to the question is hereby noted.
There is a mistake about missing definitions to instruct Clang to use
compiler_rt
. The problem is solved once I had add to relevant options.As to replace libstsdc++ with libc++, one shall not forget to add the following options:
AFAK, definitions above help to instruct clang "not to link against default libraries", but one also has to use them in conjunction with compile option "-stdlib=libc++" and especially NO "-nostdlib" for the replace to take effect. Part of the document covers in below:
However, it is much unclear to me what target refers to here and how comes to tell a compiler is dominant for a given target.