1 /*
2 * Copyright © 2011 Intel Corporation
3 *
4 * Permission is hereby granted, free of charge, to any person obtaining a
5 * copy of this software and associated documentation files (the "Software"),
6 * to deal in the Software without restriction, including without limitation
7 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8 * and/or sell copies of the Software, and to permit persons to whom the
9 * Software is furnished to do so, subject to the following conditions:
10 *
11 * The above copyright notice and this permission notice (including the next
12 * paragraph) shall be included in all copies or substantial portions of the
13 * Software.
14 *
15 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
18 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
20 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
21 * DEALINGS IN THE SOFTWARE.
22 */
23 #include <gtest/gtest.h>
24 #include <string.h>
25
26 #include "glxclient.h"
27
28 #include <xcb/glx.h>
29
30 #include "mock_xdisplay.h"
31 #include "fake_glx_screen.h"
32
33 /**
34 * \name Wrappers around some X structures to make the more usable for tests
35 */
36 /*@{*/
37 class fake_glx_screen;
38
39 class fake_glx_display : public glx_display {
40 public:
fake_glx_display(mock_XDisplay * dpy,int major,int minor)41 fake_glx_display(mock_XDisplay *dpy, int major, int minor)
42 {
43 this->next = 0;
44 this->dpy = dpy;
45 this->majorOpcode = 0;
46 this->majorVersion = major;
47 this->minorVersion = minor;
48 this->serverGLXvendor = 0;
49 this->serverGLXversion = 0;
50 this->glXDrawHash = 0;
51
52 this->screens = new glx_screen *[dpy->nscreens];
53 memset(this->screens, 0, sizeof(struct glx_screen *) * dpy->nscreens);
54 }
55
~fake_glx_display()56 ~fake_glx_display()
57 {
58 for (int i = 0; i < this->dpy->nscreens; i++) {
59 if (this->screens[i] != NULL)
60 delete this->screens[i];
61 }
62
63 delete [] this->screens;
64 }
65
66 void init_screen(int i, const char *ext);
67 };
68
69 class glX_send_client_info_test : public ::testing::Test {
70 public:
71 glX_send_client_info_test();
72 virtual ~glX_send_client_info_test();
73 virtual void SetUp();
74
75 void common_protocol_expected_false_test(unsigned major, unsigned minor,
76 const char *glx_ext, bool *value);
77
78 void common_protocol_expected_true_test(unsigned major, unsigned minor,
79 const char *glx_ext, bool *value);
80
81 void create_single_screen_display(unsigned major, unsigned minor,
82 const char *glx_ext);
83
84 void destroy_display();
85
86 protected:
87 fake_glx_display *glx_dpy;
88 mock_XDisplay *display;
89 };
90
91 void
init_screen(int i,const char * ext)92 fake_glx_display::init_screen(int i, const char *ext)
93 {
94 if (this->screens[i] != NULL)
95 delete this->screens[i];
96
97 this->screens[i] = new fake_glx_screen(this, i, ext);
98 }
99 /*@}*/
100
101 static const char ext[] = "GL_XXX_dummy";
102
103 static bool ClientInfo_was_sent;
104 static bool SetClientInfoARB_was_sent;
105 static bool SetClientInfo2ARB_was_sent;
106 static xcb_connection_t *connection_used;
107 static int gl_ext_length;
108 static char *gl_ext_string;
109 static int glx_ext_length;
110 static char *glx_ext_string;
111 static int num_gl_versions;
112 static uint32_t *gl_versions;
113 static int glx_major;
114 static int glx_minor;
115
116 extern "C" xcb_connection_t *
XGetXCBConnection(Display * dpy)117 XGetXCBConnection(Display *dpy)
118 {
119 return (xcb_connection_t *) 0xdeadbeef;
120 }
121
122 extern "C" xcb_void_cookie_t
xcb_glx_client_info(xcb_connection_t * c,uint32_t major_version,uint32_t minor_version,uint32_t str_len,const char * string)123 xcb_glx_client_info(xcb_connection_t *c,
124 uint32_t major_version,
125 uint32_t minor_version,
126 uint32_t str_len,
127 const char *string)
128 {
129 xcb_void_cookie_t cookie;
130
131 ClientInfo_was_sent = true;
132 connection_used = c;
133
134 gl_ext_string = (char *) malloc(str_len);
135 memcpy(gl_ext_string, string, str_len);
136 gl_ext_length = str_len;
137
138 glx_major = major_version;
139 glx_minor = minor_version;
140
141 cookie.sequence = 0;
142 return cookie;
143 }
144
145 extern "C" xcb_void_cookie_t
xcb_glx_set_client_info_arb(xcb_connection_t * c,uint32_t major_version,uint32_t minor_version,uint32_t num_versions,uint32_t gl_str_len,uint32_t glx_str_len,const uint32_t * versions,const char * gl_string,const char * glx_string)146 xcb_glx_set_client_info_arb(xcb_connection_t *c,
147 uint32_t major_version,
148 uint32_t minor_version,
149 uint32_t num_versions,
150 uint32_t gl_str_len,
151 uint32_t glx_str_len,
152 const uint32_t *versions,
153 const char *gl_string,
154 const char *glx_string)
155 {
156 xcb_void_cookie_t cookie;
157
158 SetClientInfoARB_was_sent = true;
159 connection_used = c;
160
161 gl_ext_string = new char[gl_str_len];
162 memcpy(gl_ext_string, gl_string, gl_str_len);
163 gl_ext_length = gl_str_len;
164
165 glx_ext_string = new char[glx_str_len];
166 memcpy(glx_ext_string, glx_string, glx_str_len);
167 glx_ext_length = glx_str_len;
168
169 gl_versions = new uint32_t[num_versions * 2];
170 memcpy(gl_versions, versions, sizeof(uint32_t) * num_versions * 2);
171 num_gl_versions = num_versions;
172
173 glx_major = major_version;
174 glx_minor = minor_version;
175
176 cookie.sequence = 0;
177 return cookie;
178 }
179
180 extern "C" xcb_void_cookie_t
xcb_glx_set_client_info_2arb(xcb_connection_t * c,uint32_t major_version,uint32_t minor_version,uint32_t num_versions,uint32_t gl_str_len,uint32_t glx_str_len,const uint32_t * versions,const char * gl_string,const char * glx_string)181 xcb_glx_set_client_info_2arb(xcb_connection_t *c,
182 uint32_t major_version,
183 uint32_t minor_version,
184 uint32_t num_versions,
185 uint32_t gl_str_len,
186 uint32_t glx_str_len,
187 const uint32_t *versions,
188 const char *gl_string,
189 const char *glx_string)
190 {
191 xcb_void_cookie_t cookie;
192
193 SetClientInfo2ARB_was_sent = true;
194 connection_used = c;
195
196 gl_ext_string = new char[gl_str_len];
197 memcpy(gl_ext_string, gl_string, gl_str_len);
198 gl_ext_length = gl_str_len;
199
200 glx_ext_string = new char[glx_str_len];
201 memcpy(glx_ext_string, glx_string, glx_str_len);
202 glx_ext_length = glx_str_len;
203
204 gl_versions = new uint32_t[num_versions * 3];
205 memcpy(gl_versions, versions, sizeof(uint32_t) * num_versions * 3);
206 num_gl_versions = num_versions;
207
208 glx_major = major_version;
209 glx_minor = minor_version;
210
211 cookie.sequence = 0;
212 return cookie;
213 }
214
215 extern "C" char *
__glXGetClientGLExtensionString()216 __glXGetClientGLExtensionString()
217 {
218 char *str = (char *) malloc(sizeof(ext));
219
220 memcpy(str, ext, sizeof(ext));
221 return str;
222 }
223
glX_send_client_info_test()224 glX_send_client_info_test::glX_send_client_info_test()
225 : glx_dpy(0), display(0)
226 {
227 /* empty */
228 }
229
~glX_send_client_info_test()230 glX_send_client_info_test::~glX_send_client_info_test()
231 {
232 if (glx_dpy)
233 delete glx_dpy;
234
235 if (display)
236 delete display;
237 }
238
239 void
destroy_display()240 glX_send_client_info_test::destroy_display()
241 {
242 if (this->glx_dpy != NULL) {
243 if (this->glx_dpy->screens != NULL) {
244 for (int i = 0; i < this->display->nscreens; i++) {
245 delete [] this->glx_dpy->screens[i]->serverGLXexts;
246 delete this->glx_dpy->screens[i];
247 }
248
249 delete [] this->glx_dpy->screens;
250 }
251
252 delete this->glx_dpy;
253 delete this->display;
254 }
255 }
256
257 void
SetUp()258 glX_send_client_info_test::SetUp()
259 {
260 ClientInfo_was_sent = false;
261 SetClientInfoARB_was_sent = false;
262 SetClientInfo2ARB_was_sent = false;
263 connection_used = (xcb_connection_t *) ~0;
264 gl_ext_length = 0;
265 gl_ext_string = (char *) 0;
266 glx_ext_length = 0;
267 glx_ext_string = (char *) 0;
268 num_gl_versions = 0;
269 gl_versions = (uint32_t *) 0;
270 glx_major = 0;
271 glx_minor = 0;
272 }
273
274 void
create_single_screen_display(unsigned major,unsigned minor,const char * glx_ext)275 glX_send_client_info_test::create_single_screen_display(unsigned major,
276 unsigned minor,
277 const char *glx_ext)
278 {
279 this->display = new mock_XDisplay(1);
280
281 this->glx_dpy = new fake_glx_display(this->display, major, minor);
282 this->glx_dpy->init_screen(0, glx_ext);
283 }
284
285 void
common_protocol_expected_false_test(unsigned major,unsigned minor,const char * glx_ext,bool * value)286 glX_send_client_info_test::common_protocol_expected_false_test(unsigned major,
287 unsigned minor,
288 const char *glx_ext,
289 bool *value)
290 {
291 create_single_screen_display(major, minor, glx_ext);
292 __glX_send_client_info(this->glx_dpy);
293 EXPECT_FALSE(*value);
294 }
295
296 void
common_protocol_expected_true_test(unsigned major,unsigned minor,const char * glx_ext,bool * value)297 glX_send_client_info_test::common_protocol_expected_true_test(unsigned major,
298 unsigned minor,
299 const char *glx_ext,
300 bool *value)
301 {
302 create_single_screen_display(major, minor, glx_ext);
303 __glX_send_client_info(this->glx_dpy);
304 EXPECT_TRUE(*value);
305 }
306
TEST_F(glX_send_client_info_test,doesnt_send_ClientInfo_for_1_0)307 TEST_F(glX_send_client_info_test, doesnt_send_ClientInfo_for_1_0)
308 {
309 /* The glXClientInfo protocol was added in GLX 1.1. Verify that no
310 * glXClientInfo is sent to a GLX server that only has GLX 1.0.
311 */
312 common_protocol_expected_false_test(1, 0, "", &ClientInfo_was_sent);
313 }
314
TEST_F(glX_send_client_info_test,doesnt_send_SetClientInfoARB_for_1_0)315 TEST_F(glX_send_client_info_test, doesnt_send_SetClientInfoARB_for_1_0)
316 {
317 /* The glXSetClientInfoARB protocol was added in GLX 1.4 with the
318 * GLX_ARB_create_context extension. Verify that no glXSetClientInfoARB is
319 * sent to a GLX server that only has GLX 1.0 regardless of the extension
320 * setting.
321 */
322 common_protocol_expected_false_test(1, 0,
323 "GLX_ARB_create_context",
324 &SetClientInfoARB_was_sent);
325 }
326
TEST_F(glX_send_client_info_test,doesnt_send_SetClientInfoARB_for_1_1)327 TEST_F(glX_send_client_info_test, doesnt_send_SetClientInfoARB_for_1_1)
328 {
329 /* The glXSetClientInfoARB protocol was added in GLX 1.4 with the
330 * GLX_ARB_create_context extension. Verify that no glXSetClientInfoARB is
331 * sent to a GLX server that only has GLX 1.0 regardless of the extension
332 * setting.
333 */
334 common_protocol_expected_false_test(1, 1,
335 "GLX_ARB_create_context",
336 &SetClientInfoARB_was_sent);
337 }
338
TEST_F(glX_send_client_info_test,doesnt_send_SetClientInfoARB_for_1_4_with_empty_extensions)339 TEST_F(glX_send_client_info_test, doesnt_send_SetClientInfoARB_for_1_4_with_empty_extensions)
340 {
341 /* The glXSetClientInfoARB protocol was added in GLX 1.4 with the
342 * GLX_ARB_create_context extension. Verify that no glXSetClientInfoARB is
343 * sent to a GLX server that has GLX 1.4 but has an empty extension string
344 * (i.e., no extensions at all).
345 */
346 common_protocol_expected_false_test(1, 4,
347 "",
348 &SetClientInfoARB_was_sent);
349 }
350
TEST_F(glX_send_client_info_test,doesnt_send_SetClientInfoARB_for_1_4_without_extension)351 TEST_F(glX_send_client_info_test, doesnt_send_SetClientInfoARB_for_1_4_without_extension)
352 {
353 /* The glXSetClientInfoARB protocol was added in GLX 1.4 with the
354 * GLX_ARB_create_context extension. Verify that no glXSetClientInfoARB is
355 * sent to a GLX server that has GLX 1.4 but doesn't have the extension.
356 */
357 common_protocol_expected_false_test(1, 4,
358 "GLX_EXT_texture_from_pixmap",
359 &SetClientInfoARB_was_sent);
360 }
361
TEST_F(glX_send_client_info_test,doesnt_send_SetClientInfoARB_for_1_4_with_wrong_extension)362 TEST_F(glX_send_client_info_test, doesnt_send_SetClientInfoARB_for_1_4_with_wrong_extension)
363 {
364 /* The glXSetClientInfoARB protocol was added in GLX 1.4 with the
365 * GLX_ARB_create_context extension. Verify that no glXSetClientInfoARB is
366 * sent to a GLX server that has GLX 1.4 but does not have the extension.
367 *
368 * This test differs from
369 * doesnt_send_SetClientInfoARB_for_1_4_without_extension in that an
370 * extension exists that looks like the correct extension but isn't.
371 */
372 common_protocol_expected_false_test(1, 4,
373 "GLX_ARB_create_context2",
374 &SetClientInfoARB_was_sent);
375 }
376
TEST_F(glX_send_client_info_test,doesnt_send_SetClientInfoARB_for_1_4_with_profile_extension)377 TEST_F(glX_send_client_info_test, doesnt_send_SetClientInfoARB_for_1_4_with_profile_extension)
378 {
379 /* The glXSetClientInfoARB protocol was added in GLX 1.4 with the
380 * GLX_ARB_create_context extension. Verify that no glXSetClientInfoARB is
381 * sent to a GLX server that has GLX 1.4 but does not have the extension.
382 *
383 * This test differs from
384 * doesnt_send_SetClientInfoARB_for_1_4_without_extension in that an
385 * extension exists that looks like the correct extension but isn't.
386 */
387 common_protocol_expected_false_test(1, 4,
388 "GLX_ARB_create_context_profile",
389 &SetClientInfoARB_was_sent);
390 }
391
TEST_F(glX_send_client_info_test,doesnt_send_SetClientInfo2ARB_for_1_0)392 TEST_F(glX_send_client_info_test, doesnt_send_SetClientInfo2ARB_for_1_0)
393 {
394 /* The glXSetClientInfo2ARB protocol was added in GLX 1.4 with the
395 * GLX_ARB_create_context_profile extension. Verify that no
396 * glXSetClientInfo2ARB is sent to a GLX server that only has GLX 1.0
397 * regardless of the extension setting.
398 */
399 common_protocol_expected_false_test(1, 0,
400 "GLX_ARB_create_context_profile",
401 &SetClientInfo2ARB_was_sent);
402 }
403
TEST_F(glX_send_client_info_test,doesnt_send_SetClientInfo2ARB_for_1_1)404 TEST_F(glX_send_client_info_test, doesnt_send_SetClientInfo2ARB_for_1_1)
405 {
406 /* The glXSetClientInfo2ARB protocol was added in GLX 1.4 with the
407 * GLX_ARB_create_context_profile extension. Verify that no
408 * glXSetClientInfo2ARB is sent to a GLX server that only has GLX 1.1
409 * regardless of the extension setting.
410 */
411 common_protocol_expected_false_test(1, 1,
412 "GLX_ARB_create_context_profile",
413 &SetClientInfo2ARB_was_sent);
414 }
415
TEST_F(glX_send_client_info_test,doesnt_send_SetClientInfo2ARB_for_1_4_with_empty_extensions)416 TEST_F(glX_send_client_info_test, doesnt_send_SetClientInfo2ARB_for_1_4_with_empty_extensions)
417 {
418 /* The glXSetClientInfo2ARB protocol was added in GLX 1.4 with the
419 * GLX_ARB_create_context_profile extension. Verify that no
420 * glXSetClientInfo2ARB is sent to a GLX server that has GLX 1.4 but has an
421 * empty extension string (i.e., no extensions at all).
422 */
423 common_protocol_expected_false_test(1, 4,
424 "",
425 &SetClientInfo2ARB_was_sent);
426 }
427
TEST_F(glX_send_client_info_test,doesnt_send_SetClientInfo2ARB_for_1_4_without_extension)428 TEST_F(glX_send_client_info_test, doesnt_send_SetClientInfo2ARB_for_1_4_without_extension)
429 {
430 /* The glXSetClientInfo2ARB protocol was added in GLX 1.4 with the
431 * GLX_ARB_create_context_profile extension. Verify that no
432 * glXSetClientInfo2ARB is sent to a GLX server that has GLX 1.4 but
433 * doesn't have the extension.
434 */
435 common_protocol_expected_false_test(1, 4,
436 "GLX_EXT_texture_from_pixmap",
437 &SetClientInfo2ARB_was_sent);
438 }
439
TEST_F(glX_send_client_info_test,doesnt_send_SetClientInfo2ARB_for_1_4_with_wrong_extension)440 TEST_F(glX_send_client_info_test, doesnt_send_SetClientInfo2ARB_for_1_4_with_wrong_extension)
441 {
442 /* The glXSetClientInfo2ARB protocol was added in GLX 1.4 with the
443 * GLX_ARB_create_context_profile extension. Verify that no
444 * glXSetClientInfo2ARB is sent to a GLX server that has GLX 1.4 but does
445 * not have the extension.
446 *
447 * This test differs from
448 * doesnt_send_SetClientInfo2ARB_for_1_4_without_extension in that an
449 * extension exists that looks like the correct extension but isn't.
450 */
451 common_protocol_expected_false_test(1, 4,
452 "GLX_ARB_create_context_profile2",
453 &SetClientInfo2ARB_was_sent);
454 }
455
TEST_F(glX_send_client_info_test,does_send_ClientInfo_for_1_1)456 TEST_F(glX_send_client_info_test, does_send_ClientInfo_for_1_1)
457 {
458 /* The glXClientInfo protocol was added in GLX 1.1. Verify that
459 * glXClientInfo is sent to a GLX server that has GLX 1.1.
460 */
461 common_protocol_expected_true_test(1, 1,
462 "",
463 &ClientInfo_was_sent);
464 }
465
TEST_F(glX_send_client_info_test,does_send_SetClientInfoARB_for_1_4_with_extension)466 TEST_F(glX_send_client_info_test, does_send_SetClientInfoARB_for_1_4_with_extension)
467 {
468 /* The glXSetClientInfoARB protocol was added in GLX 1.4 with the
469 * GLX_ARB_create_context extension. Verify that glXSetClientInfoARB is
470 * sent to a GLX server that has GLX 1.4 and the extension.
471 */
472 common_protocol_expected_true_test(1, 4,
473 "GLX_ARB_create_context",
474 &SetClientInfoARB_was_sent);
475 }
476
TEST_F(glX_send_client_info_test,does_send_SetClientInfo2ARB_for_1_4_with_just_profile_extension)477 TEST_F(glX_send_client_info_test, does_send_SetClientInfo2ARB_for_1_4_with_just_profile_extension)
478 {
479 /* The glXSetClientInfoARB protocol was added in GLX 1.4 with the
480 * GLX_ARB_create_context extension. Verify that glXSetClientInfoARB is
481 * sent to a GLX server that has GLX 1.4 and the extension.
482 */
483 common_protocol_expected_true_test(1, 4,
484 "GLX_ARB_create_context_profile",
485 &SetClientInfo2ARB_was_sent);
486 }
487
TEST_F(glX_send_client_info_test,does_send_SetClientInfo2ARB_for_1_4_with_both_extensions)488 TEST_F(glX_send_client_info_test, does_send_SetClientInfo2ARB_for_1_4_with_both_extensions)
489 {
490 /* The glXSetClientInfoARB protocol was added in GLX 1.4 with the
491 * GLX_ARB_create_context extension. Verify that glXSetClientInfoARB is
492 * sent to a GLX server that has GLX 1.4 and the extension.
493 */
494 common_protocol_expected_true_test(1, 4,
495 "GLX_ARB_create_context "
496 "GLX_ARB_create_context_profile",
497 &SetClientInfo2ARB_was_sent);
498 }
499
TEST_F(glX_send_client_info_test,does_send_SetClientInfo2ARB_for_1_4_with_both_extensions_reversed)500 TEST_F(glX_send_client_info_test, does_send_SetClientInfo2ARB_for_1_4_with_both_extensions_reversed)
501 {
502 /* The glXSetClientInfoARB protocol was added in GLX 1.4 with the
503 * GLX_ARB_create_context extension. Verify that glXSetClientInfoARB is
504 * sent to a GLX server that has GLX 1.4 and the extension.
505 */
506 common_protocol_expected_true_test(1, 4,
507 "GLX_ARB_create_context_profile "
508 "GLX_ARB_create_context",
509 &SetClientInfo2ARB_was_sent);
510 }
511
TEST_F(glX_send_client_info_test,uses_correct_connection)512 TEST_F(glX_send_client_info_test, uses_correct_connection)
513 {
514 create_single_screen_display(1, 1, "");
515 __glX_send_client_info(this->glx_dpy);
516 EXPECT_EQ((xcb_connection_t *) 0xdeadbeef, connection_used);
517 }
518
TEST_F(glX_send_client_info_test,sends_correct_gl_extension_string)519 TEST_F(glX_send_client_info_test, sends_correct_gl_extension_string)
520 {
521 create_single_screen_display(1, 1, "");
522 __glX_send_client_info(this->glx_dpy);
523
524 ASSERT_EQ((int) sizeof(ext), gl_ext_length);
525 ASSERT_NE((char *) 0, gl_ext_string);
526 EXPECT_EQ(0, memcmp(gl_ext_string, ext, sizeof(ext)));
527 }
528
TEST_F(glX_send_client_info_test,gl_versions_are_sane)529 TEST_F(glX_send_client_info_test, gl_versions_are_sane)
530 {
531 create_single_screen_display(1, 4, "GLX_ARB_create_context");
532 __glX_send_client_info(this->glx_dpy);
533
534 ASSERT_NE(0, num_gl_versions);
535
536 unsigned versions_below_3_0 = 0;
537 for (int i = 0; i < num_gl_versions; i++) {
538 EXPECT_LT(0u, gl_versions[i * 2]);
539 EXPECT_GE(4u, gl_versions[i * 2]);
540
541 /* Verify that the minor version advertised with the major version makes
542 * sense.
543 */
544 switch (gl_versions[i * 2]) {
545 case 1:
546 EXPECT_GE(5u, gl_versions[i * 2 + 1]);
547 versions_below_3_0++;
548 break;
549 case 2:
550 EXPECT_GE(1u, gl_versions[i * 2 + 1]);
551 versions_below_3_0++;
552 break;
553 case 3:
554 EXPECT_GE(3u, gl_versions[i * 2 + 1]);
555 break;
556 case 4:
557 EXPECT_GE(2u, gl_versions[i * 2 + 1]);
558 break;
559 }
560 }
561
562 /* From the GLX_ARB_create_context spec:
563 *
564 * "Only the highest supported version below 3.0 should be sent, since
565 * OpenGL 2.1 is backwards compatible with all earlier versions."
566 */
567 EXPECT_LE(versions_below_3_0, 1u);
568 }
569
TEST_F(glX_send_client_info_test,gl_versions_and_profiles_are_sane)570 TEST_F(glX_send_client_info_test, gl_versions_and_profiles_are_sane)
571 {
572 create_single_screen_display(1, 4, "GLX_ARB_create_context_profile");
573 __glX_send_client_info(this->glx_dpy);
574
575 ASSERT_NE(0, num_gl_versions);
576
577 const uint32_t all_valid_bits = GLX_CONTEXT_CORE_PROFILE_BIT_ARB
578 | GLX_CONTEXT_COMPATIBILITY_PROFILE_BIT_ARB;
579
580 unsigned versions_below_3_0 = 0;
581
582 for (int i = 0; i < num_gl_versions; i++) {
583 EXPECT_LT(0u, gl_versions[i * 3]);
584 EXPECT_GE(4u, gl_versions[i * 3]);
585
586 /* Verify that the minor version advertised with the major version makes
587 * sense.
588 */
589 switch (gl_versions[i * 3]) {
590 case 1:
591 EXPECT_GE(5u, gl_versions[i * 3 + 1]);
592 EXPECT_EQ(0u, gl_versions[i * 3 + 2]);
593 versions_below_3_0++;
594 break;
595 case 2:
596 EXPECT_GE(1u, gl_versions[i * 3 + 1]);
597 EXPECT_EQ(0u, gl_versions[i * 3 + 2]);
598 versions_below_3_0++;
599 break;
600 case 3:
601 EXPECT_GE(3u, gl_versions[i * 3 + 1]);
602
603 /* Profiles were not introduced until OpenGL 3.2.
604 */
605 if (gl_versions[i * 3 + 1] < 2) {
606 EXPECT_EQ(0u, gl_versions[i * 3 + 2]);
607 } else {
608 EXPECT_EQ(0u, gl_versions[i * 3 + 2] & ~all_valid_bits);
609 }
610 break;
611 case 4:
612 EXPECT_GE(2u, gl_versions[i * 3 + 1]);
613 EXPECT_EQ(0u, gl_versions[i * 3 + 2] & ~all_valid_bits);
614 break;
615 }
616 }
617
618 /* From the GLX_ARB_create_context_profile spec:
619 *
620 * "Only the highest supported version below 3.0 should be sent, since
621 * OpenGL 2.1 is backwards compatible with all earlier versions."
622 */
623 EXPECT_LE(versions_below_3_0, 1u);
624 }
625
TEST_F(glX_send_client_info_test,glx_version_is_1_4_for_1_1)626 TEST_F(glX_send_client_info_test, glx_version_is_1_4_for_1_1)
627 {
628 create_single_screen_display(1, 1, "");
629 __glX_send_client_info(this->glx_dpy);
630
631 EXPECT_EQ(1, glx_major);
632 EXPECT_EQ(4, glx_minor);
633 }
634
TEST_F(glX_send_client_info_test,glx_version_is_1_4_for_1_4)635 TEST_F(glX_send_client_info_test, glx_version_is_1_4_for_1_4)
636 {
637 create_single_screen_display(1, 4, "");
638 __glX_send_client_info(this->glx_dpy);
639
640 EXPECT_EQ(1, glx_major);
641 EXPECT_EQ(4, glx_minor);
642 }
643
TEST_F(glX_send_client_info_test,glx_version_is_1_4_for_1_4_with_ARB_create_context)644 TEST_F(glX_send_client_info_test, glx_version_is_1_4_for_1_4_with_ARB_create_context)
645 {
646 create_single_screen_display(1, 4, "GLX_ARB_create_context");
647 __glX_send_client_info(this->glx_dpy);
648
649 EXPECT_EQ(1, glx_major);
650 EXPECT_EQ(4, glx_minor);
651 }
652
TEST_F(glX_send_client_info_test,glx_version_is_1_4_for_1_4_with_ARB_create_context_profile)653 TEST_F(glX_send_client_info_test, glx_version_is_1_4_for_1_4_with_ARB_create_context_profile)
654 {
655 create_single_screen_display(1, 4, "GLX_ARB_create_context_profile");
656 __glX_send_client_info(this->glx_dpy);
657
658 EXPECT_EQ(1, glx_major);
659 EXPECT_EQ(4, glx_minor);
660 }
661
TEST_F(glX_send_client_info_test,glx_version_is_1_4_for_1_5)662 TEST_F(glX_send_client_info_test, glx_version_is_1_4_for_1_5)
663 {
664 create_single_screen_display(1, 5, "");
665 __glX_send_client_info(this->glx_dpy);
666
667 EXPECT_EQ(1, glx_major);
668 EXPECT_EQ(4, glx_minor);
669 }
670
TEST_F(glX_send_client_info_test,glx_extensions_has_GLX_ARB_create_context)671 TEST_F(glX_send_client_info_test, glx_extensions_has_GLX_ARB_create_context)
672 {
673 create_single_screen_display(1, 4, "GLX_ARB_create_context");
674 __glX_send_client_info(this->glx_dpy);
675
676 ASSERT_NE(0, glx_ext_length);
677 ASSERT_NE((char *) 0, glx_ext_string);
678
679 bool found_GLX_ARB_create_context = false;
680 const char *const needle = "GLX_ARB_create_context";
681 const unsigned len = strlen(needle);
682 char *haystack = glx_ext_string;
683 while (haystack != NULL) {
684 char *match = strstr(haystack, needle);
685
686 if (match[len] == '\0' || match[len] == ' ') {
687 found_GLX_ARB_create_context = true;
688 break;
689 }
690
691 haystack = match + len;
692 }
693
694 EXPECT_TRUE(found_GLX_ARB_create_context);
695 }
696
TEST_F(glX_send_client_info_test,glx_extensions_has_GLX_ARB_create_context_profile)697 TEST_F(glX_send_client_info_test, glx_extensions_has_GLX_ARB_create_context_profile)
698 {
699 create_single_screen_display(1, 4, "GLX_ARB_create_context_profile");
700 __glX_send_client_info(this->glx_dpy);
701
702 ASSERT_NE(0, glx_ext_length);
703 ASSERT_NE((char *) 0, glx_ext_string);
704
705 bool found_GLX_ARB_create_context_profile = false;
706 const char *const needle = "GLX_ARB_create_context_profile";
707 const unsigned len = strlen(needle);
708 char *haystack = glx_ext_string;
709 while (haystack != NULL) {
710 char *match = strstr(haystack, needle);
711
712 if (match[len] == '\0' || match[len] == ' ') {
713 found_GLX_ARB_create_context_profile = true;
714 break;
715 }
716
717 haystack = match + len;
718 }
719
720 EXPECT_TRUE(found_GLX_ARB_create_context_profile);
721 }
722