/**
 * Copyright © 2018 Intel Corporation
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
#pragma once
#include <cxxabi.h>

#include <boost/asio/spawn.hpp>
#include <boost/callable_traits.hpp>
#include <ipmid/api-types.hpp>
#include <ipmid/message.hpp>
#include <phosphor-logging/lg2.hpp>
#include <phosphor-logging/log.hpp>
#include <user_channel/channel_layer.hpp>

#include <algorithm>
#include <cstdint>
#include <exception>
#include <memory>
#include <optional>
#include <stdexcept>
#include <tuple>
#include <utility>

#ifdef ALLOW_DEPRECATED_API
#include <ipmid/api.h>

#include <ipmid/oemrouter.hpp>
#endif /* ALLOW_DEPRECATED_API */

namespace ipmi
{

template <typename... Args>
static inline message::Response::ptr errorResponse(
    message::Request::ptr request, ipmi::Cc cc, Args&&... args)
{
    message::Response::ptr response = request->makeResponse();
    response->cc = cc;
    response->pack(args...);
    return response;
}
static inline message::Response::ptr errorResponse(
    message::Request::ptr request, ipmi::Cc cc)
{
    message::Response::ptr response = request->makeResponse();
    response->cc = cc;
    return response;
}

/** @brief Exception extension that allows setting an IPMI return code */
class HandlerCompletion
{
  public:
    HandlerCompletion(Cc cc) noexcept : cc(cc) {}

    Cc code() const noexcept
    {
        return cc;
    }

  private:
    Cc cc;
};

/** @brief Exception extension that allows setting an IPMI return code and
 * printing out a logged error */
class HandlerException : public HandlerCompletion, public std::runtime_error
{
  public:
    HandlerException(Cc cc, const char* what) :
        HandlerCompletion(cc), std::runtime_error(what)
    {}
    HandlerException(Cc cc, const std::string& what) :
        HandlerException(cc, what.c_str())
    {}
};

static inline const char* currentExceptionType()
{
    int status;
    return abi::__cxa_demangle(abi::__cxa_current_exception_type()->name(),
                               nullptr, nullptr, &status);
}

/**
 * @brief Handler base class for dealing with IPMI request/response
 *
 * The subclasses are all templated so they can provide access to any type
 * of command callback functions.
 */
class HandlerBase
{
  public:
    using ptr = std::shared_ptr<HandlerBase>;

    virtual ~HandlerBase() = default;

    /** @brief wrap the call to the registered handler with the request
     *
     * This is called from the running queue context after it has already
     * created a request object that contains all the information required to
     * execute the ipmi command. This function will return the response object
     * pointer that owns the response object that will ultimately get sent back
     * to the requester.
     *
     * This is a non-virtual function wrapper to the virtualized executeCallback
     * function that actually does the work. This is required because of how
     * templates and virtualization work together.
     *
     * @param request a shared_ptr to a Request object
     *
     * @return a shared_ptr to a Response object
     */
    message::Response::ptr call(message::Request::ptr request)
    {
        return executeCallback(request);
    }

  private:
    /** @brief call the registered handler with the request
     *
     * This is called from the running queue context after it has already
     * created a request object that contains all the information required to
     * execute the ipmi command. This function will return the response object
     * pointer that owns the response object that will ultimately get sent back
     * to the requester.
     *
     * @param request a shared_ptr to a Request object
     *
     * @return a shared_ptr to a Response object
     */
    virtual message::Response::ptr executeCallback(
        message::Request::ptr request) = 0;
};

/**
 * @brief Main IPMI handler class
 *
 * New IPMI handlers will resolve into this class, which will read the signature
 * of the registering function, attempt to extract the appropriate arguments
 * from a request, pass the arguments to the function, and then pack the
 * response of the function back into an IPMI response.
 */
template <typename Handler>
class IpmiHandler final : public HandlerBase
{
  public:
    explicit IpmiHandler(Handler&& handler) :
        handler_(std::forward<Handler>(handler))
    {}

  private:
    Handler handler_;

