وبسایت شخصی حسن هاشمی

برنامه نویس. ایران. قم :))

مروری بر معماری اندروید - قسمت اول

فکر نمی کنم نیازی باشه که بخوایم اهمیت درک معماری سیستم عاملی که داریم ازش استفاده و یا احیاناً داریم براش برنامه می نویسیم رو اثبات کنیم.

درک عمیق از کمپوننت های مختلف شکل دهنده ساختار سیستم عامل به ما کمک می کنه تا حداکثر استفاده رو از امکانات فراهم شده توسط اون رو داشته باشیم. که از قضا اندروید هست برای این پست.

برای مثال در سیستم عامل ویندوز درک درست و حسابی از process management برای تضمین امنیت نرم افزار مهمه.

و یا مدل مدیریت thread ها که توی Multi threading حیاتیه.

برای سیستم عامل اندروید هم از این مثال ها میشه زد. 

اولش می خواستم توی یه پست اینکارو انجام بدم، اما دیدم دیاگرام توضیحات زیادی داره و توی یه پست خیلی طولانی میشه. در نتیجه به صورت چند پست می نویسمشون.

برای اولین میریم سراغ خاستگاه لینوکسی اندروید.

پس برای شروع دیاگرام رو میذارم:

توی این دیاگرام قسمت قرمز رنگ به زبان C و Assembly نوشته شده، قسمت سبز رنگ ++C و قسمت آبی هم کاملاً جاوا هست. 

همونجور که می دونید اندروید مبتنی بر kernel 2.6 لینوکس هستش.

برای این که از بحث اصلی دور نشیم و هم یه یاد آوری بشه یه توضیح مختصری از کرنل:

kernel بخشی از سیستم عامل هست که دسترسی بخش های مختلف سیستم عامل رو به منابع سخت افزار فراهم و مدیریت می کنه. در ساده ترین حالت thread ی کد برنامه شما رو اجرا می کنه از قلب kernel رد میشه:) و به cpu میرسه. 

به علاوه که kernel دسترسی شما رو به سخت افزار به صورت انتزاعی برآورده می کنه و از اونطرف خودش با استفاده از درایوارهایی که زمان اجرا لود می کنه به صورت واقعی به سخت افزار دسترسی پیدا می کنه. به صورت اختصاری به این کار می گن HAL .

 توضیحات در مورد HAL در حیطه این پست نیست.

خب برگردیم به بحث اصلیمون، کرنل لینوکس مدیریت process، مدیریت حافظه و... رو فراهم می کنه. اما ...

اما اندروید از Linux kernel بیشتر به عنوان لایه ای که انتزاع کننده سخت افزار هست استفاده می کنه. (نه به این معنی که بقیه جاهاش رو بی خیال شده ) چون اگر واقع بین باشیم واقعاً خوب پیاده سازی شده و کاراییش در این بخث ثابت کرده.


در Kernel 2.6 بهینه سازی خیلی خیلی زیادی انجام شد تا بتونن برای دیوایس های با cpu و مموری پایین ازش استفاده کنند. 

حالا این حرف هایی که زدیم به این معنیه که فی المثل اگه شما روزی خواستین یه Device بسازید که از سیستم عامل اندروید استفاده می کنه، اولین کاری که باید بکنید اینه که برای سخت افزارهایی مثل دوربین، یو اس بی ... درایورهایی بنویسید. که از قواعد کرنل لینوکس پیروی می کنن. 

که در واقع توی ++C چیزی فراتر از یه سری header نیستن، توابع اجباری رو پیاده سازی می کنید و  بعد اونا رو به عنوان module در اختیار کرنل لینوکس قرار بدید. بقیه اش با خودش؛ یه جورایی منو یاده windows service میندازه :) 


#include <linux/init.h>
#include <linux/config.h>
#include <linux/module.h>
// ... 

module_init(); // با ارائه پیاده سازی دلخواه به این تابع و توابع زیرین میتونید عملکرد سخت افزارتون 
               // رو به لینوکس بفهمونید
module_exit();
...
...            // بقیه توابع

یه نکته مثبتی دیگه ای که کرنل لینوکس داره، و برمیگرده به ماهیت اوپن سورس بودن اینه که خیلی زیاد قابل سفارشی کردنه. یعنی تا جایی که من متوجه شدم و سورس های این دوتا رو (کرنلی که گوگل استفاده می کنمه وکرنل اورجینال لینوکس) خیلی جاهاش توی کرنل اندروید حذف شدن و منطقی هم هست چون کرنل لینوکس برای سیستم بزرگتری تدارک دیده شده در حالیکه کرنل اندروید امکانات محدودتری نیاز داره.

