<h2>Real Stuff: Memory Hierarchies in Commercial Processors</h2> <p>Real processors implement the caching and memory concepts covered throughout this chapter with specific, carefully chosen parameters. Both the <code>ARM Cortex-A53</code> and <code>Intel Core i7</code>, discussed earlier in this series regarding pipeline design, also differ meaningfully in their memory hierarchies: mobile-oriented designs like the Cortex-A53 typically use smaller cache sizes at each level to conserve power and die area, while performance-oriented designs like the Core i7 use larger, multi-level caches, often three levels deep, to minimize average memory access time at the cost of additional power and chip area.</p> <h2>Applying Cache Concepts: Cache Blocking for Matrix Multiply</h2> <p>Matrix multiplication, discussed earlier in this series regarding subword parallelism and instruction-level parallelism, can also be optimized specifically for the memory hierarchy using a technique called <code>Cache Blocking</code> (also called <code>Tiling</code>). Rather than processing an entire large matrix row by row, which can repeatedly evict useful cached data due to capacity misses discussed earlier in this series, the matrix is divided into smaller sub-blocks sized specifically to fit within the cache.</p> <pre class="code-block"><code>Without blocking: Large matrix accessed row-by-row, repeatedly evicting data still needed later, causing many capacity misses With blocking: Matrix divided into smaller sub-blocks that fit entirely within the cache, each sub-block fully processed before moving to the next</code></pre><br> <p>By ensuring each sub-block's data remains in the cache throughout its processing, cache blocking significantly reduces the number of capacity misses, directly applying the locality principles introduced earlier in this series to a real, widely used computational workload.</p> <h2>Common Fallacies About Memory Hierarchies</h2> <ul> <li>Assuming a larger cache is always better — as discussed earlier regarding cache performance tradeoffs, a larger cache increases hit time and cost even as it reduces capacity misses.</li> <li>Assuming virtual memory and caching are unrelated systems — as shown earlier in the unified framework covering block placement, identification, replacement, and write policy, they answer the exact same underlying questions.</li> <li>Assuming a cache miss always costs the same amount of time — as discussed earlier regarding the three types of misses, the actual cost depends heavily on which level of the memory hierarchy must ultimately satisfy the request.</li> </ul> <h2>Common Pitfalls in Memory-Sensitive Code</h2> <ul> <li>Writing code with poor spatial locality, such as accessing array elements in a non-sequential pattern, which defeats the benefit of the block-based caching discussed earlier in this series.</li> <li>Ignoring the load-use hazard discussed earlier in this series when reasoning about why memory-heavy code sometimes performs worse than expected despite a seemingly efficient algorithm.</li> <li>Overlooking multicore cache coherence overhead, discussed earlier in this series, when writing parallel code that frequently modifies shared data across cores.</li> </ul> <h2>Chapter Summary: The Full Memory Hierarchy Picture</h2> <p>This chapter traced the path from the smallest and fastest storage to the largest and slowest: SRAM-based caches exploiting locality of reference, virtual memory providing both illusion of abundant memory and process isolation, dependable memory techniques protecting against silent data corruption, cache coherence keeping multicore systems consistent, and RAID protecting persistent storage against physical disk failure. Every one of these mechanisms exists because no single memory technology can be simultaneously fast, large, cheap, and reliable — a theme first introduced at the very start of this chapter and echoed in every technique built on top of it.</p>

مفاهیم نظری کش و حافظه در پردازنده‌های تجاری واقعی با چند سطح کش و اندازه‌های به‌دقت تنظیم‌شده شکل مشخصی به خود می‌گیرند. این مقاله سلسله‌مراتب حافظه واقعی در پردازنده‌های ARM و Intel را مقایسه می‌کند، نشان می‌دهد Cache Blocking چگونه ضرب ماتریس را در عمل تسریع می‌کند، و فصل سلسله‌مراتب حافظه را با پرداختن به تصورات غلط رایج به پایان می‌رساند.

سلسله‌مراتب حافظه واقعیCache Blockingمغالطات سلسله‌مراتب حافظه

~4 دقیقه مطالعه · آخرین به‌روزرسانی ۱۵ شهریور ۱۴۰۵

