aboutsummaryrefslogtreecommitdiff
path: root/src/core/NEON/kernels/arm_gemm/gemv_pretransposed.hpp
diff options
context:
space:
mode:
authorAnthony Barbier <anthony.barbier@arm.com>2018-07-03 16:22:02 +0100
committerAnthony Barbier <anthony.barbier@arm.com>2018-11-02 16:54:10 +0000
commit5f707736413aeac77818c42838296966f8dc6761 (patch)
treeb829ed3243ea5f3085f288836132416c78bc2e72 /src/core/NEON/kernels/arm_gemm/gemv_pretransposed.hpp
parent7485d5a62685cb745ab50e970adb722cb71557ac (diff)
downloadComputeLibrary-5f707736413aeac77818c42838296966f8dc6761.tar.gz
COMPMID-1369: Revert accidental formatting of RSH's repo
Pulled latest fixes from David's repo: commit f43ebe932c84083332b0b1a0348241b69dda63a7 Author: David Mansell <David.Mansell@arm.com> Date: Tue Jul 3 18:09:01 2018 +0100 Whitespace tidying, fixed comment in gemv_batched imported from ACL. Change-Id: Ie37a623f44e90d88072236cb853ac55ac82d5f51 Reviewed-on: https://eu-gerrit-1.euhpc.arm.com/138530 Tested-by: Jenkins <bsgcomp@arm.com> Reviewed-by: Georgios Pinitas <georgios.pinitas@arm.com> Reviewed-by: Gian Marco Iodice <gianmarco.iodice@arm.com> Reviewed-by: David Mansell <david.mansell@arm.com> Reviewed-by: Anthony Barbier <anthony.barbier@arm.com>
Diffstat (limited to 'src/core/NEON/kernels/arm_gemm/gemv_pretransposed.hpp')
-rw-r--r--src/core/NEON/kernels/arm_gemm/gemv_pretransposed.hpp87
1 files changed, 37 insertions, 50 deletions
diff --git a/src/core/NEON/kernels/arm_gemm/gemv_pretransposed.hpp b/src/core/NEON/kernels/arm_gemm/gemv_pretransposed.hpp
index 770ee033c8..e53ddb26c1 100644
--- a/src/core/NEON/kernels/arm_gemm/gemv_pretransposed.hpp
+++ b/src/core/NEON/kernels/arm_gemm/gemv_pretransposed.hpp
@@ -34,66 +34,64 @@
#include "profiler.hpp"
#endif
-namespace arm_gemm
-{
+namespace arm_gemm {
+
// Implementation of the GemmCommon abstract class.
//
// This is implementation is for GEMV with pretransposition.
+//
// batches are not supported as a batched GEMV makes no sense (can be converted to a GEMM).
-
-template <typename strategy, typename To, typename Tr>
-class GemvPretransposed : public GemmCommon<To, Tr>
-{
+template<typename strategy, typename To, typename Tr>
+class GemvPretransposed : public GemmCommon<To, Tr> {
typedef typename strategy::operand_type Toi;
- typedef typename strategy::result_type Tri;
+ typedef typename strategy::result_type Tri;
const unsigned int _Nsize;
const unsigned int _Ksize;
+
const unsigned int _nmultis;
const bool _trB;
const Tr _beta;
- const CPUInfo *const _ci;
- const unsigned int _buffer_per_multi;
+ const CPUInfo * const _ci;
- unsigned int m_block = 0;
- unsigned int n_block = 0;
+ const unsigned int _buffer_per_multi;
+
+ unsigned int m_block=0;
+ unsigned int n_block=0;
const Toi *_A_pretransposed = nullptr;
public:
GemvPretransposed(GemvPretransposed &) = delete;
- GemvPretransposed &operator=(GemvPretransposed &) = delete;
+ GemvPretransposed & operator= (GemvPretransposed &) = delete;
- GemvPretransposed(const CPUInfo *ci, const unsigned int N, const unsigned int K, const unsigned int nmultis, const bool trB, const Tr beta)
- : _Nsize(N), _Ksize(K), _nmultis(nmultis), _trB(trB), _beta(beta), _ci(ci), _buffer_per_multi(_Ksize * iceildiv(_Nsize, strategy::A_interleave) * strategy::A_interleave)
- {
+ GemvPretransposed(const CPUInfo *ci, const unsigned int N, const unsigned int K, const unsigned int nmultis, const bool trB, const Tr beta) :
+ _Nsize(N), _Ksize(K), _nmultis(nmultis), _trB(trB), _beta(beta), _ci(ci),
+ _buffer_per_multi(_Ksize * iceildiv(_Nsize, strategy::A_interleave) * strategy::A_interleave) {
/* For now don't do any blocking. TODO: figure out if we should. */
m_block = K;
n_block = N;
}
// Window is number of out_width blocks, times number of multis.
- unsigned int get_window_size() const override
- {
+ unsigned int get_window_size() const override {
return iceildiv(_Nsize, strategy::out_width) * _nmultis;
}
// Actually execute the GEMV.
- void execute(unsigned int start, unsigned int end, int) override
- {
+ void execute(unsigned int start, unsigned int end, int) override {
#ifdef CYCLE_PROFILING
profiler prof;
#endif
-
strategy strat(_ci);
/* Break the window values down into multis of interest... */
const unsigned int window_per_multi = iceildiv(_Nsize, strategy::out_width);
- const unsigned int multi_0 = start / window_per_multi;
- const unsigned int multi_end = end / window_per_multi;
+ const unsigned int multi_0 = start / window_per_multi;
+ const unsigned int multi_end = end / window_per_multi;
/* ... and figure out where we start and end in the first and last multi. */
const unsigned int n_0 = (start - (multi_0 * window_per_multi)) * strategy::out_width;
@@ -101,66 +99,56 @@ public:
static_assert(std::is_same<Tr, Tri>::value, "GemvPretransposed: Result types must be the same.");
- for(unsigned int multi = multi_0; multi <= multi_end; multi++)
- {
- const unsigned int n_start = (multi == multi_0) ? n_0 : 0;
- const unsigned int n_end = (multi == multi_end) ? n_max : _Nsize;
+ for (unsigned int multi=multi_0; multi<=multi_end; multi++) {
+ const unsigned int n_start = (multi==multi_0) ? n_0 : 0;
+ const unsigned int n_end = (multi==multi_end) ? n_max : _Nsize;
- if(n_end <= n_start)
+ if (n_end <= n_start)
continue;
- for(unsigned int m0 = 0; m0 < _Ksize; m0 += m_block)
- {
+ for (unsigned int m0=0; m0<_Ksize; m0+=m_block) {
unsigned int mmax = std::min(m0 + m_block, _Ksize);
- for(unsigned int n = n_start; n < n_end; n += n_block)
- {
+
+ for (unsigned int n=n_start; n<n_end; n+=n_block) {
unsigned int nmax = std::min(n + n_block, n_end);
#ifdef CYCLE_PROFILING
- auto p = prof.ScopedProfiler(PROFILE_KERNEL, (mmax - m0) * (nmax - n));
+ auto p = prof.ScopedProfiler(PROFILE_KERNEL, (mmax-m0) * (nmax-n));
#endif
/* This assumes that the underlying call was a GEMM with M=1; for the N=1 case we would have to pick up this->_Bptr below instead */
strat.kernel(_A_pretransposed + (multi * _buffer_per_multi) + (n * _Ksize) + (m0 * strategy::A_interleave),
(_Ksize * strategy::A_interleave),
this->_Aptr + (multi * this->_A_multi_stride) + m0,
this->_Cptr + (multi * this->_C_multi_stride) + n,
- _beta, (mmax - m0), (nmax - n));
+ _beta, (mmax-m0), (nmax-n));
}
}
}
}
/* Pretransposed interface implementation */
- bool B_is_pretransposed() const override
- {
+ bool B_is_pretransposed() const override {
return true;
}
- bool B_pretranspose_required() const override
- {
+ bool B_pretranspose_required() const override {
/* Transpose is required if _A_pretransposed is still nullptr */
return (_A_pretransposed == nullptr);
}
- size_t get_B_pretransposed_array_size() const override
- {
+ size_t get_B_pretransposed_array_size() const override {
return _buffer_per_multi * _nmultis * sizeof(To);
}
- void pretranspose_B_array(void *buffer, const To *B, const int ldb, const int B_multi_stride) override
- {
+ void pretranspose_B_array(void *buffer, const To *B, const int ldb, const int B_multi_stride) override {
Toi *A_buffer = reinterpret_cast<Toi *>(buffer);
- for(unsigned int multi = 0; multi < _nmultis; multi++)
- {
+ for (unsigned int multi=0; multi<_nmultis; multi++) {
/* Reverse sense here as we are dealing with B rather than A. So if
* strategy::A_transpose is false and _trB is false, we still
* transpose. */
- if(_trB ^ strategy::A_transpose)
- {
+ if (_trB ^ strategy::A_transpose) {
Transform<strategy::A_interleave, strategy::A_block, false>(A_buffer + (multi * _buffer_per_multi), B + (multi * B_multi_stride), ldb, 0, _Nsize, 0, _Ksize);
- }
- else
- {
+ } else {
Transform<strategy::A_interleave, strategy::A_block, true>(A_buffer + (multi * _buffer_per_multi), B + (multi * B_multi_stride), ldb, 0, _Nsize, 0, _Ksize);
}
}
@@ -168,8 +156,7 @@ public:
_A_pretransposed = A_buffer;
}
- void set_pretransposed_B_data(void *buffer) override
- {
+ void set_pretransposed_B_data(void *buffer) override {
_A_pretransposed = reinterpret_cast<Toi *>(buffer);
}
};