/*
 * Copyright (c) 2018-2021 Arm Limited.
 *
 * SPDX-License-Identifier: MIT
 *
 * Permission is hereby granted, free of charge, to any person obtaining a copy
 * of this software and associated documentation files (the "Software"), to
 * deal in the Software without restriction, including without limitation the
 * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
 * sell copies of the Software, and to permit persons to whom the Software is
 * furnished to do so, subject to the following conditions:
 *
 * The above copyright notice and this permission notice shall be included in all
 * copies or substantial portions of the Software.
 *
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
 * SOFTWARE.
 */
#include "arm_compute/runtime/NEON/functions/NEElementwiseOperations.h"
#include "arm_compute/core/Validate.h"
#include "src/runtime/cpu/operators/CpuElementwise.h"

#include "arm_compute/core/ITensor.h"

#include <utility>

namespace arm_compute
{
struct NEElementwiseMax::Impl
{
    const ITensor                          *src_0{ nullptr };
    const ITensor                          *src_1{ nullptr };
    ITensor                                *dst{ nullptr };
    std::unique_ptr<cpu::CpuElementwiseMax> op{ nullptr };
};

NEElementwiseMax::NEElementwiseMax()
    : _impl(std::make_unique<Impl>())
{
}
NEElementwiseMax::NEElementwiseMax(NEElementwiseMax &&) = default;
NEElementwiseMax &NEElementwiseMax::operator=(NEElementwiseMax &&) = default;
NEElementwiseMax::~NEElementwiseMax()                              = default;

void NEElementwiseMax::configure(ITensor *input1, ITensor *input2, ITensor *output, const ActivationLayerInfo &act_info)
{
    ARM_COMPUTE_UNUSED(act_info);
    _impl->src_0 = input1;
    _impl->src_1 = input2;
    _impl->dst   = output;
    _impl->op    = std::make_unique<cpu::CpuElementwiseMax>();
    _impl->op->configure(input1->info(), input2->info(), output->info());
}

Status NEElementwiseMax::validate(const ITensorInfo *input1, const ITensorInfo *input2, const ITensorInfo *output, const ActivationLayerInfo &act_info)
{
    ARM_COMPUTE_RETURN_ERROR_ON(act_info.enabled());
    return cpu::CpuElementwiseMax::validate(input1, input2, output);
}

void NEElementwiseMax::run()
{
    ITensorPack pack;
    pack.add_tensor(TensorType::ACL_SRC_0, _impl->src_0);
    pack.add_tensor(TensorType::ACL_SRC_1, _impl->src_1);
    pack.add_tensor(TensorType::ACL_DST, _impl->dst);
    _impl->op->run(pack);
}

struct NEElementwiseMin::Impl
{
    const ITensor                          *src_0{ nullptr };
    const ITensor                          *src_1{ nullptr };
    ITensor                                *dst{ nullptr };
    std::unique_ptr<cpu::CpuElementwiseMin> op{ nullptr };
};

NEElementwiseMin::NEElementwiseMin()
    : _impl(std::make_unique<Impl>())
{
}
NEElementwiseMin::NEElementwiseMin(NEElementwiseMin &&) = default;
NEElementwiseMin &NEElementwiseMin::operator=(NEElementwiseMin &&) = default;
NEElementwiseMin::~NEElementwiseMin()                              = default;

void NEElementwiseMin::configure(ITensor *input1, ITensor *input2, ITensor *output, const ActivationLayerInfo &act_info)
{
    ARM_COMPUTE_UNUSED(act_info);
    _impl->src_0 = input1;
    _impl->src_1 = input2;
    _impl->dst   = output;
    _impl->op    = std::make_unique<cpu::CpuElementwiseMin>();
    _impl->op->configure(input1->info(), input2->info(), output->info());
}

Status NEElementwiseMin::validate(const ITensorInfo *input1, const ITensorInfo *input2, const ITensorInfo *output, const ActivationLayerInfo &act_info)
{
    ARM_COMPUTE_RETURN_ERROR_ON(act_info.enabled());
    return cpu::CpuElementwiseMin::validate(input1, input2, output);
}

void NEElementwiseMin::run()
{
    ITensorPack pack;
    pack.add_tensor(TensorType::ACL_SRC_0, _impl->src_0);
    pack.add_tensor(TensorType::ACL_SRC_1, _impl->src_1);
    pack.add_tensor(TensorType::ACL_DST, _impl->dst);
    _impl->op->run(pack);
}

struct NEElementwiseSquaredDiff::Impl
{
    const ITensor                                  *src_0{ nullptr };
    const ITensor                                  *src_1{ nullptr };
    ITensor                                        *dst{ nullptr };
    std::unique_ptr<cpu::CpuElementwiseSquaredDiff> op{ nullptr };
};

NEElementwiseSquaredDiff::NEElementwiseSquaredDiff()
    : _impl(std::make_unique<Impl>())
{
}
NEElementwiseSquaredDiff::NEElementwiseSquaredDiff(NEElementwiseSquaredDiff &&) = default;
NEElementwiseSquaredDiff &NEElementwiseSquaredDiff::operator=(NEElementwiseSquaredDiff &&) = default;
NEElementwiseSquaredDiff::~NEElementwiseSquaredDiff()                                      = default;

void NEElementwiseSquaredDiff::configure(ITensor *input1, ITensor *input2, ITensor *output, const ActivationLayerInfo &act_info)
{
    ARM_COMPUTE_UNUSED(act_info);
    _impl->src_0 = input1;
    _impl->src_1 = input2;
    _impl->dst   = output;
    _impl->op    = std::make_unique<cpu::CpuElementwiseSquaredDiff>();
    _impl->op->configure(input1->info(), input2->info(), output->info());
}

Status NEElementwiseSquaredDiff::validate(const ITensorInfo *input1, const ITensorInfo *input2, const ITensorInfo *output, const ActivationLayerInfo &act_info)
{
    ARM_COMPUTE_RETURN_ERROR_ON(act_info.enabled());
    return cpu::CpuElementwiseSquaredDiff::validate(input1, input2, output);
}

void NEElementwiseSquaredDiff::run()
{
    ITensorPack pack;
    pack.add_tensor(TensorType::ACL_SRC_0, _impl->src_0);
    pack.add_tensor(TensorType::ACL_SRC_1, _impl->src_1);
    pack.add_tensor(TensorType::ACL_DST, _impl->dst);
    _impl->op->run(pack);
}

struct NEElementwiseDivision::Impl
{
    const ITensor                               *src_0{ nullptr };
    const ITensor                               *src_1{ nullptr };
    ITensor                                     *dst{ nullptr };
    std::unique_ptr<cpu::CpuElementwiseDivision> op{ nullptr };
};

NEElementwiseDivision::NEElementwiseDivision()
    : _impl(std::make_unique<Impl>())
{
}
NEElementwiseDivision::NEElementwiseDivision(NEElementwiseDivision &&) = default;
NEElementwiseDivision &NEElementwiseDivision::operator=(NEElementwiseDivision &&) = default;
NEElementwiseDivision::~NEElementwiseDivision()                                   = default;

void NEElementwiseDivision::configure(ITensor *input1, ITensor *input2, ITensor *output, const ActivationLayerInfo &act_info)
{
    ARM_COMPUTE_UNUSED(act_info);
    _impl->src_0 = input1;
    _impl->src_1 = input2;
    _impl->dst   = output;
    _impl->op    = std::make_unique<cpu::CpuElementwiseDivision>();
    _impl->op->configure(input1->info(), input2->info(), output->info());
}

Status NEElementwiseDivision::validate(const ITensorInfo *input1, const ITensorInfo *input2, const ITensorInfo *output, const ActivationLayerInfo &act_info)
{
    ARM_COMPUTE_RETURN_ERROR_ON(act_info.enabled());
    return cpu::CpuElementwiseDivision::validate(input1, input2, output);
}

void NEElementwiseDivision::run()
{
    ITensorPack pack;
    pack.add_tensor(TensorType::ACL_SRC_0, _impl->src_0);
    pack.add_tensor(TensorType::ACL_SRC_1, _impl->src_1);
    pack.add_tensor(TensorType::ACL_DST, _impl->dst);
    _impl->op->run(pack);
}

struct NEElementwisePower::Impl
{
    const ITensor                            *src_0{ nullptr };
    const ITensor                            *src_1{ nullptr };
    ITensor                                  *dst{ nullptr };
    std::unique_ptr<cpu::CpuElementwisePower> op{ nullptr };
};

NEElementwisePower::NEElementwisePower()
    : _impl(std::make_unique<Impl>())
{
}
NEElementwisePower::NEElementwisePower(NEElementwisePower &&) = default;
NEElementwisePower &NEElementwisePower::operator=(NEElementwisePower &&) = default;
NEElementwisePower::~NEElementwisePower()                                = default;

void NEElementwisePower::configure(ITensor *input1, ITensor *input2, ITensor *output, const ActivationLayerInfo &act_info)
{
    ARM_COMPUTE_UNUSED(act_info);
    _impl->src_0 = input1;
    _impl->src_1 = input2;
    _impl->dst   = output;
    _impl->op    = std::make_unique<cpu::CpuElementwisePower>();
    _impl->op->configure(input1->info(), input2->info(), output->info());
}

Status NEElementwisePower::validate(const ITensorInfo *input1, const ITensorInfo *input2, const ITensorInfo *output, const ActivationLayerInfo &act_info)
{
    ARM_COMPUTE_RETURN_ERROR_ON(act_info.enabled());
    return cpu::CpuElementwisePower::validate(input1, input2, output);
}

void NEElementwisePower::run()
{
    ITensorPack pack;
    pack.add_tensor(TensorType::ACL_SRC_0, _impl->src_0);
    pack.add_tensor(TensorType::ACL_SRC_1, _impl->src_1);
    pack.add_tensor(TensorType::ACL_DST, _impl->dst);
    _impl->op->run(pack);
}

template <ComparisonOperation COP>
struct NEElementwiseComparisonStatic<COP>::Impl
{
    const ITensor                                            *src_0{ nullptr };
    const ITensor                                            *src_1{ nullptr };
    ITensor                                                  *dst{ nullptr };
    std::unique_ptr<cpu::CpuElementwiseComparisonStatic<COP>> op{ nullptr };
};

template <ComparisonOperation COP>
NEElementwiseComparisonStatic<COP>::NEElementwiseComparisonStatic()
    : _impl(std::make_unique<Impl>())
{
}
template <ComparisonOperation COP>
NEElementwiseComparisonStatic<COP>::NEElementwiseComparisonStatic(NEElementwiseComparisonStatic &&) = default;
template <ComparisonOperation       COP>
NEElementwiseComparisonStatic<COP> &NEElementwiseComparisonStatic<COP>::operator=(NEElementwiseComparisonStatic &&) = default;
template <ComparisonOperation       COP>
NEElementwiseComparisonStatic<COP>::~NEElementwiseComparisonStatic() = default;

template <ComparisonOperation COP>
void NEElementwiseComparisonStatic<COP>::configure(ITensor *input1, ITensor *input2, ITensor *output)
{
    _impl->src_0 = input1;
    _impl->src_1 = input2;
    _impl->dst   = output;
    _impl->op    = std::make_unique<cpu::CpuElementwiseComparisonStatic<COP>>();
    _impl->op->configure(input1->info(), input2->info(), output->info());
}

template <ComparisonOperation COP>
Status NEElementwiseComparisonStatic<COP>::validate(const ITensorInfo *input1, const ITensorInfo *input2, const ITensorInfo *output)
{
    return cpu::CpuElementwiseComparisonStatic<COP>::validate(input1, input2, output);
}

template <ComparisonOperation COP>
void                          NEElementwiseComparisonStatic<COP>::run()
{
    ITensorPack pack;
    pack.add_tensor(TensorType::ACL_SRC_0, _impl->src_0);
    pack.add_tensor(TensorType::ACL_SRC_1, _impl->src_1);
    pack.add_tensor(TensorType::ACL_DST, _impl->dst);
    _impl->op->run(pack);
}

struct NEElementwiseComparison::Impl
{
    const ITensor                                 *src_0{ nullptr };
    const ITensor                                 *src_1{ nullptr };
    ITensor                                       *dst{ nullptr };
    std::unique_ptr<cpu::CpuElementwiseComparison> op{ nullptr };
};

NEElementwiseComparison::NEElementwiseComparison()
    : _impl(std::make_unique<Impl>())
{
}
NEElementwiseComparison::NEElementwiseComparison(NEElementwiseComparison &&) = default;
NEElementwiseComparison &NEElementwiseComparison::operator=(NEElementwiseComparison &&) = default;
NEElementwiseComparison::~NEElementwiseComparison()                                     = default;

void NEElementwiseComparison::configure(ITensor *input1, ITensor *input2, ITensor *output, ComparisonOperation op)
{
    _impl->src_0 = input1;
    _impl->src_1 = input2;
    _impl->dst   = output;
    _impl->op    = std::make_unique<cpu::CpuElementwiseComparison>();
    _impl->op->configure(input1->info(), input2->info(), output->info(), op);
}

Status NEElementwiseComparison::validate(const ITensorInfo *input1, const ITensorInfo *input2, const ITensorInfo *output, ComparisonOperation op)
{
    return cpu::CpuElementwiseComparison::validate(input1, input2, output, op);
}

void NEElementwiseComparison::run()
{
    ITensorPack pack;
    pack.add_tensor(TensorType::ACL_SRC_0, _impl->src_0);
    pack.add_tensor(TensorType::ACL_SRC_1, _impl->src_1);
    pack.add_tensor(TensorType::ACL_DST, _impl->dst);
    _impl->op->run(pack);
}

// Supported Specializations
template class NEElementwiseComparisonStatic<ComparisonOperation::Equal>;
template class NEElementwiseComparisonStatic<ComparisonOperation::NotEqual>;
template class NEElementwiseComparisonStatic<ComparisonOperation::Greater>;
template class NEElementwiseComparisonStatic<ComparisonOperation::GreaterEqual>;
template class NEElementwiseComparisonStatic<ComparisonOperation::Less>;
template class NEElementwiseComparisonStatic<ComparisonOperation::LessEqual>;
} // namespace arm_compute
