//
// Copyright © 2017 Arm Ltd. All rights reserved.
// SPDX-License-Identifier: MIT
//

#include "Pooling2d.hpp"

#include <armnn/Exceptions.hpp>
#include <armnn/Types.hpp>

#include <armnnUtils/DataLayoutIndexed.hpp>
#include <armnn/utility/NumericCast.hpp>

#include <boost/numeric/conversion/cast.hpp>

#include <limits>
#include <algorithm>
#include <functional>

namespace
{
    using PoolingAlgorithm = armnn::PoolingAlgorithm;

    float DefaultInitializer(PoolingAlgorithm algorithm)
    {
        switch (algorithm)
        {
            case PoolingAlgorithm::Max:
            {
                return std::numeric_limits<float>::lowest();
            }
            case PoolingAlgorithm::Average:
            case PoolingAlgorithm::L2:
            {
                return 0.0f;
            }
            default:
            {
                throw armnn::InvalidArgumentException("Unsupported pooling algorithm");
            }
        }
    }

    using Accumulator = std::function<void(float & accu, float value)>;

    Accumulator GetAccumulator(PoolingAlgorithm algorithm)
    {
        switch (algorithm)
        {
            case PoolingAlgorithm::Max:
            {
                return [](float & accu, float value) {
                    if (value > accu) {
                        accu = value;
                    }
                };
            }

            case PoolingAlgorithm::Average:
            {
                return [](float & accu, float value) {
                    accu += value;
                };
            }

            case PoolingAlgorithm::L2:
            {
                return [](float & accu, float value) {
                    accu += (value*value);
                };
            }

            default:
            {
                throw armnn::InvalidArgumentException("Unsupported pooling algorithm");
            }
        }
    }

    using Executor = std::function<void(float & accumulated, float kernelSize)>;

    Executor GetExecutor(PoolingAlgorithm algorithm)
    {
        switch (algorithm)
        {
            case PoolingAlgorithm::Max:
            {
                return [](float & /*accumulated*/, float /*kernelSize*/) {};
            }

            case PoolingAlgorithm::Average:
            {
                return [](float & accumulated, float kernelSize) {
                    accumulated /= kernelSize;
                };
            }

            case PoolingAlgorithm::L2:
            {
                return [](float & accumulated, float kernelSize) {
                    accumulated = sqrtf(accumulated / kernelSize);
                };
            }

            default:
            {
                throw armnn::InvalidArgumentException("Unsupported pooling algorithm");
            }
        }
    }

    bool OnPaddingOnly(int start, int end, int maxRange)
    {
        if (end <= 0 || start > maxRange)
        {
            return true;
        }
        else
        {
            return false;
        }
    }


    bool ClampRange(int & start, int & end, int maxRange)
    {
        if (start < 0 || end > maxRange)
        {
            start = std::min(std::max(start, 0), maxRange);
            end   = std::min(std::max(end, 0), maxRange);
            return true;
        }
        else
        {
            return false;
        }
    }
}

using namespace armnnUtils;

