• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 //
2 // Copyright 2016 The ANGLE Project Authors. All rights reserved.
3 // Use of this source code is governed by a BSD-style license that can be
4 // found in the LICENSE file.
5 //
6 
7 // Thread.cpp : Defines the Thread class which represents a global EGL thread.
8 
9 #include "libANGLE/Thread.h"
10 
11 #include "libANGLE/Context.h"
12 #include "libANGLE/Debug.h"
13 #include "libANGLE/Display.h"
14 #include "libANGLE/Error.h"
15 
16 namespace angle
17 {
18 #if defined(ANGLE_USE_ANDROID_TLS_SLOT)
19 bool gUseAndroidOpenGLTlsSlot = false;
20 #endif
21 
PthreadKeyDestructorCallback(void * ptr)22 void PthreadKeyDestructorCallback(void *ptr)
23 {
24     egl::Thread *thread = static_cast<egl::Thread *>(ptr);
25     ASSERT(thread);
26 
27     egl::Display::EglDisplaySet displays = egl::Display::GetEglDisplaySet();
28     for (egl::Display *display : displays)
29     {
30         ASSERT(display);
31         // Perform necessary cleanup.
32         display->threadCleanup(thread);
33     }
34 }
35 }  // namespace angle
36 
37 namespace egl
38 {
39 namespace
40 {
41 Debug *sDebug = nullptr;
42 }  // namespace
43 
Thread()44 Thread::Thread()
45     : mLabel(nullptr),
46       mError(EGL_SUCCESS),
47       mAPI(EGL_OPENGL_ES_API),
48       mContext(static_cast<gl::Context *>(EGL_NO_CONTEXT))
49 {}
50 
setLabel(EGLLabelKHR label)51 void Thread::setLabel(EGLLabelKHR label)
52 {
53     mLabel = label;
54 }
55 
getLabel() const56 EGLLabelKHR Thread::getLabel() const
57 {
58     return mLabel;
59 }
60 
setSuccess()61 void Thread::setSuccess()
62 {
63     mError = EGL_SUCCESS;
64 }
65 
setError(EGLint error,const char * command,const LabeledObject * object,const char * message)66 void Thread::setError(EGLint error,
67                       const char *command,
68                       const LabeledObject *object,
69                       const char *message)
70 {
71     mError = error;
72     if (error != EGL_SUCCESS && message)
73     {
74         EnsureDebugAllocated();
75         sDebug->insertMessage(error, command, ErrorCodeToMessageType(error), getLabel(),
76                               object ? object->getLabel() : nullptr, message);
77     }
78 }
79 
setError(const Error & error,const char * command,const LabeledObject * object)80 void Thread::setError(const Error &error, const char *command, const LabeledObject *object)
81 {
82     mError = error.getCode();
83     if (error.isError() && !error.getMessage().empty())
84     {
85         EnsureDebugAllocated();
86         sDebug->insertMessage(error.getCode(), command, ErrorCodeToMessageType(error.getCode()),
87                               getLabel(), object ? object->getLabel() : nullptr,
88                               error.getMessage());
89     }
90 }
91 
getError() const92 EGLint Thread::getError() const
93 {
94     return mError;
95 }
96 
setAPI(EGLenum api)97 void Thread::setAPI(EGLenum api)
98 {
99     mAPI = api;
100 }
101 
getAPI() const102 EGLenum Thread::getAPI() const
103 {
104     return mAPI;
105 }
106 
setCurrent(gl::Context * context)107 void Thread::setCurrent(gl::Context *context)
108 {
109     mContext = context;
110     if (mContext)
111     {
112         ASSERT(mContext->getDisplay());
113         mContext->getDisplay()->addActiveThread(this);
114     }
115 }
116 
getCurrentDrawSurface() const117 Surface *Thread::getCurrentDrawSurface() const
118 {
119     if (mContext)
120     {
121         return mContext->getCurrentDrawSurface();
122     }
123     return nullptr;
124 }
125 
getCurrentReadSurface() const126 Surface *Thread::getCurrentReadSurface() const
127 {
128     if (mContext)
129     {
130         return mContext->getCurrentReadSurface();
131     }
132     return nullptr;
133 }
134 
getContext() const135 gl::Context *Thread::getContext() const
136 {
137     return mContext;
138 }
139 
getDisplay() const140 Display *Thread::getDisplay() const
141 {
142     if (mContext)
143     {
144         return mContext->getDisplay();
145     }
146     return nullptr;
147 }
148 
EnsureDebugAllocated()149 void EnsureDebugAllocated()
150 {
151     // All EGL calls use a global lock, this is thread safe
152     if (sDebug == nullptr)
153     {
154         sDebug = new Debug();
155     }
156 }
157 
DeallocateDebug()158 void DeallocateDebug()
159 {
160     SafeDelete(sDebug);
161 }
162 
GetDebug()163 Debug *GetDebug()
164 {
165     EnsureDebugAllocated();
166     return sDebug;
167 }
168 }  // namespace egl
169