برنامه نویسی

اجرای پروژه مرحله 2 [part-2] – انجمن DEV

خوش آمدید دوباره peeps!! پس از تئوری های زیادی در مورد نسخه چند تابع در آخرین وبلاگ، ما در این قسمت کار بر روی آن را شروع خواهیم کرد. بنابراین، بدون اتلاف وقت، بیایید شروع کنیم.

من با کاوش فایل هایی مانند
tree.h،tree.ccو tree-inline.h
برای درک نحوه نمایش و شبیه سازی توابع در Gimble IR GCC. حال سوال این است که چگونه آنها را پیدا کنم. بنابراین من از دستورات زیر استفاده کردم و با آرگومان های اینجا و آنجا آزمایش کردم و به موارد زیر رسیدم.
نحو
find /path -iname filename
این دستور واقعی بود که من استفاده کردم
find ./ -iname tree.h
پرونده tree.hدر gcc/gcc/tree.h برای مشاهده محتویات فایل می توانیم از دستور استفاده کنیم cat tree.h

پس از صرف زمان برای بررسی فایل، متوجه شدم که فایل حاوی کدی برای کمک به چند نسخه‌سازی عملکرد است و آن توابع را اعلام می‌کند، اما حاوی کدی نیست که برای ایجاد کلون استفاده می‌شود.
حالا اجازه می‌دهیم فایل‌های دیگر را کاوش کنیم. این بار از ویرایشگر vim برای خواندن فایل استفاده می‌کنیم که خواندن آن را کمی آسان می‌کند. دستور آن عبارت است از:
vi tree.cc
این فایل همچنین در پوشه /gcc/gcc/ قرار دارد.
این فایل چندان مفید به نظر نمی رسد زیرا حاوی کدهایی برای ساختار درختی است و نه چند نسخه.

حالا فایل سوم را بررسی کنید tree-inline.h. با استفاده از همین دستور برای ویرایشگر vim. برای خروج از ویرایشگر vim بدون ذخیره چیزی، از دستور استفاده کنید.:Q!

این فایل حاوی کدهای مربوط به inlining، versioning، cloning و parallelization می باشد. وجود این کلمات کلیدی باعث شد من احساس کنم به کد واقعی که روشن کردن AFMV و ارسال آرایه معماری هدف در آن قرار دارد نزدیک هستم.

اگر می خواهید کلمه کلیدی را در ویرایشگر vim جستجو کنید، کافی است تایپ کنید.
/word
با استفاده از کلمه نسخه را جستجو کردم /version و اعلان تابع فراخوانی شده را پیدا کرد
bool tree_versionable_function_p(tree);
این تابع در زیر نظر اعلام شد
"/*function prototypes*/".
با اعلان و نام، به نظر می رسد که این تابع تعیین می کند که آیا کد قابل ویرایش است یا خیر. چند دستور دیگر که سعی کردم کد واقعی را پیدا کنم دنبال می‌شدند.

grep "clon" -r
این دستور تمام فایل های حاوی کلمه “clon” را می گیرد. فهرستی از فایل‌ها بدون نیاز به محتوا وجود دارد که شناسایی آن را غیرممکن می‌کند

