Blame tests/dummy/EGL_dummy.c

Packit 5af8b3
/*
Packit 5af8b3
 * Copyright (c) 2016, NVIDIA CORPORATION.
Packit 5af8b3
 *
Packit 5af8b3
 * Permission is hereby granted, free of charge, to any person obtaining a
Packit 5af8b3
 * copy of this software and/or associated documentation files (the
Packit 5af8b3
 * "Materials"), to deal in the Materials without restriction, including
Packit 5af8b3
 * without limitation the rights to use, copy, modify, merge, publish,
Packit 5af8b3
 * distribute, sublicense, and/or sell copies of the Materials, and to
Packit 5af8b3
 * permit persons to whom the Materials are furnished to do so, subject to
Packit 5af8b3
 * the following conditions:
Packit 5af8b3
 *
Packit 5af8b3
 * The above copyright notice and this permission notice shall be included
Packit 5af8b3
 * unaltered in all copies or substantial portions of the Materials.
Packit 5af8b3
 * Any additions, deletions, or changes to the original source files
Packit 5af8b3
 * must be clearly indicated in accompanying documentation.
Packit 5af8b3
 *
Packit 5af8b3
 * If only executable code is distributed, then the accompanying
Packit 5af8b3
 * documentation must state that "this software is based in part on the
Packit 5af8b3
 * work of the Khronos Group."
Packit 5af8b3
 *
Packit 5af8b3
 * THE MATERIALS ARE PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
Packit 5af8b3
 * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
Packit 5af8b3
 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
Packit 5af8b3
 * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
Packit 5af8b3
 * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
Packit 5af8b3
 * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
Packit 5af8b3
 * MATERIALS OR THE USE OR OTHER DEALINGS IN THE MATERIALS.
Packit 5af8b3
 */
Packit 5af8b3
Packit 5af8b3
#include "EGL_dummy.h"
Packit 5af8b3
Packit 5af8b3
#include <stdlib.h>
Packit 5af8b3
#include <assert.h>
Packit 5af8b3
Packit 5af8b3
#include "glvnd/libeglabi.h"
Packit 5af8b3
#include "glvnd_list.h"
Packit 5af8b3
#include "glvnd_pthread.h"
Packit 5af8b3
#include "compiler.h"
Packit 5af8b3
Packit 5af8b3
enum
Packit 5af8b3
{
Packit 5af8b3
    DI_eglTestDispatchDisplay,
Packit 5af8b3
    DI_eglTestDispatchDevice,
Packit 5af8b3
    DI_eglTestDispatchCurrent,
Packit 5af8b3
    DI_COUNT,
Packit 5af8b3
};
Packit 5af8b3
Packit 5af8b3
static const char *CLIENT_EXTENSIONS =
Packit 5af8b3
    "EGL_KHR_client_get_all_proc_addresses"
Packit 5af8b3
    " EGL_EXT_client_extensions"
Packit 5af8b3
    " EGL_EXT_device_enumeration"
Packit 5af8b3
    ;
Packit 5af8b3
Packit 5af8b3
static const char *PLATFORM_EXTENSIONS =
Packit 5af8b3
    "EGL_EXT_platform_device"
Packit 5af8b3
    ;
