OpenSceneGraph - Threadsicher?

z.B. wxWidgets, GTK+, Qt, OpenGL, DirectX
Antworten
Benutzeravatar
Dirty Oerti
Beiträge: 2229
Registriert: Di Jul 08, 2008 5:05 pm
Wohnort: Thurndorf / Würzburg

OpenSceneGraph - Threadsicher?

Beitrag von Dirty Oerti » Mo Apr 13, 2009 6:59 pm

Tag zusammen :)

In der Hoffnung, dass überhaupt jemand von euch schonmal was davon gehört hat, frage ich mal, ob sich jemand hier mit OpenSceneGraph auskennt.

Was ich tun will:

Ich will eine (simple) Game Engine auf Grundlage von OSG programmieren.
Ich hab mir das nun so überlegt:

Ich erstelle eine Instanz meiner Klasse GameManager, diese wird dann konfiguriert.
Anschließend startet diese Klasse einen osgViewer::Viewer in einem eigenen Thread.
Der Viewer bekommt als Scene (root-Node) einen leeren SceneGraph.

Im ersten Thread kann nun weiter programmiert werden.
Hier soll dann auch der SceneGraph gefüllt werden.

Und zwar während er gezeichnet wird.

Nun meine Frage: Geht das?
Oder crashe ich so OSG?
Ist OSG threadsicher?
Bei Fragen einfach an daniel[ät]proggen[Punkt]org
Ich helfe gerne! :)
----------
Wenn du ein Licht am Ende des Tunnels siehst, freu dich nicht zu früh! Es könnte ein Zug sein, der auf dich zukommt!
----
It said: "Install Win95 or better ..." So I installed Linux.

Benutzeravatar
cloidnerux
Moderator
Beiträge: 3080
Registriert: Fr Sep 26, 2008 4:37 pm
Wohnort: Ram (Gibts wirklich)

Re: OpenSceneGraph - Threadsicher?

Beitrag von cloidnerux » Mo Apr 13, 2009 8:12 pm

Beim nutzen von Threats läuft nihcts Parallel, nur nacheinander.
Du kannst natürlich die Zeichenmethode von OSG im eigen Thread aufen alssen, aber du musst aufpassen das du keine Variablen änderst wärend du Zeichnest.
Dein Problem wird sein, das die Zeit die deine Zeichenmethode braucht variieren wird und du mit threading Probleme bekommst.
Redundanz macht wiederholen unnötig.
quod erat expectandum

Benutzeravatar
Dirty Oerti
Beiträge: 2229
Registriert: Di Jul 08, 2008 5:05 pm
Wohnort: Thurndorf / Würzburg

Re: OpenSceneGraph - Threadsicher?

Beitrag von Dirty Oerti » Mo Apr 13, 2009 8:21 pm

So, für die, die's interessiert: Ich hab jetzt mal ein paar Tests gemacht.

Ich starte einen Viewer in einem eigenen SDL_Thread. Diesem Viewer habe ich die root-Node übergeben.
Danach füge ich root ein HUD mit einem kleinem Text hinzu.
Und siehe da, es erscheint auch :) Und Fehlermeldungen habe ich nicht bekommen.
DANACH hab ich ein SDL_Delay (5000) drinnen, und wenn das rum ist, wird dem Hud ein zweiter Text angefügt.
Und nach (ca) 5 Sekunden erscheint der auch :)

Nach den ersten Tests sieht es also so aus, als ob mein Plan aufgehen würde.
Ich muss das jetzt noch mit Texturen/Switches/und all dem anderen durchprobieren, man kann ja nie wissen :)

Code: Alles auswählen


SDL_Thread *mainloop;
osgViewer::Viewer viewer;


int GameManager_main_loop(void *parm) {
	std::cout << "Here is the main loop!\n";
	osgViewer::Viewer *viewer = (osgViewer::Viewer*)parm;
	viewer->realize();
	return viewer->run();
}


void start() {
	mainloop = SDL_CreateThread(GameManager_main_loop, &viewer);
	if (!mainloop) {
		std::cout << "Couldn't start main loop\n";
	}
}



