CPU چگونه کار می کند؟ – به زبان ساده
درک کارکرد اغلب قطعات رایانه مانند RAM، دیسک ذخیرهسازی، وسایل جانبی و همچنین نرمافزارهایی که در مجموع به کارکرد صحیح رایانه کمک میکنند، کار سادهای است. اما قلب هر سیستم رایانهای CPU است که حتی از نظر بسیاری از کارشناسان رایانه نیز به عنوان قطعهای جادویی نگریسته میشود. در این نوشته تلاش میکنیم کارکرد این جزء رایانه را توصیف کنیم.
نکتهای که پیش از آغاز این مقاله باید در خاطر داشته باشیم این است که اغلب CPU های مدرن از نظر اندازه بزرگی، بسیار پیچیدهتر از مواردی هستند که در این نوشته بررسی خواهیم کرد. در واقع درک همه بخشهای یک تراشه با بیش از یک میلیارد ترانزیستور برای هر فردی ناممکن است. با این وجود، مفاهیم مقدماتی در مورد هماهنگی همه بخشهای یک CPU در مورد همه CPU ها یکسان است و درک این مقدمات باعث میشود که درک بهتری از CPU های مدرن نیز به دست بیاورید.
آغاز از موارد کوچک
کارکرد رایانهها به روش دودویی یا باینری است. رایانهها فقط دو حالت را درک میکنند، روشن و خاموش. آنها برای اجرای محاسبات به زبان باینری از قطعهای به نام ترانزیستور استفاده میکنند. ترانزیستور تنها در صورتی اجازه عبور جریان منبع از خود را میدهد که روی گیت آن جریانی اعمال شده باشد. این وضعیت اساس یک سوئیچ باینری را تشکیل میدهد که بسته به سیگنال ورودی ثانویه، اتصال را قطع میکند.
رایانههای مدرن از میلیاردها ترانزیستور برای اجرای محاسبات خود استفاده میکنند؛ اما در پایینترین سطح شما تنها به تعداد معدودی از ترانزیستورها برای تشکیل ابتداییترین اجزا که گیت (gate) نامیده میشوند نیاز دارید.
گیتهای منطقی
با گرد هم آوردن صحیح چند ترانزیستور میتوان یک گیت منطقی ساخت. گیتهای منطقی دو ورودی باینری میگیرند و با اجرای یک عملیات روی آنها، مقدار خروجی را بازگشت میدهند. برای مثال، گیت OR در صورتی مقدار True بازمیگرداند که یکی از ورودهایش true باشد. گیت AND بررسی میکند که آیا هر دو ورودی true هستند یا نه و XOR نیز زمانی مقدار true بازمیگرداند که یکی از ورودیهایش true باشند. نسخههای N این گیتهای منطقی (یعنی NOR، NAND و XNOR)، نمونههای معکوس این گیتهای مقدماتی هستند.
محاسبات ریاضی با استفاده از گیتها
صرفاً به کمک دو گیت میتوان یک عمل جمع ابتدایی را اجرا کرد. نمودار فوق یک نیمجمعکننده (half adder را نمایش میدهد). گیت XOR در این مدار زمانی روشن میشود که صرفاً یکی از ورودیهایش true شده باشد و نه هر دو آنها. گیت AND زمانی روشن میشود که هر دو ورودی روشن باشند؛ اما زمانی که ورودی نباشد خاموش میماند. بنابراین اگر هر دو روشن باشند، XOR خاموش میماند و گیت AND روشن میشود و پاسخ صحیح که 2 است به دست میآید:
بدین ترتیب با این تنظیمات ساده به سه خروجی متمایز 0، 1 و 2 دست مییابیم. اما با یک بیت هیچ چیزی بزرگتر از 1 را نمیتوانیم ذخیره کنیم و این ماشین با توجه به این که صرفاً یکی از سادهترین مسائل ریاضی را حل میکند، فایده چندانی نخواهد داشت. اما دقت کنید که این مدار صرفاً یک نیمجمعکننده است و اگر دو مورد از آنها را با استفاده از یک ورودی دیگر به هم متصل کنید، میتوانید یک تمامجمعکننده (Full Adder) به دست آورید:
مدار تمامجمعکننده سه ورودی دارد که دو مورد از آنها اعدادی هستند که باید جمع شوند و یک مورد نیز ورودی نَقلی (carry in) است. این جزء نقلی زمانی که خروجی از حد قابل قبول برای ذخیره در یک بیت منفرد تجاوز میکند، مورد استفاده قرار میگیرد. آدرس کامل در یک زنجیره ذخیره میشود و عنصر نقلی از یک جمعکننده به جمعکننده دیگر ارسال میشود. در نهایت رقم نقلی به نتیجه گیت XOR در نیمجمعکننده اول اضافه میشود و یک گیت OR دیگر نیز برای مدیریت هر دو حالت در موارد نیاز وجود دارد.
زمانی که هردو ورودی روشن باشند، رقم نقلی روشن میشود و آن را به تمامجمعکننده بعدی در زنجیره اضافه میکند.
و بدین ترتیب عمل جمع انجام مییابد. بهرهگیری از بیتهای بیشتر صرفاً به معنی افزودن ایجاد آدرسهای کامل جدید در زنجیرهای طولانیتر است.
اجرای موارد دیگری از عملیات ریاضی نیز با استفاده از جمع امکانپذیر است. ضرب در واقع همان تکرار عمل جمع است، تفریق از طریق نوعی معکوسسازی بیت میسر است و تقسیم صرفاً تکرار عمل تفریق است. با این که اغلب رایانههای مدرن، راهحلهای مبتنی بر سختافزاری برای اجرای موارد پیچیدهتر عملیات ریاضی دارند؛ اما شما میتوانید از نظر فنی همه آنها را با استفاده از تمامجمعکننده نیز انجام دهید.
باس (Bus) و حافظه
اینک رایانه ما چیزی به جز یک ماشین حساب بد نیست! دلیل این مسئله آن است که این ماشین حساب نمیتواند هیچ چیز را به خاطر بیاورد و با خروجی خود نیز هیچ کاری انجام نمیدهد. در تصویر فوق یک سلول حافظه را مشاهده میکنید که همه این کارها را میتواند انجام دهد. البته در پسِ این شِماتیک تعداد زیادی گیتهای NAND قرار دارند و در عمل نیز بسته به تکنیک ذخیرهسازی ممکن است کاملاً متفاوت باشد؛ ولی در هر حال کارکرد آن به همین شکل است. شما به این سلول یک ورودی میدهید، بیت نوشتن (write) را روشن میکنید و این سلول، ورودی را درون خود ذخیره میکند.
البته ما همواره به عمل خواندن یک سلول حافظه هم نیاز داریم. این کار از طریق یک فعالساز (enabler) که مجموعهای از گیتهای AND برای هر بیت از اطلاعات است میسر میشود. این enabler به ورودی دیگری که بیت خواندن (read) است مرتبط است. بیتهای خواندن و نوشتن غالباً به صورت set و enable نیز خوانده میشوند.
کل این بسته به صورت مجموعهای به نام ثبّات (register) نامیده میشود. این ثباتها به باس (گذرگاه) وصل میشوند که مجموعهای از سیمها است که در کل سیستم میچرخند و به همه اجزا اتصال یافتهاند. در همه رایانههای مدرن باس وجود دارد، و برای بهبود عملکرد چندوظیفگی از باس های چندگانه نیز کمک گرفته میشود.
هر ثبات نیز یک بیت خواندن و نوشتن دارد؛ اما در این تنظیمات، ورودی و خروجی چیز یکسانی هستند. این وضعیت در عمل خوب است. برای مثال اگر بخواهیم محتوای R1 را به R2 کپی کنیم، باید بیت خواندن را برای R1 روشن کنیم که باعث میشود محتوای R1 به باس انتقال یابد. در حالی که بیت خواندن روشن است، باید بیت نوشتن R2 را روشن کنید تا محتوای باس به R2 کپی شود.
ثباتها برای ساخت RAM نیز مورد استفاده قرار میگیرند. رم غالباً به شکل شبکهای طراحی میشود که سیمهای آن در دو جهت کشیده شدهاند:
دیکودرها یک ورودی باینری را میگیرند و شماره سیم مربوطه را روشن میکنند. برای مثال، 11 همان عدد 3 به زبان باینری است و بالاترین عدد 2 بیتی محسوب میشود، از این رو دیکودر باید بالاترین سیم را روشن کند. در هر تقاطع ثباتهایی وجود دارند. همه اینها به باس مرکزی و همچنین به یک ورودی خواندن و نوشتن مرکزی متصل هستند. هر دو ورودی خواندن و نوشتن تنها زمانی روشن میشوند که دو سیم که از روی ثبات میکنند نیز روشن باشند و بدین ترتیب امکان انتخاب ثباتهایی که قرار است خوانده و نوشته شوند ممکن میشود. در این مورد نیز باید اشاره کنیم که RAM های مدرن بسیار پیچیدهتر هستند؛ اما همچنان از این تنظیمات استفاده میکنند.
ساعت، stepper و دیکودر
ثباتها در همه جا استفاده میشوند و ابزاری مقدماتی برای جابجایی دادهها و ذخیرهسازی اطلاعات در CPU محسوب میشوند. اما این کار چگونه صورت میپذیرد؟
ساعت (Clock) نخستین جزئی در هسته CPU است که در بازههای معین که برحسب هرتز یا چرخه بر ثانیه اندازهگیری شده است، روشن و خاموش میشود. این همان سرعتی است که هنگام تبلیغ CPU ها مشاهده میکنید. یک CPU 5 گیگاهرتز میتواند 5 میلیارد چرخه را در هر ثانیه اجرا کند. سرعت ساعت در اغلب موارد معیار خوبی برای محاسبه میزان سریع بودن CPU محسوب میشود.
ساعت سه جزء متفاوت دارد، ساعت پایه، ساعت فعالسازی و ساعت set. ساعت پایه در نیمی از چرخه روشن میشود و در نیمه دیگر خاموش میشود. ساعت فعالسازی برای روشن کردن ثباتها استفاده میشود و باید مدت بیشتری روشن بماند تا مطمئن شویم که دادهها فعال شدهاند. ساعت set همواره باید همزمان با ساعت enable روشن باشد، چون در غیر این صورت دادهها ممکن است به اشتباه نوشته شوند.
ساعت به stepper متصل است که از یک تا بیشترین گام را میشمارد و زمانی که چنین کرد، خود را ریست میکند. ساعت همچنین به گیتهای AND هر ثباتی که CPU میتواند بنویسد متصل است:
این گیتهای AND به خروجی جزء دیگر یعنی دیکودر دستورالعمل نیز اتصال دارند. دیکودر دستورالعمل، یک دستورالعمل مانند «مقدار R2 را برابر با R1 تنظیم کن» دریافت میکند و آن را به چیزی دیکود میکند که CPU بتواند آن را درک کند. این دیکودر یک ثبات درونی دارد که «ثبات دستورالعمل» (Instruction Register) نام دارد و همان جایی است که عملیات جاری در آن ذخیره میشود. طرز کار دقیق این دیکودر به سیستمی که در حال اجرا در میآید وابسته است؛ اما زمانی که دستورالعمل را کدگشایی کرد، set صحیح را روشن میکند و بیتها را برای ثباتهای صحیح فعال میسازد که بر مبنای ساعت تنظیم میشوند.
دستورالعملهای برنامه در RAM (یا در سیستمهای مدرن در کش L1 که به CPU نزدیکتر است) نگهداری میشوند. از آنجا که برنامه در ثباتهایی ذخیره شده است، مانند هر متغیر دیگری میتوان آن را دستکاری کرد و به بخشهای مختلف برنامه jump کرد. برنامهها به همین ترتیب دستورالعملهای خود را با حلقهها و دستورهای if دریافت میکنند. دستورالعمل jump مکان کنونی RAM که دیکودر دستورالعمل، مشغول خواندن است را به مکان دیگری تغییر میدهد.
همه اینها چطور با هم کار میکنند؟
اینک تصویر بسیار سادهای که از فرایند کاری CPU ارائه کردیم به پایان رسیده است. باس اصلی کل سیستم را شامل میشود و به همه ثباتها اتصال مییابد. تمام جمع کنندهها همراه با دستهای از عملیات دیگر در یک واحد منطقی محاسبات (ALU) تجمیع میشوند. این ALU اتصالهایی به باس دارد و ثباتهایی نیز دارد که عدد دومی که عملیات روی آن صورت میگیرد را ذخیره میکنند.
برای اجرای یک محاسبه، دادههای برنامه از RAM سیستم وارد بخش کنترل میشوند. بخش کنترل دو عدد را از RAM میخواند، عدد نخست را در ثبات دستورالعمل ALU ذخیره میکند و سپس عدد دوم را در باس ذخیره میسازد. به طور همزمان یک کد دستورالعمل به ALU که وظیفه آن را تعیین میکند. در این هنگام ALU همه محاسبات را انجام داده و نتیجه را در ثبات دیگری که CPU میتواند آن را خوانده و ادامه پردازش را پیگیری کند، ذخیره میکند.
اگر این مطلب برایتان مفید بوده است، آموزشهای زیر نیز به شما پیشنهاد میشوند:
- مجموعه آموزشهای دروس مهندسی کامپیوتر
- سیپییو (CPU) چیست و چه وظیفهای در رایانه بر عهده دارد
- مجموعه آموزشهای مهندسی نرمافزار
- چگونه CPU و مادربرد رایانه خود را تعویض کنیم؟ — راهنمای مصور و آسان
- منطق ترکیبی را به زبان ساده و با مجموعه مقالات فرادرس یاد بگیرید
- آموزش های ویژه علاقهمندان به کامپیوتر
- آموزش مونتاژ کامپیوتر به زبان ساده — مجموعه مقالات جامع و مصور فرادرس
- مجموعه آموزش های مدارهای منطقی (طراحی دیجیتال)
==