#include "pipe/p_state.h"
+#include "tgsi/tgsi_exec.h"
struct pipe_context;
struct draw_context;
const struct pipe_rasterizer_state *rasterizer,
unsigned prim );
+static INLINE int
+draw_get_shader_param(unsigned shader, enum pipe_cap param)
+{
+ switch(shader) {
+ case PIPE_SHADER_VERTEX:
+ case PIPE_SHADER_GEOMETRY:
+ return tgsi_exec_get_shader_param(param);
+ default:
+ return 0;
+ }
+}
+
#endif /* DRAW_CONTEXT_H */
const unsigned *buf_sizes);
+static INLINE int
+tgsi_exec_get_shader_param(enum pipe_shader_cap param)
+{
+ 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 INT_MAX;
+ case PIPE_SHADER_CAP_MAX_CONTROL_FLOW_DEPTH:
+ return TGSI_EXEC_MAX_NESTING;
+ case PIPE_SHADER_CAP_MAX_INPUTS:
+ return TGSI_EXEC_MAX_INPUT_ATTRIBS;
+ case PIPE_SHADER_CAP_MAX_CONSTS:
+ return TGSI_EXEC_MAX_CONST_BUFFER;
+ case PIPE_SHADER_CAP_MAX_CONST_BUFFERS:
+ return PIPE_MAX_CONSTANT_BUFFERS;
+ case PIPE_SHADER_CAP_MAX_TEMPS:
+ return TGSI_EXEC_NUM_TEMPS;
+ case PIPE_SHADER_CAP_MAX_ADDRS:
+ return TGSI_EXEC_NUM_ADDRS;
+ case PIPE_SHADER_CAP_MAX_PREDS:
+ return TGSI_EXEC_NUM_PREDS;
+ case PIPE_SHADER_CAP_TGSI_CONT_SUPPORTED:
+ return 1;
+ default:
+ return 0;
+ }
+}
+
#if defined __cplusplus
} /* extern "C" */
#endif
return FALSE;
}
break;
+ case UTIL_CAPS_CHECK_SHADER:
+ tmpi = screen->get_shader_param(screen, list[i] >> 24, list[i] & ((1 << 24) - 1));
+ ++i;
+ if (tmpi < (int)list[i++]) {
+ *out = i - 3;
+ return FALSE;
+ }
case UTIL_CAPS_CHECK_UNIMPLEMENTED:
*out = i - 1;
return FALSE;
/* Shader Model 3 */
static unsigned caps_sm3[] = {
- UTIL_CHECK_INT(MAX_FS_INSTRUCTIONS, 512),
- UTIL_CHECK_INT(MAX_FS_INPUTS, 10),
- UTIL_CHECK_INT(MAX_FS_TEMPS, 32),
- UTIL_CHECK_INT(MAX_FS_ADDRS, 1),
- UTIL_CHECK_INT(MAX_FS_CONSTS, 224),
+ UTIL_CHECK_SHADER(FRAGMENT, MAX_INSTRUCTIONS, 512),
+ UTIL_CHECK_SHADER(FRAGMENT, MAX_INPUTS, 10),
+ UTIL_CHECK_SHADER(FRAGMENT, MAX_TEMPS, 32),
+ UTIL_CHECK_SHADER(FRAGMENT, MAX_ADDRS, 1),
+ UTIL_CHECK_SHADER(FRAGMENT, MAX_CONSTS, 224),
- UTIL_CHECK_INT(MAX_VS_INSTRUCTIONS, 512),
- UTIL_CHECK_INT(MAX_VS_INPUTS, 16),
- UTIL_CHECK_INT(MAX_VS_TEMPS, 32),
- UTIL_CHECK_INT(MAX_VS_ADDRS, 2),
- UTIL_CHECK_INT(MAX_VS_CONSTS, 256),
+ UTIL_CHECK_SHADER(VERTEX, MAX_INSTRUCTIONS, 512),
+ UTIL_CHECK_SHADER(VERTEX, MAX_INPUTS, 16),
+ UTIL_CHECK_SHADER(VERTEX, MAX_TEMPS, 32),
+ UTIL_CHECK_SHADER(VERTEX, MAX_ADDRS, 2),
+ UTIL_CHECK_SHADER(VERTEX, MAX_CONSTS, 256),
UTIL_CHECK_TERMINATE
};
UTIL_CAPS_CHECK_INT,
UTIL_CAPS_CHECK_FLOAT,
UTIL_CAPS_CHECK_FORMAT,
+ UTIL_CAPS_CHECK_SHADER,
UTIL_CAPS_CHECK_UNIMPLEMENTED,
};
#define UTIL_CHECK_FORMAT(format) \
UTIL_CAPS_CHECK_FORMAT, PIPE_FORMAT_##format
+#define UTIL_CHECK_SHADER(shader, cap, higher) \
+ UTIL_CAPS_CHECK_SHADER, (PIPE_SHADER_##shader << 24) | PIPE_SHADER_CAP_##cap, (unsigned)(higher)
+
#define UTIL_CHECK_UNIMPLEMENTED \
UTIL_CAPS_CHECK_UNIMPLEMENTED
}
}
-
#ifdef __cplusplus
}
#endif
return 1; /* XXX not really true */
case PIPE_CAP_TEXTURE_MIRROR_CLAMP:
return 0; /* XXX to do */
- case PIPE_CAP_TGSI_CONT_SUPPORTED:
- return 1;
case PIPE_CAP_TGSI_FS_COORD_ORIGIN_UPPER_LEFT:
case PIPE_CAP_TGSI_FS_COORD_PIXEL_CENTER_HALF_INTEGER:
return 1;
}
}
+static int
+cell_get_shader_param(struct pipe_screen *screen, unsigned shader, enum pipe_shader_cap param)
+{
+ switch(shader)
+ {
+ case PIPE_SHADER_FRAGMENT:
+ return tgsi_exec_get_shader_param(param);
+ case PIPE_SHADER_VERTEX:
+ case PIPE_SHADER_GEOMETRY:
+ return draw_get_shader_param(shader, param);
+ default:
+ return 0;
+ }
+}
static float
cell_get_paramf(struct pipe_screen *screen, enum pipe_cap param)
screen->base.get_name = cell_get_name;
screen->base.get_vendor = cell_get_vendor;
screen->base.get_param = cell_get_param;
+ screen->base.get_shader_param = cell_get_shader_param;
screen->base.get_paramf = cell_get_paramf;
screen->base.is_format_supported = cell_is_format_supported;
screen->base.context_create = cell_create_context;
failover->pipe.get_name = hw->get_name;
failover->pipe.get_vendor = hw->get_vendor;
failover->pipe.get_param = hw->get_param;
+ failover->pipe.get_shader_param = hw->get_shader_param;
failover->pipe.get_paramf = hw->get_paramf;
#endif
if (index &&
index >=
- pipe->screen->get_param(pipe->screen, PIPE_CAP_MAX_CONST_BUFFERS)) {
+ pipe->screen->get_shader_param(pipe->screen, shader, PIPE_SHADER_CAP_MAX_CONST_BUFFERS)) {
glhd_error("Access to constant buffer %u requested, "
"but only %d are supported",
index,
- pipe->screen->get_param(pipe->screen, PIPE_CAP_MAX_CONST_BUFFERS));
+ pipe->screen->get_shader_param(pipe->screen, shader, PIPE_SHADER_CAP_MAX_CONST_BUFFERS));
}
/* XXX hmm? unwrap the input state */
param);
}
+static int
+galahad_screen_get_shader_param(struct pipe_screen *_screen,
+ unsigned shader, enum pipe_shader_cap param)
+{
+ struct galahad_screen *glhd_screen = galahad_screen(_screen);
+ struct pipe_screen *screen = glhd_screen->screen;
+
+ return screen->get_shader_param(screen, shader,
+ param);
+}
+
static float
galahad_screen_get_paramf(struct pipe_screen *_screen,
enum pipe_cap param)
glhd_screen->base.get_name = galahad_screen_get_name;
glhd_screen->base.get_vendor = galahad_screen_get_vendor;
glhd_screen->base.get_param = galahad_screen_get_param;
+ glhd_screen->base.get_shader_param = galahad_screen_get_shader_param;
glhd_screen->base.get_paramf = galahad_screen_get_paramf;
glhd_screen->base.is_format_supported = galahad_screen_is_format_supported;
glhd_screen->base.context_create = galahad_screen_context_create;
}
}
+static int
+i915_get_shader_param(struct pipe_screen *screen, unsigned shader, enum pipe_shader_cap param)
+{
+ switch(shader) {
+ case PIPE_SHADER_VERTEX:
+ return draw_get_shader_param(shader, param);
+ case PIPE_SHADER_FRAGMENT:
+ break;
+ default:
+ return 0;
+ }
+
+ /* XXX: these are just shader model 2.0 values, fix this! */
+ switch(param) {
+ case PIPE_SHADER_CAP_MAX_INSTRUCTIONS:
+ return 96;
+ case PIPE_SHADER_CAP_MAX_ALU_INSTRUCTIONS:
+ return 64;
+ case PIPE_SHADER_CAP_MAX_TEX_INSTRUCTIONS:
+ return 32;
+ case PIPE_SHADER_CAP_MAX_TEX_INDIRECTIONS:
+ return 8;
+ case PIPE_SHADER_CAP_MAX_CONTROL_FLOW_DEPTH:
+ return 0;
+ case PIPE_SHADER_CAP_MAX_INPUTS:
+ return 10;
+ case PIPE_SHADER_CAP_MAX_CONSTS:
+ return 32;
+ case PIPE_SHADER_CAP_MAX_CONST_BUFFERS:
+ return 1;
+ case PIPE_SHADER_CAP_MAX_TEMPS:
+ return 12; /* XXX: 12 -> 32 ? */
+ case PIPE_SHADER_CAP_MAX_ADDRS:
+ return 0;
+ case PIPE_SHADER_CAP_MAX_PREDS:
+ return 0;
+ case PIPE_SHADER_CAP_TGSI_CONT_SUPPORTED:
+ return 0;
+ default:
+ break;
+ }
+}
+
static float
i915_get_paramf(struct pipe_screen *screen, enum pipe_cap param)
{
is->base.get_name = i915_get_name;
is->base.get_vendor = i915_get_vendor;
is->base.get_param = i915_get_param;
+ is->base.get_shader_param = i915_get_shader_param;
is->base.get_paramf = i915_get_paramf;
is->base.is_format_supported = i915_is_format_supported;
}
}
+static int
+brw_get_shader_param(struct pipe_screen *screen, unsigned shader, enum pipe_shader_cap param)
+{
+ switch(shader) {
+ case PIPE_SHADER_VERTEX:
+ case PIPE_SHADER_FRAGMENT:
+ case PIPE_SHADER_GEOMETRY:
+ break;
+ default:
+ return 0;
+ }
+
+ /* XXX: these are just shader model 4.0 values, fix this! */
+ switch(param) {
+ case PIPE_SHADER_CAP_MAX_INSTRUCTIONS:
+ return 65536;
+ case PIPE_SHADER_CAP_MAX_ALU_INSTRUCTIONS:
+ return 65536;
+ case PIPE_SHADER_CAP_MAX_TEX_INSTRUCTIONS:
+ return 65536;
+ case PIPE_SHADER_CAP_MAX_TEX_INDIRECTIONS:
+ return 65536;
+ case PIPE_SHADER_CAP_MAX_CONTROL_FLOW_DEPTH:
+ return 65536;
+ case PIPE_SHADER_CAP_MAX_INPUTS:
+ return 32;
+ case PIPE_SHADER_CAP_MAX_CONSTS:
+ return 4096;
+ case PIPE_SHADER_CAP_MAX_CONST_BUFFERS:
+ return PIPE_MAX_CONSTANT_BUFFERS;
+ case PIPE_SHADER_CAP_MAX_TEMPS:
+ return 4096;
+ case PIPE_SHADER_CAP_MAX_ADDRS:
+ return 0;
+ case PIPE_SHADER_CAP_MAX_PREDS:
+ return 0;
+ case PIPE_SHADER_CAP_TGSI_CONT_SUPPORTED:
+ return 1;
+ default:
+ break;
+ }
+}
+
static float
brw_get_paramf(struct pipe_screen *screen, enum pipe_cap param)
{
bscreen->base.get_name = brw_get_name;
bscreen->base.get_vendor = brw_get_vendor;
bscreen->base.get_param = brw_get_param;
+ bscreen->base.get_shader_param = brw_get_shader_param;
bscreen->base.get_paramf = brw_get_paramf;
bscreen->base.is_format_supported = brw_is_format_supported;
bscreen->base.context_create = brw_create_context;
static int
identity_screen_get_param(struct pipe_screen *_screen,
- enum pipe_cap param)
+ unsigned shader, enum pipe_cap param)
{
struct identity_screen *id_screen = identity_screen(_screen);
struct pipe_screen *screen = id_screen->screen;
param);
}
+static int
+identity_screen_get_shader_param(struct pipe_screen *_screen,
+ unsigned shader, enum pipe_shader_cap param)
+{
+ struct identity_screen *id_screen = identity_screen(_screen);
+ struct pipe_screen *screen = id_screen->screen;
+
+ return screen->get_shader_param(screen, shader,
+ param);
+}
+
static float
identity_screen_get_paramf(struct pipe_screen *_screen,
enum pipe_cap param)
id_screen->base.get_name = identity_screen_get_name;
id_screen->base.get_vendor = identity_screen_get_vendor;
id_screen->base.get_param = identity_screen_get_param;
+ id_screen->base.get_shader_param = identity_screen_get_shader_param;
id_screen->base.get_paramf = identity_screen_get_paramf;
id_screen->base.is_format_supported = identity_screen_is_format_supported;
id_screen->base.context_create = identity_screen_context_create;
#include "util/u_format_s3tc.h"
#include "pipe/p_defines.h"
#include "pipe/p_screen.h"
+#include "draw/draw_context.h"
#include "gallivm/lp_bld_limits.h"
#include "lp_texture.h"
return LP_MAX_TEXTURE_3D_LEVELS;
case PIPE_CAP_MAX_TEXTURE_CUBE_LEVELS:
return LP_MAX_TEXTURE_2D_LEVELS;
- case PIPE_CAP_TGSI_CONT_SUPPORTED:
- return 1;
case PIPE_CAP_BLEND_EQUATION_SEPARATE:
return 1;
case PIPE_CAP_INDEP_BLEND_ENABLE:
case PIPE_CAP_TGSI_FS_COORD_ORIGIN_LOWER_LEFT:
case PIPE_CAP_TGSI_FS_COORD_PIXEL_CENTER_HALF_INTEGER:
return 0;
- case PIPE_CAP_MAX_VS_INSTRUCTIONS:
- case PIPE_CAP_MAX_FS_INSTRUCTIONS:
- case PIPE_CAP_MAX_VS_ALU_INSTRUCTIONS:
- case PIPE_CAP_MAX_FS_ALU_INSTRUCTIONS:
- case PIPE_CAP_MAX_VS_TEX_INSTRUCTIONS:
- case PIPE_CAP_MAX_FS_TEX_INSTRUCTIONS:
- case PIPE_CAP_MAX_VS_TEX_INDIRECTIONS:
- case PIPE_CAP_MAX_FS_TEX_INDIRECTIONS:
- /* There is no limit in number of instructions beyond available memory */
- return 32768;
- case PIPE_CAP_MAX_VS_CONTROL_FLOW_DEPTH:
- case PIPE_CAP_MAX_FS_CONTROL_FLOW_DEPTH:
- return LP_MAX_TGSI_NESTING;
- case PIPE_CAP_MAX_VS_INPUTS:
- case PIPE_CAP_MAX_FS_INPUTS:
- return PIPE_MAX_ATTRIBS;
- case PIPE_CAP_MAX_FS_CONSTS:
- case PIPE_CAP_MAX_VS_CONSTS:
- /* There is no limit in number of constants beyond available memory */
- return 32768;
- case PIPE_CAP_MAX_VS_TEMPS:
- case PIPE_CAP_MAX_FS_TEMPS:
- return LP_MAX_TGSI_TEMPS;
- case PIPE_CAP_MAX_VS_ADDRS:
- case PIPE_CAP_MAX_FS_ADDRS:
- return LP_MAX_TGSI_ADDRS;
- case PIPE_CAP_MAX_VS_PREDS:
- case PIPE_CAP_MAX_FS_PREDS:
- return LP_MAX_TGSI_PREDS;
case PIPE_CAP_DEPTHSTENCIL_CLEAR_SEPARATE:
return 1;
- case PIPE_CAP_GEOMETRY_SHADER4:
- return 1;
case PIPE_CAP_DEPTH_CLAMP:
return 0;
default:
- assert(0);
return 0;
}
}
+static int
+llvmpipe_get_shader_param(struct pipe_screen *screen, unsigned shader, enum pipe_shader_cap param)
+{
+ switch(shader)
+ {
+ case PIPE_SHADER_FRAGMENT:
+ return tgsi_exec_get_shader_param(param);
+ case PIPE_SHADER_VERTEX:
+ case PIPE_SHADER_GEOMETRY:
+ return draw_get_shader_param(shader, param);
+ default:
+ return 0;
+ }
+}
static float
llvmpipe_get_paramf(struct pipe_screen *screen, enum pipe_cap param)
screen->base.get_name = llvmpipe_get_name;
screen->base.get_vendor = llvmpipe_get_vendor;
screen->base.get_param = llvmpipe_get_param;
+ screen->base.get_shader_param = llvmpipe_get_shader_param;
screen->base.get_paramf = llvmpipe_get_paramf;
screen->base.is_format_supported = llvmpipe_is_format_supported;
case PIPE_CAP_TEXTURE_MIRROR_CLAMP:
case PIPE_CAP_TEXTURE_MIRROR_REPEAT:
return 1;
- case PIPE_CAP_TGSI_CONT_SUPPORTED:
- return 1;
case PIPE_CAP_BLEND_EQUATION_SEPARATE:
return 1;
case PIPE_CAP_INDEP_BLEND_ENABLE:
case PIPE_CAP_TGSI_FS_COORD_ORIGIN_LOWER_LEFT:
case PIPE_CAP_TGSI_FS_COORD_PIXEL_CENTER_INTEGER:
return 0;
- case PIPE_CAP_MAX_VS_INSTRUCTIONS:
- case PIPE_CAP_MAX_FS_INSTRUCTIONS:
- case PIPE_CAP_MAX_VS_ALU_INSTRUCTIONS:
- case PIPE_CAP_MAX_FS_ALU_INSTRUCTIONS:
- case PIPE_CAP_MAX_VS_TEX_INSTRUCTIONS:
- case PIPE_CAP_MAX_FS_TEX_INSTRUCTIONS:
- case PIPE_CAP_MAX_VS_TEX_INDIRECTIONS:
- case PIPE_CAP_MAX_FS_TEX_INDIRECTIONS: /* arbitrary limit */
+ case PIPE_CAP_DEPTH_CLAMP:
+ return 1;
+ default:
+ NOUVEAU_ERR("Unknown PIPE_CAP %d\n", param);
+ return 0;
+ }
+}
+
+static int
+nv50_screen_get_shader_param(struct pipe_screen *pscreen, unsigned shader, enum pipe_shader_cap param)
+{
+ switch(shader)
+ {
+ case PIPE_SHADER_FRAGMENT:
+ case PIPE_SHADER_VERTEX:
+ case PIPE_SHADER_GEOMETRY:
+ break;
+ default:
+ return 0;
+ }
+
+ 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: /* arbitrary limit */
return 16384;
- case PIPE_CAP_MAX_VS_CONTROL_FLOW_DEPTH:
- case PIPE_CAP_MAX_FS_CONTROL_FLOW_DEPTH: /* need stack bo */
+ case PIPE_SHADER_CAP_MAX_CONTROL_FLOW_DEPTH: /* need stack bo */
return 4;
- case PIPE_CAP_MAX_VS_INPUTS:
- return 16;
- case PIPE_CAP_MAX_FS_INPUTS: /* 128 / 4 with GP */
- return 64 / 4;
- case PIPE_CAP_MAX_VS_CONSTS:
- case PIPE_CAP_MAX_FS_CONSTS:
+ case PIPE_SHADER_CAP_MAX_INPUTS: /* 128 / 4 with GP */
+ if(shader == PIPE_SHADER_GEOMETRY)
+ return 128 / 4;
+ else
+ return 64 / 4;
+ case PIPE_SHADER_CAP_MAX_CONSTS:
return 65536 / 16;
- case PIPE_CAP_MAX_VS_ADDRS:
- case PIPE_CAP_MAX_FS_ADDRS: /* no spilling atm */
+ case PIPE_SHADER_CAP_MAX_ADDRS: /* no spilling atm */
return 1;
- case PIPE_CAP_MAX_VS_PREDS:
- case PIPE_CAP_MAX_FS_PREDS: /* not yet handled */
+ case PIPE_SHADER_CAP_MAX_PREDS: /* not yet handled */
return 0;
- case PIPE_CAP_MAX_VS_TEMPS:
- case PIPE_CAP_MAX_FS_TEMPS: /* no spilling atm */
+ case PIPE_SHADER_CAP_MAX_TEMPS: /* no spilling atm */
return 128 / 4;
- case PIPE_CAP_DEPTH_CLAMP:
+ case PIPE_SHADER_CAP_TGSI_CONT_SUPPORTED:
return 1;
default:
- NOUVEAU_ERR("Unknown PIPE_CAP %d\n", param);
return 0;
}
}
pscreen->winsys = ws;
pscreen->destroy = nv50_screen_destroy;
pscreen->get_param = nv50_screen_get_param;
+ pscreen->get_shader_param = nv50_screen_get_shader_param;
pscreen->get_paramf = nv50_screen_get_paramf;
pscreen->is_format_supported = nv50_screen_is_format_supported;
pscreen->context_create = nv50_create;
return 1;
case PIPE_CAP_MAX_VERTEX_TEXTURE_UNITS:
return 0; /* We have 4 on nv40 - but unsupported currently */
- case PIPE_CAP_TGSI_CONT_SUPPORTED:
- return 0;
case PIPE_CAP_BLEND_EQUATION_SEPARATE:
return screen->advertise_blend_equation_separate;
case PIPE_CAP_MAX_COMBINED_SAMPLERS:
case PIPE_CAP_TGSI_FS_COORD_ORIGIN_UPPER_LEFT:
case PIPE_CAP_TGSI_FS_COORD_PIXEL_CENTER_INTEGER:
return 1;
- case PIPE_CAP_MAX_FS_INSTRUCTIONS:
- case PIPE_CAP_MAX_FS_ALU_INSTRUCTIONS:
- case PIPE_CAP_MAX_FS_TEX_INSTRUCTIONS:
- case PIPE_CAP_MAX_FS_TEX_INDIRECTIONS:
- return 4096;
- case PIPE_CAP_MAX_FS_CONTROL_FLOW_DEPTH:
- /* FIXME: is it the dynamic (nv30:0/nv40:24) or the static
- value (nv30:0/nv40:4) ? */
- return screen->use_nv4x ? 4 : 0;
- case PIPE_CAP_MAX_FS_INPUTS:
- return screen->use_nv4x ? 12 : 10;
- case PIPE_CAP_MAX_FS_CONSTS:
- return screen->use_nv4x ? 224 : 32;
- case PIPE_CAP_MAX_FS_TEMPS:
- return 32;
- case PIPE_CAP_MAX_FS_ADDRS:
- return screen->use_nv4x ? 1 : 0;
- case PIPE_CAP_MAX_FS_PREDS:
- return 0; /* we could expose these, but nothing uses them */
- case PIPE_CAP_MAX_VS_INSTRUCTIONS:
- case PIPE_CAP_MAX_VS_ALU_INSTRUCTIONS:
- return screen->use_nv4x ? 512 : 256;
- case PIPE_CAP_MAX_VS_TEX_INSTRUCTIONS:
- case PIPE_CAP_MAX_VS_TEX_INDIRECTIONS:
- return screen->use_nv4x ? 512 : 0;
- case PIPE_CAP_MAX_VS_CONTROL_FLOW_DEPTH:
- /* FIXME: is it the dynamic (nv30:24/nv40:24) or the static
- value (nv30:1/nv40:4) ? */
- return screen->use_nv4x ? 4 : 1;
- case PIPE_CAP_MAX_VS_INPUTS:
- return 16;
- case PIPE_CAP_MAX_VS_CONSTS:
- /* - 6 is for clip planes; Gallium should be fixed to put
- * them in the vertex shader itself, so we don't need to reserve these */
- return (screen->use_nv4x ? 468 : 256) - 6;
- case PIPE_CAP_MAX_VS_TEMPS:
- return screen->use_nv4x ? 32 : 13;
- case PIPE_CAP_MAX_VS_ADDRS:
- return 2;
- case PIPE_CAP_MAX_VS_PREDS:
- return 0; /* we could expose these, but nothing uses them */
- case PIPE_CAP_GEOMETRY_SHADER4:
- return 0;
case PIPE_CAP_DEPTH_CLAMP:
return 0; // TODO: implement depth clamp
default:
}
}
+static int
+nvfx_screen_get_shader_param(struct pipe_screen *pscreen, unsigned shader, enum pipe_shader_cap param)
+{
+ struct nvfx_screen *screen = nvfx_screen(pscreen);
+
+ switch(shader) {
+ case PIPE_SHADER_FRAGMENT:
+ 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 4096;
+ case PIPE_SHADER_CAP_MAX_CONTROL_FLOW_DEPTH:
+ /* FIXME: is it the dynamic (nv30:0/nv40:24) or the static
+ value (nv30:0/nv40:4) ? */
+ return screen->use_nv4x ? 4 : 0;
+ case PIPE_SHADER_CAP_MAX_INPUTS:
+ return screen->use_nv4x ? 12 : 10;
+ case PIPE_SHADER_CAP_MAX_CONSTS:
+ return screen->use_nv4x ? 224 : 32;
+ case PIPE_SHADER_CAP_MAX_CONST_BUFFERS:
+ return 1;
+ case PIPE_SHADER_CAP_MAX_TEMPS:
+ return 32;
+ case PIPE_SHADER_CAP_MAX_ADDRS:
+ return screen->use_nv4x ? 1 : 0;
+ case PIPE_SHADER_CAP_MAX_PREDS:
+ return 0; /* we could expose these, but nothing uses them */
+ case PIPE_SHADER_CAP_TGSI_CONT_SUPPORTED:
+ return 0;
+ default:
+ break;
+ }
+ break;
+ case PIPE_SHADER_VERTEX:
+ switch(param) {
+ case PIPE_SHADER_CAP_MAX_INSTRUCTIONS:
+ case PIPE_SHADER_CAP_MAX_ALU_INSTRUCTIONS:
+ return screen->use_nv4x ? 512 : 256;
+ case PIPE_SHADER_CAP_MAX_TEX_INSTRUCTIONS:
+ case PIPE_SHADER_CAP_MAX_TEX_INDIRECTIONS:
+ return screen->use_nv4x ? 512 : 0;
+ case PIPE_SHADER_CAP_MAX_CONTROL_FLOW_DEPTH:
+ /* FIXME: is it the dynamic (nv30:24/nv40:24) or the static
+ value (nv30:1/nv40:4) ? */
+ return screen->use_nv4x ? 4 : 1;
+ case PIPE_SHADER_CAP_MAX_INPUTS:
+ return 16;
+ case PIPE_SHADER_CAP_MAX_CONSTS:
+ /* - 6 is for clip planes; Gallium should be fixed to put
+ * them in the vertex shader itself, so we don't need to reserve these */
+ return (screen->use_nv4x ? 468 : 256) - 6;
+ case PIPE_SHADER_CAP_MAX_CONST_BUFFERS:
+ return 1;
+ case PIPE_SHADER_CAP_MAX_TEMPS:
+ return screen->use_nv4x ? 32 : 13;
+ case PIPE_SHADER_CAP_MAX_ADDRS:
+ return 2;
+ case PIPE_SHADER_CAP_MAX_PREDS:
+ return 0; /* we could expose these, but nothing uses them */
+ case PIPE_SHADER_CAP_TGSI_CONT_SUPPORTED:
+ return 1;
+ default:
+ break;
+ }
+ break;
+ default:
+ break;
+ }
+ return 0;
+}
+
static float
nvfx_screen_get_paramf(struct pipe_screen *pscreen, enum pipe_cap param)
{
pscreen->winsys = ws;
pscreen->destroy = nvfx_screen_destroy;
pscreen->get_param = nvfx_screen_get_param;
+ pscreen->get_shader_param = nvfx_screen_get_shader_param;
pscreen->get_paramf = nvfx_screen_get_paramf;
pscreen->is_format_supported = nvfx_screen_is_format_supported;
pscreen->context_create = nvfx_create;
/* Unsupported features (boolean caps). */
case PIPE_CAP_TIMER_QUERY:
case PIPE_CAP_DUAL_SOURCE_BLEND:
- case PIPE_CAP_TGSI_CONT_SUPPORTED:
case PIPE_CAP_INDEP_BLEND_ENABLE:
case PIPE_CAP_INDEP_BLEND_FUNC:
case PIPE_CAP_DEPTH_CLAMP: /* XXX implemented, but breaks Regnum Online */
/* General shader limits and features. */
case PIPE_CAP_SM3:
return is_r500 ? 1 : 0;
- case PIPE_CAP_MAX_CONST_BUFFERS:
- return 1;
- case PIPE_CAP_MAX_CONST_BUFFER_SIZE:
- return 256;
-
/* Fragment coordinate conventions. */
case PIPE_CAP_TGSI_FS_COORD_ORIGIN_UPPER_LEFT:
case PIPE_CAP_TGSI_FS_COORD_PIXEL_CENTER_HALF_INTEGER:
case PIPE_CAP_TGSI_FS_COORD_ORIGIN_LOWER_LEFT:
case PIPE_CAP_TGSI_FS_COORD_PIXEL_CENTER_INTEGER:
return 0;
+ default:
+ fprintf(stderr, "r300: Implementation error: Bad param %d\n",
+ param);
+ return 0;
+ }
+}
- /* Fragment shader limits. */
- case PIPE_CAP_MAX_FS_INSTRUCTIONS:
+static int r300_get_shader_param(struct pipe_screen *pscreen, unsigned shader, enum pipe_shader_cap param)
+{
+ struct r300_screen* r300screen = r300_screen(pscreen);
+ boolean is_r400 = r300screen->caps.is_r400;
+ boolean is_r500 = r300screen->caps.is_r500;
+
+ /* XXX extended shader capabilities of r400 unimplemented */
+ is_r400 = FALSE;
+
+ switch (shader)
+ {
+ case PIPE_SHADER_FRAGMENT:
+ switch (param)
+ {
+ case PIPE_SHADER_CAP_MAX_INSTRUCTIONS:
return is_r500 || is_r400 ? 512 : 96;
- case PIPE_CAP_MAX_FS_ALU_INSTRUCTIONS:
+ case PIPE_SHADER_CAP_MAX_ALU_INSTRUCTIONS:
return is_r500 || is_r400 ? 512 : 64;
- case PIPE_CAP_MAX_FS_TEX_INSTRUCTIONS:
+ case PIPE_SHADER_CAP_MAX_TEX_INSTRUCTIONS:
return is_r500 || is_r400 ? 512 : 32;
- case PIPE_CAP_MAX_FS_TEX_INDIRECTIONS:
+ case PIPE_SHADER_CAP_MAX_TEX_INDIRECTIONS:
return is_r500 ? 511 : 4;
- case PIPE_CAP_MAX_FS_CONTROL_FLOW_DEPTH:
+ case PIPE_SHADER_CAP_MAX_CONTROL_FLOW_DEPTH:
return is_r500 ? 64 : 0; /* Actually unlimited on r500. */
- case PIPE_CAP_MAX_FS_INPUTS:
+ /* Fragment shader limits. */
+ case PIPE_SHADER_CAP_MAX_INPUTS:
/* 2 colors + 8 texcoords are always supported
* (minus fog and wpos).
*
* additional texcoords but there is no two-sided color
* selection then. However the facing bit can be used instead. */
return 10;
- case PIPE_CAP_MAX_FS_CONSTS:
+ case PIPE_SHADER_CAP_MAX_CONSTS:
return is_r500 ? 256 : 32;
- case PIPE_CAP_MAX_FS_TEMPS:
+ case PIPE_SHADER_CAP_MAX_CONST_BUFFERS:
+ return 1;
+ case PIPE_SHADER_CAP_MAX_TEMPS:
return is_r500 ? 128 : is_r400 ? 64 : 32;
- case PIPE_CAP_MAX_FS_ADDRS:
+ case PIPE_SHADER_CAP_MAX_ADDRS:
return 0;
- case PIPE_CAP_MAX_FS_PREDS:
+ case PIPE_SHADER_CAP_MAX_PREDS:
return is_r500 ? 1 : 0;
-
- /* Vertex shader limits. */
- case PIPE_CAP_MAX_VS_INSTRUCTIONS:
- case PIPE_CAP_MAX_VS_ALU_INSTRUCTIONS:
+ case PIPE_SHADER_CAP_TGSI_CONT_SUPPORTED:
+ return 1;
+ }
+ break;
+ case PIPE_SHADER_VERTEX:
+ switch (param)
+ {
+ case PIPE_SHADER_CAP_MAX_INSTRUCTIONS:
+ case PIPE_SHADER_CAP_MAX_ALU_INSTRUCTIONS:
return is_r500 ? 1024 : 256;
- case PIPE_CAP_MAX_VS_TEX_INSTRUCTIONS:
- case PIPE_CAP_MAX_VS_TEX_INDIRECTIONS:
+ case PIPE_SHADER_CAP_MAX_TEX_INSTRUCTIONS:
+ case PIPE_SHADER_CAP_MAX_TEX_INDIRECTIONS:
return 0;
- case PIPE_CAP_MAX_VS_CONTROL_FLOW_DEPTH:
+ case PIPE_SHADER_CAP_MAX_CONTROL_FLOW_DEPTH:
return is_r500 ? 4 : 0; /* For loops; not sure about conditionals. */
- case PIPE_CAP_MAX_VS_INPUTS:
+ case PIPE_SHADER_CAP_MAX_INPUTS:
return 16;
- case PIPE_CAP_MAX_VS_CONSTS:
+ case PIPE_SHADER_CAP_MAX_CONSTS:
return 256;
- case PIPE_CAP_MAX_VS_TEMPS:
+ case PIPE_SHADER_CAP_MAX_CONST_BUFFERS:
+ return 1;
+ case PIPE_SHADER_CAP_MAX_TEMPS:
return 32;
- case PIPE_CAP_MAX_VS_ADDRS:
+ case PIPE_SHADER_CAP_MAX_ADDRS:
return 1; /* XXX guessed */
- case PIPE_CAP_MAX_VS_PREDS:
+ case PIPE_SHADER_CAP_MAX_PREDS:
return is_r500 ? 4 : 0; /* XXX guessed. */
- case PIPE_CAP_GEOMETRY_SHADER4:
- return 0;
-
+ case PIPE_SHADER_CAP_TGSI_CONT_SUPPORTED:
+ return 1;
default:
- fprintf(stderr, "r300: Implementation error: Bad param %d\n",
- param);
- return 0;
+ break;
+ }
+ break;
+ default:
+ break;
}
+ return 0;
}
static float r300_get_paramf(struct pipe_screen* pscreen, enum pipe_cap param)
r300screen->screen.get_name = r300_get_name;
r300screen->screen.get_vendor = r300_get_vendor;
r300screen->screen.get_param = r300_get_param;
+ r300screen->screen.get_shader_param = r300_get_shader_param;
r300screen->screen.get_paramf = r300_get_paramf;
r300screen->screen.is_format_supported = r300_is_format_supported;
r300screen->screen.context_create = r300_create_context;
/* Unsupported features (boolean caps). */
case PIPE_CAP_TIMER_QUERY:
- case PIPE_CAP_TGSI_CONT_SUPPORTED:
case PIPE_CAP_STREAM_OUTPUT:
case PIPE_CAP_INDEP_BLEND_FUNC: /* FIXME allow this */
- case PIPE_CAP_GEOMETRY_SHADER4:
return 0;
/* Texturing. */
case PIPE_CAP_TGSI_FS_COORD_ORIGIN_LOWER_LEFT:
case PIPE_CAP_TGSI_FS_COORD_PIXEL_CENTER_INTEGER:
return 0;
-
- /* Shader limits. */
- case PIPE_CAP_MAX_VS_INSTRUCTIONS:
- return 16384; //max native instructions, not greater than max instructions
- case PIPE_CAP_MAX_VS_ALU_INSTRUCTIONS:
- case PIPE_CAP_MAX_VS_TEX_INSTRUCTIONS:
- case PIPE_CAP_MAX_VS_TEX_INDIRECTIONS:
- return 16384;
- case PIPE_CAP_MAX_FS_INSTRUCTIONS:
- return 16384; //max program native instructions
- case PIPE_CAP_MAX_FS_ALU_INSTRUCTIONS:
- return 16384; //max program native ALU instructions
- case PIPE_CAP_MAX_FS_TEX_INSTRUCTIONS:
- return 16384; //max program native texture instructions
- case PIPE_CAP_MAX_FS_TEX_INDIRECTIONS:
- return 2048; //max program native texture indirections
- case PIPE_CAP_MAX_VS_CONTROL_FLOW_DEPTH:
- case PIPE_CAP_MAX_FS_CONTROL_FLOW_DEPTH:
- return 8; /* FIXME */
- case PIPE_CAP_MAX_VS_INPUTS:
- return 16; //max native attributes
- case PIPE_CAP_MAX_FS_INPUTS:
- return 10; //max native attributes
- case PIPE_CAP_MAX_VS_TEMPS:
- return 256; //max native temporaries
- case PIPE_CAP_MAX_FS_TEMPS:
- return 256; //max native temporaries
- case PIPE_CAP_MAX_VS_ADDRS:
- case PIPE_CAP_MAX_FS_ADDRS:
- return 1; //max native address registers/* FIXME Isn't this equal to TEMPS? */
- case PIPE_CAP_MAX_VS_CONSTS:
- return 256; //max native parameters
- case PIPE_CAP_MAX_FS_CONSTS:
- return 256; //max program native parameters
- case PIPE_CAP_MAX_CONST_BUFFERS:
- return 1;
- case PIPE_CAP_MAX_CONST_BUFFER_SIZE: /* in bytes */
- return 4096;
- case PIPE_CAP_MAX_PREDICATE_REGISTERS:
- case PIPE_CAP_MAX_VS_PREDS:
- case PIPE_CAP_MAX_FS_PREDS:
- return 0; /* FIXME */
-
default:
R600_ERR("r600: unknown param %d\n", param);
return 0;
}
}
+static int r600_get_shader_param(struct pipe_screen* pscreen, unsigned shader, enum pipe_shader_cap param)
+{
+ switch(shader)
+ {
+ case PIPE_SHADER_FRAGMENT:
+ case PIPE_SHADER_VERTEX:
+ break;
+ case PIPE_SHADER_GEOMETRY:
+ /* TODO: support and enable geometry programs */
+ return 0;
+ default:
+ /* TODO: support tessellation on Evergreen */
+ return 0;
+ }
+
+ /* TODO: all these should be fixed, since r600 surely supports much more! */
+ 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 16384;
+ case PIPE_SHADER_CAP_MAX_CONTROL_FLOW_DEPTH:
+ return 8; /* FIXME */
+ case PIPE_SHADER_CAP_MAX_INPUTS:
+ if(shader == PIPE_SHADER_FRAGMENT)
+ return 10;
+ else
+ return 16;
+ case PIPE_SHADER_CAP_MAX_TEMPS:
+ return 256; //max native temporaries
+ case PIPE_SHADER_CAP_MAX_ADDRS:
+ return 1; //max native address registers/* FIXME Isn't this equal to TEMPS? */
+ case PIPE_SHADER_CAP_MAX_CONSTS:
+ return 256; //max native parameters
+ case PIPE_SHADER_CAP_MAX_CONST_BUFFERS:
+ return 1;
+ case PIPE_SHADER_CAP_MAX_PREDS:
+ return 0; /* FIXME */
+ case PIPE_SHADER_CAP_TGSI_CONT_SUPPORTED:
+ /* TODO: support this! */
+ return 0;
+ default:
+ return 0;
+ }
+}
+
static float r600_get_paramf(struct pipe_screen* pscreen, enum pipe_cap param)
{
switch (param) {
rscreen->screen.get_name = r600_get_name;
rscreen->screen.get_vendor = r600_get_vendor;
rscreen->screen.get_param = r600_get_param;
+ rscreen->screen.get_shader_param = r600_get_shader_param;
rscreen->screen.get_paramf = r600_get_paramf;
rscreen->screen.is_format_supported = r600_is_format_supported;
rscreen->screen.context_create = r600_create_context;
param);
}
+static int
+rbug_screen_get_shader_param(struct pipe_screen *_screen,
+ unsigned shader, enum pipe_cap param)
+{
+ struct rbug_screen *rb_screen = rbug_screen(_screen);
+ struct pipe_screen *screen = rb_screen->screen;
+
+ return screen->get_shader_param(screen, shader,
+ param);
+}
+
static float
rbug_screen_get_paramf(struct pipe_screen *_screen,
enum pipe_cap param)
rb_screen->base.get_name = rbug_screen_get_name;
rb_screen->base.get_vendor = rbug_screen_get_vendor;
rb_screen->base.get_param = rbug_screen_get_param;
+ rb_screen->base.get_shader_param = rbug_screen_get_shader_param;
rb_screen->base.get_paramf = rbug_screen_get_paramf;
rb_screen->base.is_format_supported = rbug_screen_is_format_supported;
rb_screen->base.context_create = rbug_screen_context_create;
#include "util/u_format_s3tc.h"
#include "pipe/p_defines.h"
#include "pipe/p_screen.h"
+#include "draw/draw_context.h"
#include "state_tracker/sw_winsys.h"
#include "tgsi/tgsi_exec.h"
return SP_MAX_TEXTURE_3D_LEVELS;
case PIPE_CAP_MAX_TEXTURE_CUBE_LEVELS:
return SP_MAX_TEXTURE_2D_LEVELS;
- case PIPE_CAP_TGSI_CONT_SUPPORTED:
- return 1;
case PIPE_CAP_BLEND_EQUATION_SEPARATE:
return 1;
- case PIPE_CAP_MAX_CONST_BUFFERS:
- return PIPE_MAX_CONSTANT_BUFFERS;
- case PIPE_CAP_MAX_CONST_BUFFER_SIZE:
- return 4096 * 4 * sizeof(float);
case PIPE_CAP_INDEP_BLEND_ENABLE:
return 1;
case PIPE_CAP_INDEP_BLEND_FUNC:
return 1;
case PIPE_CAP_STREAM_OUTPUT:
return 1;
-
- case PIPE_CAP_MAX_VS_INSTRUCTIONS:
- case PIPE_CAP_MAX_FS_INSTRUCTIONS:
- case PIPE_CAP_MAX_VS_ALU_INSTRUCTIONS:
- case PIPE_CAP_MAX_FS_ALU_INSTRUCTIONS:
- case PIPE_CAP_MAX_VS_TEX_INSTRUCTIONS:
- case PIPE_CAP_MAX_FS_TEX_INSTRUCTIONS:
- case PIPE_CAP_MAX_VS_TEX_INDIRECTIONS:
- case PIPE_CAP_MAX_FS_TEX_INDIRECTIONS:
- /* There is no limit in number of instructions beyond available memory */
- return 32768;
- case PIPE_CAP_MAX_VS_CONTROL_FLOW_DEPTH:
- case PIPE_CAP_MAX_FS_CONTROL_FLOW_DEPTH:
- return TGSI_EXEC_MAX_NESTING;
- case PIPE_CAP_MAX_VS_INPUTS:
- case PIPE_CAP_MAX_FS_INPUTS:
- return TGSI_EXEC_MAX_INPUT_ATTRIBS;
- case PIPE_CAP_MAX_FS_CONSTS:
- case PIPE_CAP_MAX_VS_CONSTS:
- return TGSI_EXEC_MAX_CONST_BUFFER;
- case PIPE_CAP_MAX_VS_TEMPS:
- case PIPE_CAP_MAX_FS_TEMPS:
- return TGSI_EXEC_NUM_TEMPS;
- case PIPE_CAP_MAX_VS_ADDRS:
- case PIPE_CAP_MAX_FS_ADDRS:
- return TGSI_EXEC_NUM_ADDRS;
- case PIPE_CAP_MAX_VS_PREDS:
- case PIPE_CAP_MAX_FS_PREDS:
- return TGSI_EXEC_NUM_PREDS;
-
case PIPE_CAP_DEPTHSTENCIL_CLEAR_SEPARATE:
return 0;
-
- case PIPE_CAP_GEOMETRY_SHADER4:
- return 1;
default:
return 0;
}
}
+static int
+softpipe_get_shader_param(struct pipe_screen *screen, unsigned shader, enum pipe_shader_cap param)
+{
+ switch(shader)
+ {
+ case PIPE_SHADER_FRAGMENT:
+ return tgsi_exec_get_shader_param(param);
+ case PIPE_SHADER_VERTEX:
+ case PIPE_SHADER_GEOMETRY:
+ return draw_get_shader_param(shader, param);
+ default:
+ return 0;
+ }
+}
static float
softpipe_get_paramf(struct pipe_screen *screen, enum pipe_cap param)
screen->base.get_name = softpipe_get_name;
screen->base.get_vendor = softpipe_get_vendor;
screen->base.get_param = softpipe_get_param;
+ screen->base.get_shader_param = softpipe_get_shader_param;
screen->base.get_paramf = softpipe_get_paramf;
screen->base.is_format_supported = softpipe_is_format_supported;
screen->base.context_create = softpipe_create_context;
case PIPE_CAP_TGSI_FS_COORD_PIXEL_CENTER_INTEGER:
return 0;
- /*
- * Fragment shader limits
- */
-
- case PIPE_CAP_MAX_FS_INSTRUCTIONS:
- case PIPE_CAP_MAX_FS_ALU_INSTRUCTIONS:
- case PIPE_CAP_MAX_FS_TEX_INSTRUCTIONS:
- case PIPE_CAP_MAX_FS_TEX_INDIRECTIONS:
- return svgascreen->use_ps30 ? 512 : 96;
- case PIPE_CAP_MAX_FS_CONTROL_FLOW_DEPTH:
- return SVGA3D_MAX_NESTING_LEVEL;
- case PIPE_CAP_MAX_FS_INPUTS:
- return 10;
- case PIPE_CAP_MAX_FS_CONSTS:
- return svgascreen->use_vs30 ? 224 : 16;
- case PIPE_CAP_MAX_FS_TEMPS:
- if (!sws->get_cap(sws, SVGA3D_DEVCAP_MAX_FRAGMENT_SHADER_TEMPS, &result))
- return svgascreen->use_ps30 ? 32 : 12;
- return result.u;
- case PIPE_CAP_MAX_FS_ADDRS:
- return svgascreen->use_ps30 ? 1 : 0;
- case PIPE_CAP_MAX_FS_PREDS:
- return svgascreen->use_ps30 ? 1 : 0;
-
- /*
- * Vertex shader limits
- */
- case PIPE_CAP_MAX_VS_INSTRUCTIONS:
- case PIPE_CAP_MAX_VS_ALU_INSTRUCTIONS:
- if (!sws->get_cap(sws, SVGA3D_DEVCAP_MAX_VERTEX_SHADER_INSTRUCTIONS, &result))
- return svgascreen->use_vs30 ? 512 : 256;
- return result.u;
- case PIPE_CAP_MAX_VS_TEX_INSTRUCTIONS:
- case PIPE_CAP_MAX_VS_TEX_INDIRECTIONS:
- /* XXX: until we have vertex texture support */
- return 0;
- case PIPE_CAP_MAX_VS_CONTROL_FLOW_DEPTH:
- return SVGA3D_MAX_NESTING_LEVEL;
- case PIPE_CAP_MAX_VS_INPUTS:
- return 16;
- case PIPE_CAP_MAX_VS_CONSTS:
- return 256;
- case PIPE_CAP_MAX_VS_TEMPS:
- if (!sws->get_cap(sws, SVGA3D_DEVCAP_MAX_VERTEX_SHADER_TEMPS, &result))
- return svgascreen->use_vs30 ? 32 : 12;
- return result.u;
- case PIPE_CAP_MAX_VS_ADDRS:
- return svgascreen->use_vs30 ? 1 : 0;
- case PIPE_CAP_MAX_VS_PREDS:
- return svgascreen->use_vs30 ? 1 : 0;
-
case PIPE_CAP_DEPTHSTENCIL_CLEAR_SEPARATE:
return 1;
return (int) svga_get_paramf( screen, param );
}
+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;
+ SVGA3dDevCapResult result;
+
+ switch (shader)
+ {
+ case PIPE_SHADER_FRAGMENT:
+ 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 svgascreen->use_ps30 ? 512 : 96;
+ case PIPE_SHADER_CAP_MAX_CONTROL_FLOW_DEPTH:
+ return SVGA3D_MAX_NESTING_LEVEL;
+ case PIPE_SHADER_CAP_MAX_INPUTS:
+ return 10;
+ case PIPE_SHADER_CAP_MAX_CONSTS:
+ return svgascreen->use_ps30 ? 224 : 16;
+ 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 svgascreen->use_ps30 ? 32 : 12;
+ return result.u;
+ case PIPE_SHADER_CAP_MAX_ADDRS:
+ return svgascreen->use_ps30 ? 1 : 0;
+ case PIPE_SHADER_CAP_MAX_PREDS:
+ return svgascreen->use_ps30 ? 1 : 0;
+ case PIPE_SHADER_CAP_TGSI_CONT_SUPPORTED:
+ return 1;
+ }
+ break;
+ case PIPE_SHADER_VERTEX:
+ switch (param)
+ {
+ 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 svgascreen->use_vs30 ? 512 : 256;
+ return result.u;
+ case PIPE_SHADER_CAP_MAX_TEX_INSTRUCTIONS:
+ case PIPE_SHADER_CAP_MAX_TEX_INDIRECTIONS:
+ /* XXX: until we have vertex texture support */
+ return 0;
+ case PIPE_SHADER_CAP_MAX_CONTROL_FLOW_DEPTH:
+ return SVGA3D_MAX_NESTING_LEVEL;
+ case PIPE_SHADER_CAP_MAX_INPUTS:
+ return 16;
+ case PIPE_SHADER_CAP_MAX_CONSTS:
+ return 256;
+ 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 svgascreen->use_vs30 ? 32 : 12;
+ return result.u;
+ case PIPE_SHADER_CAP_MAX_ADDRS:
+ return svgascreen->use_vs30 ? 1 : 0;
+ case PIPE_SHADER_CAP_MAX_PREDS:
+ return svgascreen->use_vs30 ? 1 : 0;
+ case PIPE_SHADER_CAP_TGSI_CONT_SUPPORTED:
+ return 1;
+ default:
+ break;
+ }
+ break;
+ default:
+ break;
+ }
+ return 0;
+}
static INLINE SVGA3dDevCapIndex
svga_translate_format_cap(enum pipe_format format)
screen->get_name = svga_get_name;
screen->get_vendor = svga_get_vendor;
screen->get_param = svga_get_param;
+ screen->get_shader_param = svga_get_shader_param;
screen->get_paramf = svga_get_paramf;
screen->is_format_supported = svga_is_format_supported;
screen->context_create = svga_context_create;
}
+static int
+trace_screen_get_shader_param(struct pipe_screen *_screen, unsigned shader,
+ enum pipe_shader_cap param)
+{
+ struct trace_screen *tr_scr = trace_screen(_screen);
+ struct pipe_screen *screen = tr_scr->screen;
+ int result;
+
+ trace_dump_call_begin("pipe_screen", "get_shader_param");
+
+ trace_dump_arg(ptr, screen);
+ trace_dump_arg(int, shader);
+ trace_dump_arg(int, param);
+
+ result = screen->get_shader_param(screen, shader, param);
+
+ trace_dump_ret(int, result);
+
+ trace_dump_call_end();
+
+ return result;
+}
+
+
static float
trace_screen_get_paramf(struct pipe_screen *_screen,
enum pipe_cap param)
tr_scr->base.get_name = trace_screen_get_name;
tr_scr->base.get_vendor = trace_screen_get_vendor;
tr_scr->base.get_param = trace_screen_get_param;
+ tr_scr->base.get_shader_param = trace_screen_get_shader_param;
tr_scr->base.get_paramf = trace_screen_get_paramf;
tr_scr->base.is_format_supported = trace_screen_is_format_supported;
assert(screen->context_create);
#include <string.h>
#include <stddef.h>
#include <stdarg.h>
+#include <limits.h>
#if defined(_WIN32) && !defined(__WIN32__)
PIPE_CAP_TEXTURE_MIRROR_CLAMP,
PIPE_CAP_TEXTURE_MIRROR_REPEAT,
PIPE_CAP_MAX_VERTEX_TEXTURE_UNITS,
- PIPE_CAP_TGSI_CONT_SUPPORTED,
PIPE_CAP_BLEND_EQUATION_SEPARATE,
PIPE_CAP_SM3, /*< Shader Model, supported */
PIPE_CAP_STREAM_OUTPUT,
- PIPE_CAP_MAX_PREDICATE_REGISTERS,
/** Maximum texture image units accessible from vertex and fragment shaders
* combined */
PIPE_CAP_MAX_COMBINED_SAMPLERS,
- PIPE_CAP_MAX_CONST_BUFFERS,
- PIPE_CAP_MAX_CONST_BUFFER_SIZE, /*< In bytes */
/** blend enables and write masks per rendertarget */
PIPE_CAP_INDEP_BLEND_ENABLE,
/** different blend funcs per rendertarget */
PIPE_CAP_TGSI_FS_COORD_ORIGIN_LOWER_LEFT,
PIPE_CAP_TGSI_FS_COORD_PIXEL_CENTER_HALF_INTEGER,
PIPE_CAP_TGSI_FS_COORD_PIXEL_CENTER_INTEGER,
-
- /*
- * Shader limits.
- */
- PIPE_CAP_MAX_FS_INSTRUCTIONS,
- PIPE_CAP_MAX_FS_ALU_INSTRUCTIONS,
- PIPE_CAP_MAX_FS_TEX_INSTRUCTIONS,
- PIPE_CAP_MAX_FS_TEX_INDIRECTIONS,
- PIPE_CAP_MAX_FS_CONTROL_FLOW_DEPTH,
- PIPE_CAP_MAX_FS_INPUTS,
- PIPE_CAP_MAX_FS_CONSTS,
- PIPE_CAP_MAX_FS_TEMPS,
- PIPE_CAP_MAX_FS_ADDRS,
- PIPE_CAP_MAX_FS_PREDS,
- PIPE_CAP_MAX_VS_INSTRUCTIONS,
- PIPE_CAP_MAX_VS_ALU_INSTRUCTIONS,
- PIPE_CAP_MAX_VS_TEX_INSTRUCTIONS,
- PIPE_CAP_MAX_VS_TEX_INDIRECTIONS,
- PIPE_CAP_MAX_VS_CONTROL_FLOW_DEPTH,
- PIPE_CAP_MAX_VS_INPUTS,
- PIPE_CAP_MAX_VS_CONSTS,
- PIPE_CAP_MAX_VS_TEMPS,
- PIPE_CAP_MAX_VS_ADDRS,
- PIPE_CAP_MAX_VS_PREDS,
-
- PIPE_CAP_GEOMETRY_SHADER4,
PIPE_CAP_DEPTH_CLAMP
};
+/* Shader caps not specific to any single stage */
+enum pipe_shader_cap
+{
+ PIPE_SHADER_CAP_MAX_INSTRUCTIONS, /* if 0, it means the stage is unsupported */
+ PIPE_SHADER_CAP_MAX_ALU_INSTRUCTIONS,
+ PIPE_SHADER_CAP_MAX_TEX_INSTRUCTIONS,
+ PIPE_SHADER_CAP_MAX_TEX_INDIRECTIONS,
+ PIPE_SHADER_CAP_MAX_CONTROL_FLOW_DEPTH,
+ PIPE_SHADER_CAP_MAX_INPUTS,
+ PIPE_SHADER_CAP_MAX_CONSTS,
+ PIPE_SHADER_CAP_MAX_CONST_BUFFERS,
+ PIPE_SHADER_CAP_MAX_TEMPS,
+ PIPE_SHADER_CAP_MAX_ADDRS,
+ PIPE_SHADER_CAP_MAX_PREDS,
+ PIPE_SHADER_CAP_TGSI_CONT_SUPPORTED,
+};
/**
* Referenced query flags.
*/
float (*get_paramf)( struct pipe_screen *, enum pipe_cap param );
+ /**
+ * Query a per-shader-stage integer-valued capability/parameter/limit
+ * \param param one of PIPE_CAP_x
+ */
+ int (*get_shader_param)( struct pipe_screen *, unsigned shader, enum pipe_shader_cap param );
+
struct pipe_context * (*context_create)( struct pipe_screen *,
void *priv );
= CLAMP(screen->get_param(screen, PIPE_CAP_MAX_RENDER_TARGETS),
1, MAX_DRAW_BUFFERS);
- for(i = 0; i < MESA_SHADER_TYPES; ++i)
- st->ctx->ShaderCompilerOptions[i].EmitNoCont = !screen->get_param(screen, PIPE_CAP_TGSI_CONT_SUPPORTED);
-
/* Quads always follow GL provoking rules. */
c->QuadsFollowProvokingVertexConvention = GL_FALSE;
- pc = &c->FragmentProgram;
- pc->MaxNativeInstructions = screen->get_param(screen, PIPE_CAP_MAX_FS_INSTRUCTIONS);
- pc->MaxNativeAluInstructions = screen->get_param(screen, PIPE_CAP_MAX_FS_ALU_INSTRUCTIONS);
- pc->MaxNativeTexInstructions = screen->get_param(screen, PIPE_CAP_MAX_FS_TEX_INSTRUCTIONS);
- pc->MaxNativeTexIndirections = screen->get_param(screen, PIPE_CAP_MAX_FS_TEX_INDIRECTIONS);
- pc->MaxNativeAttribs = screen->get_param(screen, PIPE_CAP_MAX_FS_INPUTS);
- pc->MaxNativeTemps = screen->get_param(screen, PIPE_CAP_MAX_FS_TEMPS);
- pc->MaxNativeAddressRegs = screen->get_param(screen, PIPE_CAP_MAX_FS_ADDRS);
- pc->MaxNativeParameters = screen->get_param(screen, PIPE_CAP_MAX_FS_CONSTS);
-
- pc = &c->VertexProgram;
- pc->MaxNativeInstructions = screen->get_param(screen, PIPE_CAP_MAX_VS_INSTRUCTIONS);
- pc->MaxNativeAluInstructions = screen->get_param(screen, PIPE_CAP_MAX_VS_ALU_INSTRUCTIONS);
- pc->MaxNativeTexInstructions = screen->get_param(screen, PIPE_CAP_MAX_VS_TEX_INSTRUCTIONS);
- pc->MaxNativeTexIndirections = screen->get_param(screen, PIPE_CAP_MAX_VS_TEX_INDIRECTIONS);
- pc->MaxNativeAttribs = screen->get_param(screen, PIPE_CAP_MAX_VS_INPUTS);
- pc->MaxNativeTemps = screen->get_param(screen, PIPE_CAP_MAX_VS_TEMPS);
- pc->MaxNativeAddressRegs = screen->get_param(screen, PIPE_CAP_MAX_VS_ADDRS);
- pc->MaxNativeParameters = screen->get_param(screen, PIPE_CAP_MAX_VS_CONSTS);
+ for(i = 0; i < MESA_SHADER_TYPES; ++i) {
+ struct gl_shader_compiler_options *options = &st->ctx->ShaderCompilerOptions[i];
+ switch(i)
+ {
+ case PIPE_SHADER_FRAGMENT:
+ pc = &c->FragmentProgram;
+ break;
+ case PIPE_SHADER_VERTEX:
+ pc = &c->VertexProgram;
+ break;
+ case PIPE_SHADER_GEOMETRY:
+ pc = &c->GeometryProgram;
+ break;
+ }
+
+ pc->MaxNativeInstructions = screen->get_shader_param(screen, i, PIPE_SHADER_CAP_MAX_INSTRUCTIONS);
+ pc->MaxNativeAluInstructions = screen->get_shader_param(screen, i, PIPE_SHADER_CAP_MAX_ALU_INSTRUCTIONS);
+ pc->MaxNativeTexInstructions = screen->get_shader_param(screen, i, PIPE_SHADER_CAP_MAX_TEX_INSTRUCTIONS);
+ pc->MaxNativeTexIndirections = screen->get_shader_param(screen, i, PIPE_SHADER_CAP_MAX_TEX_INDIRECTIONS);
+ pc->MaxNativeAttribs = screen->get_shader_param(screen, i, PIPE_SHADER_CAP_MAX_INPUTS);
+ pc->MaxNativeTemps = screen->get_shader_param(screen, i, PIPE_SHADER_CAP_MAX_TEMPS);
+ pc->MaxNativeAddressRegs = screen->get_shader_param(screen, i, PIPE_SHADER_CAP_MAX_ADDRS);
+ pc->MaxNativeParameters = screen->get_shader_param(screen, i, PIPE_SHADER_CAP_MAX_CONSTS);
+
+ options->EmitNoCont = !screen->get_shader_param(screen, i, PIPE_SHADER_CAP_TGSI_CONT_SUPPORTED);
+ }
/* PIPE_CAP_MAX_FS_INPUTS specifies the number of COLORn + GENERICn inputs
* and is set in MaxNativeAttribs. It's always 2 colors + N generic
* attributes. The GLSL compiler never uses COLORn for varyings, so we
* subtract the 2 colors to get the maximum number of varyings (generic
* attributes) supported by a driver. */
- c->MaxVarying = screen->get_param(screen, PIPE_CAP_MAX_FS_INPUTS) - 2;
+ c->MaxVarying = screen->get_shader_param(screen, PIPE_SHADER_FRAGMENT, PIPE_SHADER_CAP_MAX_INPUTS) - 2;
c->MaxVarying = MIN2(c->MaxVarying, MAX_VARYING);
}
}
#endif
- if (screen->get_param(screen, PIPE_CAP_GEOMETRY_SHADER4)) {
+ if (screen->get_shader_param(screen, PIPE_SHADER_GEOMETRY, PIPE_SHADER_CAP_MAX_INSTRUCTIONS) > 0) {
ctx->Extensions.ARB_geometry_shader4 = GL_TRUE;
}