Мне было интересно, есть ли какой-нибудь простой способ превратить не слитый доступ к памяти в слитый. Давайте возьмем пример этого массива:
dW[[w0,w1,w2][w3,w4,w5][w6,w7][w8,w9]]
Теперь я знаю, что если поток 0 в блоке 0 доступа dW[0]
а затем поток 1 в блоке 0 доступа dw[1]
слился доступ в глобальную память. Проблема в том, что у меня есть две операции. Первый объединяется, как описано выше. Но второй не потому, что поток 1 в блоке 0 должен выполнить операцию на обоих dW[0]
, dW[1]
а также dW[2]
,
Я знаю, что первоначальная форма контейнера разрешает или запрещает объединенный доступ. Но dW
это очень большой массив, и я не могу преобразовать его во время процесса.
Вы знаете, возможно ли облегчить эту проблему?
Вы можете попытаться использовать разделяемую память, возможно, это сработает (или нет, трудно сказать без примера).
Например, скажем, первая операция доступа объединила данные, а вторая много делает; это может ускорить вещи
__shared__ int shared[BLOCK_SIZE];
// Load data global -> shared with coalesced access ; you may need to load a bit more before/after depending on you application
shared[tid] = global[some id]
syncthreads();
// Do the math with coalescing access
function0(shared[tid])
// Do the math with the non coalescing access
function1(shared[tid+-1 or wathever])
Идея состоит в том, чтобы загружать данные в совместно используемом виде коалесцентно, а затем использовать совместно используемое для выполнения математических вычислений, поскольку коалесцентный доступ не имеет значения для совместно используемой памяти (но, с другой стороны, конфликт в банке имеет значение; обычно это нормально).
Вы должны будете предоставить нам больше информации, если вам нужна более точная помощь.
Это просто подсказка.
Других решений пока нет …