• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 //
2 // Copyright 2002 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 // Display.h: Defines the egl::Display class, representing the abstract
8 // display on which graphics are drawn. Implements EGLDisplay.
9 // [EGL 1.4] section 2.1.2 page 3.
10 
11 #ifndef LIBANGLE_DISPLAY_H_
12 #define LIBANGLE_DISPLAY_H_
13 
14 #include <mutex>
15 #include <set>
16 #include <vector>
17 
18 #include "libANGLE/AttributeMap.h"
19 #include "libANGLE/BlobCache.h"
20 #include "libANGLE/Caps.h"
21 #include "libANGLE/Config.h"
22 #include "libANGLE/Context.h"
23 #include "libANGLE/Debug.h"
24 #include "libANGLE/Error.h"
25 #include "libANGLE/LoggingAnnotator.h"
26 #include "libANGLE/MemoryProgramCache.h"
27 #include "libANGLE/Observer.h"
28 #include "libANGLE/Version.h"
29 #include "platform/Feature.h"
30 #include "platform/FrontendFeatures.h"
31 
32 namespace angle
33 {
34 class FrameCaptureShared;
35 }  // namespace angle
36 
37 namespace gl
38 {
39 class Context;
40 class TextureManager;
41 class SemaphoreManager;
42 }  // namespace gl
43 
44 namespace rx
45 {
46 class DisplayImpl;
47 class EGLImplFactory;
48 class ShareGroupImpl;
49 }  // namespace rx
50 
51 namespace egl
52 {
53 class Device;
54 class Image;
55 class Stream;
56 class Surface;
57 class Sync;
58 class Thread;
59 
60 using SurfaceSet = std::set<Surface *>;
61 
62 struct DisplayState final : private angle::NonCopyable
63 {
64     DisplayState(EGLNativeDisplayType nativeDisplayId);
65     ~DisplayState();
66 
67     EGLLabelKHR label;
68     SurfaceSet surfaceSet;
69     std::vector<std::string> featureOverridesEnabled;
70     std::vector<std::string> featureOverridesDisabled;
71     bool featuresAllDisabled;
72     EGLNativeDisplayType displayId;
73 };
74 
75 using ContextSet = std::set<gl::Context *>;
76 
77 class ShareGroup final : angle::NonCopyable
78 {
79   public:
80     ShareGroup(rx::EGLImplFactory *factory);
81 
82     void addRef();
83 
84     void release(const egl::Display *display);
85 
getImplementation()86     rx::ShareGroupImpl *getImplementation() const { return mImplementation; }
87 
generateFramebufferSerial()88     rx::Serial generateFramebufferSerial() { return mFramebufferSerialFactory.generate(); }
89 
getFrameCaptureShared()90     angle::FrameCaptureShared *getFrameCaptureShared() { return mFrameCaptureShared.get(); }
91 
92     void finishAllContexts();
93 
getContexts()94     const ContextSet &getContexts() const { return mContexts; }
95     void addSharedContext(gl::Context *context);
96 
getShareGroupContextCount()97     size_t getShareGroupContextCount() const { return mContexts.size(); }
98 
99   protected:
100     ~ShareGroup();
101 
102   private:
103     size_t mRefCount;
104     rx::ShareGroupImpl *mImplementation;
105     rx::SerialFactory mFramebufferSerialFactory;
106 
107     // Note: we use a raw pointer here so we can exclude frame capture sources from the build.
108     std::unique_ptr<angle::FrameCaptureShared> mFrameCaptureShared;
109 
110     // The list of contexts within the share group
111     ContextSet mContexts;
112 };
113 
114 // Constant coded here as a reasonable limit.
115 constexpr EGLAttrib kProgramCacheSizeAbsoluteMax = 0x4000000;
116 
117 class Display final : public LabeledObject,
118                       public angle::ObserverInterface,
119                       public angle::NonCopyable
120 {
121   public:
122     ~Display() override;
123 
124     void setLabel(EGLLabelKHR label) override;
125     EGLLabelKHR getLabel() const override;
126 
127     // Observer implementation.
128     void onSubjectStateChange(angle::SubjectIndex index, angle::SubjectMessage message) override;
129 
130     Error initialize();
131 
132     enum class TerminateReason
133     {
134         Api,
135         InternalCleanup,
136         ProcessExit,
137 
138         InvalidEnum,
139         EnumCount = InvalidEnum,
140     };
141     Error terminate(Thread *thread, TerminateReason terminateReason);
142     // Called before all display state dependent EGL functions. Backends can set up, for example,
143     // thread-specific backend state through this function. Not called for functions that do not
144     // need the state.
145     Error prepareForCall();
146     // Called on eglReleaseThread. Backends can tear down thread-specific backend state through
147     // this function.
148     Error releaseThread();
149 
150     static Display *GetDisplayFromDevice(Device *device, const AttributeMap &attribMap);
151     static Display *GetDisplayFromNativeDisplay(EGLNativeDisplayType nativeDisplay,
152                                                 const AttributeMap &attribMap);
153     static Display *GetExistingDisplayFromNativeDisplay(EGLNativeDisplayType nativeDisplay);
154 
155     using EglDisplaySet = std::set<Display *>;
156     static EglDisplaySet GetEglDisplaySet();
157 
158     static const ClientExtensions &GetClientExtensions();
159     static const std::string &GetClientExtensionString();
160 
161     std::vector<const Config *> getConfigs(const AttributeMap &attribs) const;
162     std::vector<const Config *> chooseConfig(const AttributeMap &attribs) const;
163 
164     Error createWindowSurface(const Config *configuration,
165                               EGLNativeWindowType window,
166                               const AttributeMap &attribs,
167                               Surface **outSurface);
168     Error createPbufferSurface(const Config *configuration,
169                                const AttributeMap &attribs,
170                                Surface **outSurface);
171     Error createPbufferFromClientBuffer(const Config *configuration,
172                                         EGLenum buftype,
173                                         EGLClientBuffer clientBuffer,
174                                         const AttributeMap &attribs,
175                                         Surface **outSurface);
176     Error createPixmapSurface(const Config *configuration,
177                               NativePixmapType nativePixmap,
178                               const AttributeMap &attribs,
179                               Surface **outSurface);
180 
181     Error createImage(const gl::Context *context,
182                       EGLenum target,
183                       EGLClientBuffer buffer,
184                       const AttributeMap &attribs,
185                       Image **outImage);
186 
187     Error createStream(const AttributeMap &attribs, Stream **outStream);
188 
189     Error createContext(const Config *configuration,
190                         gl::Context *shareContext,
191                         const EGLenum clientType,
192                         const AttributeMap &attribs,
193                         gl::Context **outContext);
194 
195     Error createSync(const gl::Context *currentContext,
196                      EGLenum type,
197                      const AttributeMap &attribs,
198                      Sync **outSync);
199 
200     Error makeCurrent(Thread *thread,
201                       gl::Context *previousContext,
202                       Surface *drawSurface,
203                       Surface *readSurface,
204                       gl::Context *context);
205 
206     Error destroySurface(Surface *surface);
207     void destroyImage(Image *image);
208     void destroyStream(Stream *stream);
209     Error destroyContext(Thread *thread, gl::Context *context);
210 
211     void destroySync(Sync *sync);
212 
213     bool isInitialized() const;
214     bool isValidConfig(const Config *config) const;
215     bool isValidContext(const gl::Context *context) const;
216     bool isValidSurface(const Surface *surface) const;
217     bool isValidImage(const Image *image) const;
218     bool isValidStream(const Stream *stream) const;
219     bool isValidSync(const Sync *sync) const;
220     bool isValidNativeWindow(EGLNativeWindowType window) const;
221 
222     Error validateClientBuffer(const Config *configuration,
223                                EGLenum buftype,
224                                EGLClientBuffer clientBuffer,
225                                const AttributeMap &attribs) const;
226     Error validateImageClientBuffer(const gl::Context *context,
227                                     EGLenum target,
228                                     EGLClientBuffer clientBuffer,
229                                     const egl::AttributeMap &attribs) const;
230     Error valdiatePixmap(const Config *config,
231                          EGLNativePixmapType pixmap,
232                          const AttributeMap &attributes) const;
233 
234     static bool isValidDisplay(const Display *display);
235     static bool isValidNativeDisplay(EGLNativeDisplayType display);
236     static bool hasExistingWindowSurface(EGLNativeWindowType window);
237 
238     bool isDeviceLost() const;
239     bool testDeviceLost();
240     void notifyDeviceLost();
241 
242     void setBlobCacheFuncs(EGLSetBlobFuncANDROID set, EGLGetBlobFuncANDROID get);
areBlobCacheFuncsSet()243     bool areBlobCacheFuncsSet() const { return mBlobCache.areBlobCacheFuncsSet(); }
getBlobCache()244     BlobCache &getBlobCache() { return mBlobCache; }
245 
246     static EGLClientBuffer GetNativeClientBuffer(const struct AHardwareBuffer *buffer);
247     static Error CreateNativeClientBuffer(const egl::AttributeMap &attribMap,
248                                           EGLClientBuffer *eglClientBuffer);
249 
250     Error waitClient(const gl::Context *context);
251     Error waitNative(const gl::Context *context, EGLint engine);
252 
253     const Caps &getCaps() const;
254 
255     const DisplayExtensions &getExtensions() const;
256     const std::string &getExtensionString() const;
257     const std::string &getVendorString() const;
258     const std::string &getVersionString() const;
259 
260     std::string getBackendRendererDescription() const;
261     std::string getBackendVendorString() const;
262     std::string getBackendVersionString() const;
263 
264     EGLint programCacheGetAttrib(EGLenum attrib) const;
265     Error programCacheQuery(EGLint index,
266                             void *key,
267                             EGLint *keysize,
268                             void *binary,
269                             EGLint *binarysize);
270     Error programCachePopulate(const void *key,
271                                EGLint keysize,
272                                const void *binary,
273                                EGLint binarysize);
274     EGLint programCacheResize(EGLint limit, EGLenum mode);
275 
getAttributeMap()276     const AttributeMap &getAttributeMap() const { return mAttributeMap; }
getNativeDisplayId()277     EGLNativeDisplayType getNativeDisplayId() const { return mState.displayId; }
278 
getImplementation()279     rx::DisplayImpl *getImplementation() const { return mImplementation; }
280     Device *getDevice() const;
281     Surface *getWGLSurface() const;
getPlatform()282     EGLenum getPlatform() const { return mPlatform; }
283 
284     gl::Version getMaxSupportedESVersion() const;
285 
getState()286     const DisplayState &getState() const { return mState; }
287 
getFrontendFeatures()288     const angle::FrontendFeatures &getFrontendFeatures() { return mFrontendFeatures; }
289     void overrideFrontendFeatures(const std::vector<std::string> &featureNames, bool enabled);
290 
getFeatures()291     const angle::FeatureList &getFeatures() const { return mFeatures; }
292 
293     const char *queryStringi(const EGLint name, const EGLint index);
294 
295     EGLAttrib queryAttrib(const EGLint attribute);
296 
297     angle::ScratchBuffer requestScratchBuffer();
298     void returnScratchBuffer(angle::ScratchBuffer scratchBuffer);
299 
300     angle::ScratchBuffer requestZeroFilledBuffer();
301     void returnZeroFilledBuffer(angle::ScratchBuffer zeroFilledBuffer);
302 
303     egl::Error handleGPUSwitch();
304 
getDisplayGlobalMutex()305     std::mutex &getDisplayGlobalMutex() { return mDisplayGlobalMutex; }
getProgramCacheMutex()306     std::mutex &getProgramCacheMutex() { return mProgramCacheMutex; }
307 
308     // Installs LoggingAnnotator as the global DebugAnnotator, for back-ends that do not implement
309     // their own DebugAnnotator.
setGlobalDebugAnnotator()310     void setGlobalDebugAnnotator() { gl::InitializeDebugAnnotations(&mAnnotator); }
311 
312   private:
313     Display(EGLenum platform, EGLNativeDisplayType displayId, Device *eglDevice);
314 
setAttributes(const AttributeMap & attribMap)315     void setAttributes(const AttributeMap &attribMap) { mAttributeMap = attribMap; }
316 
317     void setupDisplayPlatform(rx::DisplayImpl *impl);
318 
319     void updateAttribsFromEnvironment(const AttributeMap &attribMap);
320 
321     Error restoreLostDevice();
322     Error releaseContext(gl::Context *context, Thread *thread);
323 
324     void initDisplayExtensions();
325     void initVendorString();
326     void initVersionString();
327     void initializeFrontendFeatures();
328 
329     angle::ScratchBuffer requestScratchBufferImpl(std::vector<angle::ScratchBuffer> *bufferVector);
330     void returnScratchBufferImpl(angle::ScratchBuffer scratchBuffer,
331                                  std::vector<angle::ScratchBuffer> *bufferVector);
332 
333     DisplayState mState;
334     rx::DisplayImpl *mImplementation;
335     angle::ObserverBinding mGPUSwitchedBinding;
336 
337     AttributeMap mAttributeMap;
338 
339     ConfigSet mConfigSet;
340 
341     ContextSet mContextSet;
342 
343     typedef std::set<Image *> ImageSet;
344     ImageSet mImageSet;
345 
346     typedef std::set<Stream *> StreamSet;
347     StreamSet mStreamSet;
348 
349     typedef std::set<Sync *> SyncSet;
350     SyncSet mSyncSet;
351 
352     bool mInitialized;
353     bool mDeviceLost;
354 
355     Caps mCaps;
356 
357     DisplayExtensions mDisplayExtensions;
358     std::string mDisplayExtensionString;
359 
360     std::string mVendorString;
361     std::string mVersionString;
362 
363     Device *mDevice;
364     Surface *mSurface;
365     EGLenum mPlatform;
366     angle::LoggingAnnotator mAnnotator;
367 
368     gl::TextureManager *mTextureManager;
369     gl::SemaphoreManager *mSemaphoreManager;
370     BlobCache mBlobCache;
371     gl::MemoryProgramCache mMemoryProgramCache;
372     size_t mGlobalTextureShareGroupUsers;
373     size_t mGlobalSemaphoreShareGroupUsers;
374 
375     angle::FrontendFeatures mFrontendFeatures;
376 
377     angle::FeatureList mFeatures;
378 
379     std::mutex mScratchBufferMutex;
380     std::vector<angle::ScratchBuffer> mScratchBuffers;
381     std::vector<angle::ScratchBuffer> mZeroFilledBuffers;
382 
383     std::mutex mDisplayGlobalMutex;
384     std::mutex mProgramCacheMutex;
385 
386     bool mIsTerminated;
387 };
388 
389 }  // namespace egl
390 
391 #endif  // LIBANGLE_DISPLAY_H_
392