summaryrefslogtreecommitdiffstats
path: root/tests
diff options
context:
space:
mode:
Diffstat (limited to 'tests')
-rw-r--r--tests/compute/logic-no-short-circuit-evaluation.slang4
-rw-r--r--tests/glsl/matrix-bool-lowering.slang114
-rw-r--r--tests/glsl/matrix-integer-lowering.slang199
-rw-r--r--tests/metal/matrix-bool-lowering.slang119
-rw-r--r--tests/metal/matrix-integer-lowering.slang202
-rw-r--r--tests/spirv/matrix-bool-lowering.slang2
-rw-r--r--tests/spirv/matrix-integer-lowering.slang12
-rw-r--r--tests/wgsl/matrix-bool-lowering.slang114
-rw-r--r--tests/wgsl/matrix-integer-lowering.slang199
9 files changed, 961 insertions, 4 deletions
diff --git a/tests/compute/logic-no-short-circuit-evaluation.slang b/tests/compute/logic-no-short-circuit-evaluation.slang
index ea2b7a0c3..342a11f28 100644
--- a/tests/compute/logic-no-short-circuit-evaluation.slang
+++ b/tests/compute/logic-no-short-circuit-evaluation.slang
@@ -32,7 +32,7 @@ void computeMain(int3 dispatchThreadID : SV_DispatchThreadID)
//SM5:(all({{.*}}&&
//HLSL2018:(all({{.*}}&&
//SM6:(all(and(
- //WGS:(all(select(vec2<bool>(false),
+ //WGS:(all((select(vec2<bool>(false),
//MTL:(all({{.*}}&&
if (all(bool2(index >= 1) && assignFunc(index)))
{
@@ -54,7 +54,7 @@ void computeMain(int3 dispatchThreadID : SV_DispatchThreadID)
//SM5:(all({{.*}}?{{.*}}:
//HLSL2018:(all({{.*}}?{{.*}}:
//SM6:(all(select(
- //WGS:(all(select(vec2<bool>(false),
+ //WGS:(all((select(vec2<bool>(false),
//MTL:(all(select(bool2(false)
if (all(bool2(index >= 3) ? assignFunc(index) : bool2(false)))
{
diff --git a/tests/glsl/matrix-bool-lowering.slang b/tests/glsl/matrix-bool-lowering.slang
new file mode 100644
index 000000000..9f2ad913f
--- /dev/null
+++ b/tests/glsl/matrix-bool-lowering.slang
@@ -0,0 +1,114 @@
+//TEST(compute):COMPARE_COMPUTE_EX(filecheck-buffer=CHECK):-slang -compute -emit-spirv-via-glsl -shaderobj
+
+//TEST_INPUT:ubuffer(data=[1 0], stride=4):name inputBuffer
+//TEST_INPUT:ubuffer(data=[0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0], stride=4):out,name outputBuffer
+RWStructuredBuffer<int> inputBuffer;
+RWStructuredBuffer<int> outputBuffer;
+
+// Global bool constants to avoid constant folding
+static bool trueVal;
+static bool falseVal;
+
+struct matrixWrapper {
+ bool2x2 mat1 = bool2x2(falseVal, falseVal, falseVal, falseVal);
+ bool2x3 mat2 = bool2x3(trueVal, trueVal, falseVal, falseVal, falseVal, trueVal);
+}
+
+bool elementAnd(bool2x2 matrix)
+{
+ return trueVal
+ && matrix[0][0]
+ && matrix[0][1]
+ && matrix[1][0]
+ && matrix[1][1];
+}
+
+[numthreads(1, 1, 1)]
+void computeMain(uint3 dispatchThreadID : SV_DispatchThreadID)
+{
+ // Load true/false values from input buffer to avoid constant folding
+ trueVal = inputBuffer[0] != 0;
+ falseVal = inputBuffer[1] != 0;
+
+ // Test bool matrix construction
+ bool2x2 mat1 = bool2x2(trueVal, falseVal, falseVal, trueVal);
+ bool3x3 mat2 = bool3x3(
+ trueVal, falseVal, trueVal,
+ falseVal, trueVal, falseVal,
+ trueVal, falseVal, trueVal
+ );
+ bool2x4 mat3 = bool2x4(
+ trueVal, falseVal, trueVal, falseVal,
+ trueVal, falseVal, trueVal, falseVal
+ );
+
+ // Test bool matrix element access
+ bool val1 = mat1[0][0];
+ bool val2 = mat2[2][1];
+
+ // Test bool matrix row access
+ bool2 row = mat1[1];
+ bool3 row3 = mat2[0];
+
+ // Test logical operations
+ bool2x2 not_mat = !mat1;
+ bool2x2 and_mat = mat1 && bool2x2(trueVal, trueVal, falseVal, falseVal);
+
+ // Test element assignment
+ mat1[0][1] = trueVal;
+ mat2[1][2] = falseVal;
+
+ // Test passing bool matrices to functions
+ bool anded = elementAnd(mat1);
+
+ // Test structs with bool matrix fields
+ matrixWrapper wrapper = {};
+
+ // Test any/all operations
+ bool2x2 all_true = bool2x2(trueVal, trueVal, trueVal, trueVal);
+ bool2x2 all_false = bool2x2(falseVal, falseVal, falseVal, falseVal);
+ bool2x2 mixed = bool2x2(trueVal, falseVal, trueVal, falseVal);
+
+ bool test_all_true = all(all_true); // all elements true -> true
+ bool test_all_false = all(all_false); // all elements false -> false
+ bool test_all_mixed = all(mixed); // some elements false -> false
+ bool test_any_true = any(all_true); // some elements true -> true
+ bool test_any_false = any(all_false); // no elements true -> false
+ bool test_any_mixed = any(mixed); // some elements true -> true
+
+ // Store results
+ outputBuffer[0] = val1;
+ // CHECK: 1
+ outputBuffer[1] = val2;
+ // CHECK-NEXT: 0
+ outputBuffer[2] = row.x;
+ // CHECK-NEXT: 0
+ outputBuffer[3] = row.y;
+ // CHECK-NEXT: 1
+ outputBuffer[4] = row3.y;
+ // CHECK-NEXT: 0
+ outputBuffer[5] = not_mat[0][0];
+ // CHECK-NEXT: 0
+ outputBuffer[6] = and_mat[0][0];
+ // CHECK-NEXT: 1
+ outputBuffer[7] = mat1[0][1];
+ // CHECK-NEXT: 1
+ outputBuffer[8] = mat3[0][1];
+ // CHECK-NEXT: 0
+ outputBuffer[9] = anded;
+ // CHECK-NEXT: 0
+ outputBuffer[10] = wrapper.mat1[0][0] || wrapper.mat2[0][0];
+ // CHECK-NEXT: 1
+ outputBuffer[11] = test_all_true;
+ // CHECK-NEXT: 1
+ outputBuffer[12] = test_all_false;
+ // CHECK-NEXT: 0
+ outputBuffer[13] = test_all_mixed;
+ // CHECK-NEXT: 0
+ outputBuffer[14] = test_any_true;
+ // CHECK-NEXT: 1
+ outputBuffer[15] = test_any_false;
+ // CHECK-NEXT: 0
+ outputBuffer[16] = test_any_mixed;
+ // CHECK-NEXT: 1
+} \ No newline at end of file
diff --git a/tests/glsl/matrix-integer-lowering.slang b/tests/glsl/matrix-integer-lowering.slang
new file mode 100644
index 000000000..4d6033d79
--- /dev/null
+++ b/tests/glsl/matrix-integer-lowering.slang
@@ -0,0 +1,199 @@
+//TEST(compute):COMPARE_COMPUTE_EX(filecheck-buffer=CHECK):-slang -vk -output-using-type -compute -emit-spirv-via-glsl -shaderobj -xslang -DTYPE=int
+//TEST(compute):COMPARE_COMPUTE_EX(filecheck-buffer=CHECK):-slang -vk -output-using-type -compute -emit-spirv-via-glsl -shaderobj -xslang -DTYPE=uint
+
+#ifndef TYPE
+#define TYPE int
+#endif
+
+typealias m2x2 = matrix<TYPE, 2, 2>;
+typealias m2x3 = matrix<TYPE, 2, 3>;
+typealias m3x3 = matrix<TYPE, 3, 3>;
+typealias m2x4 = matrix<TYPE, 2, 4>;
+
+//TEST_INPUT:ubuffer(data=[0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0], stride=4):out,name outputBuffer
+//TEST_INPUT:ubuffer(data=[-1 4], stride=4):name expectedBuffer
+RWStructuredBuffer<TYPE> outputBuffer;
+RWStructuredBuffer<TYPE> expectedBuffer;
+
+struct matrixWrapper {
+ m2x2 mat1 = m2x2(1, 2, 3, 4);
+ m2x3 mat2 = m2x3(5, 6, 7, 8, 9, 10);
+};
+
+TYPE elementAdd(m2x2 matrix)
+{
+ return matrix[0][0]
+ + matrix[0][1]
+ + matrix[1][0]
+ + matrix[1][1];
+}
+
+[numthreads(1, 1, 1)]
+void computeMain(uint3 dispatchThreadID : SV_DispatchThreadID)
+{
+ // Test matrix construction
+ m2x2 mat1 = m2x2(1, 2, 3, 4);
+ m3x3 mat2 = m3x3(
+ 1, 2, 3,
+ 4, 5, 6,
+ 7, 8, 9
+ );
+ m2x4 mat3 = m2x4(
+ 10, 11, 12, 13,
+ 14, 15, 16, 17
+ );
+
+ // Test matrix element access
+ TYPE val1 = mat1[0][0];
+ TYPE val2 = mat2[2][1];
+
+ // Test matrix row access
+ vector<TYPE, 2> row = mat1[1];
+ vector<TYPE, 3> row3 = mat2[0];
+
+ // Test arithmetic operations
+ m2x2 mat5 = m2x2(2, 4, 6, 7);
+
+ m2x2 mat_scalar = 2 * mat1;
+ m2x2 mat_add = mat1 + mat5;
+ m2x2 mat_sub = mat5 - mat1;
+ m2x2 mat_mul = mat1 * mat5;
+
+ // Test passing matrices to functions
+ TYPE added = elementAdd(mat1);
+
+ // Test structs with matrix fields
+ matrixWrapper wrapper = {};
+
+ // Test matrix intrinsic operations
+
+ // Test determinant for square matrices
+ m2x2 mat6 = m2x2(2, 1, 4, 3);
+ TYPE det2x2 = TYPE(determinant(mat6));
+ TYPE det3x3 = TYPE(determinant(mat2));
+
+ // Test transpose
+ matrix<TYPE, 2, 2> trans2x2 = transpose(mat1);
+ matrix<TYPE, 3, 2> trans2x3 = transpose(wrapper.mat2);
+
+ // Test element-wise min/max
+ m2x2 mat_min = min(mat1, mat5);
+ m2x2 mat_max = max(mat1, mat5);
+
+ // Test all/any operations (these return bool, but we'll cast to TYPE for output)
+ m2x2 zero_mat = m2x2(0, 0, 0, 0);
+ m2x2 mixed_mat = m2x2(1, 0, 2, 0);
+
+ TYPE all_nonzero = TYPE(all(mat1));
+ TYPE all_zero = TYPE(all(zero_mat));
+ TYPE any_nonzero = TYPE(any(mixed_mat));
+ TYPE any_zero = TYPE(any(zero_mat));
+
+ // Test bit shift operations
+ m2x2 shift_mat = m2x2(1, 2, 4, 8);
+ m2x2 left_shift = shift_mat << 1;
+ m2x2 right_shift = shift_mat >> 1;
+
+ // Test comparison operations (these return bool matrices, cast to TYPE for output)
+ m2x2 comp_mat1 = m2x2(1, 3, 2, 4);
+ m2x2 comp_mat2 = m2x2(2, 2, 3, 3);
+
+ matrix<bool, 2, 2> less_than = comp_mat1 < comp_mat2;
+ matrix<bool, 2, 2> greater_than = comp_mat1 > comp_mat2;
+ matrix<bool, 2, 2> less_equal = comp_mat1 <= comp_mat2;
+ matrix<bool, 2, 2> greater_equal = comp_mat1 >= comp_mat2;
+ matrix<bool, 2, 2> equal_to = comp_mat1 == comp_mat2;
+ matrix<bool, 2, 2> not_equal = comp_mat1 != comp_mat2;
+
+ // Test matrix negation operations
+ m2x2 neg_mat = m2x2(1, -2, 3, -4);
+ m2x2 negated = -neg_mat;
+
+ // Store results
+ outputBuffer[0] = val1;
+ // CHECK: 1
+ outputBuffer[1] = val2;
+ // CHECK-NEXT: 8
+ outputBuffer[2] = row.x;
+ // CHECK-NEXT: 3
+ outputBuffer[3] = row.y;
+ // CHECK-NEXT: 4
+ outputBuffer[4] = row3.y;
+ // CHECK-NEXT: 2
+ outputBuffer[5] = mat_scalar[0][0];
+ // CHECK-NEXT: 2
+ outputBuffer[6] = mat_add[0][0];
+ // CHECK-NEXT: 3
+ outputBuffer[7] = mat_sub[0][0];
+ // CHECK-NEXT: 1
+ outputBuffer[8] = mat_mul[1][1];
+ // CHECK-NEXT: 28
+ outputBuffer[9] = added;
+ // CHECK-NEXT: 10
+ outputBuffer[10] = wrapper.mat1[0][0] * wrapper.mat2[0][0];
+ // CHECK-NEXT: 5
+
+ // Matrix intrinsic operation results
+ outputBuffer[11] = det2x2;
+ // CHECK-NEXT: 2
+ outputBuffer[12] = det3x3;
+ // CHECK-NEXT: 0
+ outputBuffer[13] = mat_min[0][0];
+ // CHECK-NEXT: 1
+ outputBuffer[14] = mat_min[1][1];
+ // CHECK-NEXT: 4
+ outputBuffer[15] = mat_max[0][0];
+ // CHECK-NEXT: 2
+ outputBuffer[16] = mat_max[1][1];
+ // CHECK-NEXT: 7
+ outputBuffer[17] = all_nonzero;
+ // CHECK-NEXT: 1
+ outputBuffer[18] = all_zero;
+ // CHECK-NEXT: 0
+ outputBuffer[19] = any_nonzero;
+ // CHECK-NEXT: 1
+ outputBuffer[20] = any_zero;
+ // CHECK-NEXT: 0
+ outputBuffer[21] = trans2x2[0][0];
+ // CHECK-NEXT: 1
+ outputBuffer[22] = trans2x2[1][0];
+ // CHECK-NEXT: 2
+ outputBuffer[23] = trans2x3[0][0];
+ // CHECK-NEXT: 5
+
+ // Bit shift operation results
+ outputBuffer[24] = left_shift[0][0];
+ // CHECK-NEXT: 2
+ outputBuffer[25] = left_shift[0][1];
+ // CHECK-NEXT: 4
+ outputBuffer[26] = right_shift[1][0];
+ // CHECK-NEXT: 2
+ outputBuffer[27] = right_shift[1][1];
+ // CHECK-NEXT: 4
+
+ // Comparison operation results (bool matrices cast to TYPE)
+ outputBuffer[28] = TYPE(less_than[0][0]);
+ // CHECK-NEXT: 1
+ outputBuffer[29] = TYPE(less_than[0][1]);
+ // CHECK-NEXT: 0
+ outputBuffer[30] = TYPE(greater_than[0][1]);
+ // CHECK-NEXT: 1
+ outputBuffer[31] = TYPE(greater_than[1][1]);
+ // CHECK-NEXT: 1
+ outputBuffer[32] = TYPE(less_equal[0][0]);
+ // CHECK-NEXT: 1
+ outputBuffer[33] = TYPE(less_equal[0][1]);
+ // CHECK-NEXT: 0
+ outputBuffer[34] = TYPE(greater_equal[0][1]);
+ // CHECK-NEXT: 1
+ outputBuffer[35] = TYPE(greater_equal[1][0]);
+ // CHECK-NEXT: 0
+ outputBuffer[36] = TYPE(equal_to[0][0]);
+ // CHECK-NEXT: 0
+ outputBuffer[37] = TYPE(not_equal[0][0]);
+ // CHECK-NEXT: 1
+ outputBuffer[38] = TYPE(negated[0][0] == expectedBuffer[0]);
+ // CHECK-NEXT: 1
+ outputBuffer[39] = TYPE(negated[1][1] == expectedBuffer[1]);
+ // CHECK-NEXT: 1
+} \ No newline at end of file
diff --git a/tests/metal/matrix-bool-lowering.slang b/tests/metal/matrix-bool-lowering.slang
new file mode 100644
index 000000000..4248bb573
--- /dev/null
+++ b/tests/metal/matrix-bool-lowering.slang
@@ -0,0 +1,119 @@
+//TEST:SIMPLE(filecheck=METAL): -target metal -stage compute -entry computeMain
+//TEST:SIMPLE(filecheck=METALLIB): -target metallib -stage compute -entry computeMain
+//TEST(compute):COMPARE_COMPUTE_EX(filecheck-buffer=CHECK):-slang -compute -mtl -shaderobj
+
+//TEST_INPUT:ubuffer(data=[1 0], stride=4):name inputBuffer
+//TEST_INPUT:ubuffer(data=[0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0], stride=4):out,name outputBuffer
+RWStructuredBuffer<int> inputBuffer;
+RWStructuredBuffer<int> outputBuffer;
+
+// Global bool constants to avoid constant folding
+static bool trueVal;
+static bool falseVal;
+
+struct matrixWrapper {
+ bool2x2 mat1 = bool2x2(falseVal, falseVal, falseVal, falseVal);
+ bool2x3 mat2 = bool2x3(trueVal, trueVal, falseVal, falseVal, falseVal, trueVal);
+}
+
+bool elementAnd(bool2x2 matrix)
+{
+ return trueVal
+ && matrix[0][0]
+ && matrix[0][1]
+ && matrix[1][0]
+ && matrix[1][1];
+}
+
+// METAL: array<bool2, int(2)>
+// METALLIB: @computeMain
+
+[numthreads(1, 1, 1)]
+void computeMain(uint3 dispatchThreadID : SV_DispatchThreadID)
+{
+ // Load true/false values from input buffer to avoid constant folding
+ trueVal = inputBuffer[0] != 0;
+ falseVal = inputBuffer[1] != 0;
+
+ // Test bool matrix construction
+ bool2x2 mat1 = bool2x2(trueVal, falseVal, falseVal, trueVal);
+ bool3x3 mat2 = bool3x3(
+ trueVal, falseVal, trueVal,
+ falseVal, trueVal, falseVal,
+ trueVal, falseVal, trueVal
+ );
+ bool2x4 mat3 = bool2x4(
+ trueVal, falseVal, trueVal, falseVal,
+ trueVal, falseVal, trueVal, falseVal
+ );
+
+ // Test bool matrix element access
+ bool val1 = mat1[0][0];
+ bool val2 = mat2[2][1];
+
+ // Test bool matrix row access
+ bool2 row = mat1[1];
+ bool3 row3 = mat2[0];
+
+ // Test logical operations
+ bool2x2 not_mat = !mat1;
+ bool2x2 and_mat = mat1 && bool2x2(trueVal, trueVal, falseVal, falseVal);
+
+ // Test element assignment
+ mat1[0][1] = trueVal;
+ mat2[1][2] = falseVal;
+
+ // Test passing bool matrices to functions
+ bool anded = elementAnd(mat1);
+
+ // Test structs with bool matrix fields
+ matrixWrapper wrapper = {};
+
+ // Test any/all operations
+ bool2x2 all_true = bool2x2(trueVal, trueVal, trueVal, trueVal);
+ bool2x2 all_false = bool2x2(falseVal, falseVal, falseVal, falseVal);
+ bool2x2 mixed = bool2x2(trueVal, falseVal, trueVal, falseVal);
+
+ bool test_all_true = all(all_true); // all elements true -> true
+ bool test_all_false = all(all_false); // all elements false -> false
+ bool test_all_mixed = all(mixed); // some elements false -> false
+ bool test_any_true = any(all_true); // some elements true -> true
+ bool test_any_false = any(all_false); // no elements true -> false
+ bool test_any_mixed = any(mixed); // some elements true -> true
+
+ // Store results
+ outputBuffer[0] = val1;
+ // CHECK: 1
+ outputBuffer[1] = val2;
+ // CHECK-NEXT: 0
+ outputBuffer[2] = row.x;
+ // CHECK-NEXT: 0
+ outputBuffer[3] = row.y;
+ // CHECK-NEXT: 1
+ outputBuffer[4] = row3.y;
+ // CHECK-NEXT: 0
+ outputBuffer[5] = not_mat[0][0];
+ // CHECK-NEXT: 0
+ outputBuffer[6] = and_mat[0][0];
+ // CHECK-NEXT: 1
+ outputBuffer[7] = mat1[0][1];
+ // CHECK-NEXT: 1
+ outputBuffer[8] = mat3[0][1];
+ // CHECK-NEXT: 0
+ outputBuffer[9] = anded;
+ // CHECK-NEXT: 0
+ outputBuffer[10] = wrapper.mat1[0][0] || wrapper.mat2[0][0];
+ // CHECK-NEXT: 1
+ outputBuffer[11] = test_all_true;
+ // CHECK-NEXT: 1
+ outputBuffer[12] = test_all_false;
+ // CHECK-NEXT: 0
+ outputBuffer[13] = test_all_mixed;
+ // CHECK-NEXT: 0
+ outputBuffer[14] = test_any_true;
+ // CHECK-NEXT: 1
+ outputBuffer[15] = test_any_false;
+ // CHECK-NEXT: 0
+ outputBuffer[16] = test_any_mixed;
+ // CHECK-NEXT: 1
+} \ No newline at end of file
diff --git a/tests/metal/matrix-integer-lowering.slang b/tests/metal/matrix-integer-lowering.slang
new file mode 100644
index 000000000..04aec5a7c
--- /dev/null
+++ b/tests/metal/matrix-integer-lowering.slang
@@ -0,0 +1,202 @@
+//TEST:SIMPLE(filecheck=METAL): -target metal -stage compute -entry computeMain -DTYPE=int
+//TEST:SIMPLE(filecheck=METALLIB): -target metallib -stage compute -entry computeMain -DTYPE=int
+//TEST(compute):COMPARE_COMPUTE_EX(filecheck-buffer=CHECK):-slang -output-using-type -compute -mtl -shaderobj -xslang -DTYPE=int
+//TEST(compute):COMPARE_COMPUTE_EX(filecheck-buffer=CHECK):-slang -output-using-type -compute -mtl -shaderobj -xslang -DTYPE=uint
+
+#ifndef TYPE
+#define TYPE int
+#endif
+
+typealias m2x2 = matrix<TYPE, 2, 2>;
+typealias m2x3 = matrix<TYPE, 2, 3>;
+typealias m3x3 = matrix<TYPE, 3, 3>;
+typealias m2x4 = matrix<TYPE, 2, 4>;
+
+//TEST_INPUT:ubuffer(data=[0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0], stride=4):out,name outputBuffer
+//TEST_INPUT:ubuffer(data=[-1 4], stride=4):name expectedBuffer
+RWStructuredBuffer<TYPE> outputBuffer;
+RWStructuredBuffer<TYPE> expectedBuffer;
+
+struct matrixWrapper {
+ m2x2 mat1 = m2x2(1, 2, 3, 4);
+ m2x3 mat2 = m2x3(5, 6, 7, 8, 9, 10);
+};
+
+TYPE elementAdd(m2x2 matrix)
+{
+ return matrix[0][0]
+ + matrix[0][1]
+ + matrix[1][0]
+ + matrix[1][1];
+}
+
+// METAL: array<{{(int|uint)}}2, int(2)>
+// METALLIB: @computeMain
+
+[numthreads(1, 1, 1)]
+void computeMain(uint3 dispatchThreadID : SV_DispatchThreadID)
+{
+ // Test matrix construction
+ m2x2 mat1 = m2x2(1, 2, 3, 4);
+ m3x3 mat2 = m3x3(
+ 1, 2, 3,
+ 4, 5, 6,
+ 7, 8, 9
+ );
+ m2x4 mat3 = m2x4(
+ 10, 11, 12, 13,
+ 14, 15, 16, 17
+ );
+
+ // Test matrix element access
+ TYPE val1 = mat1[0][0];
+ TYPE val2 = mat2[2][1];
+
+ // Test matrix row access
+ vector<TYPE, 2> row = mat1[1];
+ vector<TYPE, 3> row3 = mat2[0];
+
+ // Test arithmetic operations
+ m2x2 mat5 = m2x2(2, 4, 6, 7);
+
+ m2x2 mat_scalar = 2 * mat1;
+ m2x2 mat_add = mat1 + mat5;
+ m2x2 mat_sub = mat5 - mat1;
+ m2x2 mat_mul = mat1 * mat5;
+
+ // Test passing matrices to functions
+ TYPE added = elementAdd(mat1);
+
+ // Test structs with matrix fields
+ matrixWrapper wrapper = {};
+
+ // Test matrix intrinsic operations
+
+ // Test determinant for square matrices
+ m2x2 mat6 = m2x2(2, 1, 4, 3);
+ TYPE det2x2 = TYPE(determinant(mat6));
+ TYPE det3x3 = TYPE(determinant(mat2));
+
+ // Test transpose
+ matrix<TYPE, 2, 2> trans2x2 = transpose(mat1);
+ matrix<TYPE, 3, 2> trans2x3 = transpose(wrapper.mat2);
+
+ // Test element-wise min/max
+ m2x2 mat_min = min(mat1, mat5);
+ m2x2 mat_max = max(mat1, mat5);
+
+ // Test all/any operations (these return bool, but we'll cast to TYPE for output)
+ m2x2 zero_mat = m2x2(0, 0, 0, 0);
+ m2x2 mixed_mat = m2x2(1, 0, 2, 0);
+
+ TYPE all_nonzero = TYPE(all(mat1));
+ TYPE all_zero = TYPE(all(zero_mat));
+ TYPE any_nonzero = TYPE(any(mixed_mat));
+ TYPE any_zero = TYPE(any(zero_mat));
+
+ // Test bit shift operations
+ m2x2 shift_mat = m2x2(1, 2, 4, 8);
+ m2x2 left_shift = shift_mat << 1;
+ m2x2 right_shift = shift_mat >> 1;
+
+ // Test comparison operations (these return bool matrices, cast to TYPE for output)
+ m2x2 comp_mat1 = m2x2(1, 3, 2, 4);
+ m2x2 comp_mat2 = m2x2(2, 2, 3, 3);
+
+ matrix<bool, 2, 2> less_than = comp_mat1 < comp_mat2;
+ matrix<bool, 2, 2> greater_than = comp_mat1 > comp_mat2;
+ matrix<bool, 2, 2> less_equal = comp_mat1 <= comp_mat2;
+ matrix<bool, 2, 2> greater_equal = comp_mat1 >= comp_mat2;
+ matrix<bool, 2, 2> equal_to = comp_mat1 == comp_mat2;
+ matrix<bool, 2, 2> not_equal = comp_mat1 != comp_mat2;
+
+ // Test matrix negation operations
+ m2x2 neg_mat = m2x2(1, -2, 3, -4);
+ m2x2 negated = -neg_mat;
+
+ // Store results
+ outputBuffer[0] = val1;
+ // CHECK: 1
+ outputBuffer[1] = val2;
+ // CHECK-NEXT: 8
+ outputBuffer[2] = row.x;
+ // CHECK-NEXT: 3
+ outputBuffer[3] = row.y;
+ // CHECK-NEXT: 4
+ outputBuffer[4] = row3.y;
+ // CHECK-NEXT: 2
+ outputBuffer[5] = mat_scalar[0][0];
+ // CHECK-NEXT: 2
+ outputBuffer[6] = mat_add[0][0];
+ // CHECK-NEXT: 3
+ outputBuffer[7] = mat_sub[0][0];
+ // CHECK-NEXT: 1
+ outputBuffer[8] = mat_mul[1][1];
+ // CHECK-NEXT: 28
+ outputBuffer[9] = added;
+ // CHECK-NEXT: 10
+ outputBuffer[10] = wrapper.mat1[0][0] * wrapper.mat2[0][0];
+ // CHECK-NEXT: 5
+
+ // Matrix intrinsic operation results
+ outputBuffer[11] = det2x2;
+ // CHECK-NEXT: 2
+ outputBuffer[12] = det3x3;
+ // CHECK-NEXT: 0
+ outputBuffer[13] = mat_min[0][0];
+ // CHECK-NEXT: 1
+ outputBuffer[14] = mat_min[1][1];
+ // CHECK-NEXT: 4
+ outputBuffer[15] = mat_max[0][0];
+ // CHECK-NEXT: 2
+ outputBuffer[16] = mat_max[1][1];
+ // CHECK-NEXT: 7
+ outputBuffer[17] = all_nonzero;
+ // CHECK-NEXT: 1
+ outputBuffer[18] = all_zero;
+ // CHECK-NEXT: 0
+ outputBuffer[19] = any_nonzero;
+ // CHECK-NEXT: 1
+ outputBuffer[20] = any_zero;
+ // CHECK-NEXT: 0
+ outputBuffer[21] = trans2x2[0][0];
+ // CHECK-NEXT: 1
+ outputBuffer[22] = trans2x2[1][0];
+ // CHECK-NEXT: 2
+ outputBuffer[23] = trans2x3[0][0];
+ // CHECK-NEXT: 5
+
+ // Bit shift operation results
+ outputBuffer[24] = left_shift[0][0];
+ // CHECK-NEXT: 2
+ outputBuffer[25] = left_shift[0][1];
+ // CHECK-NEXT: 4
+ outputBuffer[26] = right_shift[1][0];
+ // CHECK-NEXT: 2
+ outputBuffer[27] = right_shift[1][1];
+ // CHECK-NEXT: 4
+
+ // Comparison operation results (bool matrices cast to TYPE)
+ outputBuffer[28] = TYPE(less_than[0][0]);
+ // CHECK-NEXT: 1
+ outputBuffer[29] = TYPE(less_than[0][1]);
+ // CHECK-NEXT: 0
+ outputBuffer[30] = TYPE(greater_than[0][1]);
+ // CHECK-NEXT: 1
+ outputBuffer[31] = TYPE(greater_than[1][1]);
+ // CHECK-NEXT: 1
+ outputBuffer[32] = TYPE(less_equal[0][0]);
+ // CHECK-NEXT: 1
+ outputBuffer[33] = TYPE(less_equal[0][1]);
+ // CHECK-NEXT: 0
+ outputBuffer[34] = TYPE(greater_equal[0][1]);
+ // CHECK-NEXT: 1
+ outputBuffer[35] = TYPE(greater_equal[1][0]);
+ // CHECK-NEXT: 0
+ outputBuffer[36] = TYPE(equal_to[0][0]);
+ // CHECK-NEXT: 0
+ outputBuffer[37] = TYPE(negated[0][0] == expectedBuffer[0]);
+ // CHECK-NEXT: 1
+ outputBuffer[38] = TYPE(negated[1][1] == expectedBuffer[1]);
+ // CHECK-NEXT: 1
+} \ No newline at end of file
diff --git a/tests/spirv/matrix-bool-lowering.slang b/tests/spirv/matrix-bool-lowering.slang
index 63b7caacf..f903fbf17 100644
--- a/tests/spirv/matrix-bool-lowering.slang
+++ b/tests/spirv/matrix-bool-lowering.slang
@@ -1,6 +1,6 @@
//TEST(compute):COMPARE_COMPUTE_EX(filecheck-buffer=CHECK):-slang -compute -vk -shaderobj -xslang -emit-spirv-directly
-//TEST_INPUT:ubuffer(data=[1 0], stride=4):in,name inputBuffer
+//TEST_INPUT:ubuffer(data=[1 0], stride=4):name inputBuffer
//TEST_INPUT:ubuffer(data=[0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0], stride=4):out,name outputBuffer
RWStructuredBuffer<int> inputBuffer;
RWStructuredBuffer<int> outputBuffer;
diff --git a/tests/spirv/matrix-integer-lowering.slang b/tests/spirv/matrix-integer-lowering.slang
index 518d0f78b..fded652a4 100644
--- a/tests/spirv/matrix-integer-lowering.slang
+++ b/tests/spirv/matrix-integer-lowering.slang
@@ -10,8 +10,10 @@ typealias m2x3 = matrix<TYPE, 2, 3>;
typealias m3x3 = matrix<TYPE, 3, 3>;
typealias m2x4 = matrix<TYPE, 2, 4>;
-//TEST_INPUT:ubuffer(data=[0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0], stride=4):out,name outputBuffer
+//TEST_INPUT:ubuffer(data=[0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0], stride=4):out,name outputBuffer
+//TEST_INPUT:ubuffer(data=[-1 4], stride=4):name expectedBuffer
RWStructuredBuffer<TYPE> outputBuffer;
+RWStructuredBuffer<TYPE> expectedBuffer;
struct matrixWrapper {
m2x2 mat1 = m2x2(1, 2, 3, 4);
@@ -103,6 +105,10 @@ void computeMain(uint3 dispatchThreadID : SV_DispatchThreadID)
matrix<bool, 2, 2> equal_to = comp_mat1 == comp_mat2;
matrix<bool, 2, 2> not_equal = comp_mat1 != comp_mat2;
+ // Test matrix negation operations
+ m2x2 neg_mat = m2x2(1, -2, 3, -4);
+ m2x2 negated = -neg_mat;
+
// Store results
outputBuffer[0] = val1;
// CHECK: 1
@@ -186,4 +192,8 @@ void computeMain(uint3 dispatchThreadID : SV_DispatchThreadID)
// CHECK-NEXT: 0
outputBuffer[37] = TYPE(not_equal[0][0]);
// CHECK-NEXT: 1
+ outputBuffer[38] = TYPE(negated[0][0] == expectedBuffer[0]);
+ // CHECK-NEXT: 1
+ outputBuffer[39] = TYPE(negated[1][1] == expectedBuffer[1]);
+ // CHECK-NEXT: 1
} \ No newline at end of file
diff --git a/tests/wgsl/matrix-bool-lowering.slang b/tests/wgsl/matrix-bool-lowering.slang
new file mode 100644
index 000000000..4803fa73a
--- /dev/null
+++ b/tests/wgsl/matrix-bool-lowering.slang
@@ -0,0 +1,114 @@
+//TEST(compute):COMPARE_COMPUTE_EX(filecheck-buffer=CHECK):-slang -compute -wgsl -shaderobj
+
+//TEST_INPUT:ubuffer(data=[1 0], stride=4):name inputBuffer
+//TEST_INPUT:ubuffer(data=[0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0], stride=4):out,name outputBuffer
+RWStructuredBuffer<int> inputBuffer;
+RWStructuredBuffer<int> outputBuffer;
+
+// Global bool constants to avoid constant folding
+static bool trueVal;
+static bool falseVal;
+
+struct matrixWrapper {
+ bool2x2 mat1 = bool2x2(falseVal, falseVal, falseVal, falseVal);
+ bool2x3 mat2 = bool2x3(trueVal, trueVal, falseVal, falseVal, falseVal, trueVal);
+}
+
+bool elementAnd(bool2x2 matrix)
+{
+ return trueVal
+ && matrix[0][0]
+ && matrix[0][1]
+ && matrix[1][0]
+ && matrix[1][1];
+}
+
+[numthreads(1, 1, 1)]
+void computeMain(uint3 dispatchThreadID : SV_DispatchThreadID)
+{
+ // Load true/false values from input buffer to avoid constant folding
+ trueVal = inputBuffer[0] != 0;
+ falseVal = inputBuffer[1] != 0;
+
+ // Test bool matrix construction
+ bool2x2 mat1 = bool2x2(trueVal, falseVal, falseVal, trueVal);
+ bool3x3 mat2 = bool3x3(
+ trueVal, falseVal, trueVal,
+ falseVal, trueVal, falseVal,
+ trueVal, falseVal, trueVal
+ );
+ bool2x4 mat3 = bool2x4(
+ trueVal, falseVal, trueVal, falseVal,
+ trueVal, falseVal, trueVal, falseVal
+ );
+
+ // Test bool matrix element access
+ bool val1 = mat1[0][0];
+ bool val2 = mat2[2][1];
+
+ // Test bool matrix row access
+ bool2 row = mat1[1];
+ bool3 row3 = mat2[0];
+
+ // Test logical operations
+ bool2x2 not_mat = !mat1;
+ bool2x2 and_mat = mat1 && bool2x2(trueVal, trueVal, falseVal, falseVal);
+
+ // Test element assignment
+ mat1[0][1] = trueVal;
+ mat2[1][2] = falseVal;
+
+ // Test passing bool matrices to functions
+ bool anded = elementAnd(mat1);
+
+ // Test structs with bool matrix fields
+ matrixWrapper wrapper = {};
+
+ // Test any/all operations
+ bool2x2 all_true = bool2x2(trueVal, trueVal, trueVal, trueVal);
+ bool2x2 all_false = bool2x2(falseVal, falseVal, falseVal, falseVal);
+ bool2x2 mixed = bool2x2(trueVal, falseVal, trueVal, falseVal);
+
+ bool test_all_true = all(all_true); // all elements true -> true
+ bool test_all_false = all(all_false); // all elements false -> false
+ bool test_all_mixed = all(mixed); // some elements false -> false
+ bool test_any_true = any(all_true); // some elements true -> true
+ bool test_any_false = any(all_false); // no elements true -> false
+ bool test_any_mixed = any(mixed); // some elements true -> true
+
+ // Store results
+ outputBuffer[0] = val1;
+ // CHECK: 1
+ outputBuffer[1] = val2;
+ // CHECK-NEXT: 0
+ outputBuffer[2] = row.x;
+ // CHECK-NEXT: 0
+ outputBuffer[3] = row.y;
+ // CHECK-NEXT: 1
+ outputBuffer[4] = row3.y;
+ // CHECK-NEXT: 0
+ outputBuffer[5] = not_mat[0][0];
+ // CHECK-NEXT: 0
+ outputBuffer[6] = and_mat[0][0];
+ // CHECK-NEXT: 1
+ outputBuffer[7] = mat1[0][1];
+ // CHECK-NEXT: 1
+ outputBuffer[8] = mat3[0][1];
+ // CHECK-NEXT: 0
+ outputBuffer[9] = anded;
+ // CHECK-NEXT: 0
+ outputBuffer[10] = wrapper.mat1[0][0] || wrapper.mat2[0][0];
+ // CHECK-NEXT: 1
+ outputBuffer[11] = test_all_true;
+ // CHECK-NEXT: 1
+ outputBuffer[12] = test_all_false;
+ // CHECK-NEXT: 0
+ outputBuffer[13] = test_all_mixed;
+ // CHECK-NEXT: 0
+ outputBuffer[14] = test_any_true;
+ // CHECK-NEXT: 1
+ outputBuffer[15] = test_any_false;
+ // CHECK-NEXT: 0
+ outputBuffer[16] = test_any_mixed;
+ // CHECK-NEXT: 1
+} \ No newline at end of file
diff --git a/tests/wgsl/matrix-integer-lowering.slang b/tests/wgsl/matrix-integer-lowering.slang
new file mode 100644
index 000000000..fc2a64382
--- /dev/null
+++ b/tests/wgsl/matrix-integer-lowering.slang
@@ -0,0 +1,199 @@
+//TEST(compute):COMPARE_COMPUTE_EX(filecheck-buffer=CHECK):-slang -output-using-type -compute -wgsl -shaderobj -xslang -DTYPE=int
+//TEST(compute):COMPARE_COMPUTE_EX(filecheck-buffer=CHECK):-slang -output-using-type -compute -wgsl -shaderobj -xslang -DTYPE=uint
+
+#ifndef TYPE
+#define TYPE int
+#endif
+
+typealias m2x2 = matrix<TYPE, 2, 2>;
+typealias m2x3 = matrix<TYPE, 2, 3>;
+typealias m3x3 = matrix<TYPE, 3, 3>;
+typealias m2x4 = matrix<TYPE, 2, 4>;
+
+//TEST_INPUT:ubuffer(data=[0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0], stride=4):out,name outputBuffer
+//TEST_INPUT:ubuffer(data=[-1 4], stride=4):name expectedBuffer
+RWStructuredBuffer<TYPE> outputBuffer;
+RWStructuredBuffer<TYPE> expectedBuffer;
+
+struct matrixWrapper {
+ m2x2 mat1 = m2x2(1, 2, 3, 4);
+ m2x3 mat2 = m2x3(5, 6, 7, 8, 9, 10);
+};
+
+TYPE elementAdd(m2x2 matrix)
+{
+ return matrix[0][0]
+ + matrix[0][1]
+ + matrix[1][0]
+ + matrix[1][1];
+}
+
+[numthreads(1, 1, 1)]
+void computeMain(uint3 dispatchThreadID : SV_DispatchThreadID)
+{
+ // Test matrix construction
+ m2x2 mat1 = m2x2(1, 2, 3, 4);
+ m3x3 mat2 = m3x3(
+ 1, 2, 3,
+ 4, 5, 6,
+ 7, 8, 9
+ );
+ m2x4 mat3 = m2x4(
+ 10, 11, 12, 13,
+ 14, 15, 16, 17
+ );
+
+ // Test matrix element access
+ TYPE val1 = mat1[0][0];
+ TYPE val2 = mat2[2][1];
+
+ // Test matrix row access
+ vector<TYPE, 2> row = mat1[1];
+ vector<TYPE, 3> row3 = mat2[0];
+
+ // Test arithmetic operations
+ m2x2 mat5 = m2x2(2, 4, 6, 7);
+
+ m2x2 mat_scalar = 2 * mat1;
+ m2x2 mat_add = mat1 + mat5;
+ m2x2 mat_sub = mat5 - mat1;
+ m2x2 mat_mul = mat1 * mat5;
+
+ // Test passing matrices to functions
+ TYPE added = elementAdd(mat1);
+
+ // Test structs with matrix fields
+ matrixWrapper wrapper = {};
+
+ // Test matrix intrinsic operations
+
+ // Test determinant for square matrices
+ m2x2 mat6 = m2x2(2, 1, 4, 3);
+ TYPE det2x2 = TYPE(determinant(mat6));
+ TYPE det3x3 = TYPE(determinant(mat2));
+
+ // Test transpose
+ matrix<TYPE, 2, 2> trans2x2 = transpose(mat1);
+ matrix<TYPE, 3, 2> trans2x3 = transpose(wrapper.mat2);
+
+ // Test element-wise min/max
+ m2x2 mat_min = min(mat1, mat5);
+ m2x2 mat_max = max(mat1, mat5);
+
+ // Test all/any operations (these return bool, but we'll cast to TYPE for output)
+ m2x2 zero_mat = m2x2(0, 0, 0, 0);
+ m2x2 mixed_mat = m2x2(1, 0, 2, 0);
+
+ TYPE all_nonzero = TYPE(all(mat1));
+ TYPE all_zero = TYPE(all(zero_mat));
+ TYPE any_nonzero = TYPE(any(mixed_mat));
+ TYPE any_zero = TYPE(any(zero_mat));
+
+ // Test bit shift operations
+ m2x2 shift_mat = m2x2(1, 2, 4, 8);
+ m2x2 left_shift = shift_mat << 1;
+ m2x2 right_shift = shift_mat >> 1;
+
+ // Test comparison operations (these return bool matrices, cast to TYPE for output)
+ m2x2 comp_mat1 = m2x2(1, 3, 2, 4);
+ m2x2 comp_mat2 = m2x2(2, 2, 3, 3);
+
+ matrix<bool, 2, 2> less_than = comp_mat1 < comp_mat2;
+ matrix<bool, 2, 2> greater_than = comp_mat1 > comp_mat2;
+ matrix<bool, 2, 2> less_equal = comp_mat1 <= comp_mat2;
+ matrix<bool, 2, 2> greater_equal = comp_mat1 >= comp_mat2;
+ matrix<bool, 2, 2> equal_to = comp_mat1 == comp_mat2;
+ matrix<bool, 2, 2> not_equal = comp_mat1 != comp_mat2;
+
+ // Test matrix negation operations
+ m2x2 neg_mat = m2x2(1, -2, 3, -4);
+ m2x2 negated = -neg_mat;
+
+ // Store results
+ outputBuffer[0] = val1;
+ // CHECK: 1
+ outputBuffer[1] = val2;
+ // CHECK-NEXT: 8
+ outputBuffer[2] = row.x;
+ // CHECK-NEXT: 3
+ outputBuffer[3] = row.y;
+ // CHECK-NEXT: 4
+ outputBuffer[4] = row3.y;
+ // CHECK-NEXT: 2
+ outputBuffer[5] = mat_scalar[0][0];
+ // CHECK-NEXT: 2
+ outputBuffer[6] = mat_add[0][0];
+ // CHECK-NEXT: 3
+ outputBuffer[7] = mat_sub[0][0];
+ // CHECK-NEXT: 1
+ outputBuffer[8] = mat_mul[1][1];
+ // CHECK-NEXT: 28
+ outputBuffer[9] = added;
+ // CHECK-NEXT: 10
+ outputBuffer[10] = wrapper.mat1[0][0] * wrapper.mat2[0][0];
+ // CHECK-NEXT: 5
+
+ // Matrix intrinsic operation results
+ outputBuffer[11] = det2x2;
+ // CHECK-NEXT: 2
+ outputBuffer[12] = det3x3;
+ // CHECK-NEXT: 0
+ outputBuffer[13] = mat_min[0][0];
+ // CHECK-NEXT: 1
+ outputBuffer[14] = mat_min[1][1];
+ // CHECK-NEXT: 4
+ outputBuffer[15] = mat_max[0][0];
+ // CHECK-NEXT: 2
+ outputBuffer[16] = mat_max[1][1];
+ // CHECK-NEXT: 7
+ outputBuffer[17] = all_nonzero;
+ // CHECK-NEXT: 1
+ outputBuffer[18] = all_zero;
+ // CHECK-NEXT: 0
+ outputBuffer[19] = any_nonzero;
+ // CHECK-NEXT: 1
+ outputBuffer[20] = any_zero;
+ // CHECK-NEXT: 0
+ outputBuffer[21] = trans2x2[0][0];
+ // CHECK-NEXT: 1
+ outputBuffer[22] = trans2x2[1][0];
+ // CHECK-NEXT: 2
+ outputBuffer[23] = trans2x3[0][0];
+ // CHECK-NEXT: 5
+
+ // Bit shift operation results
+ outputBuffer[24] = left_shift[0][0];
+ // CHECK-NEXT: 2
+ outputBuffer[25] = left_shift[0][1];
+ // CHECK-NEXT: 4
+ outputBuffer[26] = right_shift[1][0];
+ // CHECK-NEXT: 2
+ outputBuffer[27] = right_shift[1][1];
+ // CHECK-NEXT: 4
+
+ // Comparison operation results (bool matrices cast to TYPE)
+ outputBuffer[28] = TYPE(less_than[0][0]);
+ // CHECK-NEXT: 1
+ outputBuffer[29] = TYPE(less_than[0][1]);
+ // CHECK-NEXT: 0
+ outputBuffer[30] = TYPE(greater_than[0][1]);
+ // CHECK-NEXT: 1
+ outputBuffer[31] = TYPE(greater_than[1][1]);
+ // CHECK-NEXT: 1
+ outputBuffer[32] = TYPE(less_equal[0][0]);
+ // CHECK-NEXT: 1
+ outputBuffer[33] = TYPE(less_equal[0][1]);
+ // CHECK-NEXT: 0
+ outputBuffer[34] = TYPE(greater_equal[0][1]);
+ // CHECK-NEXT: 1
+ outputBuffer[35] = TYPE(greater_equal[1][0]);
+ // CHECK-NEXT: 0
+ outputBuffer[36] = TYPE(equal_to[0][0]);
+ // CHECK-NEXT: 0
+ outputBuffer[37] = TYPE(not_equal[0][0]);
+ // CHECK-NEXT: 1
+ outputBuffer[38] = TYPE(negated[0][0] == expectedBuffer[0]);
+ // CHECK-NEXT: 1
+ outputBuffer[39] = TYPE(negated[1][1] == expectedBuffer[1]);
+ // CHECK-NEXT: 1
+} \ No newline at end of file