    /** @brief call the registered handler with the request
     *
     * This is called from the running queue context after it has already
     * created a request object that contains all the information required to
     * execute the ipmi command. This function will return the response object
     * pointer that owns the response object that will ultimately get sent back
     * to the requester.
     *
     * Because this is the new variety of IPMI handler, this is the function
     * that attempts to extract the requested parameters in order to pass them
     * onto the callback function and then packages up the response into a plain
     * old vector to pass back to the caller.
     *
     * @param request a shared_ptr to a Request object
     *
     * @return a shared_ptr to a Response object
     */
    message::Response::ptr executeCallback(
        message::Request::ptr request) override
    {
        message::Response::ptr response = request->makeResponse();

        using CallbackSig = boost::callable_traits::args_t<Handler>;
        using InputArgsType = typename utility::DecayTuple<CallbackSig>::type;
        using UnpackArgsType = typename utility::StripFirstArgs<
            utility::NonIpmiArgsCount<InputArgsType>::size(),
            InputArgsType>::type;
        using ResultType = boost::callable_traits::return_type_t<Handler>;

        UnpackArgsType unpackArgs{};
        request->payload.trailingOk = false;
        ipmi::Cc unpackError = request->unpack(unpackArgs);
        if (unpackError != ipmi::ccSuccess)
        {
            response->cc = unpackError;
            return response;
        }
        /* callbacks can contain an optional first argument of one of:
         * 1) boost::asio::yield_context
         * 2) ipmi::Context::ptr
         * 3) ipmi::message::Request::ptr
         *
         * If any of those is part of the callback signature as the first
         * argument, it will automatically get packed into the parameter pack
         * here.
         *
         * One more special optional argument is an ipmi::message::Payload.
         * This argument can be in any position, though logically it makes the
         * most sense if it is the last. If this class is included in the
         * handler signature, it will allow for the handler to unpack optional
         * parameters. For example, the Set LAN Configuration Parameters
         * command takes variable length (and type) values for each of the LAN
         * parameters. This means that the  only fixed data is the channel and
         * parameter selector. All the remaining data can be extracted using
         * the Payload class and the unpack API available to the Payload class.
         */
        ResultType result;
        try
        {
            std::optional<InputArgsType> inputArgs;
            if constexpr (std::tuple_size<InputArgsType>::value > 0)
            {
                if constexpr (std::is_same<
                                  std::tuple_element_t<0, InputArgsType>,
                                  boost::asio::yield_context>::value)
                {
                    inputArgs.emplace(std::tuple_cat(
                        std::forward_as_tuple(request->ctx->yield),
                        std::move(unpackArgs)));
                }
                else if constexpr (std::is_same<
                                       std::tuple_element_t<0, InputArgsType>,
                                       ipmi::Context::ptr>::value)
                {
                    inputArgs.emplace(
                        std::tuple_cat(std::forward_as_tuple(request->ctx),
                                       std::move(unpackArgs)));
                }
                else if constexpr (std::is_same<
                                       std::tuple_element_t<0, InputArgsType>,
                                       ipmi::message::Request::ptr>::value)
                {
                    inputArgs.emplace(std::tuple_cat(
                        std::forward_as_tuple(request), std::move(unpackArgs)));
                }
                else
                {
                    // no special parameters were requested (but others were)
                    inputArgs.emplace(std::move(unpackArgs));
                }
            }
            else
            {
                // no parameters were requested
                inputArgs = std::move(unpackArgs);
            }

            // execute the registered callback function and get the
            // ipmi::RspType<>
            result = std::apply(handler_, *inputArgs);
        }
        catch (const HandlerException& e)
        {
            lg2::info("Handler produced exception, NetFn: {NETFN}, "
                      "Cmd: {CMD}: {ERROR}",
                      "NETFN", lg2::hex, request->ctx->netFn, "CMD", lg2::hex,
                      request->ctx->cmd, "ERROR", e);
            return errorResponse(request, e.code());
        }
        catch (const std::exception& e)
        {
            lg2::error("Handler failed to catch exception, NetFn: {NETFN}, "
                       "Cmd: {CMD}: {ERROR}",
                       "NETFN", lg2::hex, request->ctx->netFn, "CMD", lg2::hex,
                       request->ctx->cmd, "ERROR", e);
            return errorResponse(request, ccUnspecifiedError);
        }
        catch (const HandlerCompletion& c)
        {
            return errorResponse(request, c.code());
        }
        catch (...)
        {
            const char* what = currentExceptionType();
            lg2::error("Handler failed to catch exception, NetFn: {NETFN}, "
                       "Cmd: {CMD}: {ERROR}",
                       "NETFN", lg2::hex, request->ctx->netFn, "CMD", lg2::hex,
                       request->ctx->cmd, "ERROR", what);
            return errorResponse(request, ccUnspecifiedError);
        }

        response->cc = std::get<0>(result);
        auto payload = std::get<1>(result);
        // check for optional payload
        if (payload)
        {
            response->pack(*payload);
        }
        return response;
    }
};

#ifdef ALLOW_DEPRECATED_API
static constexpr size_t maxLegacyBufferSize = 64 * 1024;
/**
 * @brief Legacy IPMI handler class
 *
 * Legacy IPMI handlers will resolve into this class, which will behave the same
 * way as the legacy IPMI queue, passing in a big buffer for the request and a
 * big buffer for the response.
 *
 * As soon as all the handlers have been rewritten, this class will be marked as
 * deprecated and eventually removed.
 */
template <>
class IpmiHandler<ipmid_callback_t> final : public HandlerBase
{
  public:
    explicit IpmiHandler(const ipmid_callback_t& handler, void* ctx = nullptr) :
        handler_(handler), handlerCtx(ctx)
    {}