grep "fmv" -r
این لیست کوتاه تری به من داد اما نتیجه ای نداشت.(یک شکست روانی داشتم اما ادامه می دهم

git log --oneline --grep="multiversioning"
این دستور تمام commit های گذشته نمایش داده شده در یک خط حاوی کلمه “multiversioning” را به شما می دهد. من حدود 17 commit گرفتم که 3 تای آنها مفید بود.

تعهدات به شرح زیر است.

ثبت گزارش ها

آنهایی که به نظرم مفید بودند، بودند
"[aarch64] Add function multiversioning support"
"Add support for target version attribute"
"aarch64: Fix function multi versioning mangling "

من دو commit اول را بررسی کردم و نتوانستم کد بسیار مفیدی پیدا کنم، اما باید این دو commit را بررسی می‌کردم تا ایده‌ای از نحوه کار و نحوه عملکرد چند نسخه‌سازی عملکرد داشته باشم. من دو مورد اول را بررسی کردم و فراموش کردم که باید به روز رسانی کنیم و FMV اضافه نکنیم. سپس به کامیت سوم رسیدم.
برای بررسی هر commit می توانید از دستور استفاده کنید.
git show
پس از بررسی این commit، خواهید دید که چند خط وجود دارد که به شما می گوید کدام فایل ها تغییر کرده اند. و آدرس فایل سعی کردم از دستور استفاده کنم grep "target_clones". اما جلسه من را متوقف کرد. روش صحیح انجام grep همراه با commit به صورت زیر است.
git show | grep "taget_clones"

خروجی

به این میگن لوله کشی. این به من تمام خطوطی را داد که در آن کلون های هدف قبل از تابع مشخص شده بودند. اکنون باید تابعی را پیدا کنیم که حاوی کد FMV خودکار است. سپس کلمه کلون را جستجو کردم و بعد از این همه اتفاق نظری پیدا کردم.
/*If the function in the node has multiple target attributes, create the appropriate clone for each valid target.*/
تعریف تابع به شکل زیر است.

statuc bool expand_target_clones(struct cgraph_nodes*node, bool definition)

این تابع آرایه‌ای از کلون‌های هدف و تعریف تابعی که باید شبیه‌سازی شود را می‌گیرد. کلون‌های هدف جدا شده با کاما را تجزیه می‌کند و با استفاده از تابعی که قبلاً کشف کردیم، تأیید می‌کند که آیا تابع قابل نسخه‌سازی است یا خیر.

tree_versionable_function_p

باورم نمیشه که اینقدر وقتمو گرفت من همیشه دنبال فایل هایی با نام های واضح می گشتم. اما فایل واقعی که مفید بود بود /gcc/gcc/multiple_targets.cc
سپس کارم را شروع کردم و آرایه‌ای از معماری‌های هدف مورد نیاز را کدگذاری کردم و همچنین تعریفی را که برای اعمال نسخه‌های چندگانه تابع برای همه توابع به‌طور خودکار انجام می‌شود، درست دانستم.

توضیحات تصویر

توضیحات تصویر

بنابراین اکنون باید آن را آزمایش کنیم. بنابراین من یک مجموع ساده از برنامه آرایه نوشتم و آن را با استفاده از بهینه سازی سطح O3 ساختم

توضیحات تصویر

ابتدا اهداف کدگذاری شده سخت را روی sve و sve2 قرار دادم، اما برنامه ای که برای آزمایش آن طراحی کردم، کامپایل نشد زیرا هدف sve2 توسط GCC نسخه 11.3.1 پشتیبانی نمی شود. این نسخه ای است که من در حال حاضر از آن استفاده می کنم.

بنابراین برای اینکه بدانم کدام اهداف پشتیبانی می شوند، از دستور زیر استفاده کردم.

gcc -E -march=help -xe /dev/null

توضیحات تصویر

اما این دستور به من خطا داد، اما به من گفت که کدام اهداف معتبر هستند. و معماری های هدف توسط نسخه فعلی GCC من پشتیبانی می شوند.

سپس آرایه کدگذاری شده را به اهداف ترجیحی تغییر دادم. با این حال من همان خطا را دریافت کردم.

توضیحات تصویر

بنابراین اکنون اطلاعات CPU فایل را که در دایرکتوری proc قرار دارد بررسی کردم. و این فایل ویژگی های هر پردازنده را به من داد. و همچنین به من گفت که چه ویژگی هایی توسط هر پردازنده پشتیبانی می شود.

توضیحات تصویر

بسته بندی آن: یک ترن هوایی در سرزمین کد

پس از پیمایش در هزارتوی فایل‌ها، تجزیه اقیانوس‌های کد، و رمزگشایی هیروگلیف‌های مرموز که کار درونی GCC است، سرانجام پیروز شدم! 🎉 اگرچه با معماری‌های هدف و نسخه‌های GCC با مشکلاتی مواجه شدم (چه کسی می‌دانست که “sve2” اینقدر برای جلب توجه است؟)، اکنون به دانش و چند تار موی خاکستری دیگر مسلح شده‌ام.

نکات کلیدی:

  • Persistence Pays Off: مدتی طول کشید تا فایل مناسب (/gcc/gcc/multiple_targets.cc) را پیدا کنم، اما پشتکار مرا به گنجینه کد FMV رساند.
  • Tools are Your Friends: دستوراتی مانند grep، find و git show به همراهان قابل اعتماد من در این تلاش تبدیل شدند. (به طور جدی، من ممکن است نام حیوان خانگی بعدی ام را “grep” بگذارم.)
  • محدودیت های خود را بشناسید: GCC نسخه 11.3.1 ویژگی های خاص خود را دارد و دانستن اینکه ابزار شما چه کاری می تواند انجام دهد و چه کاری نمی تواند انجام دهد، نیمی از کار است.

درس های آموخته شده:

  • کنجکاو بمانید: کاوش در کامیت ها و کدها نه تنها به من کمک کرد FMV را بهتر درک کنم، بلکه مهارت های کارآگاهی ام را نیز بهبود بخشید (به سمت دیگر بروید، شرلوک!).
  • سازماندهی شده بمانید: دستورات مفید و مسیرهای فایل را پیگیری کنید. در دراز مدت باعث صرفه جویی در زمان و سلامت عقل می شود.
  • در حالی که این فصل از سفر FMV خود را به پایان می برم، به عقب نگاه می کنم و در لحظه ای که تقریباً صفحه کلیدم را به فریزبی تبدیل کردم، می خندم. 🥏 اما هی، هیچ کیبوردی در ساخت این وبلاگ آسیب ندیده است!

بعد چه می شود؟

مرحله بعدی آزمایش FMV با نسخه‌های مختلف GCC و اصلاح رویکرد من برای پاسخگویی به تمام معماری‌های موجود (بله، حتی آنهایی مانند “sve2”) است. من همچنین به دنبال بهینه‌سازی‌های پیشرفته‌تر و شاید سرگرمی‌های پردازش موازی خواهم بود.

با ما همراه باشید، خوانندگان عزیز، زیرا من همچنان به کشف رمز و رازهای عملکرد چند نسخه ای ادامه می دهم. و به یاد داشته باشید، اگر زمانی خود را در دریای رمز گم کردید، فقط به شنا کردن ادامه دهید… و شاید یک اسنورکل بیاورید. 🏊‍♂️

بازتاب ها:

این پروژه مانند یک ترن هوایی وحشی بود – هیجان‌انگیز، گاهی اوقات سرگیجه‌آور، اما در نهایت رضایت‌بخش. من چیزهای زیادی در مورد عملکرد داخلی GCC آموخته ام و متوجه شده ام که همیشه چیزهای بیشتری برای کشف و بهبود وجود دارد. من قصد دارم بیشتر در بهینه سازی کامپایلرها غوطه ور شوم و شاید حتی به جامعه کمک کنم.

پیوندهای کد من:

از اینکه در این سفر همراه من بودید سپاسگزارم. تا دفعه بعد، کد نویسی مبارک! 🚀

نوشته های مشابه

دیدگاهتان را بنویسید

نشانی ایمیل شما منتشر نخواهد شد. بخش‌های موردنیاز علامت‌گذاری شده‌اند *

دکمه بازگشت به بالا