OverlayComposer::~OverlayComposer() { deInitOpenGLES(); deInitEGL(); sem_destroy(&cmdSem); sem_destroy(&doneSem); sem_destroy(&displaySem); }
/*!**************************************************************************** @Function releaseView @Description Code in releaseView() will be called when the application quits or before a change in the rendering context. ******************************************************************************/ void releaseView() { deInitEGL(); #if defined XORG_BUILD deInitX(); #endif // Frees the OpenGL handles for the program and the 2 shaders glDeleteProgram(program); glDeleteShader(ver_shader); glDeleteShader(frag_shader); }
int initEGL(int n_buf) { #ifdef GLES_20 EGLint context_attr[] = {EGL_CONTEXT_CLIENT_VERSION, 2, EGL_NONE}; #else typedef NativeDisplayType EGLNativeDisplayType; typedef NativeWindowType EGLNativeWindowType; #endif EGLint disp_w, disp_h; EGLNativeDisplayType disp_type; EGLNativeWindowType window; EGLConfig cfgs[2]; EGLint n_cfgs; EGLint egl_attr[] = { EGL_BUFFER_SIZE, EGL_DONT_CARE, EGL_RED_SIZE, 8, EGL_GREEN_SIZE, 8, EGL_BLUE_SIZE, 8, EGL_DEPTH_SIZE, 8, #ifdef GLES_20 EGL_RENDERABLE_TYPE, EGL_OPENGL_ES2_BIT, #endif EGL_NONE }; #ifdef X11 if (initX11(&disp_w, &disp_h)) return -1; disp_type = (EGLNativeDisplayType)x11Display; window = (EGLNativeWindowType)x11Window; #else if (get_disp_resolution(&disp_w, &disp_h)) { printf("ERROR: get display resolution failed\n"); return -1; } printf("\n\nliuxu, 04/21/2014, get_disp_resolution, disp_w=%d, disp_h=%d\n\n", disp_w, disp_h); disp_type = (EGLNativeDisplayType)EGL_DEFAULT_DISPLAY; window = 0; #endif dpy = eglGetDisplay(disp_type); if (eglInitialize(dpy, NULL, NULL) != EGL_TRUE) { print_err("eglInitialize"); return -1; } if (eglGetConfigs(dpy, cfgs, 2, &n_cfgs) != EGL_TRUE) { print_err("eglGetConfigs"); goto cleanup; } if (eglChooseConfig(dpy, egl_attr, cfgs, 2, &n_cfgs) != EGL_TRUE) { print_err("eglChooseConfig"); goto cleanup; } surface = eglCreateWindowSurface(dpy, cfgs[0], window, NULL); if (surface == EGL_NO_SURFACE) { print_err("eglCreateWindowSurface"); goto cleanup; } #ifdef GLES_20 context = eglCreateContext(dpy, cfgs[0], EGL_NO_CONTEXT, context_attr); #else context = eglCreateContext(dpy, cfgs[0], EGL_NO_CONTEXT, NULL); #endif if (context == EGL_NO_CONTEXT) { print_err("eglCreateContext"); goto cleanup; } if (eglMakeCurrent(dpy, surface, surface, context) != EGL_TRUE) { print_err("eglMakeCurrent"); goto cleanup; } /* 0 - do not sync with video frame */ if (profiling == TRUE) { if (eglSwapInterval(dpy, 0) != EGL_TRUE) { print_err("eglSwapInterval"); goto cleanup; } } #ifndef GLES_20 glShadeModel(GL_FLAT); glTexParameterf(GL_TEXTURE_STREAM_IMG, GL_TEXTURE_MIN_FILTER, GL_NEAREST); glTexParameterf(GL_TEXTURE_STREAM_IMG, GL_TEXTURE_MAG_FILTER, GL_NEAREST); glFrontFace(GL_CW); glCullFace(GL_FRONT); glEnable(GL_CULL_FACE); glEnable(GL_NORMALIZE); glMatrixMode(GL_PROJECTION); glLoadIdentity(); glOrthof(-CUBE_V_LEN * disp_w / disp_h, CUBE_V_LEN * disp_w / disp_h, -CUBE_V_LEN, CUBE_V_LEN, -CUBE_V_LEN * 2, CUBE_V_LEN * 2); glMatrixMode(GL_MODELVIEW); glLoadIdentity(); #endif return 0; cleanup: deInitEGL(n_buf); #ifdef X11 deInitX11(); #endif return -1; }
int initEGL(int *surf_w, int *surf_h, int profile) { EGLint context_attr[] = {EGL_CONTEXT_CLIENT_VERSION, 2, EGL_NONE}; // typedef NativeDisplayType EGLNativeDisplayType; // typedef NativeWindowType EGLNativeWindowType; EGLint disp_w, disp_h; EGLNativeDisplayType disp_type; EGLNativeWindowType window; EGLConfig cfgs[2]; EGLint n_cfgs; EGLint egl_attr[] = { EGL_BUFFER_SIZE, EGL_DONT_CARE, #if 0 EGL_RED_SIZE, 8, EGL_GREEN_SIZE, 8, EGL_BLUE_SIZE, 8, EGL_DEPTH_SIZE, 8, #endif EGL_RENDERABLE_TYPE, EGL_OPENGL_ES2_BIT, EGL_NONE }; if (get_disp_resolution(&disp_w, &disp_h)) { printf("ERROR: get display resolution failed\n"); return -1; } disp_type = (EGLNativeDisplayType)EGL_DEFAULT_DISPLAY; window = 0; dpy = eglGetDisplay(disp_type); if (eglInitialize(dpy, NULL, NULL) != EGL_TRUE) { print_err("eglInitialize"); return -1; } if (eglGetConfigs(dpy, cfgs, 2, &n_cfgs) != EGL_TRUE) { print_err("eglGetConfigs"); goto cleanup; } if (eglChooseConfig(dpy, egl_attr, cfgs, 2, &n_cfgs) != EGL_TRUE) { print_err("eglChooseConfig"); goto cleanup; } surface = eglCreateWindowSurface(dpy, cfgs[0], window, NULL); if (surface == EGL_NO_SURFACE) { print_err("eglCreateWindowSurface"); goto cleanup; } if (surf_w && surf_h) { *surf_w = disp_w; *surf_h = disp_h; } context = eglCreateContext(dpy, cfgs[0], EGL_NO_CONTEXT, context_attr); if (context == EGL_NO_CONTEXT) { print_err("eglCreateContext"); goto cleanup; } if (eglMakeCurrent(dpy, surface, surface, context) != EGL_TRUE) { print_err("eglMakeCurrent"); goto cleanup; } /* do not sync with video frame if profile enabled */ if (profile == 1) { if (eglSwapInterval(dpy, 0) != EGL_TRUE) { print_err("eglSwapInterval"); goto cleanup; } } return 0; cleanup: deInitEGL(); return -1; }
// Main function with event loop int main(void) { int n = -1; int count = 0; static bc_buf_ptr_t buf_pa; int dev_fd; unsigned long chunkSize; printf("Initializing egl..\n\n"); if( 0 == initEGL(0)) //No profiling { printf("EGL init failed"); goto exitNone; } //Also initialise the pipes n = initPipes(&initAttrib); if(n) { goto exitPipes; } //Initialise CMEM allocator - TODO check err status mem_cmem_init(); //Allocate mem chunkSize = initAttrib.widthPixels* initAttrib.heightPixels* initAttrib.bytesPerPixel* initAttrib.numBuffers; if(mem_cmem_alloc( chunkSize, &virtualAddress, &physicalAddress )) {goto exitCMEMInit;} paArray = (unsigned long*)malloc(initAttrib.numBuffers * sizeof(unsigned long)); freeArray = (unsigned long*)malloc(initAttrib.numBuffers * sizeof(unsigned long)); if(!paArray || !freeArray) {goto exitCMEMAlloc;} for(count = 0; count < initAttrib.numBuffers; count++) { paArray[count] = physicalAddress + count*(chunkSize/initAttrib.numBuffers); freeArray[count] = 0; } //TODO - give the allocated buffers back to requestor via answer //write_init_buffer_pipe(); init_view(); //Loop reading new data and rendering, till something happens //TODO - exit cleanly using last msg while(read_pipe() != -1) { render(bcbuf.index); //TODO - clean up message passing //if( write_pipe() != sizeof(GstBufferClassBuffer *)) { printf("Error Writing into Init Queue\n"); //TODO - try again n times ? break; } } exit: release_view(); deInitEGL(); exitCMEMAlloc: mem_cmem_free( virtualAddress); exitPipes: if(paArray) free(paArray); if(freeArray) free(freeArray); deinit_pipes(); exitCMEMInit: mem_cmem_deinit(); exitNone: return 0; }
int main(int argc, char *argv[]) { int bcfd = -1; char bcdev_name[] = "/dev/bccatX"; BCIO_package ioctl_var; bc_buf_params_t buf_param; bc_buf_ptr_t buf_pa; unsigned long buf_paddr[MAX_BUFFERS]; char *buf_vaddr[MAX_BUFFERS] = { MAP_FAILED }; char *frame = NULL; int buf_size = 0; int c, idx, ret = -1; char opts[] = "c:pw:t:b:h"; int ii; int frame_w, frame_h; int min_w = 0, min_h = 0;; int cp_offset = 0; struct timeval tvp, tv, tv0 = {0,0}; unsigned long tdiff = 0; unsigned long fcount = 0; for (;;) { c = getopt_long(argc, argv, opts, (void *)NULL, &idx); if (-1 == c) break; switch (c) { case 0: break; case 'b': bcdev_id = atoi(optarg) % 10; break; case 'c': cap_dev = optarg; printf("INFO: capture device is %s\n", cap_dev); break; case 'p': profiling = TRUE; printf("INFO: profiling enabled\n"); break; case 'w': min_w = atoi(optarg); break; case 't': min_h = atoi(optarg); break; default: usage(argv[0]); return 0; } } signal(SIGINT, signalHandler); if (frame_init(&buf_param)) return -1; bcdev_name[strlen(bcdev_name)-1] = '0' + bcdev_id; if ((bcfd = open(bcdev_name, O_RDWR|O_NDELAY)) == -1) { printf("ERROR: open %s failed\n", bcdev_name); goto err_ret; } frame_w = buf_param.width; frame_h = buf_param.height; if (min_w > 0 && !(min_w % 8)) buf_param.width = min_w; if (min_h > 0) buf_param.height = min_h; if (ioctl(bcfd, BCIOREQ_BUFFERS, &buf_param) != 0) { printf("ERROR: BCIOREQ_BUFFERS failed\n"); goto err_ret; } if (ioctl(bcfd, BCIOGET_BUFFERCOUNT, &ioctl_var) != 0) { goto err_ret; } if (ioctl_var.output == 0) { printf("ERROR: no texture buffer available\n"); goto err_ret; } /* for BC_MEMORY_USERPTR, BCIOSET_BUFFERPHYADDR must be called * before init IMG_extensions in initTexExt()*/ if (buf_param.type == BC_MEMORY_USERPTR) { for (idx = 0; idx < buf_param.count; idx++) { while ((frame = frame_get(&buf_pa)) == NULL) { } if (frame == (char *)-1) goto err_ret; if (ioctl(bcfd, BCIOSET_BUFFERPHYADDR, &buf_pa) != 0) { frame_restore(frame); printf("ERROR: BCIOSET_BUFFERADDR[%d]: failed (0x%lx)\n", buf_pa.index, buf_pa.pa); goto err_ret; } if (frame_restore(frame)) goto err_ret; } } if (initEGL(buf_param.count)) { printf("ERROR: init EGL failed\n"); goto err_ret; } if ((ret = initTexExt(bcdev_id, &buf_info)) < 0) { printf("ERROR: initTexExt() failed [%d]\n", ret); goto err_ret; } if (buf_info.n > MAX_BUFFERS) { printf("ERROR: number of texture buffer exceeds the limit\n"); goto err_ret; } /*FIXME calc stride instead of 2*/ buf_size = buf_info.w * buf_info.h * 2; min_w = buf_info.w < frame_w ? buf_info.w : frame_w; min_h = buf_info.h < frame_h ? buf_info.h : frame_h; if (buf_info.h > frame_h) cp_offset = (buf_info.h - frame_h) * buf_info.w; if (buf_info.w > frame_w) cp_offset += buf_info.w - frame_w; if (buf_param.type == BC_MEMORY_MMAP) { for (idx = 0; idx < buf_info.n; idx++) { ioctl_var.input = idx; if (ioctl(bcfd, BCIOGET_BUFFERPHYADDR, &ioctl_var) != 0) { printf("ERROR: BCIOGET_BUFFERADDR failed\n"); goto err_ret; } buf_paddr[idx] = ioctl_var.output; buf_vaddr[idx] = (char *)mmap(NULL, buf_size, PROT_READ | PROT_WRITE, MAP_SHARED, bcfd, buf_paddr[idx]); if (buf_vaddr[idx] == MAP_FAILED) { printf("ERROR: mmap failed\n"); goto err_ret; } } } ret = 0; idx = 0; if (profiling == TRUE) { gettimeofday(&tvp, NULL); tv0 = tvp; } while (!gQuit) { #ifdef USE_SOLID_PATTERN usleep(1000 * 1000); #endif frame = frame_get(&buf_pa); if (frame == (char *) -1) break; if (frame) { if (buf_param.type == BC_MEMORY_MMAP) { for (ii = 0; ii < min_h; ii++) /*FIXME calc stride instead of 2*/ memcpy(buf_vaddr[idx] + buf_info.w * 2 * ii + cp_offset, frame + frame_w * 2 * ii, min_w * 2); } else /*buf_param.type == BC_MEMORY_USERPTR*/ idx = buf_pa.index; } drawCube(idx); if (frame_restore(frame)) break; #ifdef X11 if (doX11Events()) gQuit = TRUE; #endif idx = (idx + 1) % buf_info.n; if (profiling == FALSE) continue; gettimeofday(&tv, NULL); fcount++; if (!(fcount % 60)) { tdiff = (unsigned long)(tv.tv_sec*1000 + tv.tv_usec/1000 - tvp.tv_sec*1000 - tvp.tv_usec/1000); if (tdiff < 1800) /*print fps every 2 sec*/ continue; fprintf(stderr, "\rAvg FPS: %ld", fcount / (tv.tv_sec - tv0.tv_sec)); tvp = tv; } } printf("\n"); err_ret: if (buf_param.type == BC_MEMORY_MMAP) { for (idx = 0; idx < buf_info.n; idx++) { if (buf_vaddr[idx] != MAP_FAILED) munmap(buf_vaddr[idx], buf_size); } } if (bcfd > -1) close(bcfd); deInitEGL(buf_info.n); #ifdef X11 deInitX11(); #endif frame_cleanup(); printf("done\n"); return ret; }