@@ -258,6 +258,48 @@ TEST_F(VulkanComputeAPITest, calculate_tensor_strides_test) {
258
258
}
259
259
}
260
260
261
+ TEST_F (VulkanComputeAPITest, virtual_transpose_test) {
262
+ std::vector<int64_t > sizes = {7 , 9 , 11 , 13 };
263
+ // (dim0, dim1), new_sizes, new_dim_order, new_axis_map, new_packed_dim_idx
264
+ std::vector<std::vector<std::vector<int64_t >>> test_cases = {
265
+ {{2 , 3 }, {7 , 9 , 13 , 11 }, {0 , 1 , 3 , 2 }, {1 , 0 , 2 , 2 }, {1 }},
266
+ {{2 , 1 }, {7 , 11 , 9 , 13 }, {0 , 2 , 1 , 3 }, {0 , 2 , 1 , 2 }, {0 }},
267
+ {{1 , 3 }, {7 , 13 , 11 , 9 }, {0 , 3 , 2 , 1 }, {2 , 1 , 0 , 2 }, {2 }},
268
+ };
269
+
270
+ for (const auto & test_case : test_cases) {
271
+ const int dim0 = test_case.at (0 ).at (0 );
272
+ const int dim1 = test_case.at (0 ).at (1 );
273
+
274
+ const auto & expected_sizes = test_case.at (1 );
275
+ const auto & expected_dim_order = test_case.at (2 );
276
+ const auto & expected_axis_map = test_case.at (3 );
277
+ const int expected_packed_dim = test_case.at (4 ).at (0 );
278
+
279
+ {
280
+ vTensor a_buffer = vTensor (
281
+ context (), sizes, vkapi::kFloat , utils::kBuffer , utils::kWidthPacked );
282
+
283
+ a_buffer.virtual_transpose (dim0, dim1);
284
+ EXPECT_TRUE (a_buffer.sizes () == expected_sizes);
285
+ EXPECT_TRUE (a_buffer.dim_order () == expected_dim_order);
286
+ }
287
+
288
+ {
289
+ vTensor a_texture = vTensor (
290
+ context (),
291
+ sizes,
292
+ vkapi::kFloat ,
293
+ utils::kTexture3D ,
294
+ utils::kWidthPacked );
295
+ a_texture.virtual_transpose (dim0, dim1);
296
+ EXPECT_TRUE (a_texture.sizes () == expected_sizes);
297
+ EXPECT_TRUE (a_texture.axis_map () == expected_axis_map);
298
+ EXPECT_TRUE (a_texture.packed_dim_whcn_idx () == expected_packed_dim);
299
+ }
300
+ }
301
+ }
302
+
261
303
TEST_F (VulkanComputeAPITest, vec_test) {
262
304
utils::vec3 v3 ({1 , 2 , 3 });
263
305
ASSERT_TRUE (v3[0 ] == 1 );
@@ -637,46 +679,60 @@ TEST_F(VulkanComputeAPITest, tensor_no_copy_transpose_test) {
637
679
constexpr int N = 17 ;
638
680
std::vector<int64_t > mat1_sizes = {M, K};
639
681
std::vector<int64_t > mat2_sizes = {N, K};
640
- std::vector<int64_t > mat2_t_sizes = {K, N};
641
682
std::vector<int64_t > out_sizes = {M, N};
642
683
643
- std::vector<int64_t > transposed_dim_order = {1 , 0 };
644
-
645
- vTensor mat1 = CREATE_FLOAT_BUFFER (mat1_sizes, /* allocate_memory=*/ true );
646
- vTensor mat2 = CREATE_FLOAT_BUFFER (mat2_sizes, /* allocate_memory=*/ true );
647
- vTensor out = CREATE_FLOAT_BUFFER (out_sizes, /* allocate_memory=*/ true );
648
-
649
- // Generate data
650
- std::vector<float > mat1_data =
651
- create_random_float_buffer (mat1.staging_buffer_numel ());
652
- std::vector<float > mat2_data =
653
- create_random_float_buffer (mat2.staging_buffer_numel ());
654
-
655
- // Create direct view and modify sizes and strides later
656
- vTensor mat2_t = vTensor (mat2);
657
-
658
- std::vector<float > mat2_t_data = transpose_matrix (mat2_data, N, K);
659
- std::vector<float > ref_out =
660
- compute_reference_matmul (mat1_data, mat2_t_data, M, K, N);
661
-
662
- // Fill original tensor with some data
663
- fill_vtensor (mat1, mat1_data);
664
- fill_vtensor (mat2, mat2_data);
684
+ for (const auto storage_type : {utils::kTexture3D , utils::kBuffer }) {
685
+ vTensor mat1 = vTensor (
686
+ context (),
687
+ mat1_sizes,
688
+ vkapi::kFloat ,
689
+ storage_type,
690
+ utils::kWidthPacked );
691
+ vTensor mat2 = vTensor (
692
+ context (),
693
+ mat2_sizes,
694
+ vkapi::kFloat ,
695
+ storage_type,
696
+ utils::kWidthPacked );
697
+ vTensor out = vTensor (
698
+ context (), out_sizes, vkapi::kFloat , storage_type, utils::kWidthPacked );
699
+
700
+ // Generate data
701
+ std::vector<float > mat1_data =
702
+ create_random_float_buffer (mat1.staging_buffer_numel ());
703
+ std::vector<float > mat2_data =
704
+ create_random_float_buffer (mat2.staging_buffer_numel ());
705
+
706
+ // Create direct view and modify sizes and strides later
707
+ vTensor mat2_t = vTensor (mat2);
708
+ // Update sizes and strides of mat2_t to be that of a transposed tensor
709
+ mat2_t .virtual_transpose (0 , 1 );
710
+
711
+ EXPECT_TRUE (mat2_t .gpu_memory_layout () == utils::kHeightPacked );
712
+
713
+ std::vector<float > mat2_t_data = transpose_matrix (mat2_data, N, K);
714
+ std::vector<float > ref_out =
715
+ compute_reference_matmul (mat1_data, mat2_t_data, M, K, N);
665
716
666
- record_reference_matmul (api::context (), out, mat1, mat2_t );
717
+ // Fill original tensor with some data
718
+ fill_vtensor (mat1, mat1_data);
719
+ fill_vtensor (mat2, mat2_data);
667
720
668
- // Update sizes and strides of mat2_t to be that of a transposed tensor
669
- mat2_t .virtual_reconfigure (mat2_t_sizes, transposed_dim_order);
670
- EXPECT_TRUE (mat2_t .gpu_memory_layout () == utils::kHeightPacked );
721
+ if (storage_type == utils::kTexture3D ) {
722
+ record_matmul_texture3d (context (), out, mat1, mat2_t );
723
+ } else {
724
+ record_reference_matmul (context (), out, mat1, mat2_t );
725
+ }
671
726
672
- std::vector<float > data_out (out.staging_buffer_numel ());
673
- // Extract the copy tensor; should contain the data of the original tensor
674
- extract_vtensor (out, data_out);
727
+ std::vector<float > data_out (out.staging_buffer_numel ());
728
+ // Extract the copy tensor; should contain the data of the original tensor
729
+ extract_vtensor (out, data_out);
675
730
676
- EXPECT_TRUE (data_out.size () == ref_out.size ());
731
+ // EXPECT_TRUE(data_out.size() == ref_out.size());
677
732
678
- for (size_t i = 0 ; i < data_out.size (); ++i) {
679
- EXPECT_TRUE (check_close (data_out[i], ref_out[i]));
733
+ for (size_t i = 0 ; i < ref_out.size (); ++i) {
734
+ EXPECT_TRUE (check_close (data_out[i], ref_out[i]));
735
+ }
680
736
}
681
737
}
682
738
0 commit comments