  private:
    ipmid_callback_t handler_;
    void* handlerCtx;

    /** @brief call the registered handler with the request
     *
     * This is called from the running queue context after it has already
     * created a request object that contains all the information required to
     * execute the ipmi command. This function will return the response object
     * pointer that owns the response object that will ultimately get sent back
     * to the requester.
     *
     * Because this is the legacy variety of IPMI handler, this function does
     * not really have to do much other than pass the payload to the callback
     * and return response to the caller.
     *
     * @param request a shared_ptr to a Request object
     *
     * @return a shared_ptr to a Response object
     */
    message::Response::ptr executeCallback(
        message::Request::ptr request) override
    {
        message::Response::ptr response = request->makeResponse();
        // allocate a big response buffer here
        response->payload.resize(maxLegacyBufferSize);

        size_t len = request->payload.size() - request->payload.rawIndex;
        Cc ccRet{ccSuccess};
        try
        {
            ccRet =
                handler_(request->ctx->netFn, request->ctx->cmd,
                         request->payload.data() + request->payload.rawIndex,
                         response->payload.data(), &len, handlerCtx);
        }
        catch (const HandlerException& e)
        {
            lg2::info("Legacy Handler produced exception, NetFn: {NETFN}, "
                      "Cmd: {CMD}: {ERROR}",
                      "NETFN", lg2::hex, request->ctx->netFn, "CMD", lg2::hex,
                      request->ctx->cmd, "ERROR", e);
            return errorResponse(request, e.code());
        }
        catch (const std::exception& e)
        {
            lg2::error("Legacy Handler failed to catch exception, "
                       "NetFn: {NETFN}, Cmd: {CMD}: {ERROR}",
                       "NETFN", lg2::hex, request->ctx->netFn, "CMD", lg2::hex,
                       request->ctx->cmd, "ERROR", e);
            return errorResponse(request, ccUnspecifiedError);
        }
        catch (const HandlerCompletion& c)
        {
            return errorResponse(request, c.code());
        }
        catch (...)
        {
            const char* what = currentExceptionType();
            lg2::error("Handler failed to catch exception, NetFn: {NETFN}, "
                       "Cmd: {CMD}: {ERROR}",
                       "NETFN", lg2::hex, request->ctx->netFn, "CMD", lg2::hex,
                       request->ctx->cmd, "ERROR", what);
            return errorResponse(request, ccUnspecifiedError);
        }
        response->cc = ccRet;
        response->payload.resize(len);
        return response;
    }
};

/**
 * @brief Legacy IPMI OEM handler class
 *
 * Legacy IPMI OEM handlers will resolve into this class, which will behave the
 * same way as the legacy IPMI queue, passing in a big buffer for the request
 * and a big buffer for the response.
 *
 * As soon as all the handlers have been rewritten, this class will be marked as
 * deprecated and eventually removed.
 */
template <>
class IpmiHandler<oem::Handler> final : public HandlerBase
{
  public:
    explicit IpmiHandler(const oem::Handler& handler) : handler_(handler) {}

  private:
    oem::Handler handler_;

