#include "tgsi/tgsi_scan.h"
#include "svga_hw_reg.h"
+#include "svga_shader.h"
#include "svga_tgsi.h"
#include "svga3d_shaderdefs.h"
};
-struct svga_arl_consts {
+struct svga_arl_consts
+{
int number;
int idx;
int swizzle;
int arl_num;
};
-/* Internal functions:
- */
+/**
+ * This is the context/state used during TGSI->SVGA shader translation.
+ */
struct svga_shader_emitter
{
unsigned size;
char *buf;
char *ptr;
- union svga_compile_key key;
+ struct svga_compile_key key;
struct tgsi_shader_info info;
int unit;
int nr_hw_float_const;
int nr_hw_int_const;
int nr_hw_temp;
-
+
int insn_offset;
int internal_temp_count;
int dynamic_branching_level;
+ unsigned num_output_writes;
+ boolean constant_color_output;
+
boolean in_main_func;
- boolean created_zero_immediate;
- int zero_immediate_idx;
+ boolean created_common_immediate;
+ int common_immediate_idx[2];
boolean created_loop_const;
int loop_const_idx;
unsigned label[32];
unsigned nr_labels;
+ /** input/output register mappings, indexed by register number */
struct src_register input_map[PIPE_MAX_ATTRIBS];
SVGA3dShaderDestToken output_map[PIPE_MAX_ATTRIBS];
/* shared output for depth and fog */
SVGA3dShaderDestToken vs_depth_fog;
- SVGA3dShaderDestToken temp_col[PIPE_MAX_COLOR_BUFS];
- SVGA3dShaderDestToken true_col[PIPE_MAX_COLOR_BUFS];
+ /* PS output colors (indexed by color semantic index) */
+ SVGA3dShaderDestToken temp_color_output[PIPE_MAX_COLOR_BUFS];
+ SVGA3dShaderDestToken true_color_output[PIPE_MAX_COLOR_BUFS];
SVGA3dShaderDestToken temp_psiz;
SVGA3dShaderDestToken true_psiz;
struct svga_arl_consts arl_consts[12];
int num_arl_consts;
int current_arl;
+
+ unsigned pstipple_sampler_unit;
+
+ int num_samplers;
+ uint8_t sampler_target[PIPE_MAX_SAMPLERS];
};
-boolean svga_shader_emit_dword( struct svga_shader_emitter *emit,
- unsigned dword );
+boolean
+svga_shader_emit_dword(struct svga_shader_emitter *emit, unsigned dword);
-boolean svga_shader_emit_dwords( struct svga_shader_emitter *emit,
- const unsigned *dwords,
- unsigned nr );
+boolean
+svga_shader_emit_dwords(struct svga_shader_emitter *emit,
+ const unsigned *dwords, unsigned nr);
-boolean svga_shader_emit_opcode( struct svga_shader_emitter *emit,
- unsigned opcode );
+boolean
+svga_shader_emit_opcode(struct svga_shader_emitter *emit,
+ unsigned opcode);
-boolean svga_shader_emit_instructions( struct svga_shader_emitter *emit,
- const struct tgsi_token *tokens );
+boolean
+svga_shader_emit_instructions(struct svga_shader_emitter *emit,
+ const struct tgsi_token *tokens);
-boolean svga_translate_decl_sm30( struct svga_shader_emitter *emit,
- const struct tgsi_full_declaration *decl );
+boolean
+svga_shader_emit_samplers_decl(struct svga_shader_emitter *emit);
+boolean
+svga_translate_decl_sm30(struct svga_shader_emitter *emit,
+ const struct tgsi_full_declaration *decl);
-static INLINE boolean emit_dst( struct svga_shader_emitter *emit,
- SVGA3dShaderDestToken dest )
-{
- assert(dest.reserved0);
- assert(dest.mask);
- return svga_shader_emit_dword( emit, dest.value );
-}
-static INLINE boolean emit_src( struct svga_shader_emitter *emit,
- const struct src_register src )
-{
- if (src.base.relAddr) {
- assert(src.base.reserved0);
- assert(src.indirect.reserved0);
- return (svga_shader_emit_dword( emit, src.base.value ) &&
- svga_shader_emit_dword( emit, src.indirect.value ));
- }
- else {
- assert(src.base.reserved0);
- return svga_shader_emit_dword( emit, src.base.value );
- }
-}
+#define TRANSLATE_SWIZZLE(x,y,z,w) ((x) | ((y) << 2) | ((z) << 4) | ((w) << 6))
+#define SWIZZLE_XYZW \
+ TRANSLATE_SWIZZLE(TGSI_SWIZZLE_X,TGSI_SWIZZLE_Y,TGSI_SWIZZLE_Z,TGSI_SWIZZLE_W)
+#define SWIZZLE_XXXX \
+ TRANSLATE_SWIZZLE(TGSI_SWIZZLE_X,TGSI_SWIZZLE_X,TGSI_SWIZZLE_X,TGSI_SWIZZLE_X)
+#define SWIZZLE_YYYY \
+ TRANSLATE_SWIZZLE(TGSI_SWIZZLE_Y,TGSI_SWIZZLE_Y,TGSI_SWIZZLE_Y,TGSI_SWIZZLE_Y)
+#define SWIZZLE_ZZZZ \
+ TRANSLATE_SWIZZLE(TGSI_SWIZZLE_Z,TGSI_SWIZZLE_Z,TGSI_SWIZZLE_Z,TGSI_SWIZZLE_Z)
+#define SWIZZLE_WWWW \
+ TRANSLATE_SWIZZLE(TGSI_SWIZZLE_W,TGSI_SWIZZLE_W,TGSI_SWIZZLE_W,TGSI_SWIZZLE_W)
-static INLINE boolean emit_instruction( struct svga_shader_emitter *emit,
- SVGA3dShaderInstToken opcode )
+/** Emit the given SVGA3dShaderInstToken opcode */
+static inline boolean
+emit_instruction(struct svga_shader_emitter *emit,
+ SVGA3dShaderInstToken opcode)
{
- return svga_shader_emit_opcode( emit, opcode.value );
+ return svga_shader_emit_opcode(emit, opcode.value);
}
-static INLINE boolean emit_op1( struct svga_shader_emitter *emit,
- SVGA3dShaderInstToken inst,
- SVGA3dShaderDestToken dest,
- struct src_register src0 )
+/** Generate a SVGA3dShaderInstToken for the given SVGA3D shader opcode */
+static inline SVGA3dShaderInstToken
+inst_token(SVGA3dShaderOpCodeType opcode)
{
- return (emit_instruction( emit, inst ) &&
- emit_dst( emit, dest ) &&
- emit_src( emit, src0 ));
-}
+ SVGA3dShaderInstToken inst;
-static INLINE boolean emit_op2( struct svga_shader_emitter *emit,
- SVGA3dShaderInstToken inst,
- SVGA3dShaderDestToken dest,
- struct src_register src0,
- struct src_register src1 )
-{
- return (emit_instruction( emit, inst ) &&
- emit_dst( emit, dest ) &&
- emit_src( emit, src0 ) &&
- emit_src( emit, src1 ));
-}
+ inst.value = 0;
+ inst.op = opcode;
-static INLINE boolean emit_op3( struct svga_shader_emitter *emit,
- SVGA3dShaderInstToken inst,
- SVGA3dShaderDestToken dest,
- struct src_register src0,
- struct src_register src1,
- struct src_register src2 )
-{
- return (emit_instruction( emit, inst ) &&
- emit_dst( emit, dest ) &&
- emit_src( emit, src0 ) &&
- emit_src( emit, src1 ) &&
- emit_src( emit, src2 ));
+ return inst;
}
-static INLINE boolean emit_op4( struct svga_shader_emitter *emit,
- SVGA3dShaderInstToken inst,
- SVGA3dShaderDestToken dest,
- struct src_register src0,
- struct src_register src1,
- struct src_register src2,
- struct src_register src3)
+/**
+ * Generate a SVGA3dShaderInstToken for the given SVGA3D shader opcode
+ * with the predication flag set.
+ */
+static inline SVGA3dShaderInstToken
+inst_token_predicated(SVGA3dShaderOpCodeType opcode)
{
- return (emit_instruction( emit, inst ) &&
- emit_dst( emit, dest ) &&
- emit_src( emit, src0 ) &&
- emit_src( emit, src1 ) &&
- emit_src( emit, src2 ) &&
- emit_src( emit, src3 ));
-}
-
+ SVGA3dShaderInstToken inst;
-#define TRANSLATE_SWIZZLE(x,y,z,w) ((x) | ((y) << 2) | ((z) << 4) | ((w) << 6))
-#define SWIZZLE_XYZW \
- TRANSLATE_SWIZZLE(TGSI_SWIZZLE_X,TGSI_SWIZZLE_Y,TGSI_SWIZZLE_Z,TGSI_SWIZZLE_W)
-#define SWIZZLE_XXXX \
- TRANSLATE_SWIZZLE(TGSI_SWIZZLE_X,TGSI_SWIZZLE_X,TGSI_SWIZZLE_X,TGSI_SWIZZLE_X)
-#define SWIZZLE_YYYY \
- TRANSLATE_SWIZZLE(TGSI_SWIZZLE_Y,TGSI_SWIZZLE_Y,TGSI_SWIZZLE_Y,TGSI_SWIZZLE_Y)
-#define SWIZZLE_ZZZZ \
- TRANSLATE_SWIZZLE(TGSI_SWIZZLE_Z,TGSI_SWIZZLE_Z,TGSI_SWIZZLE_Z,TGSI_SWIZZLE_Z)
-#define SWIZZLE_WWWW \
- TRANSLATE_SWIZZLE(TGSI_SWIZZLE_W,TGSI_SWIZZLE_W,TGSI_SWIZZLE_W,TGSI_SWIZZLE_W)
+ inst.value = 0;
+ inst.op = opcode;
+ inst.predicated = 1;
+ return inst;
+}
-static INLINE SVGA3dShaderInstToken
-inst_token( unsigned opcode )
+/**
+ * Generate a SVGA3dShaderInstToken for a SETP instruction (set predicate)
+ * using the given comparison operator (one of SVGA3DOPCOMP_xx).
+ */
+static inline SVGA3dShaderInstToken
+inst_token_setp(SVGA3dShaderOpCodeCompFnType operator)
{
SVGA3dShaderInstToken inst;
inst.value = 0;
- inst.op = opcode;
+ inst.op = SVGA3DOP_SETP;
+ inst.control = operator;
return inst;
}
-static INLINE SVGA3dShaderDestToken
-dst_register( unsigned file,
- int number )
+
+/**
+ * Create an instance of a SVGA3dShaderDestToken.
+ * Note that this function is used to create tokens for output registers,
+ * temp registers AND constants (see emit_def_const()).
+ */
+static inline SVGA3dShaderDestToken
+dst_register(SVGA3dShaderRegType file, int number)
{
SVGA3dShaderDestToken dest;
+ /* check values against bitfield sizes */
+ assert(number < (1 << 11));
+ assert(file <= SVGA3DREG_PREDICATE);
+
dest.value = 0;
dest.num = number;
dest.type_upper = file >> 3;
dest.shfScale = 0;
dest.type_lower = file & 0x7;
dest.reserved0 = 1; /* is_reg */
-
+
return dest;
}
-static INLINE SVGA3dShaderDestToken
-writemask( SVGA3dShaderDestToken dest,
- unsigned mask )
+
+/**
+ * Apply a writemask to the given SVGA3dShaderDestToken, returning a
+ * new SVGA3dShaderDestToken.
+ */
+static inline SVGA3dShaderDestToken
+writemask(SVGA3dShaderDestToken dest, unsigned mask)
{
assert(dest.mask & mask);
dest.mask &= mask;
}
-static INLINE SVGA3dShaderSrcToken
-src_token( unsigned file, int number )
+/** Create a SVGA3dShaderSrcToken given a register file and number */
+static inline SVGA3dShaderSrcToken
+src_token(SVGA3dShaderRegType file, int number)
{
SVGA3dShaderSrcToken src;
+ /* check values against bitfield sizes */
+ assert(number < (1 << 11));
+ assert(file <= SVGA3DREG_PREDICATE);
+
src.value = 0;
src.num = number;
src.type_upper = file >> 3;
}
-static INLINE struct src_register
-absolute( struct src_register src )
-{
- src.base.srcMod = SVGA3DSRCMOD_ABS;
-
- return src;
-}
-
-
-static INLINE struct src_register
-negate( struct src_register src )
-{
- switch (src.base.srcMod) {
- case SVGA3DSRCMOD_ABS:
- src.base.srcMod = SVGA3DSRCMOD_ABSNEG;
- break;
- case SVGA3DSRCMOD_ABSNEG:
- src.base.srcMod = SVGA3DSRCMOD_ABS;
- break;
- case SVGA3DSRCMOD_NEG:
- src.base.srcMod = SVGA3DSRCMOD_NONE;
- break;
- case SVGA3DSRCMOD_NONE:
- src.base.srcMod = SVGA3DSRCMOD_NEG;
- break;
- }
- return src;
-}
-
-
-static INLINE struct src_register
-src_register( unsigned file, int number )
+/** Create a src_register given a register file and register number */
+static inline struct src_register
+src_register(SVGA3dShaderRegType file, int number)
{
struct src_register src;
-
- src.base = src_token( file, number );
+
+ src.base = src_token(file, number);
src.indirect.value = 0;
return src;
}
-static INLINE SVGA3dShaderDestToken dst( struct src_register src )
+/** Translate src_register into SVGA3dShaderDestToken */
+static inline SVGA3dShaderDestToken
+dst(struct src_register src)
{
- return dst_register( SVGA3dShaderGetRegType( src.base.value ),
- src.base.num );
+ return dst_register(SVGA3dShaderGetRegType(src.base.value), src.base.num);
}
-static INLINE struct src_register src( SVGA3dShaderDestToken dst )
-{
- return src_register( SVGA3dShaderGetRegType( dst.value ),
- dst.num );
-}
-static INLINE ubyte svga_tgsi_sampler_type( struct svga_shader_emitter *emit,
- int idx )
+/** Translate SVGA3dShaderDestToken to a src_register */
+static inline struct src_register
+src(SVGA3dShaderDestToken dst)
{
- switch (emit->key.fkey.tex[idx].texture_target) {
- case PIPE_TEXTURE_1D:
- return SVGA3DSAMP_2D;
- case PIPE_TEXTURE_2D:
- case PIPE_TEXTURE_RECT:
- return SVGA3DSAMP_2D;
- case PIPE_TEXTURE_3D:
- return SVGA3DSAMP_VOLUME;
- case PIPE_TEXTURE_CUBE:
- return SVGA3DSAMP_CUBE;
- }
-
- return SVGA3DSAMP_UNKNOWN;
+ return src_register(SVGA3dShaderGetRegType(dst.value), dst.num);
}
#endif