VirtualBox

source: vbox/trunk/src/VBox/HostServices/SharedOpenGL/crserverlib/server_lists.c@ 50436

Last change on this file since 50436 was 50095, checked in by vboxsync, 11 years ago

crOpenGL: presentation infrastructure rework (still work in progress)

  • Property svn:eol-style set to native
  • Property svn:keywords set to Id
File size: 12.0 KB
Line 
1/* Copyright (c) 2001-2003, Stanford University
2 All rights reserved.
3
4 See the file LICENSE.txt for information on redistributing this software. */
5
6#include "server_dispatch.h"
7#include "server.h"
8#include "cr_mem.h"
9
10
11/*
12 * Notes on ID translation:
13 *
14 * If a server has multiple clients (in the case of parallel applications)
15 * and N of the clients all create a display list with ID K, does K name
16 * one display list or N different display lists?
17 *
18 * By default, there is one display list named K. If the clients put
19 * identical commands into list K, then this is fine. But if the clients
20 * each put something different into list K when they created it, then this
21 * is a serious problem.
22 *
23 * By zeroing the 'shared_display_lists' configuration option, we can tell
24 * the server to make list K be unique for all N clients. We do this by
25 * translating K into a new, unique ID dependent on which client we're
26 * talking to (curClient->number).
27 *
28 * Same story for texture objects, vertex programs, etc.
29 *
30 * The application can also dynamically switch between shared and private
31 * display lists with:
32 * glChromiumParameteri(GL_SHARED_DISPLAY_LISTS_CR, GL_TRUE)
33 * and
34 * glChromiumParameteri(GL_SHARED_DISPLAY_LISTS_CR, GL_FALSE)
35 *
36 */
37
38
39
40static GLuint TranslateListID( GLuint id )
41{
42 if (!cr_server.sharedDisplayLists) {
43 int client = cr_server.curClient->number;
44 return id + client * 100000;
45 }
46 return id;
47}
48
49/* XXXX Note: shared/separate Program ID numbers aren't totally implemented! */
50GLuint crServerTranslateProgramID( GLuint id )
51{
52 if (!cr_server.sharedPrograms && id) {
53 int client = cr_server.curClient->number;
54 return id + client * 100000;
55 }
56 return id;
57}
58
59
60void SERVER_DISPATCH_APIENTRY
61crServerDispatchNewList( GLuint list, GLenum mode )
62{
63 Assert(0);
64 if (mode == GL_COMPILE_AND_EXECUTE)
65 crWarning("using glNewList(GL_COMPILE_AND_EXECUTE) can confuse the crserver");
66
67 list = TranslateListID( list );
68 crStateNewList( list, mode );
69 cr_server.head_spu->dispatch_table.NewList( list, mode );
70}
71
72static void crServerQueryHWState()
73{
74 GLuint fbFbo, bbFbo;
75 CRClient *client = cr_server.curClient;
76 CRMuralInfo *mural = client ? client->currentMural : NULL;
77 if (mural && mural->fRedirected)
78 {
79 fbFbo = mural->aidFBOs[CR_SERVER_FBO_FB_IDX(mural)];
80 bbFbo = mural->aidFBOs[CR_SERVER_FBO_BB_IDX(mural)];
81 }
82 else
83 {
84 fbFbo = bbFbo = 0;
85 }
86 crStateQueryHWState(fbFbo, bbFbo);
87}
88
89void SERVER_DISPATCH_APIENTRY crServerDispatchEndList(void)
90{
91 CRContext *g = crStateGetCurrent();
92 CRListsState *l = &(g->lists);
93
94 cr_server.head_spu->dispatch_table.EndList();
95 crStateEndList();
96
97#ifndef IN_GUEST
98 if (l->mode==GL_COMPILE)
99 {
100 crServerQueryHWState();
101 }
102#endif
103}
104
105void SERVER_DISPATCH_APIENTRY
106crServerDispatchCallList( GLuint list )
107{
108 list = TranslateListID( list );
109
110 if (cr_server.curClient->currentCtxInfo->pContext->lists.mode == 0) {
111 /* we're not compiling, so execute the list now */
112 /* Issue the list as-is */
113 cr_server.head_spu->dispatch_table.CallList( list );
114 crServerQueryHWState();
115 }
116 else {
117 /* we're compiling glCallList into another list - just pass it through */
118 cr_server.head_spu->dispatch_table.CallList( list );
119 }
120}
121
122
123/**
124 * Translate an array of display list IDs from various datatypes to GLuint
125 * IDs while adding the per-client offset.
126 */
127static void
128TranslateListIDs(GLsizei n, GLenum type, const GLvoid *lists, GLuint *newLists)
129{
130 int offset = cr_server.curClient->number * 100000;
131 GLsizei i;
132 switch (type) {
133 case GL_UNSIGNED_BYTE:
134 {
135 const GLubyte *src = (const GLubyte *) lists;
136 for (i = 0; i < n; i++) {
137 newLists[i] = src[i] + offset;
138 }
139 }
140 break;
141 case GL_BYTE:
142 {
143 const GLbyte *src = (const GLbyte *) lists;
144 for (i = 0; i < n; i++) {
145 newLists[i] = src[i] + offset;
146 }
147 }
148 break;
149 case GL_UNSIGNED_SHORT:
150 {
151 const GLushort *src = (const GLushort *) lists;
152 for (i = 0; i < n; i++) {
153 newLists[i] = src[i] + offset;
154 }
155 }
156 break;
157 case GL_SHORT:
158 {
159 const GLshort *src = (const GLshort *) lists;
160 for (i = 0; i < n; i++) {
161 newLists[i] = src[i] + offset;
162 }
163 }
164 break;
165 case GL_UNSIGNED_INT:
166 {
167 const GLuint *src = (const GLuint *) lists;
168 for (i = 0; i < n; i++) {
169 newLists[i] = src[i] + offset;
170 }
171 }
172 break;
173 case GL_INT:
174 {
175 const GLint *src = (const GLint *) lists;
176 for (i = 0; i < n; i++) {
177 newLists[i] = src[i] + offset;
178 }
179 }
180 break;
181 case GL_FLOAT:
182 {
183 const GLfloat *src = (const GLfloat *) lists;
184 for (i = 0; i < n; i++) {
185 newLists[i] = (GLuint) src[i] + offset;
186 }
187 }
188 break;
189 case GL_2_BYTES:
190 {
191 const GLubyte *src = (const GLubyte *) lists;
192 for (i = 0; i < n; i++) {
193 newLists[i] = (src[i*2+0] * 256 +
194 src[i*2+1]) + offset;
195 }
196 }
197 break;
198 case GL_3_BYTES:
199 {
200 const GLubyte *src = (const GLubyte *) lists;
201 for (i = 0; i < n; i++) {
202 newLists[i] = (src[i*3+0] * 256 * 256 +
203 src[i*3+1] * 256 +
204 src[i*3+2]) + offset;
205 }
206 }
207 break;
208 case GL_4_BYTES:
209 {
210 const GLubyte *src = (const GLubyte *) lists;
211 for (i = 0; i < n; i++) {
212 newLists[i] = (src[i*4+0] * 256 * 256 * 256 +
213 src[i*4+1] * 256 * 256 +
214 src[i*4+2] * 256 +
215 src[i*4+3]) + offset;
216 }
217 }
218 break;
219 default:
220 crWarning("CRServer: invalid display list datatype 0x%x", type);
221 }
222}
223
224
225void SERVER_DISPATCH_APIENTRY
226crServerDispatchCallLists( GLsizei n, GLenum type, const GLvoid *lists )
227{
228 if (!cr_server.sharedDisplayLists) {
229 /* need to translate IDs */
230 GLuint *newLists = (GLuint *) crAlloc(n * sizeof(GLuint));
231 if (newLists) {
232 TranslateListIDs(n, type, lists, newLists);
233 }
234 lists = newLists;
235 type = GL_UNSIGNED_INT;
236 }
237
238 if (cr_server.curClient->currentCtxInfo->pContext->lists.mode == 0) {
239 /* we're not compiling, so execute the list now */
240 /* Issue the list as-is */
241 cr_server.head_spu->dispatch_table.CallLists( n, type, lists );
242 crServerQueryHWState();
243 }
244 else {
245 /* we're compiling glCallList into another list - just pass it through */
246 cr_server.head_spu->dispatch_table.CallLists( n, type, lists );
247 }
248
249 if (!cr_server.sharedDisplayLists) {
250 crFree((void *) lists); /* malloc'd above */
251 }
252}
253
254
255GLboolean SERVER_DISPATCH_APIENTRY crServerDispatchIsList( GLuint list )
256{
257 GLboolean retval;
258 list = TranslateListID( list );
259 retval = cr_server.head_spu->dispatch_table.IsList( list );
260 crServerReturnValue( &retval, sizeof(retval) );
261 return retval;
262}
263
264
265void SERVER_DISPATCH_APIENTRY crServerDispatchDeleteLists( GLuint list, GLsizei range )
266{
267 list = TranslateListID( list );
268 crStateDeleteLists( list, range );
269 cr_server.head_spu->dispatch_table.DeleteLists( list, range );
270}
271
272
273void SERVER_DISPATCH_APIENTRY crServerDispatchBindTexture( GLenum target, GLuint texture )
274{
275 crStateBindTexture( target, texture );
276 cr_server.head_spu->dispatch_table.BindTexture(target, crStateGetTextureHWID(texture));
277}
278
279void SERVER_DISPATCH_APIENTRY crServerDispatchDeleteTextures( GLsizei n, const GLuint *textures)
280{
281 GLuint *newTextures = (GLuint *) crAlloc(n * sizeof(GLuint));
282 GLint i;
283
284 if (!newTextures)
285 {
286 crError("crServerDispatchDeleteTextures: out of memory");
287 return;
288 }
289
290 for (i = 0; i < n; i++)
291 {
292 newTextures[i] = crStateGetTextureHWID(textures[i]);
293 }
294
295 for (i = 0; i < n; ++i)
296 {
297 crDebug("DeleteTexture: %d, pid %d, ctx %d", textures[i], (uint32_t)cr_server.curClient->pid, cr_server.currentCtxInfo->pContext->id);
298 }
299
300
301 crStateDeleteTextures(n, textures);
302 cr_server.head_spu->dispatch_table.DeleteTextures(n, newTextures);
303 crFree(newTextures);
304}
305
306void SERVER_DISPATCH_APIENTRY crServerDispatchPrioritizeTextures( GLsizei n, const GLuint * textures, const GLclampf * priorities )
307{
308 GLuint *newTextures = (GLuint *) crAlloc(n * sizeof(GLuint));
309 GLint i;
310
311 if (!newTextures)
312 {
313 crError("crServerDispatchDeleteTextures: out of memory");
314 return;
315 }
316
317 crStatePrioritizeTextures(n, textures, priorities);
318
319 for (i = 0; i < n; i++)
320 {
321 newTextures[i] = crStateGetTextureHWID(textures[i]);
322 }
323
324 cr_server.head_spu->dispatch_table.PrioritizeTextures(n, newTextures, priorities);
325 crFree(newTextures);
326}
327
328void SERVER_DISPATCH_APIENTRY crServerDispatchDeleteProgramsARB(GLsizei n, const GLuint * programs)
329{
330 GLuint *pLocalProgs = (GLuint *) crAlloc(n * sizeof(GLuint));
331 GLint i;
332 if (!pLocalProgs) {
333 crError("crServerDispatchDeleteProgramsARB: out of memory");
334 return;
335 }
336 for (i = 0; i < n; i++) {
337 pLocalProgs[i] = crServerTranslateProgramID(programs[i]);
338 }
339 crStateDeleteProgramsARB(n, pLocalProgs);
340 cr_server.head_spu->dispatch_table.DeleteProgramsARB(n, pLocalProgs);
341 crFree(pLocalProgs);
342}
343
344/*@todo will fail for textures loaded from snapshot */
345GLboolean SERVER_DISPATCH_APIENTRY crServerDispatchIsTexture( GLuint texture )
346{
347 GLboolean retval;
348 retval = cr_server.head_spu->dispatch_table.IsTexture(crStateGetTextureHWID(texture));
349 crServerReturnValue( &retval, sizeof(retval) );
350 return retval; /* WILL PROBABLY BE IGNORED */
351}
352
353/*@todo will fail for progs loaded from snapshot */
354GLboolean SERVER_DISPATCH_APIENTRY crServerDispatchIsProgramARB( GLuint program )
355{
356 GLboolean retval;
357 program = crServerTranslateProgramID(program);
358 retval = cr_server.head_spu->dispatch_table.IsProgramARB( program );
359 crServerReturnValue( &retval, sizeof(retval) );
360 return retval; /* WILL PROBABLY BE IGNORED */
361}
362
363GLboolean SERVER_DISPATCH_APIENTRY
364crServerDispatchAreTexturesResident(GLsizei n, const GLuint *textures,
365 GLboolean *residences)
366{
367 GLboolean retval;
368 GLsizei i;
369 GLboolean *res = (GLboolean *) crAlloc(n * sizeof(GLboolean));
370 GLuint *textures2 = (GLuint *) crAlloc(n * sizeof(GLuint));
371
372 (void) residences;
373
374 for (i = 0; i < n; i++)
375 {
376 textures2[i] = crStateGetTextureHWID(textures[i]);
377 }
378 retval = cr_server.head_spu->dispatch_table.AreTexturesResident(n, textures2, res);
379
380 crFree(textures2);
381
382 crServerReturnValue(res, n * sizeof(GLboolean));
383
384 crFree(res);
385
386 return retval; /* WILL PROBABLY BE IGNORED */
387}
388
389
390GLboolean SERVER_DISPATCH_APIENTRY
391crServerDispatchAreProgramsResidentNV(GLsizei n, const GLuint *programs,
392 GLboolean *residences)
393{
394 GLboolean retval;
395 GLboolean *res = (GLboolean *) crAlloc(n * sizeof(GLboolean));
396 GLsizei i;
397
398 (void) residences;
399
400 if (!cr_server.sharedTextureObjects) {
401 GLuint *programs2 = (GLuint *) crAlloc(n * sizeof(GLuint));
402 for (i = 0; i < n; i++)
403 programs2[i] = crServerTranslateProgramID(programs[i]);
404 retval = cr_server.head_spu->dispatch_table.AreProgramsResidentNV(n, programs2, res);
405 crFree(programs2);
406 }
407 else {
408 retval = cr_server.head_spu->dispatch_table.AreProgramsResidentNV(n, programs, res);
409 }
410
411 crServerReturnValue(res, n * sizeof(GLboolean));
412 crFree(res);
413
414 return retval; /* WILL PROBABLY BE IGNORED */
415}
Note: See TracBrowser for help on using the repository browser.

© 2025 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette