Frage

Ist es möglich, benutzerdefinierte Typen in OpenCL-Kernel wie gmp Typen zu verwenden (mpz_t, mpq_t, ...)?

Um so etwas wie dieses haben (dieser Kernel bauen nicht nur wegen #include <gmp.h>):

#include <gmp.h>
__kernel square(
   __global mpz_t* input,
   __global mpz_t number,
   __global int* output,
   const unsigned int count)
{
   int i = get_global_id(0);
   if(i < count)
       output[i] = mpz_divisible_p(number,input[i]);
}

Vielleicht durch verschiedene Argumente an den vierten Parameter hinzugefügt ( Optionen ) von clBuildProgram?

Oder OpenCL bereits Typen haben, die verarbeiten kann groß Zahlen?

War es hilfreich?

Lösung

Sie können benutzerdefinierte Typen verwenden, aber alles im Kernel benötigt verwendet speziell für OpenCL geschrieben werden. Sehen Sie sich diese Webseite heraus vielleicht wie größere Präzision Zahlen zu implementieren: FP128

Edit:. NVIDIAs CUDA SDK eine komplexe Zahl Datentyp hat, ist es nicht ideal ist, aber können Sie einige Ideen geben, wie sie darüber gehen, sollten OpenCL ähnlich sein

Andere Tipps

Im Allgemeinen können Sie alle Arten in einem OpenCL-Programm verwenden. Aber da die Einfuhren nicht funktionieren, müssen Sie neu definieren sie innerhalb des gleichen Programms. Zum Beispiel:

typedef char my_char[8];

typedef struct tag_my_struct
{
    long int        id;
    my_char         chars[2];
    int             numerics[4]
    float           decimals[4];
} my_struct;

__kernel void foo(__global my_struct * input,
                  __global int * output)
{
    int gid = get_global_id(0);
    output[gid] = input[gid].numerics[3]== 2 ? 1 : 0;
}

Sie müssen jedoch offensichtlich die Definitionen halten innerhalb und außerhalb von OpenCL gleich. Auch sicherstellen, dass die Art die gleiche Größe hat sowohl auf dem Gerät und dem Host (unter Verwendung eines sizeof(my_struct) sollte es tun). In einigen Fällen hatte ich die Definitionen anzupassen, passende Größen zu haben.

Ich habe VHristov Antwort und Dietr Kommentar zu meinem Arbeits zu bekommen. Dieser Code funktioniert für mich in OpenCL 1.2

kernel

typedef struct tag_my_struct{
  int a;
  char b;
}my_struct;

__kernel void myKernel(__global my_struct *myStruct)
{
    int gid = get_global_id(0);
    (myStruct+gid)->a = gid;
    (myStruct+gid)->b = gid + 1;
}

Host

typedef struct tag_my_struct{
  cl_int a;
  cl_char b;
}my_struct;

void runCode() 
{
    cl_int status = 0;
    my_struct* ms = new my_struct[5];

    cl_mem mem = clCreateBuffer(*context, 0, sizeof(my_struct)*5, NULL, &status);
    clEnqueueWriteBuffer(*queue, mem, CL_TRUE, 0, sizeof(my_struct)*5, &ms, 0, NULL, NULL);

    status = clSetKernelArg(*kernel, 0, sizeof(ms), &mem);

    size_t global[] = {5};
    status = clEnqueueNDRangeKernel(*queue, *kernel, 1, NULL, global, NULL, 0, NULL, NULL);

    status = clEnqueueReadBuffer(*queue, mem, CL_TRUE, 0, sizeof(my_struct)*5, ms, 0, NULL, NULL);

    for(int i = 0; i < 5; i++)
        cout << (ms+i)->a << " " << (ms+i)->b << endl;
}

Ausgang

0 ☺

1 ☻

2 ♥

3 ♦

4 ♣

Wenn Sie die Header-Dateien in den Kernel-Datei aufnehmen möchten, können Sie fügen Sie die -l dir als Argument an clBuildProgram, wobei dir ist das Verzeichnis mit den Header-Dateien .

Weitere Erklärung hier: Header OpenCL .cl Datei enthalten

Quelle: http: // www .khronos.org / registry / cl / sdk / 1.0 / docs / man / xhtml / clBuildProgram.html

Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top