implement auto mipmap generation for compressed textures
[mesa.git] / src / mesa / main / imports.c
1 /* $Id: imports.c,v 1.20 2002/10/15 15:36:26 brianp Exp $ */
2
3 /*
4 * Mesa 3-D graphics library
5 * Version: 4.1
6 *
7 * Copyright (C) 1999-2002 Brian Paul All Rights Reserved.
8 *
9 * Permission is hereby granted, free of charge, to any person obtaining a
10 * copy of this software and associated documentation files (the "Software"),
11 * to deal in the Software without restriction, including without limitation
12 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
13 * and/or sell copies of the Software, and to permit persons to whom the
14 * Software is furnished to do so, subject to the following conditions:
15 *
16 * The above copyright notice and this permission notice shall be included
17 * in all copies or substantial portions of the Software.
18 *
19 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
20 * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
21 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
22 * BRIAN PAUL BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
23 * AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
24 * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
25 */
26
27
28 /*
29 * Imports are services which the device driver or window system or
30 * operating system provides to the core renderer. The core renderer (Mesa)
31 * will call these functions in order to do memory allocation, simple I/O,
32 * etc.
33 *
34 * Some drivers will want to override/replace this file with something
35 * specialized, but most Mesa drivers will be able to call
36 *_mesa_init_default_imports() and go with what's here.
37 *
38 * Eventually, I'd like to move most of the stuff in glheader.h and mem.[ch]
39 * into imports.[ch]. Then we'll really have one, single place where
40 * all OS-related dependencies are isolated.
41 */
42
43
44 #include "glheader.h"
45 #include "mtypes.h"
46 #include "context.h"
47 #include "imports.h"
48 #include "mem.h"
49
50 #define MAXSTRING 4000 /* for vsnprintf() */
51
52 #ifdef WIN32
53 #define vsnprintf _vsnprintf
54 #endif
55
56 static void *
57 _mesa_Malloc(__GLcontext *gc, size_t size)
58 {
59 return MALLOC(size);
60 }
61
62 static void *
63 _mesa_Calloc(__GLcontext *gc, size_t numElem, size_t elemSize)
64 {
65 return CALLOC(numElem * elemSize);
66 }
67
68 static void *
69 _mesa_Realloc(__GLcontext *gc, void *oldAddr, size_t newSize)
70 {
71 return realloc(oldAddr, newSize);
72 }
73
74 static void
75 _mesa_Free(__GLcontext *gc, void *addr)
76 {
77 FREE(addr);
78 }
79
80
81 /* Must be before '#undef getenv' for inclusion in XFree86.
82 */
83 char * CAPI
84 _mesa_getenv(__GLcontext *gc, const char *var)
85 {
86 (void) gc;
87 #ifdef XFree86LOADER
88 return xf86getenv(var);
89 #else
90 return getenv(var);
91 #endif
92 }
93
94
95 static void
96 warning(__GLcontext *gc, char *str)
97 {
98 GLboolean debug;
99 #ifdef DEBUG
100 debug = GL_TRUE;
101 #else
102 if (_mesa_getenv(gc , "MESA_DEBUG"))
103 debug = GL_TRUE;
104 else
105 debug = GL_FALSE;
106 #endif
107 if (debug) {
108 fprintf(stderr, "Mesa warning: %s\n", str);
109 }
110 }
111
112
113 void
114 _mesa_fatal(__GLcontext *gc, char *str)
115 {
116 (void) gc;
117 fprintf(stderr, "%s\n", str);
118 abort();
119 }
120
121
122 static int CAPI
123 _mesa_atoi(__GLcontext *gc, const char *str)
124 {
125 (void) gc;
126 return atoi(str);
127 }
128
129
130 int CAPI
131 _mesa_sprintf(__GLcontext *gc, char *str, const char *fmt, ...)
132 {
133 int r;
134 va_list args;
135 va_start( args, fmt );
136 r = vsprintf( str, fmt, args );
137 va_end( args );
138 return r;
139 }
140
141
142 void * CAPI
143 _mesa_fopen(__GLcontext *gc, const char *path, const char *mode)
144 {
145 return fopen(path, mode);
146 }
147
148
149 int CAPI
150 _mesa_fclose(__GLcontext *gc, void *stream)
151 {
152 return fclose((FILE *) stream);
153 }
154
155
156 int CAPI
157 _mesa_fprintf(__GLcontext *gc, void *stream, const char *fmt, ...)
158 {
159 int r;
160 va_list args;
161 va_start( args, fmt );
162 r = vfprintf( (FILE *) stream, fmt, args );
163 va_end( args );
164 return r;
165 }
166
167
168 /* XXX this really is driver-specific and can't be here */
169 static __GLdrawablePrivate *
170 _mesa_GetDrawablePrivate(__GLcontext *gc)
171 {
172 return NULL;
173 }
174
175
176
177 void
178 _mesa_warning(__GLcontext *gc, const char *fmtString, ...)
179 {
180 char str[MAXSTRING];
181 va_list args;
182 va_start( args, fmtString );
183 (void) vsnprintf( str, MAXSTRING, fmtString, args );
184 va_end( args );
185 warning(gc, str);
186 }
187
188
189 /*
190 * This function is called when the Mesa user has stumbled into a code
191 * path which may not be implemented fully or correctly.
192 */
193 void
194 _mesa_problem( const GLcontext *ctx, const char *s )
195 {
196 if (ctx) {
197 ctx->imports.fprintf((GLcontext *) ctx, stderr, "Mesa implementation error: %s\n", s);
198 #ifdef XF86DRI
199 ctx->imports.fprintf((GLcontext *) ctx, stderr, "Please report to the DRI bug database at dri.sourceforge.net\n");
200 #else
201 ctx->imports.fprintf((GLcontext *) ctx, stderr, "Please report to the Mesa bug database at www.mesa3d.org\n" );
202 #endif
203 }
204 else {
205 /* what can we do if we don't have a context???? */
206 fprintf( stderr, "Mesa implementation error: %s\n", s );
207 #ifdef XF86DRI
208 fprintf( stderr, "Please report to the DRI bug database at dri.sourceforge.net\n");
209 #else
210 fprintf( stderr, "Please report to the Mesa bug database at www.mesa3d.org\n" );
211 #endif
212 }
213 }
214
215
216 /*
217 * If in debug mode, print error message to stdout.
218 * Also, record the error code by calling _mesa_record_error().
219 * Input: ctx - the GL context
220 * error - the error value
221 * fmtString - printf-style format string, followed by optional args
222 */
223 void
224 _mesa_error( GLcontext *ctx, GLenum error, const char *fmtString, ... )
225 {
226 const char *debugEnv;
227 GLboolean debug;
228
229 debugEnv = _mesa_getenv(ctx, "MESA_DEBUG");
230
231 #ifdef DEBUG
232 if (debugEnv && strstr(debugEnv, "silent"))
233 debug = GL_FALSE;
234 else
235 debug = GL_TRUE;
236 #else
237 if (debugEnv)
238 debug = GL_TRUE;
239 else
240 debug = GL_FALSE;
241 #endif
242
243 if (debug) {
244 va_list args;
245 char where[MAXSTRING];
246 const char *errstr;
247
248 va_start( args, fmtString );
249 vsnprintf( where, MAXSTRING, fmtString, args );
250 va_end( args );
251
252 switch (error) {
253 case GL_NO_ERROR:
254 errstr = "GL_NO_ERROR";
255 break;
256 case GL_INVALID_VALUE:
257 errstr = "GL_INVALID_VALUE";
258 break;
259 case GL_INVALID_ENUM:
260 errstr = "GL_INVALID_ENUM";
261 break;
262 case GL_INVALID_OPERATION:
263 errstr = "GL_INVALID_OPERATION";
264 break;
265 case GL_STACK_OVERFLOW:
266 errstr = "GL_STACK_OVERFLOW";
267 break;
268 case GL_STACK_UNDERFLOW:
269 errstr = "GL_STACK_UNDERFLOW";
270 break;
271 case GL_OUT_OF_MEMORY:
272 errstr = "GL_OUT_OF_MEMORY";
273 break;
274 case GL_TABLE_TOO_LARGE:
275 errstr = "GL_TABLE_TOO_LARGE";
276 break;
277 default:
278 errstr = "unknown";
279 break;
280 }
281 _mesa_debug(ctx, "Mesa user error: %s in %s\n", errstr, where);
282 }
283
284 _mesa_record_error(ctx, error);
285 }
286
287
288 /*
289 * Call this to report debug information. Uses stderr.
290 */
291 void
292 _mesa_debug( const GLcontext *ctx, const char *fmtString, ... )
293 {
294 char s[MAXSTRING];
295 va_list args;
296 va_start(args, fmtString);
297 vsnprintf(s, MAXSTRING, fmtString, args);
298 if (ctx)
299 (void) ctx->imports.fprintf( (__GLcontext *) ctx, stderr, s );
300 else
301 fprintf( stderr, s );
302 va_end(args);
303 }
304
305
306 /*
307 * A wrapper for printf. Uses stdout.
308 */
309 void
310 _mesa_printf( const GLcontext *ctx, const char *fmtString, ... )
311 {
312 char s[MAXSTRING];
313 va_list args;
314 va_start( args, fmtString );
315 vsnprintf(s, MAXSTRING, fmtString, args);
316 if (ctx)
317 (void) ctx->imports.fprintf( (__GLcontext *) ctx, stdout, s );
318 else
319 printf( s );
320 va_end( args );
321 }
322
323
324 /*
325 * Initialize a __GLimports object to point to the functions in
326 * this file. This is to be called from device drivers.
327 * Input: imports - the object to init
328 * driverCtx - pointer to device driver-specific data
329 */
330 void
331 _mesa_init_default_imports(__GLimports *imports, void *driverCtx)
332 {
333 imports->malloc = _mesa_Malloc;
334 imports->calloc = _mesa_Calloc;
335 imports->realloc = _mesa_Realloc;
336 imports->free = _mesa_Free;
337 imports->warning = warning;
338 imports->fatal = _mesa_fatal;
339 imports->getenv = _mesa_getenv;
340 imports->atoi = _mesa_atoi;
341 imports->sprintf = _mesa_sprintf;
342 imports->fopen = _mesa_fopen;
343 imports->fclose = _mesa_fclose;
344 imports->fprintf = _mesa_fprintf;
345 imports->getDrawablePrivate = _mesa_GetDrawablePrivate;
346 imports->other = driverCtx;
347 }