int main ()
{
//Starte die mainloop, in der der Viewer läuft
	ref_ptr<Group> root (new Group);
	viewer.setSceneData(root.get());
	start();

//Generiere das HUD
	ref_ptr<Camera> Hud (new Camera);
	Hud = createHUD();
        root->addChild(Hud.get());
	
//Erstelle ersten Text und füge ihn in den SceneGraph ein
	ref_ptr<Geode> HudText (new Geode);
	HudText = createHUDText("Hier koennte DEIN Text stehen! ^^",
				Vec3 (5.0f,5.0f,-10.0f)
			       );
	Hud->addChild(HudText.get());

//Warten...	
	SDL_Delay(5000);

//Zweiten Text erstellen und ins HUD einfügen
	ref_ptr<Geode> HudText2 (new Geode);
	HudText2 = createHUDText("Das kommt JETZT erst?!?!",
				 Vec3 (25.0f,55.0f, -1.0f));
	Hud->addChild(HudText2.get());
	
	
	wait_for_end(); //nur eine Funktion die drauf wartet, dass OSG beendet wird
	return 0;
}
Eine Frage hab ich: Wie kann man (mit evtl einem Debuger) überprüfen, ob es hierbei zu "Speicherlöchern" kommt?
ein_text.png
zweiter_text.png
-----------------------------------------------------------------------------------------------
cloidnerux hat geschrieben:Beim nutzen von Threats läuft nihcts Parallel, nur nacheinander.
Ähm, doch? Also zumindest "Pseudoparallel", soweit es die CPU/ das Betriebssystem unterstützt.
http://de.wikibooks.org/wiki/SDL:_Threads

cloidnerux hat geschrieben:Du kannst natürlich die Zeichenmethode von OSG im eigen Thread aufen alssen, aber du musst aufpassen das du keine Variablen änderst wärend du Zeichnest.
Die Befürchtung hatte ich eben. Der SceneGraph ist ja eben nichts anderes als eine (sehr komplexe) Variable.
Aber anscheinend funktioniert es, ich kann den SceneGraph ändern, während gezeichnet wird.
cloidnerux hat geschrieben:Dein Problem wird sein, das die Zeit die deine Zeichenmethode braucht variieren wird und du mit threading Probleme bekommst.
Wie meinst du das? Probleme welcher Art?
Du hast keine ausreichende Berechtigung, um die Dateianhänge dieses Beitrags anzusehen.
Bei Fragen einfach an daniel[ät]proggen[Punkt]org
Ich helfe gerne! :)
----------
Wenn du ein Licht am Ende des Tunnels siehst, freu dich nicht zu früh! Es könnte ein Zug sein, der auf dich zukommt!
----
It said: "Install Win95 or better ..." So I installed Linux.

Benutzeravatar
cloidnerux
Moderator
Beiträge: 3080
Registriert: Fr Sep 26, 2008 4:37 pm
Wohnort: Ram (Gibts wirklich)

Re: OpenSceneGraph - Threadsicher?

Beitrag von cloidnerux » Mo Apr 13, 2009 8:27 pm

Wie meinst du das? Probleme welcher Art?
Du hast eine Komplexe strucktur zu zeichen, dazu brauchst du viel zeit und eben ein bisschen mehr als du Wartest.
Jezt wird wieder OSG aktualisiert und es werden varaiablen geändert. OSG greift auf eine geänderte Variable zu und stellt etwas falsch da -> Grafikfehler.
Mit deinem SDL-Delay hast du aber ein Problem, wenn du es zu lang einstellst verschwendest du zeit, wenn es zu kurz einstellst werden warscheinlich Fehler auftreten.
Redundanz macht wiederholen unnötig.
quod erat expectandum

Benutzeravatar
Dirty Oerti
Beiträge: 2229
Registriert: Di Jul 08, 2008 5:05 pm
Wohnort: Thurndorf / Würzburg

Re: OpenSceneGraph - Threadsicher?

Beitrag von Dirty Oerti » Mo Apr 13, 2009 8:32 pm

cloidnerux hat geschrieben:Du hast eine Komplexe strucktur zu zeichen, dazu brauchst du viel zeit und eben ein bisschen mehr als du Wartest.
Jezt wird wieder OSG aktualisiert und es werden varaiablen geändert. OSG greift auf eine geänderte Variable zu und stellt etwas falsch da -> Grafikfehler.
So lange dauert es im Moment noch nicht (ca 400-500 FPS, das ist Maximalwert mit meiner Grafikkarte).

