OpenGL ES SDK for Android ARM Developer Center
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
ListEGLConfigs.cpp
Go to the documentation of this file.
1 /* Copyright (c) 2012-2017, ARM Limited and Contributors
2  *
3  * SPDX-License-Identifier: MIT
4  *
5  * Permission is hereby granted, free of charge,
6  * to any person obtaining a copy of this software and associated documentation files (the "Software"),
7  * to deal in the Software without restriction, including without limitation the rights to
8  * use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software,
9  * and to permit persons to whom the Software is furnished to do so, subject to the following conditions:
10  *
11  * The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
12  *
13  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
14  * INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
15  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
16  * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
17  * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
18  * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
19  */
20 
30 #include <EGL/egl.h>
31 #include <cstdlib>
32 #include <cstdio>
33 
34 #include <jni.h>
35 #include <android/log.h>
36 
37 #include "Platform.h"
38 #include "AndroidPlatform.h"
39 
40 using namespace MaliSDK;
41 
42 /*
43  * Function pointer type, taking an EGL token and value
44  * returning a textual meaning
45  */
46 typedef const char*(*decodeToken)(EGLint);
47 const char* decodeColorBuffer(EGLint value);
48 const char* decodeCaveat(EGLint value);
49 const char* decodeSurface(EGLint value);
50 const char* decodeAPISupport(EGLint value);
51 
52 /* List of EGL attributes to query, text to be printed and function to decode meaning */
53 typedef struct {
54  EGLint attribute;
55  const char* text;
57 } query;
58 
59 /*
60  * Additional attributes to be inspected can be added here
61  * The first member is the attribute as passed to eglGetConfigAttrib.
62  * The value of the attribute can either be interpreted as
63  * (i) an integer in which case the string to be printed should
64  * contain a single integer format specifier e.g. %d or %x
65  * and the third member should be NULL
66  * or
67  * (ii) a value to be decoded into a human readable form e.g. a bitfield.
68  * In this case the third member is a pointer to a function of type
69  * decodeToken which will decode the attribute value. The string
70  * to be printed should contain a single string format specifier
71  * i.e. %s which will take the return value of the decode function.
72  */
74  {EGL_CONFIG_ID, " EGL_CONFIG_ID %d\n", NULL},
75  {EGL_CONFIG_CAVEAT, " Config caveat: %s ", decodeCaveat},
76  {EGL_COLOR_BUFFER_TYPE, " Colour buffer type: %s\n", decodeColorBuffer},
77  {EGL_BUFFER_SIZE, " Colour depth: %d", NULL},
78  {EGL_RED_SIZE, " Red %d ", NULL},
79  {EGL_GREEN_SIZE, " Green %d ", NULL},
80  {EGL_BLUE_SIZE, " Blue %d ", NULL},
81  {EGL_ALPHA_SIZE, " Alpha %d\n", NULL},
82  {EGL_DEPTH_SIZE, " Z-buffer bits: %d\n", NULL},
83  {EGL_SAMPLES, " %dx anti-aliasing\n", NULL},
84  {EGL_SURFACE_TYPE, " Surfaces: %s\n ", decodeSurface},
85  {EGL_RENDERABLE_TYPE, " API support: %s\n", decodeAPISupport},
86  {EGL_NONE, NULL, NULL}
87 };
88 
89 /*
90  * Decipher an EGLConfig into more human readable terms.
91  * EGLDisplay display : EGLDisplay handle required to call other EGL functions
92  * EGLConfig* configs: Pointer to array of EGLConfigs
93  * int configIndex: Element of list to inspect
94  */
95 void describeConfig(EGLDisplay display, EGLConfig* configs, int configIndex)
96 {
97  EGLint attribute;
98  EGLint value;
99  EGLint allAttributes = 0;
100 
101  LOGI("Config number %d in returned configs\n", configIndex);
102 
103  /* Loop through all the attributes listed in queryList */
104  while((attribute = queryList[allAttributes].attribute) != EGL_NONE)
105  {
106  /* Get the value of the attribute */
107  EGLBoolean result = eglGetConfigAttrib(display, configs[configIndex], attribute, &value);
108 
109  if(result == EGL_FALSE)
110  {
111  LOGE("eglGetConfigAttrib failed (%d, %d)\n", configIndex, allAttributes);
112  }
113  else
114  {
115  /*
116  * Display the information, calling a function to decode
117  * EGL tokens into human readable forms if available
118  */
119  if(queryList[allAttributes].meaning)
120  {
121  LOGI(queryList[allAttributes].text, queryList[allAttributes].meaning(value));
122  }
123  else
124  {
125  LOGI(queryList[allAttributes].text, value);
126  }
127  }
128  allAttributes++;
129  }
130  LOGI("\n");
131 }
132 
133 /* Decode EGL_SURFACE_TYPE */
134 const char* decodeSurfaceStrings[] = {
135  "None!",
136  "PBuffer",
137  "Pixmap",
138  "PBuffer+Pixmap",
139  "Window",
140  "Window+PBuffer",
141  "Window+Pixmap",
142  "Window+Pixmap+PBuffer"
143 };
144 
145 const char* decodeSurface(EGLint value)
146 {
147  /* TODO consider more than just bits 0-2 */
148  return decodeSurfaceStrings[value&7];
149 }
150 
151 /* Decode EGL_CONFIG_CAVEAT */
152 const char* decodeCaveat( EGLint value)
153 {
154  switch(value)
155  {
156  case EGL_NONE:
157  return "Normal";
158  break;
159  case EGL_SLOW_CONFIG:
160  return "Slow";
161  break;
162  case EGL_NON_CONFORMANT_CONFIG:
163  return "Non-conformant";
164  break;
165  default:
166  return "Unknown EGL_CONFIG_CAVEAT";
167  break;
168  }
169 }
170 
171 /* Decode EGL_COLOR_BUFFER_TYPE */
172 const char* decodeColorBuffer(EGLint value)
173 {
174  switch(value)
175  {
176  case EGL_RGB_BUFFER:
177  return "RGB colour buffer";
178  break;
179  case EGL_LUMINANCE_BUFFER:
180  return "Luminance buffer";
181  break;
182  default:
183  return "Unknown EGL_COLOR_BUFFER_TYPE";
184  break;
185  }
186 }
187 
188 /* Decode EGL_RENDERABLE_TYPE */
189 const char* decodeAPISupportStrings[] = {
190  "No API support(?)",
191  "OpenGL ES",
192  "OpenVG",
193  "OpenGL ES, OpenVG",
194  "OpenGL ES 2.0",
195  "OpenGL ES, OpenGL ES 2.0",
196  "OpenGL ES 2.0, OpenVG",
197  "OpenGL ES, OpenGL ES 2.0, OpenVG"
198 };
199 
200 const char* decodeAPISupport(EGLint value)
201 {
202  /* Ignores OpenGL (desktop) support (bit 3 set) */
203  return decodeAPISupportStrings[value&7];
204 }
205 
206 bool listConfigs(void)
207 {
208  EGLBoolean success;
209 
210  /* Get a display handle and initalize EGL */
211  EGLDisplay display = eglGetDisplay(EGL_DEFAULT_DISPLAY);
212  if(display == EGL_NO_DISPLAY)
213  {
214  LOGD("eglGetDisplay returned EGL_NO_DISPLAY\n");
215  return false;
216  }
217 
218  EGLint major, minor;
219  success = eglInitialize(display, &major, &minor);
220  if(success == EGL_FALSE)
221  {
222  LOGD("eglInitialize failed\n");
223  return false;
224  }
225  /* Read the vendor string */
226  const char *vendor = eglQueryString(display, EGL_VENDOR);
227  if(vendor == NULL)
228  {
229  LOGD("eglQueryString failed\n");
230  return false;
231  }
232 
233  LOGI("EGL_VENDOR = %s, version %d.%d\n", vendor, major, minor);
234 
235  /*
236  * Find out how many configs are available in total,
237  * allocate some memory to hold them, and then
238  * get all of the configs.
239  * In the first call to eglGetConfigs 'numberOfConfigs' is an
240  * output telling us the total number of configs
241  * available (total because we passed a NULL pointer
242  * to the memory to be filled with configs).
243  * In the second call to eglGetConfigs 'numberOfConfigs' is an
244  * input (telling EGL the size of the 'configs' buffer)
245  * and also an output telling us how many configs are
246  * in the configs.
247  * It should have the same value after both calls.
248  */
249  EGLint numberOfConfigs;
250  success = eglGetConfigs(display, NULL, 0, &numberOfConfigs);
251  EGLConfig *configs = (EGLConfig*)malloc(sizeof(EGLConfig)*numberOfConfigs);
252  success &= eglGetConfigs(display, configs, numberOfConfigs, &numberOfConfigs);
253  if(success == EGL_FALSE)
254  {
255  LOGD("eglGetConfigs failed\n");
256  return false;
257  }
258 
259  /* Look at each config */
260  for(int allConfigs = 0; allConfigs < numberOfConfigs; allConfigs++)
261  {
262  describeConfig(display, configs, allConfigs);
263  }
264 
265  free(configs);
266 
267  fflush(stdout);
268 
269  /* Tell EGL we have finished */
270  eglTerminate(display);
271 
272  return true;
273 }
274 
275 extern "C"
276 {
278  (JNIEnv *env, jclass jcls, jint width, jint height)
279  {
280  listConfigs();
281  }
282 
284  (JNIEnv *env, jclass jcls)
285  {
286  /* We don't need to render frames. */
287  }
288 
290  (JNIEnv *, jclass)
291  {
292 
293  }
294 }
const char *(* decodeToken)(EGLint)
decodeToken meaning
#define LOGI(...)
Definition: AstcTextures.h:29
const char * decodeCaveat(EGLint value)
GLint GLsizei GLsizei height
Definition: gl2ext.h:179
query queryList[]
GLint value
Definition: gl2ext.h:558
bool listConfigs(void)
#define LOGD(...)
Definition: AstcTextures.h:28
const char * decodeAPISupport(EGLint value)
JNIEXPORT void JNICALL Java_com_arm_malideveloper_openglessdk_listeglconfigs_ListEGLConfigs_init(JNIEnv *env, jclass jcls, jint width, jint height)
const char * decodeAPISupportStrings[]
const char * text
const char * decodeColorBuffer(EGLint value)
JNIEXPORT void JNICALL Java_com_arm_malideveloper_openglessdk_listeglconfigs_ListEGLConfigs_uninit(JNIEnv *, jclass)
const char * decodeSurfaceStrings[]
const char * decodeSurface(EGLint value)
#define LOGE(...)
Definition: AstcTextures.h:30
GLint GLsizei width
Definition: gl2ext.h:179
void describeConfig(EGLDisplay display, EGLConfig *configs, int configIndex)
JNIEXPORT void JNICALL Java_com_arm_malideveloper_openglessdk_listeglconfigs_ListEGLConfigs_step(JNIEnv *env, jclass jcls)
Text * text
Definition: AntiAlias.cpp:69
EGLint attribute