2010-01-10 6 views
7

Я пишу свою собственную графическую библиотеку (да, домашнее задание :) и использую cuda, чтобы делать все рендеринг и вычисления быстро.Рисование треугольников с CUDA

У меня проблема с рисованием заполненных треугольников. Я написал это так, чтобы один процесс рисовал один треугольник. Он работает очень хорошо, когда на сцене появляется много маленьких треугольников, но он полностью разрушает производительность, когда треугольники большие.

Моя идея - сделать два прохода. Вначале подсчитайте только вкладку с информацией о сканированных линиях (отрисуйте оттуда сюда). Это будет треугольник для вычисления процесса, как в текущем алгоритме. И во втором проходе действительно рисуют линии сканирования с несколькими процессами на треугольник.

Но будет ли это достаточно быстро? Может быть, есть лучшее решение?

ответ

3

Вы можете проверить это blog: Проводка рендеринга программного обеспечения в CUDA. Я не думаю, что это оптимальный способ сделать это, но, по крайней мере, автор делится некоторыми полезными источниками.

Во-вторых, читайте это paper: Программируемая архитектура параллельного рендеринга.Я думаю, что это одна из самых последних статей, и это также CUDA.

Если бы я должен был сделать это, я бы с данных параллельного растрирования трубопровода как в Larrabee (который TBR) или даже РЕЙС и адаптировать его к CUDA:

http://www.ddj.com/architect/217200602 http://home.comcast.net/~tom_forsyth/larrabee/Standford%20Forsyth%20Larrabee%202010.zip (см вторая часть презентации)

http://graphics.stanford.edu/papers/mprast/

0

Я подозреваю, что у вас есть некоторые неправильные представления о CUDA и о том, как их использовать, тем более, что вы ссылаетесь на «процесс», когда в терминологии CUDA такой вещи нет.

Для большинства приложений CUDA есть две важные вещи для получения хорошей производительности: оптимизация доступа к памяти и обеспечение того, чтобы каждый «активный» поток CUDA в warp выполнял одну и ту же операцию одновременно с активными нитями в warp. Оба они звучат так, как будто они важны для вашего приложения.

Чтобы оптимизировать доступ к памяти, вы хотите, чтобы ваши чтения из глобальной памяти и записи в глобальную память были объединены. Вы можете прочитать об этом больше в руководстве по программированию CUDA, но по сути это означает, что смежные потоки в половине основы должны читать или записывать в соседние ячейки памяти. Кроме того, каждый поток должен читать или писать 4, 8 или 16 байтов за раз.

Если ваш шаблон доступа к памяти случайный, вам может потребоваться использовать текстурную память. Когда вам нужно обратиться к памяти, которая была прочитана другими потоками в блоке, вам следует использовать общую память.

В вашем случае я не уверен, что ваши входные данные, но вы должны хотя бы убедиться, что ваши записи объединены. Вам, вероятно, придется инвестировать некоторые нетривиальные усилия, чтобы ваши чтения были эффективными.

Для второй части я бы рекомендовал, чтобы каждый поток CUDA обрабатывал один пиксель в вашем выходном изображении. С помощью этой стратегии вы должны следить за циклами в ваших ядрах, которые будут выполняться дольше или короче в зависимости от данных за потоки. Каждый поток в ваших деформациях должен выполнять одинаковое количество шагов в одном порядке. Единственным исключением из этого является то, что нет реального штрафа за производительность за то, что некоторые потоки в warp не выполняют операцию, в то время как остальные потоки выполняют одну и ту же операцию вместе.

Таким образом, я бы рекомендовал, чтобы каждый поток проверял, находится ли его пиксель внутри заданного треугольника. Если нет, он ничего не должен делать. Если это так, он должен вычислить выходной цвет для этого пикселя.

Кроме того, я настоятельно рекомендую прочитать больше о CUDA, поскольку кажется, что вы прыгаете в глубокий конец, не имея хорошего понимания некоторых основных принципов.

+1

Извините за мой язык, английский не мой родной. Итак, какова правильная терминология для обработки на видеокартах? Ну, я думаю, я понимаю CUDA довольно хорошо, но да, у меня нет знаний в параллельных алгоритмах. Мой ввод - это набор вершин в пространстве отсечения, и мне приходилось рисовать треугольники. Я думаю, что алгоритм, в котором каждый пиксель должен проверять каждый треугольник, не был бы оптимальным. – qba

+0

Избегание каждого пикселя, проверяющего каждый треугольник, можно сделать, разбив ваши треугольники с помощью BVH, KD-Tree или R-Tree. – whatnick

-1

не быть грубым, но это не то, что видеокарты предназначены сделать так или иначе? Похоже, что использование стандартных API OpenGL и Direct3D будет иметь больше смысла.

Почему бы не использовать API для выполнения основного рендеринга, а не CUDA, который является гораздо более низким уровнем? Затем, если вы хотите выполнять дополнительные операции, которые не поддерживаются, вы можете использовать CUDA для их применения сверху. Или, возможно, реализовать их как шейдеры.

+0

Да, да. Но его целью здесь является создание графического конвейера растрирования без традиционных API. Подумайте об этом как о доказательстве концепции или цели образовательных целей. – Stringer

+0

Да, его проект для учебы. Нам пришлось делать все растеризацию. Большинство людей используют процессор, но я решил использовать CUDA. – qba

+0

Хм, в этом случае это звучит как интересный проект. Вид обратного подхода, но тем не менее интересный. – BobMcGee