Ja, die Befürchtung hatte ich ja. Aber anscheinend unterstützt das OSG eine Art LOCK/UNLOCK-Mechanismus, der es nur erlaubt, den SceneGraph zu ändern, wenn er gerade nicht gezeichnet wird bzw nur zu zeichnen, wenn gerade keine Änderungen vorgenommen werden.
cloidnerux hat geschrieben:Mit deinem SDL-Delay hast du aber ein Problem, wenn du es zu lang einstellst verschwendest du zeit, wenn es zu kurz einstellst werden warscheinlich Fehler auftreten.
Das dient doch nicht zur Synchronisation :)
Das SDL_Delay ist nur da, um ein bisschen Zeit zwischen dem Erscheinen des ersten Texts und dem Erscheinen des zweiten Texts zu haben...
Bei Fragen einfach an daniel[ät]proggen[Punkt]org
Ich helfe gerne! :)
----------
Wenn du ein Licht am Ende des Tunnels siehst, freu dich nicht zu früh! Es könnte ein Zug sein, der auf dich zukommt!
----
It said: "Install Win95 or better ..." So I installed Linux.

Benutzeravatar
cloidnerux
Moderator
Beiträge: 3080
Registriert: Fr Sep 26, 2008 4:37 pm
Wohnort: Ram (Gibts wirklich)

Re: OpenSceneGraph - Threadsicher?

Beitrag von cloidnerux » Mo Apr 13, 2009 8:52 pm

Das SDL_Delay ist nur da, um ein bisschen Zeit zwischen dem Erscheinen des ersten Texts und dem Erscheinen des zweiten Texts zu haben...
Achso, hab jezt in ein C# Buch was über Threads gelesn, da wurde auch etwas über Verzögerung gelesen.
OSG eine Art LOCK/UNLOCK-Mechanismus,
Zum einen gut, zum anderen, woher weißt du ob OSG gerade gesperrt?
Ich weiß nicht ob OSG variablen die wärend des zeichnes geändert werden zwischenspeichert, aber wenn nciht, dann hast du Probleme.
Aber am besten wäre ein Test.
Redundanz macht wiederholen unnötig.
quod erat expectandum

Benutzeravatar
Dirty Oerti
Beiträge: 2229
Registriert: Di Jul 08, 2008 5:05 pm
Wohnort: Thurndorf / Würzburg

Re: OpenSceneGraph - Threadsicher?

Beitrag von Dirty Oerti » Mo Apr 13, 2009 9:25 pm

cloidnerux hat geschrieben:Aber am besten wäre ein Test.
Hab ich ja gemacht, zumindest einen simplen (der mit den 2 Texten).

Ich guck jetzt mal, ob das auch mit mehr als einem (zusätzlichen)Thread funktioniert (also jetzt 3 Threads).
Bei Fragen einfach an daniel[ät]proggen[Punkt]org
Ich helfe gerne! :)
----------
Wenn du ein Licht am Ende des Tunnels siehst, freu dich nicht zu früh! Es könnte ein Zug sein, der auf dich zukommt!
----
It said: "Install Win95 or better ..." So I installed Linux.

Benutzeravatar
Dirty Oerti
Beiträge: 2229
Registriert: Di Jul 08, 2008 5:05 pm
Wohnort: Thurndorf / Würzburg

Re: OpenSceneGraph - Threadsicher?

Beitrag von Dirty Oerti » Mo Apr 13, 2009 9:41 pm

Ich hab jetzt insgesamt 4 Threads:

Einen, der zeichnet.
Einen, der die beiden Texte auf den Schirm bringt und wartet, dass der Zeichner fertig ist.
Einen, der einen Text im Interval von einer Sekunde blinken lässt.
Und einen, der exat das gleiche tut wie der 3., aber eine halbe Sekunde später gestartet wurde.

Ich hab die Anwendung nun ein paar mal gestartet, und hatte bisher einmal einen Segmentation Fault -> nicht gut.
Ich weiß aber nich, ob das von der Parameterübergabe an die Threads kommen könnte.

OSG nutzt nämlich ref_ptr, eine Klasse, die sich darum kümmert, ob man das Objekt im Speicher halten muss oder nicht. Nun weiß ich nicht, ob ich das gut übergeben hab...
Bei Fragen einfach an daniel[ät]proggen[Punkt]org
Ich helfe gerne! :)
----------
Wenn du ein Licht am Ende des Tunnels siehst, freu dich nicht zu früh! Es könnte ein Zug sein, der auf dich zukommt!
----
It said: "Install Win95 or better ..." So I installed Linux.

Benutzeravatar
Dirty Oerti
Beiträge: 2229
Registriert: Di Jul 08, 2008 5:05 pm
Wohnort: Thurndorf / Würzburg

Re: OpenSceneGraph - Threadsicher?

Beitrag von Dirty Oerti » Sa Aug 15, 2009 9:10 am

*Wieder hervorkram*

So :)

