summaryrefslogtreecommitdiffstats
path: root/src/gallium/drivers/svga/svga_screen.c
diff options
context:
space:
mode:
authorBrian Paul <[email protected]>2015-08-13 11:00:58 -0700
committerBrian Paul <[email protected]>2015-09-02 09:27:43 -0600
commite054251ed11e25a080f64b92db9334c9b07c8c76 (patch)
treeefef5b1ec8f9252e40032774747b2ca124a4de07 /src/gallium/drivers/svga/svga_screen.c
parent656dac120d27e060986d97e790334f67a34a6e23 (diff)
svga: update driver for version 10 GPU interface
This is a squash commit of roughly two years of development work. Authors include: Brian Paul Charmaine Lee Thomas Hellstrom Jakob Bornecrantz Sinclair Yeh Mingcheng Chen Kai Ninomiya MengLin Wu The driver supports OpenGL 3.3. Signed-off-by: Brian Paul <[email protected]>
Diffstat (limited to 'src/gallium/drivers/svga/svga_screen.c')
-rw-r--r--src/gallium/drivers/svga/svga_screen.c441
1 files changed, 329 insertions, 112 deletions
diff --git a/src/gallium/drivers/svga/svga_screen.c b/src/gallium/drivers/svga/svga_screen.c
index 66c3deaa9e7..f2ae40b4fad 100644
--- a/src/gallium/drivers/svga/svga_screen.c
+++ b/src/gallium/drivers/svga/svga_screen.c
@@ -34,31 +34,37 @@
#include "svga_context.h"
#include "svga_format.h"
#include "svga_screen.h"
+#include "svga_tgsi.h"
#include "svga_resource_texture.h"
#include "svga_resource.h"
#include "svga_debug.h"
#include "svga3d_shaderdefs.h"
+#include "VGPU10ShaderTokens.h"
+/* NOTE: this constant may get moved into a svga3d*.h header file */
+#define SVGA3D_DX_MAX_RESOURCE_SIZE (128 * 1024 * 1024)
#ifdef DEBUG
int SVGA_DEBUG = 0;
static const struct debug_named_value svga_debug_flags[] = {
- { "dma", DEBUG_DMA, NULL },
- { "tgsi", DEBUG_TGSI, NULL },
- { "pipe", DEBUG_PIPE, NULL },
- { "state", DEBUG_STATE, NULL },
- { "screen", DEBUG_SCREEN, NULL },
- { "tex", DEBUG_TEX, NULL },
- { "swtnl", DEBUG_SWTNL, NULL },
- { "const", DEBUG_CONSTS, NULL },
- { "viewport", DEBUG_VIEWPORT, NULL },
- { "views", DEBUG_VIEWS, NULL },
- { "perf", DEBUG_PERF, NULL },
- { "flush", DEBUG_FLUSH, NULL },
- { "sync", DEBUG_SYNC, NULL },
- { "cache", DEBUG_CACHE, NULL },
+ { "dma", DEBUG_DMA, NULL },
+ { "tgsi", DEBUG_TGSI, NULL },
+ { "pipe", DEBUG_PIPE, NULL },
+ { "state", DEBUG_STATE, NULL },
+ { "screen", DEBUG_SCREEN, NULL },
+ { "tex", DEBUG_TEX, NULL },
+ { "swtnl", DEBUG_SWTNL, NULL },
+ { "const", DEBUG_CONSTS, NULL },
+ { "viewport", DEBUG_VIEWPORT, NULL },
+ { "views", DEBUG_VIEWS, NULL },
+ { "perf", DEBUG_PERF, NULL },
+ { "flush", DEBUG_FLUSH, NULL },
+ { "sync", DEBUG_SYNC, NULL },
+ { "cache", DEBUG_CACHE, NULL },
+ { "streamout", DEBUG_STREAMOUT, NULL },
+ { "query", DEBUG_QUERY, NULL },
DEBUG_NAMED_VALUE_END
};
#endif
@@ -80,18 +86,52 @@ svga_get_name( struct pipe_screen *pscreen )
*/
build = "build: DEBUG;";
mutex = "mutex: " PIPE_ATOMIC ";";
-#ifdef HAVE_LLVM
- llvm = "LLVM;";
-#endif
#else
build = "build: RELEASE;";
#endif
+#ifdef HAVE_LLVM
+ llvm = "LLVM;";
+#endif
util_snprintf(name, sizeof(name), "SVGA3D; %s %s %s", build, mutex, llvm);
return name;
}
+/** Helper for querying float-valued device cap */
+static float
+get_float_cap(struct svga_winsys_screen *sws, unsigned cap, float defaultVal)
+{
+ SVGA3dDevCapResult result;
+ if (sws->get_cap(sws, cap, &result))
+ return result.f;
+ else
+ return defaultVal;
+}
+
+
+/** Helper for querying uint-valued device cap */
+static unsigned
+get_uint_cap(struct svga_winsys_screen *sws, unsigned cap, unsigned defaultVal)
+{
+ SVGA3dDevCapResult result;
+ if (sws->get_cap(sws, cap, &result))
+ return result.u;
+ else
+ return defaultVal;
+}
+
+
+/** Helper for querying boolean-valued device cap */
+static boolean
+get_bool_cap(struct svga_winsys_screen *sws, unsigned cap, boolean defaultVal)
+{
+ SVGA3dDevCapResult result;
+ if (sws->get_cap(sws, cap, &result))
+ return result.b;
+ else
+ return defaultVal;
+}
static float
@@ -99,7 +139,6 @@ svga_get_paramf(struct pipe_screen *screen, enum pipe_capf param)
{
struct svga_screen *svgascreen = svga_screen(screen);
struct svga_winsys_screen *sws = svgascreen->sws;
- SVGA3dDevCapResult result;
switch (param) {
case PIPE_CAPF_MAX_LINE_WIDTH:
@@ -113,12 +152,11 @@ svga_get_paramf(struct pipe_screen *screen, enum pipe_capf param)
return svgascreen->maxPointSize;
case PIPE_CAPF_MAX_TEXTURE_ANISOTROPY:
- if(!sws->get_cap(sws, SVGA3D_DEVCAP_MAX_TEXTURE_ANISOTROPY, &result))
- return 4.0f;
- return (float) result.u;
+ return (float) get_uint_cap(sws, SVGA3D_DEVCAP_MAX_TEXTURE_ANISOTROPY, 4);
case PIPE_CAPF_MAX_TEXTURE_LOD_BIAS:
return 15.0;
+
case PIPE_CAPF_GUARD_BAND_LEFT:
case PIPE_CAPF_GUARD_BAND_TOP:
case PIPE_CAPF_GUARD_BAND_RIGHT:
@@ -145,7 +183,12 @@ svga_get_param(struct pipe_screen *screen, enum pipe_cap param)
case PIPE_CAP_TWO_SIDED_STENCIL:
return 1;
case PIPE_CAP_MAX_DUAL_SOURCE_RENDER_TARGETS:
- return 0;
+ /*
+ * "In virtually every OpenGL implementation and hardware,
+ * GL_MAX_DUAL_SOURCE_DRAW_BUFFERS is 1"
+ * http://www.opengl.org/wiki/Blending
+ */
+ return sws->have_vgpu10 ? 1 : 0;
case PIPE_CAP_ANISOTROPIC_FILTER:
return 1;
case PIPE_CAP_POINT_SPRITE:
@@ -158,6 +201,8 @@ svga_get_param(struct pipe_screen *screen, enum pipe_cap param)
return 1;
case PIPE_CAP_QUERY_TIME_ELAPSED:
return 0;
+ case PIPE_CAP_TEXTURE_BUFFER_OBJECTS:
+ return sws->have_vgpu10;
case PIPE_CAP_TEXTURE_SHADOW_MAP:
return 1;
case PIPE_CAP_TEXTURE_SWIZZLE:
@@ -170,7 +215,7 @@ svga_get_param(struct pipe_screen *screen, enum pipe_cap param)
case PIPE_CAP_USER_CONSTANT_BUFFERS:
return 1;
case PIPE_CAP_CONSTANT_BUFFER_OFFSET_ALIGNMENT:
- return 16;
+ return 256;
case PIPE_CAP_MAX_TEXTURE_2D_LEVELS:
{
@@ -199,17 +244,20 @@ svga_get_param(struct pipe_screen *screen, enum pipe_cap param)
return MIN2(screen->get_param(screen, PIPE_CAP_MAX_TEXTURE_2D_LEVELS),
12 /* 2048x2048 */);
+ case PIPE_CAP_MAX_TEXTURE_ARRAY_LAYERS:
+ return sws->have_vgpu10 ? SVGA3D_MAX_SURFACE_ARRAYSIZE : 0;
+
case PIPE_CAP_BLEND_EQUATION_SEPARATE: /* req. for GL 1.5 */
return 1;
case PIPE_CAP_TGSI_FS_COORD_ORIGIN_UPPER_LEFT:
return 1;
case PIPE_CAP_TGSI_FS_COORD_PIXEL_CENTER_HALF_INTEGER:
- return 0;
+ return sws->have_vgpu10;
case PIPE_CAP_TGSI_FS_COORD_ORIGIN_LOWER_LEFT:
return 0;
case PIPE_CAP_TGSI_FS_COORD_PIXEL_CENTER_INTEGER:
- return 1;
+ return !sws->have_vgpu10;
case PIPE_CAP_VERTEX_COLOR_UNCLAMPED:
return 1; /* The color outputs of vertex shaders are not clamped */
@@ -222,7 +270,7 @@ svga_get_param(struct pipe_screen *screen, enum pipe_cap param)
return 1; /* expected for GL_ARB_framebuffer_object */
case PIPE_CAP_GLSL_FEATURE_LEVEL:
- return 120;
+ return sws->have_vgpu10 ? 330 : 120;
case PIPE_CAP_PREFER_BLIT_BASED_TEXTURE_TRANSFER:
return 0;
@@ -230,49 +278,65 @@ svga_get_param(struct pipe_screen *screen, enum pipe_cap param)
case PIPE_CAP_SM3:
return 1;
- /* Unsupported features */
- case PIPE_CAP_QUADS_FOLLOW_PROVOKING_VERTEX_CONVENTION:
- case PIPE_CAP_TEXTURE_MIRROR_CLAMP:
- case PIPE_CAP_SHADER_STENCIL_EXPORT:
case PIPE_CAP_DEPTH_CLIP_DISABLE:
- case PIPE_CAP_SEAMLESS_CUBE_MAP:
- case PIPE_CAP_SEAMLESS_CUBE_MAP_PER_TEXTURE:
case PIPE_CAP_INDEP_BLEND_ENABLE:
- case PIPE_CAP_INDEP_BLEND_FUNC:
- case PIPE_CAP_MAX_STREAM_OUTPUT_BUFFERS:
- case PIPE_CAP_PRIMITIVE_RESTART:
+ case PIPE_CAP_CONDITIONAL_RENDER:
+ case PIPE_CAP_QUERY_TIMESTAMP:
case PIPE_CAP_TGSI_INSTANCEID:
case PIPE_CAP_VERTEX_ELEMENT_INSTANCE_DIVISOR:
- case PIPE_CAP_MAX_TEXTURE_ARRAY_LAYERS:
+ case PIPE_CAP_SEAMLESS_CUBE_MAP:
+ case PIPE_CAP_FAKE_SW_MSAA:
+ return sws->have_vgpu10;
+
+ case PIPE_CAP_MAX_STREAM_OUTPUT_BUFFERS:
+ return sws->have_vgpu10 ? SVGA3D_DX_MAX_SOTARGETS : 0;
+ case PIPE_CAP_MAX_STREAM_OUTPUT_SEPARATE_COMPONENTS:
+ return sws->have_vgpu10 ? 4 : 0;
+ case PIPE_CAP_MAX_STREAM_OUTPUT_INTERLEAVED_COMPONENTS:
+ return sws->have_vgpu10 ? SVGA3D_MAX_STREAMOUT_DECLS : 0;
+ case PIPE_CAP_STREAM_OUTPUT_PAUSE_RESUME:
+ return 0;
+ case PIPE_CAP_TEXTURE_MULTISAMPLE:
+ return svgascreen->ms_samples ? 1 : 0;
+
+ case PIPE_CAP_MAX_TEXTURE_BUFFER_SIZE:
+ return SVGA3D_DX_MAX_RESOURCE_SIZE;
+
case PIPE_CAP_MIN_TEXEL_OFFSET:
+ return sws->have_vgpu10 ? VGPU10_MIN_TEXEL_FETCH_OFFSET : 0;
case PIPE_CAP_MAX_TEXEL_OFFSET:
+ return sws->have_vgpu10 ? VGPU10_MAX_TEXEL_FETCH_OFFSET : 0;
+
case PIPE_CAP_MIN_TEXTURE_GATHER_OFFSET:
case PIPE_CAP_MAX_TEXTURE_GATHER_OFFSET:
- case PIPE_CAP_CONDITIONAL_RENDER:
- case PIPE_CAP_TEXTURE_BARRIER:
- case PIPE_CAP_MAX_STREAM_OUTPUT_SEPARATE_COMPONENTS:
- case PIPE_CAP_MAX_STREAM_OUTPUT_INTERLEAVED_COMPONENTS:
- case PIPE_CAP_STREAM_OUTPUT_PAUSE_RESUME:
+ return 0;
+
case PIPE_CAP_MAX_GEOMETRY_OUTPUT_VERTICES:
+ return sws->have_vgpu10 ? 256 : 0;
case PIPE_CAP_MAX_GEOMETRY_TOTAL_OUTPUT_COMPONENTS:
+ return sws->have_vgpu10 ? 1024 : 0;
+
+ case PIPE_CAP_PRIMITIVE_RESTART:
+ return 1; /* may be a sw fallback, depending on restart index */
+
+ /* Unsupported features */
+ case PIPE_CAP_QUADS_FOLLOW_PROVOKING_VERTEX_CONVENTION:
+ case PIPE_CAP_TEXTURE_MIRROR_CLAMP:
+ case PIPE_CAP_SHADER_STENCIL_EXPORT:
+ case PIPE_CAP_SEAMLESS_CUBE_MAP_PER_TEXTURE:
+ case PIPE_CAP_INDEP_BLEND_FUNC:
+ case PIPE_CAP_TEXTURE_BARRIER:
case PIPE_CAP_MAX_VERTEX_STREAMS:
case PIPE_CAP_TGSI_CAN_COMPACT_CONSTANTS:
- case PIPE_CAP_VERTEX_BUFFER_OFFSET_4BYTE_ALIGNED_ONLY:
- case PIPE_CAP_VERTEX_BUFFER_STRIDE_4BYTE_ALIGNED_ONLY:
case PIPE_CAP_COMPUTE:
case PIPE_CAP_START_INSTANCE:
- case PIPE_CAP_QUERY_TIMESTAMP:
- case PIPE_CAP_TEXTURE_MULTISAMPLE:
case PIPE_CAP_CUBE_MAP_ARRAY:
- case PIPE_CAP_TEXTURE_BUFFER_OBJECTS:
case PIPE_CAP_TEXTURE_BUFFER_OFFSET_ALIGNMENT:
case PIPE_CAP_QUERY_PIPELINE_STATISTICS:
- case PIPE_CAP_MAX_TEXTURE_BUFFER_SIZE:
case PIPE_CAP_TGSI_VS_LAYER_VIEWPORT:
case PIPE_CAP_MAX_TEXTURE_GATHER_COMPONENTS:
case PIPE_CAP_TEXTURE_GATHER_SM5:
case PIPE_CAP_BUFFER_MAP_PERSISTENT_COHERENT:
- case PIPE_CAP_FAKE_SW_MSAA:
case PIPE_CAP_TEXTURE_QUERY_LOD:
case PIPE_CAP_SAMPLE_SHADING:
case PIPE_CAP_TEXTURE_GATHER_OFFSETS:
@@ -288,8 +352,10 @@ svga_get_param(struct pipe_screen *screen, enum pipe_cap param)
return 0;
case PIPE_CAP_MIN_MAP_BUFFER_ALIGNMENT:
return 64;
+ case PIPE_CAP_VERTEX_BUFFER_STRIDE_4BYTE_ALIGNED_ONLY:
+ case PIPE_CAP_VERTEX_BUFFER_OFFSET_4BYTE_ALIGNED_ONLY:
case PIPE_CAP_VERTEX_ELEMENT_SRC_OFFSET_4BYTE_ALIGNED_ONLY:
- return 1;
+ return 1; /* need 4-byte alignment for all offsets and strides */
case PIPE_CAP_MAX_VERTEX_ATTRIB_STRIDE:
return 2048;
case PIPE_CAP_MAX_VIEWPORTS:
@@ -320,11 +386,16 @@ svga_get_param(struct pipe_screen *screen, enum pipe_cap param)
return 0;
}
-static int svga_get_shader_param(struct pipe_screen *screen, unsigned shader, enum pipe_shader_cap param)
+
+static int
+vgpu9_get_shader_param(struct pipe_screen *screen, unsigned shader,
+ enum pipe_shader_cap param)
{
struct svga_screen *svgascreen = svga_screen(screen);
struct svga_winsys_screen *sws = svgascreen->sws;
- SVGA3dDevCapResult result;
+ unsigned val;
+
+ assert(!sws->have_vgpu10);
switch (shader)
{
@@ -347,9 +418,8 @@ static int svga_get_shader_param(struct pipe_screen *screen, unsigned shader, en
case PIPE_SHADER_CAP_MAX_CONST_BUFFERS:
return 1;
case PIPE_SHADER_CAP_MAX_TEMPS:
- if (!sws->get_cap(sws, SVGA3D_DEVCAP_MAX_FRAGMENT_SHADER_TEMPS, &result))
- return 32;
- return MIN2(result.u, SVGA3D_TEMPREG_MAX);
+ val = get_uint_cap(sws, SVGA3D_DEVCAP_MAX_FRAGMENT_SHADER_TEMPS, 32);
+ return MIN2(val, SVGA3D_TEMPREG_MAX);
case PIPE_SHADER_CAP_INDIRECT_INPUT_ADDR:
/*
* Although PS 3.0 has some addressing abilities it can only represent
@@ -392,9 +462,8 @@ static int svga_get_shader_param(struct pipe_screen *screen, unsigned shader, en
{
case PIPE_SHADER_CAP_MAX_INSTRUCTIONS:
case PIPE_SHADER_CAP_MAX_ALU_INSTRUCTIONS:
- if (!sws->get_cap(sws, SVGA3D_DEVCAP_MAX_VERTEX_SHADER_INSTRUCTIONS, &result))
- return 512;
- return result.u;
+ return get_uint_cap(sws, SVGA3D_DEVCAP_MAX_VERTEX_SHADER_INSTRUCTIONS,
+ 512);
case PIPE_SHADER_CAP_MAX_TEX_INSTRUCTIONS:
case PIPE_SHADER_CAP_MAX_TEX_INDIRECTIONS:
/* XXX: until we have vertex texture support */
@@ -410,9 +479,8 @@ static int svga_get_shader_param(struct pipe_screen *screen, unsigned shader, en
case PIPE_SHADER_CAP_MAX_CONST_BUFFERS:
return 1;
case PIPE_SHADER_CAP_MAX_TEMPS:
- if (!sws->get_cap(sws, SVGA3D_DEVCAP_MAX_VERTEX_SHADER_TEMPS, &result))
- return 32;
- return MIN2(result.u, SVGA3D_TEMPREG_MAX);
+ val = get_uint_cap(sws, SVGA3D_DEVCAP_MAX_VERTEX_SHADER_TEMPS, 32);
+ return MIN2(val, SVGA3D_TEMPREG_MAX);
case PIPE_SHADER_CAP_MAX_PREDS:
return 1;
case PIPE_SHADER_CAP_TGSI_CONT_SUPPORTED:
@@ -459,8 +527,102 @@ static int svga_get_shader_param(struct pipe_screen *screen, unsigned shader, en
}
+static int
+vgpu10_get_shader_param(struct pipe_screen *screen, unsigned shader,
+ enum pipe_shader_cap param)
+{
+ struct svga_screen *svgascreen = svga_screen(screen);
+ struct svga_winsys_screen *sws = svgascreen->sws;
+
+ assert(sws->have_vgpu10);
+ (void) sws; /* silence unused var warnings in non-debug builds */
+
+ /* Only VS, GS, FS supported */
+ if (shader != PIPE_SHADER_VERTEX &&
+ shader != PIPE_SHADER_GEOMETRY &&
+ shader != PIPE_SHADER_FRAGMENT) {
+ return 0;
+ }
+
+ /* NOTE: we do not query the device for any caps/limits at this time */
+
+ /* Generally the same limits for vertex, geometry and fragment shaders */
+ switch (param) {
+ case PIPE_SHADER_CAP_MAX_INSTRUCTIONS:
+ case PIPE_SHADER_CAP_MAX_ALU_INSTRUCTIONS:
+ case PIPE_SHADER_CAP_MAX_TEX_INSTRUCTIONS:
+ case PIPE_SHADER_CAP_MAX_TEX_INDIRECTIONS:
+ return 64 * 1024;
+ case PIPE_SHADER_CAP_MAX_CONTROL_FLOW_DEPTH:
+ return 64;
+ case PIPE_SHADER_CAP_MAX_INPUTS:
+ if (shader == PIPE_SHADER_FRAGMENT)
+ return VGPU10_MAX_FS_INPUTS;
+ else if (shader == PIPE_SHADER_GEOMETRY)
+ return VGPU10_MAX_GS_INPUTS;
+ else
+ return VGPU10_MAX_VS_INPUTS;
+ case PIPE_SHADER_CAP_MAX_OUTPUTS:
+ if (shader == PIPE_SHADER_FRAGMENT)
+ return VGPU10_MAX_FS_OUTPUTS;
+ else if (shader == PIPE_SHADER_GEOMETRY)
+ return VGPU10_MAX_GS_OUTPUTS;
+ else
+ return VGPU10_MAX_VS_OUTPUTS;
+ case PIPE_SHADER_CAP_MAX_CONST_BUFFER_SIZE:
+ return VGPU10_MAX_CONSTANT_BUFFER_ELEMENT_COUNT * sizeof(float[4]);
+ case PIPE_SHADER_CAP_MAX_CONST_BUFFERS:
+ return svgascreen->max_const_buffers;
+ case PIPE_SHADER_CAP_MAX_TEMPS:
+ return VGPU10_MAX_TEMPS;
+ case PIPE_SHADER_CAP_INDIRECT_INPUT_ADDR:
+ case PIPE_SHADER_CAP_INDIRECT_OUTPUT_ADDR:
+ case PIPE_SHADER_CAP_INDIRECT_TEMP_ADDR:
+ case PIPE_SHADER_CAP_INDIRECT_CONST_ADDR:
+ return TRUE; /* XXX verify */
+ case PIPE_SHADER_CAP_MAX_PREDS:
+ return 0;
+ case PIPE_SHADER_CAP_TGSI_CONT_SUPPORTED:
+ case PIPE_SHADER_CAP_TGSI_SQRT_SUPPORTED:
+ case PIPE_SHADER_CAP_SUBROUTINES:
+ case PIPE_SHADER_CAP_INTEGERS:
+ return TRUE;
+ case PIPE_SHADER_CAP_MAX_TEXTURE_SAMPLERS:
+ case PIPE_SHADER_CAP_MAX_SAMPLER_VIEWS:
+ return SVGA3D_DX_MAX_SAMPLERS;
+ case PIPE_SHADER_CAP_PREFERRED_IR:
+ return PIPE_SHADER_IR_TGSI;
+ case PIPE_SHADER_CAP_DOUBLES:
+ case PIPE_SHADER_CAP_TGSI_DROUND_SUPPORTED:
+ case PIPE_SHADER_CAP_TGSI_DFRACEXP_DLDEXP_SUPPORTED:
+ case PIPE_SHADER_CAP_TGSI_FMA_SUPPORTED:
+ case PIPE_SHADER_CAP_TGSI_ANY_INOUT_DECL_RANGE:
+ return 0;
+ default:
+ debug_printf("Unexpected vgpu10 shader query %u\n", param);
+ return 0;
+ }
+ return 0;
+}
+
+
+static int
+svga_get_shader_param(struct pipe_screen *screen, unsigned shader,
+ enum pipe_shader_cap param)
+{
+ struct svga_screen *svgascreen = svga_screen(screen);
+ struct svga_winsys_screen *sws = svgascreen->sws;
+ if (sws->have_vgpu10) {
+ return vgpu10_get_shader_param(screen, shader, param);
+ }
+ else {
+ return vgpu9_get_shader_param(screen, shader, param);
+ }
+}
+
+
/**
- * Implemnt pipe_screen::is_format_supported().
+ * Implement pipe_screen::is_format_supported().
* \param bindings bitmask of PIPE_BIND_x flags
*/
static boolean
@@ -478,7 +640,12 @@ svga_is_format_supported( struct pipe_screen *screen,
assert(bindings);
if (sample_count > 1) {
- return FALSE;
+ /* In ms_samples, if bit N is set it means that we support
+ * multisample with N+1 samples per pixel.
+ */
+ if ((ss->ms_samples & (1 << (sample_count - 1))) == 0) {
+ return FALSE;
+ }
}
svga_format = svga_translate_format(ss, format, bindings);
@@ -486,6 +653,22 @@ svga_is_format_supported( struct pipe_screen *screen,
return FALSE;
}
+ /* we don't support sRGB rendering into display targets */
+ if (util_format_is_srgb(format) && (bindings & PIPE_BIND_DISPLAY_TARGET)) {
+ return FALSE;
+ }
+
+ /*
+ * For VGPU10 vertex formats, skip querying host capabilities
+ */
+
+ if (ss->sws->have_vgpu10 && (bindings & PIPE_BIND_VERTEX_BUFFER)) {
+ SVGA3dSurfaceFormat svga_format;
+ unsigned flags;
+ svga_translate_vertex_format_vgpu10(format, &svga_format, &flags);
+ return svga_format != SVGA3D_FORMAT_INVALID;
+ }
+
/*
* Override host capabilities, so that we end up with the same
* visuals for all virtual hardware implementations.
@@ -498,6 +681,12 @@ svga_is_format_supported( struct pipe_screen *screen,
case SVGA3D_R5G6B5:
break;
+ /* VGPU10 formats */
+ case SVGA3D_B8G8R8A8_UNORM:
+ case SVGA3D_B8G8R8X8_UNORM:
+ case SVGA3D_B5G6R5_UNORM:
+ break;
+
/* Often unsupported/problematic. This means we end up with the same
* visuals for all virtual hardware implementations.
*/
@@ -516,22 +705,32 @@ svga_is_format_supported( struct pipe_screen *screen,
svga_get_format_cap(ss, svga_format, &caps);
+ if (bindings & PIPE_BIND_RENDER_TARGET) {
+ /* Check that the color surface is blendable, unless it's an
+ * integer format.
+ */
+ if (!svga_format_is_integer(svga_format) &&
+ (caps.value & SVGA3DFORMAT_OP_NOALPHABLEND)) {
+ return FALSE;
+ }
+ }
+
mask.value = 0;
if (bindings & PIPE_BIND_RENDER_TARGET) {
- mask.offscreenRenderTarget = 1;
+ mask.value |= SVGA3DFORMAT_OP_OFFSCREEN_RENDERTARGET;
}
if (bindings & PIPE_BIND_DEPTH_STENCIL) {
- mask.zStencil = 1;
+ mask.value |= SVGA3DFORMAT_OP_ZSTENCIL;
}
if (bindings & PIPE_BIND_SAMPLER_VIEW) {
- mask.texture = 1;
+ mask.value |= SVGA3DFORMAT_OP_TEXTURE;
}
if (target == PIPE_TEXTURE_CUBE) {
- mask.cubeTexture = 1;
+ mask.value |= SVGA3DFORMAT_OP_CUBETEXTURE;
}
- if (target == PIPE_TEXTURE_3D) {
- mask.volumeTexture = 1;
+ else if (target == PIPE_TEXTURE_3D) {
+ mask.value |= SVGA3DFORMAT_OP_VOLUMETEXTURE;
}
return (caps.value & mask.value) == mask.value;
@@ -611,8 +810,6 @@ svga_screen_create(struct svga_winsys_screen *sws)
{
struct svga_screen *svgascreen;
struct pipe_screen *screen;
- SVGA3dDevCapResult result;
- boolean use_vs30, use_ps30;
#ifdef DEBUG
SVGA_DEBUG = debug_get_flags_option("SVGA_DEBUG", svga_debug_flags, 0 );
@@ -642,6 +839,7 @@ svga_screen_create(struct svga_winsys_screen *sws)
screen->get_param = svga_get_param;
screen->get_shader_param = svga_get_shader_param;
screen->get_paramf = svga_get_paramf;
+ screen->get_timestamp = NULL;
screen->is_format_supported = svga_is_format_supported;
screen->context_create = svga_context_create;
screen->fence_reference = svga_fence_reference;
@@ -657,18 +855,6 @@ svga_screen_create(struct svga_winsys_screen *sws)
svgascreen->hw_version = SVGA3D_HWVERSION_WS65_B1;
}
- use_ps30 =
- sws->get_cap(sws, SVGA3D_DEVCAP_FRAGMENT_SHADER_VERSION, &result) &&
- result.u >= SVGA3DPSVERSION_30 ? TRUE : FALSE;
-
- use_vs30 =
- sws->get_cap(sws, SVGA3D_DEVCAP_VERTEX_SHADER_VERSION, &result) &&
- result.u >= SVGA3DVSVERSION_30 ? TRUE : FALSE;
-
- /* we require Shader model 3.0 or later */
- if (!use_ps30 || !use_vs30)
- goto error2;
-
/*
* The D16, D24X8, and D24S8 formats always do an implicit shadow compare
* when sampled from, where as the DF16, DF24, and D24S8_INT do not. So
@@ -716,46 +902,77 @@ svga_screen_create(struct svga_winsys_screen *sws)
/* Query device caps
*/
- if (!sws->get_cap(sws, SVGA3D_DEVCAP_LINE_STIPPLE, &result))
- svgascreen->haveLineStipple = FALSE;
- else
- svgascreen->haveLineStipple = result.u;
+ if (sws->have_vgpu10) {
+ svgascreen->haveProvokingVertex
+ = get_bool_cap(sws, SVGA3D_DEVCAP_DX_PROVOKING_VERTEX, FALSE);
+ svgascreen->haveLineSmooth = TRUE;
+ svgascreen->maxPointSize = 80.0F;
+ svgascreen->max_color_buffers = SVGA3D_DX_MAX_RENDER_TARGETS;
+
+ /* Multisample samples per pixel */
+ svgascreen->ms_samples =
+ get_uint_cap(sws, SVGA3D_DEVCAP_MULTISAMPLE_MASKABLESAMPLES, 0);
+
+ /* Maximum number of constant buffers */
+ svgascreen->max_const_buffers =
+ get_uint_cap(sws, SVGA3D_DEVCAP_DX_MAX_CONSTANT_BUFFERS, 1);
+ assert(svgascreen->max_const_buffers <= SVGA_MAX_CONST_BUFS);
+ }
+ else {
+ /* VGPU9 */
+ unsigned vs_ver = get_uint_cap(sws, SVGA3D_DEVCAP_VERTEX_SHADER_VERSION,
+ SVGA3DVSVERSION_NONE);
+ unsigned fs_ver = get_uint_cap(sws, SVGA3D_DEVCAP_FRAGMENT_SHADER_VERSION,
+ SVGA3DPSVERSION_NONE);
+
+ /* we require Shader model 3.0 or later */
+ if (fs_ver < SVGA3DPSVERSION_30 || vs_ver < SVGA3DVSVERSION_30) {
+ goto error2;
+ }
- if (!sws->get_cap(sws, SVGA3D_DEVCAP_LINE_AA, &result))
- svgascreen->haveLineSmooth = FALSE;
- else
- svgascreen->haveLineSmooth = result.u;
+ svgascreen->haveProvokingVertex = FALSE;
- if (!sws->get_cap(sws, SVGA3D_DEVCAP_MAX_LINE_WIDTH, &result))
- svgascreen->maxLineWidth = 1.0F;
- else
- svgascreen->maxLineWidth = result.f;
+ svgascreen->haveLineSmooth =
+ get_bool_cap(sws, SVGA3D_DEVCAP_LINE_AA, FALSE);
- if (!sws->get_cap(sws, SVGA3D_DEVCAP_MAX_AA_LINE_WIDTH, &result))
- svgascreen->maxLineWidthAA = 1.0F;
- else
- svgascreen->maxLineWidthAA = result.f;
+ svgascreen->maxPointSize =
+ get_float_cap(sws, SVGA3D_DEVCAP_MAX_POINT_SIZE, 1.0f);
+ /* Keep this to a reasonable size to avoid failures in conform/pntaa.c */
+ svgascreen->maxPointSize = MIN2(svgascreen->maxPointSize, 80.0f);
+
+ /* The SVGA3D device always supports 4 targets at this time, regardless
+ * of what querying SVGA3D_DEVCAP_MAX_RENDER_TARGETS might return.
+ */
+ svgascreen->max_color_buffers = 4;
+
+ /* Only support one constant buffer
+ */
+ svgascreen->max_const_buffers = 1;
- if (0)
+ /* No multisampling */
+ svgascreen->ms_samples = 0;
+ }
+
+ /* common VGPU9 / VGPU10 caps */
+ svgascreen->haveLineStipple =
+ get_bool_cap(sws, SVGA3D_DEVCAP_LINE_STIPPLE, FALSE);
+
+ svgascreen->maxLineWidth =
+ get_float_cap(sws, SVGA3D_DEVCAP_MAX_LINE_WIDTH, 1.0f);
+
+ svgascreen->maxLineWidthAA =
+ get_float_cap(sws, SVGA3D_DEVCAP_MAX_AA_LINE_WIDTH, 1.0f);
+
+ if (0) {
+ debug_printf("svga: haveProvokingVertex %u\n",
+ svgascreen->haveProvokingVertex);
debug_printf("svga: haveLineStip %u "
"haveLineSmooth %u maxLineWidth %f\n",
svgascreen->haveLineStipple, svgascreen->haveLineSmooth,
svgascreen->maxLineWidth);
-
- if (!sws->get_cap(sws, SVGA3D_DEVCAP_MAX_POINT_SIZE, &result)) {
- svgascreen->maxPointSize = 1.0F;
- } else {
- /* Keep this to a reasonable size to avoid failures in
- * conform/pntaa.c:
- */
- svgascreen->maxPointSize = MIN2(result.f, 80.0f);
+ debug_printf("svga: maxPointSize %g\n", svgascreen->maxPointSize);
}
- /* The SVGA3D device always supports 4 targets at this time, regardless
- * of what querying SVGA3D_DEVCAP_MAX_RENDER_TARGETS might return.
- */
- svgascreen->max_color_buffers = 4;
-
pipe_mutex_init(svgascreen->tex_mutex);
pipe_mutex_init(svgascreen->swc_mutex);