The realization of the picture rotation of OpenCL

Source: Internet
Author: User

    • Principle
    • Early
    • Kernel
    • Configuration file
    • Effect
    • Reference

What you do here is to use OpenCL to rotate the image 90 degrees, which is a relatively entry-level program. Hope to help you, look at the code is familiar with.

Principle

Image rotation refers to the definition of the image around a point in a counterclockwise or clockwise rotation of a certain angle, usually refers to the center of the image around the direction of rotation counterclockwise. Assuming that the upper-left corner of the image is (Ieft, top), and the lower-right corner is (r, bottom), any point on the image (x0, y0) rotates the ycenter angle counterclockwise around its center (xcenter, Angle), and the new coordinate position (x′, y′) is calculated as:

Early

Need to process the image, then introduce a library here to everyone: freeimage.
Not familiar to see: please click here.
Methods for using this library: (common method, very effective)

    • Property->c/c++-> General, additional Include Directories: path to Add. h.

    • Additional Library Directories: Add Lib Path, general, Linker.

    • Additional dependencies, input, linker: Add the required Lib name.

    • Put the DLL file under the EXE path.

Kernel
#pragma OPENCL EXTENSION cl_amd_printf:enable__kernelvoidImage_rotate (__globalUchar* Src_data, __globalUchar* Dest_data,//data in global memory    intWintH//image Dimensions    floatSintheta,floatCostheta)//rotation Parameters{//thread gets its index within index space    Const intIX = GET_GLOBAL_ID (0);Const intiy = get_global_id (1);intXC = w/2;intYC = h/2;intXpos = (IX-XC) *costheta-(IY-YC) *sintheta+xc;intYpos = (IX-XC) *sintheta + (IY-YC) *costheta+yc; if ((xpos>=0) && (xpos< W) && (ypos>=0) && (ypos< H))//bound Checking{dest_data[ypos*w+xpos]= Src_data[iy*w+ix]; }}

We compare this with the CPU serial processing can be obtained as follows:

//cpu Rotate an Image: Use the CPU to rotate the picturevoidCpu_rotate (unsigned Char* Inbuf,unsigned Char* Outbuf,intWintHfloatSintheta,floatCostheta) {intI, J;intXC = w/2;intYC = h/2; for(i =0; I < H; i++) { for(j=0; j< W; J + +) {intXpos = (J-XC) *costheta-(I-YC) *sintheta+xc;intYpos = (J-XC) *sintheta + (I-YC) *costheta+yc;if(xpos>=0&&ypos>=0&AMP;&AMP;XPOS&LT;W&AMP;&AMP;YPOS&LT;H) Outbuf[ypos*w + xpos] = Inbuf[i*w+j]; }    }}

After comparison we found that the OpenCL write kernel when the cycle is not, instead of giving global_id can be.

Configuration file

Here also involves a number of pictures of the operation, see the use of freeimage.

