2010-03-13 75 views
11

Gần đây tôi đã chiến đấu với một số vấn đề đang cố gắng biên dịch thư viện nguồn mở trên máy Mac phụ thuộc vào thư viện khác và có một số lỗi về kiến ​​trúc thư viện không tương thích. Ai đó có thể giải thích khái niệm đằng sau việc biên dịch một chương trình C cho một kiến ​​trúc cụ thể không? Tôi đã thấy cờ trình biên dịch -arch trước đây và đã thấy các giá trị được truyền cho nó như ppc, i386x86_64 mà tôi cho rằng ánh xạ tới "ngôn ngữ" của CPU, nhưng sự hiểu biết của tôi dừng ở đó. Nếu một chương trình sử dụng một kiến ​​trúc cụ thể, thì tất cả các thư viện mà nó tải cần phải có cùng kiến ​​trúc không? Làm thế nào tôi có thể nói kiến ​​trúc nào cho một chương trình/quy trình cụ thể đang chạy theo?Biên dịch chương trình C với kiến ​​trúc cụ thể

Trả lời

13

Ai đó có thể giải thích khái niệm đằng sau việc biên dịch chương trình C cho một kiến ​​trúc cụ thể không?

Có. Ý tưởng là dịch C thành một chuỗi các lệnh máy gốc, có chương trình được mã hóa thành dạng nhị phân. Ý nghĩa của "kiến trúc" ở đây là "kiến trúc bộ chỉ dẫn", đó là cách các lệnh được mã hóa theo dạng nhị phân. Ví dụ, mọi kiến ​​trúc đều có cách mã hóa riêng cho một lệnh có thêm hai số nguyên.

Lý do để biên dịch thành lệnh máy là chúng chạy rất nhanh.

Nếu một chương trình sử dụng kiến ​​trúc cụ thể, tất cả thư viện mà nó tải cũng cần phải có cùng kiến ​​trúc không?

Có. (Ngoại lệ tồn tại nhưng chúng rất hiếm.)

Làm cách nào để biết cấu trúc của một chương trình/quy trình cụ thể đang hoạt động?

Nếu một quá trình đang chạy trên phần cứng của bạn, nó đang chạy trên kiến ​​trúc bản địa mà trên Unix bạn có thể khám phá bằng cách chạy lệnh uname -m, mặc dù đối với người đọc người đầu ra từ uname -a có thể nhiều thông tin hơn.

Nếu bạn có một thực thi nhị phân hoặc một thư viện chia sẻ (.so tập tin), bạn có thể khám phá kiến ​​trúc của nó bằng cách sử dụng file lệnh:

% file /lib/libm-2.10.2.so 
/lib/libm-2.10.2.so: ELF 32-bit LSB shared object, Intel 80386, version 1 (SYSV), dynamically linked (uses shared libs), for GNU/Linux 2.6.18, stripped 
% file /bin/ls 
/bin/ls: ELF 32-bit LSB executable, Intel 80386, version 1 (SYSV), dynamically linked (uses shared libs), for GNU/Linux 2.6.8, stripped 

Bạn có thể thấy rằng những mã nhị phân đã được biên soạn cho người già Kiến trúc 80386, mặc dù phần cứng của tôi là một i686 hiện đại hơn. I686 (Pentium Pro) tương thích ngược với 80386 và chạy 80386 nhị phân cũng như các tệp nhị phân gốc. Để làm cho khả năng tương thích ngược này có thể xảy ra, Intel đã gặp rất nhiều rắc rối và chi phí — nhưng họ thực tế đã dồn vào thị trường trên các CPU máy tính để bàn, vì vậy nó rất đáng giá!

1

Để xây dựng cho một kiến ​​trúc khác với bản gốc của CPU, bạn sẽ cần một trình biên dịch chéo, có nghĩa là mã được tạo không thể chạy tự nhiên trên máy bạn đang ngồi. GCC có thể làm điều này tốt. Để tìm ra kiến ​​trúc mà chương trình được xây dựng để kiểm tra lệnh tập tin. Trong các hệ thống dựa trên Linux ít nhất, một chương trình 32-bit x86 sẽ yêu cầu lib 32 bit x86 đi cùng với nó. Tôi đoán nó giống nhau đối với hầu hết các hệ điều hành.

3

Một điều có thể gây nhầm lẫn ở đây là nền tảng Mac có thứ mà họ gọi là universal binary, thực sự là hai tệp nhị phân trong một tệp lưu trữ, một cho intel và một cho kiến ​​trúc ppc. Máy tính của bạn sẽ tự động quyết định cái nào sẽ chạy. Bạn có thể (đôi khi) chạy nhị phân cho kiến ​​trúc khác trong chế độ mô phỏng, và một số kiến ​​trúc là supersets của những người khác (tức là mã i386 sẽ thường chạy trên i486, i586, i686, v.v.) nhưng phần lớn mã duy nhất bạn có thể chạy là mã cho kiến ​​trúc bộ vi xử lý của bạn.

Để biên dịch chéo, không chỉ chương trình, mà tất cả các thư viện mà nó sử dụng, cần phải tương thích với bộ xử lý đích. Đôi khi điều này có nghĩa là có một trình biên dịch thứ hai được cài đặt, đôi khi nó chỉ là một câu hỏi có mô-đun bổ sung phù hợp cho trình biên dịch khả thi. Trình biên dịch chéo cho gcc is actually a seperate executable, though it can sometimes be accessed via a command line switch. Trình biên dịch chéo gcc cho các kiến ​​trúc khác nhau có nhiều khả năng cài đặt riêng biệt.

1

ldd trợ giúp trong trường hợp này không?

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