Herausforderungen und Fallstricke bei der Entwicklung für Multi-Core-Systeme

Fazit

Um moderne Mehrkernsysteme (Multi-Core-Prozessoren, Grafikkarten oder HPC-Cluster) effizient auszulasten, sind Techniken der parallelen Programmierung notwendig. Dadurch lassen sich erhebliche Performanceverbesserungen hinsichtlich der Laufzeit komplexer Anwendungen erzielen. Das Beispiel auf Basis von Java-Threads zeigt die grundlegenden Herausforderungen paralleler Applikationsentwicklung und lässt sich auf andere Sprachen wie C++ und C# sowie Techniken der Parallelverarbeitung auf Grafikkarten übertragen. Die Grundfragestellungen bleiben immer dieselben:

  1. Die Problemstellung muss gut parallelisierbar sein und einen möglichst geringen sequenziellen (nichtparallelisierbaren) Anteil aufweisen. Gut geeignet sind numerische Simulationsverfahren, das Training neuronaler Netze sowie mathematische Verfahren wie Matrizen-, Tensor- und Vektorberechnungen.
  2. Um parallele Anwendungen zu entwickeln, sind Kenntnisse über das Speichermodell entscheidend, wie beispielsweise bezüglich der Atomarität von Datentypen oder Sichtbarkeit (sind Änderungen von Variablen über mehrere Threads hinweg sichtbar).
  3. Nichtsynchronisierte parallele Speicherzugriffe können zu fehlerhaften Ergebnissen und Programmabbrüchen führen. Aber jede Form der Synchronisation (atomare Variablen, synchronized etc.) ist teuer und reduziert die parallele Effizienz. Außerdem verschlechtert sich die Nachvollziehbarkeit des Programmcodes deutlich.
  4. Gemeinsam genutzte, veränderliche Daten sind auf ein Minimum zu reduzieren. Optimal sind separate Speicherzugriffe pro Thread oder ein Read-only-Zugriff auf Daten von mehreren Threads. (map)

Dr. Sebastian Bindick
ist IT-Architekt bei der Volkswagen Group IT. Seine Schwerpunkte liegen in den Bereichen moderne Architekturen, Web-Technologien, Testautomatisierung und Computational Engineering. Er ist Autor von Fachartikeln, hält Vorträge auf IT-Konferenzen und ist Gastdozent an verschiedenen Universitäten.