/*
 * Copyright (c) 2017 Cisco and/or its affiliates.
 * 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.
 */

#ifndef __VOM_RPC_CMD_H__
#define __VOM_RPC_CMD_H__

#include <future>

#include "vom/cmd.hpp"
#include "vom/logger.hpp"

namespace VOM {
/**
 * A base class for all RPC commands to VPP.
 *  RPC commands are one of the sub-set of command types to VPP
 * that modify/create state in VPP and thus return an error code.
 * Commands are issued in one thread context, but read in another. The
 * command has an associated std::promise that is met by the RX thread.
 * this allows the sender, which waits on the promise's future, to
 * experience a synchronous command.
 *
 * The command is templatised on the type of the HW::item to be set by
 * the command, and the data returned in the promise,
 */
template <typename HWITEM, typename DATA, typename MSG>
class rpc_cmd : public cmd
{
public:
  /**
   * convenient typedef
   */
  typedef MSG msg_t;

  /**
   * Constructor taking the HW item that will be updated by the command
   */
  rpc_cmd(HWITEM& item)
    : cmd()
    , m_hw_item(item)
    , m_promise()
  {
  }

  /**
   * Desructor
   */
  virtual ~rpc_cmd() {}

  /**
   * return the HW item the command updates
   */
  HWITEM& item() { return m_hw_item; }

  /**
   * return the const HW item the command updates
   */
  const HWITEM& item() const { return m_hw_item; }

  /**
   * Fulfill the commands promise. Called from the RX thread
   */
  void fulfill(const DATA& d)
  {
    m_promise.set_value(d);

    /*
     * we reset the promise after setting the value to reuse it
     * when we run the retire command from the same cmd object
     */
    //    m_promise = std::promise<DATA>();
  }

  /**
   * Wait on the commands promise. i.e. block on the completion
   * of the command.
   */
  DATA wait()
  {
    std::future_status status;
    std::future<DATA> result;

    result = m_promise.get_future();
    status = result.wait_for(std::chrono::seconds(5));

    if (status != std::future_status::ready) {
      return (DATA(rc_t::TIMEOUT));
    }

    return (result.get());
  }

  /**
   * Called by the HW Command Q when it is disabled to indicate the
   * command can be considered successful without issuing it to HW
   */
  virtual void succeeded()
  {
    m_hw_item.set(rc_t::OK);
    VOM_LOG(log_level_t::DEBUG) << to_string();
  }

  /**
   * call operator used as a callback by VAPI when the reply is available
   */
  virtual vapi_error_e operator()(MSG& reply)
  {
    int retval = reply.get_response().get_payload().retval;
    VOM_LOG(log_level_t::DEBUG) << to_string() << " " << retval;
    fulfill(rc_t::from_vpp_retval(retval));

    return (VAPI_OK);
  }

  /**
   * Retire/cancel a long running command
   */
  virtual void retire(connection& con) {}

protected:
  /**
   * A reference to an object's HW::item that the command will update
   */
  HWITEM& m_hw_item;

  /**
   * The promise that implements the synchronous issue
   */
  std::promise<DATA> m_promise;
};
};

/*
 * fd.io coding-style-patch-verification: ON
 *
 * Local Variables:
 * eval: (c-set-style "mozilla")
 * End:
 */

#endif
