Was bedeuten die Begriffe "CPU-gebunden" und "E / A-gebunden"?
optimization
terminology
Entwickler
quelle
quelle
Antworten:
Es ist ziemlich intuitiv:
Ein Programm ist CPU-gebunden, wenn es schneller laufen würde, wenn die CPU schneller wäre, dh es verbringt den größten Teil seiner Zeit damit, einfach die CPU zu verwenden (Berechnungen durchzuführen). Ein Programm, das neue Ziffern von π berechnet, ist normalerweise CPU-gebunden, es knackt nur Zahlen.
Ein Programm ist E / A-gebunden, wenn es schneller gehen würde, wenn das E / A-Subsystem schneller wäre. Welches genaue E / A-System gemeint ist, kann variieren. Normalerweise verbinde ich es mit Festplatte, aber natürlich ist auch die Vernetzung oder Kommunikation im Allgemeinen üblich. Ein Programm, das eine große Datei nach einigen Daten durchsucht, kann E / A-gebunden werden, da der Engpass dann das Lesen der Daten von der Festplatte ist (tatsächlich ist dieses Beispiel heutzutage mit Hunderten von MB / s vielleicht etwas altmodisch von SSDs kommen).
quelle
CPU-gebunden bedeutet, dass die Geschwindigkeit, mit der der Prozess fortschreitet, durch die Geschwindigkeit der CPU begrenzt wird. Eine Aufgabe, die Berechnungen für einen kleinen Satz von Zahlen durchführt, beispielsweise das Multiplizieren kleiner Matrizen, ist wahrscheinlich CPU-gebunden.
E / A-gebunden bedeutet, dass die Geschwindigkeit, mit der ein Prozess fortschreitet, durch die Geschwindigkeit des E / A-Subsystems begrenzt ist. Eine Aufgabe, die Daten von der Festplatte verarbeitet, z. B. die Anzahl der Zeilen in einer Datei zählt, ist wahrscheinlich an die E / A gebunden.
Speicher gebunden bedeutet, dass die Geschwindigkeit, mit der ein Prozess fortschreitet, durch die verfügbare Speichermenge und die Geschwindigkeit dieses Speicherzugriffs begrenzt ist. Eine Aufgabe, die große Mengen an Speicherdaten verarbeitet, beispielsweise das Multiplizieren großer Matrizen, ist wahrscheinlich speichergebunden.
Cache-gebunden bedeutet die Geschwindigkeit, mit der ein Prozessfortschritt durch die Menge und Geschwindigkeit des verfügbaren Caches begrenzt wird. Eine Aufgabe, die einfach mehr Daten verarbeitet, als in den Cache passt, wird an den Cache gebunden.
I / O Bound wäre langsamer als Memory Bound wäre langsamer als Cache Bound wäre langsamer als CPU Bound.
Die Lösung für die E / A-Bindung besteht nicht unbedingt darin, mehr Speicher zu erhalten. In einigen Situationen kann der Zugriffsalgorithmus auf die Einschränkungen von E / A, Speicher oder Cache ausgelegt sein. Siehe Cache Oblivious Algorithms .
quelle
Multithreading
In dieser Antwort werde ich einen wichtigen Anwendungsfall für die Unterscheidung zwischen CPU- und E / A-gebundener Arbeit untersuchen: beim Schreiben von Multithread-Code.
Beispiel für eine RAM-E / A-Bindung: Vektorsumme
Stellen Sie sich ein Programm vor, das alle Werte eines einzelnen Vektors summiert:
Die Parallelisierung durch gleichmäßige Aufteilung des Arrays für jeden Ihrer Kerne ist auf gängigen modernen Desktops von begrenztem Nutzen.
Auf meinem Ubuntu 19.04, Lenovo ThinkPad P51-Laptop mit CPU: Intel Core i7-7820HQ-CPU (4 Kerne / 8 Threads), RAM: 2x Samsung M471A2K43BB1-CRC (2x 16GiB) erhalte ich folgende Ergebnisse:
Plotdaten .
Beachten Sie jedoch, dass zwischen den Läufen große Unterschiede bestehen. Aber ich kann die Array-Größe nicht weiter erhöhen, da ich bereits bei 8 GB bin und heute nicht in der Stimmung für Statistiken über mehrere Läufe hinweg bin. Dies schien jedoch ein typischer Lauf zu sein, nachdem viele manuelle Läufe durchgeführt wurden.
Benchmark-Code:
pthread
In der Grafik verwendeter POSIX C- Quellcode .Und hier ist eine C ++ - Version , die analoge Ergebnisse liefert.
Handlungsskript
Ich kenne nicht genug Computerarchitektur, um die Form der Kurve vollständig zu erklären, aber eines ist klar: Die Berechnung wird nicht 8x schneller als naiv erwartet, da ich alle meine 8 Threads verwende! Aus irgendeinem Grund waren 2 und 3 Threads das Optimum, und das Hinzufügen von mehr macht die Dinge nur viel langsamer.
Vergleichen Sie dies mit CPU-gebundener Arbeit, die tatsächlich achtmal schneller wird: Was bedeuten "real", "user" und "sys" in der Ausgabe von Zeit (1)?
Der Grund dafür ist, dass alle Prozessoren einen einzigen Speicherbus gemeinsam nutzen, der mit dem RAM verbunden ist:
So wird der Speicherbus schnell zum Engpass, nicht zur CPU.
Dies geschieht, weil das Hinzufügen von zwei Zahlen einen einzelnen CPU-Zyklus erfordert und das Lesen von Speichern in der Hardware von 2016 etwa 100 CPU-Zyklen dauert .
Die CPU-Arbeit pro Byte der Eingabedaten ist also zu gering, und wir nennen dies einen E / A-gebundenen Prozess.
Die einzige Möglichkeit, diese Berechnung weiter zu beschleunigen, besteht darin, einzelne Speicherzugriffe mit neuer Speicherhardware, z. B. Mehrkanalspeicher , zu beschleunigen .
Ein Upgrade auf einen schnelleren CPU-Takt wäre beispielsweise nicht sehr nützlich.
Andere Beispiele
Die Matrixmultiplikation ist auf RAM und GPUs CPU-gebunden. Die Eingabe enthält:
Zahlen, aber:
Multiplikationen werden durchgeführt, und das reicht aus, damit sich die Parallelisierung für das praktische große N lohnt.
Aus diesem Grund gibt es parallele CPU-Matrix-Multiplikationsbibliotheken wie die folgenden:
Die Cache-Nutzung hat einen großen Einfluss auf die Geschwindigkeit der Implementierung. Siehe zum Beispiel dieses didaktische GPU-Vergleichsbeispiel .
Siehe auch:
Networking ist das prototypische IO-gebundene Beispiel.
Selbst wenn wir ein einzelnes Datenbyte senden, dauert es immer noch lange, bis das Ziel erreicht ist.
Das Parallelisieren kleiner Netzwerkanforderungen wie HTTP-Anforderungen kann enorme Leistungssteigerungen bieten.
Wenn das Netzwerk bereits voll ausgelastet ist (z. B. Herunterladen eines Torrents), kann die Parallelisierung die Latenz noch verbessern (z. B. können Sie eine Webseite "gleichzeitig" laden).
Eine Dummy-C ++ - CPU-gebundene Operation, die eine Zahl akzeptiert und häufig knirscht:
Die Sortierung scheint CPU basierend auf dem folgenden Experiment zu sein: Sind parallele C ++ 17-Algorithmen bereits implementiert? Dies zeigte eine 4-fache Leistungsverbesserung für die parallele Sortierung, aber ich hätte auch gerne eine theoretischere Bestätigung
So finden Sie heraus, ob Sie CPU- oder E / A-gebunden sind
Nicht-RAM-E / A gebunden wie Festplatte, Netzwerk :
ps aux
, dann prüfen, obCPU% / 100 < n threads
. Wenn ja, sind Sie an die E / A gebunden, z. B.read
warten Blockierungen nur auf Daten, und der Scheduler überspringt diesen Prozess. Verwenden Sie dann weitere Toolssudo iotop
, um zu entscheiden, welches E / A genau das Problem ist.Wenn die Ausführung schnell ist und Sie die Anzahl der Threads parametrisieren, können Sie leicht erkennen,
time
dass sich die Leistung verbessert, wenn die Anzahl der Threads für CPU-gebundene Arbeit zunimmt: Was bedeuten "real", "user" und "sys"? die Ausgabe der Zeit (1)?RAM-IO-gebunden: schwerer zu sagen, da die RAM-Wartezeit in den
CPU%
Messungen enthalten ist, siehe auch:Einige Optionen:
GPUs
GPUs haben einen E / A-Engpass, wenn Sie die Eingabedaten zum ersten Mal vom regulären CPU-lesbaren RAM auf die GPU übertragen.
Daher können GPUs nur für CPU-gebundene Anwendungen besser sein als CPUs.
Sobald die Daten jedoch an die GPU übertragen wurden, können diese Bytes schneller verarbeitet werden als die CPU, da die GPU:
hat mehr Datenlokalisierung als die meisten CPU-Systeme, sodass auf Daten für einige Kerne schneller zugegriffen werden kann als für andere
Nutzt die Datenparallelität und opfert die Latenz, indem nur Daten übersprungen werden, die nicht sofort bearbeitet werden können.
Da die GPU mit großen parallelen Eingangsdaten arbeiten muss, ist es besser, einfach zu den nächsten verfügbaren Daten zu springen, anstatt darauf zu warten, dass die aktuellen Daten verfügbar sind, und alle anderen Vorgänge zu blockieren, wie dies die CPU meistens tut
Daher kann die GPU schneller sein als eine CPU, wenn Ihre Anwendung:
Diese Entwurfsauswahl zielte ursprünglich auf die Anwendung von 3D-Rendering ab. Die Hauptschritte sind wie folgt unter Was sind Shader in OpenGL und wofür benötigen wir sie?
und so schließen wir, dass diese Anwendungen CPU-gebunden sind.
Mit dem Aufkommen der programmierbaren GPGPU können wir mehrere GPGPU-Anwendungen beobachten, die als Beispiele für CPU-gebundene Operationen dienen:
Bildverarbeitung mit GLSL-Shadern?
Lokale Bildverarbeitungsvorgänge wie ein Unschärfefilter sind von Natur aus sehr parallel.
Ist es möglich, eine Heatmap aus Punktdaten mit 60 Mal pro Sekunde zu erstellen?
Zeichnen von Heatmap-Diagrammen, wenn die geplottete Funktion komplex genug ist.
https://www.youtube.com/watch?v=fE0P6H8eK4I "Echtzeit-Fluiddynamik: CPU gegen GPU" von Jesús Martín Berlanga
Lösen partieller Differentialgleichungen wie der Navier-Stokes-Gleichung der Fluiddynamik:
Siehe auch:
CPython Global Intepreter Lock (GIL)
Als kurze Fallstudie möchte ich auf die Python Global Interpreter Lock (GIL) hinweisen: Was ist die globale Interpreter Lock (GIL) in CPython?
Dieses CPython-Implementierungsdetail verhindert, dass mehrere Python-Threads CPU-gebundene Arbeit effizient nutzen. In den CPython-Dokumenten heißt es:
Daher haben wir hier ein Beispiel, in dem CPU-gebundener Inhalt nicht geeignet ist und E / A-gebunden ist.
quelle
CPU-gebunden bedeutet, dass das Programm von der CPU oder der Zentraleinheit einen Engpass aufweist, während E / A- gebunden bedeutet, dass das Programm durch E / A oder Eingabe / Ausgabe, wie z. B. Lesen oder Schreiben auf Festplatte, Netzwerk usw., einen Engpass aufweist.
Im Allgemeinen wird bei der Optimierung von Computerprogrammen versucht, den Engpass zu ermitteln und zu beseitigen. Zu wissen, dass Ihr Programm CPU-gebunden ist, hilft, damit Sie nicht unnötig etwas anderes optimieren.
[Und mit "Engpass" meine ich die Sache, die Ihr Programm langsamer macht, als es sonst hätte.]
quelle
Eine andere Möglichkeit, dieselbe Idee zu formulieren:
Wenn das Beschleunigen der CPU Ihr Programm nicht beschleunigt, ist es möglicherweise an die E / A gebunden.
Wenn das Beschleunigen der E / A (z. B. die Verwendung einer schnelleren Festplatte) nicht hilft, ist Ihr Programm möglicherweise an die CPU gebunden.
(Ich habe "kann sein" verwendet, weil Sie andere Ressourcen berücksichtigen müssen. Speicher ist ein Beispiel.)
quelle
Wenn Ihr Programm auf E / A wartet (z. B. Lesen / Schreiben auf der Festplatte oder Lesen / Schreiben im Netzwerk usw.), kann die CPU auch dann andere Aufgaben ausführen, wenn Ihr Programm gestoppt ist. Die Geschwindigkeit Ihres Programms hängt hauptsächlich davon ab, wie schnell E / A-Vorgänge ausgeführt werden können. Wenn Sie die E / A beschleunigen möchten, müssen Sie die E / A beschleunigen.
Wenn Ihr Programm viele Programmanweisungen ausführt und nicht auf E / A wartet, wird es als CPU-gebunden bezeichnet. Wenn Sie die CPU beschleunigen, wird das Programm schneller ausgeführt.
In beiden Fällen besteht der Schlüssel zur Beschleunigung des Programms möglicherweise nicht darin, die Hardware zu beschleunigen, sondern das Programm zu optimieren, um die Menge an E / A oder CPU zu reduzieren, die es benötigt, oder es E / A ausführen zu lassen, während es gleichzeitig CPU-intensiv ist Zeug.
quelle
Die E / A-Bindung bezieht sich auf einen Zustand, in dem die Zeit, die zum Abschließen einer Berechnung benötigt wird, hauptsächlich durch die Wartezeit auf den Abschluss von Eingabe- / Ausgabeoperationen bestimmt wird.
Dies ist das Gegenteil einer CPU-gebundenen Aufgabe. Dieser Umstand tritt auf, wenn die Rate, mit der Daten angefordert werden, langsamer ist als die Rate, mit der sie verbraucht werden, oder mit anderen Worten, mehr Zeit für das Anfordern von Daten aufgewendet wird als für die Verarbeitung.
quelle
E / A-gebundene Prozesse: Verbringen Sie mehr Zeit mit E / A als mit Berechnungen, haben Sie viele kurze CPU-Bursts. CPU-gebundene Prozesse: Verbringen Sie mehr Zeit mit Berechnungen, wenige sehr lange CPU-Bursts
quelle
Sehen Sie, was Microsoft sagt.
E / A-gebundenes Beispiel: Herunterladen von Daten von einem Webdienst
CPU-gebundenes Beispiel: Durchführen einer Berechnung für ein Spiel
quelle
Eine Anwendung ist CPU-gebunden, wenn die Leistung von Arithmetik / Logik / Gleitkomma (A / L / FP) während der Ausführung meist nahe an der theoretischen Spitzenleistung des Prozessors liegt (Daten vom Hersteller bereitgestellt und durch die Eigenschaften des Prozessors bestimmt) Prozessor: Anzahl der Kerne, Frequenz, Register, ALUs, FPUs usw.).
Die Peek-Leistung ist in realen Anwendungen sehr schwer zu erreichen, da dies nicht unmöglich ist. Die meisten Anwendungen greifen in verschiedenen Teilen der Ausführung auf den Speicher zu, und der Prozessor führt während mehrerer Zyklen keine A / L / FP-Operationen aus. Dies wird aufgrund der Entfernung zwischen Speicher und Prozessor als Von-Neumann-Einschränkung bezeichnet .
Wenn Sie sich der CPU-Spitzenleistung nähern möchten, besteht eine Strategie darin, zu versuchen, die meisten Daten im Cache-Speicher wiederzuverwenden, um zu vermeiden, dass Daten aus dem Hauptspeicher benötigt werden. Ein Algorithmus, der diese Funktion ausnutzt, ist die Matrix-Matrix-Multiplikation (wenn beide Matrizen im Cache-Speicher gespeichert werden können). Dies geschieht, weil Sie, wenn die Matrizen eine Größe
n x n
haben,2 n^3
Operationen ausführen müssen, bei denen nur2 n^2
FP-Datenzahlen verwendet werden. Andererseits ist die Matrixaddition beispielsweise eine weniger CPU-gebundene oder mehr speichergebundene Anwendung als die Matrixmultiplikation, da nurn^2
FLOPs mit denselben Daten erforderlich sind .In der folgenden Abbildung sind die FLOPs dargestellt, die mit einem naiven Algorithmus für die Matrixaddition und die Matrixmultiplikation in einem Intel i5-9300H erhalten wurden:
Beachten Sie, dass die Leistung der Matrixmultiplikation erwartungsgemäß größer ist als die Matrixaddition. Diese Ergebnisse können durch Ausführen reproduziert werden
test/gemm
undtest/matadd
sind in diesem Repository verfügbar .Ich schlage auch vor, das Video von J. Dongarra über diesen Effekt zu sehen.
quelle
E / A-gebundener Prozess: - Wenn der größte Teil der Lebensdauer eines Prozesses im E / A-Status verbracht wird, ist der Prozess ai / o-gebundener Prozess. Beispiel: -Calculator, Internet Explorer
CPU-gebundener Prozess: - Wenn der größte Teil der Prozesslebensdauer in CPU verbracht wird, handelt es sich um einen CPU-gebundenen Prozess.
quelle