Files
GRA-Project/Projektbericht.md
T
2026-07-15 21:01:00 +02:00

6.8 KiB
Raw Blame History

Projektbericht – Tricorn-Fraktal

1. Ziel des Projekts

Ziel ist ein C-Programm, das einen Ausschnitt des Tricorn-Fraktals berechnet und als BMP-Datei speichert. Über Kommandozeilenargumente werden Startpunkt, Bildgröße, Auflösung, maximale Iterationszahl, Ausgabedatei, Farbmodus und Implementierungsvariante festgelegt. Neben der skalaren Vergleichsversion enthält das Projekt SIMD- und Thread-Varianten, deren Laufzeiten miteinander verglichen werden.

2. Implementierungen

V1 ist die skalare Vergleichsimplementierung. Real- und Imaginärteil werden direkt mit float-Operationen berechnet. Das Bild wird zeilenweise durchlaufen und die Koordinaten werden inkrementell erhöht.

V2 verarbeitet vier benachbarte Pixel gleichzeitig mit 128-Bit-SSE-Registern. Eine aktive Maske speichert, welche SIMD-Lanes die Fluchtschranke noch nicht überschritten haben. Sobald alle vier Lanes inaktiv sind, wird die Iterationsschleife beendet. Für null bis drei Restpixel am Zeilenende wird eine skalare Funktion verwendet.

V0, die Hauptimplementierung, verwendet ebenfalls SIMD. Gegenüber V2 werden Real- und Imaginärkoordinaten inkrementell als Vektoren fortgeführt.

V3 erweitert die optimierte SIMD-Berechnung um POSIX-Threads. Die verfügbaren logischen Prozessoren werden mit sysconf beziehungsweise GetSystemInfo bestimmt. Jeder Thread erhält einen zusammenhängenden Zeilenbereich und schreibt ausschließlich in diesen Teil des gemeinsamen Bildpuffers. Bei kleinen Bildern wird die Threadzahl reduziert, sodass ungefähr mindestens zehn Zeilen pro Thread verbleiben.

3. Tests und Performanzanalyse

Die Laufzeit wird mit clock_gettime(CLOCK_MONOTONIC) gemessen. Im Benchmark-Modus wird die gewählte Berechnung mehrfach ausgeführt; die BMP-Ausgabe liegt außerhalb der Messung. Der Mittelwert ist Gesamtzeit geteilt durch Wiederholungszahl. Der Speedup gegenüber einer Referenz (R) lautet


S=\frac{T_R}{T_\mathrm{optimiert}}

Die Testsuite enthält ein farbiges 1920×1080-Bild, ein 7680×4320-Bild mit niedriger Iterationszahl, einen vergrößerten Fraktalrand und einen nahezu schwarzen Bereich mit hoher Iterationszahl. Für einen fairen Versionsvergleich müssen in jedem Szenario identische Parameter verwendet werden

Wir haben versucht die Tests so zu wählen, dass unsere Implementierung in verschiedene Situationen zu testen, die zu verschiedene Ergebnissen führen.

Alle Tests werden auf die Rechnerhalle ausgeführt, um die volles Potenzial, die Optimierungen für High-End-Hardware zu prüfen.

Testumgebung:

  • Host-System: TUM lxhalle
  • OS: Ubuntu 24.04.2 LTS
  • CPU: AMD EPYC 9554P 64-Core Processor
    • Thread-Anzahl: 64 physische Kerne / 128 logische Threads
    • Taktfrequenz: Basis 2.3 GHz / Boost 3.1 GHz
    • L3 Cache: 256 MiB
    • L2 Cache: 64 MiB
  • RAM: 768 GB
  • Compiler: gcc 13.3.0 (mit -O3 flag)

(Diese Spezifikationen werden aus der Ausgabe von lscpu und lshw Befehle auf lxhalle, der CIT wiki und der Message of the Day)

Alle Benchmarking-Tests werden 100 mal ausgeführt um eine genaue Messung zu erhalten.

Test 1: Default 1920x1080 Bild

Durchnitliches Laufzeit Speedup gegenüber V1
V0 0.046 3.2528
V1 0.150 1.00
V2 0.047 3.21
V3 0.007 20.29

Test 2: 7680×4320-Bild mit niedriger Iterationszahl

Durchnitliches Laufzeit Speedup gegenüber V1
V0 0.047 1.81
V1 0.086 1.00
V2 0.049 1.74
V3 0.006 13.71

Test 3: Fraktalrand

Durchnitliches Laufzeit Speedup gegenüber V0
V0 0.591 2.54
V1 1.502 1.00
V2 0.419 3.59
V3 0.031 48.38

Test 4: Schwarzen Bereich mit hoher Iterationszahl

Durchnitliches Laufzeit Speedup gegenüber V0
V0 1.572 3.55
V1 5.589 1.00
V2 1.573 3.55
V3 0.022 250.64

4. Korrektheit und Fazit

Zur Korrektheitsprüfung wurden V0, V1, V2 und V3 mit identischen Parametern ausgeführt. Die erzeugten Graustufenbilder wurden mit ImageMagick und der Metrik AE pixelweise verglichen. Von insgesamt 523776 Pixeln unterschieden sich V0 und V1 an 5864 Pixeln (1,120 %), V2 und V1 an 5523 Pixeln (1,054 %) sowie V3 und V1 an 5993 Pixeln (1,144 %).

Die Implementierungen erzeugen somit keine vollständig identischen Ergebnisse. Ursache sind unterschiedlich angeordnete Gleitkommaoperationen bei der Berechnung der komplexen Koordinaten. Da res nicht immer exakt als float darstellbar ist, entstehen kleine Rundungsabweichungen, die insbesondere nahe der Fraktalgrenze eine andere Fluchtiteration verursachen können.

Zusätzlich wurden nicht durch vier teilbare Bildbreiten, positive und negative Höhen sowie Grau- und Farbausgabe getestet. Die verbleibenden Pixel am Zeilenende wurden durch den skalaren Restpfad verarbeitet. Bei umgekehrter Bildhöhe traten ebenfalls geringe Rundungsabweichungen auf.

Die Messungen zeigen, dass SIMD die skalare Berechnung deutlich beschleunigt. V3 erreicht gegenüber V1 einen Speedup zwischen 13,71 und 250,64. Der größte Vorteil tritt bei hohen Iterationszahlen auf, da der Aufwand für die Thread-Verwaltung gegenüber der eigentlichen Berechnung weniger ins Gewicht fällt. V0 und V2 besitzen dagegen in mehreren Tests nahezu identische Laufzeiten, sodass die Thread-Parallelisierung den größten zusätzlichen Performanzgewinn liefert.

Insgesamt zeigt das Projekt die schrittweise Optimierung von einer skalaren Implementierung über SIMD bis zur Kombination aus SIMD und Multithreading. Grenzen bleiben Rundungsabweichungen, unterschiedlich lange aktive SIMD-Lanes, der Aufwand der Thread-Verwaltung und die Geschwindigkeit von RAM-Zugriffe.

5. Individuelle Beiträge

Yashar Alan Zenker:

Nikola Granitsky:

  • Implementierung von SIMD- und Skalar-Optimierungen
  • Implementierung des BMP-Exports
  • Konzeption und Integration von Testfällen
  • Refactoring und Bugfixing

Cem Temizkan:

  • Implementierung des Rahmenprogramms
  • Implementierung der Kommandozeilenverarbeitung
  • Implementierung des Benchmarkings
  • Beschreibung der mathematischen Grundlagen.