    /** @brief call the registered handler with the request
     *
     * This is called from the running queue context after it has already
     * created a request object that contains all the information required to
     * execute the ipmi command. This function will return the response object
     * pointer that owns the response object that will ultimately get sent back
     * to the requester.
     *
     * Because this is the legacy variety of IPMI handler, this function does
     * not really have to do much other than pass the payload to the callback
     * and return response to the caller.
     *
     * @param request a shared_ptr to a Request object
     *
     * @return a shared_ptr to a Response object
     */
    message::Response::ptr executeCallback(
        message::Request::ptr request) override
    {
        message::Response::ptr response = request->makeResponse();
        // allocate a big response buffer here
        response->payload.resize(maxLegacyBufferSize);

        size_t len = request->payload.size() - request->payload.rawIndex;
        Cc ccRet{ccSuccess};
        try
        {
            ccRet =
                handler_(request->ctx->cmd,
                         request->payload.data() + request->payload.rawIndex,
                         response->payload.data(), &len);
        }
        catch (const HandlerException& e)
        {
            lg2::info("Legacy OEM Handler produced exception, NetFn: {NETFN}, "
                      "Cmd: {CMD}: {ERROR}",
                      "NETFN", lg2::hex, request->ctx->netFn, "CMD", lg2::hex,
                      request->ctx->cmd, "ERROR", e);
            return errorResponse(request, e.code());
        }
        catch (const std::exception& e)
        {
            lg2::error("Legacy OEM Handler failed to catch exception, "
                       "NetFn: {NETFN}, Cmd: {CMD}: {ERROR}",
                       "NETFN", lg2::hex, request->ctx->netFn, "CMD", lg2::hex,
                       request->ctx->cmd, "ERROR", e);
            return errorResponse(request, ccUnspecifiedError);
        }
        catch (const HandlerCompletion& c)
        {
            return errorResponse(request, c.code());
        }
        catch (...)
        {
            const char* what = currentExceptionType();
            lg2::error("Legacy failed to catch exception, NetFn: {NETFN}, "
                       "Cmd: {CMD}: {ERROR}",
                       "NETFN", lg2::hex, request->ctx->netFn, "CMD", lg2::hex,
                       request->ctx->cmd, "ERROR", what);
            return errorResponse(request, ccUnspecifiedError);
        }
        response->cc = ccRet;
        response->payload.resize(len);
        return response;
    }
};

/**
 * @brief create a legacy IPMI handler class and return a shared_ptr
 *
 * The queue uses a map of pointers to do the lookup. This function returns the
 * shared_ptr that owns the Handler object.
 *
 * This is called internally via the ipmi_register_callback function.
 *
 * @param handler the function pointer to the callback
 *
 * @return A shared_ptr to the created handler object
 */
inline auto makeLegacyHandler(const ipmid_callback_t& handler,
                              void* ctx = nullptr)
{
    HandlerBase::ptr ptr(new IpmiHandler<ipmid_callback_t>(handler, ctx));
    return ptr;
}

/**
 * @brief create a legacy IPMI OEM handler class and return a shared_ptr
 *
 * The queue uses a map of pointers to do the lookup. This function returns the
 * shared_ptr that owns the Handler object.
 *
 * This is called internally via the Router::registerHandler method.
 *
 * @param handler the function pointer to the callback
 *
 * @return A shared_ptr to the created handler object
 */
inline auto makeLegacyHandler(oem::Handler&& handler)
{
    HandlerBase::ptr ptr(
        new IpmiHandler<oem::Handler>(std::forward<oem::Handler>(handler)));
    return ptr;
}
#endif // ALLOW_DEPRECATED_API

/**
 * @brief create an IPMI handler class and return a shared_ptr
 *
 * The queue uses a map of pointers to do the lookup. This function returns the
 * shared_ptr that owns the Handler object.
 *
 * This is called internally via the ipmi::registerHandler function.
 *
 * @param handler the function pointer to the callback
 *
 * @return A shared_ptr to the created handler object
 */
template <typename Handler>
inline auto makeHandler(Handler&& handler)
{
    HandlerBase::ptr ptr(
        new IpmiHandler<Handler>(std::forward<Handler>(handler)));
    return ptr;
}

namespace impl
{

// IPMI command handler registration implementation
bool registerHandler(int prio, NetFn netFn, Cmd cmd, Privilege priv,
                     ::ipmi::HandlerBase::ptr handler);
bool registerGroupHandler(int prio, Group group, Cmd cmd, Privilege priv,
                          ::ipmi::HandlerBase::ptr handler);
bool registerOemHandler(int prio, Iana iana, Cmd cmd, Privilege priv,
                        ::ipmi::HandlerBase::ptr handler);

} // namespace impl

/**
 * @brief main IPMI handler registration function
 *
 * This function should be used to register all new-style IPMI handler
 * functions. This function just passes the callback to makeHandler, which
 * creates a new wrapper object that will automatically extract the appropriate
 * parameters for the callback function as well as pack up the response.
 *
 * @param prio - priority at which to register; see api.hpp
 * @param netFn - the IPMI net function number to register
 * @param cmd - the IPMI command number to register
 * @param priv - the IPMI user privilige required for this command
 * @param handler - the callback function that will handle this request
 *
 * @return bool - success of registering the handler
 */
template <typename Handler>
bool registerHandler(int prio, NetFn netFn, Cmd cmd, Privilege priv,
                     Handler&& handler)
{
    auto h = ipmi::makeHandler(std::forward<Handler>(handler));
    return impl::registerHandler(prio, netFn, cmd, priv, h);
}

/**
 * @brief register a IPMI OEM group handler
 *
 * From IPMI 2.0 spec Network Function Codes Table (Row 2Ch):
 * The first data byte position in requests and responses under this network
 * function identifies the defining body that specifies command functionality.
 * Software assumes that the command and completion code field positions will
 * hold command and completion code values.
 *
 * The following values are used to identify the defining body:
 * 00h PICMG - PCI Industrial Computer Manufacturer’s Group.  (www.picmg.com)
 * 01h DMTF Pre-OS Working Group ASF Specification (www.dmtf.org)
 * 02h Server System Infrastructure (SSI) Forum (www.ssiforum.org)
 * 03h VITA Standards Organization (VSO) (www.vita.com)
 * DCh DCMI Specifications (www.intel.com/go/dcmi)
 * all other Reserved
 *
 * When this network function is used, the ID for the defining body occupies
 * the first data byte in a request, and the second data byte (following the
 * completion code) in a response.
 *
 * @tparam Handler - implicitly specified callback function type
 * @param prio - priority at which to register; see api.hpp
 * @param netFn - the IPMI net function number to register
 * @param cmd - the IPMI command number to register
 * @param priv - the IPMI user privilige required for this command
 * @param handler - the callback function that will handle this request
 *
 * @return bool - success of registering the handler
 *
 */
template <typename Handler>
void registerGroupHandler(int prio, Group group, Cmd cmd, Privilege priv,
                          Handler&& handler)
{
    auto h = ipmi::makeHandler(handler);
    impl::registerGroupHandler(prio, group, cmd, priv, h);
}

/**
 * @brief register a IPMI OEM IANA handler
 *
 * From IPMI spec Network Function Codes Table (Row 2Eh):
 * The first three data bytes of requests and responses under this network
 * function explicitly identify the OEM or non-IPMI group that specifies the
 * command functionality. While the OEM or non-IPMI group defines the
 * functional semantics for the cmd and remaining data fields, the cmd field
 * is required to hold the same value in requests and responses for a given
 * operation in order to be supported under the IPMI message handling and
 * transport mechanisms.
 *
 * When this network function is used, the IANA Enterprise Number for the
 * defining body occupies the first three data bytes in a request, and the
 * first three data bytes following the completion code position in a
 * response.
 *
 * @tparam Handler - implicitly specified callback function type
 * @param prio - priority at which to register; see api.hpp
 * @param netFn - the IPMI net function number to register
 * @param cmd - the IPMI command number to register
 * @param priv - the IPMI user privilige required for this command
 * @param handler - the callback function that will handle this request
 *
 * @return bool - success of registering the handler
 *
 */
template <typename Handler>
void registerOemHandler(int prio, Iana iana, Cmd cmd, Privilege priv,
                        Handler&& handler)
{
    auto h = ipmi::makeHandler(handler);
    impl::registerOemHandler(prio, iana, cmd, priv, h);
}

} // namespace ipmi

#ifdef ALLOW_DEPRECATED_API
/**
 * @brief legacy IPMI handler registration function
 *
 * This function should be used to register all legacy IPMI handler
 * functions. This function just behaves just as the legacy registration
 * mechanism did, silently replacing any existing handler with a new one.
 *
 * @param netFn - the IPMI net function number to register
 * @param cmd - the IPMI command number to register
 * @param context - ignored
 * @param handler - the callback function that will handle this request
 * @param priv - the IPMI user privilige required for this command
 */
// [[deprecated("Use ipmi::registerHandler() instead")]]
void ipmi_register_callback(ipmi_netfn_t netFn, ipmi_cmd_t cmd,
                            ipmi_context_t context, ipmid_callback_t handler,
                            ipmi_cmd_privilege_t priv);

#endif /* ALLOW_DEPRECATED_API */
