blob: ed4b50c49f2acabe3f6f60706c8cee95ad9e8cf7 [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) {
14 while (GR_GL_NO_ERROR != gl->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) {
bsalomon@google.com845eafd2012-06-18 12:27:29 +000042 GrPrintf("---- glGetError 0x%x(%s)", err, get_error_string(err));
bsalomon@google.com27847de2011-02-22 20:59:41 +000043 if (NULL != location) {
44 GrPrintf(" at\n\t%s", location);
45 }
46 if (NULL != call) {
47 GrPrintf("\n\t\t%s", call);
48 }
49 GrPrintf("\n");
50 }
51}
52
bsalomon@google.com960d1142013-05-29 13:11:54 +000053namespace {
54// Mesa uses a non-standard version string of format: 1.4 Mesa <mesa_major>.<mesa_minor>.
55// The mapping of from mesa version to GL version came from here: http://www.mesa3d.org/intro.html
56bool get_gl_version_for_mesa(int mesaMajorVersion, int* major, int* minor) {
57 switch (mesaMajorVersion) {
58 case 2:
59 case 3:
60 case 4:
61 case 5:
62 case 6:
63 *major = 1;
64 *minor = mesaMajorVersion - 1;
65 return true;
66 case 7:
67 *major = 2;
68 *minor = 1;
69 return true;
70 case 8:
71 *major = 3;
72 *minor = 0;
73 return true;
74 case 9:
75 *major = 3;
76 *minor = 1;
77 return true;
78 default:
79 return false;
80 }
81}
82}
83
bsalomon@google.com27847de2011-02-22 20:59:41 +000084///////////////////////////////////////////////////////////////////////////////
85
bsalomon@google.comd5d10492011-04-28 21:16:31 +000086#if GR_GL_LOG_CALLS
87 bool gLogCallsGL = !!(GR_GL_LOG_CALLS_START);
88#endif
bsalomon@google.com27847de2011-02-22 20:59:41 +000089
bsalomon@google.comd5d10492011-04-28 21:16:31 +000090#if GR_GL_CHECK_ERROR
91 bool gCheckErrorGL = !!(GR_GL_CHECK_ERROR_START);
92#endif
93
bsalomon@google.com9c1f1ac2012-05-07 17:09:37 +000094///////////////////////////////////////////////////////////////////////////////
95
96GrGLBinding GrGLGetBindingInUseFromString(const char* versionString) {
97 if (NULL == versionString) {
mtklein@google.com330313a2013-08-22 15:37:26 +000098 SkDEBUGFAIL("NULL GL version string.");
bsalomon@google.com9c1f1ac2012-05-07 17:09:37 +000099 return kNone_GrGLBinding;
100 }
101
102 int major, minor;
103
104 // check for desktop
105 int n = sscanf(versionString, "%d.%d", &major, &minor);
106 if (2 == n) {
107 return kDesktop_GrGLBinding;
108 }
109
110 // check for ES 1
111 char profile[2];
bsalomon@google.com960d1142013-05-29 13:11:54 +0000112 n = sscanf(versionString, "OpenGL ES-%c%c %d.%d", profile, profile+1, &major, &minor);
bsalomon@google.com9c1f1ac2012-05-07 17:09:37 +0000113 if (4 == n) {
114 // we no longer support ES1.
115 return kNone_GrGLBinding;
116 }
117
118 // check for ES2
119 n = sscanf(versionString, "OpenGL ES %d.%d", &major, &minor);
120 if (2 == n) {
bsalomon@google.com791816a2013-08-15 18:54:39 +0000121 return kES_GrGLBinding;
bsalomon@google.com9c1f1ac2012-05-07 17:09:37 +0000122 }
123 return kNone_GrGLBinding;
124}
125
commit-bot@chromium.org459104c2013-06-14 14:42:56 +0000126bool GrGLIsMesaFromVersionString(const char* versionString) {
127 int major, minor, mesaMajor, mesaMinor;
128 int n = sscanf(versionString, "%d.%d Mesa %d.%d", &major, &minor, &mesaMajor, &mesaMinor);
129 return 4 == n;
130}
131
bsalomon@google.com9c1f1ac2012-05-07 17:09:37 +0000132GrGLVersion GrGLGetVersionFromString(const char* versionString) {
133 if (NULL == versionString) {
mtklein@google.com330313a2013-08-22 15:37:26 +0000134 SkDEBUGFAIL("NULL GL version string.");
bsalomon@google.com9c1f1ac2012-05-07 17:09:37 +0000135 return 0;
136 }
137
138 int major, minor;
139
bsalomon@google.com960d1142013-05-29 13:11:54 +0000140 // check for mesa
141 int mesaMajor, mesaMinor;
142 int n = sscanf(versionString, "%d.%d Mesa %d.%d", &major, &minor, &mesaMajor, &mesaMinor);
143 if (4 == n) {
144 if (get_gl_version_for_mesa(mesaMajor, &major, &minor)) {
145 return GR_GL_VER(major, minor);
146 } else {
147 return 0;
148 }
149 }
150
151 n = sscanf(versionString, "%d.%d", &major, &minor);
bsalomon@google.com9c1f1ac2012-05-07 17:09:37 +0000152 if (2 == n) {
153 return GR_GL_VER(major, minor);
154 }
155
156 char profile[2];
157 n = sscanf(versionString, "OpenGL ES-%c%c %d.%d", profile, profile+1,
158 &major, &minor);
159 if (4 == n) {
160 return GR_GL_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 %d.%d", &major, &minor);
164 if (2 == n) {
165 return GR_GL_VER(major, minor);
166 }
167
168 return 0;
169}
170
171GrGLSLVersion GrGLGetGLSLVersionFromString(const char* versionString) {
172 if (NULL == versionString) {
mtklein@google.com330313a2013-08-22 15:37:26 +0000173 SkDEBUGFAIL("NULL GLSL version string.");
bsalomon@google.com9c1f1ac2012-05-07 17:09:37 +0000174 return 0;
175 }
176
177 int major, minor;
178
179 int n = sscanf(versionString, "%d.%d", &major, &minor);
180 if (2 == n) {
181 return GR_GLSL_VER(major, minor);
182 }
rmistry@google.comfbfcd562012-08-23 18:09:54 +0000183
bsalomon@google.com9c1f1ac2012-05-07 17:09:37 +0000184 n = sscanf(versionString, "OpenGL ES GLSL ES %d.%d", &major, &minor);
185 if (2 == n) {
186 return GR_GLSL_VER(major, minor);
187 }
188
189#ifdef SK_BUILD_FOR_ANDROID
190 // android hack until the gpu vender updates their drivers
191 n = sscanf(versionString, "OpenGL ES GLSL %d.%d", &major, &minor);
192 if (2 == n) {
193 return GR_GLSL_VER(major, minor);
194 }
195#endif
196
197 return 0;
198}
199
bsalomon@google.com0b1e4812012-10-23 13:52:43 +0000200GrGLVendor GrGLGetVendorFromString(const char* vendorString) {
201 if (NULL != vendorString) {
bsalomon@google.com96966a52013-02-21 16:34:21 +0000202 if (0 == strcmp(vendorString, "ARM")) {
203 return kARM_GrGLVendor;
204 }
bsalomon@google.com3012ded2013-02-22 16:44:04 +0000205 if (0 == strcmp(vendorString, "Imagination Technologies")) {
206 return kImagination_GrGLVendor;
207 }
208 if (0 == strcmp(vendorString, "Intel")) {
209 return kIntel_GrGLVendor;
210 }
commit-bot@chromium.org7a434a22013-08-21 14:01:56 +0000211 if (0 == strcmp(vendorString, "Qualcomm")) {
212 return kQualcomm_GrGLVendor;
213 }
bsalomon@google.com0b1e4812012-10-23 13:52:43 +0000214 }
bsalomon@google.com0b1e4812012-10-23 13:52:43 +0000215 return kOther_GrGLVendor;
216}
217
commit-bot@chromium.org0694ea72013-09-18 13:00:28 +0000218GrGLRenderer GrGLGetRendererFromString(const char* rendererString) {
219 if (NULL != rendererString) {
220 if (0 == strcmp(rendererString, "NVIDIA Tegra 3")) {
221 return kTegra3_GrGLRenderer;
222 }
223 }
224 return kOther_GrGLRenderer;
225}
226
bsalomon@google.com9c1f1ac2012-05-07 17:09:37 +0000227GrGLBinding GrGLGetBindingInUse(const GrGLInterface* gl) {
228 const GrGLubyte* v;
229 GR_GL_CALL_RET(gl, v, GetString(GR_GL_VERSION));
230 return GrGLGetBindingInUseFromString((const char*) v);
231}
232
233GrGLVersion GrGLGetVersion(const GrGLInterface* gl) {
234 const GrGLubyte* v;
235 GR_GL_CALL_RET(gl, v, GetString(GR_GL_VERSION));
236 return GrGLGetVersionFromString((const char*) v);
237}
238
239GrGLSLVersion GrGLGetGLSLVersion(const GrGLInterface* gl) {
240 const GrGLubyte* v;
241 GR_GL_CALL_RET(gl, v, GetString(GR_GL_SHADING_LANGUAGE_VERSION));
242 return GrGLGetGLSLVersionFromString((const char*) v);
243}
bsalomon@google.com0b1e4812012-10-23 13:52:43 +0000244
245GrGLVendor GrGLGetVendor(const GrGLInterface* gl) {
246 const GrGLubyte* v;
247 GR_GL_CALL_RET(gl, v, GetString(GR_GL_VENDOR));
248 return GrGLGetVendorFromString((const char*) v);
249}
commit-bot@chromium.org215a6822013-09-05 18:28:42 +0000250
commit-bot@chromium.org0694ea72013-09-18 13:00:28 +0000251GrGLRenderer GrGLGetRenderer(const GrGLInterface* gl) {
252 const GrGLubyte* v;
253 GR_GL_CALL_RET(gl, v, GetString(GR_GL_RENDERER));
254 return GrGLGetRendererFromString((const char*) v);
255}
256
commit-bot@chromium.org215a6822013-09-05 18:28:42 +0000257template<> void GrGLGetMatrix<3>(GrGLfloat* dest, const SkMatrix& src) {
258 // Col 0
259 dest[0] = SkScalarToFloat(src[SkMatrix::kMScaleX]);
260 dest[1] = SkScalarToFloat(src[SkMatrix::kMSkewY]);
261 dest[2] = SkScalarToFloat(src[SkMatrix::kMPersp0]);
262
263 // Col 1
264 dest[3] = SkScalarToFloat(src[SkMatrix::kMSkewX]);
265 dest[4] = SkScalarToFloat(src[SkMatrix::kMScaleY]);
266 dest[5] = SkScalarToFloat(src[SkMatrix::kMPersp1]);
267
268 // Col 2
269 dest[6] = SkScalarToFloat(src[SkMatrix::kMTransX]);
270 dest[7] = SkScalarToFloat(src[SkMatrix::kMTransY]);
271 dest[8] = SkScalarToFloat(src[SkMatrix::kMPersp2]);
272}
273
274template<> void GrGLGetMatrix<4>(GrGLfloat* dest, const SkMatrix& src) {
275 // Col 0
276 dest[0] = SkScalarToFloat(src[SkMatrix::kMScaleX]);
277 dest[1] = SkScalarToFloat(src[SkMatrix::kMSkewY]);
278 dest[2] = 0;
279 dest[3] = SkScalarToFloat(src[SkMatrix::kMPersp0]);
280
281 // Col 1
282 dest[4] = SkScalarToFloat(src[SkMatrix::kMSkewX]);
283 dest[5] = SkScalarToFloat(src[SkMatrix::kMScaleY]);
284 dest[6] = 0;
285 dest[7] = SkScalarToFloat(src[SkMatrix::kMPersp1]);
286
287 // Col 2
288 dest[8] = 0;
289 dest[9] = 0;
290 dest[10] = 1;
291 dest[11] = 0;
292
293 // Col 3
294 dest[12] = SkScalarToFloat(src[SkMatrix::kMTransX]);
295 dest[13] = SkScalarToFloat(src[SkMatrix::kMTransY]);
296 dest[14] = 0;
297 dest[15] = SkScalarToFloat(src[SkMatrix::kMPersp2]);
298}