blob: 9f7b05a3c900853dc981a13289bfa52b7af30cb4 [file] [log] [blame]
bsalomon@google.com27847de2011-02-22 20:59:41 +00001/*
epoger@google.comec3ed6a2011-07-28 14:26:00 +00002 * Copyright 2011 Google Inc.
3 *
4 * Use of this source code is governed by a BSD-style license that can be
5 * found in the LICENSE file.
bsalomon@google.com27847de2011-02-22 20:59:41 +00006 */
7
epoger@google.comec3ed6a2011-07-28 14:26:00 +00008
bsalomon@google.com9c1f1ac2012-05-07 17:09:37 +00009#include "GrGLUtil.h"
commit-bot@chromium.org215a6822013-09-05 18:28:42 +000010#include "SkMatrix.h"
bungeman@google.comfab44db2013-10-11 18:50:45 +000011#include <stdio.h>
bsalomon@google.comf987d1b2011-04-04 17:13:52 +000012
bsalomon@google.com0b77d682011-08-19 13:28:54 +000013void GrGLClearErr(const GrGLInterface* gl) {
commit-bot@chromium.orgc72425a2014-01-21 16:09:18 +000014 while (GR_GL_NO_ERROR != gl->fFunctions.fGetError()) {}
bsalomon@google.comf987d1b2011-04-04 17:13:52 +000015}
bsalomon@google.com27847de2011-02-22 20:59:41 +000016
bsalomon@google.com845eafd2012-06-18 12:27:29 +000017namespace {
18const char *get_error_string(uint32_t err) {
19 switch (err) {
20 case GR_GL_NO_ERROR:
21 return "";
22 case GR_GL_INVALID_ENUM:
23 return "Invalid Enum";
24 case GR_GL_INVALID_VALUE:
25 return "Invalid Value";
26 case GR_GL_INVALID_OPERATION:
27 return "Invalid Operation";
28 case GR_GL_OUT_OF_MEMORY:
29 return "Out of Memory";
30 case GR_GL_CONTEXT_LOST:
31 return "Context Lost";
32 }
33 return "Unknown";
34}
35}
36
bsalomon@google.com0b77d682011-08-19 13:28:54 +000037void GrGLCheckErr(const GrGLInterface* gl,
38 const char* location,
39 const char* call) {
40 uint32_t err = GR_GL_GET_ERROR(gl);
twiz@google.com0f31ca72011-03-18 17:38:11 +000041 if (GR_GL_NO_ERROR != err) {
tfarina38406c82014-10-31 07:11:12 -070042 SkDebugf("---- glGetError 0x%x(%s)", err, get_error_string(err));
bsalomon49f085d2014-09-05 13:34:00 -070043 if (location) {
tfarina38406c82014-10-31 07:11:12 -070044 SkDebugf(" at\n\t%s", location);
bsalomon@google.com27847de2011-02-22 20:59:41 +000045 }
bsalomon49f085d2014-09-05 13:34:00 -070046 if (call) {
tfarina38406c82014-10-31 07:11:12 -070047 SkDebugf("\n\t\t%s", call);
bsalomon@google.com27847de2011-02-22 20:59:41 +000048 }
tfarina38406c82014-10-31 07:11:12 -070049 SkDebugf("\n");
bsalomon@google.com27847de2011-02-22 20:59:41 +000050 }
51}
52
53///////////////////////////////////////////////////////////////////////////////
54
bsalomon@google.comd5d10492011-04-28 21:16:31 +000055#if GR_GL_LOG_CALLS
56 bool gLogCallsGL = !!(GR_GL_LOG_CALLS_START);
57#endif
bsalomon@google.com27847de2011-02-22 20:59:41 +000058
bsalomon@google.comd5d10492011-04-28 21:16:31 +000059#if GR_GL_CHECK_ERROR
60 bool gCheckErrorGL = !!(GR_GL_CHECK_ERROR_START);
61#endif
62
bsalomon@google.com9c1f1ac2012-05-07 17:09:37 +000063///////////////////////////////////////////////////////////////////////////////
64
commit-bot@chromium.org9e90aed2014-01-16 16:35:09 +000065GrGLStandard GrGLGetStandardInUseFromString(const char* versionString) {
bsalomon@google.com9c1f1ac2012-05-07 17:09:37 +000066 if (NULL == versionString) {
commit-bot@chromium.orge83b9b72014-05-01 19:21:41 +000067 SkDebugf("NULL GL version string.");
commit-bot@chromium.org9e90aed2014-01-16 16:35:09 +000068 return kNone_GrGLStandard;
bsalomon@google.com9c1f1ac2012-05-07 17:09:37 +000069 }
70
71 int major, minor;
72
73 // check for desktop
74 int n = sscanf(versionString, "%d.%d", &major, &minor);
75 if (2 == n) {
commit-bot@chromium.org9e90aed2014-01-16 16:35:09 +000076 return kGL_GrGLStandard;
bsalomon@google.com9c1f1ac2012-05-07 17:09:37 +000077 }
78
79 // check for ES 1
80 char profile[2];
bsalomon@google.com960d1142013-05-29 13:11:54 +000081 n = sscanf(versionString, "OpenGL ES-%c%c %d.%d", profile, profile+1, &major, &minor);
bsalomon@google.com9c1f1ac2012-05-07 17:09:37 +000082 if (4 == n) {
83 // we no longer support ES1.
commit-bot@chromium.org9e90aed2014-01-16 16:35:09 +000084 return kNone_GrGLStandard;
bsalomon@google.com9c1f1ac2012-05-07 17:09:37 +000085 }
86
87 // check for ES2
88 n = sscanf(versionString, "OpenGL ES %d.%d", &major, &minor);
89 if (2 == n) {
commit-bot@chromium.org9e90aed2014-01-16 16:35:09 +000090 return kGLES_GrGLStandard;
bsalomon@google.com9c1f1ac2012-05-07 17:09:37 +000091 }
commit-bot@chromium.org9e90aed2014-01-16 16:35:09 +000092 return kNone_GrGLStandard;
bsalomon@google.com9c1f1ac2012-05-07 17:09:37 +000093}
94
commit-bot@chromium.org459104c2013-06-14 14:42:56 +000095bool GrGLIsMesaFromVersionString(const char* versionString) {
96 int major, minor, mesaMajor, mesaMinor;
derekfa6ca5a02014-11-03 13:36:40 -080097
98 GrGLStandard standard = GrGLGetStandardInUseFromString(versionString);
99
100 if (standard == kGL_GrGLStandard) {
101 int n = sscanf(versionString, "%d.%d Mesa %d.%d", &major, &minor, &mesaMajor, &mesaMinor);
102 return 4 == n;
103 }
104 else {
105 int n = sscanf(versionString, "OpenGL ES %d.%d Mesa %d.%d", &major, &minor, &mesaMajor, &mesaMinor);
106 return 4 == n;
107 }
108 return false;
commit-bot@chromium.org459104c2013-06-14 14:42:56 +0000109}
110
commit-bot@chromium.orgc9424b82013-10-30 20:03:16 +0000111bool GrGLIsChromiumFromRendererString(const char* rendererString) {
112 return 0 == strcmp(rendererString, "Chromium");
113}
114
bsalomon@google.com9c1f1ac2012-05-07 17:09:37 +0000115GrGLVersion GrGLGetVersionFromString(const char* versionString) {
116 if (NULL == versionString) {
commit-bot@chromium.orge83b9b72014-05-01 19:21:41 +0000117 SkDebugf("NULL GL version string.");
commit-bot@chromium.orgf4e67e32014-04-30 01:26:04 +0000118 return GR_GL_INVALID_VER;
bsalomon@google.com9c1f1ac2012-05-07 17:09:37 +0000119 }
120
121 int major, minor;
122
bsalomon@google.com960d1142013-05-29 13:11:54 +0000123 // check for mesa
124 int mesaMajor, mesaMinor;
125 int n = sscanf(versionString, "%d.%d Mesa %d.%d", &major, &minor, &mesaMajor, &mesaMinor);
126 if (4 == n) {
joshualitt46821702014-07-30 11:49:12 -0700127 return GR_GL_VER(major, minor);
bsalomon@google.com960d1142013-05-29 13:11:54 +0000128 }
129
130 n = sscanf(versionString, "%d.%d", &major, &minor);
bsalomon@google.com9c1f1ac2012-05-07 17:09:37 +0000131 if (2 == n) {
132 return GR_GL_VER(major, minor);
133 }
134
135 char profile[2];
136 n = sscanf(versionString, "OpenGL ES-%c%c %d.%d", profile, profile+1,
137 &major, &minor);
138 if (4 == n) {
139 return GR_GL_VER(major, minor);
140 }
rmistry@google.comfbfcd562012-08-23 18:09:54 +0000141
bsalomon@google.com9c1f1ac2012-05-07 17:09:37 +0000142 n = sscanf(versionString, "OpenGL ES %d.%d", &major, &minor);
143 if (2 == n) {
144 return GR_GL_VER(major, minor);
145 }
146
commit-bot@chromium.orgf4e67e32014-04-30 01:26:04 +0000147 return GR_GL_INVALID_VER;
bsalomon@google.com9c1f1ac2012-05-07 17:09:37 +0000148}
149
150GrGLSLVersion GrGLGetGLSLVersionFromString(const char* versionString) {
151 if (NULL == versionString) {
commit-bot@chromium.orge83b9b72014-05-01 19:21:41 +0000152 SkDebugf("NULL GLSL version string.");
commit-bot@chromium.orgf4e67e32014-04-30 01:26:04 +0000153 return GR_GLSL_INVALID_VER;
bsalomon@google.com9c1f1ac2012-05-07 17:09:37 +0000154 }
155
156 int major, minor;
157
158 int n = sscanf(versionString, "%d.%d", &major, &minor);
159 if (2 == n) {
160 return GR_GLSL_VER(major, minor);
161 }
rmistry@google.comfbfcd562012-08-23 18:09:54 +0000162
bsalomon@google.com9c1f1ac2012-05-07 17:09:37 +0000163 n = sscanf(versionString, "OpenGL ES GLSL ES %d.%d", &major, &minor);
164 if (2 == n) {
165 return GR_GLSL_VER(major, minor);
166 }
167
168#ifdef SK_BUILD_FOR_ANDROID
169 // android hack until the gpu vender updates their drivers
170 n = sscanf(versionString, "OpenGL ES GLSL %d.%d", &major, &minor);
171 if (2 == n) {
172 return GR_GLSL_VER(major, minor);
173 }
174#endif
175
commit-bot@chromium.orgf4e67e32014-04-30 01:26:04 +0000176 return GR_GLSL_INVALID_VER;
bsalomon@google.com9c1f1ac2012-05-07 17:09:37 +0000177}
178
bsalomon@google.com0b1e4812012-10-23 13:52:43 +0000179GrGLVendor GrGLGetVendorFromString(const char* vendorString) {
bsalomon49f085d2014-09-05 13:34:00 -0700180 if (vendorString) {
bsalomon@google.com96966a52013-02-21 16:34:21 +0000181 if (0 == strcmp(vendorString, "ARM")) {
182 return kARM_GrGLVendor;
183 }
bsalomon@google.com3012ded2013-02-22 16:44:04 +0000184 if (0 == strcmp(vendorString, "Imagination Technologies")) {
185 return kImagination_GrGLVendor;
186 }
commit-bot@chromium.org54318d32014-02-14 17:27:04 +0000187 if (0 == strncmp(vendorString, "Intel ", 6) || 0 == strcmp(vendorString, "Intel")) {
bsalomon@google.com3012ded2013-02-22 16:44:04 +0000188 return kIntel_GrGLVendor;
189 }
commit-bot@chromium.org7a434a22013-08-21 14:01:56 +0000190 if (0 == strcmp(vendorString, "Qualcomm")) {
191 return kQualcomm_GrGLVendor;
192 }
bsalomone904c092014-07-17 10:50:59 -0700193 if (0 == strcmp(vendorString, "NVIDIA Corporation")) {
bsalomon63b21962014-11-05 07:05:34 -0800194 return kNVIDIA_GrGLVendor;
bsalomone904c092014-07-17 10:50:59 -0700195 }
bsalomon@google.com0b1e4812012-10-23 13:52:43 +0000196 }
bsalomon@google.com0b1e4812012-10-23 13:52:43 +0000197 return kOther_GrGLVendor;
198}
199
commit-bot@chromium.org0694ea72013-09-18 13:00:28 +0000200GrGLRenderer GrGLGetRendererFromString(const char* rendererString) {
bsalomon49f085d2014-09-05 13:34:00 -0700201 if (rendererString) {
commit-bot@chromium.org0694ea72013-09-18 13:00:28 +0000202 if (0 == strcmp(rendererString, "NVIDIA Tegra 3")) {
203 return kTegra3_GrGLRenderer;
commit-bot@chromium.org6dee8752014-02-07 22:39:01 +0000204 } else if (0 == strcmp(rendererString, "NVIDIA Tegra")) {
205 return kTegra2_GrGLRenderer;
commit-bot@chromium.org0694ea72013-09-18 13:00:28 +0000206 }
bsalomon63b21962014-11-05 07:05:34 -0800207 int lastDigit;
208 int n = sscanf(rendererString, "PowerVR SGX 54%d", &lastDigit);
209 if (1 == n && lastDigit >= 0 && lastDigit <= 9) {
210 return kPowerVR54x_GrGLRenderer;
211 }
212 static const char kPowerVRRogueStr[] = "PowerVR Rogue";
213 if (0 == strncmp(rendererString, kPowerVRRogueStr,
214 SK_ARRAY_COUNT(kPowerVRRogueStr)-1)) {
215 return kPowerVRRogue_GrGLRenderer;
216 }
commit-bot@chromium.org0694ea72013-09-18 13:00:28 +0000217 }
218 return kOther_GrGLRenderer;
219}
220
bsalomon@google.com9c1f1ac2012-05-07 17:09:37 +0000221GrGLVersion GrGLGetVersion(const GrGLInterface* gl) {
222 const GrGLubyte* v;
223 GR_GL_CALL_RET(gl, v, GetString(GR_GL_VERSION));
224 return GrGLGetVersionFromString((const char*) v);
225}
226
227GrGLSLVersion GrGLGetGLSLVersion(const GrGLInterface* gl) {
228 const GrGLubyte* v;
229 GR_GL_CALL_RET(gl, v, GetString(GR_GL_SHADING_LANGUAGE_VERSION));
230 return GrGLGetGLSLVersionFromString((const char*) v);
231}
bsalomon@google.com0b1e4812012-10-23 13:52:43 +0000232
233GrGLVendor GrGLGetVendor(const GrGLInterface* gl) {
234 const GrGLubyte* v;
235 GR_GL_CALL_RET(gl, v, GetString(GR_GL_VENDOR));
236 return GrGLGetVendorFromString((const char*) v);
237}
commit-bot@chromium.org215a6822013-09-05 18:28:42 +0000238
commit-bot@chromium.org0694ea72013-09-18 13:00:28 +0000239GrGLRenderer GrGLGetRenderer(const GrGLInterface* gl) {
240 const GrGLubyte* v;
241 GR_GL_CALL_RET(gl, v, GetString(GR_GL_RENDERER));
242 return GrGLGetRendererFromString((const char*) v);
243}
244
commit-bot@chromium.org215a6822013-09-05 18:28:42 +0000245template<> void GrGLGetMatrix<3>(GrGLfloat* dest, const SkMatrix& src) {
246 // Col 0
247 dest[0] = SkScalarToFloat(src[SkMatrix::kMScaleX]);
248 dest[1] = SkScalarToFloat(src[SkMatrix::kMSkewY]);
249 dest[2] = SkScalarToFloat(src[SkMatrix::kMPersp0]);
250
251 // Col 1
252 dest[3] = SkScalarToFloat(src[SkMatrix::kMSkewX]);
253 dest[4] = SkScalarToFloat(src[SkMatrix::kMScaleY]);
254 dest[5] = SkScalarToFloat(src[SkMatrix::kMPersp1]);
255
256 // Col 2
257 dest[6] = SkScalarToFloat(src[SkMatrix::kMTransX]);
258 dest[7] = SkScalarToFloat(src[SkMatrix::kMTransY]);
259 dest[8] = SkScalarToFloat(src[SkMatrix::kMPersp2]);
260}
261
262template<> void GrGLGetMatrix<4>(GrGLfloat* dest, const SkMatrix& src) {
263 // Col 0
264 dest[0] = SkScalarToFloat(src[SkMatrix::kMScaleX]);
265 dest[1] = SkScalarToFloat(src[SkMatrix::kMSkewY]);
266 dest[2] = 0;
267 dest[3] = SkScalarToFloat(src[SkMatrix::kMPersp0]);
268
269 // Col 1
270 dest[4] = SkScalarToFloat(src[SkMatrix::kMSkewX]);
271 dest[5] = SkScalarToFloat(src[SkMatrix::kMScaleY]);
272 dest[6] = 0;
273 dest[7] = SkScalarToFloat(src[SkMatrix::kMPersp1]);
274
275 // Col 2
276 dest[8] = 0;
277 dest[9] = 0;
278 dest[10] = 1;
279 dest[11] = 0;
280
281 // Col 3
282 dest[12] = SkScalarToFloat(src[SkMatrix::kMTransX]);
283 dest[13] = SkScalarToFloat(src[SkMatrix::kMTransY]);
284 dest[14] = 0;
285 dest[15] = SkScalarToFloat(src[SkMatrix::kMPersp2]);
286}
kkinnunenccdaa042014-08-20 01:36:23 -0700287
288GrGLenum GrToGLStencilFunc(GrStencilFunc basicFunc) {
289 static const GrGLenum gTable[] = {
290 GR_GL_ALWAYS, // kAlways_StencilFunc
291 GR_GL_NEVER, // kNever_StencilFunc
292 GR_GL_GREATER, // kGreater_StencilFunc
293 GR_GL_GEQUAL, // kGEqual_StencilFunc
294 GR_GL_LESS, // kLess_StencilFunc
295 GR_GL_LEQUAL, // kLEqual_StencilFunc,
296 GR_GL_EQUAL, // kEqual_StencilFunc,
297 GR_GL_NOTEQUAL, // kNotEqual_StencilFunc,
298 };
299 GR_STATIC_ASSERT(SK_ARRAY_COUNT(gTable) == kBasicStencilFuncCount);
300 GR_STATIC_ASSERT(0 == kAlways_StencilFunc);
301 GR_STATIC_ASSERT(1 == kNever_StencilFunc);
302 GR_STATIC_ASSERT(2 == kGreater_StencilFunc);
303 GR_STATIC_ASSERT(3 == kGEqual_StencilFunc);
304 GR_STATIC_ASSERT(4 == kLess_StencilFunc);
305 GR_STATIC_ASSERT(5 == kLEqual_StencilFunc);
306 GR_STATIC_ASSERT(6 == kEqual_StencilFunc);
307 GR_STATIC_ASSERT(7 == kNotEqual_StencilFunc);
308 SkASSERT((unsigned) basicFunc < kBasicStencilFuncCount);
309
310 return gTable[basicFunc];
311}