/*
 * DIB driver OpenGL support
 *
 * Copyright 2012 Alexandre Julliard
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
 */

#include "config.h"
#include "wine/port.h"

#ifdef HAVE_GL_OSMESA_H
#include <GL/osmesa.h>
#undef APIENTRY
#undef GLAPI
#undef WINGDIAPI
#endif

#include "gdi_private.h"
#include "dibdrv.h"

#include "wine/library.h"
#include "wine/debug.h"

WINE_DEFAULT_DEBUG_CHANNEL(dib);

#ifdef SONAME_LIBOSMESA

#include "wine/wgl_driver.h"

extern BOOL WINAPI GdiSetPixelFormat( HDC hdc, INT fmt, const PIXELFORMATDESCRIPTOR *pfd );

struct wgl_context
{
    OSMesaContext context;
    int           format;
};

static struct opengl_funcs opengl_funcs;

#define USE_GL_FUNC(name) #name,
static const char *opengl_func_names[] = { ALL_WGL_FUNCS };
#undef USE_GL_FUNC

#define MAKE_FUNCPTR(f) static typeof(f) * p##f;
MAKE_FUNCPTR(OSMesaCreateContextExt)
MAKE_FUNCPTR(OSMesaDestroyContext)
MAKE_FUNCPTR(OSMesaGetProcAddress)
MAKE_FUNCPTR(OSMesaMakeCurrent)
MAKE_FUNCPTR(OSMesaPixelStore)
#undef MAKE_FUNCPTR

static const struct
{
    UINT mesa;
    BYTE color_bits;
    BYTE red_bits, red_shift;
    BYTE green_bits, green_shift;
    BYTE blue_bits, blue_shift;
    BYTE alpha_bits, alpha_shift;
    BYTE accum_bits;
    BYTE depth_bits;
    BYTE stencil_bits;
} pixel_formats[] =
{
    { OSMESA_BGRA,     32,  8, 16, 8, 8,  8, 0,  8, 24,  16, 32, 8 },
    { OSMESA_BGRA,     32,  8, 16, 8, 8,  8, 0,  8, 24,  16, 16, 8 },
    { OSMESA_RGBA,     32,  8, 0,  8, 8,  8, 16, 8, 24,  16, 32, 8 },
    { OSMESA_RGBA,     32,  8, 0,  8, 8,  8, 16, 8, 24,  16, 16, 8 },
    { OSMESA_ARGB,     32,  8, 8,  8, 16, 8, 24, 8, 0,   16, 32, 8 },
    { OSMESA_ARGB,     32,  8, 8,  8, 16, 8, 24, 8, 0,   16, 16, 8 },
    { OSMESA_RGB,      24,  8, 0,  8, 8,  8, 16, 0, 0,   16, 32, 8 },
    { OSMESA_RGB,      24,  8, 0,  8, 8,  8, 16, 0, 0,   16, 16, 8 },
    { OSMESA_BGR,      24,  8, 16, 8, 8,  8, 0,  0, 0,   16, 32, 8 },
    { OSMESA_BGR,      24,  8, 16, 8, 8,  8, 0,  0, 0,   16, 16, 8 },
    { OSMESA_RGB_565,  16,  5, 0,  6, 5,  5, 11, 0, 0,   16, 32, 8 },
    { OSMESA_RGB_565,  16,  5, 0,  6, 5,  5, 11, 0, 0,   16, 16, 8 },
};
static const int nb_formats = sizeof(pixel_formats) / sizeof(pixel_formats[0]);

static BOOL init_opengl(void)
{
    static int init_done;
    static void *osmesa_handle;
    char buffer[200];
    unsigned int i;

    if (init_done) return (osmesa_handle != NULL);
    init_done = 1;

    osmesa_handle = wine_dlopen( SONAME_LIBOSMESA, RTLD_NOW, buffer, sizeof(buffer) );
    if (osmesa_handle == NULL)
    {
        ERR( "Failed to load OSMesa: %s\n", buffer );
        return FALSE;
    }

    for (i = 0; i < sizeof(opengl_func_names)/sizeof(opengl_func_names[0]); i++)
    {
        if (!(((void **)&opengl_funcs.gl)[i] = wine_dlsym( osmesa_handle, opengl_func_names[i], NULL, 0 )))
        {
            ERR( "%s not found in %s, disabling.\n", opengl_func_names[i], SONAME_LIBOSMESA );
            goto failed;
        }
    }
#define LOAD_FUNCPTR(f) do if (!(p##f = (void *)wine_dlsym( osmesa_handle, #f, NULL, 0 ))) \
    { \
        ERR( "%s not found in %s, disabling.\n", #f, SONAME_LIBOSMESA ); \
        goto failed; \
    } while(0)

    LOAD_FUNCPTR(OSMesaCreateContextExt);
    LOAD_FUNCPTR(OSMesaDestroyContext);
    LOAD_FUNCPTR(OSMesaGetProcAddress);
    LOAD_FUNCPTR(OSMesaMakeCurrent);
    LOAD_FUNCPTR(OSMesaPixelStore);
#undef LOAD_FUNCPTR

    return TRUE;

failed:
    wine_dlclose( osmesa_handle, NULL, 0 );
    osmesa_handle = NULL;
    return FALSE;
}

/**********************************************************************
 *	     dibdrv_wglDescribePixelFormat
 */
int dibdrv_wglDescribePixelFormat( HDC hdc, int fmt, UINT size, PIXELFORMATDESCRIPTOR *descr )
{
    int ret = sizeof(pixel_formats) / sizeof(pixel_formats[0]);

    if (fmt <= 0 || fmt > ret) return ret;
    if (size < sizeof(*descr)) return 0;

    memset( descr, 0, sizeof(*descr) );
    descr->nSize            = sizeof(*descr);
    descr->nVersion         = 1;
    descr->dwFlags          = PFD_SUPPORT_GDI | PFD_SUPPORT_OPENGL | PFD_DRAW_TO_BITMAP | PFD_GENERIC_FORMAT;
    descr->iPixelType       = PFD_TYPE_RGBA;
    descr->cColorBits       = pixel_formats[fmt - 1].color_bits;
    descr->cRedBits         = pixel_formats[fmt - 1].red_bits;
    descr->cRedShift        = pixel_formats[fmt - 1].red_shift;
    descr->cGreenBits       = pixel_formats[fmt - 1].green_bits;
    descr->cGreenShift      = pixel_formats[fmt - 1].green_shift;
    descr->cBlueBits        = pixel_formats[fmt - 1].blue_bits;
    descr->cBlueShift       = pixel_formats[fmt - 1].blue_shift;
    descr->cAlphaBits       = pixel_formats[fmt - 1].alpha_bits;
    descr->cAlphaShift      = pixel_formats[fmt - 1].alpha_shift;
    descr->cAccumBits       = pixel_formats[fmt - 1].accum_bits;
    descr->cAccumRedBits    = pixel_formats[fmt - 1].accum_bits / 4;
    descr->cAccumGreenBits  = pixel_formats[fmt - 1].accum_bits / 4;
    descr->cAccumBlueBits   = pixel_formats[fmt - 1].accum_bits / 4;
    descr->cAccumAlphaBits  = pixel_formats[fmt - 1].accum_bits / 4;
    descr->cDepthBits       = pixel_formats[fmt - 1].depth_bits;
    descr->cStencilBits     = pixel_formats[fmt - 1].stencil_bits;
    descr->cAuxBuffers      = 0;
    descr->iLayerType       = PFD_MAIN_PLANE;
    return ret;
}

/***********************************************************************
 *		dibdrv_wglCopyContext
 */
static BOOL dibdrv_wglCopyContext( struct wgl_context *src, struct wgl_context *dst, UINT mask )
{
    FIXME( "not supported yet\n" );
    return FALSE;
}

/***********************************************************************
 *		dibdrv_wglCreateContext
 */
static struct wgl_context *dibdrv_wglCreateContext( HDC hdc )
{
    struct wgl_context *context;

    if (!(context = HeapAlloc( GetProcessHeap(), 0, sizeof( *context )))) return NULL;
    context->format = GetPixelFormat( hdc );
    if (!context->format || context->format > nb_formats) context->format = 1;

    if (!(context->context = pOSMesaCreateContextExt( pixel_formats[context->format - 1].mesa,
                                                      pixel_formats[context->format - 1].depth_bits,
                                                      pixel_formats[context->format - 1].stencil_bits,
                                                      pixel_formats[context->format - 1].accum_bits, 0 )))
    {
        HeapFree( GetProcessHeap(), 0, context );
        return NULL;
    }
    return context;
}

/***********************************************************************
 *		dibdrv_wglDeleteContext
 */
static void dibdrv_wglDeleteContext( struct wgl_context *context )
{
    pOSMesaDestroyContext( context->context );
    HeapFree( GetProcessHeap(), 0, context );
}

/***********************************************************************
 *		dibdrv_wglGetPixelFormat
 */
static int dibdrv_wglGetPixelFormat( HDC hdc )
{
    DC *dc = get_dc_ptr( hdc );
    int ret = 0;

    if (dc)
    {
        ret = dc->pixel_format;
        release_dc_ptr( dc );
    }
    return ret;
}

/***********************************************************************
 *		dibdrv_wglGetProcAddress
 */
static PROC dibdrv_wglGetProcAddress( const char *proc )
{
    if (!strncmp( proc, "wgl", 3 )) return NULL;
    return (PROC)pOSMesaGetProcAddress( proc );
}

/***********************************************************************
 *		dibdrv_wglMakeCurrent
 */
static BOOL dibdrv_wglMakeCurrent( HDC hdc, struct wgl_context *context )
{
    HBITMAP bitmap;
    BITMAPOBJ *bmp;
    dib_info dib;
    BOOL ret = FALSE;

    if (!context)
    {
        pOSMesaMakeCurrent( NULL, NULL, GL_UNSIGNED_BYTE, 0, 0 );
        return TRUE;
    }

    if (GetPixelFormat( hdc ) != context->format)
        FIXME( "mismatched pixel formats %u/%u not supported yet\n",
               GetPixelFormat( hdc ), context->format );

    bitmap = GetCurrentObject( hdc, OBJ_BITMAP );
    bmp = GDI_GetObjPtr( bitmap, OBJ_BITMAP );
    if (!bmp) return FALSE;

    if (init_dib_info_from_bitmapobj( &dib, bmp ))
    {
        char *bits;
        int width = dib.rect.right - dib.rect.left;
        int height = dib.rect.bottom - dib.rect.top;

        if (dib.stride < 0)
            bits = (char *)dib.bits.ptr + (dib.rect.bottom - 1) * dib.stride;
        else
            bits = (char *)dib.bits.ptr + dib.rect.top * dib.stride;
        bits += dib.rect.left * dib.bit_count / 8;

        TRACE( "context %p bits %p size %ux%u\n", context, bits, width, height );

        ret = pOSMesaMakeCurrent( context->context, bits, GL_UNSIGNED_BYTE, width, height );
        if (ret)
        {
            pOSMesaPixelStore( OSMESA_ROW_LENGTH, abs( dib.stride ) * 8 / dib.bit_count );
            pOSMesaPixelStore( OSMESA_Y_UP, 1 );  /* Windows seems to assume bottom-up */
        }
    }
    GDI_ReleaseObj( bitmap );
    return ret;
}

/**********************************************************************
 *	     dibdrv_wglSetPixelFormat
 */
BOOL dibdrv_wglSetPixelFormat( HDC hdc, int fmt, const PIXELFORMATDESCRIPTOR *descr )
{
    if (fmt <= 0 || fmt > nb_formats) return FALSE;
    return GdiSetPixelFormat( hdc, fmt, descr );
}

/***********************************************************************
 *		dibdrv_wglShareLists
 */
static BOOL dibdrv_wglShareLists( struct wgl_context *org, struct wgl_context *dest )
{
    FIXME( "not supported yet\n" );
    return FALSE;
}

static struct opengl_funcs opengl_funcs =
{
    {
        dibdrv_wglCopyContext,        /* p_wglCopyContext */
        dibdrv_wglCreateContext,      /* p_wglCreateContext */
        dibdrv_wglDeleteContext,      /* p_wglDeleteContext */
        dibdrv_wglDescribePixelFormat,/* p_wglDescribePixelFormat */
        dibdrv_wglGetPixelFormat,     /* p_wglGetPixelFormat */
        dibdrv_wglGetProcAddress,     /* p_wglGetProcAddress */
        dibdrv_wglMakeCurrent,        /* p_wglMakeCurrent */
        dibdrv_wglSetPixelFormat,     /* p_wglSetPixelFormat */
        dibdrv_wglShareLists,         /* p_wglShareLists */
    }
};

/**********************************************************************
 *	     dibdrv_wine_get_wgl_driver
 */
struct opengl_funcs *dibdrv_wine_get_wgl_driver( PHYSDEV dev, UINT version )
{
    if (version != WINE_WGL_DRIVER_VERSION)
    {
        ERR( "version mismatch, opengl32 wants %u but dibdrv has %u\n", version, WINE_WGL_DRIVER_VERSION );
        return NULL;
    }

    if (!init_opengl()) return (void *)-1;

    return &opengl_funcs;
}

#else  /* SONAME_LIBOSMESA */

/**********************************************************************
 *	     dibdrv_wine_get_wgl_driver
 */
struct opengl_funcs *dibdrv_wine_get_wgl_driver( PHYSDEV dev, UINT version )
{
    static int warned;
    if (!warned++) ERR( "OSMesa not compiled in, no OpenGL bitmap support\n" );
    return (void *)-1;
}

#endif  /* SONAME_LIBOSMESA */
