Flutter Engine
The Flutter Engine
mock_gles.cc
Go to the documentation of this file.
1// Copyright 2013 The Flutter Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5#include <memory>
6
7#include "GLES3/gl3.h"
8#include "fml/logging.h"
11
12namespace impeller {
13namespace testing {
14
15// OpenGLES is not thread safe.
16//
17// This mutex is used to ensure that only one test is using the mock at a time.
18static std::mutex g_test_lock;
19
20static std::weak_ptr<MockGLES> g_mock_gles;
21
23
24static std::vector<const unsigned char*> g_extensions;
25
26static const unsigned char* g_version;
27
28// Has friend visibility into MockGLES to record calls.
29void RecordGLCall(const char* name) {
30 if (auto mock_gles = g_mock_gles.lock()) {
31 mock_gles->RecordCall(name);
32 }
33}
34
35template <typename T, typename U>
36struct CheckSameSignature : std::false_type {};
37
38template <typename Ret, typename... Args>
39struct CheckSameSignature<Ret(Args...), Ret(Args...)> : std::true_type {};
40
41// This is a stub function that does nothing/records nothing.
42void doNothing() {}
43
44auto const kMockVendor = (unsigned char*)"MockGLES";
45const auto kMockShadingLanguageVersion = (unsigned char*)"GLSL ES 1.0";
46auto const kExtensions = std::vector<const unsigned char*>{
47 (unsigned char*)"GL_KHR_debug" //
48};
49
50const unsigned char* mockGetString(GLenum name) {
51 switch (name) {
52 case GL_VENDOR:
53 return kMockVendor;
54 case GL_VERSION:
55 return g_version;
56 case GL_SHADING_LANGUAGE_VERSION:
58 default:
59 return (unsigned char*)"";
60 }
61}
62
63static_assert(CheckSameSignature<decltype(mockGetString), //
64 decltype(glGetString)>::value);
65
66const unsigned char* mockGetStringi(GLenum name, GLuint index) {
67 switch (name) {
68 case GL_EXTENSIONS:
69 return g_extensions[index];
70 default:
71 return (unsigned char*)"";
72 }
73}
74
75static_assert(CheckSameSignature<decltype(mockGetStringi), //
76 decltype(glGetStringi)>::value);
77
78void mockGetIntegerv(GLenum name, int* value) {
79 switch (name) {
80 case GL_NUM_EXTENSIONS: {
81 *value = g_extensions.size();
82 } break;
83 case GL_MAX_COMBINED_TEXTURE_IMAGE_UNITS:
84 *value = 8;
85 break;
86 default:
87 *value = 0;
88 break;
89 }
90}
91
92static_assert(CheckSameSignature<decltype(mockGetIntegerv), //
93 decltype(glGetIntegerv)>::value);
94
95GLenum mockGetError() {
96 return GL_NO_ERROR;
97}
98
99static_assert(CheckSameSignature<decltype(mockGetError), //
100 decltype(glGetError)>::value);
101
103 RecordGLCall("PopDebugGroupKHR");
104}
105
106static_assert(CheckSameSignature<decltype(mockPopDebugGroupKHR), //
107 decltype(glPopDebugGroupKHR)>::value);
108
110 GLuint id,
111 GLsizei length,
112 const GLchar* message) {
113 RecordGLCall("PushDebugGroupKHR");
114}
115
116static_assert(CheckSameSignature<decltype(mockPushDebugGroupKHR), //
117 decltype(glPushDebugGroupKHR)>::value);
118
119void mockGenQueriesEXT(GLsizei n, GLuint* ids) {
120 RecordGLCall("glGenQueriesEXT");
121 for (auto i = 0; i < n; i++) {
122 ids[i] = i + 1;
123 }
124}
125
126static_assert(CheckSameSignature<decltype(mockGenQueriesEXT), //
127 decltype(glGenQueriesEXT)>::value);
128
129void mockBeginQueryEXT(GLenum target, GLuint id) {
130 RecordGLCall("glBeginQueryEXT");
131}
132
133static_assert(CheckSameSignature<decltype(mockBeginQueryEXT), //
134 decltype(glBeginQueryEXT)>::value);
135
136void mockEndQueryEXT(GLuint id) {
137 RecordGLCall("glEndQueryEXT");
138}
139
140static_assert(CheckSameSignature<decltype(mockEndQueryEXT), //
141 decltype(glEndQueryEXT)>::value);
142
143void mockGetQueryObjectuivEXT(GLuint id, GLenum target, GLuint* result) {
144 RecordGLCall("glGetQueryObjectuivEXT");
145 *result = GL_TRUE;
146}
147
148static_assert(CheckSameSignature<decltype(mockGetQueryObjectuivEXT), //
149 decltype(glGetQueryObjectuivEXT)>::value);
150
151void mockGetQueryObjectui64vEXT(GLuint id, GLenum target, GLuint64* result) {
152 RecordGLCall("glGetQueryObjectui64vEXT");
153 *result = 1000u;
154}
155
156static_assert(CheckSameSignature<decltype(mockGetQueryObjectui64vEXT), //
157 decltype(glGetQueryObjectui64vEXT)>::value);
158
159void mockDeleteQueriesEXT(GLsizei size, const GLuint* queries) {
160 RecordGLCall("glDeleteQueriesEXT");
161}
162
163static_assert(CheckSameSignature<decltype(mockDeleteQueriesEXT), //
164 decltype(glDeleteQueriesEXT)>::value);
165
166std::shared_ptr<MockGLES> MockGLES::Init(
167 const std::optional<std::vector<const unsigned char*>>& extensions,
168 const char* version_string,
169 ProcTableGLES::Resolver resolver) {
170 // If we cannot obtain a lock, MockGLES is already being used elsewhere.
171 FML_CHECK(g_test_lock.try_lock())
172 << "MockGLES is already being used by another test.";
173 g_version = (unsigned char*)version_string;
175 auto mock_gles = std::shared_ptr<MockGLES>(new MockGLES(std::move(resolver)));
176 g_mock_gles = mock_gles;
177 return mock_gles;
178}
179
181 if (strcmp(name, "glPopDebugGroupKHR") == 0) {
182 return reinterpret_cast<void*>(&mockPopDebugGroupKHR);
183 } else if (strcmp(name, "glPushDebugGroupKHR") == 0) {
184 return reinterpret_cast<void*>(&mockPushDebugGroupKHR);
185 } else if (strcmp(name, "glGetString") == 0) {
186 return reinterpret_cast<void*>(&mockGetString);
187 } else if (strcmp(name, "glGetStringi") == 0) {
188 return reinterpret_cast<void*>(&mockGetStringi);
189 } else if (strcmp(name, "glGetIntegerv") == 0) {
190 return reinterpret_cast<void*>(&mockGetIntegerv);
191 } else if (strcmp(name, "glGetError") == 0) {
192 return reinterpret_cast<void*>(&mockGetError);
193 } else if (strcmp(name, "glGenQueriesEXT") == 0) {
194 return reinterpret_cast<void*>(&mockGenQueriesEXT);
195 } else if (strcmp(name, "glBeginQueryEXT") == 0) {
196 return reinterpret_cast<void*>(&mockBeginQueryEXT);
197 } else if (strcmp(name, "glEndQueryEXT") == 0) {
198 return reinterpret_cast<void*>(&mockEndQueryEXT);
199 } else if (strcmp(name, "glDeleteQueriesEXT") == 0) {
200 return reinterpret_cast<void*>(&mockDeleteQueriesEXT);
201 } else if (strcmp(name, "glGetQueryObjectui64vEXT") == 0) {
202 return reinterpret_cast<void*>(mockGetQueryObjectui64vEXT);
203 } else if (strcmp(name, "glGetQueryObjectuivEXT") == 0) {
204 return reinterpret_cast<void*>(mockGetQueryObjectuivEXT);
205 } else {
206 return reinterpret_cast<void*>(&doNothing);
207 }
208};
209
210MockGLES::MockGLES(ProcTableGLES::Resolver resolver)
211 : proc_table_(std::move(resolver)) {}
212
213MockGLES::~MockGLES() {
214 g_test_lock.unlock();
215}
216
217} // namespace testing
218} // namespace impeller
std::function< void *(const char *function_name)> Resolver
Provides a mocked version of the |ProcTableGLES| class.
Definition: mock_gles.h:26
static std::shared_ptr< MockGLES > Init(const std::optional< std::vector< const unsigned char * > > &extensions=std::nullopt, const char *version_string="OpenGL ES 3.0", ProcTableGLES::Resolver resolver=kMockResolverGLES)
Returns an initialized |MockGLES| instance.
Definition: mock_gles.cc:166
SkBitmap source
Definition: examples.cpp:28
uint8_t value
GAsyncResult * result
uint32_t * target
#define FML_CHECK(condition)
Definition: logging.h:85
size_t length
Win32Message message
DEF_SWITCHES_START aot vmservice shared library name
Definition: switches.h:32
it will be possible to load the file into Perfetto s trace viewer disable asset Prevents usage of any non test fonts unless they were explicitly Loaded via prefetched default font Indicates whether the embedding started a prefetch of the default font manager before creating the engine run In non interactive keep the shell running after the Dart script has completed enable serial On low power devices with low core running concurrent GC tasks on threads can cause them to contend with the UI thread which could potentially lead to jank This option turns off all concurrent GC activities domain network JSON encoded network policy per domain This overrides the DisallowInsecureConnections switch Embedder can specify whether to allow or disallow insecure connections at a domain level old gen heap size
Definition: switches.h:259
void mockDeleteQueriesEXT(GLsizei size, const GLuint *queries)
Definition: mock_gles.cc:159
void mockGetQueryObjectuivEXT(GLuint id, GLenum target, GLuint *result)
Definition: mock_gles.cc:143
static std::mutex g_test_lock
Definition: mock_gles.cc:18
GLenum mockGetError()
Definition: mock_gles.cc:95
const auto kMockShadingLanguageVersion
Definition: mock_gles.cc:45
void mockPopDebugGroupKHR()
Definition: mock_gles.cc:102
const unsigned char * mockGetStringi(GLenum name, GLuint index)
Definition: mock_gles.cc:66
void mockGetIntegerv(GLenum name, int *value)
Definition: mock_gles.cc:78
void mockGetQueryObjectui64vEXT(GLuint id, GLenum target, GLuint64 *result)
Definition: mock_gles.cc:151
auto const kExtensions
Definition: mock_gles.cc:46
void RecordGLCall(const char *name)
Definition: mock_gles.cc:29
static std::weak_ptr< MockGLES > g_mock_gles
Definition: mock_gles.cc:20
static ProcTableGLES::Resolver g_resolver
Definition: mock_gles.cc:22
auto const kMockVendor
Definition: mock_gles.cc:44
const ProcTableGLES::Resolver kMockResolverGLES
Definition: mock_gles.cc:180
void mockPushDebugGroupKHR(GLenum source, GLuint id, GLsizei length, const GLchar *message)
Definition: mock_gles.cc:109
static std::vector< const unsigned char * > g_extensions
Definition: mock_gles.cc:24
void mockEndQueryEXT(GLuint id)
Definition: mock_gles.cc:136
void mockGenQueriesEXT(GLsizei n, GLuint *ids)
Definition: mock_gles.cc:119
const unsigned char * mockGetString(GLenum name)
Definition: mock_gles.cc:50
void mockBeginQueryEXT(GLenum target, GLuint id)
Definition: mock_gles.cc:129
static const unsigned char * g_version
Definition: mock_gles.cc:26
Definition: ref_ptr.h:256