需求
常见的有分布式代码编译,如 icecream fastbuild 等分布式编译 C/C++ 代码
有时候,会有其他类似需求,执行某种操作,与编译代码类似,但不是编译代码
通常可以有 2 种常见的做法:
- 使用 jenkins pipeline
- 伪造 gcc 程序,使用 icecream fastbuild
本文主要介绍如何伪造 gcc 程序,骗过 cmake make icecream fastbuild 等等工具
例子
github 地址: https://github.com/fananchong/custom_build_example
该例子主要伪造了一个 gcc : mygcc ,具备以下功能:
- 具备 gcc build 功能
- 具备 gcc link 功能
- 打印主机名
- 把输入的 txt 文件,加行
hello world
,输出
原理说明
make 调用 gcc ,主要 2 个作用:
- 使用 gcc 把输入的 xxx.cpp 等代码文件,输出 xxx.o 文件
- 使用 gcc 把 xxx.o 等系列 .o 文件,生成 out 可执行文件
make 只看输出结果,即:
- gcc build 时,有无 .o 文件
- gcc link 时,有无 out 可执行文件(不用真的可执行,有这个文件即可)
因此很好写伪造的 gcc :
以下是伪代码:
int main(int argc, char **argv)
{
std::string type, input, output;
parse_cmd_args(argc, argv, type, input, output);
if (type == "build")
{
// 创建 output .o 文件
}
else
{
// 创建 output 可执行文件
}
}
只要这样的代码,make 就无条件信任为 gcc
例子展示
执行,大致如下,输出:
++ pwd
+ cur_dir=/home/fananchong/custom_build_example/example
+ rm -rf build temp bin
+ mkdir -p build temp bin
+ grep -v CMakeLists.txt
+ ls a10.txt a11.txt a12.txt a13.txt a14.txt a15.txt a16.txt a17.txt a18.txt a19.txt a1.txt a20.txt a2.txt a3.txt a4.txt a5.txt a6.txt a7.txt a8.txt a9.txt CMakeLists.txt
+ xargs -i cp '{}' 'temp/{}.cpp'
+ pushd build
~/custom_build_example/example/build ~/custom_build_example/example
+ cmake ..
-- The C compiler identification is GNU 4.8.5
-- The CXX compiler identification is GNU 4.8.5
-- Detecting C compiler ABI info
-- Detecting C compiler ABI info - done
-- Check for working C compiler: /usr/bin/cc - skipped
-- Detecting C compile features
-- Detecting C compile features - done
-- Detecting CXX compiler ABI info
-- Detecting CXX compiler ABI info - done
-- Check for working CXX compiler: /usr/bin/c++ - skipped
-- Detecting CXX compile features
-- Detecting CXX compile features - done
-- CMAKE_SOURCE_DIR: /home/fananchong/custom_build_example/example
-- Configuring done
-- Generating done
-- Build files have been written to: /home/fananchong/custom_build_example/example/build
+ make VERBOSE=1
/usr/local/bin/cmake -S/home/fananchong/custom_build_example/example -B/home/fananchong/custom_build_example/example/build --check-build-system CMakeFiles/Makefile.cmake 0
/usr/local/bin/cmake -E cmake_progress_start /home/fananchong/custom_build_example/example/build/CMakeFiles /home/fananchong/custom_build_example/example/build//CMakeFiles/progress.marks
make -f CMakeFiles/Makefile2 all
make[1]: 进入目录“/home/fananchong/custom_build_example/example/build”
make -f CMakeFiles/test.dir/build.make CMakeFiles/test.dir/depend
make[2]: 进入目录“/home/fananchong/custom_build_example/example/build”
cd /home/fananchong/custom_build_example/example/build && /usr/local/bin/cmake -E cmake_depends "Unix Makefiles" /home/fananchong/custom_build_example/example /home/fananchong/custom_build_example/example /home/fananchong/custom_build_example/example/build /home/fananchong/custom_build_example/example/build /home/fananchong/custom_build_example/example/build/CMakeFiles/test.dir/DependInfo.cmake --color=
make[2]: 离开目录“/home/fananchong/custom_build_example/example/build”
make -f CMakeFiles/test.dir/build.make CMakeFiles/test.dir/build
make[2]: 进入目录“/home/fananchong/custom_build_example/example/build”
[ 4%] Building CXX object CMakeFiles/test.dir/temp/a1.txt.cpp.o
/home/fananchong/custom_build_example/example/../bin/mygcc -std=gnu++11 -MD -MT CMakeFiles/test.dir/temp/a1.txt.cpp.o -MF CMakeFiles/test.dir/temp/a1.txt.cpp.o.d -o CMakeFiles/test.dir/temp/a1.txt.cpp.o -c /home/fananchong/custom_build_example/example/temp/a1.txt.cpp
output: CMakeFiles/test.dir/temp/a1.txt.cpp.o
[ 9%] Building CXX object CMakeFiles/test.dir/temp/a10.txt.cpp.o
/home/fananchong/custom_build_example/example/../bin/mygcc -std=gnu++11 -MD -MT CMakeFiles/test.dir/temp/a10.txt.cpp.o -MF CMakeFiles/test.dir/temp/a10.txt.cpp.o.d -o CMakeFiles/test.dir/temp/a10.txt.cpp.o -c /home/fananchong/custom_build_example/example/temp/a10.txt.cpp
output: CMakeFiles/test.dir/temp/a10.txt.cpp.o
[ 14%] Building CXX object CMakeFiles/test.dir/temp/a11.txt.cpp.o
/home/fananchong/custom_build_example/example/../bin/mygcc -std=gnu++11 -MD -MT CMakeFiles/test.dir/temp/a11.txt.cpp.o -MF CMakeFiles/test.dir/temp/a11.txt.cpp.o.d -o CMakeFiles/test.dir/temp/a11.txt.cpp.o -c /home/fananchong/custom_build_example/example/temp/a11.txt.cpp
output: CMakeFiles/test.dir/temp/a11.txt.cpp.o
[ 19%] Building CXX object CMakeFiles/test.dir/temp/a12.txt.cpp.o
/home/fananchong/custom_build_example/example/../bin/mygcc -std=gnu++11 -MD -MT CMakeFiles/test.dir/temp/a12.txt.cpp.o -MF CMakeFiles/test.dir/temp/a12.txt.cpp.o.d -o CMakeFiles/test.dir/temp/a12.txt.cpp.o -c /home/fananchong/custom_build_example/example/temp/a12.txt.cpp
output: CMakeFiles/test.dir/temp/a12.txt.cpp.o
[ 23%] Building CXX object CMakeFiles/test.dir/temp/a13.txt.cpp.o
/home/fananchong/custom_build_example/example/../bin/mygcc -std=gnu++11 -MD -MT CMakeFiles/test.dir/temp/a13.txt.cpp.o -MF CMakeFiles/test.dir/temp/a13.txt.cpp.o.d -o CMakeFiles/test.dir/temp/a13.txt.cpp.o -c /home/fananchong/custom_build_example/example/temp/a13.txt.cpp
output: CMakeFiles/test.dir/temp/a13.txt.cpp.o
[ 28%] Building CXX object CMakeFiles/test.dir/temp/a14.txt.cpp.o
/home/fananchong/custom_build_example/example/../bin/mygcc -std=gnu++11 -MD -MT CMakeFiles/test.dir/temp/a14.txt.cpp.o -MF CMakeFiles/test.dir/temp/a14.txt.cpp.o.d -o CMakeFiles/test.dir/temp/a14.txt.cpp.o -c /home/fananchong/custom_build_example/example/temp/a14.txt.cpp
output: CMakeFiles/test.dir/temp/a14.txt.cpp.o
[ 33%] Building CXX object CMakeFiles/test.dir/temp/a15.txt.cpp.o
/home/fananchong/custom_build_example/example/../bin/mygcc -std=gnu++11 -MD -MT CMakeFiles/test.dir/temp/a15.txt.cpp.o -MF CMakeFiles/test.dir/temp/a15.txt.cpp.o.d -o CMakeFiles/test.dir/temp/a15.txt.cpp.o -c /home/fananchong/custom_build_example/example/temp/a15.txt.cpp
output: CMakeFiles/test.dir/temp/a15.txt.cpp.o
[ 38%] Building CXX object CMakeFiles/test.dir/temp/a16.txt.cpp.o
/home/fananchong/custom_build_example/example/../bin/mygcc -std=gnu++11 -MD -MT CMakeFiles/test.dir/temp/a16.txt.cpp.o -MF CMakeFiles/test.dir/temp/a16.txt.cpp.o.d -o CMakeFiles/test.dir/temp/a16.txt.cpp.o -c /home/fananchong/custom_build_example/example/temp/a16.txt.cpp
output: CMakeFiles/test.dir/temp/a16.txt.cpp.o
[ 42%] Building CXX object CMakeFiles/test.dir/temp/a17.txt.cpp.o
/home/fananchong/custom_build_example/example/../bin/mygcc -std=gnu++11 -MD -MT CMakeFiles/test.dir/temp/a17.txt.cpp.o -MF CMakeFiles/test.dir/temp/a17.txt.cpp.o.d -o CMakeFiles/test.dir/temp/a17.txt.cpp.o -c /home/fananchong/custom_build_example/example/temp/a17.txt.cpp
output: CMakeFiles/test.dir/temp/a17.txt.cpp.o
[ 47%] Building CXX object CMakeFiles/test.dir/temp/a18.txt.cpp.o
/home/fananchong/custom_build_example/example/../bin/mygcc -std=gnu++11 -MD -MT CMakeFiles/test.dir/temp/a18.txt.cpp.o -MF CMakeFiles/test.dir/temp/a18.txt.cpp.o.d -o CMakeFiles/test.dir/temp/a18.txt.cpp.o -c /home/fananchong/custom_build_example/example/temp/a18.txt.cpp
output: CMakeFiles/test.dir/temp/a18.txt.cpp.o
[ 52%] Building CXX object CMakeFiles/test.dir/temp/a19.txt.cpp.o
/home/fananchong/custom_build_example/example/../bin/mygcc -std=gnu++11 -MD -MT CMakeFiles/test.dir/temp/a19.txt.cpp.o -MF CMakeFiles/test.dir/temp/a19.txt.cpp.o.d -o CMakeFiles/test.dir/temp/a19.txt.cpp.o -c /home/fananchong/custom_build_example/example/temp/a19.txt.cpp
output: CMakeFiles/test.dir/temp/a19.txt.cpp.o
[ 57%] Building CXX object CMakeFiles/test.dir/temp/a2.txt.cpp.o
/home/fananchong/custom_build_example/example/../bin/mygcc -std=gnu++11 -MD -MT CMakeFiles/test.dir/temp/a2.txt.cpp.o -MF CMakeFiles/test.dir/temp/a2.txt.cpp.o.d -o CMakeFiles/test.dir/temp/a2.txt.cpp.o -c /home/fananchong/custom_build_example/example/temp/a2.txt.cpp
output: CMakeFiles/test.dir/temp/a2.txt.cpp.o
[ 61%] Building CXX object CMakeFiles/test.dir/temp/a20.txt.cpp.o
/home/fananchong/custom_build_example/example/../bin/mygcc -std=gnu++11 -MD -MT CMakeFiles/test.dir/temp/a20.txt.cpp.o -MF CMakeFiles/test.dir/temp/a20.txt.cpp.o.d -o CMakeFiles/test.dir/temp/a20.txt.cpp.o -c /home/fananchong/custom_build_example/example/temp/a20.txt.cpp
output: CMakeFiles/test.dir/temp/a20.txt.cpp.o
[ 66%] Building CXX object CMakeFiles/test.dir/temp/a3.txt.cpp.o
/home/fananchong/custom_build_example/example/../bin/mygcc -std=gnu++11 -MD -MT CMakeFiles/test.dir/temp/a3.txt.cpp.o -MF CMakeFiles/test.dir/temp/a3.txt.cpp.o.d -o CMakeFiles/test.dir/temp/a3.txt.cpp.o -c /home/fananchong/custom_build_example/example/temp/a3.txt.cpp
output: CMakeFiles/test.dir/temp/a3.txt.cpp.o
[ 71%] Building CXX object CMakeFiles/test.dir/temp/a4.txt.cpp.o
/home/fananchong/custom_build_example/example/../bin/mygcc -std=gnu++11 -MD -MT CMakeFiles/test.dir/temp/a4.txt.cpp.o -MF CMakeFiles/test.dir/temp/a4.txt.cpp.o.d -o CMakeFiles/test.dir/temp/a4.txt.cpp.o -c /home/fananchong/custom_build_example/example/temp/a4.txt.cpp
output: CMakeFiles/test.dir/temp/a4.txt.cpp.o
[ 76%] Building CXX object CMakeFiles/test.dir/temp/a5.txt.cpp.o
/home/fananchong/custom_build_example/example/../bin/mygcc -std=gnu++11 -MD -MT CMakeFiles/test.dir/temp/a5.txt.cpp.o -MF CMakeFiles/test.dir/temp/a5.txt.cpp.o.d -o CMakeFiles/test.dir/temp/a5.txt.cpp.o -c /home/fananchong/custom_build_example/example/temp/a5.txt.cpp
output: CMakeFiles/test.dir/temp/a5.txt.cpp.o
[ 80%] Building CXX object CMakeFiles/test.dir/temp/a6.txt.cpp.o
/home/fananchong/custom_build_example/example/../bin/mygcc -std=gnu++11 -MD -MT CMakeFiles/test.dir/temp/a6.txt.cpp.o -MF CMakeFiles/test.dir/temp/a6.txt.cpp.o.d -o CMakeFiles/test.dir/temp/a6.txt.cpp.o -c /home/fananchong/custom_build_example/example/temp/a6.txt.cpp
output: CMakeFiles/test.dir/temp/a6.txt.cpp.o
[ 85%] Building CXX object CMakeFiles/test.dir/temp/a7.txt.cpp.o
/home/fananchong/custom_build_example/example/../bin/mygcc -std=gnu++11 -MD -MT CMakeFiles/test.dir/temp/a7.txt.cpp.o -MF CMakeFiles/test.dir/temp/a7.txt.cpp.o.d -o CMakeFiles/test.dir/temp/a7.txt.cpp.o -c /home/fananchong/custom_build_example/example/temp/a7.txt.cpp
output: CMakeFiles/test.dir/temp/a7.txt.cpp.o
[ 90%] Building CXX object CMakeFiles/test.dir/temp/a8.txt.cpp.o
/home/fananchong/custom_build_example/example/../bin/mygcc -std=gnu++11 -MD -MT CMakeFiles/test.dir/temp/a8.txt.cpp.o -MF CMakeFiles/test.dir/temp/a8.txt.cpp.o.d -o CMakeFiles/test.dir/temp/a8.txt.cpp.o -c /home/fananchong/custom_build_example/example/temp/a8.txt.cpp
output: CMakeFiles/test.dir/temp/a8.txt.cpp.o
[ 95%] Building CXX object CMakeFiles/test.dir/temp/a9.txt.cpp.o
/home/fananchong/custom_build_example/example/../bin/mygcc -std=gnu++11 -MD -MT CMakeFiles/test.dir/temp/a9.txt.cpp.o -MF CMakeFiles/test.dir/temp/a9.txt.cpp.o.d -o CMakeFiles/test.dir/temp/a9.txt.cpp.o -c /home/fananchong/custom_build_example/example/temp/a9.txt.cpp
output: CMakeFiles/test.dir/temp/a9.txt.cpp.o
[100%] Linking CXX executable test
/usr/local/bin/cmake -E cmake_link_script CMakeFiles/test.dir/link.txt --verbose=1
/home/fananchong/custom_build_example/example/../bin/mygcc CMakeFiles/test.dir/temp/a1.txt.cpp.o CMakeFiles/test.dir/temp/a10.txt.cpp.o CMakeFiles/test.dir/temp/a11.txt.cpp.o CMakeFiles/test.dir/temp/a12.txt.cpp.o CMakeFiles/test.dir/temp/a13.txt.cpp.o CMakeFiles/test.dir/temp/a14.txt.cpp.o CMakeFiles/test.dir/temp/a15.txt.cpp.o CMakeFiles/test.dir/temp/a16.txt.cpp.o CMakeFiles/test.dir/temp/a17.txt.cpp.o CMakeFiles/test.dir/temp/a18.txt.cpp.o CMakeFiles/test.dir/temp/a19.txt.cpp.o CMakeFiles/test.dir/temp/a2.txt.cpp.o CMakeFiles/test.dir/temp/a20.txt.cpp.o CMakeFiles/test.dir/temp/a3.txt.cpp.o CMakeFiles/test.dir/temp/a4.txt.cpp.o CMakeFiles/test.dir/temp/a5.txt.cpp.o CMakeFiles/test.dir/temp/a6.txt.cpp.o CMakeFiles/test.dir/temp/a7.txt.cpp.o CMakeFiles/test.dir/temp/a8.txt.cpp.o CMakeFiles/test.dir/temp/a9.txt.cpp.o -o test
make[2]: 离开目录“/home/fananchong/custom_build_example/example/build”
[100%] Built target test
make[1]: 离开目录“/home/fananchong/custom_build_example/example/build”
/usr/local/bin/cmake -E cmake_progress_start /home/fananchong/custom_build_example/example/build/CMakeFiles 0
+ make install
[100%] Built target test
Install the project...
-- Install configuration: ""
-- Installing: /home/fananchong/custom_build_example/example/bin/./test
+ popd
~/custom_build_example/example
支持分布式编译
这个本质上,只要会用 icecream fastbuild 即可,它们使用 make gcc ,更上层,更不会关心 gcc 是否是伪造的