aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorSang-Hoon Park <sang-hoon.park@arm.com>2019-09-17 08:59:09 +0100
committerSiCongLi <sicong.li@arm.com>2019-12-11 17:05:24 +0000
commite6c3344f2a76b0724172200b1d5a443393045336 (patch)
tree8cfa3fb5ed70ab226b35a09f38b3ffaf226bba98
parent35c3eb011d8e2813d83c6a6cbe28a446534e4a14 (diff)
downloadComputeLibrary-e6c3344f2a76b0724172200b1d5a443393045336.tar.gz
COMPMID-2637 [CL] fix broadcast pixel-wise multiplication with 5D tensors
Broadcast pixel-wise multiplication with 5D tensors is fixed by adding information whether a dimension has been broadcasted to compute correct start offset when adding 3D tensor argument. The testcase that failed is added to the validation test suite. Change-Id: I320876f507012c27b39daae1316f9b69138ed204 Signed-off-by: Sang-Hoon Park <sang-hoon.park@arm.com> Reviewed-on: https://review.mlplatform.org/c/1994 Tested-by: Arm Jenkins <bsgcomp@arm.com> Comments-Addressed: Arm Jenkins <bsgcomp@arm.com> Reviewed-by: Georgios Pinitas <georgios.pinitas@arm.com>
-rw-r--r--arm_compute/core/Window.h17
-rw-r--r--arm_compute/core/Window.inl18
-rw-r--r--arm_compute/core/utils/misc/Utility.h16
-rw-r--r--src/core/CL/ICLKernel.cpp2
-rw-r--r--tests/datasets/ShapeDatasets.h12
5 files changed, 56 insertions, 9 deletions
diff --git a/arm_compute/core/Window.h b/arm_compute/core/Window.h
index a56227996b..be42fe9a87 100644
--- a/arm_compute/core/Window.h
+++ b/arm_compute/core/Window.h
@@ -48,7 +48,7 @@ public:
/** Default constructor: create a window containing a single element. */
constexpr Window()
- : _dims()
+ : _dims(), _is_broadcasted(utility::generate_array<bool, Coordinates::num_max_dimensions, false>::value)
{
}
/** Copy constructor
@@ -170,6 +170,20 @@ public:
*/
void set(size_t dimension, const Dimension &dim);
+ /** Set the dimension as broadcasted dimension
+ *
+ * @param[in] dimension The dimension to set
+ */
+ void set_broadcasted(size_t dimension);
+
+ /** Return whether a dimension has been broadcasted
+ *
+ * @param[in] dimension The requested dimension
+ *
+ * @return true if the dimension has been broadcasted
+ */
+ bool is_broadcasted(size_t dimension) const;
+
/** Use the tensor's dimensions to fill the window dimensions.
*
* @param[in] shape @ref TensorShape to copy the dimensions from.
@@ -419,6 +433,7 @@ private:
private:
std::array<Dimension, Coordinates::num_max_dimensions> _dims;
+ std::array<bool, Coordinates::num_max_dimensions> _is_broadcasted;
};
} // namespace arm_compute
#include "Window.inl"
diff --git a/arm_compute/core/Window.inl b/arm_compute/core/Window.inl
index eeef3df7b0..589d6bfafc 100644
--- a/arm_compute/core/Window.inl
+++ b/arm_compute/core/Window.inl
@@ -24,11 +24,12 @@
namespace arm_compute
{
inline Window::Window(const Window &src)
- : _dims()
+ : _dims(), _is_broadcasted(utility::generate_array<bool, Coordinates::num_max_dimensions, false>::value)
{
for(size_t i = 0; i < Coordinates::num_max_dimensions; ++i)
{
set(i, src[i]);
+ _is_broadcasted[i] = src.is_broadcasted(i);
}
}
@@ -51,6 +52,19 @@ inline void Window::set(size_t dimension, const Window::Dimension &dim)
_dims[dimension] = dim;
}
+inline void Window::set_broadcasted(size_t dimension)
+{
+ ARM_COMPUTE_ERROR_ON(dimension >= Coordinates::num_max_dimensions);
+ set(dimension, Dimension(0, 0, 0));
+ _is_broadcasted[dimension] = true;
+}
+
+inline bool Window::is_broadcasted(size_t dimension) const
+{
+ ARM_COMPUTE_ERROR_ON(dimension >= Coordinates::num_max_dimensions);
+ return _is_broadcasted[dimension];
+}
+
inline Window Window::collapse_if_possible(const Window &full_window, const size_t first,
const size_t last, bool *has_collapsed) const
{
@@ -110,7 +124,7 @@ inline Window Window::broadcast_if_dimension_le_one(const TensorShape &shape) co
{
if(shape[d] <= 1)
{
- broadcastWin.set(d, Dimension(0, 0, 0));
+ broadcastWin.set_broadcasted(d);
}
}
return broadcastWin;
diff --git a/arm_compute/core/utils/misc/Utility.h b/arm_compute/core/utils/misc/Utility.h
index 8dd9afd5cd..2325644e72 100644
--- a/arm_compute/core/utils/misc/Utility.h
+++ b/arm_compute/core/utils/misc/Utility.h
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2017-2018 ARM Limited.
+ * Copyright (c) 2017-2019 ARM Limited.
*
* SPDX-License-Identifier: MIT
*
@@ -53,6 +53,20 @@ struct index_sequence_generator<0u, S...> : index_sequence<S...>
template <std::size_t N>
using index_sequence_t = typename index_sequence_generator<N>::type;
+
+template <typename T, std::size_t N, T val, T... vals>
+struct generate_array : generate_array < T, N - 1, val, val, vals... >
+{
+};
+
+template <typename T, T val, T... vals>
+struct generate_array<T, 0, val, vals...>
+{
+ static constexpr std::array<T, sizeof...(vals)> value{ vals... };
+};
+
+template <typename T, T val, T... vals>
+constexpr std::array<T, sizeof...(vals)> generate_array<T, 0, val, vals...>::value;
/** @endcond */
namespace detail
diff --git a/src/core/CL/ICLKernel.cpp b/src/core/CL/ICLKernel.cpp
index 2d28a496c9..d81ad46b29 100644
--- a/src/core/CL/ICLKernel.cpp
+++ b/src/core/CL/ICLKernel.cpp
@@ -98,7 +98,7 @@ void ICLKernel::add_tensor_argument(unsigned &idx, const ICLTensor *tensor, cons
for(unsigned int n = 0; n < info->num_dimensions(); ++n)
{
- offset_first_element += window[n].start() * strides[n];
+ offset_first_element += (window.is_broadcasted(n) ? 0 : window[n].start()) * strides[n];
}
unsigned int idx_start = idx;
diff --git a/tests/datasets/ShapeDatasets.h b/tests/datasets/ShapeDatasets.h
index 07ecf45d81..b479eb4953 100644
--- a/tests/datasets/ShapeDatasets.h
+++ b/tests/datasets/ShapeDatasets.h
@@ -203,7 +203,9 @@ public:
TensorShape{ 128U, 1U, 5U, 3U },
TensorShape{ 9U, 9U, 3U, 4U },
TensorShape{ 27U, 13U, 2U, 4U },
- TensorShape{ 1U, 1U, 1U, 5U }
+ TensorShape{ 1U, 1U, 1U, 5U },
+ TensorShape{ 1U, 16U, 10U, 2U, 128U },
+ TensorShape{ 1U, 16U, 10U, 2U, 128U }
}),
ShapeDataset("Shape1",
{
@@ -212,7 +214,9 @@ public:
TensorShape{ 128U, 64U, 1U, 3U },
TensorShape{ 9U, 1U, 3U },
TensorShape{ 1U },
- TensorShape{ 9U, 9U, 3U, 5U }
+ TensorShape{ 9U, 9U, 3U, 5U },
+ TensorShape{ 1U, 1U, 1U, 1U, 128U },
+ TensorShape{ 128U }
}))
{
}
@@ -686,7 +690,7 @@ public:
: ShapeDataset("InputShape",
{
// Batch size 1
- TensorShape{ 32U, 37U, 3U },
+ TensorShape{ 32U, 37U, 3U },
// Batch size 4
TensorShape{ 32U, 37U, 3U, 4U },
})
@@ -702,7 +706,7 @@ public:
: ShapeDataset("InputShape",
{
// Batch size 1
- TensorShape{ 32U, 37U, 3U },
+ TensorShape{ 32U, 37U, 3U },
// Batch size 4
TensorShape{ 32U, 37U, 3U, 4U },
// Arbitrary batch size