توی دیاگرام در بخش کرنل قسمت های دیگه ای هم هستن که فکر نمی کنم نیازی به توضیح داشته باشن:)

اما فکر می کنم Binder (IPC) Driver رو یه نگاهی باید بهش بکنیم.

یه خاصیت جالب دیگه کرنل لینوکس هم اینه که برای ارتباط بین دو تا process مکانیزمش تحمیل نمی کنه، یعنی لفظ کلمه driver همه چیز رو حل می کنه. یعنی داره میگه اگه مکانیزم پیش فرض لینوکس برای ارتباط خارج از process رو نمی پسندید کافیه یه درایور بنویسید. 

در واقع سازندگان اندروید موقعی که می خواستن مکانیزم Binding رو برای Interprocess Communication پیاده سازی کنن تنها لازم بود یه درایور بنویسن. که همین کارو هم کردن به خاطر همین اسم مکانیزم فعلی اندروید برای اینکار Binder IPC Driver هست.

Binder واقعاً مکانیزم ساده ای هست که کارو برای برنامه نویسان اندروید راحت می کنه و یه جورایی داره سعی می کنه دردسرهایی که مکانیزم های ویندوز برای ارتباط خارج از process رو داشت رفع کنه. (البته چون ویندوز سیستم عامل گسترده تری اون دردسرها اجتناب ناپذیر هستن).

یه دیاگرام از مراحل عملکرد BInder رو که تو گوگل پیدا کردم براتون می ذارم:


این وسط تنها چیزی که می درخشه نقش Binder هست که توسط درایور در اختیار کرنل قرار گرفته.

واقعاً از اینجا یه درود به معمار کرنل لینوکس می فرستم:)  (یه جور Dependency Injection رو توی اون سطح پیاده کرده.)

تنها کاری که Caller می کنه اینه که یه پروکسی بسازه و پیام ها رو دریافت کنه. اینکه سرویس کجاست و چجوری باید بهش وصل شه دیگه بر عهده Driver IPC Binder ی هست قبلاً نوشته شده.

انشالله در پست های بعد میریم سراغ Android runtime, Dalvik, Libraries ... 

