#1 08.05.2012 19:57:30

DerPeer
GodlikeMember
Ort: Berlin
Registriert: 04.02.2005
Beiträge: 1291

shader debuggen

Heute habe ich mal nicht nur Fragen, sondern auch Antworten :-)

Aber die Cracks unter euch wussten das alles sicher schon längst. Ich habe nämlich heute viel übers Shader-Debugging gelernt. Oder besser: Was man lieber nicht machen sollte.

Bisher hatte ich in großen Projekten immer mit unschönen Exceptions zu tun, die ich nicht verstand oder lösen konnte. Meistens lag das an Fehlern im Shader - was mir Delphi allerdings nicht gern mitteilte.

Zum Beispiel habe ich momentan einen Bug, wo der ganze Rechner komplett abschmiert und neubootet. Ich glaube, ich weiß jetzt woran das liegt, aber sowas ist doch wirklich nicht schön!

Naja, lassen wir das Gelaber mal.

1.: Ich hatte bisher im Shader oft sowas: float4 a = b / time;
Wobei time eine globale Variable war, die durch die Delpi-Applikation gesetzt wurde. Ich habe immer PEINLICH darauf geachtet, dass time nicht =0 wurde, aber trotzdem kam immer eine Division by zero-Exception.
Schön, man kann das beheben und 1/time übergeben und im shader multipizieren statt zu dividieren.
Aber verstehen muss ich das nicht, oder?

2.: Ebenso scheint folgendes ein Problem zu sein:
float4 a = pow(time, 0.5);
Auch wenn time niemals null wird (werden sollte), muss man damit rechnen, dass das dennoch passiert. Also hab ich time durch time+0.01 ersetzt. Das hat geholfen. Hat jemand ne bessere Idee?

3.: Bestimmt gibts noch andere arithmetische Operationen, die Exceptions werfen können. Atan, asin und acos bestimmt. Man sollte also immer eine Art Sicherheitsabstand mit in den Shader-Code packen, und die Variablen eher fuzzy/jittery betrachten.

Habt ihr noch mehr Hinweise, die tagelanges Debugging im Shader abkürzen könnten?

Ich hatte auch gelesen, dass man floats immer mit Argwohn behandeln sollte. Sie können leicht von dem abweichen, was man erwartet (wie oben halt). Weiß jemand, warum das so ist? Ich meine, floats mögen ja keine Integers sein, aber deterministisch ist mein Computer noch immer, und wenn ich tausendmal 1 addiere sollte nicht 999.9998 rauskommen.

Schönen Abend noch!

DerPeer

Offline

 

#2 15.05.2012 13:44:25

Lotipats
UltraMember
Registriert: 17.05.2005
Beiträge: 395

Re: shader debuggen

[quote=DerPeer]Ich hatte auch gelesen, dass man floats immer mit Argwohn behandeln sollte. Sie können leicht von dem abweichen, was man erwartet (wie oben halt). Weiß jemand, warum das so ist?

Der Computer stellt mit float/double (bzw. single/double) eine Fließkommazahl vor als ((-1)^[S])*1.[M] * 2^[E-127], wobei S das Vorzeichen bestimmt, M der (binäre) Wert nach der "1," und E der Exponent (auch binär wink ).
Beispiele: -1,0101011 * 2^(10000001-1111111), also -101,01011 bzw. dezimal -5,34375 (da -(5 + 1/4+1/16+1/32)).
Die Zahl hinter dem Komma wird also als Summe von 1/(2^n) dargestellt. Hier gibt es nun das Problem. Stelle mal 0,3 als eine solche Summe dar. 0,3=0,25+0,03125+0,015625+... Mit jeder Erhöhung von n erhältst du eine weitere dezimale Nachkommastelle. 0,3 lässt sich damit nur als Grenzwert einer unendlichen Summe darstellen. Also schneidet der Computer einfach ab.
Durch die Festlegung, dass die Zahl immer mit "1," beginnt, kann man sich diese noch sparen, der Computer speichert also nach IEEE 754 die Zahl als [S|E|M], bei float ist das [1|8|23]=32 als Bit-Belegung und bei double [1|11|52]=64. Es gibt hier allerdings einige Spezialzahlen, deren Format fest vorgegeben ist (z.B. [0/1|0..0|0...0] ist 0 oder [1|1..1|0...0] als -Unendlich) und für die es eigene Rechenregeln gibt.

Dadurch ergeben sich verschiedene "Nebenwirkungen", beispielsweise wie viele Stellen eine Zahl haben darf, ohne dass Informationen verloren gehen (bei float sind es 7-8 dezimale Ziffern), genauso wie Informationen von double -> float verloren gehen. Ferner gehen auch beim Rechnen Informationen verloren, wenn der Unterschied zwischen den Zahlen zu groß ist, im schlimmsten Fall kommt eine der beiden Zahlen als Ergebnis heraus.
Ein gutes Beispiel ist hier epsilon e. Dieses gibt die kleinste Zahl an, für die gilt: (1+e)-1 != 0. Für float dürfte das ca. 1.19209e-007 sein. [http://msdn.microsoft.com/en-us/library … 80%29.aspx]
Das dürften die oben gemeinten Probleme sein - natürlich nur in Kurzform.

Bei deinen Problemen wüsste ich erst einmal nicht genau, woran es liegen könnte. Ich weiß auch nicht, welchen Datentyp "time" hat. Ich weiß noch, dass ich auch mal solche Probleme mit Shadern (allerdings OpenGL) hatte, das war auch irgendein dummer Fehler, ich weiß nur nicht mehr, was es war. hmm
Ich hoffe aber, dir vllt. dennoch irgendwie geholfen zu haben.

LOTIPATS

Beitrag geändert von Lotipats (15.05.2012 13:51:36)

Offline

 

#3 25.05.2012 15:57:01

DerPeer
GodlikeMember
Ort: Berlin
Registriert: 04.02.2005
Beiträge: 1291

Re: shader debuggen

Lieber Lotipats! Vielen Dank für die Antwort. Ich hab so langsam das Gefühl, mein Computer ist zu alt und müsste mal ersetzt werden :-)

DerPeer

Offline

 

Brett Fußzeile

Powered by PunBB
© Copyright 2002–2005 Rickard Andersson