Ниже я опубликовал некоторый код, который я использую, чтобы попытаться понять, что такое CUDA. Прежде чем кто-нибудь скажет что-нибудь, что я знаю, это крайне неэффективный способ найти простые числа, я просто хочу, чтобы что-то проверяло параллелизм. К сожалению, когда я запускаю это, я получаю сообщение об ошибке: это Unhandled exception at at 0x76FCC41F in Thrust_2.exe: Microsoft C++ exception: thrust::system::system_error at memory location 0x0022F500.
Если я переключу device_vector
на host_vector
в функцию doTest, я больше не получаю ошибку, и программа работает безупречно. Почему это происходит и как я могу заставить его использовать device_vector без сбоев? Я бы хотел сделать то же самое параллельно. Также вся программа работает по назначению с помощью host_vector.
PS:
Я использую VS2012
Cuda: V5.5
Графический процессор: geforce gt 540M
Thrust: Получил cuda.
Заранее спасибо!
struct prime{
__host__ __device__
void operator()(long& x){
bool result = true;
long stop = ceil(sqrt((float)x));
if(x%2!=0){
for(int i = 3;i<stop;i+=2){
if(x%i==0){
result = false;
break;
};
}
}else{
result = false;
}
if(!result)
x = -1;
}
};
void doTest(long gen){
using namespace thrust;
device_vector<long> tNum(gen);
sequence(tNum.begin(),tNum.end()); // fails here when using a device_vector
}
int main(){
doTest(1000);
return 0;
}
Проблема в том, что у меня были неправильные аргументы компилятора, теперь я чувствую себя глупо сейчас...
Я составлял 1.0, я переключил его на 2.0 и теперь его работаю.
Это проблема:
void operator()(long& x){
bool result = true;
long stop = ceil(sqrt(x));
И на самом деле вы должны получать предупреждающее сообщение от компилятора об этом.
Функция sqrt
доступная в коде устройства, доступна только для float
и double
аргументов. Ваш аргумент long
. Это означает, что компилятор попытается использовать версию библиотеки sqrt
для хост-библиотеки, которая не будет работать в коде устройства. Когда вы создаете вектор в качестве вектора-хозяина, это не проблема, так как функтор запускается в главном коде. Однако, когда вы переключаетесь на вектор устройства, функтор (работает на устройстве) сбой в этой точке и бросает ошибку тяги.
В качестве простого теста вы можете изменить его на:
long stop = ceil(sqrt((float)x));
и посмотреть, устраняет ли он крах. Будь или не отлитый из long
, чтобы float
действителен для вашего кода то, что вам придется решать.
doTest
не использует ваш функторprime()
. Это твое намерение? Вы предлагаете, чтобы ваша функцияdoTest
потерпела неудачу, как написано? Или ошибка происходит в какой-то другой части кода (возможно, она использует функторprime()
)?