(فصل دوم – بخش هشتم)
خوب! توی قسمت قبل با crosstool-NG و menuconfig آشنا شدیم و همین طور تونستیم برای “رسپبری پای سه بی پلاس – Raspberry Pi 3 B Plus” و “لیچی پای نانو – Lichee Pi Nano” هم تولچین ساختیم. توی این قسمت میخوایم اجزا تولچین رو بررسی کنیم و کمی بیشتر با ابزار های داخل اون آشنا بشیم.
در قسمتهای قبلی آموزش، مسیر حرکت و فصلهای پیش رو، بسیاری از مفاهیم مورد نیاز و سؤالها و ابهامات شما در این دوره پاسخ داده شده است.
پس اگر اولین بار است که این آموزش را شروع میکنید، با توجه به سلسله مراتب پیش بینی شده برای آموزشها، بهتر است از جلسه اول شروع کنید!
جلسه اول آموزش، ورود به دنیای امبدد لینوکس
همه آموزشهای امبدد لینوکس
آناتومی تولچین
سلامی دوباره!
الآن که من دارم قسمت جدید رو مینویسم عید هست پس سال نوتون مبارک و امیدوارم در سال جدید مهارتی جدید به تواناییهاتون اضافه بشه ?
آخرین جمله قبلیمون این بود «خوب الان همه چیز رو برای ساختن همه چیز دارید!» علاوه بر همه چیز زمان زیادی هم داشتین تقریبا شش ماه!
امیدوارم که یک کارهایی کرده باشین ?
بیاید یه سری اطلاعات از اجزا تولچین که ساختیم کسب کنیم.
اول مسیر تولچینی که ساختیم رو به فایل at00exports.sh اضافه میکنیم:
export PATH=$PATH:/home/at00/EmbeddedLinux/F1C100s/build-tools/at00toolchain/bin/
حالا فایل at00exports.sh رو source میکنیم:
source /home/at00/EmbeddedLinux/F1C100s/at00exports.sh
حالا از کامپایلرمون ورژنش رو میپرسیم :
$GCC --version arm-richdad-linux-gnueabi-gcc (crosstool-NG 1.24.0.105_5659366) 9.2.0 Copyright (C) 2019 Free Software Foundation, Inc. This is free software; see the source for copying conditions. There is NO warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
و با این دستور ازش تنظیماتش رو میپرسیم:
$GCC -v Using built-in specs. COLLECT_GCC=/home/at00/EmbeddedLinux/F1C100s/build-tools/at00toolchain/bin/arm-richdad-linux-gnueabi-gcc COLLECT_LTO_WRAPPER=/home/at00/EmbeddedLinux/F1C100s/build-tools/at00toolchain/libexec/gcc/arm-richdad-linux-gnueabi/9.2.0/lto-wrapper Target: arm-richdad-linux-gnueabi Configured with: /home/at00/EmbeddedLinux/F1C100s/build-tools/.build/arm-richdad-linux-gnueabi/src/gcc/configure --build=x86_64-build_pc-linux-gnu --host=x86_64-build_pc-linux-gnu --target=arm-richdad-linux-gnueabi --prefix=/home/at00/EmbeddedLinux/F1C100s/build-tools/at00toolchain --with-sysroot=/home/at00/EmbeddedLinux/F1C100s/build-tools/at00toolchain/arm-richdad-linux-gnueabi/sysroot --enable-languages=c,c++ --with-cpu=arm926ej-s --with-float=soft --with-pkgversion='crosstool-NG 1.24.0.105_5659366' --disable-sjlj-exceptions --enable-__cxa_atexit --disable-libmudflap --disable-libgomp --disable-libssp --disable-libquadmath --disable-libquadmath-support --disable-libsanitizer --disable-libmpx --with-gmp=/home/at00/EmbeddedLinux/F1C100s/build-tools/.build/arm-richdad-linux-gnueabi/buildtools --with-mpfr=/home/at00/EmbeddedLinux/F1C100s/build-tools/.build/arm-richdad-linux-gnueabi/buildtools --with-mpc=/home/at00/EmbeddedLinux/F1C100s/build-tools/.build/arm-richdad-linux-gnueabi/buildtools --with-isl=/home/at00/EmbeddedLinux/F1C100s/build-tools/.build/arm-richdad-linux-gnueabi/buildtools --enable-lto --with-host-libstdcxx='-static-libgcc -Wl,-Bstatic,-lstdc++,-Bdynamic -lm' --enable-threads=posix --enable-target-optspace --enable-plugin --enable-gold --disable-nls --disable-multilib --with-local-prefix=/home/at00/EmbeddedLinux/F1C100s/build-tools/at00toolchain/arm-richdad-linux-gnueabi/sysroot --enable-long-long Thread model: posix gcc version 9.2.0 (crosstool-NG 1.24.0.105_5659366)
از این همه اطلاعات اینا بیشتر بدرد میخورن:
--with-sysroot=/home/at00/EmbeddedLinux/F1C100s/build-tools/at00toolchain/arm-richdad-linux-gnueabi/sysroot --enable-languages=c,c++ --with-cpu=arm926ej-s --with-float=soft
به جز خط اول بقیه رو فکر نکنم توضیح خاصی بخواد.
Sysroot، کتابخانه و سرآیندها
واسه sysroot معادل فارسی سراغ نداشتم ?
Sysroot درحقیقت یه دایرکتوری هست با یه سری زیردایرکتوریها که توشون کتابخانهها و فایلهای سرآیند و فایلهای تنظیماتی هست. Sysroot رو میشه در زمان کامپایل برای کامپایلرمون با آرگومان –sysroot ست کنیم.
محتویات sysroot معمولا اینهاست:
You will find the following subdirectories in sysroot : lib: Contains the shared objects for the C library and the dynamic linker/loader, ld-linux usr/lib: the static library archive files for the C library, and any other libraries that may be installed subsequently usr/include: Contains the headers for all the libraries usr/bin: Contains the utility programs that run on the target, such as the ldd command use/share: Used for localization and internationalization sbin: Provides the ldconfig utility, used to optimize library loading paths
سوال: خوب که چی؟
جواب: بعضی از این محتویات بدرد تارگت میخوره در زمان اجرای برنامه. برخی هم بدرد هاست میخوره در زمان کامپایل و بیلد کردن برنامه ولی در کل بدانید و آگاه باشید سیسروتی هست تا زمانی که گیر افتادین راه حل داشته باشین!
تولچین به جز کامپایلر دیگه چیا داره؟
خیلی چیزا!
برای شناخت اجزا تولچین کافیه یه نگاه به محتویات فولدر bin بندازین؟ (کدوم bin؟ همونی که توش کامپایلر هست.)
اجزای کتابخانه
کتابخانه C یک کتابخانه نیست و در حقیقت از چهارتا بخش تشکیل شده که باهم APIی POSIX رو پیاده سازی میکنن:
libc: The main C library that contains the well-known POSIX functions such as printf , open , close , read , write , and so on
libm: Contains maths functions such as cos , exp , and log
libpthread: Contains all the POSIX thread functions with names beginning with pthread_
librt: Has the real-time extensions to POSIX, including shared memory and asynchronous I/O
از این چهار تا کتابخانه فقط libc به صورت پیش فرض با کامپایلر لینک هست بقیه رو در صورتی که توی برنامه ازشون استفاده کرده باشیم باید به کامپایلرمون بگیم، چه جوری؟ اینجوری که –l میذاریم و بدون اسم کتابخانه رو که lib ازش حذف شده در ادامهش مینویسم، البته این قانون معمولا در مورد بقیه کتابخانهها هم صدق میکنه. مثلا اگه از توابع ریاضیاتی استفاده کرده باشیم در برنامهمون این جوری کامپایلش میکنیم:
$GCC myprog.c -o myprog –lm
سوال: یه وقتایی یه برنامههایی هست که هی میگه این کتابخونه نیست اون یکی نیست، این ورژنش نمیخونه و … چه کنیم؟
جواب با دو تا دستور اول ببینید چه کتابخونههایی با چه ورژنهایی میخواد و بعد برید دنبال یافتنشون و گذاشتنشون سرجاش!
مثلا این برنامه رو در نظر بگیرید:
#include <stdio.h> #include <stdlib.h> #include <string.h> #include <math.h> int main(void) { printf("\r\nHello World!\r\n"); printf("I'm AT00FirstF1C100S!\r\n"); printf("sin(137)=%f",sin(137)); return 0; }
که این جوری کامپایلش میکنم:
$GCC first.c -o sin137 –lm
حالا خروجی این دو تا دستور رو ببنید:
arm-richdad-linux-gnueabi-readelf -a sin137 | grep "Shared library" 0x00000001 (NEEDED) Shared library: [libm.so.6] 0x00000001 (NEEDED) Shared library: [libc.so.6] arm-richdad-linux-gnueabi-readelf -a sin137 | grep "program interpreter" Start of program headers: 52 (bytes into file) Size of program headers: 32 (bytes) Number of program headers: 9 [Requesting program interpreter: /lib/ld-linux.so.3]
سوال: از کجا این کتابخونهها رو پیدا کنیم؟
جواب: از همون سیسروت شروع کنید!
پایان بخش هشتم از فصل دوم
توصیه میکنم یه سری هم به نظرات این پایین بندازید، نظرات رو بخونید و اگر شما هم نظری دارید، مشارکت کنید!
همه آموزش های امبدد لینوکس
منبع:سیسوگ