Поведението на OpenCL кода е различно за картите AMD спрямо NVIDIA

Имам константа в горната част на моя код...

__constant uint uintmaxx =  (uint)(  (((ulong)1)<<32) - 1 );

Той се компилира добре на AMD и NVIDIA OpenCL компилатори... след това се изпълнява.

(правилно) на ATI карти, връща... 4294967295 или (всички 32 бита = 1)

(грешно) на NVIDIA карти, връща... 2147483648 или (само 32-ри бит = 1)

Опитах също -1 + 1‹‹32 и работи на ATI, но не и на NVIDIA.

Какво дава? Просто пропускам нещо?

Докато съм на темата за разликите в компилатора на OpenCL, някой знае ли добър ресурс, който изброява разликите в компилатора между AMD и NVIDIA?


person extracrispy    schedule 07.11.2013    source източник


Отговори (2)


OpenCL вече удобно предоставя това за вас. Можете да използвате предварително дефинирания UINT_MAX в кода на ядрото си и реализацията ще гарантира, че съдържа правилната стойност.

Но също така няма нищо лошо в метода, който използвате. Спецификацията гарантира, че uint е 32 бита, а ulong 64 бита, ints са допълващи се двойки и всичко, което не е изрично споменато, работи точно както е написано в спецификацията на C99.

Дори само това трябва да работи и да ви даде правилния резултат: uint uintmaxx = -1;

Изглежда, че NVidia просто има повреден компилатор, ако не, наистина се надявам да бъда коригиран по проблема. Наистина странната част е, че как, за бога, 32-ият бит е 1? Преместването наляво с 32 премества оригиналния бит на 33-то място. И така, какво, за бога, поставя малко на 32-ро място? Единственото нещо, което имам в предвид е, че те изобщо не зачитат подреждането на оператори и трансформират формулата в (ulong)1 ‹‹ (32-1) или нещо подобно.

Вероятно трябва да подадете доклад за грешка. Но за да бъда откровен, като се има предвид, че те мразят OpenCL толкова, колкото Microsoft мрази OpenGL, ако не дори повече, не бих очаквал бързо време за реакция.

person sharpneli    schedule 07.11.2013
comment
Благодаря. Трябваше просто да използвам дефиницията или -1. Не се замислих и накрая ме ухапа. - person extracrispy; 07.11.2013

Напълно съм съгласен с отговора на @sharpneli. Но просто опитайте това:

__constant uint uintmaxx = -1;

И както каза Sharpneli, използвайте макроса UINT_MAX, това е по-безопасният начин.

person DarkZeros    schedule 07.11.2013