Windows Scheduler: Auslagern von Threads auf NUMA-Node vs. Auslagern auf HT

Gewuerzwiesel

Lt. Junior Grade
Registriert
Feb. 2017
Beiträge
307
Hallo Zusammen,

neulich ist mir aufgefallen, dass Windows bevorzugt Threads auf virtuelle Kerne verteilt statt diese auf einen weiteren NUMA-Node zu verteilen an dem keine Last anliegt.

Haben die Latenzen zwischen den NUMA-Nodes einen so großen Einfluss auf die Performance, dass Windows der Meinung ist es wäre immer noch schneller es auf dem selben NUMA-Node im HT zu berechnen als es dann auf eine Node zu schieben der vor sich hin idlet?

Manchmal ist es sogar so, dass auch bei nicht voller Auslastung des aktiven NUMA-Nodes HT Threads statt der idle-Kerne angesprochen werden.
Hat jemand von euch noch ein ähnliches Verhalten beobachtet, hat es was mit Daten zu tun, die dann im L1 und L2 Cache liegen?

Vielen Dank für eure Antworten.
 
Ist sehr wahrscheinlich, dass es um die Caches geht. Da ist es natürlich sehr viel Aufwändiger die Daten zwischen 2 Caches synchron zu halten bzw. hin und her zu kopieren.

Sonst gibt's noch die Möglichkeit des Energiesparens. Die CPU kann einen ungenutzten Kern deaktivieren oder in einen low power Mode versetzen. Bei 4 Threads und HT wären das dann nur 2 aktive Kerne statt 4.
 
Das mit den Caches habe ich mir fast schon gedacht.
benneque schrieb:
Sonst gibt's noch die Möglichkeit des Energiesparens. Die CPU kann einen ungenutzten Kern deaktivieren oder in einen low power Mode versetzen. Bei 4 Threads und HT wären das dann nur 2 aktive Kerne statt 4.

Daran dürfte es nicht liegen, Windows läuft im High Perf. Modus, da sonst nicht der volle Turbo ausgefahren wurde.
 
Kannst du das mit den NUMA nodes mal präzisieren?
Meinst du verschiedene Sockets auf dem gleichen Mainboard?
Haswell-EP hat z.b. mit aktiviertem Cluster-On-Die schon zwei NUMA Domains auf einer CPU
 
aroxx schrieb:
Kannst du das mit den NUMA nodes mal präzisieren?
Meinst du verschiedene Sockets auf dem gleichen Mainboard?
Haswell-EP hat z.b. mit aktiviertem Cluster-On-Die schon zwei NUMA Domains auf einer CPU

Genau, es sind 2 E5-2699 v4. Wobei Windows nur 2 NUMA-Nodes anzeigt.
 
Die Daten müssten bei einem 2 Socket System nicht nur wie bei Ryzen durch den L3 Cache kopiert werden sondern tatsächlich über den RAM, was bei zusammenhängenden Threads enorm Perfomance kosten kann. Daher versucht Windows sie auf einem Node zusammen zu halten. Solltest Du eine komplett andere Anwendung starten, sollte diese i.d.R. auf den anderen NUMA-Node laufen.
 
Die Vermutung habe ich ja auch geäußert, aber kostet es dann so viel mehr, dass das Auslagern auf einem "HT-Kern" mehr bringt?
 
Da du von Threads sprichst, nehme ich dann, dass du ein Programm hast, welches mehrere Threads hat.

Die Daten auf denen ein Thread arbeitet sollten immer in der gleichen NUMA-Domain sein wie der CPU-Kern auf den der Thread gescheduled wird. Da im Fall von Intel die Daten sonst alle über den Socket-Interconnect QPI laufen müssen. (Linux macht dann unter Umständen page migration um die Daten wieder in die "bessere" NUMA-Domain zu schieben)

Zurück zu deinem Problem: Ein Programm, mehrere Threads. (data set size sei viel größer als L3 Cache)
Hier gibt es zwei Möglichkeiten:
1) Die Threads arbeiten unabhängig voneinander auf ihren eigenen Daten.
In diesem Fall kann es besser sein die Threads auf verschiedene NUMA-Domains zu verteilen, weil ihnen dann mehr RAM-Bandbreite zur Verfügung steht.

2) Die Threads arbeiten auf den gleichen Daten.
In diesem Fall ist es sehr wichtig mit Hilfe des Caches die räumliche und zeitliche Lokalität der Daten auszunutzen. Das funktioniert am besten, wenn sich alle Threads in einer NUMA-Domain befinden.


Wann bringt HyperThreading etwas?
Wenn viele Löcher in den Pipelines der Execution Units des CPU Kerns sind.
Beispiel: https://de.wikipedia.org/wiki/Hyper-Threading


Hilft das ein wenig?
 
Vielen Dank für die zahlreichen Infos.

Ich habe heute morgen mal ein Paar kleinere Tests mit aktiviertem/deaktiviertem HT und CoD gemacht.
Scheinbar gibt es tatsächlich einen minimalen Performancegewinn für die Kombinationen mit aktivem HT.

Setup bestand aus 2-Socketsystem mit Xeon E5 2699-v4 je Socket.
Die Angelegte Last war eine FEM-Berechung welche auf 12 Threads aufgeteilt wurde.

Die Zeiten pro Iteration waren:

6.216 s bei deaktiviertem HT und deaktivertem CoD
6.358 s bei deaktiviertem HT und aktiviertem CoD
6.233 s bei aktiviertem HT und aktiviertem CoD
6.141 s bei aktiviertem HT und deaktiviertem CoD

bei Test mit aktivem CoD und inaktivem HT mit der selben FEM-Berechnung auf 11 Kernen (So dass die Threads in ein Cluster on Die passten) betrug die Zeit 7.027 s. Passt somit in etwa in das Bild, dass CoD für meine Anwendung Leistung kostet.

So wirklich erklären warum HT mir einen Performancevorteil bringt kann ich mir aber nicht. Bei dem Setup hätte ich es nicht erwartet.
 
sind das 6 tausend sekunden oder 6,216 sekunden?
Wie viele Iterationen hast du insgesamt gemacht?
Wie groß war der Gesamtspeicherbedarf?

Womit hast du die Laufzeit gemessen?

hast du oder der FEM-Code die threads explizit auf cores gepinnt?
 
Zuletzt bearbeitet:
Zurück
Oben