From: Patrick Porlan Date: Wed, 18 Sep 2013 13:14:49 +0000 (+0200) Subject: Initial revision of the VIGS module for OS X X-Git-Tag: Tizen_Studio_1.3_Release_p2.3.1~726^2~1 X-Git-Url: http://review.tizen.org/git/?a=commitdiff_plain;h=550a0dfce0c92623f50995b002329bc6af75b803;p=sdk%2Femulator%2Fqemu.git Initial revision of the VIGS module for OS X --- diff --git a/hw/vigs_gl_backend_agl.c b/hw/vigs_gl_backend_agl.c index 5d3d3fc90c..19a334c9ce 100644 --- a/hw/vigs_gl_backend_agl.c +++ b/hw/vigs_gl_backend_agl.c @@ -1,12 +1,272 @@ #include "vigs_gl_backend.h" #include "vigs_log.h" +#include +#include +#include +#include + + +#define LIBGL_IMAGE_NAME \ +"/System/Library/Frameworks/OpenGL.framework/Libraries/libGL.dylib" + +#define VIGS_GL_GET_PROC(func, proc_name) \ + do { \ + *(void**)(&gl_backend_agl->base.func) = dlsym(gl_backend_agl->handle, #proc_name); \ + if (!gl_backend_agl->base.func) { \ + VIGS_LOG_CRITICAL("Unable to load " #proc_name " symbol"); \ + goto fail; \ + } \ + } while (0) struct vigs_gl_backend_agl { struct vigs_gl_backend base; + + void *handle; + AGLContext context; + AGLPbuffer surface; + AGLPixelFormat pixfmt; }; + +static int vigs_gl_backend_agl_choose_config(struct vigs_gl_backend_agl *gl_backend_agl) +{ + const int attrib_list[] = { + AGL_RGBA, + AGL_ACCELERATED, + AGL_MINIMUM_POLICY, + AGL_BUFFER_SIZE, 32, + AGL_RED_SIZE, 8, + AGL_GREEN_SIZE, 8, + AGL_BLUE_SIZE, 8, + AGL_ALPHA_SIZE, 8, + AGL_DEPTH_SIZE, 24, + AGL_STENCIL_SIZE, 8, + AGL_NO_RECOVERY, + AGL_DOUBLEBUFFER, + AGL_PBUFFER, + AGL_NONE + }; + AGLPixelFormat pixfmt; + + /* Select first AGL pixel format matching our constraints */ + + pixfmt = aglChoosePixelFormat(NULL, 0, attrib_list); + + gl_backend_agl->pixfmt = pixfmt; + + return (pixfmt != NULL); +} + + +static bool vigs_gl_backend_agl_create_surface(struct vigs_gl_backend_agl *gl_backend_agl, + int config_id) +{ + gl_backend_agl->surface = NULL; + + aglCreatePBuffer(2048, 2048, GL_TEXTURE_2D, GL_RGBA, 0, &gl_backend_agl->surface); + + if (!gl_backend_agl->surface) { + VIGS_LOG_CRITICAL("aglCreatePBuffer failed"); + return false; + } + + return true; +} + + +static bool vigs_gl_backend_agl_create_context(struct vigs_gl_backend_agl *gl_backend_agl) +{ + gl_backend_agl->context = aglCreateContext(gl_backend_agl->pixfmt, NULL); + + if (!gl_backend_agl->context) { + VIGS_LOG_CRITICAL("aglCreateContext failed"); + return false; + } + + return true; +} + + +static void vigs_gl_backend_agl_destroy(struct vigs_backend *backend) +{ + struct vigs_gl_backend_agl *gl_backend_agl = (struct vigs_gl_backend_agl*)backend; + + vigs_gl_backend_cleanup(&gl_backend_agl->base); + + if (gl_backend_agl->surface) { + aglDestroyPBuffer(gl_backend_agl->surface); + } + + if (gl_backend_agl->context) { + aglDestroyContext(gl_backend_agl->context); + } + + if (gl_backend_agl->handle) { + dlclose(gl_backend_agl->handle); + } + + vigs_backend_cleanup(&gl_backend_agl->base.base); + + g_free(gl_backend_agl); + + VIGS_LOG_DEBUG("destroyed"); +} + + +static bool vigs_gl_backend_agl_has_current(struct vigs_gl_backend *gl_backend) +{ + return aglGetCurrentContext() != NULL; +} + + +static bool vigs_gl_backend_agl_make_current(struct vigs_gl_backend *gl_backend, + bool enable) +{ + struct vigs_gl_backend_agl *gl_backend_agl = + (struct vigs_gl_backend_agl*)gl_backend; + AGLPbuffer buf = NULL; + AGLContext context = gl_backend_agl->context; + + if (enable) { + buf = gl_backend_agl->surface; + + if (!buf) { + VIGS_LOG_CRITICAL("surface retrieval failed"); + return false; + } + + if (aglSetPBuffer(context, buf, 0, 0, 0) == GL_FALSE) { + VIGS_LOG_CRITICAL("aglSetPBuffer failed"); + return false; + } + + if (aglSetCurrentContext(context) == GL_FALSE) { + VIGS_LOG_CRITICAL("aglSetCurrentContext failed"); + aglSetPBuffer(context, NULL, 0, 0, 0); + return false; + } + } else { + if (aglSetCurrentContext(NULL) == GL_FALSE) { + VIGS_LOG_CRITICAL("aglSetCurrentContext(NULL) failed"); + return false; + } + } + + return true; +} + + struct vigs_backend *vigs_gl_backend_create(void *display) { + struct vigs_gl_backend_agl *gl_backend_agl; + int config_id; + + gl_backend_agl = g_malloc0(sizeof(*gl_backend_agl)); + + vigs_backend_init(&gl_backend_agl->base.base, + &gl_backend_agl->base.ws_info.base); + + gl_backend_agl->handle = dlopen(LIBGL_IMAGE_NAME, RTLD_GLOBAL); + + VIGS_GL_GET_PROC(GenTextures, glGenTextures); + VIGS_GL_GET_PROC(DeleteTextures, glDeleteTextures); + VIGS_GL_GET_PROC(BindTexture, glBindTexture); + VIGS_GL_GET_PROC(Begin, glBegin); + VIGS_GL_GET_PROC(End, glEnd); + VIGS_GL_GET_PROC(CullFace, glCullFace); + VIGS_GL_GET_PROC(TexParameterf, glTexParameterf); + VIGS_GL_GET_PROC(TexParameterfv, glTexParameterfv); + VIGS_GL_GET_PROC(TexParameteri, glTexParameteri); + VIGS_GL_GET_PROC(TexParameteriv, glTexParameteriv); + VIGS_GL_GET_PROC(TexImage2D, glTexImage2D); + VIGS_GL_GET_PROC(TexSubImage2D, glTexSubImage2D); + VIGS_GL_GET_PROC(TexEnvf, glTexEnvf); + VIGS_GL_GET_PROC(TexEnvfv, glTexEnvfv); + VIGS_GL_GET_PROC(TexEnvi, glTexEnvi); + VIGS_GL_GET_PROC(TexEnviv, glTexEnviv); + VIGS_GL_GET_PROC(Clear, glClear); + VIGS_GL_GET_PROC(ClearColor, glClearColor); + VIGS_GL_GET_PROC(Disable, glDisable); + VIGS_GL_GET_PROC(Enable, glEnable); + VIGS_GL_GET_PROC(Finish, glFinish); + VIGS_GL_GET_PROC(Flush, glFlush); + VIGS_GL_GET_PROC(PixelStorei, glPixelStorei); + VIGS_GL_GET_PROC(ReadPixels, glReadPixels); + VIGS_GL_GET_PROC(Viewport, glViewport); + VIGS_GL_GET_PROC(GenFramebuffers, glGenFramebuffersEXT); + VIGS_GL_GET_PROC(GenRenderbuffers, glGenRenderbuffersEXT); + VIGS_GL_GET_PROC(DeleteFramebuffers, glDeleteFramebuffersEXT); + VIGS_GL_GET_PROC(DeleteRenderbuffers, glDeleteRenderbuffersEXT); + VIGS_GL_GET_PROC(BindFramebuffer, glBindFramebufferEXT); + VIGS_GL_GET_PROC(BindRenderbuffer, glBindRenderbufferEXT); + VIGS_GL_GET_PROC(RenderbufferStorage, glRenderbufferStorageEXT); + VIGS_GL_GET_PROC(FramebufferRenderbuffer, glFramebufferRenderbufferEXT); + VIGS_GL_GET_PROC(FramebufferTexture2D, glFramebufferTexture2DEXT); + VIGS_GL_GET_PROC(GetIntegerv, glGetIntegerv); + VIGS_GL_GET_PROC(GetString, glGetString); + VIGS_GL_GET_PROC(LoadIdentity, glLoadIdentity); + VIGS_GL_GET_PROC(MatrixMode, glMatrixMode); + VIGS_GL_GET_PROC(Ortho, glOrtho); + VIGS_GL_GET_PROC(EnableClientState, glEnableClientState); + VIGS_GL_GET_PROC(DisableClientState, glDisableClientState); + VIGS_GL_GET_PROC(Color4f, glColor4f); + VIGS_GL_GET_PROC(TexCoordPointer, glTexCoordPointer); + VIGS_GL_GET_PROC(VertexPointer, glVertexPointer); + VIGS_GL_GET_PROC(DrawArrays, glDrawArrays); + VIGS_GL_GET_PROC(Color4ub, glColor4ub); + VIGS_GL_GET_PROC(WindowPos2f, glWindowPos2f); + VIGS_GL_GET_PROC(PixelZoom, glPixelZoom); + VIGS_GL_GET_PROC(DrawPixels, glDrawPixels); + VIGS_GL_GET_PROC(BlendFunc, glBlendFunc); + VIGS_GL_GET_PROC(CopyTexImage2D, glCopyTexImage2D); + VIGS_GL_GET_PROC(BlitFramebuffer, glBlitFramebufferEXT); + + config_id = vigs_gl_backend_agl_choose_config(gl_backend_agl); + + if (!config_id) { + goto fail; + } + + if (!vigs_gl_backend_agl_create_surface(gl_backend_agl, config_id)) { + goto fail; + } + + if (!vigs_gl_backend_agl_create_context(gl_backend_agl)) { + goto fail; + } + + + gl_backend_agl->base.base.destroy = &vigs_gl_backend_agl_destroy; + gl_backend_agl->base.has_current = &vigs_gl_backend_agl_has_current; + gl_backend_agl->base.make_current = &vigs_gl_backend_agl_make_current; + gl_backend_agl->base.ws_info.context = &gl_backend_agl->context; + + if (!vigs_gl_backend_init(&gl_backend_agl->base)) { + goto fail; + } + + VIGS_LOG_DEBUG("created"); + + return &gl_backend_agl->base.base; + +fail: + + if (gl_backend_agl->handle) { + dlclose(gl_backend_agl->handle); + } + + if (gl_backend_agl->surface) { + aglDestroyPBuffer(gl_backend_agl->surface); + } + + if (gl_backend_agl->context) { + aglDestroyContext(gl_backend_agl->context); + } + + vigs_backend_cleanup(&gl_backend_agl->base.base); + + g_free(gl_backend_agl); + return NULL; }