clray
changeset 41:057b8575a1c1
- changed the membuffer into an imagebuffer for the non-GL/CL-interop case
- fixed the segfault
author | John Tsiombikas <nuclear@member.fsf.org> |
---|---|
date | Fri, 27 Aug 2010 20:39:55 +0100 |
parents | 1bcbb53b3505 |
children | 1169f3d04135 |
files | src/clray.cc src/ocl.cc src/ocl.h src/rt.cc |
diffstat | 4 files changed, 113 insertions(+), 11 deletions(-) [+] |
line diff
1.1 --- a/src/clray.cc Fri Aug 27 19:00:14 2010 +0100 1.2 +++ b/src/clray.cc Fri Aug 27 20:39:55 2010 +0100 1.3 @@ -135,13 +135,14 @@ 1.4 1.5 void cleanup() 1.6 { 1.7 - printf("destroying renderer...\n"); 1.8 + printf("destroying renderer ...\n"); 1.9 destroy_renderer(); 1.10 1.11 - printf("shutting down OpenCL...\n"); 1.12 + printf("shutting down OpenCL ...\n"); 1.13 destroy_opencl(); 1.14 1.15 - printf("done cleaning up\n"); 1.16 + printf("cleaning up OpenGL resources ...\n"); 1.17 + glDeleteTextures(1, &tex); 1.18 } 1.19 1.20 static Matrix4x4 mat, inv_mat, inv_trans;
2.1 --- a/src/ocl.cc Fri Aug 27 19:00:14 2010 +0100 2.2 +++ b/src/ocl.cc Fri Aug 27 20:39:55 2010 +0100 2.3 @@ -122,17 +122,63 @@ 2.4 } 2.5 2.6 CLMemBuffer *mbuf = new CLMemBuffer; 2.7 + mbuf->type = MEM_BUFFER; 2.8 mbuf->mem = mem; 2.9 mbuf->size = sz; 2.10 + mbuf->xsz = mbuf->ysz = 0; 2.11 mbuf->ptr = 0; 2.12 mbuf->tex = 0; 2.13 return mbuf; 2.14 } 2.15 2.16 -CLMemBuffer *create_mem_buffer(int rdwr, unsigned int tex) 2.17 +CLMemBuffer *create_image_buffer(int rdwr, int xsz, int ysz, const void *pixels) 2.18 { 2.19 - int err; 2.20 + int err, pitch; 2.21 cl_mem mem; 2.22 + cl_mem_flags flags = rdwr | CL_MEM_ALLOC_HOST_PTR; 2.23 + 2.24 + if(pixels) { 2.25 + flags |= CL_MEM_COPY_HOST_PTR; 2.26 + pitch = xsz * 4 * sizeof(float); 2.27 + } else { 2.28 + pitch = 0; 2.29 + } 2.30 + 2.31 + cl_image_format fmt = {CL_RGBA, CL_FLOAT}; 2.32 + 2.33 + if(!(mem = clCreateImage2D(ctx, flags, &fmt, xsz, ysz, pitch, (void*)pixels, &err))) { 2.34 + fprintf(stderr, "failed to create %dx%d image: %s\n", xsz, ysz, clstrerror(err)); 2.35 + return 0; 2.36 + } 2.37 + 2.38 + CLMemBuffer *mbuf = new CLMemBuffer; 2.39 + mbuf->type = IMAGE_BUFFER; 2.40 + mbuf->mem = mem; 2.41 + mbuf->size = ysz * pitch; 2.42 + mbuf->xsz = xsz; 2.43 + mbuf->ysz = ysz; 2.44 + mbuf->ptr = 0; 2.45 + mbuf->tex = 0; 2.46 + return mbuf; 2.47 +} 2.48 + 2.49 +CLMemBuffer *create_image_buffer(int rdwr, unsigned int tex) 2.50 +{ 2.51 + int err, xsz, ysz; 2.52 + cl_mem mem; 2.53 + 2.54 + glGetError(); // clear previous OpenGL errors 2.55 + 2.56 + glPushAttrib(GL_TEXTURE_BIT); 2.57 + glBindTexture(GL_TEXTURE_2D, tex); 2.58 + glGetTexLevelParameteriv(GL_TEXTURE_2D, 0, GL_TEXTURE_WIDTH, &xsz); 2.59 + glGetTexLevelParameteriv(GL_TEXTURE_2D, 0, GL_TEXTURE_HEIGHT, &ysz); 2.60 + glPopAttrib(); 2.61 + 2.62 + if(glGetError()) { 2.63 + fprintf(stderr, "create_image_buffer: GL error while retreiving texture parameters for texture %u\n", tex); 2.64 + return 0; 2.65 + } 2.66 2.67 if(!(mem = clCreateFromGLTexture2D(ctx, rdwr, GL_TEXTURE_2D, 0, tex, &err))) { 2.68 fprintf(stderr, "failed to create memory buffer from GL texture %u: %s\n", tex, clstrerror(err)); 2.69 @@ -140,10 +186,14 @@ 2.70 } 2.71 2.72 CLMemBuffer *mbuf = new CLMemBuffer; 2.73 + mbuf->type = IMAGE_BUFFER; 2.74 mbuf->mem = mem; 2.75 mbuf->size = 0; 2.76 + mbuf->xsz = xsz; 2.77 + mbuf->ysz = ysz; 2.78 mbuf->ptr = 0; 2.79 mbuf->tex = tex; 2.80 + 2.81 return mbuf; 2.82 } 2.83 2.84 @@ -166,10 +216,27 @@ 2.85 #endif 2.86 2.87 int err; 2.88 - mbuf->ptr = clEnqueueMapBuffer(cmdq, mbuf->mem, 1, rdwr, 0, mbuf->size, 0, 0, ev, &err); 2.89 - if(!mbuf->ptr) { 2.90 - fprintf(stderr, "failed to map buffer: %s\n", clstrerror(err)); 2.91 - return 0; 2.92 + 2.93 + if(mbuf->type == MEM_BUFFER) { 2.94 + mbuf->ptr = clEnqueueMapBuffer(cmdq, mbuf->mem, 1, rdwr, 0, mbuf->size, 0, 0, ev, &err); 2.95 + if(!mbuf->ptr) { 2.96 + fprintf(stderr, "failed to map buffer: %s\n", clstrerror(err)); 2.97 + return 0; 2.98 + } 2.99 + } else { 2.100 + assert(mbuf->type == IMAGE_BUFFER); 2.101 + 2.102 + size_t orig[] = {0, 0, 0}; 2.103 + size_t rgn[] = {mbuf->xsz, mbuf->ysz, 1}; 2.104 + size_t pitch; 2.105 + 2.106 + mbuf->ptr = clEnqueueMapImage(cmdq, mbuf->mem, 1, rdwr, orig, rgn, &pitch, 0, 0, 0, ev, &err); 2.107 + if(!mbuf->ptr) { 2.108 + fprintf(stderr, "failed to map image: %s\n", clstrerror(err)); 2.109 + return 0; 2.110 + } 2.111 + 2.112 + assert(pitch == mbuf->xsz * 4 * sizeof(float)); 2.113 } 2.114 return mbuf->ptr; 2.115 } 2.116 @@ -177,6 +244,7 @@ 2.117 void unmap_mem_buffer(CLMemBuffer *mbuf, cl_event *ev) 2.118 { 2.119 if(!mbuf || !mbuf->ptr) return; 2.120 + 2.121 clEnqueueUnmapMemObject(cmdq, mbuf->mem, mbuf->ptr, 0, 0, ev); 2.122 mbuf->ptr = 0; 2.123 } 2.124 @@ -351,12 +419,29 @@ 2.125 return true; 2.126 } 2.127 2.128 +bool CLProgram::set_arg_image(int idx, int rdwr, int xsz, int ysz, const void *pix) 2.129 +{ 2.130 + printf("create argument %d from %dx%d image\n", idx, xsz, ysz); 2.131 + CLMemBuffer *buf; 2.132 + 2.133 + if(!(buf = create_image_buffer(rdwr, xsz, ysz, pix))) { 2.134 + return false; 2.135 + } 2.136 + 2.137 + if((int)args.size() <= idx) { 2.138 + args.resize(idx + 1); 2.139 + } 2.140 + args[idx].type = ARGTYPE_MEM_BUF; 2.141 + args[idx].v.mbuf = buf; 2.142 + return true; 2.143 +} 2.144 + 2.145 bool CLProgram::set_arg_texture(int idx, int rdwr, unsigned int tex) 2.146 { 2.147 printf("create argument %d from texture %u\n", idx, tex); 2.148 CLMemBuffer *buf; 2.149 2.150 - if(!(buf = create_mem_buffer(rdwr, tex))) { 2.151 + if(!(buf = create_image_buffer(rdwr, tex))) { 2.152 return false; 2.153 } 2.154
3.1 --- a/src/ocl.h Fri Aug 27 19:00:14 2010 +0100 3.2 +++ b/src/ocl.h Fri Aug 27 20:39:55 2010 +0100 3.3 @@ -22,9 +22,17 @@ 3.4 MAP_RDWR = CL_MAP_READ | CL_MAP_WRITE 3.5 }; 3.6 3.7 +enum { 3.8 + MEM_BUFFER, 3.9 + IMAGE_BUFFER 3.10 +}; 3.11 + 3.12 struct CLMemBuffer { 3.13 + int type; 3.14 cl_mem mem; 3.15 + 3.16 size_t size; 3.17 + size_t xsz, ysz; 3.18 void *ptr; 3.19 unsigned int tex; 3.20 }; 3.21 @@ -34,7 +42,10 @@ 3.22 void destroy_opencl(); 3.23 3.24 CLMemBuffer *create_mem_buffer(int rdwr, size_t sz, const void *buf); 3.25 -CLMemBuffer *create_mem_buffer(int rdwr, unsigned int tex); 3.26 + 3.27 +CLMemBuffer *create_image_buffer(int rdwr, int xsz, int ysz, const void *pixels = 0); 3.28 +CLMemBuffer *create_image_buffer(int rdwr, unsigned int tex); 3.29 + 3.30 void destroy_mem_buffer(CLMemBuffer *mbuf); 3.31 3.32 void *map_mem_buffer(CLMemBuffer *mbuf, int rdwr, cl_event *ev = 0); 3.33 @@ -87,6 +98,7 @@ 3.34 bool set_argi(int arg, int val); 3.35 bool set_argf(int arg, float val); 3.36 bool set_arg_buffer(int arg, int rdwr, size_t sz, const void *buf = 0); 3.37 + bool set_arg_image(int arg, int rdwr, int xsz, int ysz, const void *pix = 0); 3.38 bool set_arg_texture(int arg, int rdwr, unsigned int tex); 3.39 CLMemBuffer *get_arg_buffer(int arg); 3.40 int get_num_args() const;
4.1 --- a/src/rt.cc Fri Aug 27 19:00:14 2010 +0100 4.2 +++ b/src/rt.cc Fri Aug 27 20:39:55 2010 +0100 4.3 @@ -94,7 +94,11 @@ 4.4 // XXX now we can actually destroy the original kdtree and keep only the GPU version 4.5 4.6 /* setup argument buffers */ 4.7 +#ifdef CLGL_INTEROP 4.8 prog->set_arg_texture(KARG_FRAMEBUFFER, ARG_WR, tex); 4.9 +#else 4.10 + prog->set_arg_image(KARG_FRAMEBUFFER, ARG_WR, xsz, ysz); 4.11 +#endif 4.12 prog->set_arg_buffer(KARG_RENDER_INFO, ARG_RD, sizeof rinf, &rinf); 4.13 prog->set_arg_buffer(KARG_FACES, ARG_RD, rinf.num_faces * sizeof(Face), faces); 4.14 prog->set_arg_buffer(KARG_MATLIB, ARG_RD, scn->get_num_materials() * sizeof(Material), scn->get_materials());