#include "libANGLE/Display.h"
#include <algorithm>
#include <iterator>
#include <sstream>
#include <vector>
#include <EGL/eglext.h>
#include <platform/PlatformMethods.h>
#include "anglebase/no_destructor.h"
#include "common/android_util.h"
#include "common/debug.h"
#include "common/mathutil.h"
#include "common/platform_helpers.h"
#include "common/string_utils.h"
#include "common/system_utils.h"
#include "common/tls.h"
#include "common/utilities.h"
#include "gpu_info_util/SystemInfo.h"
#include "image_util/loadimage.h"
#include "libANGLE/Context.h"
#include "libANGLE/Device.h"
#include "libANGLE/EGLSync.h"
#include "libANGLE/Image.h"
#include "libANGLE/ResourceManager.h"
#include "libANGLE/Stream.h"
#include "libANGLE/Surface.h"
#include "libANGLE/Thread.h"
#include "libANGLE/capture/FrameCapture.h"
#include "libANGLE/histogram_macros.h"
#include "libANGLE/renderer/DeviceImpl.h"
#include "libANGLE/renderer/DisplayImpl.h"
#include "libANGLE/renderer/ImageImpl.h"
#include "libANGLE/trace.h"
#if defined(ANGLE_PLATFORM_APPLE)
# include <dispatch/dispatch.h>
# include "common/tls.h"
#endif
#if defined(ANGLE_ENABLE_D3D9) || defined(ANGLE_ENABLE_D3D11)
# include "libANGLE/renderer/d3d/DisplayD3D.h"
#endif
#if defined(ANGLE_ENABLE_OPENGL)
# if defined(ANGLE_PLATFORM_WINDOWS)
# include "libANGLE/renderer/gl/wgl/DisplayWGL.h"
# elif ANGLE_ENABLE_CGL
# include "libANGLE/renderer/gl/cgl/DisplayCGL.h"
# elif ANGLE_ENABLE_EAGL
# include "libANGLE/renderer/gl/eagl/DisplayEAGL.h"
# elif defined(ANGLE_PLATFORM_LINUX)
# include "libANGLE/renderer/gl/egl/DisplayEGL.h"
# if defined(ANGLE_USE_X11)
# include "libANGLE/renderer/gl/glx/DisplayGLX_api.h"
# endif
# elif defined(ANGLE_PLATFORM_ANDROID)
# include "libANGLE/renderer/gl/egl/android/DisplayAndroid.h"
# else
# error Unsupported OpenGL platform.
# endif
#endif
#if defined(ANGLE_ENABLE_NULL)
# include "libANGLE/renderer/null/DisplayNULL.h"
#endif
#if defined(ANGLE_ENABLE_WGPU)
# include "libANGLE/renderer/wgpu/DisplayWgpu_api.h"
#endif
#if defined(ANGLE_ENABLE_VULKAN)
# include "libANGLE/renderer/vulkan/DisplayVk_api.h"
#endif
#if defined(ANGLE_ENABLE_METAL)
# include "libANGLE/renderer/metal/DisplayMtl_api.h"
#endif
namespace egl
{
namespace
{
struct TLSData
{ … };
TLSData::TLSData() : … { … }
#if defined(ANGLE_PLATFORM_APPLE)
static angle::TLSIndex GetDisplayTLSIndex()
{
static angle::TLSIndex DisplayIndex = TLS_INVALID_INDEX;
static dispatch_once_t once;
dispatch_once(&once, ^{
ASSERT(DisplayIndex == TLS_INVALID_INDEX);
DisplayIndex = angle::CreateTLSIndex(nullptr);
});
return DisplayIndex;
}
TLSData *GetDisplayTLS()
{
angle::TLSIndex DisplayIndex = GetDisplayTLSIndex();
ASSERT(DisplayIndex != TLS_INVALID_INDEX);
return static_cast<TLSData *>(angle::GetTLSValue(DisplayIndex));
}
void SetDisplayTLS(TLSData *tlsData)
{
angle::TLSIndex DisplayIndex = GetDisplayTLSIndex();
ASSERT(DisplayIndex != TLS_INVALID_INDEX);
angle::SetTLSValue(DisplayIndex, tlsData);
}
#else
thread_local TLSData *gDisplayTLS = …;
TLSData *GetDisplayTLS()
{ … }
#endif
constexpr angle::SubjectIndex kGPUSwitchedSubjectIndex = …;
static constexpr size_t kWindowSurfaceMapSize = …;
WindowSurfaceMap;
static WindowSurfaceMap *GetWindowSurfaces()
{ … }
size_t EGLStringArrayHash(const char **ary)
{ … }
struct ANGLEPlatformDisplay
{ … };
inline bool operator==(const ANGLEPlatformDisplay &a, const ANGLEPlatformDisplay &b)
{ … }
static constexpr size_t kANGLEPlatformDisplayMapSize = …;
ANGLEPlatformDisplayMap;
static ANGLEPlatformDisplayMap *GetANGLEPlatformDisplayMap()
{ … }
static constexpr size_t kDevicePlatformDisplayMapSize = …;
DevicePlatformDisplayMap;
static DevicePlatformDisplayMap *GetDevicePlatformDisplayMap()
{ … }
rx::DisplayImpl *CreateDisplayFromDevice(Device *eglDevice, const DisplayState &state)
{ … }
EGLAttrib GetDisplayTypeFromEnvironment()
{ … }
EGLAttrib GetDeviceTypeFromEnvironment()
{ … }
EGLAttrib GetPlatformTypeFromEnvironment()
{ … }
rx::DisplayImpl *CreateDisplayFromAttribs(EGLAttrib displayType,
EGLAttrib deviceType,
EGLAttrib platformType,
const DisplayState &state)
{ … }
void Display_logError(angle::PlatformMethods *platform, const char *errorMessage)
{ … }
void Display_logWarning(angle::PlatformMethods *platform, const char *warningMessage)
{ … }
void Display_logInfo(angle::PlatformMethods *platform, const char *infoMessage)
{ … }
const std::vector<std::string> EGLStringArrayToStringVector(const char **ary)
{ … }
void ANGLESetDefaultDisplayPlatform(angle::EGLDisplayType display)
{ … }
void UpdateAttribsFromEnvironment(AttributeMap &attribMap)
{ … }
static constexpr uint32_t kScratchBufferLifetime = …;
}
DisplayState::DisplayState(EGLNativeDisplayType nativeDisplayId)
: … { … }
DisplayState::~DisplayState() { … }
void DisplayState::notifyDeviceLost() const
{ … }
Display *Display::GetDisplayFromNativeDisplay(EGLenum platform,
EGLNativeDisplayType nativeDisplay,
const AttributeMap &attribMap)
{ … }
Display *Display::GetExistingDisplayFromNativeDisplay(EGLNativeDisplayType nativeDisplay)
{ … }
Display *Display::GetDisplayFromDevice(Device *device, const AttributeMap &attribMap)
{ … }
Display::EglDisplaySet Display::GetEglDisplaySet()
{ … }
Display::Display(EGLenum platform, EGLNativeDisplayType displayId, Device *eglDevice)
: … { … }
Display::~Display()
{ … }
void Display::setLabel(EGLLabelKHR label)
{ … }
EGLLabelKHR Display::getLabel() const
{ … }
void Display::onSubjectStateChange(angle::SubjectIndex index, angle::SubjectMessage message)
{ … }
void Display::setupDisplayPlatform(rx::DisplayImpl *impl)
{ … }
Error Display::initialize()
{ … }
Error Display::destroyInvalidEglObjects()
{ … }
Error Display::terminate(Thread *thread, TerminateReason terminateReason)
{ … }
#if ANGLE_USE_DISPLAY_PREPARE_FOR_CALL
Error Display::prepareForCall()
{
return mImplementation->prepareForCall();
}
#endif
Error Display::releaseThread()
{ … }
std::vector<const Config *> Display::getConfigs(const egl::AttributeMap &attribs) const
{ … }
std::vector<const Config *> Display::chooseConfig(const egl::AttributeMap &attribs) const
{ … }
Error Display::createWindowSurface(const Config *configuration,
EGLNativeWindowType window,
const AttributeMap &attribs,
Surface **outSurface)
{ … }
Error Display::createPbufferSurface(const Config *configuration,
const AttributeMap &attribs,
Surface **outSurface)
{ … }
Error Display::createPbufferFromClientBuffer(const Config *configuration,
EGLenum buftype,
EGLClientBuffer clientBuffer,
const AttributeMap &attribs,
Surface **outSurface)
{ … }
Error Display::createPixmapSurface(const Config *configuration,
NativePixmapType nativePixmap,
const AttributeMap &attribs,
Surface **outSurface)
{ … }
Error Display::createImage(const gl::Context *context,
EGLenum target,
EGLClientBuffer buffer,
const AttributeMap &attribs,
Image **outImage)
{ … }
Error Display::createStream(const AttributeMap &attribs, Stream **outStream)
{ … }
Error Display::createContext(const Config *configuration,
gl::Context *shareContext,
EGLenum clientType,
const AttributeMap &attribs,
gl::Context **outContext)
{ … }
Error Display::createSync(const gl::Context *currentContext,
EGLenum type,
const AttributeMap &attribs,
Sync **outSync)
{ … }
Error Display::makeCurrent(Thread *thread,
gl::Context *previousContext,
egl::Surface *drawSurface,
egl::Surface *readSurface,
gl::Context *context)
{ … }
Error Display::restoreLostDevice()
{ … }
Error Display::destroySurfaceImpl(Surface *surface, SurfaceMap *surfaces)
{ … }
void Display::destroyImageImpl(Image *image, ImageMap *images)
{ … }
void Display::destroyStreamImpl(Stream *stream, StreamSet *streams)
{ … }
Error Display::releaseContext(gl::Context *context, Thread *thread)
{ … }
Error Display::releaseContextImpl(gl::Context *context, ContextMap *contexts)
{ … }
Error Display::destroyContext(Thread *thread, gl::Context *context)
{ … }
void Display::destroySyncImpl(SyncID syncId, SyncMap *syncs)
{ … }
void Display::destroyImage(Image *image)
{ … }
void Display::destroyStream(Stream *stream)
{ … }
Error Display::destroySurface(Surface *surface)
{ … }
void Display::destroySync(Sync *sync)
{ … }
bool Display::isDeviceLost() const
{ … }
bool Display::testDeviceLost()
{ … }
void Display::notifyDeviceLost()
{ … }
void Display::setBlobCacheFuncs(EGLSetBlobFuncANDROID set, EGLGetBlobFuncANDROID get)
{ … }
EGLClientBuffer Display::GetNativeClientBuffer(const AHardwareBuffer *buffer)
{ … }
Error Display::CreateNativeClientBuffer(const egl::AttributeMap &attribMap,
EGLClientBuffer *eglClientBuffer)
{ … }
Error Display::waitClient(const gl::Context *context)
{ … }
Error Display::waitNative(const gl::Context *context, EGLint engine)
{ … }
const Caps &Display::getCaps() const
{ … }
bool Display::isInitialized() const
{ … }
bool Display::isValidConfig(const Config *config) const
{ … }
bool Display::isValidContext(const gl::ContextID contextID) const
{ … }
bool Display::isValidSurface(SurfaceID surfaceID) const
{ … }
bool Display::isValidImage(ImageID imageID) const
{ … }
bool Display::isValidStream(const Stream *stream) const
{ … }
bool Display::isValidSync(SyncID syncID) const
{ … }
bool Display::hasExistingWindowSurface(EGLNativeWindowType window)
{ … }
static ClientExtensions GenerateClientExtensions()
{ … }
template <typename T>
static std::string GenerateExtensionsString(const T &extensions)
{ … }
const ClientExtensions &Display::GetClientExtensions()
{ … }
const std::string &Display::GetClientExtensionString()
{ … }
void Display::initDisplayExtensions()
{ … }
bool Display::isValidNativeWindow(EGLNativeWindowType window) const
{ … }
Error Display::validateClientBuffer(const Config *configuration,
EGLenum buftype,
EGLClientBuffer clientBuffer,
const AttributeMap &attribs) const
{ … }
Error Display::validateImageClientBuffer(const gl::Context *context,
EGLenum target,
EGLClientBuffer clientBuffer,
const egl::AttributeMap &attribs) const
{ … }
Error Display::valdiatePixmap(const Config *config,
EGLNativePixmapType pixmap,
const AttributeMap &attributes) const
{ … }
bool Display::isValidDisplay(const egl::Display *display)
{ … }
bool Display::isValidNativeDisplay(EGLNativeDisplayType display)
{ … }
void Display::initVendorString()
{ … }
void Display::initVersionString()
{ … }
void Display::initClientAPIString()
{ … }
void Display::initializeFrontendFeatures()
{ … }
const DisplayExtensions &Display::getExtensions() const
{ … }
const std::string &Display::getExtensionString() const
{ … }
const std::string &Display::getVendorString() const
{ … }
const std::string &Display::getVersionString() const
{ … }
const std::string &Display::getClientAPIString() const
{ … }
std::string Display::getBackendRendererDescription() const
{ … }
std::string Display::getBackendVendorString() const
{ … }
std::string Display::getBackendVersionString(bool includeFullVersion) const
{ … }
Device *Display::getDevice() const
{ … }
Surface *Display::getWGLSurface() const
{ … }
gl::Version Display::getMaxSupportedESVersion() const
{ … }
EGLint Display::programCacheGetAttrib(EGLenum attrib) const
{ … }
Error Display::programCacheQuery(EGLint index,
void *key,
EGLint *keysize,
void *binary,
EGLint *binarysize)
{ … }
Error Display::programCachePopulate(const void *key,
EGLint keysize,
const void *binary,
EGLint binarysize)
{ … }
EGLint Display::programCacheResize(EGLint limit, EGLenum mode)
{ … }
void Display::overrideFrontendFeatures(const std::vector<std::string> &featureNames, bool enabled)
{ … }
const char *Display::queryStringi(const EGLint name, const EGLint index)
{ … }
EGLAttrib Display::queryAttrib(const EGLint attribute)
{ … }
angle::ScratchBuffer Display::requestScratchBuffer()
{ … }
void Display::returnScratchBuffer(angle::ScratchBuffer scratchBuffer)
{ … }
angle::ScratchBuffer Display::requestZeroFilledBuffer()
{ … }
void Display::returnZeroFilledBuffer(angle::ScratchBuffer zeroFilledBuffer)
{ … }
angle::ScratchBuffer Display::requestScratchBufferImpl(
std::vector<angle::ScratchBuffer> *bufferVector)
{ … }
void Display::returnScratchBufferImpl(angle::ScratchBuffer scratchBuffer,
std::vector<angle::ScratchBuffer> *bufferVector)
{ … }
Error Display::handleGPUSwitch()
{ … }
Error Display::forceGPUSwitch(EGLint gpuIDHigh, EGLint gpuIDLow)
{ … }
Error Display::waitUntilWorkScheduled()
{ … }
bool Display::supportsDmaBufFormat(EGLint format) const
{ … }
Error Display::queryDmaBufFormats(EGLint max_formats, EGLint *formats, EGLint *num_formats)
{ … }
Error Display::queryDmaBufModifiers(EGLint format,
EGLint max_modifiers,
EGLuint64KHR *modifiers,
EGLBoolean *external_only,
EGLint *num_modifiers)
{ … }
angle::ImageLoadContext Display::getImageLoadContext() const
{ … }
const gl::Context *Display::getContext(gl::ContextID contextID) const
{ … }
const egl::Surface *Display::getSurface(egl::SurfaceID surfaceID) const
{ … }
const egl::Image *Display::getImage(egl::ImageID imageID) const
{ … }
const egl::Sync *Display::getSync(egl::SyncID syncID) const
{ … }
gl::Context *Display::getContext(gl::ContextID contextID)
{ … }
egl::Surface *Display::getSurface(egl::SurfaceID surfaceID)
{ … }
egl::Image *Display::getImage(egl::ImageID imageID)
{ … }
egl::Sync *Display::getSync(egl::SyncID syncID)
{ … }
void Display::InitTLS()
{ … }
angle::UnlockedTailCall *Display::GetCurrentThreadUnlockedTailCall()
{ … }
Error *Display::GetCurrentThreadErrorScratchSpace()
{ … }
}