1c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill#include "gtest/gtest.h"
2c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill
3c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill#define GL_GLEXT_PROTOTYPES
4c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill
5c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill#include <EGL/egl.h>
6c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill#include <EGL/eglext.h>
7c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill
8c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madilltypedef EGLAPI EGLDisplay EGLAPIENTRY EGLGetDisplay(EGLNativeDisplayType display_id);
9c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madilltypedef EGLAPI EGLBoolean EGLAPIENTRY EGLInitialize(EGLDisplay dpy, EGLint *major, EGLint *minor);
10c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madilltypedef EGLAPI EGLContext EGLAPIENTRY EGLGetCurrentContext(void);
11c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madilltypedef EGLAPI EGLSurface EGLAPIENTRY EGLGetCurrentSurface(EGLint readdraw);
12c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill
13c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madillclass EGLThreadTest : public testing::Test
14c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill{
15c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill  public:
16c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    virtual void SetUp() {}
17c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    virtual void TearDown() {}
18c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill
19c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    EGLGetDisplay *mGetDisplay;
20c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    EGLInitialize *mInitialize;
21c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    EGLGetCurrentContext *mGetCurrentContext;
22c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    EGLGetCurrentSurface *mGetCurrentSurface;
23c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill
24c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    EGLDisplay mDisplay;
25c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill
26c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    HMODULE mEGL;
27c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    HMODULE mGLESv2;
28c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill
29c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    static DWORD WINAPI ThreadingTestEntryPoint(LPVOID thisPointer);
30c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill
31c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill  private:
32c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    void ThreadingTest();
33c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill};
34c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill
35c5a631240d0a79096ba9f1d189a91f411e67407cJamie MadillDWORD WINAPI EGLThreadTest::ThreadingTestEntryPoint(LPVOID lpParameter)
36c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill{
37c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    EGLThreadTest *test = (EGLThreadTest *)lpParameter;
38c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    test->ThreadingTest();
39c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    return 0;
40c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill}
41c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill
42c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madillvoid EGLThreadTest::ThreadingTest()
43c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill{
445df9f5233c7aa6b92987f32ea6d62cbe5e1800f8Geoff Lang    mEGL = LoadLibrary(TEXT("libEGL.dll"));
455df9f5233c7aa6b92987f32ea6d62cbe5e1800f8Geoff Lang    mGLESv2 = LoadLibrary(TEXT("libGLESv2.dll"));
46c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill
47c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    EXPECT_TRUE(mEGL != NULL);
48c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    EXPECT_TRUE(mGLESv2 != NULL);
49c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill
50c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    mGetDisplay = (EGLGetDisplay *)GetProcAddress(mEGL, "eglGetDisplay");
51c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    mInitialize = (EGLInitialize *)GetProcAddress(mEGL, "eglInitialize");
52c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    mGetCurrentContext = (EGLGetCurrentContext *)GetProcAddress(mEGL, "eglGetCurrentContext");
53c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    mGetCurrentSurface = (EGLGetCurrentSurface *)GetProcAddress(mEGL, "eglGetCurrentSurface");
54c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill
55c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    EXPECT_TRUE(mGetDisplay != NULL);
56c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    EXPECT_TRUE(mInitialize != NULL);
57c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    EXPECT_TRUE(mGetCurrentContext != NULL);
58c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    EXPECT_TRUE(mGetCurrentSurface != NULL);
59c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill
60c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    mDisplay = mGetDisplay(EGL_D3D11_ELSE_D3D9_DISPLAY_ANGLE);
61c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill
62c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    EXPECT_TRUE(mDisplay!= EGL_NO_DISPLAY);
63c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill
64c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    mInitialize(mDisplay, NULL, NULL);
65c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    mGetCurrentContext();
66c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill}
67c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill
68c5a631240d0a79096ba9f1d189a91f411e67407cJamie MadillTEST_F(EGLThreadTest, thread_init_crash)
69c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill{
70c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    DWORD threadId;
71c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    HANDLE threadHandle = CreateThread(NULL, 0, EGLThreadTest::ThreadingTestEntryPoint, this, 0, &threadId);
72c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    EXPECT_TRUE(threadHandle != NULL);
73c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill
74c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    // wait for signal from thread
75c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    DWORD waitResult = WaitForSingleObject(threadHandle, 1000);
76c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    EXPECT_EQ(waitResult, WAIT_OBJECT_0);
77c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill
78c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    // crash, because the TLS value is NULL on main thread
79c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    mGetCurrentSurface(EGL_DRAW);
80c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill    mGetCurrentContext();
81c5a631240d0a79096ba9f1d189a91f411e67407cJamie Madill}