namespace armnn
{
void Pooling2d(Decoder<float>& rInputDecoder,
               Encoder<float>& rOutputEncoder,
               const TensorInfo& inputInfo,
               const TensorInfo& outputInfo,
               const Pooling2dDescriptor& params)
{
    const DataLayoutIndexed dataLayout(params.m_DataLayout);
    auto channelsIndex = dataLayout.GetChannelsIndex();
    auto heightIndex = dataLayout.GetHeightIndex();
    auto widthIndex = dataLayout.GetWidthIndex();

    const int batchSize    = armnn::numeric_cast<int>(outputInfo.GetShape()[0]);
    const int channels     = armnn::numeric_cast<int>(outputInfo.GetShape()[channelsIndex]);
    const int heightOutput = armnn::numeric_cast<int>(outputInfo.GetShape()[heightIndex]);
    const int widthOutput  = armnn::numeric_cast<int>(outputInfo.GetShape()[widthIndex]);
    const int heightInput  = armnn::numeric_cast<int>(inputInfo.GetShape()[heightIndex]);
    const int widthInput   = armnn::numeric_cast<int>(inputInfo.GetShape()[widthIndex]);
    const int padLeft      = armnn::numeric_cast<int>(params.m_PadLeft);
    const int padRight     = armnn::numeric_cast<int>(params.m_PadRight);
    const int padTop       = armnn::numeric_cast<int>(params.m_PadTop);
    const int padBottom    = armnn::numeric_cast<int>(params.m_PadBottom);
    const int strideX      = armnn::numeric_cast<int>(params.m_StrideX);
    const int strideY      = armnn::numeric_cast<int>(params.m_StrideY);
    const int poolHeight   = armnn::numeric_cast<int>(params.m_PoolHeight);
    const int poolWidth    = armnn::numeric_cast<int>(params.m_PoolWidth);

    float defaultInitializer = DefaultInitializer(params.m_PoolType);

    Accumulator accumulate = GetAccumulator(params.m_PoolType);
    Executor execute       = GetExecutor(params.m_PoolType);

    TensorShape outputShape = outputInfo.GetShape();
    TensorShape inputShape =  inputInfo.GetShape();

    // Check supported padding methods outside the loop to simplify
    // the inner loop.
    if (params.m_PaddingMethod != PaddingMethod::Exclude &&
        params.m_PaddingMethod != PaddingMethod::IgnoreValue)
    {
        throw armnn::InvalidArgumentException("Unsupported padding type");
    }

    for (int n = 0; n < batchSize; n++)
    {
        for (int c = 0; c < channels; c++)
        {
            for (int yOutput = 0; yOutput < heightOutput; yOutput++)
            {
                //  Calculate values independent of the x axis
                int hstart = (yOutput * strideY) - padTop;
                int hend = hstart + poolHeight;
                // Clamp the pooling region inside the valid input area (which includes the padding).
                // This is necessary because the final pooling in a row may overlap beyond the padding.
                hend = std::min(hend, heightInput + padBottom);

                int height = hend - hstart;
                bool hclamped = ClampRange(hstart, hend, heightInput);

                for (int xOutput = 0; xOutput < widthOutput; xOutput++)
                {
                    int wstart = (xOutput * strideX) - padLeft;
                    int wend = wstart + poolWidth;

                    // Clamp the pooling region inside the valid input area (which includes the padding).
                    // This is necessary because the final pooling in a row may overlap beyond the padding.
                    wend = std::min(wend, widthInput + padRight);

                    float result = defaultInitializer;
                    float poolAreaSize = boost::numeric_cast<float>(height * (wend - wstart));

                    // Special case: when the pooling kernel is over a padding region and the padding
                    //               size is larger or equal to the kernel and the kernel only covers
                    //               padding and no real values, then we initialize the result as zero
                    //               by convention. This is because we need to choose a value here and
                    //               all values we have are padding, which we ignore.
                    if (OnPaddingOnly(hstart, hend, heightInput) ||
                        OnPaddingOnly(wstart, wend, widthInput))
                    {
                        result = 0.0f;

                        unsigned int outputIndex = dataLayout.GetIndex(outputShape,
                                                                       armnn::numeric_cast<unsigned int>(n),
                                                                       armnn::numeric_cast<unsigned int>(c),
                                                                       armnn::numeric_cast<unsigned int>(yOutput),
                                                                       armnn::numeric_cast<unsigned int>(xOutput));
                        rOutputEncoder[outputIndex];
                        rOutputEncoder.Set(result);
                        continue;
                    }

                    bool clamped = hclamped |= ClampRange(wstart, wend, widthInput);

                    if (clamped && params.m_PaddingMethod == PaddingMethod::Exclude)
                    {
                        // When we exclude the padding, it means we calculate with a smaller
                        // kernel size, so I changed the divisor here.
                        poolAreaSize = boost::numeric_cast<float>((hend - hstart) * (wend - wstart));
                    }

                    for (auto yInput = hstart; yInput < hend; yInput++)
                    {
                        for (auto xInput = wstart; xInput < wend; xInput++)
                        {
                            unsigned int inputIndex = dataLayout.GetIndex(inputShape,
                                                                          armnn::numeric_cast<unsigned int>(n),
                                                                          armnn::numeric_cast<unsigned int>(c),
                                                                          armnn::numeric_cast<unsigned int>(yInput),
                                                                          armnn::numeric_cast<unsigned int>(xInput));

                            rInputDecoder[inputIndex];
                            float inval = rInputDecoder.Get();

                            accumulate(result, inval);
                        }
                    }

                    execute(result, poolAreaSize);

                    unsigned int outputIndex = dataLayout.GetIndex(outputShape,
                                                                   armnn::numeric_cast<unsigned int>(n),
                                                                   armnn::numeric_cast<unsigned int>(c),
                                                                   armnn::numeric_cast<unsigned int>(yOutput),
                                                                   armnn::numeric_cast<unsigned int>(xOutput));

                    rOutputEncoder[outputIndex];
                    rOutputEncoder.Set(result);
                }
            }
        }
    }
}

} //namespace armnn
