Parallele Simulation mit OpenModelica
Ein ausführliche Einführung in die Task-Graph-basierte Parallelisierung, auf dem das HPCOM-Modul basiert, findet sich im Tutorial.
Um den vollen Funktionsumfang der parallelen Simulation zu nutzen, sollte die aktuelle Nightly-Builds Version von OpenModelica installiert sein, mindestens aber OpenModelica 1.9.3.
Die Parallelisierung mit hpcom wird über das Flag "hpcom" aktiviert. Zudem muss die Anzahl der zu verwendenden Threads über das Flag "+n=" angegeben werden. Diese Flags werden bei der Ausführung des omc übergeben:
> omc +d=hpcom +n=4 model.mos
Wird die parallele Simulation so ausgeführt, werden die Ausführungszeiten und Kommunikationszeiten, die für das Scheduling benötigt werden, geschätzt.
Die bessere Möglichkeit besteht darin, die Zeiten zu messen. Dazu wird die serielle Simulation mit dem Flag +profiling=all ausgeführt:
> omc model.mos +profiling=all;
Dabei wird ein model_prof.json erzeugt. Dieses json file enthält die Ausführungszeiten der einzelnen Tasks. Da die Ausführungszeiten jedoch in Takten benötigt werden, muss die generierte Modelsimulation mit dem Flag -clock=CYC ausgeführt werden. Wenn die C++ Codegenerierung (+simCodeTarget=Cpp) benutzt wird, ist dieser Schritt nicht mehr notwendig.
> model -clock=CYC
Das model_prof.json muss danach noch in model_eqs_prof.json umbenannt werden. Danach kann die parallele Simulation mit +d=hpcom und +n=N(N=2,3,4,...) unter Zuhilfenahme der gemessenen Ausführungszeiten erfolgen.
Weitere Einstellungen
Generierter Code
Es sind weitere nützliche Einstellungen verfügbar. Beispielsweise kann für die Codeerzeugung zwischen openmp, pthreads mit mutex oder spinlock gewählt werden. Unter Windows ist Pthreads mit spinlock meistens die beste Option. Unter Linux ist die Codegenerierung mit openmp sehr performant. Die Auswahl erfolgt über das flag hpcomCode.
> +hpcomCode=openmp
> +hpcomCode=pthreads
> +hpcomCode=pthreads_spin
Scheduler
Über das flag hpcomScheduler können außerdem verschiedene Schedulingalgorithmen ausgewählt werden. List-Scheduling oder mcp liefern im Allgemeinen gute Ergebnisse.
> +hpcomScheduler=level (nur mit openmp)
> +hpcomScheduler=list
> +hpcomScheduler=listr
> +hpcomScheduler=mcp
Eine vollständige Auflistung der verfügbaren Scheduler und Codegenerierungsverfahren ist in der unten stehenden Tabelle gegeben. Alle mit einem "X" markierten Kombinationen können genutzt werden.
Zusätzliche Informationen
Über hpcomDump können nützliche Informationen zum getroffenen Scheduling abgerufen werden. Das ist unter anderem der theoretische speedUp für das Modell.
> +d=hpcomDump
Wenn man das flag +d=hpcom setzt, werden einige *.graphml dateien erzeugt. Unser Lieblingswerkzeug zum Visualisieren der Task-Graphen ist yEd. Dieses beinhaltet eine Vielzahl von Funktionen wie beispielsweise automatisches Anordnen.
Das ist extrem nützlich um die Parallelität des Modells einzuschätzen.
Scheduler | OpenMP | MPI | pThreads | pThreads_spin | TBB |
---|---|---|---|---|---|
Serial | X | X | X | X | X |
Levelfix | X | ||||
External | X | X | X | ||
Metis | X | X | X | ||
hMetis | X | X | X | ||
List | X | X | X | ||
List reverse | X | X | X | ||
Random | X | X | X | ||
MCP (Modified Critical Path) | X | X | X | ||
Partition | X | X | X | ||
Task dependency | X | X | |||
BLS (Balanced Level Scheduler) | |||||
SBS (Single Block Scheduler) | X | X | X |
Aufspalten von Gleichungssystemen
Große Gleichungssysteme nehmen oft einen Großteil der Simulationszeit in Anspruch. Sie sind nur bedingt gut parallelisierbar und deshalb ein ist es sinnvoll einzelne Systeme in mehrere kleinere Systeme aufzuspalten, sofern möglich.
In OpenModelica ist ein Compiler-Modul implementiert, welches solch ein Aufspalten realisieren kann. Das ist natürlich nicht für alle Modelle möglich. Für elektrische Systeme zeigten sich doch häufig Anwendungsfälle. Aktiviert wird das Modul mit dem debug-flag
+d=resolveLoops