2012-05-30 29 views
33

Tôi phải biên dịch một chương trình trên ubuntu hiện tại (12.04). Chương trình này sau đó sẽ chạy trên một cụm bằng cách sử dụng CentOS với một hạt nhân cũ (2.6.18). Tôi không thể biên dịch trực tiếp trên cụm. Nếu tôi chỉ biên dịch và sao chép chương trình mà không có bất kỳ thay đổi nào, tôi nhận được thông báo lỗi "kernel quá cũ".Biên dịch với libc cũ hơn (phiên bản 'GLIBC_2.14' không được tìm thấy)

Cách tôi hiểu nó, lý do cho điều này không phải là quá nhiều phiên bản Kernel, nhưng phiên bản của libc đã được sử dụng để biên dịch. Vì vậy, tôi đã cố gắng biên dịch chương trình của mình tự động liên kết libc từ cụm và liên kết tĩnh mọi thứ khác.

Nghiên cứu

Hiện đã có rất nhiều câu hỏi về vấn đề này trên SO nhưng không ai trong số các câu trả lời thực sự làm việc cho tôi. Vì vậy, đây là nghiên cứu của tôi về chủ đề đó:

  • This question giải thích lý do cho thông điệp quá cũ Kernel
  • This question là tương tự nhưng chuyên biệt hơn và không có câu trả lời
  • Liên kết tĩnh như đề xuất here đã không làm việc vì libc quá cũ trên cụm. Một câu trả lời cũng đề cập đến việc xây dựng bằng cách sử dụng libc cũ, nhưng không giải thích cách thực hiện điều này.
  • One way là để biên dịch trong máy ảo chạy một hệ điều hành cũ. Điều này làm việc nhưng phức tạp. Tôi cũng đọc mà you should not link libc statically
  • Apparentlyis possible để biên dịch cho một phiên bản libc khác nhau với các tùy chọn -rpath nhưng điều này không làm việc cho tôi (xem dưới đây)

trạng thái hiện tại

tôi đã sao chép các tệp sau từ cụm vào thư mục /path/to/copied/libs

  • libc-2.5.so
  • libgcc_s.so.1
  • libstdC++. So.6

và đang biên soạn với các tùy chọn -nodefaultlibs -Xlinker -rpath=/path/to/copied/libs -Wl,-Bstatic,-lrt,-lboost_system,-lboost_filesystem -Wl,-Bdynamic,-lc,-lstdc++,-lgcc_s

Kết quả của ldd trên nhị phân biên soạn là

mybin: /path/to/copied/libs/libc.so.6: version `GLIBC_2.14' not found (required by mybin) 
mybin: /path/to/copied/libs/libstdc++.so.6: version `GLIBCXX_3.4.15' not found (required by mybin) 
linux-vdso.so.1 => (0x00007ffff36bb000) 
libc.so.6 => /path/to/copied/libs/libc.so.6 (0x00007fbe3789a000) 
libstdc++.so.6 => /path/to/copied/libs/libstdc++.so.6 (0x00007fbe37599000) 
libgcc_s.so.1 => /path/to/copied/libs/libgcc_s.so.1 (0x00007fbe3738b000) 
/lib64/ld-linux-x86-64.so.2 (0x00007fbe37bf3000) 
libm.so.6 => /lib/x86_64-linux-gnu/libm.so.6 (0x00007fbe37071000) 

tôi m hơi bối rối bởi lỗi, bởi vì nó sử dụng đường dẫn chính xác (tức là libc từ cụm) nhưng vẫn than phiền về phiên bản glibc bị thiếu. Khi chạy ldd trên cụm, nó trả về not a dynamic executable và chạy kết quả nhị phân trong cùng hai lỗi được đề cập ở trên. Nó cũng giống như có các thư viện khác bao gồm (linux-vdso.so.1, ld-linux-x86-64.so.2 và libm.so.6). Tôi có nên sử dụng các phiên bản cũ hơn cho những người đó không?

Vì vậy, bây giờ tôi có hai câu hỏi chính:

  • là ngay cả những cách tiếp cận đúng ở đây?
  • Nếu có: làm cách nào để liên kết libc cũ chính xác?

Trả lời

10

Xem câu trả lời this.

Đây có phải là ngay cả những cách tiếp cận đúng đây

Số: bạn không thể sử dụng không hạnh phúc phiên bản của glibc như lệnh liên kết của bạn không. Bạn đã sử dụng crt0.old-linux.so từ mới (hệ thống đã cài đặt) libc, nhưng libc.so.6 từ libc cũ (được sao chép từ cụm). Điều đó sẽ không hoạt động.

2

-rpath đặt thẻ DT_RPATH nhưng không yêu cầu trình liên kết xem ở đó cho libs, bạn muốn -L cho điều đó.

Các vấn đề liên quan