CentOS 上编译安装gcc8.1版本全过程记录(包括排坑与常见错误解决)

原文出处

 

之前发现开发机上安装的gcc版本太旧了,连C++11新特性都不支持,于是决定对其进行升级。本文详细记录了在CentOS 6上升级gcc的整个过程,特别是其中遇到的坑和解决办法。

安装依赖项
先把依赖项装好

sudo yum install glibc-devel bison flex texinfo build-essential
1
在安装的过程中就会发现翻车了:

$ ll
relocation error: /usr/lib64/libc.so.6: symbol _dl_starting_up, version GLIBC_PRIVATE not defined in file ld-linux-x86-64.so.2 with link time reference
1
2
这时会发现几乎所有常见命令都无法执行了——因为他们都依赖C库,而现在C库处于gg状态。解决方案也很简单,两条指令就能搞定。想比于已经启动不了的ln,sln真是雪中送炭啊!

LD_PRELOAD="/lib64/libc-2.12.so"
sudo sln /lib64/libc-2.12.so /lib64/libc.so.6
1
2
下载源码
wget http://ftp.gnu.org/gnu/gcc/gcc-8.1.0/gcc-8.1.0.tar.xz
tar -xf ./gcc-8.1.0.tar.xz
cd ./contrib/
./download_prerequisites
cd ..
1
2
3
4
5
如果目标机网络不好,则需要下载gcc源码到本地,并且将./contrib/download_prerequisites中需要的4个依赖库源码下载好,然后手动上传、解压并设置链接。

tar -xf ./isl-0.18.tar.bz2 
tar -xf ./mpc-1.0.3.tar.gz 
tar -xf ./mpfr-3.1.4.tar.bz2 
tar -xf ./gmp-6.1.0.tar.bz2 
ln -sv ./gmp-6.1.0 ./gmp
ln -sv ./mpc-1.0.3 ./mpc
ln -sv ./mpfr-3.1.4 ./mpfr
ln -sv ./isl-0.18 ./isl
1
2
3
4
5
6
7
8
编译
mkdir gcc-build; cd $_
../configure -enable-checking=release -enable-languages=c,c++ -disable-multilib
1
2
配置完成之后就可以开始编译了,这里依据目标机配置选定make后的参数。

make -j8
1
编译完后进行安装

sudo make install
1
至此已将gcc8.1安装到了/usr/local/bin下。

软链接
先查看当前gcc、g++的路径:

which gcc
which g++
1
2
发现在/usr/bin下。于是先进行备份:

cd /usr/bin
sudo mv gcc gcc.old
sudo mv g++ g++.old
sudo mv gcov gcov.old
sudo mv gccmakedep gccmakedep.old
1
2
3
4
5
重要部分备份之后,就可以进行删除操作了

sudo rm c++ gcc-ar gcov x86_64-pc-linux-gnu-c++ x86_64-pc-linux-gnu-gcc-ar cpp gcc-nm gcov-dump x86_64-pc-linux-gnu-g++ x86_64-pc-linux-gnu-gcc-nm g++ gcc-ranlib gcov-tool x86_64-pc-linux-gnu-gcc x86_64-pc-linux-gnu-gcc-ranlib gcc gcore x86_64-pc-linux-gnu-gcc-8.1.0
1
下面链接到新编译的gcc上:

cd /usr/local/bin
sudo ln -s $(pwd)/c++ /usr/bin/c++
sudo ln -s $(pwd)/gcc-ar /usr/bin/gcc-ar
sudo ln -s $(pwd)/gcov /usr/bin/gcov
sudo ln -s $(pwd)/x86_64-pc-linux-gnu-c++ /usr/bin/x86_64-pc-linux-gnu-c++
sudo ln -s $(pwd)/x86_64-pc-linux-gnu-gcc-ar /usr/bin/x86_64-pc-linux-gnu-gcc-ar
sudo ln -s $(pwd)/cpp /usr/bin/cpp
sudo ln -s $(pwd)/gcc-nm /usr/bin/gcc-nm
sudo ln -s $(pwd)/gcov-dump /usr/bin/gcov-dump
sudo ln -s $(pwd)/x86_64-pc-linux-gnu-g++ /usr/bin/x86_64-pc-linux-gnu-g++
sudo ln -s $(pwd)/x86_64-pc-linux-gnu-gcc-nm /usr/bin/x86_64-pc-linux-gnu-gcc-nm
sudo ln -s $(pwd)/g++ /usr/bin/g++
sudo ln -s $(pwd)/gcc-ranlib /usr/bin/gcc-ranlib
sudo ln -s $(pwd)/gcov-tool /usr/bin/gcov-tool
sudo ln -s $(pwd)/x86_64-pc-linux-gnu-gcc /usr/bin/x86_64-pc-linux-gnu-gcc
sudo ln -s $(pwd)/x86_64-pc-linux-gnu-gcc-ranlib /usr/bin/x86_64-pc-linux-gnu-gcc-ranlib
sudo ln -s $(pwd)/gcc /usr/bin/gcc
sudo ln -s $(pwd)/gcore /usr/bin/gcore
sudo ln -s $(pwd)/x86_64-pc-linux-gnu-gcc-8.1.0 /usr/bin/x86_64-pc-linux-gnu-gcc-8.1.0
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
最后别忘了将C库更新:

strings /usr/lib64/libstdc++.so.6 | grep GLIBCXX
cd /usr/local/lib64
strings libstdc++.so.6.0.25 | grep GLIBCXX
cd /usr/lib64
rm -r ./libstdc++.so.6
ln -s /usr/local/lib64/libstdc++.so.6.0.25 libstdc++.so.6
1
2
3
4
5
6
升级后常见问题
1.C库版本不匹配问题
安装后,如果不进行最后一步,可能会报类似于“/usr/lib64/libstdc++.so.6: version ‘GLIBCXX_3.4.19’ not found”的错误,这就是忘了进行上述最后一步造成的。如果遇到了,更新一下C库就好了。

2. 编译时错误:字符串格式非法
之前能编译通过的项目,现在编译时会报错:

unable to find string literal operator 'operator""fmt' with 'const char [15]'
1
这是由于C++11语法规定,当字符串跟变量连接的时候,必须在变量前后增加一个空格才行。

"[%s][%s:%d]: "fmt"\n"          // 在C++11语法下非法
"[%s][%s:%d]: "  fmt  "\n"      // 修改后合法
1
2
3. 编译时警告:无法将字符串常量转为char*
即“warning: ISO C++ forbids converting a string constant to ‘char*’”。这个很好解决,加一个类型强制转换就行了:

string strSome = "test";
string strSome = (char *)"test";
1
2
4. 链接时错误:千奇百怪的字符串报错问题
类似于“undefined reference to `google::protobuf::internal::WireFormatLite::ReadBytes(google::protobuf::io::CodedInputStream*, std::__cxx11::basic_string

5. ldconfig报错
$ ldconfig
ldconfig: Can't unlink /usr/lib64/libstdc++.so.6
ldconfig: /usr/local/lib64/libstdc++.so.6.0.25-gdb.py is not an ELF file - it has the wrong magic bytes at the start.
1
2
3
一个py文件怎么可能符合elf格式呢?解决方案也很简单粗暴,直接将这个文件删除,然后再重新ldconfig即可。

你可能感兴趣的:(开发工具)