Hardware: Gängige Mythen über CPU-Caches
Vieles, was über CPU-Caches erzählt wird, stimmt nicht. Zum Beispiel, dass Caches nicht auf Hardware-Ebene für Kohärenz sorgen können. Zeit, mit einigen Mythen über volatile Variablen und Nebenläufigkeit aufzuräumen.

Dieser Artikel ist eine Übersetzung. Das Original des Softwareentwicklers und Bloggers Rajiv Prabhakar ist hier zu finden.
- Hardware: Gängige Mythen über CPU-Caches
- Mögliche Abläufe für Schreib- und Lesevorgänge bei einer CPU mit vier Kernen
- Warum Synchronisation trotzdem wichtig ist
Als Computertechniker, der ein halbes Jahrzehnt lang bei Intel und Sun mit Caches gearbeitet hat, weiß ich einiges über Cache-Kohärenz. Im Studium gehörte das zu den schwersten Fächern, aber wenn man es einmal wirklich verstanden hat, lernt man Systemdesign-Prinzipien plötzlich zu schätzen.
Sie fragen sich vielleicht, warum sich Softwareentwickler überhaupt mit CPU-Cache-Design beschäftigen sollten. Ein Grund ist: Viele der Konzepte der Cache-Kohärenz sind direkt auf die Architektur verteilter Systeme und auf Isolationsebenen von Datenbanken anwendbar. Wenn man zum Beispiel versteht, wie Kohärenz in Hardware-Caches implementiert wird, versteht man besser, wie starke und schwache Konsistenz (beziehungsweise die sogenannte eventual consistency) funktionieren. Vielleicht kommt man auf Ideen, wie sich die Konsistenz in verteilten Systemen verbessern lässt, indem man die Erkenntnisse und Prinzipien aus der Hardware anwendet.
Ein weiterer Grund für Softwareentwickler, sich mit CPU-Cache-Design zu befassen, ist, dass Missverständnisse über Caches oft zu falschen Annahmen führen - und zwar vor allem, wenn es um eine parallele Ausführung und Race Conditions geht. Zum Beispiel gibt es die gängige Behauptung, nebenläufige Programmierung sei schwierig, weil "verschiedene Kerne veraltete Werte in ihren individuellen Caches haben können".
Auch kursiert die Annahme, dass volatile Variablen, etwa in Java, deswegen gebraucht werden, um zu verhindern, dass gemeinsam genutzte Daten lokal gecacht werden - und stattdessen gewährleisten, dass die Daten in den Hauptspeicher geschrieben oder aus dem Hauptspeicher gelesen werden.
Meistens sind solche Fehleinschätzungen harmlos (manchmal vielleicht sogar hilfreich), mitunter führen sie aber zu schlechten Designentscheidungen. Zum Beispiel mögen Entwickler so vielleicht glauben, gegen Parallelitätsfehler gefeit zu sein, wenn sie mit Single-Core-Systemen arbeiten. Allerdings kann es in Single-Core-Systemen durchaus Parallelitätsfehler geben, wenn nicht die richtigen Parallelitätskonstrukte verwendet werden.
Außerdem: Wenn volatile Variablen wirklich jedes Mal aus dem Hauptspeicher geschrieben/gelesen würden, wäre das extrem langsam. Schließlich sind Hauptspeicher-Zugriffe 200x langsamer als L1-Cache-Referenzen. Tatsächlich kann das Auslesen volatiler Variablen (in Java) oft genauso schnell sein wie eine L1-Cache-Referenz, was wiederum die Vorstellung widerlegt, dass Lese-/Schreibvorgänge mit volatilen Variablen bis in den Hauptspeicher vordringen würden. Wenn Sie bislang keine volatilen Variablen verwenden, weil Sie Bedenken wegen der Performance haben, sind Sie wahrscheinlich ein Opfer dieses Missverständnisses geworden.
Die Bedeutung von Kohärenz
Wenn aber nun verschiedene Kerne ihren eigenen Cache haben, in dem Kopien der gleichen Daten gespeichert sind, führt das nicht automatisch zu Inkongruenz bei den Daten, sobald sie mit den Schreibvorgängen beginnen? Nein, denn Hardware-Caches auf modernen x86-CPUs wie von Intel werden synchron zueinander gehalten. Solche Caches sind nicht so "dumm", wie viele Entwickler offenbar denken.
Vielmehr gibt es einige sehr komplizierte Protokolle und Logiken, die in jeden Cache eingebettet sind, mit anderen Caches kommunizieren und die Kohärenz über alle Threads hinweg erzwingen. All das geschieht auf der Hardware-Ebene - was bedeutet, dass wir als Software-/Compiler-/Systementwickler uns nicht damit befassen müssen.
Aber was meine ich eigentlich mit "synchron"? Es gibt einige Feinheiten bei dem Thema, aber eine relativ einfache Definition könnte sein: Wenn zwei Threads irgendwo im System von der gleichen Speicheradresse lesen, sollten sie niemals gleichzeitig unterschiedliche Werte lesen.
Ein Beispiel, wie nicht-kohärente Caches diese Regel verletzen können, finden Sie im ersten Abschnitt dieses Tutorials. Keine moderne x86-CPU verhält sich so, wie es im Tutorial beschrieben wird - ein fehlerhafter Prozessor aber schon.
Oder nutzen Sie das Golem-pur-Angebot
und lesen Golem.de
- ohne Werbung
- mit ausgeschaltetem Javascript
- mit RSS-Volltext-Feed
Mögliche Abläufe für Schreib- und Lesevorgänge bei einer CPU mit vier Kernen |
CPU Top 10 nach dem Leistungsindex 2022 - von PCGH getestet
![]() | ![]() | ![]() | ![]() | ![]() | ![]() | ![]() | ![]() | ![]() | ![]() | |
Produktname | Core i7-13700K | Core i9-13900K | Core i5-13600K | Ryzen 9 7950X | Ryzen 7700X | Ryzen 9 7900X | Ryzen 5 7600X | Ryzen 7 5800X3D | Core i9-12900K | Ryzen 5 5600 |
Hersteller | Intel | Intel | Intel | AMD | AMD | AMD | AMD | AMD | Intel | AMD |
Weitere Daten anzeigen ... | ||||||||||
Leistung | 97,4 %/84,0 % | 100,0 %/ 100,0 % | 92,6 %/73,2 % | 86,7 %/96,9 % | 86,5 %/68,4 % | 85,7 %/81,9 % | 82,6 %/59,7 % | 88,2 %/53,7 % | 82,9 %/76,4 % | 68,5 %/46,2 % |
Kerne | 16c/24t | 24c/32t | 14c/20t | 16c/32t | 8c/16t | 12c/24t | 6c/12t | 8c/16t | 16c/24t | 6c/12t |
Grafikeinheit | Ja | Ja | Ja | Ja | Ja | Ja | Ja | Ja | Ja | Ja |
Basis-Takt (Turbo) | 3,40/2,50 GHz (5,4/4,2 GHz) | 3,00/2,20 GHz (5,8/4,3 GHz) | 3,50/2,60 GHz (5,1/3,9 GHz) | 4,5 GHz (5,8 GHz) | 4,5 GHz (5,6 GHz) | 4,7 GHz (5,7 GHz) | 4,7 GHz (5,5 GHz) | 3,4 GHz (4,6 GHz) | 3,20/2,40 GHz (5,20/3,90 GHz) | 3,5 GHz (4,5 GHz) |
RAM | DDR5-5600 G2/ DDR4-3200 G1 | DDR5-5600 G2/ DDR4-3200 G1 | DDR5-5600 G2/ DDR4-3200 G1 | DDR5-5200 | DDR5-5200 | DDR5-5200 | DDR5-5200 | DDR4-3200 | DDR5-4800 G2/ DDR4-3200 G1 | DDR4-3200 |
Sockel | 1700 | 1700 | 1700 | AM5 | AM5 | AM5 | AM5 | AM4 | 1700 | AM4 |
Features |
|
|
|
|
|
|
|
|
|
|
Angebote |
Das ist so als ob Mann einen Trabi tunen will. Lieber eine bessere Programmiersprache...
Die Schwierigkeit ergibt sich daraus, dass es gerade in C eine große Menge "undefined...
Das kommt darauf an, auf welcher Position man auf der Erdscheibe wohnt und ob am Tag...