1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
|
/* $Id: expandospu.c $ */
/** @file
* Implementation of routines which Expando SPU explicitly overrides.
*/
/* Copyright (c) 2001, Stanford University
* All rights reserved
*
* See the file LICENSE.txt for information on redistributing this software.
*/
/*
* Copyright (C) 2015-2019 Oracle Corporation
*
* This file is part of VirtualBox Open Source Edition (OSE), as
* available from http://www.virtualbox.org. This file is free software;
* you can redistribute it and/or modify it under the terms of the GNU
* General Public License (GPL) as published by the Free Software
* Foundation, in version 2 as it comes in the "COPYING" file of the
* VirtualBox OSE distribution. VirtualBox OSE is distributed in the
* hope that it will be useful, but WITHOUT ANY WARRANTY of any kind.
*/
#include <stdio.h>
#include "cr_spu.h"
#include "cr_dlm.h"
#include "cr_mem.h"
#include "expandospu.h"
extern GLint EXPANDOSPU_APIENTRY
expandoCreateContext(const char *displayName, GLint visBits, GLint shareCtx)
{
ExpandoContextState *contextState;
/* Allocate our own per-context record */
contextState = crCalloc(sizeof(ExpandoContextState));
if (contextState)
{
GLint contextId;
/* Get an official context ID from our super */
contextId = expando_spu.super.CreateContext(displayName, visBits, shareCtx);
/* Supplement that with our DLM. In a more correct situation, we should
* see if we've been called through glXCreateContext, which has a parameter
* for sharing DLMs. We don't currently get that information, so for now
* give each context its own DLM.
*/
contextState->dlm = crDLMNewDLM(0, NULL);
if (contextState->dlm)
{
contextState->dlmContext = crDLMNewContext(contextState->dlm);
if (contextState->dlmContext)
{
/* The DLM needs us to use the state tracker to track client
* state, so we can compile client-state-using functions correctly.
*/
contextState->State = crStateCreateContext(NULL, visBits, NULL);
/* Associate the Expando context with the user context. */
crHashtableAdd(expando_spu.contextTable, contextId, (void *)contextState);
crDebug("Expando SPU: created context %d (contextState=%p, contextState->dlm=%p, "
"contextState->dlmContext=%p, contextState->State=%p).",
contextId, contextState, contextState->dlm, contextState->dlmContext, contextState->State);
return contextId;
}
else
crError("Expando SPU: can't allocate new DLM context.");
crDLMFreeDLM(contextState->dlm, &expando_spu.super);
}
else
crError("Expando SPU: can't allocate new DLM.");
crFree(contextState);
}
else
crError("Expando SPU: couldn't allocate per-context state");
return 0;
}
void expando_free_context_state(void *data)
{
ExpandoContextState *contextState = (ExpandoContextState *)data;
crDebug("Expando SPU: destroying context internals: "
"contextState=%p, contextState->dlm=%p, contextState->dlmContext=%p, contextState->State=%p",
contextState, contextState->dlm, contextState->dlmContext, contextState->State);
crDLMFreeContext(contextState->dlmContext, &expando_spu.super);
crDLMFreeDLM(contextState->dlm, &expando_spu.super);
crStateDestroyContext(contextState->State);
crFree(contextState);
}
void EXPANDOSPU_APIENTRY
expandoDestroyContext(GLint contextId)
{
crDebug("Expando SPU: destroy context %d.", contextId);
/* Destroy our context information */
crHashtableDelete(expando_spu.contextTable, contextId, expando_free_context_state);
/* Pass along the destruction to our super. */
expando_spu.super.DestroyContext(contextId);
}
void EXPANDOSPU_APIENTRY
expandoMakeCurrent(GLint crWindow, GLint nativeWindow, GLint contextId)
{
ExpandoContextState *expandoContextState;
expando_spu.super.MakeCurrent(crWindow, nativeWindow, contextId);
expandoContextState = crHashtableSearch(expando_spu.contextTable, contextId);
if (expandoContextState)
{
crDebug("Expando SPU: switch to context %d.", contextId);
crDLMSetCurrentState(expandoContextState->dlmContext);
crStateMakeCurrent(expandoContextState->State);
}
else
{
crDebug("Expando SPU: can't switch to context %d: not found.", contextId);
crDLMSetCurrentState(NULL);
crStateMakeCurrent(NULL);
}
}
extern void EXPANDOSPU_APIENTRY
expandoNewList(GLuint list, GLenum mode)
{
crDLMNewList(list, mode, &expando_spu.super);
}
extern void EXPANDOSPU_APIENTRY
expandoEndList(void)
{
crDLMEndList(&expando_spu.super);
}
extern void EXPANDOSPU_APIENTRY
expandoDeleteLists(GLuint first, GLsizei range)
{
crDLMDeleteLists(first, range, &expando_spu.super);
}
extern GLuint EXPANDOSPU_APIENTRY
expandoGenLists(GLsizei range)
{
return crDLMGenLists(range, &expando_spu.super);
}
void EXPANDOSPU_APIENTRY
expandoListBase(GLuint base)
{
crDLMListBase(base, &expando_spu.super);
}
extern GLboolean EXPANDOSPU_APIENTRY
expandoIsList(GLuint list)
{
return crDLMIsList(list, &expando_spu.super);
}
extern void EXPANDOSPU_APIENTRY
expandoCallList(GLuint list)
{
crDLMCallList(list, &expando_spu.super);
}
extern void EXPANDOSPU_APIENTRY
expandoCallLists(GLsizei n, GLenum type, const GLvoid *lists)
{
crDLMCallLists(n, type, lists, &expando_spu.super);
}
|