// SwiftShader Software Renderer
//
// Copyright(c) 2005-2013 TransGaming Inc.
//
// All rights reserved. No part of this software may be copied, distributed, transmitted,
// transcribed, stored in a retrieval system, translated into any human or computer
// language by any means, or disclosed to third parties without the explicit written
// agreement of TransGaming Inc. Without such an agreement, no rights or licenses, express
// or implied, including but not limited to any patent rights, are granted to you.
//

// main.cpp: DLL entry point and management of thread-local data.

#include "main.h"

#include "Common/Thread.hpp"
#include "Common/SharedLibrary.hpp"
#include "common/debug.h"

static sw::Thread::LocalStorageKey currentTLS = TLS_OUT_OF_INDEXES;

#if !defined(_MSC_VER)
#define CONSTRUCTOR __attribute__((constructor))
#define DESTRUCTOR __attribute__((destructor))
#else
#define CONSTRUCTOR
#define DESTRUCTOR
#endif

static void eglAttachThread()
{
    TRACE("()");

    egl::Current *current = new egl::Current;

    if(current)
    {
        sw::Thread::setLocalStorage(currentTLS, current);

        current->error = EGL_SUCCESS;
        current->API = EGL_OPENGL_ES_API;
        current->display = EGL_NO_DISPLAY;
        current->drawSurface = EGL_NO_SURFACE;
        current->readSurface = EGL_NO_SURFACE;
	}
}

static void eglDetachThread()
{
    TRACE("()");

	egl::Current *current = (egl::Current*)sw::Thread::getLocalStorage(currentTLS);

	if(current)
	{
        delete current;
	}
}

CONSTRUCTOR static bool eglAttachProcess()
{
    TRACE("()");

	#if !defined(ANGLE_DISABLE_TRACE)
        FILE *debug = fopen(TRACE_OUTPUT_FILE, "rt");

        if(debug)
        {
            fclose(debug);
            debug = fopen(TRACE_OUTPUT_FILE, "wt");   // Erase
            fclose(debug);
        }
	#endif

    currentTLS = sw::Thread::allocateLocalStorageKey();

    if(currentTLS == TLS_OUT_OF_INDEXES)
    {
        return false;
    }

	eglAttachThread();

	#if defined(_WIN32)
	const char *libGLESv2_lib = "libGLESv2.dll";
	#else
	const char *libGLESv2_lib = "libGLESv2.so";
	#endif
	
    libGLESv2 = loadLibrary(libGLESv2_lib);
    gl::createDevice = (gl::Device*(*)())getProcAddress(libGLESv2, "createDevice");
    gl::createContext = (gl::Context *(*)(const egl::Config*, const gl::Context*))getProcAddress(libGLESv2, "glCreateContext");
    gl::destroyContext = (void (*)(gl::Context*))getProcAddress(libGLESv2, "glDestroyContext");
    gl::makeCurrent = (void (*)(gl::Context*, egl::Display*, egl::Surface*))getProcAddress(libGLESv2, "glMakeCurrent");
    gl::getCurrentContext = (gl::Context *(*)())getProcAddress(libGLESv2, "glGetCurrentContext");
    gl::getProcAddress = (__eglMustCastToProperFunctionPointerType (*)(const char*))getProcAddress(libGLESv2, "glGetProcAddress");
    gl::createBackBuffer = (gl::Image *(*)(int, int, const egl::Config*))getProcAddress(libGLESv2, "createBackBuffer");
    gl::createFrameBuffer = (sw::FrameBuffer *(*)(EGLNativeWindowType, int, int))getProcAddress(libGLESv2, "createFrameBuffer");

	return libGLESv2 != 0;
}

DESTRUCTOR static void eglDetachProcess()
{
    TRACE("()");

	eglDetachThread();
	sw::Thread::freeLocalStorageKey(currentTLS);
	freeLibrary(libGLESv2);
}

#if defined(_WIN32)
extern "C" BOOL WINAPI DllMain(HINSTANCE instance, DWORD reason, LPVOID reserved)
{
    switch(reason)
    {
    case DLL_PROCESS_ATTACH:
        return eglAttachProcess();
        break;
    case DLL_THREAD_ATTACH:
        eglAttachThread();
        break;
    case DLL_THREAD_DETACH:
        eglDetachThread();
        break;
    case DLL_PROCESS_DETACH:
        eglDetachProcess();
        break;
    default:
        break;
    }

    return TRUE;
}
#endif

