1. 程式人生 > 實用技巧 >記錄在Ubuntu18.04編譯gcc-4.4.7與glibc-2.20遇到的坑

記錄在Ubuntu18.04編譯gcc-4.4.7與glibc-2.20遇到的坑

記錄在Ubuntu18.04編譯gcc-4.4.7與glibc-2.20遇到的坑

因為工作緣故,程式碼需要在本地寫,但是由於伺服器環境與本地環境差異比較大,在本地編譯的二進位制檔案無法直接在伺服器執行。看了許多解決方案,選擇了其中一種比較可行的,具體請看這裡[1]

為了實驗一下,得在本地搭建伺服器上的老環境nmd,為什麼,本地環境為Ubuntu18.04lts,伺服器為Centos,具體版本不清楚,只得知gcc版本為4.4.7,glibc版本為2.20。apt源gcc最老的版本為4.8,因此打算一併編譯4.4.7的gcc,廢話不多說,開幹。

1、gcc安裝

1、原始碼獲取

從gnu的中國映象中選擇了中科大源。

https://mirrors.ustc.edu.cn/gnu/ ,包括gcc所有gnu專案的原始碼都可以在這裡找到,所以後面glibc的原始碼也是在這裡下載的。

2、安裝指導

從原始碼中的INSTALL資料夾中可以找到一些安裝所需資訊,有時間的同學可以閱讀一下。

3、編譯前

在原始碼目錄下新建目錄build作為編譯目錄,進入目錄執行配置指令,其中--prefix選項指定編譯完成後的安裝目錄,注意儘量不要選擇系統預設的gcc所在目錄進行安裝,以免出現不可預料的後果。

cd gcc-4.4.7
mkdir build
cd build
../configure --prefix=/usr/local/bin/gcc-4.4.7

執行結果如下

checking build system type... x86_64-unknown-linux-gnu
checking host system type... x86_64-unknown-linux-gnu
checking target system type... x86_64-unknown-linux-gnu
checking for a BSD-compatible install... /usr/bin/install -c
checking whether ln works... yes
checking whether ln -s works... yes
checking for gcc... gcc
checking for C compiler default output file name... a.out
checking whether the C compiler works... yes
checking whether we are cross compiling... no
checking for suffix of executables... 
checking for suffix of object files... o
checking whether we are using the GNU C compiler... yes
checking whether gcc accepts -g... yes
checking for gcc option to accept ANSI C... none needed
checking for g++... g++
checking whether we are using the GNU C++ compiler... yes
checking whether g++ accepts -g... yes
checking for gnatbind... no
checking for gnatmake... no
checking whether compiler driver understands Ada... no
checking how to compare bootstrapped objects... cmp --ignore-initial=16 $$f1 $$f2
checking for correct version of gmp.h... no
configure: error: Building GCC requires GMP 4.1+ and MPFR 2.3.2+.
Try the --with-gmp and/or --with-mpfr options to specify their locations.
Copies of these libraries' source code can be found at their respective
hosting sites as well as at ftp://gcc.gnu.org/pub/gcc/infrastructure/.
See also http://gcc.gnu.org/install/prerequisites.html for additional info.
If you obtained GMP and/or MPFR from a vendor distribution package, make
sure that you have installed both the libraries and the header files.
They may be located in separate packages.

可以看到報錯是由於環境缺少了GMP 4.1+MPFR 2.3.2+,在ubuntu18.04中可以通過apt安裝libgmp-devlibmpfr-dev解決報錯。

4、正式編譯

  • texinfo錯誤
make[1]: Entering directory '/home/fo/gcc-4.4.7/objdir/gcc'
if [ xinfo = xinfo ]; then \
        makeinfo --split-size=5000000 --no-split -I . -I ../../gcc/doc \
                -I ../../gcc/doc/include -o doc/cpp.info ../../gcc/doc/cpp.texi; \
