/*****************************************************************************

  Licensed to Accellera Systems Initiative Inc. (Accellera) under one or
  more contributor license agreements.  See the NOTICE file distributed
  with this work for additional information regarding copyright ownership.
  Accellera licenses this file to you 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 __SYSTEMC_EXT_TLM_CORE_1_REQ_RSP_CHANNELS_FIFO_FIFO_HH__
#define __SYSTEMC_EXT_TLM_CORE_1_REQ_RSP_CHANNELS_FIFO_FIFO_HH__

//
// This implements put, get and peek
//
// It also implements 0 and infinite size fifos - but the size
// zero fifos aren't rendezvous like zero length fifos, they simply are both
// full and empty at the same time.
//
// The size can be dynamically changed using the resize interface
//
// To get an infinite fifo use a -ve size in the constructor.
// The absolute value of the size is taken as the starting size of the
// actual physical buffer.
//

#include "tlm_core/1/req_rsp/channels/fifo/circular_buffer.hh"
#include "tlm_core/1/req_rsp/interfaces/fifo_ifs.hh"

namespace tlm
{

template <typename T>
class tlm_fifo : public virtual tlm_fifo_get_if<T>,
    public virtual tlm_fifo_put_if<T>, public sc_core::sc_prim_channel
{
  public:
    // Constructors.
    explicit tlm_fifo(int size_=1) :
        sc_core::sc_prim_channel(sc_core::sc_gen_unique_name("fifo"))
    {
        init(size_);
    }

    explicit tlm_fifo(const char *name_, int size_=1) :
        sc_core::sc_prim_channel(name_)
    {
        init(size_);
    }

    // Destructor..
    virtual ~tlm_fifo() {}

    // Tlm get interface.
    T get(tlm_tag<T> * =nullptr);

    bool nb_get(T &);
    bool nb_can_get(tlm_tag<T> * =nullptr) const;
    const sc_core::sc_event &
    ok_to_get(tlm_tag<T> * =nullptr) const
    {
        return m_data_written_event;
    }

    // Tlm peek interface.
    T peek(tlm_tag<T> * =nullptr) const;

    bool nb_peek(T &) const;
    bool nb_can_peek(tlm_tag<T> * =nullptr) const;
    const sc_core::sc_event &
    ok_to_peek(tlm_tag<T> * =nullptr) const
    {
        return m_data_written_event;
    }

    // Tlm put interface.
    void put(const T &);

    bool nb_put(const T &);
    bool nb_can_put(tlm_tag<T> * =nullptr) const;
    const sc_core::sc_event &
    ok_to_put(tlm_tag<T> * =nullptr) const
    {
        return m_data_read_event;
    }

    // Resize if.
    void nb_expand(unsigned int n=1);
    void nb_unbound(unsigned int n=16);

    bool nb_reduce(unsigned int n=1);
    bool nb_bound(unsigned int n);

    // Debug interface.
    bool nb_peek(T &, int n) const;
    bool nb_poke(const T &, int n=0);

    int used() const { return m_num_readable - m_num_read; }
    int size() const { return m_size; }

    void
    debug() const
    {
        if (is_empty())
            std::cout << "empty" << std::endl;
        if (is_full())
            std::cout << "full" << std::endl;

        std::cout << "size " << size() << " - " << used() << " used "
                  << std::endl;
        std::cout << "readable " << m_num_readable << std::endl;
        std::cout << "written/read " << m_num_written << "/" << m_num_read
                  << std::endl;
    }

    // Support functions.
    static const char * const kind_string;
    const char *kind() const { return kind_string; }

  protected:
    sc_core::sc_event &
    read_event(tlm_tag<T> * =nullptr)
    {
        return m_data_read_event;
    }

    void update();
    void init(int);

    circular_buffer<T> buffer;

    int m_size; // logical size of fifo

    int m_num_readable; // #samples readable
    int m_num_read; // #samples read during this delta cycle
    int m_num_written; // #samples written during this delta cycle
    bool m_expand; // has an expand occurred during this delta cycle ?
    // #samples read without notify during this delta cycle
    int m_num_read_no_notify;

    sc_core::sc_event m_data_read_event;
    sc_core::sc_event m_data_written_event;

  private:
    // disabled
    tlm_fifo(const tlm_fifo<T> &);
    tlm_fifo &operator = (const tlm_fifo<T> &);

    //
    // use nb_can_get() and nb_can_put() rather than the following two
    // private functions
    //

    bool is_empty() const { return used() == 0; }

    bool
    is_full() const
    {
        if (size() < 0)
            return false;
        else
            return size() <= m_num_readable + m_num_written;
    }
};

template <typename T>
const char *const tlm_fifo<T>::kind_string = "tlm_fifo";

/******************************************************************
//
// init and update
//
******************************************************************/

template <typename T>
inline void
tlm_fifo<T>::init(int size_)
{
    if (size_ > 0) {
        buffer.resize( size_ );
    } else if (size_ < 0) {
        buffer.resize(-size_);
    } else {
        buffer.resize(16);
    }

    m_size = size_;
    m_num_readable = 0;
    m_num_read = 0;
    m_num_written = 0;
    m_expand = false;
    m_num_read_no_notify = false;
}

template <typename T>
inline void
tlm_fifo<T>::update()
{
    if (m_num_read > m_num_read_no_notify || m_expand) {
        m_data_read_event.notify(sc_core::SC_ZERO_TIME);
    }

    if (m_num_written > 0) {
        m_data_written_event.notify(sc_core::SC_ZERO_TIME);
    }

    m_expand = false;
    m_num_read = 0;
    m_num_written = 0;
    m_num_readable = buffer.used();
    m_num_read_no_notify = 0;
}

} // namespace tlm

#include "tlm_core/1/req_rsp/channels/fifo/fifo_peek.hh"
#include "tlm_core/1/req_rsp/channels/fifo/fifo_put_get.hh"
#include "tlm_core/1/req_rsp/channels/fifo/fifo_resize.hh"

#endif /* __SYSTEMC_EXT_TLM_CORE_1_REQ_RSP_CHANNELS_FIFO_FIFO_HH__ */
