i965g: consolidate some includes
[mesa.git] / src / gallium / winsys / drm / i965 / xlib / xlib_i965.c
1 /**************************************************************************
2 *
3 * Copyright 2007 Tungsten Graphics, Inc., Bismarck, ND., USA
4 * All Rights Reserved.
5 *
6 * Permission is hereby granted, free of charge, to any person obtaining a
7 * copy of this software and associated documentation files (the
8 * "Software"), to deal in the Software without restriction, including
9 * without limitation the rights to use, copy, modify, merge, publish,
10 * distribute, sub license, and/or sell copies of the Software, and to
11 * permit persons to whom the Software is furnished to do so, subject to
12 * the following conditions:
13 *
14 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16 * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
17 * THE COPYRIGHT HOLDERS, AUTHORS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM,
18 * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
19 * OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE
20 * USE OR OTHER DEALINGS IN THE SOFTWARE.
21 *
22 * The above copyright notice and this permission notice (including the
23 * next paragraph) shall be included in all copies or substantial portions
24 * of the Software.
25 *
26 *
27 **************************************************************************/
28
29 /*
30 * Authors:
31 * Keith Whitwell
32 * Brian Paul
33 */
34
35
36 #include "util/u_memory.h"
37 #include "util/u_math.h"
38 #include "pipe/p_error.h"
39 #include "pipe/p_context.h"
40
41 #include "xm_winsys.h"
42
43 #include "i965/brw_winsys.h"
44 #include "i965/brw_screen.h"
45 #include "i965/brw_reg.h"
46
47 #define MAX_VRAM (128*1024*1024)
48
49 struct xlib_brw_buffer
50 {
51 struct brw_winsys_buffer base;
52 unsigned offset;
53 unsigned type;
54 char *virtual;
55 unsigned cheesy_refcount;
56 int map_count;
57 };
58
59
60 /**
61 * Subclass of brw_winsys_screen for Xlib winsys
62 */
63 struct xlib_brw_winsys
64 {
65 struct brw_winsys_screen base;
66 unsigned offset;
67 };
68
69 static struct xlib_brw_winsys *
70 xlib_brw_winsys( struct brw_winsys_screen *screen )
71 {
72 return (struct xlib_brw_winsys *)screen;
73 }
74
75
76 static struct xlib_brw_buffer *
77 xlib_brw_buffer( struct brw_winsys_buffer *buffer )
78 {
79 return (struct xlib_brw_buffer *)buffer;
80 }
81
82
83
84 const char *names[BRW_BUFFER_TYPE_MAX] = {
85 "texture",
86 "scanout",
87 "vertex",
88 "curbe",
89 "query",
90 "shader_constants",
91 "wm_scratch",
92 "batch",
93 "state_cache",
94 "pixel",
95 "generic",
96 };
97
98 const char *usages[BRW_USAGE_MAX] = {
99 "state",
100 "query_result",
101 "render_target",
102 "depth_buffer",
103 "blit_source",
104 "blit_dest",
105 "sampler",
106 "vertex",
107 "scratch"
108 };
109
110 static struct brw_winsys_buffer *
111 xlib_brw_bo_alloc( struct brw_winsys_screen *sws,
112 enum brw_buffer_type type,
113 unsigned size,
114 unsigned alignment )
115 {
116 struct xlib_brw_winsys *xbw = xlib_brw_winsys(sws);
117 struct xlib_brw_buffer *buf;
118
119 debug_printf("%s type %d sz %d align %d\n",
120 __FUNCTION__, type, size, alignment );
121
122 buf = CALLOC_STRUCT(xlib_brw_buffer);
123 if (!buf)
124 return NULL;
125
126 buf->offset = align(xbw->offset, alignment);
127 buf->type = type;
128 buf->virtual = MALLOC(size);
129 buf->cheesy_refcount = 1;
130 buf->base.offset = &buf->offset; /* hmm, cheesy */
131 buf->base.size = size;
132
133 xbw->offset = align(xbw->offset, alignment) + size;
134 if (xbw->offset > MAX_VRAM)
135 goto err;
136
137 return &buf->base;
138
139 err:
140 assert(0);
141 FREE(buf);
142 return NULL;
143 }
144
145 static void
146 xlib_brw_bo_reference( struct brw_winsys_buffer *buffer )
147 {
148 struct xlib_brw_buffer *buf = xlib_brw_buffer(buffer);
149
150 buf->cheesy_refcount++;
151 }
152
153 static void
154 xlib_brw_bo_unreference( struct brw_winsys_buffer *buffer )
155 {
156 struct xlib_brw_buffer *buf = xlib_brw_buffer(buffer);
157
158 /* As a special favor in this call only, buffer is allowed to be
159 * NULL:
160 */
161 if (buffer == NULL)
162 return;
163
164 if (--buf->cheesy_refcount == 0) {
165 FREE(buffer);
166 }
167 }
168
169 static int
170 xlib_brw_bo_emit_reloc( struct brw_winsys_buffer *buffer,
171 enum brw_buffer_usage usage,
172 unsigned delta,
173 unsigned offset,
174 struct brw_winsys_buffer *buffer2)
175 {
176 struct xlib_brw_buffer *buf = xlib_brw_buffer(buffer);
177 struct xlib_brw_buffer *buf2 = xlib_brw_buffer(buffer2);
178
179 debug_printf("%s buf %p offset %x val %x + %x buf2 %p/%s/%s\n",
180 __FUNCTION__, (void *)buffer, offset,
181 buf2->offset, delta,
182 (void *)buffer2, names[buf2->type], usages[usage]);
183
184 *(uint32_t *)(buf->virtual + offset) = buf2->offset + delta;
185
186 return 0;
187 }
188
189 static int
190 xlib_brw_bo_exec( struct brw_winsys_buffer *buffer,
191 unsigned bytes_used )
192 {
193 debug_printf("execute buffer %p, bytes %d\n", (void *)buffer, bytes_used);
194
195 return 0;
196 }
197
198 static int
199 xlib_brw_bo_subdata(struct brw_winsys_buffer *buffer,
200 size_t offset,
201 size_t size,
202 const void *data)
203 {
204 struct xlib_brw_buffer *buf = xlib_brw_buffer(buffer);
205
206 debug_printf("%s buf %p off %d sz %d data %p\n",
207 __FUNCTION__,
208 (void *)buffer, offset, size, data);
209
210 memcpy(buf->virtual + offset, data, size);
211 return 0;
212 }
213
214
215 static boolean
216 xlib_brw_bo_is_busy(struct brw_winsys_buffer *buffer)
217 {
218 debug_printf("%s %p\n", __FUNCTION__, (void *)buffer);
219 return TRUE;
220 }
221
222 static boolean
223 xlib_brw_bo_references(struct brw_winsys_buffer *a,
224 struct brw_winsys_buffer *b)
225 {
226 debug_printf("%s %p %p\n", __FUNCTION__, (void *)a, (void *)b);
227 return TRUE;
228 }
229
230 static enum pipe_error
231 xlib_brw_check_aperture_space( struct brw_winsys_screen *iws,
232 struct brw_winsys_buffer **buffers,
233 unsigned count )
234 {
235 unsigned tot_size = 0;
236 unsigned i;
237
238 for (i = 0; i < count; i++)
239 tot_size += buffers[i]->size;
240
241 debug_printf("%s %d bufs, tot_size: %d kb\n",
242 __FUNCTION__, count,
243 (tot_size + 1023) / 1024);
244
245 return PIPE_OK;
246 }
247
248 static void *
249 xlib_brw_bo_map(struct brw_winsys_buffer *buffer,
250 boolean write)
251 {
252 struct xlib_brw_buffer *buf = xlib_brw_buffer(buffer);
253
254 debug_printf("%s %p %s\n", __FUNCTION__, (void *)buffer,
255 write ? "read/write" : "read");
256
257 buf->map_count++;
258 return buf->virtual;
259 }
260
261 static void
262 xlib_brw_bo_unmap(struct brw_winsys_buffer *buffer)
263 {
264 struct xlib_brw_buffer *buf = xlib_brw_buffer(buffer);
265
266 debug_printf("%s %p\n", __FUNCTION__, (void *)buffer);
267
268 --buf->map_count;
269 assert(buf->map_count >= 0);
270 }
271
272
273 static void
274 xlib_brw_winsys_destroy( struct brw_winsys_screen *screen )
275 {
276 /* XXX: free all buffers */
277 FREE(screen);
278 }
279
280 static struct brw_winsys_screen *
281 xlib_create_brw_winsys_screen( void )
282 {
283 struct xlib_brw_winsys *ws;
284
285 ws = CALLOC_STRUCT(xlib_brw_winsys);
286 if (!ws)
287 return NULL;
288
289 ws->base.destroy = xlib_brw_winsys_destroy;
290 ws->base.bo_alloc = xlib_brw_bo_alloc;
291 ws->base.bo_reference = xlib_brw_bo_reference;
292 ws->base.bo_unreference = xlib_brw_bo_unreference;
293 ws->base.bo_emit_reloc = xlib_brw_bo_emit_reloc;
294 ws->base.bo_exec = xlib_brw_bo_exec;
295 ws->base.bo_subdata = xlib_brw_bo_subdata;
296 ws->base.bo_is_busy = xlib_brw_bo_is_busy;
297 ws->base.bo_references = xlib_brw_bo_references;
298 ws->base.check_aperture_space = xlib_brw_check_aperture_space;
299 ws->base.bo_map = xlib_brw_bo_map;
300 ws->base.bo_unmap = xlib_brw_bo_unmap;
301
302 return &ws->base;
303 }
304
305
306 /***********************************************************************
307 * Implementation of Xlib co-state-tracker's winsys interface
308 */
309
310 static void
311 xlib_i965_display_surface(struct xmesa_buffer *xm_buffer,
312 struct pipe_surface *surf)
313 {
314 /* struct brw_texture *texture = brw_texture(surf->texture); */
315
316 debug_printf("%s tex %p, sz %dx%d\n", __FUNCTION__,
317 (void *)surf->texture,
318 surf->texture->width[0],
319 surf->texture->height[0]);
320 }
321
322 static void
323 xlib_i965_flush_frontbuffer(struct pipe_screen *screen,
324 struct pipe_surface *surf,
325 void *context_private)
326 {
327 xlib_i965_display_surface(NULL, surf);
328 }
329
330
331 static struct pipe_screen *
332 xlib_create_i965_screen( void )
333 {
334 struct brw_winsys_screen *winsys;
335 struct pipe_screen *screen;
336
337 winsys = xlib_create_brw_winsys_screen();
338 if (winsys == NULL)
339 return NULL;
340
341 screen = brw_create_screen(winsys, PCI_CHIP_GM45_GM);
342 if (screen == NULL)
343 goto fail;
344
345 screen->flush_frontbuffer = xlib_i965_flush_frontbuffer;
346 return screen;
347
348 fail:
349 if (winsys)
350 winsys->destroy( winsys );
351
352 return NULL;
353 }
354
355
356 static struct pipe_context *
357 xlib_create_i965_context( struct pipe_screen *screen,
358 void *context_private )
359 {
360 struct pipe_context *pipe;
361
362 pipe = brw_create_context(screen);
363 if (pipe == NULL)
364 goto fail;
365
366 pipe->priv = context_private;
367 return pipe;
368
369 fail:
370 /* Free stuff here */
371 return NULL;
372 }
373
374
375
376
377 struct xm_driver xlib_i965_driver =
378 {
379 .create_pipe_screen = xlib_create_i965_screen,
380 .create_pipe_context = xlib_create_i965_context,
381 .display_surface = xlib_i965_display_surface
382 };
383
384
385 /* Register this driver at library load:
386 */
387 static void _init( void ) __attribute__((constructor));
388 static void _init( void )
389 {
390 xmesa_set_driver( &xlib_i965_driver );
391 }
392
393
394
395 /***********************************************************************
396 *
397 * Butt-ugly hack to convince the linker not to throw away public GL
398 * symbols (they are all referenced from getprocaddress, I guess).
399 */
400 extern void (*linker_foo(const unsigned char *procName))();
401 extern void (*glXGetProcAddress(const unsigned char *procName))();
402
403 extern void (*linker_foo(const unsigned char *procName))()
404 {
405 return glXGetProcAddress(procName);
406 }