aboutsummaryrefslogtreecommitdiff
path: root/src/core/NEON/kernels/NEIm2ColKernel.cpp
diff options
context:
space:
mode:
authorGeorgios Pinitas <georgios.pinitas@arm.com>2020-12-31 15:35:17 +0000
committerGeorgios Pinitas <georgios.pinitas@arm.com>2021-01-05 10:28:51 +0000
commitdff29359f46cccf1239b9ae109a773eadb320594 (patch)
tree61a4ec2585b4ba4eac390342ecd64c2e2410e3af /src/core/NEON/kernels/NEIm2ColKernel.cpp
parent932402276935a5fdf3a15b0c10e5310c7a0ae393 (diff)
downloadComputeLibrary-dff29359f46cccf1239b9ae109a773eadb320594.tar.gz
Improve NEIm2Col validation for invalid shapes
Ensure that Im2Col transformation is valid for the given input meta-data. In more detail, validate that the combination of input shape, padding and kernel width leads to a valid execution window and output shape. Resolves: COMPMID-4040 Signed-off-by: Georgios Pinitas <georgios.pinitas@arm.com> Change-Id: Id813373b2efdfdfbe71dc0d0acc1d7bf8ecd5e84 Reviewed-on: https://review.mlplatform.org/c/ml/ComputeLibrary/+/4757 Tested-by: Arm Jenkins <bsgcomp@arm.com> Reviewed-by: Michele Di Giorgio <michele.digiorgio@arm.com> Comments-Addressed: Arm Jenkins <bsgcomp@arm.com>
Diffstat (limited to 'src/core/NEON/kernels/NEIm2ColKernel.cpp')
-rw-r--r--src/core/NEON/kernels/NEIm2ColKernel.cpp25
1 files changed, 18 insertions, 7 deletions
diff --git a/src/core/NEON/kernels/NEIm2ColKernel.cpp b/src/core/NEON/kernels/NEIm2ColKernel.cpp
index 93bfcc501a..72821c890d 100644
--- a/src/core/NEON/kernels/NEIm2ColKernel.cpp
+++ b/src/core/NEON/kernels/NEIm2ColKernel.cpp
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2017-2020 Arm Limited.
+ * Copyright (c) 2017-2021 Arm Limited.
*
* SPDX-License-Identifier: MIT
*
@@ -51,11 +51,19 @@ Status validate_arguments(const ITensorInfo *input, const ITensorInfo *output, c
bool has_bias, const Size2D &dilation, unsigned int num_groups)
{
ARM_COMPUTE_RETURN_ERROR_ON_CPU_F16_UNSUPPORTED(input);
+ ARM_COMPUTE_RETURN_ERROR_ON_NULLPTR(output);
ARM_COMPUTE_RETURN_ERROR_ON_DATA_TYPE_CHANNEL_NOT_IN(input, 1, DataType::QASYMM8, DataType::QASYMM8_SIGNED, DataType::BFLOAT16, DataType::F16, DataType::F32);
ARM_COMPUTE_RETURN_ERROR_ON(is_data_type_quantized(input->data_type()) && has_bias);
ARM_COMPUTE_RETURN_ERROR_ON((dilation.x() < 1) || (dilation.y() < 1));
ARM_COMPUTE_RETURN_ERROR_ON_MSG(num_groups > 1, "Number of groups greater than one are not supported on NEON");
+ // Since there's no implicit padding added, check the total input spatial dimensions (with conv paddings) are big enough for the kernel dimensions
+ const unsigned int width_idx = get_data_layout_dimension_index(input->data_layout(), DataLayoutDimension::WIDTH);
+ const unsigned int height_idx = get_data_layout_dimension_index(input->data_layout(), DataLayoutDimension::HEIGHT);
+ const unsigned total_width = input->dimension(width_idx) + conv_info.pad_left() + conv_info.pad_right();
+ const unsigned total_height = input->dimension(height_idx) + conv_info.pad_top() + conv_info.pad_bottom();
+ ARM_COMPUTE_RETURN_ERROR_ON((total_width < kernel_dims.width) || (total_height < kernel_dims.height));
+
if(output->total_size() > 0)
{
TensorInfo expected_output = output->clone()->set_tensor_shape(compute_im2col_conv_shape(input, kernel_dims, conv_info, has_bias, dilation, false));
@@ -70,17 +78,20 @@ Status validate_arguments(const ITensorInfo *input, const ITensorInfo *output, c
std::pair<Status, Window> validate_and_configure_window(ITensorInfo *input, ITensorInfo *output, const Size2D &kernel_dims, const PadStrideInfo &conv_info,
bool has_bias, const Size2D &dilation)
{
- const unsigned int width_idx = get_data_layout_dimension_index(input->data_layout(), DataLayoutDimension::WIDTH);
- const unsigned int height_idx = get_data_layout_dimension_index(input->data_layout(), DataLayoutDimension::HEIGHT);
- const unsigned int channel_idx = get_data_layout_dimension_index(input->data_layout(), DataLayoutDimension::CHANNEL);
+ ARM_COMPUTE_ERROR_ON_NULLPTR(input, output);
+
+ // Output tensor auto initialization if not yet initialized
+ auto_init_if_empty(*output, input->clone()->set_tensor_shape(compute_im2col_conv_shape(input, kernel_dims, conv_info, has_bias, dilation, false)));
+
+ const DataLayout data_layout = input->data_layout();
+ const unsigned int width_idx = get_data_layout_dimension_index(data_layout, DataLayoutDimension::WIDTH);
+ const unsigned int height_idx = get_data_layout_dimension_index(data_layout, DataLayoutDimension::HEIGHT);
+ const unsigned int channel_idx = get_data_layout_dimension_index(data_layout, DataLayoutDimension::CHANNEL);
std::pair<unsigned int, unsigned int> convolved_dims = scaled_dimensions(input->dimension(width_idx), input->dimension(height_idx),
kernel_dims.width, kernel_dims.height,
conv_info, dilation);
- // Output tensor auto initialization if not yet initialized
- auto_init_if_empty(*output, input->clone()->set_tensor_shape(compute_im2col_conv_shape(input, kernel_dims, conv_info, has_bias, dilation, false)));
-
Window win = calculate_max_window(*input, Steps());
win.set(width_idx, Window::Dimension(0, convolved_dims.first, 1));
win.set(height_idx, Window::Dimension(0, convolved_dims.second, 1));