نظرات (4) -

  • ایمان

    08/22/1394 07:58:59 ب.ظ | پاسخ به این نظر

    سید جان. عالی هست. سپاسگزارم.
    خواهشا این بحث های چندنخی و کرنل رو بیشتر برایش مطلب بگذارید. چون واقعا ادم رو به فکر وا می دارد.
    فقط منابع رو نیز ذکر کنید تا برای مطالعه بیشتر بتوانیم رجوع کنیم.

    سوال:

    1. به نظر جنابعالی برنامه نویسی اندروید با چه زبانی و در چه محیط ide مناسب هست؟
    2. برنامه نویسی کرنل لینوکس آیا ارزش وقت گذاشتن دارد یا نه؟ آینده ای دارد؟ کلا چطور هست؟ چه پیش زمینه هایی لازم است؟
    3. ضمنا بهترین ide برای ++c چی هست؟
    4. برای اندروید و قضیه port کردن به دیگر دستگاه ها چه منابعی خوب هست؟
    5. برای سفارشی سازی کرنل باید چه پیش زمینه هایی را یاد گرفت؟

    از شما دوست خوبم بسیار سپاسگزارم که دانش خود را به اشتراک می گذارید.
    همیشه سالم و موفق باشید.
    در پناه حق.

  • حسن

    08/23/1394 11:02:47 ق.ظ | پاسخ به این نظر

    سلام
    1- برای افرادی که تجربه کمی در برنامه نویسی دارن جاوا و اندروید استودیو بهتره.
    2- آینده شغلی نداره توی ایران و افغانستان نداره.
    اما این امکان رو برای شما فراهم می کنه که به صدها پروژه اون سورس مثل لینوکس یا ... کمک کنید. (بنده خودم به صورت پاره وقت اینکارو انجام میدم و واقعاً لذت بخشه).
    آشنایی زیاد به عملکرد cpu و زبان assembly حیاتیه و بعد از اون زبان C و بعد از همه اینا ++C.
    3- ویژوال استودیو
    4- منظور شما رو متوجه نشدم Smile
    5- مانند سوال دوم.

  • ایمان

    08/23/1394 03:18:18 ب.ظ | پاسخ به این نظر

    سلام دوباره حسن جان. ممنونم از پاسخ ها.
    واقعا سیپاس فراوان.

    1. در مورد پاسخ اول منظورتان را متوجه نشدم، "افراد کم تجربه از جاوا استفاده کنند". افراد با تجربه از چه چیزی استفاده می کنند؟

    2. واقعیتش توی کل آسیا به غیر چند کشور انگشت شمار بقیه فقط به دنبال عمله هستن. که ایران و افغانستان فکیر میکنم پرچم دار عملگی باشند. و رقابت شدیدی هم بین این دو در به دست گرفتن پرچم عملگی وجود دارد.
    گذشته از اینده شغلی و ... واقعیتش من می خواهم قدرت دیدم را بیشتر کنم بتوانم بهتر بفهمم به همین علت می پرسم که برای کار کردن در زمینه کرنل و خصوصا نحوه تغییر کدها و اضافه کردن و کامپایل کرنل باید چی کار کرد؟ آیا ابزارهای خاصی دارد؟ چه سایت و کتاب راهنمایی وجود دارد؟

    3. در خصوص زبان اسمبلی همان زبان قدیمی 16 بیتی منظورتان هست که برای سری های 8086 و ... اینتل هست؟ یا چیزهای دیگر هم مدنظر هست؟
    برای عملکرد cpu که فکیر میکنم باید معماری کامپیوتر را بیخوانیم؟درسته؟
    فقط نمیدانم کدام منبع خوبه؟

    4. در خصوص سوال چهارم منظورم این بود که:  پیاده سازی و port کردن کرنل برای یک دستگاه هست. اگر توجه کنید الان اندروید در گوشی های مختلف وجود دارد. و در عین حال در دستگاه های مختلفی همچون ساعات هوشمند هم port شده هست. البته بر روی pc هم یک نسخه را port کرده اند.یعنی اینکه از سایت فایل iso را دانلود می کنیم و رایت میکنیم و سپس مانند دیگر سیستم عامل ها نصبش می کنیم. اینی که برای pc آماده شده را یه چندتا تایوانی آماده کرده اند. البته من روی pc نصیب کردم ولی متاسفانه آنچنان که خوب باشد نبود و مشکلات فراوانی را دارد.
    حالا سوالم این بود که چطوری این ها رو برای این دستگاه ها آماده می کنند؟ و یا به تعبیر دیگر port می کنند؟

    باز هم ببخشید که سرتان را درد آوردم و مزاحمتان شدم.
    از شما دوست خوب گرامیم کمال تیشکر را دارم.
    امید به بیهروزی و موفقیتهای بیشترتان.
    یا حق.

    • حسن

      08/23/1394 05:09:54 ب.ظ | پاسخ به این نظر

      سلام
      1- ++C، C و #C

      2- واقعاً جواب دقیق و روشنی توی ذهنم غیر از اونی که توی سوال بالا گفتم، ندارم Smile

      3- بستگی داره تو هر بخشی کار میکنید روی همون ISA تمرکز کنید.
      قسمت 2: منظورم از cpu کلاً، کارکرد سخت افزار هست. ساختار رم، bus، Memorty Controller و ...
      در کل اگر می خواهید در این بخش واقعا تاپ باشید (در حدی که توی تکامل سیستم عامل ها صاحب نظر باشید) کنید نیازمند اطلاعات زیادی هستید که توی کل رشته علوم کامپیوتر (مدار، جبر بول، ریاضیات گسسته، معادلات دیفرانسیل) پراکنده هستن.
      به عنوان مثال توی سوالای قبلی که در مورد سرعت جاوا و سی شارپ بود در مورد پیچیدگی الگوریتم بهت گفتم به انگلیسی یه جورایی میتونی با Asymptotic notations پیداش کنی توی پیاده سازی مدارها اهمیت دارن.
      ویا برای تحلیل عملکرد cpu و رم، و شبیه سازی سیستم به درس معادلات دیفرانسیل نیاز داری.

      4- در این حوزه اطلاعات کافی ندارم متأسفانه (به گوشم هم نخورده تا حالا) Smile
      اما در صورتی که خودتون می خواید فی المثل یه گوشی هوشمند جدید بسازید اول از همه باید درایورهاشو فراهم کنید.

Loading