La vitesse de cos() et sin() fonction en GLSL shaders?
Je suis intéressé par des informations sur la vitesse de sin()
et cos()
dans Open GL Langage de Shader.
La GLSL Document de Spécification indique que:
Les fonctions intégrées essentiellement répartis en trois catégories:
- ...
- ...
- Ils représentent une opération de matériel graphique est susceptible de s'accélérer à un certain point. Les fonctions trigonométriques tomber dans ce
catégorie.
EDIT:
Comme cela a été souligné, le comptage de cycles d'horloge des opérations comme sin()
et cos()
n'a pas vraiment raconter toute l'histoire de rendement.
Donc pour préciser ma question, ce qui m'intéresse vraiment est de savoir si c'est utile pour optimiser loin sin()
et cos()
appels pour les cas courants.
Par exemple, dans mon application, il va être très commun pour l'argument 0
. Donc fait quelque chose comme cela un sens:
float sina, cosa;
if ( rotation == 0 )
{
sina = 0;
cosa = 1;
}
else
{
sina = sin( rotation );
cosa = cos( rotation );
}
Ou le GLSL
compilateur ou le sin()
et cos()
implémentations de prendre soin d'optimisations comme ça pour moi?
- Qu'entendez-vous faire "les Gpu modernes fournissent une accélération matérielle pour
sin()
etcos()
?" Si elle est en cours d'exécution sur le GPU, il peut être dit d'une accélération matérielle. En tout cas, votre meilleur pari est de l'essayer et de profil, comme les cycles d'horloge sur un GPU sont un peu vide de sens, sans plus de contexte à ce que vous faites. Même entre les différentes cartes du même fournisseur, il peut y avoir des différences dans le nombre d'unités d'exécution, de sorte que les cycles ne vous raconte une partie de l'histoire. - Avec ces Gpu, je pense que vous aurez le plus rapidement possible le temps d'exécution de ces fonctions trigonométriques. Question intéressante...
- Comme indiqué dans le this et this question, cette question est essentiellement sans réponse. Une utilisation particulière de
sin
pourrait ne coûtent rien, selon l'endroit où vous l'utilisez et le matériel. - Les bons points. J'ai modifié ma question pour essayer de la rendre un peu plus explicite.
- Merci pour les liens. stackoverflow.com/questions/8415251/... est particulièrement instructif concernant les raisons de simplement compter les gpu d'exécution de l'unité de cycles d'horloge ne pas raconter toute l'histoire de rendement. J'ai édité ma question pour essayer de le plus explicitement l'adresse de l'optimisation que je pense à faire en vaut la peine.
- Pour le dessus, vous pouvez trouver le shader exécute les deux branches, et seulement alors, décide de la suite à faire usage de. Le genre d'optimisation que vous avez à faire ici est, à mon avis, n'en vaut pas la peine et peut même entraîner une diminution de la performance, et non une augmentation.
- Hmm, je ne sais pas si c'est raisonnable de supposer une sorte d'optimisation spécifiques
uniform
vars. Ne fait pas de sens pourin/attribute
vars, cependant. - Je vais voter pour fermer cette question hors-sujet parce que cette question est essentiellement de se demander "quelle est la vitesse de cette opération dans cette langue", quiest sans réponse, parce qu'il dépend du compilateur, plate-forme, et un tas d'autres choses, dont aucun n'a été spécifié.
Vous devez vous connecter pour publier un commentaire.
Pas.
Votre compilateur va faire une de deux choses.
En général, ce n'est pas une bonne idée d'utiliser la logique conditionnelle pour la danse autour des petits spectacle comme celui-là. Il doit être vraiment gros pour être utile, comme un
discard
ou quelque chose.Aussi, notez que le floating-point d'équivalence n'est pas susceptible de travailler. Non, sauf si vous avez réellement passer un uniforme ou un sommet de l'attribut contenant exactement 0.0 pour le shader. Même en interpolant entre 0 et non-nul ne sera probablement jamais produire exactement 0 pour tout fragment.
rotation==0
tandis que les autres bloc (ou noop), puis d'évaluer le deuxième côté alors que le premier bloc. Qui serait évidemment mal. Même si c'est en supposant que les shaders évaluer de la même façon pour les noyaux CUDA.discard
est vraiment trop cher. Si vous n'avez pas l'esprit de l'écriture Z, ou ne sont pas de l'écriture Z de toute façon, un zero alpha écrire peut être beaucoup plus rapide. (J'ai pris+ de 100 pour cent de la vitesse-ups remplacement de rejets avec 0 alpha attire.) Gpu aime quand tous les threads sont en train de faire la même chose.C'est une bonne question. Moi aussi, je me demandais ce.
Google avait des liens dire
cos
etsin
sont en un seul cycle sur les cartes depuis 2005 environ.Vous auriez à tester cela par vous-même, mais je suis assez sûr que la ramification dans un shader est beaucoup plus cher qu'un
sin
oucos
de calcul. GLSL compilateurs sont très bonnes sur l'optimisation des shaders, se soucier de ce qui est l'optimisation prématurée. Si plus tard vous trouvez que, à travers l'ensemble de votre programme, vos shaders sont le goulot d'étranglement, alors vous pouvez vous soucier de l'optimisation.Si vous voulez prendre un coup d'oeil à l'assemblée, le code de votre shader pour une plate-forme spécifique, je vous recommande AMD GPU ShaderAnalyzer.
Ne sais pas si cela répond à votre question, mais il est très difficile de vous dire combien d'horloges de fentes ou d'une instruction prend comme il dépend beaucoup sur le GPU. Habituellement, c'est un seul cycle. Mais même si pas, le compilateur peut réorganiser l'ordre d'exécution des instructions pour masquer le coût réel. Il est certainement plus lent à utiliser la texture des recherches pour sin/cos comme il est d'exécuter les instructions.
SCS <operand>
qui renvoie le sinus(d'entrée.x) dans la composante x et cos(d'entrée.x) dans l'axe de la composante.voir combien le péché est que vous pouvez obtenir dans un shader dans une rangée, par rapport aux mathématiques.abs,frac, ect... je pense qu'une gtx 470 peut gérer 200 péché fonctions par fragment, pas de probs, le cadre sera 10% plus lent qu'un vide shader. c'est farly rapide, vous pouvez envoyer les résultats. ce sera un bon indicateur de l'efficacité de calcul.
Le compilateur évalue à la fois les branches, ce qui rend les conditions assez cher. Si vous utilisez à la fois sin et cos dans votre shader, vous pouvez calculer sin(a) cos(a) = sqrt(1.0 - sin(a)) puisque sin(x)*sin(x) + cos(x)*cos(x) est toujours 1.0