Add flag for mapping buffer in native surface
[platform/core/uifw/dali-adaptor.git] / dali / internal / graphics / gles / egl-sync-implementation.cpp
1 /*
2  * Copyright (c) 2021 Samsung Electronics Co., Ltd.
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  *
16  */
17
18 // CLASS HEADER
19 #include <dali/internal/graphics/gles/egl-sync-implementation.h>
20
21 // EXTERNAL INCLUDES
22
23 #ifdef _ARCH_ARM_
24
25 #include <EGL/eglext.h>
26 #include <GLES2/gl2.h>
27 #include <GLES2/gl2ext.h>
28
29 #endif
30
31 #include <dali/integration-api/debug.h>
32
33 // INTERNAL INCLUDES
34 #include <dali/internal/graphics/gles/egl-implementation.h>
35
36 #ifdef _ARCH_ARM_
37
38 // function pointers
39 static PFNEGLCREATESYNCKHRPROC     eglCreateSyncKHR     = NULL;
40 static PFNEGLCLIENTWAITSYNCKHRPROC eglClientWaitSyncKHR = NULL;
41 static PFNEGLDESTROYSYNCKHRPROC    eglDestroySyncKHR    = NULL;
42
43 #endif
44
45 namespace Dali
46 {
47 namespace Internal
48 {
49 namespace Adaptor
50 {
51 #ifdef _ARCH_ARM_
52
53 EglSyncObject::EglSyncObject(EglImplementation& eglSyncImpl)
54 : mEglSync(NULL),
55   mEglImplementation(eglSyncImpl)
56 {
57   EGLDisplay display = mEglImplementation.GetDisplay();
58   mEglSync           = eglCreateSyncKHR(display, EGL_SYNC_FENCE_KHR, NULL);
59   if(mEglSync == EGL_NO_SYNC_KHR)
60   {
61     DALI_LOG_ERROR("eglCreateSyncKHR failed %#0.4x\n", eglGetError());
62     mEglSync = NULL;
63   }
64 }
65
66 EglSyncObject::~EglSyncObject()
67 {
68   if(mEglSync != NULL)
69   {
70     eglDestroySyncKHR(mEglImplementation.GetDisplay(), mEglSync);
71     EGLint error = eglGetError();
72     if(EGL_SUCCESS != error)
73     {
74       DALI_LOG_ERROR("eglDestroySyncKHR failed %#0.4x\n", error);
75     }
76   }
77 }
78
79 bool EglSyncObject::IsSynced()
80 {
81   bool synced = false;
82
83   if(mEglSync != NULL)
84   {
85     EGLint result = eglClientWaitSyncKHR(mEglImplementation.GetDisplay(), mEglSync, 0, 0ull);
86     EGLint error  = eglGetError();
87     if(EGL_SUCCESS != error)
88     {
89       DALI_LOG_ERROR("eglClientWaitSyncKHR failed %#0.4x\n", error);
90     }
91     else if(result == EGL_CONDITION_SATISFIED_KHR)
92     {
93       synced = true;
94     }
95   }
96
97   return synced;
98 }
99
100 EglSyncImplementation::EglSyncImplementation()
101 : mEglImplementation(NULL),
102   mSyncInitialized(false),
103   mSyncInitializeFailed(false)
104 {
105 }
106
107 EglSyncImplementation::~EglSyncImplementation()
108 {
109 }
110
111 void EglSyncImplementation::Initialize(EglImplementation* eglImpl)
112 {
113   mEglImplementation = eglImpl;
114 }
115
116 Integration::GlSyncAbstraction::SyncObject* EglSyncImplementation::CreateSyncObject()
117 {
118   DALI_ASSERT_ALWAYS(mEglImplementation && "Sync Implementation not initialized");
119   if(mSyncInitialized == false)
120   {
121     InitializeEglSync();
122   }
123
124   EglSyncObject* syncObject = new EglSyncObject(*mEglImplementation);
125   mSyncObjects.PushBack(syncObject);
126   return syncObject;
127 }
128
129 void EglSyncImplementation::DestroySyncObject(Integration::GlSyncAbstraction::SyncObject* syncObject)
130 {
131   DALI_ASSERT_ALWAYS(mEglImplementation && "Sync Implementation not initialized");
132
133   if(mSyncInitialized == false)
134   {
135     InitializeEglSync();
136   }
137
138   for(SyncIter iter = mSyncObjects.Begin(), end = mSyncObjects.End(); iter != end; ++iter)
139   {
140     if(*iter == syncObject)
141     {
142       mSyncObjects.Erase(iter);
143       break;
144     }
145   }
146   EglSyncObject* eglSyncObject = static_cast<EglSyncObject*>(syncObject);
147   delete eglSyncObject;
148 }
149
150 void EglSyncImplementation::InitializeEglSync()
151 {
152   if(!mSyncInitializeFailed)
153   {
154     eglCreateSyncKHR     = reinterpret_cast<PFNEGLCREATESYNCKHRPROC>(eglGetProcAddress("eglCreateSyncKHR"));
155     eglClientWaitSyncKHR = reinterpret_cast<PFNEGLCLIENTWAITSYNCKHRPROC>(eglGetProcAddress("eglClientWaitSyncKHR"));
156     eglDestroySyncKHR    = reinterpret_cast<PFNEGLDESTROYSYNCKHRPROC>(eglGetProcAddress("eglDestroySyncKHR"));
157   }
158
159   if(eglCreateSyncKHR && eglClientWaitSyncKHR && eglDestroySyncKHR)
160   {
161     mSyncInitialized = true;
162   }
163   else
164   {
165     mSyncInitializeFailed = true;
166   }
167 }
168
169 #else
170
171 EglSyncObject::EglSyncObject(EglImplementation& eglImpl)
172 : mPollCounter(3),
173   mEglImplementation(eglImpl)
174 {
175 }
176
177 EglSyncObject::~EglSyncObject()
178 {
179 }
180
181 bool EglSyncObject::IsSynced()
182 {
183   if(mPollCounter <= 0)
184   {
185     return true;
186   }
187   --mPollCounter;
188   return false;
189 }
190
191 EglSyncImplementation::EglSyncImplementation()
192 : mEglImplementation(NULL),
193   mSyncInitialized(false),
194   mSyncInitializeFailed(false)
195 {
196 }
197
198 EglSyncImplementation::~EglSyncImplementation()
199 {
200 }
201
202 void EglSyncImplementation::Initialize(EglImplementation* eglImpl)
203 {
204   mEglImplementation = eglImpl;
205 }
206
207 Integration::GlSyncAbstraction::SyncObject* EglSyncImplementation::CreateSyncObject()
208 {
209   DALI_ASSERT_ALWAYS(mEglImplementation && "Sync Implementation not initialized");
210   return new EglSyncObject(*mEglImplementation);
211 }
212
213 void EglSyncImplementation::DestroySyncObject(Integration::GlSyncAbstraction::SyncObject* syncObject)
214 {
215   DALI_ASSERT_ALWAYS(mEglImplementation && "Sync Implementation not initialized");
216
217   // The abstraction's virtual destructor is protected, so that Core can't delete the sync objects
218   // directly (This object also needs removing from the mSyncObject container in the ARM
219   // implementation above). We therefore need to cast to the actual implementation object first.
220   EglSyncObject* eglSyncObject = static_cast<EglSyncObject*>(syncObject);
221   delete eglSyncObject;
222 }
223
224 void EglSyncImplementation::InitializeEglSync()
225 {
226 }
227
228 #endif
229
230 } // namespace Adaptor
231 } // namespace Internal
232 } // namespace Dali