واقعیت‌های عملی: سلسله‌مراتب حافظه در پردازنده‌های تجاری

پردازنده‌های واقعی مفاهیم کش و حافظه پوشش‌داده‌شده در سراسر این فصل را با پارامترهای مشخص و به‌دقت انتخاب‌شده پیاده‌سازی می‌کنند. هم ARM Cortex-A53 و هم Intel Core i7، که پیش‌تر در این مجموعه درباره طراحی پایپ‌لاین بحث شد، همچنین به‌طور معناداری در سلسله‌مراتب حافظه‌شان متفاوت‌اند: طرح‌های موبایل‌محور مانند Cortex-A53 معمولاً از اندازه‌های کش کوچک‌تر در هر سطح برای صرفه‌جویی در توان و مساحت die استفاده می‌کنند، در حالی که طرح‌های کارایی‌محور مانند Core i7 از کش‌های بزرگ‌تر و چندسطحی، اغلب سه سطح عمیق، استفاده می‌کنند تا میانگین زمان دسترسی حافظه را به قیمت توان و مساحت تراشه اضافه به حداقل برسانند.

به‌کارگیری مفاهیم کش: Cache Blocking برای ضرب ماتریس

ضرب ماتریس، که پیش‌تر در این مجموعه درباره موازی‌سازی زیرکلمه‌ای و موازی‌سازی سطح دستور بحث شد، همچنین می‌تواند به‌طور خاص برای سلسله‌مراتب حافظه با استفاده از تکنیکی به نام Cache Blocking (که Tiling نیز نامیده می‌شود) بهینه شود. به‌جای پردازش یک ماتریس بزرگ کامل ردیف‌به‌ردیف، که می‌تواند به‌طور مکرر داده کش‌شده مفید را به‌دلیل capacity miss هایی که پیش‌تر در این مجموعه بحث شد تخلیه کند، ماتریس به زیربلوک‌های کوچک‌تری تقسیم می‌شود که به‌طور خاص برای جا شدن درون کش اندازه‌گیری شده‌اند.

بدون blocking:
ماتریس بزرگ ردیف‌به‌ردیف دسترسی می‌شود،
داده‌ای که بعداً هنوز مورد نیاز است به‌طور مکرر تخلیه می‌شود،
که باعث بسیاری از capacity miss ها می‌شود

با blocking:
ماتریس به زیربلوک‌های کوچک‌تری تقسیم می‌شود
که کاملاً درون کش جا می‌شوند،
هر زیربلوک به‌طور کامل پردازش می‌شود
پیش از حرکت به بعدی

با اطمینان از اینکه داده هر زیربلوک در طول پردازش آن در کش باقی می‌ماند، cache blocking به‌طور قابل‌توجهی تعداد capacity miss ها را کاهش می‌دهد، و مستقیماً اصول محلیت معرفی‌شده پیش‌تر در این مجموعه را به یک بار کاری محاسباتی واقعی و به‌طور گسترده استفاده‌شده اعمال می‌کند.

مغالطات رایج درباره سلسله‌مراتب حافظه

  • فرض اینکه کش بزرگ‌تر همیشه بهتر است — همان‌طور که پیش‌تر درباره مبادلات کارایی کش بحث شد، کش بزرگ‌تر زمان hit و هزینه را افزایش می‌دهد حتی در حالی که capacity miss را کاهش می‌دهد.
  • فرض اینکه حافظه مجازی و کشینگ سیستم‌های نامرتبطی هستند — همان‌طور که پیش‌تر در چارچوب یکپارچه پوشش‌دهنده جای‌گذاری، شناسایی، جایگزینی، و سیاست نوشتن نشان داده شد، آن‌ها دقیقاً به همان پرسش‌های زیربنایی پاسخ می‌دهند.
  • فرض اینکه یک cache miss همیشه همان مقدار زمان هزینه دارد — همان‌طور که پیش‌تر درباره سه نوع miss بحث شد، هزینه واقعی به‌شدت به این بستگی دارد که کدام سطح از سلسله‌مراتب حافظه باید در نهایت درخواست را برآورده کند.