Um das mal zu einem Abschluss zu bringen:
"Damals" im April hatte ich dann das Problem, dass ich Segmentation Faults rein wahllos bekommen habe.
Nach ein bisschen suchen bin ich darauf gekommen, das es KEINEN Lock/Unlock-Mechanismus direkt in OpenSceneGraph gibt.
Also hatte ich das Projekt vorerst auf Eis gelegt.

Jetzt weiß ich nicht, was mich gestern/vorgestern geritten hat, aber ich habs nochmal aufgegriffen :D

Und zwar wie folgt:

Der Plan war, einen Verbund aus SDL und OSG (wie in diesem Tutorial beschrieben: http://www.cs.clemson.edu/~malloy/cours ... index.html ) aufzusetzen (also eine GameLoop), und das in einen eigenen Thread zu verbannen.
Anstatt dieses mal jedoch die SDL_Threads zu verwenden, bin ich "klüger" geworden:

OSG selbst unterstützt unterschiedliche ThreadingModelle (das sind Interna). Dazu nutzt es die Bibliothek OpenThreads. Gut, über OpenThreads habe ich erstmal so gar keine Informationen gefunden.
Doch: In der Dokumentation (/usr/share/doc/openscenegraph/) von OSG findet sich auch ein Abschnitt über OpenThreads (genau gesagt eine komplette Referenz).
OpenThreads bildet Threads auf einer rein Objektbasierten-Basis. Das gefiel mir schon mal besser als das Konzept von SDL.

Nach diversen Tests und auch diversen Fehlern (siehe http://forum.proggen.org/viewtopic.php?p=9289#p9289 ) und einer umfangreicheren Suche als beim letzten mal bin ich zu folgendem Ergebnis gekommen:

OSG und SDL zusammen ist kein Problem.
OSG (Unter Benutzung des Viewers) in einen extra Thread mittels OpenThreads zu schicken ist kein Problem. Probleme kommen erst, wenn auch wirklich gezeichnet und verändert wird.
OSG und SDL zusammen in einen eigenen OpenThreads Thread zu schieben resultiert darin: http://forum.proggen.org/viewtopic.php?p=9289#p9289 Und zwar egal, wie man es dreht und wendet.^^

Allgemein zu OSG und externen Threads habe ich auch einiges herausgefunden.
Zum einem mal - wie schon angesprochen - hat OSG keinen Lock/Unlock-Mechanismus beim Zeichnen und Ändern des SceneGraphs.
Zumindest in der Art, das man ihn "von außen" erreichen könnte.
OSG selbst ist nämlich in der Lage, Threads zu starten, die genau das vorraussetzen. (aus diesem Grund KÖNNTE es auch gehen, wenn man OSG und OpenThreads verwendet. KÖNNTE!)
Dieses Problem kann man "sicher" umgehen, wenn man den Zeichenvorgang und den Änderungsvorgang in Mutexe setzt.

Code: Alles auswählen

while (!viewer.done())
{
  mutex.lock(); 
  viewer.frame();
  mutex.unlock();
}



//bei jeder Änderung, die den SceneGraph antastet. Welche das genau sind muss rausgefunden werden.
mutex.lock();
root->attachChild(ieine_node.get());
mutex.unlock();
Das Obige könnte evtl nicht reichen, wenn nämlich der Viewer automatisch eigene Threads startet. Das könnte man unterbinden, das geht aber auch die Performance.
Also evtl noch das folgende einbringen:

Code: Alles auswählen

while (!viewer.done())
{
  mutex.lock(); 
  viewer.startThreading();
  viewer.frame();
  viewer.stopThreading();
  mutex.unlock();
}
Ob das nun klug oder performant ist bleibt offen...


Es gibt aber ein viel...unangenehmeres Problem:
Den Zeichen (bzw Event) Thread auszulagern hat keinen Sinn. Der Hauptthread läuft weiter und hat keine Möglichkeit, sinnvoll auf den anderen Thread zu warten.
Somit verliert das alles seinen Sinn^^ :)

Mir bleibt also nur: Lieber über Callbacks und Events arbeiten, als versuchen, die GameLogik in einen eigenen Thread zu bugsieren.
(Wofür aber ein eigener Thread durchaus Sinn macht ist abspielen von Musik)

http://forum.openscenegraph.org/viewtop ... &view=next
Bei Fragen einfach an daniel[ät]proggen[Punkt]org
Ich helfe gerne! :)
----------
Wenn du ein Licht am Ende des Tunnels siehst, freu dich nicht zu früh! Es könnte ein Zug sein, der auf dich zukommt!
----
It said: "Install Win95 or better ..." So I installed Linux.

Antworten