Packit 5af8b3
Packit 5af8b3
static const char *DISPLAY_EXTENSIONS = "";
Packit 5af8b3
Packit 5af8b3
typedef struct DummyEGLDisplayRec {
Packit 5af8b3
    EGLenum platform;
Packit 5af8b3
    void *native_display;
Packit 5af8b3
    EGLLabelKHR label;
Packit 5af8b3
Packit 5af8b3
    struct glvnd_list entry;
Packit 5af8b3
} DummyEGLDisplay;
Packit 5af8b3
Packit 5af8b3
typedef struct DummyThreadStateRec {
Packit 5af8b3
    EGLint lastError;
Packit 5af8b3
    EGLContext currentContext;
Packit 5af8b3
    EGLLabelKHR label;
Packit 5af8b3
} DummyThreadState;
Packit 5af8b3
Packit 5af8b3
static const __EGLapiExports *apiExports = NULL;
Packit 5af8b3
static glvnd_key_t threadStateKey;
Packit 5af8b3
static struct glvnd_list displayList;
Packit 5af8b3
static EGLint failNextMakeCurrentError = EGL_NONE;
Packit 5af8b3
Packit 5af8b3
static EGLDEBUGPROCKHR debugCallbackFunc = NULL;
Packit 5af8b3
static EGLBoolean debugCallbackEnabled = EGL_TRUE;
Packit 5af8b3
Packit 5af8b3
static DummyThreadState *GetThreadState(void)
Packit 5af8b3
{
Packit 5af8b3
    DummyThreadState *thr = (DummyThreadState *)
Packit 5af8b3
        __glvndPthreadFuncs.getspecific(threadStateKey);
Packit 5af8b3
    if (thr == NULL) {
Packit 5af8b3
        thr = (DummyThreadState *) calloc(1, sizeof(DummyThreadState));
Packit 5af8b3
        if (thr == NULL) {
Packit 5af8b3
            printf("Can't allocate thread state\n");
Packit 5af8b3
            abort();
Packit 5af8b3
        }
Packit 5af8b3
        thr->lastError = EGL_SUCCESS;
Packit 5af8b3
        __glvndPthreadFuncs.setspecific(threadStateKey, thr);
Packit 5af8b3
    }
Packit 5af8b3
    return thr;
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static void OnThreadTerminate(void *ptr)
Packit 5af8b3
{
Packit 5af8b3
    free(ptr);
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static void CommonEntrypoint(void)
Packit 5af8b3
{
Packit 5af8b3
    DummyThreadState *thr = GetThreadState();
Packit 5af8b3
    thr->lastError = EGL_SUCCESS;
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static void SetLastError(const char *command, EGLLabelKHR label, EGLint error)
Packit 5af8b3
{
Packit 5af8b3
    DummyThreadState *thr = GetThreadState();
Packit 5af8b3
Packit 5af8b3
    thr->lastError = error;
Packit 5af8b3
Packit 5af8b3
    if (error != EGL_SUCCESS && debugCallbackFunc != NULL && debugCallbackEnabled) {
Packit 5af8b3
        debugCallbackFunc(error, command, EGL_DEBUG_MSG_ERROR_KHR, thr->label,
Packit 5af8b3
                label, DUMMY_VENDOR_NAME);
Packit 5af8b3
    }
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static DummyEGLDisplay *LookupEGLDisplay(EGLDisplay dpy)
Packit 5af8b3
{
Packit 5af8b3
    DummyEGLDisplay *disp = NULL;
Packit 5af8b3
    glvnd_list_for_each_entry(disp, &displayList, entry) {
Packit 5af8b3
        if (dpy == (EGLDisplay) disp) {
Packit 5af8b3
            return disp;
Packit 5af8b3
        }
Packit 5af8b3
    }
Packit 5af8b3
    // Libglvnd should never pass an invalid EGLDisplay handle to a vendor
Packit 5af8b3
    // library.
Packit 5af8b3
    printf("Invalid EGLDisplay %p\n", dpy);
Packit 5af8b3
    abort();
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLDeviceEXT GetEGLDevice(EGLint index)
Packit 5af8b3
{
Packit 5af8b3
    // The EGLDeviceEXT handle values have to be pointers, so just use the
Packit 5af8b3
    // address of an array element for each EGLDeviceEXT handle.
Packit 5af8b3
    static const char EGL_DEVICE_HANDLES[DUMMY_EGL_DEVICE_COUNT];
Packit 5af8b3
Packit 5af8b3
    assert(index >= 0 && index < DUMMY_EGL_DEVICE_COUNT);
Packit 5af8b3
    return (EGLDeviceEXT) (EGL_DEVICE_HANDLES + index);
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLBoolean IsEGLDeviceValid(EGLDeviceEXT dev)
Packit 5af8b3
{
Packit 5af8b3
    int i;
Packit 5af8b3
    for (i=0; i
Packit 5af8b3
        if (dev == GetEGLDevice(i)) {
Packit 5af8b3
            return EGL_TRUE;
Packit 5af8b3
        }
Packit 5af8b3
    }
Packit 5af8b3
    return EGL_FALSE;
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static const char *dummyGetVendorString(int name)
Packit 5af8b3
{
Packit 5af8b3
    if (name == __EGL_VENDOR_STRING_PLATFORM_EXTENSIONS) {
Packit 5af8b3
        return PLATFORM_EXTENSIONS;
Packit 5af8b3
    }
Packit 5af8b3
Packit 5af8b3
    return NULL;
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLDisplay dummyGetPlatformDisplay(EGLenum platform, void *native_display,
Packit 5af8b3
      const EGLAttrib *attrib_list)
Packit 5af8b3
{
Packit 5af8b3
    CommonEntrypoint();
Packit 5af8b3
    DummyEGLDisplay *disp = NULL;
Packit 5af8b3
Packit 5af8b3
    if (platform == EGL_NONE) {
Packit 5af8b3
        if (native_display != EGL_DEFAULT_DISPLAY) {
Packit 5af8b3
            // If the native display is not EGL_DEFAULT_DISPLAY, then libEGL
Packit 5af8b3
            // is supposed to guess a platform enum.
Packit 5af8b3
            printf("getPlatformDisplay called without a platform enum.");
Packit 5af8b3
            abort();
Packit 5af8b3
        }
Packit 5af8b3
Packit 5af8b3
        platform = EGL_DUMMY_PLATFORM;
Packit 5af8b3
        native_display = NULL;
Packit 5af8b3
    } else if (platform == EGL_DUMMY_PLATFORM) {
Packit 5af8b3
        if (native_display != NULL) {
Packit 5af8b3
            const char *name = (const char *) native_display;
Packit 5af8b3
            if (strcmp(name, DUMMY_VENDOR_NAME) != 0) {
Packit 5af8b3
                return EGL_NO_DISPLAY;
Packit 5af8b3
            }
Packit 5af8b3
Packit 5af8b3
            // Set the native_display pointer to NULL. This makes it simpler to
Packit 5af8b3
            // find the same dispaly below.
Packit 5af8b3
            native_display = NULL;
Packit 5af8b3
        }
Packit 5af8b3
    } else if (platform == EGL_PLATFORM_DEVICE_EXT) {
Packit 5af8b3
        if (native_display == EGL_DEFAULT_DISPLAY) {
Packit 5af8b3
            native_display = (void *) GetEGLDevice(0);
Packit 5af8b3
        } else {
Packit 5af8b3
            if (!IsEGLDeviceValid((EGLDeviceEXT) native_display)) {
Packit 5af8b3
                return EGL_NO_DISPLAY;
Packit 5af8b3
            }
Packit 5af8b3
        }
Packit 5af8b3
    } else {
Packit 5af8b3
        // We don't support this platform.
Packit 5af8b3
        SetLastError("eglGetPlatformDisplay", NULL, EGL_BAD_PARAMETER);
Packit 5af8b3
        return EGL_NO_DISPLAY;
Packit 5af8b3
    }
Packit 5af8b3
Packit 5af8b3
    glvnd_list_for_each_entry(disp, &displayList, entry) {
Packit 5af8b3
        if (disp->platform == platform && disp->native_display == native_display) {
Packit 5af8b3
            return disp;
Packit 5af8b3
        }
Packit 5af8b3
    }
Packit 5af8b3
Packit 5af8b3
    // Create a new DummyEGLDisplay structure.
Packit 5af8b3
    disp = (DummyEGLDisplay *) calloc(1, sizeof(DummyEGLDisplay));
Packit 5af8b3
    disp->platform = platform;
Packit 5af8b3
    disp->native_display = native_display;
Packit 5af8b3
    glvnd_list_append(&disp->entry, &displayList);
Packit 5af8b3
    return disp;
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
/**
Packit 5af8b3
 * A common function for a bunch of EGL functions that the dummy vendor doesn't
Packit 5af8b3
 * implement. This just checks that the display is valid, and returns EGL_FALSE.
Packit 5af8b3
 */
Packit 5af8b3
static EGLBoolean CommonDisplayStub(EGLDisplay dpy)
Packit 5af8b3
{
Packit 5af8b3
    CommonEntrypoint();
Packit 5af8b3
    LookupEGLDisplay(dpy);
Packit 5af8b3
    return EGL_FALSE;
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLBoolean EGLAPIENTRY dummy_eglInitialize(EGLDisplay dpy,
Packit 5af8b3
        EGLint *major, EGLint *minor)
Packit 5af8b3
{
Packit 5af8b3
    CommonEntrypoint();
Packit 5af8b3
    LookupEGLDisplay(dpy);
Packit 5af8b3
Packit 5af8b3
    *major = 1;
Packit 5af8b3
    *minor = 5;
Packit 5af8b3
    return EGL_TRUE;
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLBoolean EGLAPIENTRY dummy_eglTerminate(EGLDisplay dpy)
Packit 5af8b3
{
Packit 5af8b3
    CommonEntrypoint();
Packit 5af8b3
    LookupEGLDisplay(dpy);
Packit 5af8b3
    return EGL_TRUE;
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLBoolean EGLAPIENTRY dummy_eglChooseConfig(EGLDisplay dpy,
Packit 5af8b3
        const EGLint *attrib_list, EGLConfig *configs, EGLint config_size,
Packit 5af8b3
        EGLint *num_config)
Packit 5af8b3
{
Packit 5af8b3
    return CommonDisplayStub(dpy);
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLBoolean EGLAPIENTRY dummy_eglGetConfigs(EGLDisplay dpy, EGLConfig *configs,
Packit 5af8b3
        EGLint config_size, EGLint *num_config)
Packit 5af8b3
{
Packit 5af8b3
    return CommonDisplayStub(dpy);
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLBoolean EGLAPIENTRY dummy_eglCopyBuffers(EGLDisplay dpy, EGLSurface surface, EGLNativePixmapType target)
Packit 5af8b3
{
Packit 5af8b3
    return CommonDisplayStub(dpy);
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLContext EGLAPIENTRY dummy_eglCreateContext(EGLDisplay dpy,
Packit 5af8b3
        EGLConfig config, EGLContext share_context, const EGLint *attrib_list)
Packit 5af8b3
{
Packit 5af8b3
    DummyEGLContext *dctx;
Packit 5af8b3
    DummyEGLDisplay *disp;
Packit 5af8b3
Packit 5af8b3
    CommonEntrypoint();
Packit 5af8b3
    disp = LookupEGLDisplay(dpy);
Packit 5af8b3
Packit 5af8b3
    if (attrib_list != NULL) {
Packit 5af8b3
        int i;
Packit 5af8b3
        for (i=0; attrib_list[i] != EGL_NONE; i += 2) {
Packit 5af8b3
            if (attrib_list[i] == EGL_CREATE_CONTEXT_FAIL) {
Packit 5af8b3
                SetLastError("eglCreateContext", disp->label, attrib_list[i + 1]);
Packit 5af8b3
                return EGL_NO_CONTEXT;
Packit 5af8b3
            } else {
Packit 5af8b3
                printf("Invalid attribute 0x%04x in eglCreateContext\n", attrib_list[i]);
Packit 5af8b3
                abort();
Packit 5af8b3
            }
Packit 5af8b3
        }
Packit 5af8b3
    }
Packit 5af8b3
Packit 5af8b3
    dctx = (DummyEGLContext *) calloc(1, sizeof(DummyEGLContext));
Packit 5af8b3
    dctx->vendorName = DUMMY_VENDOR_NAME;
Packit 5af8b3
Packit 5af8b3
    return (EGLContext) dctx;
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLBoolean EGLAPIENTRY dummy_eglDestroyContext(EGLDisplay dpy, EGLContext ctx)
Packit 5af8b3
{
Packit 5af8b3
    CommonEntrypoint();
Packit 5af8b3
    LookupEGLDisplay(dpy);
Packit 5af8b3
Packit 5af8b3
    if (ctx != EGL_NO_CONTEXT) {
Packit 5af8b3
        DummyEGLContext *dctx = (DummyEGLContext *) ctx;
Packit 5af8b3
        free(dctx);
Packit 5af8b3
    }
Packit 5af8b3
    return EGL_TRUE;
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLSurface CommonCreateSurface(EGLDisplay dpy)
Packit 5af8b3
{
Packit 5af8b3
    CommonEntrypoint();
Packit 5af8b3
    LookupEGLDisplay(dpy);
Packit 5af8b3
    return EGL_NO_SURFACE;
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLSurface dummy_eglCreatePlatformWindowSurface(EGLDisplay dpy,
Packit 5af8b3
        EGLConfig config, void *native_window, const EGLAttrib *attrib_list)
Packit 5af8b3
{
Packit 5af8b3
    return CommonCreateSurface(dpy);
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLSurface dummy_eglCreatePlatformPixmapSurface(EGLDisplay dpy,
Packit 5af8b3
        EGLConfig config, void *native_pixmap, const EGLAttrib *attrib_list)
Packit 5af8b3
{
Packit 5af8b3
    return CommonCreateSurface(dpy);
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLSurface EGLAPIENTRY dummy_eglCreatePbufferSurface(EGLDisplay dpy,
Packit 5af8b3
        EGLConfig config, const EGLint *attrib_list)
Packit 5af8b3
{
Packit 5af8b3
    return CommonCreateSurface(dpy);
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLSurface EGLAPIENTRY dummy_eglCreatePixmapSurface(EGLDisplay dpy,
Packit 5af8b3
        EGLConfig config, EGLNativePixmapType pixmap, const EGLint *attrib_list)
Packit 5af8b3
{
Packit 5af8b3
    return CommonCreateSurface(dpy);
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLSurface EGLAPIENTRY dummy_eglCreateWindowSurface(EGLDisplay dpy,
Packit 5af8b3
        EGLConfig config, EGLNativeWindowType win, const EGLint *attrib_list)
Packit 5af8b3
{
Packit 5af8b3
    return CommonCreateSurface(dpy);
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLSurface EGLAPIENTRY dummy_eglCreatePbufferFromClientBuffer(EGLDisplay dpy,
Packit 5af8b3
        EGLenum buftype, EGLClientBuffer buffer, EGLConfig config,
Packit 5af8b3
        const EGLint *attrib_list)
Packit 5af8b3
{
Packit 5af8b3
    return CommonCreateSurface(dpy);
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLBoolean EGLAPIENTRY dummy_eglDestroySurface(EGLDisplay dpy, EGLSurface surface)
Packit 5af8b3
{
Packit 5af8b3
    return CommonDisplayStub(dpy);
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLBoolean EGLAPIENTRY dummy_eglGetConfigAttrib(EGLDisplay dpy, EGLConfig config, EGLint attribute, EGLint *value)
Packit 5af8b3
{
Packit 5af8b3
    return CommonDisplayStub(dpy);
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLBoolean EGLAPIENTRY dummy_eglMakeCurrent(EGLDisplay dpy, EGLSurface draw, EGLSurface read, EGLContext ctx)
Packit 5af8b3
{
Packit 5af8b3
    DummyThreadState *thr;
Packit 5af8b3
    CommonEntrypoint();
Packit 5af8b3
Packit 5af8b3
    LookupEGLDisplay(dpy);
Packit 5af8b3
Packit 5af8b3
    if (failNextMakeCurrentError != EGL_NONE) {
Packit 5af8b3
        SetLastError("eglMakeCurrent", NULL, failNextMakeCurrentError);
Packit 5af8b3
        failNextMakeCurrentError = EGL_NONE;
Packit 5af8b3
        return EGL_FALSE;
Packit 5af8b3
    }
Packit 5af8b3
Packit 5af8b3
    thr = GetThreadState();
Packit 5af8b3
    thr->currentContext = ctx;
Packit 5af8b3
Packit 5af8b3
    return EGL_TRUE;
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLBoolean EGLAPIENTRY dummy_eglQueryContext(EGLDisplay dpy, EGLContext ctx, EGLint attribute, EGLint *value)
Packit 5af8b3
{
Packit 5af8b3
    return CommonDisplayStub(dpy);
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static const char * EGLAPIENTRY dummy_eglQueryString(EGLDisplay dpy, EGLenum name)
Packit 5af8b3
{
Packit 5af8b3
    CommonEntrypoint();
Packit 5af8b3
Packit 5af8b3
    if (dpy == EGL_NO_DISPLAY) {
Packit 5af8b3
        if (name == EGL_VERSION) {
Packit 5af8b3
            return "1.5 EGL dummy";
Packit 5af8b3
        } else if (name == EGL_EXTENSIONS) {
Packit 5af8b3
            return CLIENT_EXTENSIONS;
Packit 5af8b3
        } else {
Packit 5af8b3
            return NULL;
Packit 5af8b3
        }
Packit 5af8b3
    }
Packit 5af8b3
Packit 5af8b3
    LookupEGLDisplay(dpy);
Packit 5af8b3
Packit 5af8b3
    if (name == EGL_VENDOR) {
Packit 5af8b3
        return DUMMY_VENDOR_NAME;
Packit 5af8b3
    } else if (name == EGL_CLIENT_APIS) {
Packit 5af8b3
        return "OpenGL OpenGL_ES";
Packit 5af8b3
    } else if (name == EGL_EXTENSIONS) {
Packit 5af8b3
        return DISPLAY_EXTENSIONS;
Packit 5af8b3
    } else {
Packit 5af8b3
        return NULL;
Packit 5af8b3
    }
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLBoolean EGLAPIENTRY dummy_eglQuerySurface(EGLDisplay dpy, EGLSurface surface, EGLint attribute, EGLint *value)
Packit 5af8b3
{
Packit 5af8b3
    return CommonDisplayStub(dpy);
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLBoolean EGLAPIENTRY dummy_eglSwapBuffers(EGLDisplay dpy, EGLSurface surface)
Packit 5af8b3
{
Packit 5af8b3
    return CommonDisplayStub(dpy);
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLBoolean EGLAPIENTRY dummy_eglWaitGL(void)
Packit 5af8b3
{
Packit 5af8b3
    CommonEntrypoint();
Packit 5af8b3
    return EGL_FALSE;
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLBoolean EGLAPIENTRY dummy_eglWaitNative(EGLint engine)
Packit 5af8b3
{
Packit 5af8b3
    CommonEntrypoint();
Packit 5af8b3
    return EGL_FALSE;
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLBoolean EGLAPIENTRY dummy_eglBindTexImage(EGLDisplay dpy, EGLSurface surface, EGLint buffer)
Packit 5af8b3
{
Packit 5af8b3
    return CommonDisplayStub(dpy);
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLBoolean EGLAPIENTRY dummy_eglReleaseTexImage(EGLDisplay dpy, EGLSurface surface, EGLint buffer)
Packit 5af8b3
{
Packit 5af8b3
    return CommonDisplayStub(dpy);
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLBoolean EGLAPIENTRY dummy_eglSurfaceAttrib(EGLDisplay dpy, EGLSurface surface, EGLint attribute, EGLint value)
Packit 5af8b3
{
Packit 5af8b3
    return CommonDisplayStub(dpy);
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLBoolean EGLAPIENTRY dummy_eglSwapInterval(EGLDisplay dpy, EGLint interval)
Packit 5af8b3
{
Packit 5af8b3
    return CommonDisplayStub(dpy);
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLBoolean EGLAPIENTRY dummy_eglBindAPI(EGLenum api)
Packit 5af8b3
{
Packit 5af8b3
    CommonEntrypoint();
Packit 5af8b3
    if (api != EGL_OPENGL_API && api != EGL_OPENGL_ES_API) {
Packit 5af8b3
        printf("eglBindAPI called with invalid API 0x%04x\n", api);
Packit 5af8b3
        abort();
Packit 5af8b3
    }
Packit 5af8b3
    return EGL_TRUE;
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLBoolean EGLAPIENTRY dummy_eglReleaseThread(void)
Packit 5af8b3
{
Packit 5af8b3
    DummyThreadState *thr = (DummyThreadState *)
Packit 5af8b3
        __glvndPthreadFuncs.getspecific(threadStateKey);
Packit 5af8b3
    if (thr != NULL) {
Packit 5af8b3
        __glvndPthreadFuncs.setspecific(threadStateKey, NULL);
Packit 5af8b3
        free(thr);
Packit 5af8b3
    }
Packit 5af8b3
    return EGL_TRUE;
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLBoolean EGLAPIENTRY dummy_eglWaitClient(void)
Packit 5af8b3
{
Packit 5af8b3
    CommonEntrypoint();
Packit 5af8b3
    return EGL_FALSE;
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLint EGLAPIENTRY dummy_eglGetError(void)
Packit 5af8b3
{
Packit 5af8b3
    DummyThreadState *thr = GetThreadState();
Packit 5af8b3
    EGLint error = thr->lastError;
Packit 5af8b3
    thr->lastError = EGL_SUCCESS;
Packit 5af8b3
    return error;
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLBoolean EGLAPIENTRY dummy_eglQueryDevicesEXT(EGLint max_devices, EGLDeviceEXT *devices, EGLint *num_devices)
Packit 5af8b3
{
Packit 5af8b3
    CommonEntrypoint();
Packit 5af8b3
    if (devices != NULL) {
Packit 5af8b3
        EGLint i;
Packit 5af8b3
        if (max_devices != DUMMY_EGL_DEVICE_COUNT) {
Packit 5af8b3
            // libEGL should only every query the full list of devices.
Packit 5af8b3
            printf("Wrong max_devices in eglQueryDevicesEXT: %d\n", max_devices);
Packit 5af8b3
            abort();
Packit 5af8b3
        }
Packit 5af8b3
        *num_devices = DUMMY_EGL_DEVICE_COUNT;
Packit 5af8b3
        for (i=0; i<*num_devices; i++) {
Packit 5af8b3
            devices[i] = GetEGLDevice(i);
Packit 5af8b3
        }
Packit 5af8b3
    } else {
Packit 5af8b3
        *num_devices = DUMMY_EGL_DEVICE_COUNT;
Packit 5af8b3
    }
Packit 5af8b3
    return EGL_TRUE;
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLint EGLAPIENTRY dummy_eglDebugMessageControlKHR(EGLDEBUGPROCKHR callback, const EGLAttrib *attrib_list)
Packit 5af8b3
{
Packit 5af8b3
    CommonEntrypoint();
Packit 5af8b3
Packit 5af8b3
    if (callback != NULL) {
Packit 5af8b3
        if (attrib_list != NULL) {
Packit 5af8b3
            int i;
Packit 5af8b3
            for (i=0; attrib_list[i] != EGL_NONE; i += 2) {
Packit 5af8b3
                if (EGL_DEBUG_MSG_ERROR_KHR) {
Packit 5af8b3
                    debugCallbackEnabled = (attrib_list[i + 1] != 0);
Packit 5af8b3
                }
Packit 5af8b3
            }
Packit 5af8b3
        }
Packit 5af8b3
    } else {
Packit 5af8b3
        debugCallbackEnabled = EGL_TRUE;
Packit 5af8b3
    }
Packit 5af8b3
    debugCallbackFunc = callback;
Packit 5af8b3
Packit 5af8b3
    return EGL_SUCCESS;
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLBoolean EGLAPIENTRY dummy_eglQueryDebugKHR(EGLint attribute, EGLAttrib *value)
Packit 5af8b3
{
Packit 5af8b3
    // eglQueryDebugKHR should never be called, because libEGL keeps track of
Packit 5af8b3
    // all of the debug state.
Packit 5af8b3
    printf("eglQueryDebugKHR should never be called\n");
Packit 5af8b3
    abort();
Packit 5af8b3
    return EGL_FALSE;
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLint EGLAPIENTRY dummy_eglLabelObjectKHR(EGLDisplay dpy,
Packit 5af8b3
        EGLenum objectType, EGLObjectKHR object, EGLLabelKHR label)
Packit 5af8b3
{
Packit 5af8b3
    CommonEntrypoint();
Packit 5af8b3
Packit 5af8b3
    if (objectType == EGL_OBJECT_THREAD_KHR) {
Packit 5af8b3
        DummyThreadState *thr = GetThreadState();
Packit 5af8b3
        thr->label = label;
Packit 5af8b3
    } else if (objectType == EGL_OBJECT_DISPLAY_KHR) {
Packit 5af8b3
        DummyEGLDisplay *disp = LookupEGLDisplay(dpy);
Packit 5af8b3
        disp->label = label;
Packit 5af8b3
    }
Packit 5af8b3
    return EGL_SUCCESS;
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static const GLubyte *dummy_glGetString(GLenum name)
Packit 5af8b3
{
Packit 5af8b3
    if (name == GL_VENDOR) {
Packit 5af8b3
        return (const GLubyte *) DUMMY_VENDOR_NAME;
Packit 5af8b3
    }
Packit 5af8b3
    return NULL;
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static void *CommonTestDispatch(const char *funcName,
Packit 5af8b3
        EGLDisplay dpy, EGLDeviceEXT dev,
Packit 5af8b3
        EGLint command, EGLAttrib param)
Packit 5af8b3
{
Packit 5af8b3
    CommonEntrypoint();
Packit 5af8b3
Packit 5af8b3
    if (dpy != EGL_NO_DISPLAY) {
Packit 5af8b3
        LookupEGLDisplay(dpy);
Packit 5af8b3
    }
Packit 5af8b3
Packit 5af8b3
    if (command == DUMMY_COMMAND_GET_VENDOR_NAME) {
Packit 5af8b3
        // Just return the vendor name and don't do anything else.
Packit 5af8b3
        return DUMMY_VENDOR_NAME;
Packit 5af8b3
    } else if (command == DUMMY_COMMAND_GET_CURRENT_CONTEXT) {
Packit 5af8b3
        DummyThreadState *thr = GetThreadState();
Packit 5af8b3
        return (void *) thr->currentContext;
Packit 5af8b3
    } else if (command == DUMMY_COMMAND_FAIL_NEXT_MAKE_CURRENT) {
Packit 5af8b3
        failNextMakeCurrentError = (EGLint) param;
Packit 5af8b3
        return DUMMY_VENDOR_NAME;
Packit 5af8b3
    } else {
Packit 5af8b3
        printf("Invalid command: %d\n", command);
Packit 5af8b3
        abort();
Packit 5af8b3
    }
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static void *dummy_eglTestDispatchDisplay(EGLDisplay dpy, EGLint command, EGLAttrib param)
Packit 5af8b3
{
Packit 5af8b3
    return CommonTestDispatch("eglTestDispatchDisplay", dpy, EGL_NO_DEVICE_EXT, command, param);
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static void *dummy_eglTestDispatchDevice(EGLDeviceEXT dev, EGLint command, EGLAttrib param)
Packit 5af8b3
{
Packit 5af8b3
    return CommonTestDispatch("eglTestDispatchDevice", EGL_NO_DISPLAY, dev, command, param);
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static void *dummy_eglTestDispatchCurrent(EGLint command, EGLAttrib param)
Packit 5af8b3
{
Packit 5af8b3
    return CommonTestDispatch("eglTestDispatchCurrent", EGL_NO_DISPLAY, EGL_NO_DEVICE_EXT, command, param);
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static void *dispatch_eglTestDispatchDisplay(EGLDisplay dpy, EGLint command, EGLAttrib param);
Packit 5af8b3
static void *dispatch_eglTestDispatchDevice(EGLDeviceEXT dpy, EGLint command, EGLAttrib param);
Packit 5af8b3
static void *dispatch_eglTestDispatchCurrent(EGLint command, EGLAttrib param);
Packit 5af8b3
Packit 5af8b3
static struct {
Packit 5af8b3
    const char *name;
Packit 5af8b3
    void *addr;
Packit 5af8b3
    void *dispatchAddress;
Packit 5af8b3
    int index;
Packit 5af8b3
} EGL_EXTENSION_PROCS[DI_COUNT] = {
Packit 5af8b3
#define PROC_ENTRY(name) { #name, dummy_##name, dispatch_##name, -1 }
Packit 5af8b3
    PROC_ENTRY(eglTestDispatchDisplay),
Packit 5af8b3
    PROC_ENTRY(eglTestDispatchDevice),
Packit 5af8b3
    PROC_ENTRY(eglTestDispatchCurrent),
Packit 5af8b3
#undef PROC_ENTRY
Packit 5af8b3
};
Packit 5af8b3
Packit 5af8b3
static __eglMustCastToProperFunctionPointerType FetchVendorFunc(__EGLvendorInfo *vendor,
Packit 5af8b3
        int index, EGLint errorCode)
Packit 5af8b3
{
Packit 5af8b3
    __eglMustCastToProperFunctionPointerType func = NULL;
Packit 5af8b3
Packit 5af8b3
    if (vendor != NULL) {
Packit 5af8b3
        func = apiExports->fetchDispatchEntry(vendor, EGL_EXTENSION_PROCS[index].index);
Packit 5af8b3
    }
Packit 5af8b3
    if (func == NULL) {
Packit 5af8b3
        if (errorCode != EGL_SUCCESS) {
Packit 5af8b3
            apiExports->setEGLError(errorCode);
Packit 5af8b3
        }
Packit 5af8b3
        return NULL;
Packit 5af8b3
    }
Packit 5af8b3
Packit 5af8b3
    if (!apiExports->setLastVendor(vendor)) {
Packit 5af8b3
        printf("setLastVendor failed\n");
Packit 5af8b3
        abort();
Packit 5af8b3
    }
Packit 5af8b3
Packit 5af8b3
    return func;
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static void *dispatch_eglTestDispatchDisplay(EGLDisplay dpy, EGLint command, EGLAttrib param)
Packit 5af8b3
{
Packit 5af8b3
    __EGLvendorInfo *vendor;
Packit 5af8b3
    pfn_eglTestDispatchDisplay func;
Packit 5af8b3
Packit 5af8b3
    apiExports->threadInit();
Packit 5af8b3
    vendor = apiExports->getVendorFromDisplay(dpy);
Packit 5af8b3
    func = (pfn_eglTestDispatchDisplay) FetchVendorFunc(vendor, DI_eglTestDispatchDisplay, EGL_BAD_DISPLAY);
Packit 5af8b3
    if (func != NULL) {
Packit 5af8b3
        return func(dpy, command, param);
Packit 5af8b3
    } else {
Packit 5af8b3
        return NULL;
Packit 5af8b3
    }
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static void *dispatch_eglTestDispatchDevice(EGLDeviceEXT dev, EGLint command, EGLAttrib param)
Packit 5af8b3
{
Packit 5af8b3
    __EGLvendorInfo *vendor;
Packit 5af8b3
    pfn_eglTestDispatchDevice func;
Packit 5af8b3
Packit 5af8b3
    apiExports->threadInit();
Packit 5af8b3
    vendor = apiExports->getVendorFromDevice(dev);
Packit 5af8b3
    func = (pfn_eglTestDispatchDevice) FetchVendorFunc(vendor, DI_eglTestDispatchDevice, EGL_BAD_DEVICE_EXT);
Packit 5af8b3
    if (func != NULL) {
Packit 5af8b3
        return func(dev, command, param);
Packit 5af8b3
    } else {
Packit 5af8b3
        return NULL;
Packit 5af8b3
    }
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static void *dispatch_eglTestDispatchCurrent(EGLint command, EGLAttrib param)
Packit 5af8b3
{
Packit 5af8b3
    __EGLvendorInfo *vendor;
Packit 5af8b3
    pfn_eglTestDispatchCurrent func;
Packit 5af8b3
Packit 5af8b3
    apiExports->threadInit();
Packit 5af8b3
    vendor = apiExports->getCurrentVendor();
Packit 5af8b3
    func = (pfn_eglTestDispatchCurrent) FetchVendorFunc(vendor, DI_eglTestDispatchCurrent, EGL_SUCCESS);
Packit 5af8b3
    if (func != NULL) {
Packit 5af8b3
        return func(command, param);
Packit 5af8b3
    } else {
Packit 5af8b3
        return NULL;
Packit 5af8b3
    }
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
Packit 5af8b3
static const struct {
Packit 5af8b3
    const char *name;
Packit 5af8b3
    void *addr;
Packit 5af8b3
} PROC_ADDRESSES[] = {
Packit 5af8b3
#define PROC_ENTRY(name) { #name, (void *)dummy_ ## name }
Packit 5af8b3
    PROC_ENTRY(eglInitialize),
Packit 5af8b3
    PROC_ENTRY(eglTerminate),
Packit 5af8b3
    PROC_ENTRY(eglChooseConfig),
Packit 5af8b3
    PROC_ENTRY(eglGetConfigs),
Packit 5af8b3
    PROC_ENTRY(eglCopyBuffers),
Packit 5af8b3
    PROC_ENTRY(eglCreateContext),
Packit 5af8b3
    PROC_ENTRY(eglDestroyContext),
Packit 5af8b3
    PROC_ENTRY(eglCreatePlatformWindowSurface),
Packit 5af8b3
    PROC_ENTRY(eglCreatePlatformPixmapSurface),
Packit 5af8b3
    PROC_ENTRY(eglCreatePbufferSurface),
Packit 5af8b3
    PROC_ENTRY(eglCreatePixmapSurface),
Packit 5af8b3
    PROC_ENTRY(eglCreateWindowSurface),
Packit 5af8b3
    PROC_ENTRY(eglCreatePbufferFromClientBuffer),
Packit 5af8b3
    PROC_ENTRY(eglDestroySurface),
Packit 5af8b3
    PROC_ENTRY(eglGetConfigAttrib),
Packit 5af8b3
    PROC_ENTRY(eglMakeCurrent),
Packit 5af8b3
    PROC_ENTRY(eglQueryContext),
Packit 5af8b3
    PROC_ENTRY(eglQueryString),
Packit 5af8b3
    PROC_ENTRY(eglQuerySurface),
Packit 5af8b3
    PROC_ENTRY(eglSwapBuffers),
Packit 5af8b3
    PROC_ENTRY(eglWaitGL),
Packit 5af8b3
    PROC_ENTRY(eglWaitNative),
Packit 5af8b3
    PROC_ENTRY(eglBindTexImage),
Packit 5af8b3
    PROC_ENTRY(eglReleaseTexImage),
Packit 5af8b3
    PROC_ENTRY(eglSurfaceAttrib),
Packit 5af8b3
    PROC_ENTRY(eglSwapInterval),
Packit 5af8b3
    PROC_ENTRY(eglBindAPI),
Packit 5af8b3
    PROC_ENTRY(eglReleaseThread),
Packit 5af8b3
    PROC_ENTRY(eglWaitClient),
Packit 5af8b3
    PROC_ENTRY(eglGetError),
Packit 5af8b3
Packit 5af8b3
    PROC_ENTRY(eglQueryDevicesEXT),
Packit 5af8b3
    PROC_ENTRY(eglDebugMessageControlKHR),
Packit 5af8b3
    PROC_ENTRY(eglQueryDebugKHR),
Packit 5af8b3
    PROC_ENTRY(eglLabelObjectKHR),
Packit 5af8b3
Packit 5af8b3
    PROC_ENTRY(glGetString),
Packit 5af8b3
#undef PROC_ENTRY
Packit 5af8b3
    { NULL, NULL }
Packit 5af8b3
};
Packit 5af8b3
Packit 5af8b3
static void *dummyGetProcAddress(const char *procName)
Packit 5af8b3
{
Packit 5af8b3
    int i;
Packit 5af8b3
    for (i=0; PROC_ADDRESSES[i].name != NULL; i++) {
Packit 5af8b3
        if (strcmp(procName, PROC_ADDRESSES[i].name) == 0) {
Packit 5af8b3
            return PROC_ADDRESSES[i].addr;
Packit 5af8b3
        }
Packit 5af8b3
    }
Packit 5af8b3
Packit 5af8b3
    for (i=0; i < DI_COUNT; i++) {
Packit 5af8b3
        if (strcmp(procName, EGL_EXTENSION_PROCS[i].name) == 0) {
Packit 5af8b3
            return EGL_EXTENSION_PROCS[i].addr;
Packit 5af8b3
        }
Packit 5af8b3
    }
Packit 5af8b3
    return NULL;
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static void *dummyFindDispatchFunction(const char *name)
Packit 5af8b3
{
Packit 5af8b3
    int i;
Packit 5af8b3
    for (i=0; i < DI_COUNT; i++) {
Packit 5af8b3
        if (strcmp(name, EGL_EXTENSION_PROCS[i].name) == 0) {
Packit 5af8b3
            return EGL_EXTENSION_PROCS[i].dispatchAddress;
Packit 5af8b3
        }
Packit 5af8b3
    }
Packit 5af8b3
    return NULL;
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static void dummySetDispatchIndex(const char *name, int index)
Packit 5af8b3
{
Packit 5af8b3
    int i;
Packit 5af8b3
    for (i=0; i < DI_COUNT; i++) {
Packit 5af8b3
        if (strcmp(name, EGL_EXTENSION_PROCS[i].name) == 0) {
Packit 5af8b3
            EGL_EXTENSION_PROCS[i].index = index;
Packit 5af8b3
        }
Packit 5af8b3
    }
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
static EGLBoolean dummyGetSupportsAPI(EGLenum api)
Packit 5af8b3
{
Packit 5af8b3
    if (api == EGL_OPENGL_ES_API || api == EGL_OPENGL_API) {
Packit 5af8b3
        return EGL_TRUE;
Packit 5af8b3
    } else {
Packit 5af8b3
        return EGL_FALSE;
Packit 5af8b3
    }
Packit 5af8b3
}
Packit 5af8b3
Packit 5af8b3
PUBLIC EGLBoolean
Packit 5af8b3
__egl_Main(uint32_t version, const __EGLapiExports *exports,
Packit 5af8b3
     __EGLvendorInfo *vendor, __EGLapiImports *imports)
Packit 5af8b3
{
Packit 5af8b3
    if (EGL_VENDOR_ABI_GET_MAJOR_VERSION(version) !=
Packit 5af8b3
        EGL_VENDOR_ABI_MAJOR_VERSION) {
Packit 5af8b3
        return EGL_FALSE;
Packit 5af8b3
    }
Packit 5af8b3
Packit 5af8b3
    if (apiExports != NULL) {
Packit 5af8b3
        // Already initialized.
Packit 5af8b3
        return EGL_TRUE;
Packit 5af8b3
    }
Packit 5af8b3
Packit 5af8b3
    glvndSetupPthreads();
Packit 5af8b3
Packit 5af8b3
    apiExports = exports;
Packit 5af8b3
    __glvndPthreadFuncs.key_create(&threadStateKey, OnThreadTerminate);
Packit 5af8b3
    glvnd_list_init(&displayList);
Packit 5af8b3
Packit 5af8b3
    imports->getPlatformDisplay = dummyGetPlatformDisplay;
Packit 5af8b3
    imports->getSupportsAPI = dummyGetSupportsAPI;
Packit 5af8b3
    imports->getVendorString = dummyGetVendorString;
Packit 5af8b3
    imports->getProcAddress = dummyGetProcAddress;
Packit 5af8b3
    imports->getDispatchAddress = dummyFindDispatchFunction;
Packit 5af8b3
    imports->setDispatchIndex = dummySetDispatchIndex;
Packit 5af8b3
Packit 5af8b3
    return EGL_TRUE;
Packit 5af8b3
}
Packit 5af8b3