Я использую CUDA несколько недель, но у меня есть некоторые сомнения по поводу распределения блоков / деформаций / потоков. Я изучаю архитектуру с дидактической точки зрения (университетский проект), поэтому достижение максимальной производительности - не моя забота.
Прежде всего, я хотел бы понять, правильно ли я понял эти факты:
Программист пишет ядро и организует его выполнение в виде сетки блоков потоков.
Каждый блок закреплен за потоковым мультипроцессором (SM). После назначения он не может перейти на другой SM.
Каждый SM разбивает свои блоки на Warps (в настоящее время максимальный размер 32 потока). Все потоки в основе выполняются одновременно на ресурсах SM.
Фактическое выполнение потока выполняется ядрами CUDA, содержащимися в SM. Нет никакого конкретного сопоставления между потоками и ядрами.
Если деформация содержит 20 потоков, но в настоящее время доступно только 16 ядер, деформация не будет выполняться.
С другой стороны, если блок содержит 48 потоков, он будет разделен на 2 деформации, и они будут выполняться параллельно при условии, что доступно достаточно памяти.
Если поток запускается на ядре, то он останавливается для доступа к памяти или для длительной операции с плавающей запятой, его выполнение может возобновиться на другом ядре.
Они правы?
Теперь у меня есть GeForce 560 Ti, поэтому, согласно спецификациям, он оснащен 8 SM, каждый из которых содержит 48 ядер CUDA (всего 384 ядра).
Моя цель - убедиться, что каждое ядро архитектуры выполняет ОДИНАКОВЫЕ инструкции. Предполагая, что моему коду не потребуется больше регистров, чем доступно в каждом SM, я придумал разные подходы:
Я создаю 8 блоков по 48 потоков в каждом, так что каждому SM нужно выполнить 1 блок. В этом случае будут ли 48 потоков выполняться в SM параллельно (используя все 48 ядер, доступных для них)?
Есть ли разница, если я запускаю 64 блока по 6 потоков? (Предполагая, что они будут равномерно отображены среди SM)
Если я «погружаю» графический процессор в запланированную работу (например, создавая 1024 блока по 1024 потока в каждом), можно ли предположить, что все ядра будут использоваться в определенный момент и будут выполнять одни и те же вычисления (при условии, что потоки никогда не глохнет)?
Есть ли способ проверить эти ситуации с помощью профилировщика?
Есть ли ссылка на этот материал? Я прочитал Руководство по программированию CUDA и главы, посвященные архитектуре оборудования, в статьях «Программирование массивно-параллельных процессоров» и «Проектирование и разработка приложений CUDA»; но я не мог получить точного ответа.