gallivm: add swizzle support where one channel isn't defined.
NIR doesn't always define all output channels relies on outputs being memset to 0 Reviewed-by: Roland Scheidegger <sroland@vmware.com>
This commit is contained in:
@@ -1673,7 +1673,7 @@ draw_llvm_generate(struct draw_llvm *llvm, struct draw_llvm_variant *variant)
|
||||
struct lp_bld_tgsi_system_values system_values;
|
||||
|
||||
memset(&system_values, 0, sizeof(system_values));
|
||||
|
||||
memset(&outputs, 0, sizeof(outputs));
|
||||
snprintf(func_name, sizeof(func_name), "draw_llvm_vs_variant%u",
|
||||
variant->shader->variants_cached);
|
||||
|
||||
@@ -2416,6 +2416,7 @@ draw_gs_llvm_generate(struct draw_llvm *llvm,
|
||||
unsigned vector_length = variant->shader->base.vector_length;
|
||||
|
||||
memset(&system_values, 0, sizeof(system_values));
|
||||
memset(&outputs, 0, sizeof(outputs));
|
||||
|
||||
snprintf(func_name, sizeof(func_name), "draw_llvm_gs_variant%u",
|
||||
variant->shader->variants_cached);
|
||||
|
@@ -652,7 +652,7 @@ lp_build_transpose_aos(struct gallivm_state *gallivm,
|
||||
struct lp_type double_type_lp = single_type_lp;
|
||||
LLVMTypeRef single_type;
|
||||
LLVMTypeRef double_type;
|
||||
LLVMValueRef t0, t1, t2, t3;
|
||||
LLVMValueRef t0 = NULL, t1 = NULL, t2 = NULL, t3 = NULL;
|
||||
|
||||
double_type_lp.length >>= 1;
|
||||
double_type_lp.width <<= 1;
|
||||
@@ -660,17 +660,39 @@ lp_build_transpose_aos(struct gallivm_state *gallivm,
|
||||
double_type = lp_build_vec_type(gallivm, double_type_lp);
|
||||
single_type = lp_build_vec_type(gallivm, single_type_lp);
|
||||
|
||||
LLVMValueRef double_type_zero = LLVMConstNull(double_type);
|
||||
/* Interleave x, y, z, w -> xy and zw */
|
||||
t0 = lp_build_interleave2_half(gallivm, single_type_lp, src[0], src[1], 0);
|
||||
t1 = lp_build_interleave2_half(gallivm, single_type_lp, src[2], src[3], 0);
|
||||
t2 = lp_build_interleave2_half(gallivm, single_type_lp, src[0], src[1], 1);
|
||||
t3 = lp_build_interleave2_half(gallivm, single_type_lp, src[2], src[3], 1);
|
||||
if (src[0]) {
|
||||
LLVMValueRef src1 = src[1];
|
||||
if (!src1)
|
||||
src1 = LLVMConstNull(single_type);
|
||||
t0 = lp_build_interleave2_half(gallivm, single_type_lp, src[0], src1, 0);
|
||||
t2 = lp_build_interleave2_half(gallivm, single_type_lp, src[0], src1, 1);
|
||||
|
||||
/* Cast to double width type for second interleave */
|
||||
t0 = LLVMBuildBitCast(gallivm->builder, t0, double_type, "t0");
|
||||
t1 = LLVMBuildBitCast(gallivm->builder, t1, double_type, "t1");
|
||||
t2 = LLVMBuildBitCast(gallivm->builder, t2, double_type, "t2");
|
||||
t3 = LLVMBuildBitCast(gallivm->builder, t3, double_type, "t3");
|
||||
/* Cast to double width type for second interleave */
|
||||
t0 = LLVMBuildBitCast(gallivm->builder, t0, double_type, "t0");
|
||||
t2 = LLVMBuildBitCast(gallivm->builder, t2, double_type, "t2");
|
||||
}
|
||||
if (src[2]) {
|
||||
LLVMValueRef src3 = src[3];
|
||||
if (!src3)
|
||||
src3 = LLVMConstNull(single_type);
|
||||
t1 = lp_build_interleave2_half(gallivm, single_type_lp, src[2], src3, 0);
|
||||
t3 = lp_build_interleave2_half(gallivm, single_type_lp, src[2], src3, 1);
|
||||
|
||||
/* Cast to double width type for second interleave */
|
||||
t1 = LLVMBuildBitCast(gallivm->builder, t1, double_type, "t1");
|
||||
t3 = LLVMBuildBitCast(gallivm->builder, t3, double_type, "t3");
|
||||
}
|
||||
|
||||
if (!t0)
|
||||
t0 = double_type_zero;
|
||||
if (!t1)
|
||||
t1 = double_type_zero;
|
||||
if (!t2)
|
||||
t2 = double_type_zero;
|
||||
if (!t3)
|
||||
t3 = double_type_zero;
|
||||
|
||||
/* Interleave xy, zw -> xyzw */
|
||||
dst[0] = lp_build_interleave2_half(gallivm, double_type_lp, t0, t1, 0);
|
||||
|
Reference in New Issue
Block a user