Die Last definieren, bevor Sie den Zähler wählen
„Ein 7B-Modell“ präzisiert weder die Darstellung der Gewichte noch die auszuführende Arbeit. Erfassen Sie seine Revision, das Framework, die Versionen der Erweiterungen, das tatsächlich geladene Format und den Vorgang: Training, Anpassung oder Generierung. Notieren Sie für Text die Eingabe- und Ausgabelängen; für Vision die Auflösung und die Anzahl der Bilder. Ein multimodales Modell erfordert, beide Dimensionen zu berücksichtigen.
Bereiten Sie eine gewöhnliche Eingabe, eine lange, aber erwartete und eine nahe Ihrer funktionalen Grenze vor. Behalten Sie sie während der Vergleiche bei. Überprüfen Sie die Formen nach Tokenisierung, Padding, Gruppierung oder Größenänderung: Der in der Konfiguration eingetragene Wert beweist nicht die tatsächlich verarbeitete Form.
Legen Sie außerdem fest, was gleichzeitig im Speicher bleibt: eine Sequenz, ein Mikrobatch, mehrere Anfragen oder eine nach dem Training gestartete Evaluierung. Ihre Frage wird überprüfbar: Hält diese vollständige Last auf jedem verwendeten Gerät stand, auch während ihres anspruchsvollsten Schritts?
- Identität des Versuchs: Modell oder Code, Revision, Eingabesatz und Seed, sofern relevant.
- Dimensionen: Batch, Kontext, generierte Tokens, Auflösung oder Anzahl gleichzeitiger Anfragen.
- Umgebung: ausgewählte GPU, Treiber, Python, PyTorch, CUDA- oder HIP/ROCm-Backend und Allocator-Einstellungen.
- Umfang: Laden, Berechnung, Transfer, Auswertung, Export; erster Durchlauf oder Durchlauf nach dem Aufwärmen.
Gewichte berechnen, ohne GB und GiB zu vermischen
Ein GB entspricht 1 000 000 000 Bytes; ein GiB entspricht 1 073 741 824 Bytes. Die hier verwendeten PyTorch-Zähler liefern Bytes zurück. Behalten Sie diesen Rohwert in der Ergebnisdatei bei und wenden Sie dann eine einzige Umrechnung an, um die Zeilen zu vergleichen. Die kommerzielle Bezeichnung einer Karte ersetzt nicht die tatsächlich vom Gerät gemeldete Kapazität.
Für ein dichtes Modell mit sieben Milliarden Parametern, die jeweils auf zwei Bytes gespeichert sind, betragen die Gewichte 14 000 000 000 Bytes: 14 GB oder etwa 13,04 GiB. Diese Rechnung umfasst weder Aktivierungen noch Gradienten, KV-Cache oder Optimierer-Zustände. Fügt man eine Reserve von 4 GiB hinzu, erhält man etwa 17,04 GiB als Vorbereitungsannahme; das beweist nicht, dass eine Last in dieses Budget passt.
Die theoretische Division bei vier Bits setzt eine gleichmäßige, kompakte Speicherung voraus. Ein echtes quantisiertes Laden kann Skalen und weitere Informationen hinzufügen und einige Module in einer anderen Genauigkeit belassen. Das Speicherformat der Gewichte und das Berechnungsformat sollten daher getrennt in Ihrem Datenblatt erscheinen.
| Speicherannahme | Berechnete Bytes | Ungefähre GiB |
|---|---|---|
| 32 Bit einheitlich | 28 000 000 000 | 26,08 |
| 16 Bit einheitlich | 14 000 000 000 | 13,04 |
| 4 Bit kompakt, ohne Metadaten | 3 500 000 000 | 3,26 |
Technische Quellen: NIST — binäre Präfixe und Vergleich GB/GiB · Hugging Face — quantisierte Formate und Module mit bitsandbytes
Beim Training einen vollständigen Schritt messen
Die Gewichte existieren neben anderen Objekten: Gradienten, Optimierer-Zustände, für den Rückwärtsdurchlauf benötigte Aktivierungen und temporäre Tensoren. Ihre Größen hängen von der Schleife, der Genauigkeit und den Dimensionen der Last ab. Eine universelle Konstante in Bytes pro Parameter würde insbesondere den Effekt des Microbatch und der Eingaben verschleiern.
Instrumentieren Sie den Vorwärtsdurchlauf, die Verlustberechnung, die Rückpropagierung und die Aktualisierung. Um die tatsächlich von Ihrem Optimierer erzeugten Zustände zu beobachten, sollten Sie nicht beim Laden des Modells stehen bleiben. Behalten Sie außerdem eine Messung des ersten vollständigen Schritts bei: Ein erfolgreiches Aufwärmen kann bereits eine Initialisierung durchgeführt haben, die Sie beim Start im Speicher finanzieren können müssen.
Fügen Sie eine Auswertung und den Export hinzu, den Ihr Projekt benötigt. Wenn der Fehler während der Auswertung auftritt, behebt eine bloße Verkleinerung des Trainings-Batch diese Phase nicht. Eine Anpassung, die nur wenige Parameter trainiert, kann dennoch ein Basismodell und umfangreiche Aktivierungen beibehalten.
Technische Quellen: Hugging Face — Speicherkategorien während des Trainings
Bei der Inferenz Kontext und Nebenläufigkeit verfolgen
In einer autoregressiven Generierung mit Attention behält der KV-Cache Zustände, die mit den Tokens verknüpft sind. Bei einem dichten, gleichmäßigen Cache hängt seine Größe von den Schichten, den KV-Köpfen, deren Dimension, den beibehaltenen Tokens und den gleichzeitig vorhandenen Sequenzen ab. Verwenden Sie die KV-Köpfe des Modells, nicht automatisch seine Query-Köpfe.
Rechenbeispiel: 32 Schichten, 8 KV-Köpfe, eine Dimension von 128, 8 192 Tokens, zwei Bytes pro Wert und eine Sequenz ergeben 1 073 741 824 Bytes, also 1 GiB für K und V zusammen. Vier identische Sequenzen ergeben 4 GiB allein für diesen Posten. Diese Rechnung misst weder Durchsatz noch vollständige GPU-Auslastung.
Passen Sie die Formel an den tatsächlich verwendeten Cache an. Ein gleitendes Fenster behält nicht unbedingt den gesamten Verlauf; ein statischer Cache kann seine maximale Kapazität vorab reservieren. Quantisierte und ausgelagerte Caches verändern das Problem ebenfalls. Messen Sie die anfängliche Verarbeitung der Eingabe und die Generierung getrennt, ohne deren gesamte Differenz automatisch dem Cache zuzuschreiben.
Technische Quellen: Hugging Face — Cache-Strategien, statische Zuweisung und Fenster
Allocated und reserved: zwei Messwerte, die sich nicht addieren lassen
memory_allocated beschreibt die von PyTorch verfolgten, auf dem Gerät belegten Bytes durch Tensoren. memory_reserved beschreibt den von seinem Allocator mit Cache verwalteten Speicher, einschließlich des bereits für diese Tensoren genutzten. Beide zu addieren zählt einen Teil des Speichers doppelt. Behalten Sie sie in zwei getrennten Spalten bei.
Ihre Max-Varianten verzeichnen jeweils einen Höchstwert seit Beginn der Aufzeichnung oder deren letztem Zurücksetzen. Es handelt sich um absolute Höchstwerte des Zeitraums, die bereits zu Beginn vorhandene Allokationen einschließen. Das Ergebnis repräsentiert nicht automatisch nur die von der Phase erzeugten Objekte.
Eine Systemmessung kann einen größeren Umfang haben. Allokationen, die direkt von einer CUDA-Bibliothek vorgenommen werden, etwa bestimmte NCCL-Kommunikationen, sind nicht alle im PyTorch-Allocator sichtbar. Eine Abweichung zu einem Systemwerkzeug belegt daher für sich allein keine Speicherleckage.
| Zähler | Frage, die er beantwortet | Zu vermeidender Fehler |
|---|---|---|
| memory_allocated | Wie viel belegen die Tensoren zu diesem Lesezeitpunkt? | Ihn für die gesamte Belegung der Karte halten. |
| memory_reserved | Wie viel verwaltet der Allocator zu diesem Lesezeitpunkt? | Ihn zu allocated addieren. |
| max_memory_allocated | Welcher Höchstwert der Tensoren wurde während des Zeitraums aufgezeichnet? | Ihn mit dem Wert am Ende der Phase verwechseln. |
| max_memory_reserved | Welchen Höchstwert der Reservierung meldet der Allocator? | Annehmen, dass er zum selben Zeitpunkt wie der andere Höchstwert auftritt. |
Technische Quellen: PyTorch — memory_allocated · PyTorch — memory_reserved · PyTorch — max_memory_allocated · PyTorch — Allokationen außerhalb seines Allocators
Warum die Differenz zwischen den beiden Höchstwerten nicht den Cache misst
Betrachten wir ausschließlich die beiden fiktiven Zeitpunkte aus der Tabelle. Der Spitzenwert von allocated beträgt 8 GiB und der Spitzenwert von reserved 12 GiB. Ihre Differenz, 4 GiB, ist nicht die zu einem dieser beiden Zeitpunkte beobachtete Differenz: Diese beträgt jeweils 2 und 6 GiB. Zwei Maxima beschreiben nicht zwangsläufig denselben Zustand.
Um ihren Abstand zu einem bestimmten Zeitpunkt zu untersuchen, erfassen Sie allocated und reserved am selben Kontrollpunkt, nach der Synchronisierung und ohne eine neue absichtliche Operation zwischen den Messungen. Sie erhalten eine Zählerdifferenz zu diesem Zeitpunkt, weder eine Messung des KV-Caches des Modells noch eine Garantie, dass diese gesamte Differenz die nächste Allokation erfüllen kann.
Behalten Sie außerdem das Backend des Allocators im Bericht. Die PyTorch-Dokumentation 2.14 führt aus, dass max_memory_reserved bei cudaMallocAsync die höchsten Stände zweier Pools kombinieren und damit eine obere Schranke für den gleichzeitigen Höchstwert liefern kann. Das verstärkt die Notwendigkeit, Name und Umfang des Zählers beizubehalten.
| Illustrativer Zeitpunkt | Allocated | Reserved | Reserved − allocated zu diesem Zeitpunkt |
|---|---|---|---|
| A | 8 GiB | 10 GiB | 2 GiB |
| B | 6 GiB | 12 GiB | 6 GiB |
Technische Quellen: PyTorch — Definition und Grenze von max_memory_reserved
Jede Phase abgrenzen, bevor ihr Höchstwert erfasst wird
GPU-Operationen können in die Warteschlange gestellt werden, bevor sie abgeschlossen sind. Für eine Messung pro Phase schließen Sie die vorherigen Arbeiten ab, bevor Sie die Höchstwerte zurücksetzen, und warten Sie dann das Ende der Phase vor der Messung ab. torch.cuda.synchronize wartet auf die Kernel aller Streams des ausgewählten Geräts; diese Wahl legt eine explizite Grenze für dieses Protokoll fest.
reset_peak_memory_stats setzt die Aufzeichnung der Höchstwerte ab dem aktuellen Zustand zurück; es gibt die Tensoren des Programms nicht frei. Erfassen Sie zuerst die Ausgangsstände. Behalten Sie am Ende die beiden absoluten Höchstwerte und die beiden aktuellen Stände. Stellen Sie die Subtraktion eines Ausgangsstands nicht als das exakte Volumen aller temporären Tensoren dar: Auch frühere Objekte können während der Phase freigegeben worden sein.
Diese Instrumentierung kann die übliche Überlappung der Phasen verändern. Nutzen Sie sie, um das Problem zu lokalisieren, und überprüfen Sie anschließend auch die vollständige Schleife mit ihrer tatsächlichen Ablaufplanung. Wiederholen Sie die Messungen bei mehreren Karten für jedes Gerät; eine Messung auf cuda:0 beschreibt die anderen GPUs nicht.
- 1. Der Phase einen Namen geben und ihre genauen Eingaben notieren.
- 2. Das Gerät synchronisieren und dann die Ausgangswerte von allocated und reserved erfassen.
- 3. reset_peak_memory_stats auf demselben Gerät aufrufen.
- 4. Die definierte Phase ausführen und dabei die für den weiteren Verlauf benötigten Ausgaben beibehalten.
- 5. Synchronisieren, die Höchstwerte und die Endstände erfassen und dann Erfolg oder Fehler festhalten.
- 6. Das Rohergebnis, die Dimensionen und die Konfiguration beibehalten; keine fehlende Messung durch null ersetzen.
Technische Quellen: PyTorch — Synchronisierung eines Geräts · PyTorch — Zurücksetzen der Höchstwertstatistiken
Ersten Durchlauf und Durchläufe nach dem Aufwärmen unterscheiden
Der erste Versuch und eine bereits vorbereitete Schleife beantworten nicht dieselbe Frage. Halten Sie das Laden und den ersten Durchlauf fest, und dokumentieren Sie anschließend die Anzahl der Aufwärm-Iterationen vor den Wiederholungen. Löschen Sie einen Initialisierungsfehler nicht mit der Begründung, die folgenden Durchläufe seien leichter gewesen.
Das Skript von IteraGPU unterscheidet model_load, inputs, cold_forward, warmup und warm_forward. Sein cold_forward ist der erste Durchlauf des kleinen Modells nach der Initialisierung des Geräts. Er misst nicht den gesamten Start eines Servers, eines Treibers oder eines Dienstes. Die warm_forward-Wiederholungen bleiben im selben Prozess und profitieren von dessen bestehendem Zustand.
Starten Sie für Ihr Modell dann eine neue Serie in einem neuen Prozess, wenn Sie eine Bedingung ändern, die vorherige Objekte oder Reservierungen hinterlassen könnte. Notieren Sie die Reihenfolge der Versuche und die Aufwärmstrategie. Eine Schleife fünfmal neu zu starten und fünf Prozesse zu starten sind nicht dasselbe Protokoll.
Notebook und Skript von IteraGPU Lab v1 verwenden
Beginnen Sie mit der README, und laden Sie anschließend das eigenständige Notebook oder das Python-Skript herunter. Die estimate-Berechnung verwendet die Standardbibliothek. Die Messung erfordert ein installiertes PyTorch mit einem kompatiblen GPU-Backend und einem zugänglichen Gerät; sie lädt weder Modell noch Paket herunter. Das Notebook benötigt eine Umgebung, die ipynb-Dateien lesen kann.
Die Messübung verwendet ein kleines dichtes Netz eigener Bauart und synthetische Eingaben. Die Optionen batch, context und width beschreiben dessen Tensoren; context ist hier nicht die Länge eines echten LLM mit KV-Cache. Dieses Hilfsmittel dient dazu, die Messmethode zu untersuchen und eine Dimension zu variieren. Es belegt nicht die Leistungsfähigkeit einer Karte für Ihr Forschungsmodell.
Führen Sie die untenstehenden Befehle aus dem Ordner aus, der das Skript enthält. Sehen Sie sich zuerst den environment-Bericht an. Fehlt PyTorch oder die GPU, muss measure ausdrücklich mit dem Code 2 abbrechen; kein CPU-Ergebnis darf als GPU-Messung interpretiert werden. Die Ausgabe-JSON einer erfolgreichen Messung wird in Ihrer Umgebung erzeugt. Wählen Sie für jede Serie einen neuen Dateinamen: Das Skript weigert sich, ein vorhandenes Ergebnis zu überschreiben.
Der erste Befehl berechnet die Gewichte und die hypothetische Reserve von 4 GB erneut. Verwenden Sie für die folgenden Befehle ein Gerät, das Sie belasten dürfen, und halten Sie die Dimensionen zunächst bescheiden. Notieren Sie die tatsächlich verwendete PyTorch-Version: Die technischen Referenzen dieser Seite beschreiben unter anderem Version 2.14, ohne vorzuschreiben, dass sie bei Ihnen installiert sein muss.
Die Funktionsweise des Skripts wurde an einem kleinen Fall geprüft: lokale RTX 5070 außerhalb des Katalogs, Treiber 610.62, Python 3.14.6 und PyTorch 2.11.0+cu128. Der Versuch verwendete batch 1, Kontext 16, Breite 64, float32, ein Aufwärmen und zwei Wiederholungen. Er validiert diesen Ausführungspfad, ohne ein LLM, ein Training oder die zur Miete angebotenen GPUs zu qualifizieren. Das Notebook wird ohne Ausgaben und die Vergleichstabelle ohne Ergebnisse geliefert; die Absicherung gegen fehlendes PyTorch wurde zudem in einer separaten Umgebung geprüft.
python mesure_memoire.py estimate --parameters 7000000000 --bits 16 --reserve-gib 4
python mesure_memoire.py environment --device cuda:0
python mesure_memoire.py measure --device cuda:0 --batch 2 --context 128 --width 1024 --dtype float32 --warmup 3 --repeats 5 --output mesures.json- Notebook für Berechnung und Messung
Eigenständiges Notebook zum Öffnen, Prüfen und Ausführen in Ihrer Umgebung.
- Skript mesure_memoire.py
Berechnung ohne externe Abhängigkeit, Umgebungsprüfung und ausdrückliche GPU-Messung.
- Anleitung zum Ordner
Voraussetzungen, Befehle, Umfang der Phasen und Grenzen der Interpretation.
- Archiv IteraGPU Lab v1
Die versionierten Ressourcen an einem Ort, mit Anleitung und Lizenz.
- Lizenz der Ressourcen
Bedingungen für die Wiederverwendung der bereitgestellten Dateien.
Einen Fehler interpretieren, bevor Sie die Karte wechseln
Ein unvollständiger Versuch bleibt eine nützliche Beobachtung. Halten Sie die Phase, die angeforderten Dimensionen, die Fehlermeldung und die letzten verfügbaren Werte fest. Ein teilweiser Spitzenwert vor einer Sättigung entspricht nicht dem Speicherbedarf eines vollständigen Durchlaufs. Reduzieren Sie nur eine Dimension, um einen Fall zu konstruieren, der erfolgreich ist, und suchen Sie dann die Grenze zwischen Erfolg und Misserfolg.
empty_cache gibt ungenutzte Blöcke aus dem Cache des Allocators frei, ohne noch lebende Tensoren freizugeben. Das ist keine universelle Lösung für eine zu große Last. Der Aufruf zwischen jeder Wiederholung verändert die Bedingungen: Dokumentieren Sie diese Wahl, statt diese Versuche mit denen zu vermischen, die den Cache beibehalten.
Wenn einfache Zähler die Situation nicht erklären, kann ein Speicher-Trace helfen, die Allokationen im Zeitverlauf zu identifizieren. Sein Umfang bleibt auf die von PyTorch sichtbaren Allokationen beschränkt. Eine niedrige allocated-Spitze schließt daher eine externe Allokation oder einen anderen Nutzer der Karte nicht aus.
| Beobachtung | Nützliche Überprüfung | Nächster Versuch |
|---|---|---|
| Fehler beim Laden | Geladenes Format, Platzierung der Gewichte und bereits belegter Speicher. | Das Laden allein in einem neuen Prozess reproduzieren. |
| Laden erfolgreich, Rückwärtsdurchlauf unmöglich | Microbatch, Eingaben, beibehaltene Aktivierungen und Zustand der Schleife. | Eine Dimension verkleinern und dann den vollständigen Schritt wiederholen. |
| Nur die Evaluierung schlägt fehl | Evaluierungs-Batch, beibehaltene Ausgaben und Berechnungskontext. | Die Evaluierung mit ihren eigenen Grenzen messen. |
| Allocated steigt von einer Wiederholung zur nächsten | Behaltene Referenzen in Listen, Anwendungs-Caches oder Graphen. | Deren Lebensdauer prüfen, bevor Sie den Allocator beschuldigen. |
| Reserved bleibt nach der Berechnung hoch | Noch lebende Tensoren und Cache-Richtlinie. | Die aktuellen Werte vergleichen, ohne die Zähler zu addieren. |
| Ein Systemwerkzeug zeigt mehr an | Umfang des Werkzeugs, GPU-Kontext, andere Prozesse und Bibliotheken. | Die Last isolieren und zeitgleich abgelesene Werte einander annähern. |
Technische Quellen: PyTorch — was empty_cache freigibt · PyTorch — Traces und Grenzen der Speichersichtbarkeit
Eine Marge aus vergleichbaren Lasten aufbauen
Vermeiden Sie einen Margenprozentsatz, der als universell dargestellt wird. Die Marge muss identifizierte Schwankungen abdecken: längere Eingabe, zulässiger Batch, Evaluierung, Export, Bibliotheksversion oder andere Belegung der Karte. Testen Sie die erwarteten Grenzfälle und halten Sie dann fest, was außerhalb des Umfangs bleibt. Eine erfolgreiche Ausführung mit einer einzigen kleinen Eingabe validiert nicht die maximale Last.
Ändern Sie jeweils nur eine Variable: Batch 1, dann 2 bei konstantem Kontext oder Kontexte 2 048, dann 4 096 bei konstantem Batch. Behalten Sie denselben Inhalt und dieselben Aufbereitungsregeln bei. Eine Kürzung, die eine notwendige Information entfernt, verändert die Aufgabe, auch wenn sie die Spitze senkt.
Wenn die Gewichte dominieren, prüfen Sie ein anderes Format bei kontrollierter Qualität. Wenn die Aktivierungen dominieren, können Microbatch oder Aktivierungs-Checkpointing Ansätze sein. Letzteres tauscht Speicher gegen Neuberechnung: Messen Sie auch die Dauer und überprüfen Sie die Ergebnisse. Wenn der KV-Cache dominiert, untersuchen Sie Kontext, Nebenläufigkeit und Cache-Strategie. Der Vergleichsordner ergänzt dieses Vorgehen mit einer gemeinsamen Qualitätsregel.
Technische Quellen: PyTorch — Aktivierungs-Checkpointing und Neuberechnung
Vom Trace zu einer Konfigurationsentscheidung gelangen
Ihr erwartetes Ergebnis ist ein kurzes Datenblatt: Schätzung der Gewichte, getestete maximale Last, erfolgreiche oder fehlgeschlagene Phasen, vier Zähler mit Einheiten, Umgebung und getroffene Wahl. Fügen Sie diesem Datenblatt das Rohresultat bei. Trennen Sie, was Sie berechnet, was Sie beobachtet und was Sie noch vermutet haben.
Vergleichen Sie anschließend den Bedarf mit der Kapazität jeder Karte und behalten Sie die Software-Einschränkungen bei. Mehrere GPUs erfordern eine Aufteilung von Arbeit und Daten; ihr Vorhandensein schafft nicht automatisch einen einzigen Speicherpool für die Anwendung. Ein Fehler auf einer Karte kann trotz freien Speichers auf einer anderen bestehen bleiben.
Das PyTorch-Protokoll verwendet die Schnittstelle torch.cuda; ein HIP/ROCm-Build von PyTorch nutzt diesen Namen weiter. Identifizieren Sie das tatsächlich installierte Backend, bevor Sie zwei Hardware-Familien vergleichen. Die Verwendung derselben Python-Funktion beweist nicht, dass die Kerne, Genauigkeiten oder Ergebnisse gleichwertig sind.
Der Dimensionierer ermöglicht es, die ursprüngliche Annahme aufzugreifen; die GPU-Datenblätter ermöglichen den Vergleich der Kapazitäten. Kehren Sie dann zum selben Arbeitsfall zurück, um die Wahl zu überprüfen. Das kleine Netzwerk aus dem Download bleibt eine Instrumentierungsübung: Nur die Ausführung Ihrer Last in ihrer dokumentierten Umgebung kann Ihre eigene Marge validieren.
Technische Quellen: NVIDIA — Aufteilung der Arbeit auf mehrere GPUs · PyTorch — Schnittstelle torch.cuda in HIP/ROCm-Builds