دام‌های رایج در کد حساس به حافظه

  • نوشتن کد با محلیت مکانی ضعیف، مانند دسترسی به عناصر آرایه در یک الگوی غیرپی‌درپی، که بهره کشینگ مبتنی‌بر‌بلوک که پیش‌تر در این مجموعه بحث شد را از بین می‌برد.
  • نادیده گرفتن خطر load-use که پیش‌تر در این مجموعه بحث شد هنگام استدلال درباره اینکه چرا کد سنگین از نظر حافظه گاهی با وجود یک الگوریتم به‌ظاهر کارآمد، بدتر از انتظار عمل می‌کند.
  • نادیده گرفتن سربار انسجام کش چندهسته‌ای، که پیش‌تر در این مجموعه بحث شد، هنگام نوشتن کد موازی که به‌طور مکرر داده مشترک را در سراسر هسته‌ها تغییر می‌دهد.

جمع‌بندی فصل: تصویر کامل سلسله‌مراتب حافظه

این فصل مسیر از کوچک‌ترین و سریع‌ترین ذخیره‌سازی تا بزرگ‌ترین و کندترین را دنبال کرد: کش‌های مبتنی بر SRAM که محلیت مرجع را بهره‌برداری می‌کنند، حافظه مجازی که هم توهم حافظه فراوان و هم ایزوله‌سازی فرآیند فراهم می‌کند، تکنیک‌های حافظه قابل‌اعتماد که در برابر خرابی بی‌سروصدای داده محافظت می‌کنند، انسجام کش که سیستم‌های چندهسته‌ای را سازگار نگه می‌دارد، و RAID که ذخیره‌سازی پایدار را در برابر خرابی فیزیکی دیسک محافظت می‌کند. هرکدام از این مکانیزم‌ها به این دلیل وجود دارند که هیچ فناوری حافظه واحدی نمی‌تواند هم‌زمان سریع، بزرگ، ارزان، و قابل‌اعتماد باشد — موضوعی که ابتدا در همان ابتدای این فصل معرفی شد و در هر تکنیکی که روی آن ساخته شد بازتاب یافت.

نوشته و پژوهش‌شده توسط دکتر شاهین صیامی

مقالات مرتبط

تصورات غلط رایج درباره محاسبات موازی و درس‌های نهایی کتاب

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

ادامه

واقعیت‌های عملی: بنچمارک CPU در مقابل GPU و ضرب ماتریس چندپردازنده‌ای

مقایسه منصفانه یک CPU و یک GPU نیازمند مدلی است که هم توان عملیاتی محاسباتی و هم محدودیت‌های پهنای باند حافظه را با هم در نظر بگیرد. این مقاله مدل roofline مورد استفاده برای مقایسه سخت‌افزار واقعی مانند Intel Core i7 و NVIDIA Tesla GPU را معرفی می‌کند، سپس نشان می‌دهد ضرب ماتریس چگونه در سراسر چند پردازنده تسریع می‌شود، به‌عنوان کاربرد عملی نهایی مفاهیم موازی این فصل.

ادامه

بنچمارک کردن چندپردازنده‌ها و مدل‌سازی کارایی موازی

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

ادامه

شبکه‌سازی کلاستر: ارتباط با دنیای بیرون

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

ادامه

کلاسترها، کامپیوترهای در مقیاس انبار، و توپولوژی‌های شبکه

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

ادامه

مقدمه‌ای بر GPU: موازی‌سازی عظیم برای بارهای کاری سنگین از نظر داده

یک GPU ایده SIMD که پیش‌تر در این مجموعه پوشش داده شد را به یک مقیاس افراطی می‌برد، و هزاران رشته سبک را به‌طور هم‌زمان اجرا می‌کند تا حجم عظیمی از داده مستقل را پردازش کند. این مقاله توضیح می‌دهد چرا GPU ها از نظر معماری این‌قدر با CPU متفاوت‌اند، مدل اجرای رشته آن‌ها چگونه کار می‌کند، و چه نوع بارهای کاری بیشترین بهره را از این طراحی می‌برند.

ادامه