fi
../../gcc/doc/cppopts.texi:772: @itemx must follow @item
Makefile:4270: recipe for target 'doc/cpp.info' failed
make[1]: *** [doc/cpp.info] Error 1
make[1]: Leaving directory '/home/ADMIN/cort ex_m4/gcc-4.4.7/objdir/gcc'
Makefile:5256: recipe for target 'all-gcc' failed
make: *** [all-gcc] Error 2

原因:環境中texinfo版本過高,原始碼中的.texi程式碼在高版本的texinfo語法為錯誤,無法通過編譯。

解決辦法:編譯過程中暫時解除安裝texinfo,編譯後再重新安裝[2]

sudo apt remove texinfo
  • struct siginfo型別錯誤

待施工

原因:從某個版本訊號量型別從struct siginfo變更為siginfo_t

解決辦法:將原始碼中的struct siginfo替換為siginfo_t

  • struct ucontext型別錯誤
/dev/shm/GCCcore/6.3.0/dummy-/gcc-6.3.0/stage1_obj/./gcc/xgcc -B/dev/shm/GCCcore/6.3.0/dummy-/gcc-6.3.0/stage1_obj/./gcc/ -B/dev/shm/GCCcore/6.3.0/dummy-/GCC_stage1_eb/x86_64-pc-linux-gnu/bin/ -B/dev/shm/GCCcore/6.3.0/dummy-/GCC_stage1_eb/x86_64-pc-linux-gnu/lib/ -isystem /dev/shm/GCCcore/6.3.0/dummy-/GCC_stage1_eb/x86_64-pc-linux-gnu/include -isystem /dev/shm/GCCcore/6.3.0/dummy-/GCC_stage1_eb/x86_64-pc-linux-gnu/sys-include    -g -O2 -O2  -g -O2 -DIN_GCC    -W -Wall -Wno-narrowing -Wwrite-strings -Wcast-qual -Wstrict-prototypes -Wmissing-prototypes -Wold-style-definition  -isystem ./include   -fpic -mlong-double-80 -DUSE_ELF_SYMVER -g -DIN_LIBGCC2 -fbuilding-libgcc -fno-stack-protector   -fpic -mlong-double-80 -DUSE_ELF_SYMVER -I. -I. -I../.././gcc -I../../../libgcc -I../../../libgcc/. -I../../../libgcc/../gcc -I../../../libgcc/../include -I../../../libgcc/config/libbid -DENABLE_DECIMAL_BID_FORMAT -DHAVE_CC_TLS  -DUSE_TLS -o unwind-sjlj.o -MT unwind-sjlj.o -MD -MP -MF unwind-sjlj.dep -fexceptions -c ../../../libgcc/unwind-sjlj.c -fvisibility=hidden -DHIDE_EXPORTS
In file included from ../../../libgcc/unwind-dw2.c:401:0:
./md-unwind-support.h: In function ‘x86_64_fallback_frame_state’:
./md-unwind-support.h:65:47: error: dereferencing pointer to incomplete type ‘struct ucontext’
       sc = (struct sigcontext *) (void *) &uc_->uc_mcontext;
                                               ^~
make[2]: *** [../../../libgcc/shared-object.mk:14: unwind-dw2.o] Error 1
make[2]: *** Waiting for unfinished jobs....
make[2]: Leaving directory '/dev/shm/GCCcore/6.3.0/dummy-/gcc-6.3.0/stage1_obj/x86_64-pc-linux-gnu/libgcc'
make[1]: *** [Makefile:14075: all-target-libgcc] Error 2
make[1]: Leaving directory '/dev/shm/GCCcore/6.3.0/dummy-/gcc-6.3.0/stage1_obj'
make: *** [Makefile:888: all] Error 2

原因:本地glibc版本過高,struct ucontext從glibc2.26起就不再存在在庫中。

解決辦法:使用高版本gcc,建議在6.5版本之後[3]

  • 待施工

2、glibc安裝

待施工