From e383c35c336002ce15945ed48facd7d4ba715aa8 Mon Sep 17 00:00:00 2001 From: morgolock Date: Fri, 3 Apr 2020 16:57:46 +0100 Subject: MLCE-166: Add support for extracting indices in NEPoolingLayer 2x2 NHWC * Added support for pooling indices in NHWC Poolsize 2x2 Change-Id: Ib2a3468e794f58bbf2c03aba9f6b184b9d76b183 Signed-off-by: morgolock Reviewed-on: https://review.mlplatform.org/c/ml/ComputeLibrary/+/2997 Tested-by: Arm Jenkins Reviewed-by: Manuel Bottini Reviewed-by: Michele Di Giorgio Comments-Addressed: Arm Jenkins --- tests/validation/NEON/PoolingLayer.cpp | 3 +- tests/validation/fixtures/PoolingLayerFixture.h | 12 +++---- tests/validation/reference/PoolingLayer.cpp | 47 ++++++++++++++++--------- tests/validation/reference/PoolingLayer.h | 7 ++-- 4 files changed, 41 insertions(+), 28 deletions(-) (limited to 'tests') diff --git a/tests/validation/NEON/PoolingLayer.cpp b/tests/validation/NEON/PoolingLayer.cpp index a5876dcd0a..4b073d5352 100644 --- a/tests/validation/NEON/PoolingLayer.cpp +++ b/tests/validation/NEON/PoolingLayer.cpp @@ -35,7 +35,6 @@ #include "tests/framework/datasets/Datasets.h" #include "tests/validation/Validation.h" #include "tests/validation/fixtures/PoolingLayerFixture.h" - namespace arm_compute { namespace test @@ -129,7 +128,7 @@ TEST_SUITE(FP32) FIXTURE_DATA_TEST_CASE(RunIndices, NEPoolingLayerIndicesFixture, framework::DatasetMode::PRECOMMIT, combine(combine(datasets::SmallShapes(), combine(PoolingLayerIndicesDatasetFPSmall, framework::dataset::make("DataType", DataType::F32))), - framework::dataset::make("DataLayout", { DataLayout::NCHW }) + framework::dataset::make("DataLayout", { DataLayout::NCHW, DataLayout::NHWC }) )) { diff --git a/tests/validation/fixtures/PoolingLayerFixture.h b/tests/validation/fixtures/PoolingLayerFixture.h index 7f2d7ac225..eb40cea0c2 100644 --- a/tests/validation/fixtures/PoolingLayerFixture.h +++ b/tests/validation/fixtures/PoolingLayerFixture.h @@ -35,7 +35,6 @@ #include "tests/framework/Fixture.h" #include "tests/validation/reference/PoolingLayer.h" #include - namespace arm_compute { namespace test @@ -59,7 +58,7 @@ public: _pool_info = pool_info; _target = compute_target(shape, pool_info, data_type, data_layout, input_qinfo, output_qinfo, indices); - _reference = compute_reference(shape, pool_info, data_type, input_qinfo, output_qinfo, indices); + _reference = compute_reference(shape, pool_info, data_type, data_layout, input_qinfo, output_qinfo, indices); } protected: @@ -92,7 +91,7 @@ protected: TensorType src = create_tensor(shape, data_type, 1, input_qinfo, data_layout); const TensorShape dst_shape = misc::shape_calculator::compute_pool_shape(*(src.info()), info); TensorType dst = create_tensor(dst_shape, data_type, 1, output_qinfo, data_layout); - _target_indices = create_tensor(dst_shape, DataType::U32, 1); + _target_indices = create_tensor(dst_shape, DataType::U32, 1, output_qinfo, data_layout); // Create and configure function FunctionType pool_layer; @@ -120,15 +119,14 @@ protected: return dst; } - SimpleTensor compute_reference(const TensorShape &shape, PoolingLayerInfo info, DataType data_type, + SimpleTensor compute_reference(TensorShape shape, PoolingLayerInfo info, DataType data_type, DataLayout data_layout, QuantizationInfo input_qinfo, QuantizationInfo output_qinfo, bool indices) { // Create reference - SimpleTensor src{ shape, data_type, 1, input_qinfo }; + SimpleTensor src(shape, data_type, 1, input_qinfo); // Fill reference fill(src); - - return reference::pooling_layer(src, info, output_qinfo, indices ? &_ref_indices : nullptr); + return reference::pooling_layer(src, info, output_qinfo, indices ? &_ref_indices : nullptr, data_layout); } TensorType _target{}; diff --git a/tests/validation/reference/PoolingLayer.cpp b/tests/validation/reference/PoolingLayer.cpp index 1a1aebd1b4..778e28d7c1 100644 --- a/tests/validation/reference/PoolingLayer.cpp +++ b/tests/validation/reference/PoolingLayer.cpp @@ -38,7 +38,7 @@ namespace reference using namespace arm_compute::misc::shape_calculator; template ::value, int>::type> -SimpleTensor pooling_layer_internal(const SimpleTensor &src, const PoolingLayerInfo &info, SimpleTensor *indices) +SimpleTensor pooling_layer_internal(const SimpleTensor &src, const PoolingLayerInfo &info, SimpleTensor *indices, DataLayout data_layout) { ARM_COMPUTE_ERROR_ON(info.is_global_pooling && (src.shape().x() != src.shape().y())); // Create reference @@ -62,8 +62,10 @@ SimpleTensor pooling_layer_internal(const SimpleTensor &src, const Pooling const auto h_src = static_cast(src.shape()[1]); const int upper_dims = src.shape().total_size() / (w_src * h_src); - const auto w_dst = static_cast(dst.shape()[0]); - const auto h_dst = static_cast(dst.shape()[1]); + const auto w_dst = static_cast(dst.shape()[0]); + const auto h_dst = static_cast(dst.shape()[1]); + TensorShape shape_nhwc(src.shape()); + permute(shape_nhwc, PermutationVector(2U, 0U, 1U)); if(type == PoolingType::MAX) { @@ -89,8 +91,15 @@ SimpleTensor pooling_layer_internal(const SimpleTensor &src, const Pooling const auto val = static_cast(src[r * h_src * w_src + y * w_src + x]); if(val > max_val) { - max_val = val; - max_index = coord2index(src.shape(), Coordinates(x, y, r)); + max_val = val; + if(data_layout == DataLayout::NCHW) + { + max_index = coord2index(src.shape(), Coordinates(x, y, r)); + } + else + { + max_index = coord2index(shape_nhwc, Coordinates(r, x, y)); + } } } } @@ -159,48 +168,52 @@ SimpleTensor pooling_layer_internal(const SimpleTensor &src, const Pooling return dst; } -template SimpleTensor pooling_layer_internal(const SimpleTensor &src, const PoolingLayerInfo &info, SimpleTensor *indices); -template SimpleTensor pooling_layer_internal(const SimpleTensor &src, const PoolingLayerInfo &info, SimpleTensor *indices); -template SimpleTensor pooling_layer_internal(const SimpleTensor &src, const PoolingLayerInfo &info, SimpleTensor *indices); +template SimpleTensor pooling_layer_internal(const SimpleTensor &src, const PoolingLayerInfo &info, SimpleTensor *indices, DataLayout data_layout); + +template SimpleTensor pooling_layer_internal(const SimpleTensor &src, const PoolingLayerInfo &info, SimpleTensor *indices, DataLayout data_layout); + +template SimpleTensor pooling_layer_internal(const SimpleTensor &src, const PoolingLayerInfo &info, SimpleTensor *indices, DataLayout data_layout); template -SimpleTensor pooling_layer(const SimpleTensor &src, const PoolingLayerInfo &info, const QuantizationInfo &output_qinfo, SimpleTensor *indices) +SimpleTensor pooling_layer(const SimpleTensor &src, const PoolingLayerInfo &info, const QuantizationInfo &output_qinfo, SimpleTensor *indices, DataLayout data_layout) { ARM_COMPUTE_UNUSED(output_qinfo); - return pooling_layer_internal(src, info, indices); + return pooling_layer_internal(src, info, indices, data_layout); } template <> -SimpleTensor pooling_layer(const SimpleTensor &src, const PoolingLayerInfo &info, const QuantizationInfo &output_qinfo, SimpleTensor *indices) +SimpleTensor pooling_layer(const SimpleTensor &src, const PoolingLayerInfo &info, const QuantizationInfo &output_qinfo, SimpleTensor *indices, + DataLayout data_layout) { SimpleTensor src_tmp = convert_from_asymmetric(src); - SimpleTensor dst_tmp = pooling_layer_internal(src_tmp, info, indices); + SimpleTensor dst_tmp = pooling_layer_internal(src_tmp, info, indices, data_layout); SimpleTensor dst = convert_to_asymmetric(dst_tmp, output_qinfo); return dst; } template <> -SimpleTensor pooling_layer(const SimpleTensor &src, const PoolingLayerInfo &info, const QuantizationInfo &output_qinfo, SimpleTensor *indices) +SimpleTensor pooling_layer(const SimpleTensor &src, const PoolingLayerInfo &info, const QuantizationInfo &output_qinfo, SimpleTensor *indices, DataLayout data_layout) { SimpleTensor src_tmp = convert_from_asymmetric(src); - SimpleTensor dst_tmp = pooling_layer_internal(src_tmp, info, indices); + SimpleTensor dst_tmp = pooling_layer_internal(src_tmp, info, indices, data_layout); SimpleTensor dst = convert_to_asymmetric(dst_tmp, output_qinfo); return dst; } template <> -SimpleTensor pooling_layer(const SimpleTensor &src, const PoolingLayerInfo &info, const QuantizationInfo &output_qinfo, SimpleTensor *indices) +SimpleTensor pooling_layer(const SimpleTensor &src, const PoolingLayerInfo &info, const QuantizationInfo &output_qinfo, SimpleTensor *indices, DataLayout data_layout) { ARM_COMPUTE_UNUSED(output_qinfo); if(src.data_type() == DataType::F16 && info.fp_mixed_precision) { - return pooling_layer_internal(src, info, indices); + return pooling_layer_internal(src, info, indices, data_layout); } return pooling_layer_internal(src, info, indices); } -template SimpleTensor pooling_layer(const SimpleTensor &src, const PoolingLayerInfo &info, const QuantizationInfo &output_qinfo, SimpleTensor *indices); +template SimpleTensor pooling_layer(const SimpleTensor &src, const PoolingLayerInfo &info, const QuantizationInfo &output_qinfo, SimpleTensor *indices, DataLayout data_layout); + } // namespace reference } // namespace validation } // namespace test diff --git a/tests/validation/reference/PoolingLayer.h b/tests/validation/reference/PoolingLayer.h index 3ca7f28d5a..346f1c0c9f 100644 --- a/tests/validation/reference/PoolingLayer.h +++ b/tests/validation/reference/PoolingLayer.h @@ -36,9 +36,12 @@ namespace validation namespace reference { template ::value, int>::type = 0> -SimpleTensor pooling_layer_internal(const SimpleTensor &src, const PoolingLayerInfo &info, SimpleTensor *indices); +SimpleTensor pooling_layer_internal(const SimpleTensor &src, const PoolingLayerInfo &info, SimpleTensor *indices, DataLayout data_layout = DataLayout::NCHW); + template -SimpleTensor pooling_layer(const SimpleTensor &src, const PoolingLayerInfo &info, const QuantizationInfo &output_qinfo, SimpleTensor *indices); +SimpleTensor pooling_layer(const SimpleTensor &src, const PoolingLayerInfo &info, const QuantizationInfo &output_qinfo, SimpleTensor *indices, + DataLayout data_layout = DataLayout::NCHW); + } // namespace reference } // namespace validation } // namespace test -- cgit v1.2.1