OpenCL做並行濾波

2021-07-23 17:34:22 字數 4736 閱讀 5048

本實驗主要進行opencl一維訊號的濾波;主要思路是以離散訊號的序列點作為目標,乙個工作項負責乙個訊號點的計算;這樣做的好處是方便,相對於序列實現獲得相當大的效能提公升;但是每個工作項負載不均衡。

host.c
#include

#include

#include

#include

#pragma warning( disable : 4996 )

#define mixsize 8192*65

int main()

error = clgetdeviceids(platforms, cl_device_type_gpu, 1, &devices, null);

if (error != 0)

//建立上下文

context = clcreatecontext(null,1,&devices,null,null,&error);

if (error != 0)

//建立程式

program_handle = fopen("kernel.cl","rb");

if (program_handle == null)

fseek(program_handle,0,seek_end);

program_size = ftell(program_handle);

rewind(program_handle);

program_buffer = (char *)malloc(program_size+1);

program_buffer[program_size] = '\0';

error=fread(program_buffer,sizeof(char),program_size,program_handle);

if (error == 0)

fclose(program_handle);

program = clcreateprogramwithsource(context,1,(const

char **)&program_buffer,&program_size,&error);

if (error < 0)

//編譯程式

error = clbuildprogram(program,1,&devices,null,null,null);

if (error < 0)

//建立命令佇列

queue = clcreatecommandqueue(context, devices, cl_queue_profiling_enable, &error);

if (error < 0)

//建立核心

kernel = clcreatekernel(program,kernel_name,&error);

if (kernel==null)

//建立快取物件

cl_mem memobject1 = clcreatebuffer(context,cl_mem_read_only ,

sizeof(float) * 256,null,&error);

if (error < 0)

cl_mem memobject2 = clcreatebuffer(context, cl_mem_read_only ,

sizeof(float) * mixsize / 65, null, &error);

if (error < 0)

cl_mem memobject3 = clcreatebuffer(context, cl_mem_write_only ,

sizeof(float) * mixsize/65, null, &error);

if (error < 0)

//設定核心引數

error = clsetkernelarg(kernel,0,sizeof(cl_mem),&memobject1);

error |= clsetkernelarg(kernel, 1, sizeof(cl_mem), &memobject2);

error |= clsetkernelarg(kernel, 2, sizeof(cl_mem), &memobject3);

if (error != cl_success)

//初始化引數

float* input1 = (float *)malloc(sizeof(float)* 256);

float* input2 = (float *)malloc(sizeof(float)* mixsize / 65);

float* result = (float *)malloc(sizeof(float)* mixsize / 65);

float *check = (float *)malloc(sizeof(float) * mixsize / 65);

memset(check, 0, sizeof(float) * mixsize / 65);

memset(input1, 1, sizeof(float) * 256);

memset(input2, 0, sizeof(float) * mixsize / 65);

memset(result, 0, sizeof(float) * mixsize / 65);

cl_event evt1;

cl_event evt2;

cl_event evt3;

float* tmp1 = (float *)malloc(sizeof(float)* mixsize);

float *tmp2 = (float *)malloc(sizeof(float) * mixsize / 65);

memset(tmp2, 0, sizeof(float) * mixsize / 65);

//資料讀入

//採用隨機數函式產生輸入

//input2是65*8192

srand(1);

for (int j = 0; j < 8192; j++)

for (int j = 0; j < 256; j++)

//檢查運算結果

for (int j = 0; j < 8192; j++)

}else

}

}//資料寫入記憶體

error = clenqueuewritebuffer(queue, memobject1, cl_false, 0,

256 * sizeof(float), input1, 0, null, &evt1);

if (error != cl_success)

error = clenqueuewritebuffer(queue, memobject2, cl_false, 0,

mixsize * sizeof(float) / 65, input2, 1, &evt1, &evt2);

if (error != cl_success)

//配置工作項

size_t maxworkgroupsize = 0;

clgetdeviceinfo(devices, cl_device_max_work_group_size,

sizeof(maxworkgroupsize), &maxworkgroupsize, null);

size_t globalworksize = 8192;

size_t localworksize = maxworkgroupsize;

//執行核心

error = clenqueuendrangekernel(queue, kernel, 1, null, &globalworksize,

&localworksize, 1, &evt2, &evt3);

if (error != cl_success)

//讀取執行結果

error = clenqueuereadbuffer(queue,memobject3,cl_true,0,

mixsize*sizeof(float)/65,result,1,&evt3,null);

if (error != cl_success)

//顯示結果

for (int i = 0; i < mixsize/65; i++)

}printf("successed!\n");

clreleaseevent(evt1);

clreleaseevent(evt2);

clreleaseevent(evt3);

clreleaseprogram(program);

clreleasecontext(context);

clreleasecommandqueue(queue);

clreleasedevice(devices);

clreleasekernel(kernel);

getchar();

return

0;}

kernel.cl
//卷積

//假設有8192個資料

//全域性工作項8192

//卷積係數256

//輸入1為卷積係數

//輸入2為資料

__kernel void createbuffer(__global float *input1,

__global float *input2,

__global float *result)

}else

}}

並行程式設計OpenCL 矩陣相加

並行程式設計opencl 矩陣相加 1 host端 include include include include const int array size 1000 一 選擇opencl平台並建立乙個上下文 cl context createcontext 建立乙個opencl上下文環境 cl c...

OpenCL與異構平行計算

異構平行計算包含兩個子概念 異構和並行。1 異構是指異構平行計算需要同時處理多個不同架構的計算平台的問 題,比如目前主流的異構平行計算平台x86 gpu x86 fpga,以及目前正在研發中的arm power gpu。2 並行是指異構平行計算主要採用並行的程式設計方式,無論是x86處理器,還是ar...

OpenCL與異構平行計算

原文 異構平行計算包含兩個子概念 異構和並行。1 異構是指異構平行計算需要同時處理多個不同架構的計算平台的問 題,比如目前主流的異構平行計算平台x86 gpu x86 fpga,以及目前正在研發中的arm power gpu。2 並行是指異構平行計算主要採用並行的程式設計方式,無論是x86處理器,還...