Accès optimal à la mémoire lors de l'utilisation des tables de recherche sur le GPU?


9

J'explore des algorithmes d'isosurface sur GPU pour un projet de baccalauréat (en me concentrant spécifiquement sur les données voxels d'entrée / sortie binaires plutôt que sur les champs à valeur réelle). J'ai donc une implémentation CPU de bons vieux cubes de marche en place dans OpenFrameworks, et maintenant au stade d'essayer de le porter sur les shaders de calcul GLSL, et de considérer les pièges avant de plonger. Je n'ai écrit que des shaders vert et frag avant donc c'est tout nouveau pour moi.

Mon premier problème est de savoir comment utiliser efficacement une table de recherche sur des dizaines ou des centaines de threads dans un groupe de travail? Je comprends qu'un GPU possède différents types de mémoire pour différentes tâches, mais je ne sais pas exactement comment chacun fonctionne ou quel type utiliser.

La table copypasta classique de Paul Bourke est un tableau 256 * 16, donc si vous utilisez un type d'octet scalaire, cela peut probablement être compressé dans une texture de 4 Ko ou SSBO.

La question est, comment empêcher les différents fils de se déclencher? De nombreux cubes dans chaque groupe de travail peuvent potentiellement avoir la même configuration, essayant donc d'accéder au même emplacement dans le tampon en même temps. Existe-t-il une solution de contournement ou une optimisation pour résoudre ce problème?


S'il s'agit d'une table de recherche en lecture seule, vous pouvez simplement utiliser un tampon / une texture. Vous pouvez soit l'emballer dans l'un des formats de texture normaux, soit utiliser certaines des nouvelles fonctionnalités de DX11 / OpenGL pour avoir un format personnalisé. UAV en terre DX11, ou une texture / shader_image_load_store en terre OpenGL.
RichieSams

De plus, jetez un œil à cette présentation: cvg.ethz.ch/teaching/2011spring/gpgpu/cuda_memory.pdf C'est pour CUDA, mais cela devrait vous donner une meilleure idée de ce qui se passe sur le matériel sous-jacent
RichieSams

Ce n'est pas une réponse complète, mais la plus petite quantité de mémoire que vous utilisez est la meilleure, car elle sera plus susceptible de tenir dans les caches et d'avoir moins de cache manquant. Si vous avez des valeurs interpolables, comme si vous étalez des points sur une courbe dans des textures, vous pouvez vérifier cela comme un moyen d'obtenir des tables de recherche de courbe de meilleure qualité avec moins de mémoire: blog.demofox.org/2016/02/22/…
Alan Wolfe

Réponses:


6

Le meilleur endroit pour mettre une table de recherche pour un shader de calcul GPU dépend de la taille de la table de recherche et de la fréquence / cohérence de l'accès. Dans votre cas (vous avez mentionné 4 Ko), la mémoire locale partagée serait probablement la meilleure (en supposant que vous n'avez pas besoin de cette mémoire à d'autres fins dans le même noyau). Cette mémoire a des noms différents dans différentes API, mais est la même chose architecturale et suit les mêmes directives de performances:

  • CUDA: mémoire partagée de groupe de threads
  • DirectCompute: mémoire partagée par groupe
  • OpenCL: mémoire locale
  • Métal: mémoire de groupe de threads
  • OpenGL: mémoire partagée

Le stockage de la table de recherche dans la mémoire globale en tant que tampon en lecture seule peut tout aussi bien fonctionner, en fonction de la taille du cache du GPU particulier que vous utilisez.

Notez que je suppose qu'il s'agit d'une table de recherche en lecture seule. Une table de recherche en lecture-écriture est une bête complètement différente, et vous n'avez pas de bonnes options là-bas.


Il existe également des cas où un tampon en lecture seule fera mieux que de stocker 4 Ko de données en lecture seule dans la mémoire locale partagée. Par exemple, le stockage dans la mémoire locale peut signifier qu'il existe une copie unique de vos données pour chaque groupe de threads. Si le tampon tient dans le cache, il est fort possible que le cache fonctionne mieux que la mémoire locale pour les modèles d'accès en lecture seule.
John Calsbeek

Merci pour les commentaires les amis. J'ai terminé le projet que j'utilisais pour l'instant, et j'ai simplement utilisé une texture de tampon en lecture seule r8ui, qui fonctionnait très bien :)
russ
En utilisant notre site, vous reconnaissez avoir lu et compris notre politique liée aux cookies et notre politique de confidentialité.
Licensed under cc by-sa 3.0 with attribution required.