#include "stdafx.h"#include <CL/cl.h>#include <stdio.h>#include <stdlib.h>#include <time.h>#include <iostream>#include <fstream>#include "gFreeImage.h"using namespace STD;#define NWITEMS 4#pragma comment (lib, "OpenCL.lib")#pragma comment (lib, "FreeImage.lib")//To read a text file into a string, which is actually to pass the running program to the slave machineintConvertToString (Const Char*filename,STD::string& s) {size_t size;Char* STR;STD:: FStream f (filename, (STD:: Fstream::in |STD:: Fstream::binary));if(F.is_open ())        {size_t fileSize; F.SEEKG (0,STD:: Fstream::end);        Size = FileSize = (size_t) f.tellg (); F.SEEKG (0,STD:: Fstream::beg); str =New Char[size+1];if(!STR) {F.close ();returnNULL;        } f.read (str, fileSize);        F.close (); Str[size] =' + '; s = str;Delete[] str;return 0; }printf("error:failed to open file%s\n", filename);return 1;}//cpu Rotate an Image: Use the CPU to rotate the picturevoidCpu_rotate (unsigned Char* Inbuf,unsigned Char* Outbuf,intWintHfloatSintheta,floatCostheta) {intI, J;intXC = w/2;intYC = h/2; for(i =0; I < H; i++) { for(j=0; j< W; J + +) {intXpos = (J-XC) *costheta-(I-YC) *sintheta+xc;intYpos = (J-XC) *sintheta + (I-YC) *costheta+yc;if(xpos>=0&&ypos>=0&AMP;&AMP;XPOS&LT;W&AMP;&AMP;YPOS&LT;H) Outbuf[ypos*w + xpos] = Inbuf[i*w+j]; }    }}intMainintargcChar* argv[]) {//Loading images    unsigned Char*src_image=0;unsigned Char*cpu_image=0;intW, H; Gfreeimage img;if(!img. Loadimagegrey ("Lenna.jpg"))    {printf("Loading lenna.jpg failed \ n");Exit(0); }ElseSrc_image = Img.getimagedatagrey (W, H);    size_t mem_size = w*h; Cpu_image = (unsigned Char*)malloc(mem_size);    Cl_uint status; CL_PLATFORM_ID platform;//Create platform ObjectStatus = Clgetplatformids (1, &platform, NULL); CL_DEVICE_ID device;//Create GPU devicesClgetdeviceids (Platform, Cl_device_type_gpu,1, &device, NULL);//Create ContextCl_context context = Clcreatecontext (NULL,1, &device, NULL, NULL, or NULL);//create command queueCl_command_queueQueue= Clcreatecommandqueue (context, device, cl_queue_profiling_enable, NULL);//Create three OpenCL memory objects and put the contents of the BUF1 through an implicit copy    //Copy to CLBUF1,BUF2 content copied to Clbuf2 by means of a copy displayCl_mem d_ip = Clcreatebuffer (Context, cl_mem_read_only, mem_size, NULL, NULL);    Cl_mem D_op = Clcreatebuffer (Context, cl_mem_write_only, mem_size, NULL, NULL); Status = Clenqueuewritebuffer (Queue, D_ip, Cl_true,0, Mem_size, (void*) Src_image,0, NULL, NULL);Const Char* filename ="rotate.cl";STD::stringSOURCESTR; Status = ConvertToString (filename, sourcestr);Const Char* Source = Sourcestr.c_str (); size_t sourcesize[] = {strlen(source)};//Create program ObjectCl_program program = Clcreateprogramwithsource (Context,1, &source, Sourcesize, NULL);//Compile program objectStatus = Clbuildprogram (program,1, &device, NULL, NULL, or NULL);if(Status! =0)    {printf("Clbuild failed:%d\n", status);Chartbuf[0x10000]; Clgetprogrambuildinfo (program, device, Cl_program_build_log,0x10000, Tbuf, NULL);printf("\n%s\n", TBUF);return-1; }//Create kernel object    //use the "image_rotate" function as the kernel    //Create kernel objectCl_kernel kernel = Clcreatekernel (program,"Image_rotate", NULL);//Set kernel parameters    floatSintheta =1, Costheta =0; Clsetkernelarg (Kernel,0,sizeof(Cl_mem), (void*) &d_ip); Clsetkernelarg (Kernel,1,sizeof(Cl_mem), (void*) &d_op); Clsetkernelarg (Kernel,2,sizeof(Cl_int), (void*) &w); Clsetkernelarg (Kernel,3,sizeof(Cl_int), (void*) &h); Clsetkernelarg (Kernel,4,sizeof(Cl_float), (void*) &sintheta); Clsetkernelarg (Kernel,5,sizeof(Cl_float), (void*) &costheta);//set Local and global workgroup sizessize_t localws[2] = { -, -} ; size_t globalws[2] = {W, H};//assume divisible byCl_event ev;//Execute kernelClenqueuendrangekernel (Queue, Kernel,2,0, GLOBALWS, LOCALWS,0, NULL, &ev); ClFinish (Queue);//Calculate kerenl Execution TimeCl_ulong StartTime, EndTime; Clgeteventprofilinginfo (EV, Cl_profiling_command_start,sizeof(Cl_ulong), &starttime, NULL); Clgeteventprofilinginfo (EV, Cl_profiling_command_end,sizeof(Cl_ulong), &endtime, NULL); Cl_ulong kernelexectimens = endtime-starttime;printf("Kernal exec time:%8.6f ms\n", kernelexectimens*1e-6);//Data copy back to host memory    //Copy results from device to host    unsigned Char*op_data=0; Op_data = (Cl_uchar *) Clenqueuemapbuffer (Queue, D_op, Cl_true, Cl_map_read,0, Mem_size,0, NULL, NULL, NULL);intI Cpu_rotate (Src_image,cpu_image, W, H,1,0); for(i =0; i < mem_size;    i++) {src_image[i] =cpu_image[i]; } img. SaveImage ("Cpu_lenna_rotate.jpg"); for(i =0; i < mem_size;    i++) {src_image[i] =op_data[i]; } img. SaveImage ("Lenna_rotate.jpg");if(Cpu_image) Free(Cpu_image);//Delete OpenCL resource objectClreleasememobject (D_IP);    Clreleasememobject (D_OP);    Clreleaseprogram (program); Clreleasecommandqueue (Queue); Clreleasecontext (context);return 0;}
Effect

Initial Picture:

After processing with OpenCL: A grayscale image is used.

After processing with the CPU: Grayscale image is used.

Reference

Freeimage Download, please click here.

Please click here for the reference code.

The realization of the picture rotation of OpenCL

Related Article

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.