Was könnte dazu führen, dass mein Programm nach einiger Zeit nicht alle Kerne verwendet?

8

Ich habe ein Programm geschrieben, das Videos von drei Grafikkarten aufnimmt und anzeigt. Für jeden Frame spawne ich einen Thread, der den Frame nach Jpeg komprimiert und ihn dann in die Warteschlange schreibt, um ihn auf die Festplatte zu schreiben. Ich habe auch andere Threads, die aus diesen Dateien lesen und sie in ihren eigenen Threads dekodieren. Normalerweise funktioniert das gut, es ist ein ziemlich CPU-intensives Programm, das ungefähr 70-80 Prozent aller sechs CPU-Kerne verwendet. Aber nach einer Weile wird die Kodierung plötzlich langsamer und das Programm kann das Video nicht schnell genug verarbeiten und beginnt Frames zu löschen. Wenn ich die CPU-Auslastung überprüfe, kann ich sehen, dass ein Kern (normalerweise Kern 5) nicht mehr viel macht.

Wenn das passiert, ist es egal, ob ich mein Programm beende und neu starte. CPU 5 wird immer noch eine geringe Auslastung haben und das Programm beginnt sofort Frames zu löschen. Das Löschen aller gespeicherten Videos hat ebenfalls keine Auswirkungen. Neustart des Computers ist das einzige, was hilft. Oh, und wenn ich die Affinität meines Programms so einstelle, dass alle außer dem halbleeren Kern verwendet werden, funktioniert es, bis dasselbe mit einem anderen Kern passiert. Hier ist mein Setup:

  • AMD X6 1055T (kühl und leise AUS)
  • GA-790FX-UD5-Motherboard
  • 4Gig RAM unangegangen 1333Mhz '
  • Blackmagic Decklink DUO-Aufnahmekarten (x2)
  • Linux - Ubuntu x64 10.10 mit Kernel 2.6.32.29

Meine App verwendet:

  • libjpeg-turbo
  • Posix-Threads
  • decklink api
  • Qt
  • In C / C ++ geschrieben
  • Alle Bibliotheken sind dynamisch verknüpft

Es scheint mir, als wäre es ein Problem mit der Art, wie Linux Threads auf den Kernen plant. Oder gibt es eine Möglichkeit, mein Programm kann so schlecht durcheinander bringen, dass es nicht hilft, das Programm neu zu starten?

Danke für das Lesen, jeder Input ist willkommen. Ich stecke fest:)

    
Nioreh 02.10.2011, 12:59
quelle

2 Antworten

4

Stellen Sie zuerst sicher, dass es nicht Ihr Programm ist - vielleicht stoßen Sie auf einen verschachtelten Nebenläufigkeits-Bug, obwohl dies mit Ihrer Programmarchitektur und der Tatsache, dass ein Neustart des Kernels hilft, nicht so wahrscheinlich ist. Ich habe festgestellt, dass ein guter Weg in der Regel ein Post-Mortem-Debugging ist. Kompilieren Sie mit Debugging-Symbolen, beenden Sie das Programm mit -SEGV, wenn es sich merkwürdig verhält, und untersuchen Sie den Core-Dump mit gdb.

    
thiton 02.10.2011 13:11
quelle
2

Ich würde versuchen, ein Kern-Round-Robin-A zu wählen, wenn ein neuer Frame-Verarbeitungs-Thread erzeugt wird, und den Thread an diesen Core anheften. Verfolgen Sie Statistiken darüber, wie lange es dauert, bis der Thread ausgeführt wird. Wenn dies tatsächlich ein Fehler im Linux-Scheduler ist - Ihre Threads benötigen ungefähr die gleiche Zeit, um auf jedem Kern zu laufen. Wenn der Kern tatsächlich mit etwas anderem beschäftigt ist, erhalten Ihre an diesen Kern angehefteten Threads weniger CPU-Zeit.

    
msh 02.10.2011 18:24
quelle