xref: /aosp_15_r20/external/mesa3d/src/glx/render2.c (revision 6104692788411f58d303aa86923a9ff6ecaded22)
1 /*
2  * SGI FREE SOFTWARE LICENSE B (Version 2.0, Sept. 18, 2008)
3  * Copyright (C) 1991-2000 Silicon Graphics, Inc. All Rights Reserved.
4  *
5  * SPDX-License-Identifier: SGI-B-2.0
6  */
7 
8 #if !defined(GLX_USE_APPLEGL) || defined(GLX_USE_APPLE)
9 
10 #include "packrender.h"
11 #include "indirect.h"
12 #include "indirect_size.h"
13 
14 /*
15 ** This file contains routines that might need to be transported as
16 ** GLXRender or GLXRenderLarge commands, and these commands don't
17 ** use the pixel header.  See renderpix.c for those routines.
18 */
19 
20 void
__indirect_glMap1d(GLenum target,GLdouble u1,GLdouble u2,GLint stride,GLint order,const GLdouble * pnts)21 __indirect_glMap1d(GLenum target, GLdouble u1, GLdouble u2, GLint stride,
22                    GLint order, const GLdouble * pnts)
23 {
24    __GLX_DECLARE_VARIABLES();
25    GLint k;
26 
27    __GLX_LOAD_VARIABLES();
28    k = __glMap1d_size(target);
29    if (k == 0) {
30       __glXSetError(gc, GL_INVALID_ENUM);
31       return;
32    }
33    else if (stride < k || order <= 0) {
34       __glXSetError(gc, GL_INVALID_VALUE);
35       return;
36    }
37    compsize = k * order * __GLX_SIZE_FLOAT64;
38    cmdlen = 28 + compsize;
39    if (!gc->currentDpy)
40       return;
41 
42    if (cmdlen <= gc->maxSmallRenderCommandSize) {
43       /* Use GLXRender protocol to send small command */
44       __GLX_BEGIN_VARIABLE(X_GLrop_Map1d, cmdlen);
45       __GLX_PUT_DOUBLE(4, u1);
46       __GLX_PUT_DOUBLE(12, u2);
47       __GLX_PUT_LONG(20, target);
48       __GLX_PUT_LONG(24, order);
49       /*
50        ** NOTE: the doubles that follow are not aligned because of 3
51        ** longs preceeding
52        */
53       __glFillMap1d(k, order, stride, pnts, (pc + 28));
54       __GLX_END(cmdlen);
55    }
56    else {
57       /* Use GLXRenderLarge protocol to send command */
58       __GLX_BEGIN_VARIABLE_LARGE(X_GLrop_Map1d, cmdlen + 4);
59       __GLX_PUT_DOUBLE(8, u1);
60       __GLX_PUT_DOUBLE(16, u2);
61       __GLX_PUT_LONG(24, target);
62       __GLX_PUT_LONG(28, order);
63 
64       /*
65        ** NOTE: the doubles that follow are not aligned because of 3
66        ** longs preceeding
67        */
68       if (stride != k) {
69          GLubyte *buf;
70 
71          buf = malloc(compsize);
72          if (!buf) {
73             __glXSetError(gc, GL_OUT_OF_MEMORY);
74             return;
75          }
76          __glFillMap1d(k, order, stride, pnts, buf);
77          __glXSendLargeCommand(gc, pc, 32, buf, compsize);
78          free((char *) buf);
79       }
80       else {
81          /* Data is already packed.  Just send it out */
82          __glXSendLargeCommand(gc, pc, 32, pnts, compsize);
83       }
84    }
85 }
86 
87 void
__indirect_glMap1f(GLenum target,GLfloat u1,GLfloat u2,GLint stride,GLint order,const GLfloat * pnts)88 __indirect_glMap1f(GLenum target, GLfloat u1, GLfloat u2, GLint stride,
89                    GLint order, const GLfloat * pnts)
90 {
91    __GLX_DECLARE_VARIABLES();
92    GLint k;
93 
94    __GLX_LOAD_VARIABLES();
95    k = __glMap1f_size(target);
96    if (k == 0) {
97       __glXSetError(gc, GL_INVALID_ENUM);
98       return;
99    }
100    else if (stride < k || order <= 0) {
101       __glXSetError(gc, GL_INVALID_VALUE);
102       return;
103    }
104    compsize = k * order * __GLX_SIZE_FLOAT32;
105    cmdlen = 20 + compsize;
106    if (!gc->currentDpy)
107       return;
108 
109    /*
110     ** The order that arguments are packed is different from the order
111     ** for glMap1d.
112     */
113    if (cmdlen <= gc->maxSmallRenderCommandSize) {
114       /* Use GLXRender protocol to send small command */
115       __GLX_BEGIN_VARIABLE(X_GLrop_Map1f, cmdlen);
116       __GLX_PUT_LONG(4, target);
117       __GLX_PUT_FLOAT(8, u1);
118       __GLX_PUT_FLOAT(12, u2);
119       __GLX_PUT_LONG(16, order);
120       __glFillMap1f(k, order, stride, pnts, (GLubyte *) (pc + 20));
121       __GLX_END(cmdlen);
122    }
123    else {
124       /* Use GLXRenderLarge protocol to send command */
125       __GLX_BEGIN_VARIABLE_LARGE(X_GLrop_Map1f, cmdlen + 4);
126       __GLX_PUT_LONG(8, target);
127       __GLX_PUT_FLOAT(12, u1);
128       __GLX_PUT_FLOAT(16, u2);
129       __GLX_PUT_LONG(20, order);
130 
131       if (stride != k) {
132          GLubyte *buf;
133 
134          buf = malloc(compsize);
135          if (!buf) {
136             __glXSetError(gc, GL_OUT_OF_MEMORY);
137             return;
138          }
139          __glFillMap1f(k, order, stride, pnts, buf);
140          __glXSendLargeCommand(gc, pc, 24, buf, compsize);
141          free((char *) buf);
142       }
143       else {
144          /* Data is already packed.  Just send it out */
145          __glXSendLargeCommand(gc, pc, 24, pnts, compsize);
146       }
147    }
148 }
149 
150 void
__indirect_glMap2d(GLenum target,GLdouble u1,GLdouble u2,GLint ustr,GLint uord,GLdouble v1,GLdouble v2,GLint vstr,GLint vord,const GLdouble * pnts)151 __indirect_glMap2d(GLenum target, GLdouble u1, GLdouble u2, GLint ustr,
152                    GLint uord, GLdouble v1, GLdouble v2, GLint vstr,
153                    GLint vord, const GLdouble * pnts)
154 {
155    __GLX_DECLARE_VARIABLES();
156    GLint k;
157 
158    __GLX_LOAD_VARIABLES();
159    k = __glMap2d_size(target);
160    if (k == 0) {
161       __glXSetError(gc, GL_INVALID_ENUM);
162       return;
163    }
164    else if (vstr < k || ustr < k || vord <= 0 || uord <= 0) {
165       __glXSetError(gc, GL_INVALID_VALUE);
166       return;
167    }
168    compsize = k * uord * vord * __GLX_SIZE_FLOAT64;
169    cmdlen = 48 + compsize;
170    if (!gc->currentDpy)
171       return;
172 
173    if (cmdlen <= gc->maxSmallRenderCommandSize) {
174       /* Use GLXRender protocol to send small command */
175       __GLX_BEGIN_VARIABLE(X_GLrop_Map2d, cmdlen);
176       __GLX_PUT_DOUBLE(4, u1);
177       __GLX_PUT_DOUBLE(12, u2);
178       __GLX_PUT_DOUBLE(20, v1);
179       __GLX_PUT_DOUBLE(28, v2);
180       __GLX_PUT_LONG(36, target);
181       __GLX_PUT_LONG(40, uord);
182       __GLX_PUT_LONG(44, vord);
183       /*
184        ** Pack into a u-major ordering.
185        ** NOTE: the doubles that follow are not aligned because of 5
186        ** longs preceeding
187        */
188       __glFillMap2d(k, uord, vord, ustr, vstr, pnts, (GLdouble *) (pc + 48));
189       __GLX_END(cmdlen);
190    }
191    else {
192       /* Use GLXRenderLarge protocol to send command */
193       __GLX_BEGIN_VARIABLE_LARGE(X_GLrop_Map2d, cmdlen + 4);
194       __GLX_PUT_DOUBLE(8, u1);
195       __GLX_PUT_DOUBLE(16, u2);
196       __GLX_PUT_DOUBLE(24, v1);
197       __GLX_PUT_DOUBLE(32, v2);
198       __GLX_PUT_LONG(40, target);
199       __GLX_PUT_LONG(44, uord);
200       __GLX_PUT_LONG(48, vord);
201 
202       /*
203        ** NOTE: the doubles that follow are not aligned because of 5
204        ** longs preceeding
205        */
206       if ((vstr != k) || (ustr != k * vord)) {
207          GLdouble *buf;
208 
209          buf = malloc(compsize);
210          if (!buf) {
211             __glXSetError(gc, GL_OUT_OF_MEMORY);
212             return;
213          }
214          /*
215           ** Pack into a u-major ordering.
216           */
217          __glFillMap2d(k, uord, vord, ustr, vstr, pnts, buf);
218          __glXSendLargeCommand(gc, pc, 52, buf, compsize);
219          free((char *) buf);
220       }
221       else {
222          /* Data is already packed.  Just send it out */
223          __glXSendLargeCommand(gc, pc, 52, pnts, compsize);
224       }
225    }
226 }
227 
228 void
__indirect_glMap2f(GLenum target,GLfloat u1,GLfloat u2,GLint ustr,GLint uord,GLfloat v1,GLfloat v2,GLint vstr,GLint vord,const GLfloat * pnts)229 __indirect_glMap2f(GLenum target, GLfloat u1, GLfloat u2, GLint ustr,
230                    GLint uord, GLfloat v1, GLfloat v2, GLint vstr, GLint vord,
231                    const GLfloat * pnts)
232 {
233    __GLX_DECLARE_VARIABLES();
234    GLint k;
235 
236    __GLX_LOAD_VARIABLES();
237    k = __glMap2f_size(target);
238    if (k == 0) {
239       __glXSetError(gc, GL_INVALID_ENUM);
240       return;
241    }
242    else if (vstr < k || ustr < k || vord <= 0 || uord <= 0) {
243       __glXSetError(gc, GL_INVALID_VALUE);
244       return;
245    }
246    compsize = k * uord * vord * __GLX_SIZE_FLOAT32;
247    cmdlen = 32 + compsize;
248    if (!gc->currentDpy)
249       return;
250 
251    /*
252     ** The order that arguments are packed is different from the order
253     ** for glMap2d.
254     */
255    if (cmdlen <= gc->maxSmallRenderCommandSize) {
256       /* Use GLXRender protocol to send small command */
257       __GLX_BEGIN_VARIABLE(X_GLrop_Map2f, cmdlen);
258       __GLX_PUT_LONG(4, target);
259       __GLX_PUT_FLOAT(8, u1);
260       __GLX_PUT_FLOAT(12, u2);
261       __GLX_PUT_LONG(16, uord);
262       __GLX_PUT_FLOAT(20, v1);
263       __GLX_PUT_FLOAT(24, v2);
264       __GLX_PUT_LONG(28, vord);
265       /*
266        ** Pack into a u-major ordering.
267        */
268       __glFillMap2f(k, uord, vord, ustr, vstr, pnts, (GLfloat *) (pc + 32));
269       __GLX_END(cmdlen);
270    }
271    else {
272       /* Use GLXRenderLarge protocol to send command */
273       __GLX_BEGIN_VARIABLE_LARGE(X_GLrop_Map2f, cmdlen + 4);
274       __GLX_PUT_LONG(8, target);
275       __GLX_PUT_FLOAT(12, u1);
276       __GLX_PUT_FLOAT(16, u2);
277       __GLX_PUT_LONG(20, uord);
278       __GLX_PUT_FLOAT(24, v1);
279       __GLX_PUT_FLOAT(28, v2);
280       __GLX_PUT_LONG(32, vord);
281 
282       if ((vstr != k) || (ustr != k * vord)) {
283          GLfloat *buf;
284 
285          buf = malloc(compsize);
286          if (!buf) {
287             __glXSetError(gc, GL_OUT_OF_MEMORY);
288             return;
289          }
290          /*
291           ** Pack into a u-major ordering.
292           */
293          __glFillMap2f(k, uord, vord, ustr, vstr, pnts, buf);
294          __glXSendLargeCommand(gc, pc, 36, buf, compsize);
295          free((char *) buf);
296       }
297       else {
298          /* Data is already packed.  Just send it out */
299          __glXSendLargeCommand(gc, pc, 36, pnts, compsize);
300       }
301    }
302 }
303 
304 void
__indirect_glEnable(GLenum cap)305 __indirect_glEnable(GLenum cap)
306 {
307    __GLX_DECLARE_VARIABLES();
308 
309    __GLX_LOAD_VARIABLES();
310    if (!gc->currentDpy)
311       return;
312 
313    switch (cap) {
314    case GL_COLOR_ARRAY:
315    case GL_EDGE_FLAG_ARRAY:
316    case GL_INDEX_ARRAY:
317    case GL_NORMAL_ARRAY:
318    case GL_TEXTURE_COORD_ARRAY:
319    case GL_VERTEX_ARRAY:
320    case GL_SECONDARY_COLOR_ARRAY:
321    case GL_FOG_COORD_ARRAY:
322       __indirect_glEnableClientState(cap);
323       return;
324    default:
325       break;
326    }
327 
328    __GLX_BEGIN(X_GLrop_Enable, 8);
329    __GLX_PUT_LONG(4, cap);
330    __GLX_END(8);
331 }
332 
333 void
__indirect_glDisable(GLenum cap)334 __indirect_glDisable(GLenum cap)
335 {
336    __GLX_DECLARE_VARIABLES();
337 
338    __GLX_LOAD_VARIABLES();
339    if (!gc->currentDpy)
340       return;
341 
342    switch (cap) {
343    case GL_COLOR_ARRAY:
344    case GL_EDGE_FLAG_ARRAY:
345    case GL_INDEX_ARRAY:
346    case GL_NORMAL_ARRAY:
347    case GL_TEXTURE_COORD_ARRAY:
348    case GL_VERTEX_ARRAY:
349    case GL_SECONDARY_COLOR_ARRAY:
350    case GL_FOG_COORD_ARRAY:
351       __indirect_glDisableClientState(cap);
352       return;
353    default:
354       break;
355    }
356 
357    __GLX_BEGIN(X_GLrop_Disable, 8);
358    __GLX_PUT_LONG(4, cap);
359    __GLX_END(8);
360 }
361 
362 #endif
363