Правильно было передать массив из функции Metal Kernel в локальную функцию - PullRequest
0 голосов
/ 06 мая 2018

Я работаю над преобразованием вычислительной модели из Cuda в Metal.

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

Я получаю следующую ошибку:

  1. Функция-кандидат недопустима: неизвестное преобразование из «устройства float3 [32]» в «float3 *» (также известное как vector_float3 *) для второго аргумента

Для тестовой функции.

Вот пример кода:

#include <metal_stdlib>
using namespace metal;

struct DOBJ
{
    int      num_vertex;        /* Number of vertcies */
    float3   vert       [32];  /* Rotated on CPU */    
};

bool testFunction(
                          uint num_vertex_B,
                          float3 Vertex_B[32])
{
}

kernel void TestKernel( device DOBJ *VolumeObject )
{

    int d_index = 5;

    bool SP_Check = testFunction(
                                    VolumeObject[d_index].num_vertex,
                                    VolumeObject[d_index].vert );
}

Исходное формирование тестовой функции CUDA имело следующий формат:

__device__ bool testFunction(
                          uint num_vertex_B,
                          float3 *Vertex_B)
{
}

У меня есть тонна кода, которая соответствует этой структуре в программе. Как правильно отформатировать функцию testFunction для принятия Vertex_B?

Еще немного тестового кода после комментария от Warrenm

  1. Это компилируется, но я еще не пробовал запускать тесты.
  2. У вас может быть две функции «testFunction», отличающиеся только расположением памяти в векторе, но точно таким же кодом.
  3. float3 Vertex_B [5] компилируется для памяти потоков, но не для памяти устройства.

    #include <metal_stdlib>
    using namespace metal;
    
    struct DOBJ
    {
        int      num_vertex;        /* Number of vertcies */
        float3   vert       [32];  /* Rotated on CPU */ 
    };
    
    bool testFunction(uint num_vertex_B, device float3 *Vertex_B) { return false; }
    
    bool testFunction(uint num_vertex_B, thread float3 *Vertex_B) { return false; }
    
    bool testFunction2( uint num_vertex_B, float3 Vertex_B[5]) { return false; }
    
    kernel void VolumeObject_InteractionPolyhedra( device DOBJ *VolumeObject )
    {
    
        int d_index = 5;
    
        bool SP_Check = testFunction( VolumeObject[d_index].num_vertex, VolumeObject[d_index].vert);
    
        // Compiler error: 1. Candidate function not viable: no known conversion from 'float3 device[32]' to 'float3 *' (aka 'vector_float3 *') for 2nd argument
        // bool SP_Check2 = testFunction2( VolumeObject[d_index].num_vertex, VolumeObject[d_index].vert);
    
        thread float3 *vertList;
        bool SP_Check3 = testFunction( 5, vertList);
    
        bool SP_Check4 = testFunction2( 5, vertList);
    }
    

1 Ответ

0 голосов
/ 06 мая 2018

Невозможно передать массив по значению в C или C ++ (из которых Metal Shading Language является диалектом). Однако ваша функция может принимать параметр указателя, который ссылается на массив, если указатель находится в том же адресном пространстве, что и исходный буфер:

bool testFunction(uint num_vertex_B, device float3 *Vertex_B)
{
}
...