svga_screen.c revision 2d958853080d74da3abb4251fba75cd7df9cd879
1/**********************************************************
2 * Copyright 2008-2009 VMware, Inc.  All rights reserved.
3 *
4 * Permission is hereby granted, free of charge, to any person
5 * obtaining a copy of this software and associated documentation
6 * files (the "Software"), to deal in the Software without
7 * restriction, including without limitation the rights to use, copy,
8 * modify, merge, publish, distribute, sublicense, and/or sell copies
9 * of the Software, and to permit persons to whom the Software is
10 * furnished to do so, subject to the following conditions:
11 *
12 * The above copyright notice and this permission notice shall be
13 * included in all copies or substantial portions of the Software.
14 *
15 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
16 * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
17 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
18 * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
19 * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
20 * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
21 * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
22 * SOFTWARE.
23 *
24 **********************************************************/
25
26#include "util/u_memory.h"
27#include "util/u_inlines.h"
28#include "util/u_string.h"
29#include "util/u_math.h"
30
31#include "svga_winsys.h"
32#include "svga_public.h"
33#include "svga_context.h"
34#include "svga_screen.h"
35#include "svga_resource_texture.h"
36#include "svga_resource.h"
37#include "svga_debug.h"
38
39#include "svga3d_shaderdefs.h"
40
41
42#ifdef DEBUG
43int SVGA_DEBUG = 0;
44
45static const struct debug_named_value svga_debug_flags[] = {
46   { "dma",      DEBUG_DMA, NULL },
47   { "tgsi",     DEBUG_TGSI, NULL },
48   { "pipe",     DEBUG_PIPE, NULL },
49   { "state",    DEBUG_STATE, NULL },
50   { "screen",   DEBUG_SCREEN, NULL },
51   { "tex",      DEBUG_TEX, NULL },
52   { "swtnl",    DEBUG_SWTNL, NULL },
53   { "const",    DEBUG_CONSTS, NULL },
54   { "viewport", DEBUG_VIEWPORT, NULL },
55   { "views",    DEBUG_VIEWS, NULL },
56   { "perf",     DEBUG_PERF, NULL },
57   { "flush",    DEBUG_FLUSH, NULL },
58   { "sync",     DEBUG_SYNC, NULL },
59   { "cache",    DEBUG_CACHE, NULL },
60   DEBUG_NAMED_VALUE_END
61};
62#endif
63
64static const char *
65svga_get_vendor( struct pipe_screen *pscreen )
66{
67   return "VMware, Inc.";
68}
69
70
71static const char *
72svga_get_name( struct pipe_screen *pscreen )
73{
74#ifdef DEBUG
75   /* Only return internal details in the DEBUG version:
76    */
77   return "SVGA3D; build: DEBUG; mutex: " PIPE_ATOMIC;
78#else
79   return "SVGA3D; build: RELEASE; ";
80#endif
81}
82
83
84
85
86static float
87svga_get_paramf(struct pipe_screen *screen, enum pipe_cap param)
88{
89   struct svga_screen *svgascreen = svga_screen(screen);
90   struct svga_winsys_screen *sws = svgascreen->sws;
91   SVGA3dDevCapResult result;
92
93   switch (param) {
94   case PIPE_CAP_MAX_LINE_WIDTH:
95      /* fall-through */
96   case PIPE_CAP_MAX_LINE_WIDTH_AA:
97      return 7.0;
98
99   case PIPE_CAP_MAX_POINT_WIDTH:
100      /* fall-through */
101   case PIPE_CAP_MAX_POINT_WIDTH_AA:
102      /* Keep this to a reasonable size to avoid failures in
103       * conform/pntaa.c:
104       */
105      return SVGA_MAX_POINTSIZE;
106
107   case PIPE_CAP_MAX_TEXTURE_ANISOTROPY:
108      if(!sws->get_cap(sws, SVGA3D_DEVCAP_MAX_TEXTURE_ANISOTROPY, &result))
109         return 4.0;
110      return result.u;
111
112   case PIPE_CAP_MAX_TEXTURE_LOD_BIAS:
113      return 16.0;
114
115   case PIPE_CAP_MAX_TEXTURE_IMAGE_UNITS:
116      return 16;
117   case PIPE_CAP_MAX_COMBINED_SAMPLERS:
118      return 16;
119   case PIPE_CAP_NPOT_TEXTURES:
120      return 1;
121   case PIPE_CAP_TWO_SIDED_STENCIL:
122      return 1;
123   case PIPE_CAP_GLSL:
124      return svgascreen->use_ps30 && svgascreen->use_vs30;
125   case PIPE_CAP_ANISOTROPIC_FILTER:
126      return 1;
127   case PIPE_CAP_POINT_SPRITE:
128      return 1;
129   case PIPE_CAP_MAX_RENDER_TARGETS:
130      if(!sws->get_cap(sws, SVGA3D_DEVCAP_MAX_RENDER_TARGETS, &result))
131         return 1;
132      if(!result.u)
133         return 1;
134      return MIN2(result.u, PIPE_MAX_COLOR_BUFS);
135   case PIPE_CAP_OCCLUSION_QUERY:
136      return 1;
137   case PIPE_CAP_TIMER_QUERY:
138      return 0;
139   case PIPE_CAP_TEXTURE_SHADOW_MAP:
140      return 1;
141
142   case PIPE_CAP_MAX_TEXTURE_2D_LEVELS:
143      {
144         unsigned levels = SVGA_MAX_TEXTURE_LEVELS;
145         if (sws->get_cap(sws, SVGA3D_DEVCAP_MAX_TEXTURE_WIDTH, &result))
146            levels = MIN2(util_logbase2(result.u) + 1, levels);
147         else
148            levels = 12 /* 2048x2048 */;
149         if (sws->get_cap(sws, SVGA3D_DEVCAP_MAX_TEXTURE_HEIGHT, &result))
150            levels = MIN2(util_logbase2(result.u) + 1, levels);
151         else
152            levels = 12 /* 2048x2048 */;
153         return levels;
154      }
155
156   case PIPE_CAP_MAX_TEXTURE_3D_LEVELS:
157      if (!sws->get_cap(sws, SVGA3D_DEVCAP_MAX_VOLUME_EXTENT, &result))
158         return 8;  /* max 128x128x128 */
159      return MIN2(util_logbase2(result.u) + 1, SVGA_MAX_TEXTURE_LEVELS);
160
161   case PIPE_CAP_MAX_TEXTURE_CUBE_LEVELS:
162      /*
163       * No mechanism to query the host, and at least limited to 2048x2048 on
164       * certain hardware.
165       */
166      return MIN2(screen->get_paramf(screen, PIPE_CAP_MAX_TEXTURE_2D_LEVELS),
167                  12.0 /* 2048x2048 */);
168
169   case PIPE_CAP_TEXTURE_MIRROR_REPEAT: /* req. for GL 1.4 */
170      return 1;
171
172   case PIPE_CAP_BLEND_EQUATION_SEPARATE: /* req. for GL 1.5 */
173      return 1;
174
175   case PIPE_CAP_TGSI_FS_COORD_ORIGIN_UPPER_LEFT:
176   case PIPE_CAP_TGSI_FS_COORD_PIXEL_CENTER_HALF_INTEGER:
177      return 1;
178   case PIPE_CAP_TGSI_FS_COORD_ORIGIN_LOWER_LEFT:
179   case PIPE_CAP_TGSI_FS_COORD_PIXEL_CENTER_INTEGER:
180      return 0;
181
182   case PIPE_CAP_DEPTHSTENCIL_CLEAR_SEPARATE:
183      return 1;
184
185   default:
186      return 0;
187   }
188}
189
190
191/* This is a fairly pointless interface
192 */
193static int
194svga_get_param(struct pipe_screen *screen, enum pipe_cap param)
195{
196   return (int) svga_get_paramf( screen, param );
197}
198
199static int svga_get_shader_param(struct pipe_screen *screen, unsigned shader, enum pipe_shader_cap param)
200{
201   struct svga_screen *svgascreen = svga_screen(screen);
202   struct svga_winsys_screen *sws = svgascreen->sws;
203   SVGA3dDevCapResult result;
204
205   switch (shader)
206   {
207   case PIPE_SHADER_FRAGMENT:
208      switch (param)
209      {
210      case PIPE_SHADER_CAP_MAX_INSTRUCTIONS:
211      case PIPE_SHADER_CAP_MAX_ALU_INSTRUCTIONS:
212      case PIPE_SHADER_CAP_MAX_TEX_INSTRUCTIONS:
213      case PIPE_SHADER_CAP_MAX_TEX_INDIRECTIONS:
214         return svgascreen->use_ps30 ? 512 : 96;
215      case PIPE_SHADER_CAP_MAX_CONTROL_FLOW_DEPTH:
216         return SVGA3D_MAX_NESTING_LEVEL;
217      case PIPE_SHADER_CAP_MAX_INPUTS:
218         return 10;
219      case PIPE_SHADER_CAP_MAX_CONSTS:
220         return svgascreen->use_ps30 ? 224 : 16;
221      case PIPE_SHADER_CAP_MAX_CONST_BUFFERS:
222         return 1;
223      case PIPE_SHADER_CAP_MAX_TEMPS:
224         if (!sws->get_cap(sws, SVGA3D_DEVCAP_MAX_FRAGMENT_SHADER_TEMPS, &result))
225            return svgascreen->use_ps30 ? 32 : 12;
226         return result.u;
227      case PIPE_SHADER_CAP_MAX_ADDRS:
228      case PIPE_SHADER_CAP_INDIRECT_INPUT_ADDR:
229	 /*
230	  * Although PS 3.0 has some addressing abilities it can only represent
231	  * loops that can be statically determined and unrolled. Given we can
232	  * only handle a subset of the cases that the state tracker already
233	  * does it is better to defer loop unrolling to the state tracker.
234	  */
235         return 0;
236      case PIPE_SHADER_CAP_MAX_PREDS:
237         return svgascreen->use_ps30 ? 1 : 0;
238      case PIPE_SHADER_CAP_TGSI_CONT_SUPPORTED:
239         return 1;
240      case PIPE_SHADER_CAP_INDIRECT_OUTPUT_ADDR:
241      case PIPE_SHADER_CAP_INDIRECT_TEMP_ADDR:
242      case PIPE_SHADER_CAP_INDIRECT_CONST_ADDR:
243         return 0;
244      case PIPE_SHADER_CAP_SUBROUTINES:
245         return 0;
246      }
247      break;
248   case PIPE_SHADER_VERTEX:
249      switch (param)
250      {
251      case PIPE_SHADER_CAP_MAX_INSTRUCTIONS:
252      case PIPE_SHADER_CAP_MAX_ALU_INSTRUCTIONS:
253         if (!sws->get_cap(sws, SVGA3D_DEVCAP_MAX_VERTEX_SHADER_INSTRUCTIONS, &result))
254            return svgascreen->use_vs30 ? 512 : 256;
255         return result.u;
256      case PIPE_SHADER_CAP_MAX_TEX_INSTRUCTIONS:
257      case PIPE_SHADER_CAP_MAX_TEX_INDIRECTIONS:
258         /* XXX: until we have vertex texture support */
259         return 0;
260      case PIPE_SHADER_CAP_MAX_CONTROL_FLOW_DEPTH:
261         return SVGA3D_MAX_NESTING_LEVEL;
262      case PIPE_SHADER_CAP_MAX_INPUTS:
263         return 16;
264      case PIPE_SHADER_CAP_MAX_CONSTS:
265         return 256;
266      case PIPE_SHADER_CAP_MAX_CONST_BUFFERS:
267         return 1;
268      case PIPE_SHADER_CAP_MAX_TEMPS:
269         if (!sws->get_cap(sws, SVGA3D_DEVCAP_MAX_VERTEX_SHADER_TEMPS, &result))
270            return svgascreen->use_vs30 ? 32 : 12;
271         return result.u;
272      case PIPE_SHADER_CAP_MAX_ADDRS:
273         return svgascreen->use_vs30 ? 1 : 0;
274      case PIPE_SHADER_CAP_MAX_PREDS:
275         return svgascreen->use_vs30 ? 1 : 0;
276      case PIPE_SHADER_CAP_TGSI_CONT_SUPPORTED:
277         return 1;
278      case PIPE_SHADER_CAP_INDIRECT_INPUT_ADDR:
279      case PIPE_SHADER_CAP_INDIRECT_OUTPUT_ADDR:
280         return svgascreen->use_vs30 ? 1 : 0;
281      case PIPE_SHADER_CAP_INDIRECT_TEMP_ADDR:
282         return 0;
283      case PIPE_SHADER_CAP_INDIRECT_CONST_ADDR:
284         return 1;
285      case PIPE_SHADER_CAP_SUBROUTINES:
286         return 0;
287      default:
288         break;
289      }
290      break;
291   default:
292      break;
293   }
294   return 0;
295}
296
297static INLINE SVGA3dDevCapIndex
298svga_translate_format_cap(enum pipe_format format)
299{
300   switch(format) {
301
302   case PIPE_FORMAT_B8G8R8A8_UNORM:
303      return SVGA3D_DEVCAP_SURFACEFMT_A8R8G8B8;
304   case PIPE_FORMAT_B8G8R8X8_UNORM:
305      return SVGA3D_DEVCAP_SURFACEFMT_X8R8G8B8;
306
307   case PIPE_FORMAT_B5G6R5_UNORM:
308      return SVGA3D_DEVCAP_SURFACEFMT_R5G6B5;
309   case PIPE_FORMAT_B5G5R5A1_UNORM:
310      return SVGA3D_DEVCAP_SURFACEFMT_A1R5G5B5;
311   case PIPE_FORMAT_B4G4R4A4_UNORM:
312      return SVGA3D_DEVCAP_SURFACEFMT_A4R4G4B4;
313
314   case PIPE_FORMAT_Z16_UNORM:
315      return SVGA3D_DEVCAP_SURFACEFMT_Z_D16;
316   case PIPE_FORMAT_S8_USCALED_Z24_UNORM:
317      return SVGA3D_DEVCAP_SURFACEFMT_Z_D24S8;
318   case PIPE_FORMAT_X8Z24_UNORM:
319      return SVGA3D_DEVCAP_SURFACEFMT_Z_D24X8;
320
321   case PIPE_FORMAT_A8_UNORM:
322      return SVGA3D_DEVCAP_SURFACEFMT_ALPHA8;
323   case PIPE_FORMAT_L8_UNORM:
324      return SVGA3D_DEVCAP_SURFACEFMT_LUMINANCE8;
325
326   case PIPE_FORMAT_DXT1_RGB:
327   case PIPE_FORMAT_DXT1_RGBA:
328      return SVGA3D_DEVCAP_SURFACEFMT_DXT1;
329   case PIPE_FORMAT_DXT3_RGBA:
330      return SVGA3D_DEVCAP_SURFACEFMT_DXT3;
331   case PIPE_FORMAT_DXT5_RGBA:
332      return SVGA3D_DEVCAP_SURFACEFMT_DXT5;
333
334   default:
335      return SVGA3D_DEVCAP_MAX;
336   }
337}
338
339
340static boolean
341svga_is_format_supported( struct pipe_screen *screen,
342                          enum pipe_format format,
343                          enum pipe_texture_target target,
344                          unsigned sample_count,
345                          unsigned tex_usage,
346                          unsigned geom_flags )
347{
348   struct svga_winsys_screen *sws = svga_screen(screen)->sws;
349   SVGA3dDevCapIndex index;
350   SVGA3dDevCapResult result;
351
352   assert(tex_usage);
353
354   if (sample_count > 1)
355      return FALSE;
356
357   /* Override host capabilities */
358   if (tex_usage & PIPE_BIND_RENDER_TARGET) {
359      switch(format) {
360
361      /* Often unsupported/problematic. This means we end up with the same
362       * visuals for all virtual hardware implementations.
363       */
364      case PIPE_FORMAT_B4G4R4A4_UNORM:
365      case PIPE_FORMAT_B5G5R5A1_UNORM:
366         return FALSE;
367
368      /* Simulate ability to render into compressed textures */
369      case PIPE_FORMAT_DXT1_RGB:
370      case PIPE_FORMAT_DXT1_RGBA:
371      case PIPE_FORMAT_DXT3_RGBA:
372      case PIPE_FORMAT_DXT5_RGBA:
373         return TRUE;
374
375      default:
376         break;
377      }
378   }
379
380   /* Try to query the host */
381   index = svga_translate_format_cap(format);
382   if( index < SVGA3D_DEVCAP_MAX &&
383       sws->get_cap(sws, index, &result) )
384   {
385      SVGA3dSurfaceFormatCaps mask;
386
387      mask.value = 0;
388      if (tex_usage & PIPE_BIND_RENDER_TARGET)
389         mask.offscreenRenderTarget = 1;
390      if (tex_usage & PIPE_BIND_DEPTH_STENCIL)
391         mask.zStencil = 1;
392      if (tex_usage & PIPE_BIND_SAMPLER_VIEW)
393         mask.texture = 1;
394
395      if ((result.u & mask.value) == mask.value)
396         return TRUE;
397      else
398         return FALSE;
399   }
400
401   /* Use our translate functions directly rather than relying on a
402    * duplicated list of supported formats which is prone to getting
403    * out of sync:
404    */
405   if(tex_usage & (PIPE_BIND_RENDER_TARGET | PIPE_BIND_DEPTH_STENCIL))
406      return svga_translate_format_render(format) != SVGA3D_FORMAT_INVALID;
407   else
408      return svga_translate_format(format) != SVGA3D_FORMAT_INVALID;
409}
410
411
412static void
413svga_fence_reference(struct pipe_screen *screen,
414                     struct pipe_fence_handle **ptr,
415                     struct pipe_fence_handle *fence)
416{
417   struct svga_winsys_screen *sws = svga_screen(screen)->sws;
418   sws->fence_reference(sws, ptr, fence);
419}
420
421
422static int
423svga_fence_signalled(struct pipe_screen *screen,
424                     struct pipe_fence_handle *fence,
425                     unsigned flag)
426{
427   struct svga_winsys_screen *sws = svga_screen(screen)->sws;
428   return sws->fence_signalled(sws, fence, flag);
429}
430
431
432static int
433svga_fence_finish(struct pipe_screen *screen,
434                  struct pipe_fence_handle *fence,
435                  unsigned flag)
436{
437   struct svga_winsys_screen *sws = svga_screen(screen)->sws;
438
439   SVGA_DBG(DEBUG_DMA|DEBUG_PERF, "%s fence_ptr %p\n",
440            __FUNCTION__, fence);
441
442   return sws->fence_finish(sws, fence, flag);
443}
444
445
446static void
447svga_destroy_screen( struct pipe_screen *screen )
448{
449   struct svga_screen *svgascreen = svga_screen(screen);
450
451   svga_screen_cache_cleanup(svgascreen);
452
453   pipe_mutex_destroy(svgascreen->swc_mutex);
454   pipe_mutex_destroy(svgascreen->tex_mutex);
455
456   svgascreen->sws->destroy(svgascreen->sws);
457
458   FREE(svgascreen);
459}
460
461
462/**
463 * Create a new svga_screen object
464 */
465struct pipe_screen *
466svga_screen_create(struct svga_winsys_screen *sws)
467{
468   struct svga_screen *svgascreen;
469   struct pipe_screen *screen;
470   SVGA3dDevCapResult result;
471
472#ifdef DEBUG
473   SVGA_DEBUG = debug_get_flags_option("SVGA_DEBUG", svga_debug_flags, 0 );
474#endif
475
476   svgascreen = CALLOC_STRUCT(svga_screen);
477   if (!svgascreen)
478      goto error1;
479
480   svgascreen->debug.force_level_surface_view =
481      debug_get_bool_option("SVGA_FORCE_LEVEL_SURFACE_VIEW", FALSE);
482   svgascreen->debug.force_surface_view =
483      debug_get_bool_option("SVGA_FORCE_SURFACE_VIEW", FALSE);
484   svgascreen->debug.force_sampler_view =
485      debug_get_bool_option("SVGA_FORCE_SAMPLER_VIEW", FALSE);
486   svgascreen->debug.no_surface_view =
487      debug_get_bool_option("SVGA_NO_SURFACE_VIEW", FALSE);
488   svgascreen->debug.no_sampler_view =
489      debug_get_bool_option("SVGA_NO_SAMPLER_VIEW", FALSE);
490
491   screen = &svgascreen->screen;
492
493   screen->destroy = svga_destroy_screen;
494   screen->get_name = svga_get_name;
495   screen->get_vendor = svga_get_vendor;
496   screen->get_param = svga_get_param;
497   screen->get_shader_param = svga_get_shader_param;
498   screen->get_paramf = svga_get_paramf;
499   screen->is_format_supported = svga_is_format_supported;
500   screen->context_create = svga_context_create;
501   screen->fence_reference = svga_fence_reference;
502   screen->fence_signalled = svga_fence_signalled;
503   screen->fence_finish = svga_fence_finish;
504   svgascreen->sws = sws;
505
506   svga_init_screen_resource_functions(svgascreen);
507
508   svgascreen->use_ps30 =
509      sws->get_cap(sws, SVGA3D_DEVCAP_FRAGMENT_SHADER_VERSION, &result) &&
510      result.u >= SVGA3DPSVERSION_30 ? TRUE : FALSE;
511
512   svgascreen->use_vs30 =
513      sws->get_cap(sws, SVGA3D_DEVCAP_VERTEX_SHADER_VERSION, &result) &&
514      result.u >= SVGA3DVSVERSION_30 ? TRUE : FALSE;
515
516#if 1
517   /* Shader model 2.0 is unsupported at the moment. */
518   if(!svgascreen->use_ps30 || !svgascreen->use_vs30)
519      goto error2;
520#else
521   if(debug_get_bool_option("SVGA_NO_SM30", FALSE))
522      svgascreen->use_vs30 = svgascreen->use_ps30 = FALSE;
523#endif
524
525   pipe_mutex_init(svgascreen->tex_mutex);
526   pipe_mutex_init(svgascreen->swc_mutex);
527
528   svga_screen_cache_init(svgascreen);
529
530   return screen;
531error2:
532   FREE(svgascreen);
533error1:
534   return NULL;
535}
536
537struct svga_winsys_screen *
538svga_winsys_screen(struct pipe_screen *screen)
539{
540   return svga_screen(screen)->sws;
541}
542
543#ifdef DEBUG
544struct svga_screen *
545svga_screen(struct pipe_screen *screen)
546{
547   assert(screen);
548   assert(screen->destroy == svga_destroy_screen);
549   return (struct svga_screen *)screen;
550}
551#endif
552