namespace egl
{
static Current *eglGetCurrent(void)
{
	Current *current = (Current*)sw::Thread::getLocalStorage(currentTLS);

	if(!current)
	{
		eglAttachThread();
	}

	return (Current*)sw::Thread::getLocalStorage(currentTLS);
}

void setCurrentError(EGLint error)
{
    Current *current = eglGetCurrent();

    current->error = error;
}

EGLint getCurrentError()
{
    Current *current = eglGetCurrent();

    return current->error;
}

void setCurrentAPI(EGLenum API)
{
    Current *current = eglGetCurrent();

    current->API = API;
}

EGLenum getCurrentAPI()
{
    Current *current = eglGetCurrent();

    return current->API;
}

void setCurrentDisplay(EGLDisplay dpy)
{
    Current *current = eglGetCurrent();

    current->display = dpy;
}

EGLDisplay getCurrentDisplay()
{
    Current *current = eglGetCurrent();

    return current->display;
}

void setCurrentDrawSurface(EGLSurface surface)
{
    Current *current = eglGetCurrent();

    current->drawSurface = surface;
}

EGLSurface getCurrentDrawSurface()
{
    Current *current = eglGetCurrent();

    return current->drawSurface;
}

void setCurrentReadSurface(EGLSurface surface)
{
    Current *current = eglGetCurrent();

    current->readSurface = surface;
}

EGLSurface getCurrentReadSurface()
{
    Current *current = eglGetCurrent();

    return current->readSurface;
}
}

void error(EGLint errorCode)
{
    egl::setCurrentError(errorCode);

    switch(errorCode)
    {
    case EGL_SUCCESS:                                                                  break;
    case EGL_NOT_INITIALIZED:     TRACE("\t! Error generated: not initialized\n");     break;
    case EGL_BAD_ACCESS:          TRACE("\t! Error generated: bad access\n");          break;
    case EGL_BAD_ALLOC:           TRACE("\t! Error generated: bad alloc\n");           break;
    case EGL_BAD_ATTRIBUTE:       TRACE("\t! Error generated: bad attribute\n");       break;
    case EGL_BAD_CONFIG:          TRACE("\t! Error generated: bad config\n");          break;
    case EGL_BAD_CONTEXT:         TRACE("\t! Error generated: bad context\n");         break;
    case EGL_BAD_CURRENT_SURFACE: TRACE("\t! Error generated: bad current surface\n"); break;
    case EGL_BAD_DISPLAY:         TRACE("\t! Error generated: bad display\n");         break;
    case EGL_BAD_MATCH:           TRACE("\t! Error generated: bad match\n");           break;
    case EGL_BAD_NATIVE_PIXMAP:   TRACE("\t! Error generated: bad native pixmap\n");   break;
    case EGL_BAD_NATIVE_WINDOW:   TRACE("\t! Error generated: bad native window\n");   break;
    case EGL_BAD_PARAMETER:       TRACE("\t! Error generated: bad parameter\n");       break;
    case EGL_BAD_SURFACE:         TRACE("\t! Error generated: bad surface\n");         break;
    case EGL_CONTEXT_LOST:        TRACE("\t! Error generated: context lost\n");        break;
    default:                      TRACE("\t! Error generated: <0x%X>\n", errorCode);   break;
    }
}

namespace gl
{
	Device *(*createDevice)() = 0;
	Context *(*createContext)(const egl::Config *config, const Context *shareContext) = 0;
	void (*destroyContext)(Context *context) = 0;
	void (*bindTexImage)(egl::Surface *surface) = 0;
	void (*makeCurrent)(Context *context, egl::Display *display, egl::Surface *surface) = 0;
	Context *(*getCurrentContext)() = 0;
	__eglMustCastToProperFunctionPointerType (*getProcAddress)(const char *procname) = 0;
	Image *(*createBackBuffer)(int width, int height, const egl::Config *config) = 0;
	sw::FrameBuffer *(*createFrameBuffer)(EGLNativeWindowType window, int width, int height) = 0;
}

void *libGLESv2 = 0;   // Handle to the libGLESv2 module
