1c041511dScube
2c041511dScube/* Copyright (c) Mark J. Kilgard, 1997. */
3c041511dScube
4c041511dScube/* This program is freely distributable without licensing fees
5c041511dScube   and is provided without guarantee or warrantee expressed or
6c041511dScube   implied. This program is -not- in the public domain. */
7c041511dScube
8c041511dScube#include <stdlib.h>
9c041511dScube#include <string.h>
10c041511dScube#include "glutint.h"
11c041511dScube
12c041511dScube#if defined(GLX_VERSION_1_1)
13c041511dScubeint
14c041511dScube__glutIsSupportedByGLX(char *extension)
15c041511dScube{
16c041511dScube  static const char *extensions = NULL;
17c041511dScube  const char *start;
18c041511dScube  char *where, *terminator;
19c041511dScube  int major, minor;
20c041511dScube
21c041511dScube  glXQueryVersion(__glutDisplay, &major, &minor);
22c041511dScube  /* Be careful not to call glXQueryExtensionsString if it
23c041511dScube     looks like the server doesn't support GLX 1.1.
24c041511dScube     Unfortunately, the original GLX 1.0 didn't have the notion
25c041511dScube     of GLX extensions. */
26c041511dScube  if ((major == 1 && minor >= 1) || (major > 1)) {
27c041511dScube    if (!extensions)
28c041511dScube      extensions = glXQueryExtensionsString(__glutDisplay, __glutScreen);
29c041511dScube    /* It takes a bit of care to be fool-proof about parsing
30c041511dScube       the GLX extensions string.  Don't be fooled by
31c041511dScube       sub-strings,  etc. */
32c041511dScube    start = extensions;
33c041511dScube    for (;;) {
34c041511dScube      where = strstr(start, extension);
35c041511dScube      if (!where)
36c041511dScube        return 0;
37c041511dScube      terminator = where + strlen(extension);
38c041511dScube      if (where == start || *(where - 1) == ' ') {
39c041511dScube        if (*terminator == ' ' || *terminator == '\0') {
40c041511dScube          return 1;
41c041511dScube        }
42c041511dScube      }
43c041511dScube      start = terminator;
44c041511dScube    }
45c041511dScube  }
46c041511dScube  return 0;
47c041511dScube}
48c041511dScube#endif
49c041511dScube
50c041511dScube
51c041511dScube
52c041511dScube/*
53c041511dScube * Wrapping of GLX extension functions.
54c041511dScube * Technically, we should do a runtime test to see if we've got the
55c041511dScube * glXGetProcAddressARB() function.  I think GLX_ARB_get_proc_address
56c041511dScube * is pretty widely supported now and any system that has
57c041511dScube * GLX_ARB_get_proc_address defined in its header files should be OK
58c041511dScube * at runtime.
59c041511dScube */
60c041511dScube
61c041511dScubeint
62c041511dScube__glut_glXBindChannelToWindowSGIX(Display *dpy, int screen,
63c041511dScube                                  int channel, Window window)
64c041511dScube{
65c041511dScube#ifdef GLX_ARB_get_proc_address
66c041511dScube  typedef int (*glXBindChannelToWindowSGIX_t) (Display *, int, int, Window);
67c041511dScube  static glXBindChannelToWindowSGIX_t glXBindChannelToWindowSGIX_ptr = NULL;
68c041511dScube  if (!glXBindChannelToWindowSGIX_ptr) {
69c041511dScube    glXBindChannelToWindowSGIX_ptr = (glXBindChannelToWindowSGIX_t)
70c041511dScube      glXGetProcAddressARB((const GLubyte *) "glXBindChannelToWindowSGIX");
71c041511dScube  }
72c041511dScube  if (glXBindChannelToWindowSGIX_ptr)
73c041511dScube    return (*glXBindChannelToWindowSGIX_ptr)(dpy, screen, channel, window);
74c041511dScube  else
75c041511dScube    return 0;
76c041511dScube#elif defined(GLX_SGIX_video_resize)
77c041511dScube  return glXBindChannelToWindowSGIX(dpy, screen, channel, window);
78c041511dScube#else
79c041511dScube  return 0;
80c041511dScube#endif
81c041511dScube}
82c041511dScube
83c041511dScube
84c041511dScubeint
85c041511dScube__glut_glXChannelRectSGIX(Display *dpy, int screen, int channel,
86c041511dScube                          int x, int y, int w, int h)
87c041511dScube{
88c041511dScube#ifdef GLX_ARB_get_proc_address
89c041511dScube  typedef int (*glXChannelRectSGIX_t)(Display *, int, int, int, int, int, int);
90c041511dScube  static glXChannelRectSGIX_t glXChannelRectSGIX_ptr = NULL;
91c041511dScube  if (!glXChannelRectSGIX_ptr) {
92c041511dScube    glXChannelRectSGIX_ptr = (glXChannelRectSGIX_t)
93c041511dScube      glXGetProcAddressARB((const GLubyte *) "glXChannelRectSGIX");
94c041511dScube  }
95c041511dScube  if (glXChannelRectSGIX_ptr)
96c041511dScube    return (*glXChannelRectSGIX_ptr)(dpy, screen, channel, x, y, w, h);
97c041511dScube  else
98c041511dScube    return 0;
99c041511dScube#elif defined(GLX_SGIX_video_resize)
100c041511dScube  return glXChannelRectSGIX(dpy, screen, channel, x, y, w, h);
101c041511dScube#else
102c041511dScube  return 0;
103c041511dScube#endif
104c041511dScube}
105c041511dScube
106c041511dScube
107c041511dScubeint
108c041511dScube__glut_glXQueryChannelRectSGIX(Display *dpy, int screen, int channel,
109c041511dScube                               int *x, int *y, int *w, int *h)
110c041511dScube{
111c041511dScube#ifdef GLX_ARB_get_proc_address
112c041511dScube  typedef int (*glXQueryChannelRectSGIX_t)(Display *, int, int,
113c041511dScube                                           int *, int *, int *, int *);
114c041511dScube  static glXQueryChannelRectSGIX_t glXQueryChannelRectSGIX_ptr = NULL;
115c041511dScube  if (!glXQueryChannelRectSGIX_ptr) {
116c041511dScube    glXQueryChannelRectSGIX_ptr = (glXQueryChannelRectSGIX_t)
117c041511dScube      glXGetProcAddressARB((const GLubyte *) "glXQueryChannelRectSGIX");
118c041511dScube  }
119c041511dScube  if (glXQueryChannelRectSGIX_ptr)
120c041511dScube    return (*glXQueryChannelRectSGIX_ptr)(dpy, screen, channel, x, y, w, h);
121c041511dScube  else
122c041511dScube    return 0;
123c041511dScube#elif defined(GLX_SGIX_video_resize)
124c041511dScube  return glXQueryChannelRectSGIX(dpy, screen, channel, x, y, w, h);
125c041511dScube#else
126c041511dScube  return 0;
127c041511dScube#endif
128c041511dScube}
129c041511dScube
130c041511dScube
131c041511dScubeint
132c041511dScube__glut_glXQueryChannelDeltasSGIX(Display *dpy, int screen, int channel,
133c041511dScube                                 int *dx, int *dy, int *dw, int *dh)
134c041511dScube{
135c041511dScube#ifdef GLX_ARB_get_proc_address
136c041511dScube  typedef int (*glXQueryChannelDeltasSGIX_t)(Display *, int, int,
137c041511dScube                                             int *, int *, int *, int *);
138c041511dScube  static glXQueryChannelDeltasSGIX_t glXQueryChannelDeltasSGIX_ptr = NULL;
139c041511dScube  if (!glXQueryChannelDeltasSGIX_ptr) {
140c041511dScube    glXQueryChannelDeltasSGIX_ptr = (glXQueryChannelDeltasSGIX_t)
141c041511dScube      glXGetProcAddressARB((const GLubyte *) "glXQueryChannelDeltasSGIX");
142c041511dScube  }
143c041511dScube  if (glXQueryChannelDeltasSGIX_ptr)
144c041511dScube    return (*glXQueryChannelDeltasSGIX_ptr)(dpy, screen, channel,
145c041511dScube                                            dx, dy, dw, dh);
146c041511dScube  else
147c041511dScube    return 0;
148c041511dScube#elif defined(GLX_SGIX_video_resize)
149c041511dScube  return glXQueryChannelDeltasSGIX(dpy, screen, channel, dx, dy, dw, dh);
150c041511dScube#else
151c041511dScube  return 0;
152c041511dScube#endif
153c041511dScube}
154c041511dScube
155c041511dScube
156c041511dScubeint
157c041511dScube__glut_glXChannelRectSyncSGIX(Display *dpy, int screen,
158c041511dScube                              int channel, GLenum synctype)
159c041511dScube{
160c041511dScube#ifdef GLX_ARB_get_proc_address
161c041511dScube  typedef int (*glXChannelRectSyncSGIX_t)(Display *, int, int, GLenum);
162c041511dScube  static glXChannelRectSyncSGIX_t glXChannelRectSyncSGIX_ptr = NULL;
163c041511dScube  if (!glXChannelRectSyncSGIX_ptr) {
164c041511dScube    glXChannelRectSyncSGIX_ptr = (glXChannelRectSyncSGIX_t)
165c041511dScube      glXGetProcAddressARB((const GLubyte *) "glXChannelRectSyncSGIX");
166c041511dScube  }
167c041511dScube  if (glXChannelRectSyncSGIX_ptr)
168c041511dScube    return (*glXChannelRectSyncSGIX_ptr)(dpy, screen, channel, synctype);
169c041511dScube  else
170c041511dScube    return 0;
171c041511dScube#elif defined(GLX_SGIX_video_resize)
172c041511dScube  return glXChannelRectSyncSGIX(dpy, screen, channel, synctype);
173c041511dScube#else
174c041511dScube  return 0;
175c041511dScube#endif
176c041511dScube}
177c041511dScube
178c041511dScube
179c041511dScube
180c041511dScubeGLXContext
181c041511dScube__glut_glXCreateContextWithConfigSGIX(Display *dpy, GLXFBConfigSGIX config,
182c041511dScube                                      int render_type, GLXContext share_list,
183c041511dScube                                      Bool direct)
184c041511dScube{
185c041511dScube#ifdef GLX_ARB_get_proc_address
186c041511dScube  typedef GLXContext (*glXCreateContextWithConfigSGIX_t)(Display *,
187c041511dScube                                 GLXFBConfigSGIX, int, GLXContext, Bool);
188c041511dScube  static glXCreateContextWithConfigSGIX_t glXCreateContextWithConfig_ptr = NULL;
189c041511dScube  if (!glXCreateContextWithConfig_ptr) {
190c041511dScube    glXCreateContextWithConfig_ptr = (glXCreateContextWithConfigSGIX_t)
191c041511dScube       glXGetProcAddressARB((const GLubyte *) "glXCreateContextWithConfigSGIX");
192c041511dScube  }
193c041511dScube  if (glXCreateContextWithConfig_ptr)
194c041511dScube    return (*glXCreateContextWithConfig_ptr)(dpy, config, render_type,
195c041511dScube                                             share_list, direct);
196c041511dScube  else
197c041511dScube    return 0;
198c041511dScube#elif defined(GLX_SGIX_fbconfig)
199c041511dScube  return glXCreateContextWithConfigSGIX(dpy, config, render_type,
200c041511dScube                                        share_list, direct);
201c041511dScube#else
202c041511dScube  return 0;
203c041511dScube#endif
204c041511dScube}
205c041511dScube
206c041511dScube
207c041511dScubeint
208c041511dScube__glut_glXGetFBConfigAttribSGIX(Display *dpy, GLXFBConfigSGIX config,
209c041511dScube                                int attribute, int *value)
210c041511dScube{
211c041511dScube#ifdef GLX_ARB_get_proc_address
212c041511dScube  typedef int (*glXGetFBConfigAttribSGIX_t)(Display *,
213c041511dScube                                            GLXFBConfigSGIX, int, int *);
214c041511dScube  static glXGetFBConfigAttribSGIX_t glXGetFBConfigAttrib_ptr = NULL;
215c041511dScube  if (!glXGetFBConfigAttrib_ptr) {
216c041511dScube    glXGetFBConfigAttrib_ptr = (glXGetFBConfigAttribSGIX_t)
217c041511dScube       glXGetProcAddressARB((const GLubyte *) "glXGetFBConfigAttribSGIX");
218c041511dScube  }
219c041511dScube  if (glXGetFBConfigAttrib_ptr)
220c041511dScube    return (*glXGetFBConfigAttrib_ptr)(dpy, config, attribute, value);
221c041511dScube  else
222c041511dScube    return 0;
223c041511dScube#elif defined(GLX_SGIX_fbconfig)
224c041511dScube  return glXGetFBConfigAttribSGIX(dpy, config, attribute, value);
225c041511dScube#else
226c041511dScube  return 0;
227c041511dScube#endif
228c041511dScube}
229c041511dScube
230c041511dScube
231c041511dScubeGLXFBConfigSGIX
232c041511dScube__glut_glXGetFBConfigFromVisualSGIX(Display *dpy, XVisualInfo *vis)
233c041511dScube{
234c041511dScube#ifdef GLX_ARB_get_proc_address
235c041511dScube  typedef GLXFBConfigSGIX (*glXGetFBConfigFromVisualSGIX_t)(Display *,
236c041511dScube                                                            XVisualInfo *);
237c041511dScube  static glXGetFBConfigFromVisualSGIX_t glXGetFBConfigFromVisual_ptr = NULL;
238c041511dScube  if (!glXGetFBConfigFromVisual_ptr) {
239c041511dScube    glXGetFBConfigFromVisual_ptr = (glXGetFBConfigFromVisualSGIX_t)
240c041511dScube       glXGetProcAddressARB((const GLubyte *) "glXGetFBConfigFromVisualSGIX");
241c041511dScube  }
242c041511dScube  if (glXGetFBConfigFromVisual_ptr)
243c041511dScube    return (*glXGetFBConfigFromVisual_ptr)(dpy, vis);
244c041511dScube  else
245c041511dScube    return 0;
246c041511dScube#elif defined(GLX_SGIX_fbconfig)
247c041511dScube  return glXGetFBConfigFromVisualSGIX(dpy, vis);
248c041511dScube#else
249c041511dScube  return 0;
250c041511dScube#endif
251c041511dScube}
252c041511dScube
253c041511dScube
254c041511dScube
255c041511dScube
256