OpenCores
URL https://opencores.org/ocsvn/wb2axip/wb2axip/trunk

Subversion Repositories wb2axip

[/] [wb2axip/] [trunk/] [bench/] [cpp/] [aximemsim.cpp] - Diff between revs 8 and 16

Only display areas with differences | Details | Blame | View Log

Rev 8 Rev 16
////////////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////////////
//
//
// Filename:    aximemsim.cpp
// Filename:    aximemsim.cpp
//
//
// Project:     Pipelined Wishbone to AXI converter
// Project:     Pipelined Wishbone to AXI converter
//
//
// Purpose:     
// Purpose:     
//
//
// Creator:     Dan Gisselquist, Ph.D.
// Creator:     Dan Gisselquist, Ph.D.
//              Gisselquist Technology, LLC
//              Gisselquist Technology, LLC
//
//
////////////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////////////
//
//
// Copyright (C) 2016, Gisselquist Technology, LLC
// Copyright (C) 2016-2018, Gisselquist Technology, LLC
//
//
// This program is free software (firmware): you can redistribute it and/or
// This file is part of the pipelined Wishbone to AXI converter project, a
// modify it under the terms of  the GNU General Public License as published
// project that contains multiple bus bridging designs and formal bus property
// by the Free Software Foundation, either version 3 of the License, or (at
// sets.
// your option) any later version.
//
//
// The bus bridge designs and property sets are free RTL designs: you can
// This program is distributed in the hope that it will be useful, but WITHOUT
// redistribute them and/or modify any of them under the terms of the GNU
// ANY WARRANTY; without even the implied warranty of MERCHANTIBILITY or
// Lesser General Public License as published by the Free Software Foundation,
// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
// either version 3 of the License, or (at your option) any later version.
// for more details.
//
//
// The bus bridge designs and property sets are distributed in the hope that
// You should have received a copy of the GNU General Public License along
// they will be useful, but WITHOUT ANY WARRANTY; without even the implied
// with this program.  (It's in the $(ROOT)/doc directory, run make with no
// warranty of MERCHANTIBILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
// target there if the PDF file isn't present.)  If not, see
// GNU Lesser General Public License for more details.
 
//
 
// You should have received a copy of the GNU Lesser General Public License
 
// along with these designs.  (It's in the $(ROOT)/doc directory.  Run make
 
// with no target there if the PDF file isn't present.)  If not, see
// <http://www.gnu.org/licenses/> for a copy.
// <http://www.gnu.org/licenses/> for a copy.
//
//
// License:     GPL, v3, as defined and found on www.gnu.org,
// License:     LGPL, v3, as defined and found on www.gnu.org,
//              http://www.gnu.org/licenses/gpl.html
//              http://www.gnu.org/licenses/lgpl.html
//
 
//
//
////////////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////////////
//
//
//
//
#include <stdio.h>
#include <stdio.h>
 
 
#include "aximemsim.h"
#include "aximemsim.h"
 
 
class   ADRFIFO {
class   ADRFIFO {
        typedef {
        typedef {
                int id; unsigned addr;
                int id; unsigned addr;
        } ADRFIFOELEMENT;
        } ADRFIFOELEMENT;
        int     m_head, m_tail, m_len;
        int     m_head, m_tail, m_len;
        int     *m_mem;
        int     *m_mem;
public:
public:
        ADRFIFO(int ln) {
        ADRFIFO(int ln) {
                m_mem = new ADRFIFOELEMENT[ln];
                m_mem = new ADRFIFOELEMENT[ln];
                m_head = m_tail = 0;
                m_head = m_tail = 0;
                m_len = ln;
                m_len = ln;
        }
        }
 
 
        void    push(int id, unsigned addr) {
        void    push(int id, unsigned addr) {
                int nhead = m_head + 1;
                int nhead = m_head + 1;
                if (nhead >= m_len)
                if (nhead >= m_len)
                        nhead = 0;
                        nhead = 0;
                assert(nhead != m_tail);
                assert(nhead != m_tail);
                m_mem[m_head].id   = id;
                m_mem[m_head].id   = id;
                m_mem[m_head].addr = addr;
                m_mem[m_head].addr = addr;
                m_head = nhead;
                m_head = nhead;
        }
        }
 
 
        bool    full(void) {
        bool    full(void) {
                int nhead = m_head + 1;
                int nhead = m_head + 1;
                if (nhead >= m_len)
                if (nhead >= m_len)
                        nhead = 0;
                        nhead = 0;
                return (nhead == m_tail);
                return (nhead == m_tail);
        }
        }
 
 
        bool    valid(void) {
        bool    valid(void) {
                return (m_head != m_tail);
                return (m_head != m_tail);
        }
        }
 
 
        int     id(void)        { return m_mem[m_tail].id; }
        int     id(void)        { return m_mem[m_tail].id; }
        int     addr(void)      { return m_mem[m_tail].addr; }
        int     addr(void)      { return m_mem[m_tail].addr; }
        int     pop(void)       {
        int     pop(void)       {
                if (m_tail == m_head)
                if (m_tail == m_head)
                        return;
                        return;
                m_tail++;
                m_tail++;
                if (m_tail >= m_len)
                if (m_tail >= m_len)
                        m_tail = 0;
                        m_tail = 0;
        }
        }
};
};
 
 
class   DATFIFO {
class   DATFIFO {
        typedef {
        typedef {
                unsigned data[4];
                unsigned data[4];
                int     strb;
                int     strb;
        } DATAFIFOELEMENT;
        } DATAFIFOELEMENT;
        int     m_head, m_tail, m_len;
        int     m_head, m_tail, m_len;
        int     *m_mem;
        int     *m_mem;
public:
public:
        DATAFIFO(int ln) {
        DATAFIFO(int ln) {
                m_mem = new DATAFIFOELEMENT[ln];
                m_mem = new DATAFIFOELEMENT[ln];
                m_head = m_tail = 0;
                m_head = m_tail = 0;
                m_len = ln;
                m_len = ln;
        }
        }
 
 
        void    push(int strb, unsigned dat0, unsigned dat1,
        void    push(int strb, unsigned dat0, unsigned dat1,
                        unsigned dat, unsigned dat3) {
                        unsigned dat, unsigned dat3) {
                int nhead = m_head + 1;
                int nhead = m_head + 1;
                if (nhead >= m_len)
                if (nhead >= m_len)
                        nhead = 0;
                        nhead = 0;
                assert(nhead != m_tail);
                assert(nhead != m_tail);
                m_mem[m_head].strb   = id;
                m_mem[m_head].strb   = id;
                m_mem[m_head].data[0] = dat0;
                m_mem[m_head].data[0] = dat0;
                m_mem[m_head].data[1] = dat1;
                m_mem[m_head].data[1] = dat1;
                m_mem[m_head].data[2] = dat2;
                m_mem[m_head].data[2] = dat2;
                m_mem[m_head].data[3] = dat3;
                m_mem[m_head].data[3] = dat3;
                m_head = nhead;
                m_head = nhead;
        }
        }
 
 
        bool    full(void) {
        bool    full(void) {
                int nhead = m_head + 1;
                int nhead = m_head + 1;
                if (nhead >= m_len)
                if (nhead >= m_len)
                        nhead = 0;
                        nhead = 0;
                return (nhead == m_tail);
                return (nhead == m_tail);
        }
        }
 
 
        bool    valid(void) {
        bool    valid(void) {
                return (m_head != m_tail);
                return (m_head != m_tail);
        }
        }
 
 
        int     strb(void)      { return m_mem[m_tail].strb; }
        int     strb(void)      { return m_mem[m_tail].strb; }
        unsigned *data(void)    { return &m_mem[m_tail].data[0]; }
        unsigned *data(void)    { return &m_mem[m_tail].data[0]; }
        int     pop(void)       {
        int     pop(void)       {
                if (m_tail == m_head)
                if (m_tail == m_head)
                        return;
                        return;
                m_tail++;
                m_tail++;
                if (m_tail >= m_len)
                if (m_tail >= m_len)
                        m_tail = 0;
                        m_tail = 0;
        }
        }
};
};
 
 
AXIMEMSIM::AXIMEMSIM(unsigned abits) {
AXIMEMSIM::AXIMEMSIM(unsigned abits) {
        // abits is the number of bits in a memory address, referencing 8-bit
        // abits is the number of bits in a memory address, referencing 8-bit
        // bytes, therefore we can size our memory properly.
        // bytes, therefore we can size our memory properly.
        assert(abits>2);
        assert(abits>2);
        m_len = (1<<(abits-2));
        m_len = (1<<(abits-2));
        m_mask= m_len-1;
        m_mask= m_len-1;
        m_mem = new unsigned[(1<<(abits-2))];
        m_mem = new unsigned[(1<<(abits-2))];
 
 
        memset(m_mem, 0, sizeof(unsigned)<<(abits-2));
        memset(m_mem, 0, sizeof(unsigned)<<(abits-2));
}
}
 
 
void AXIMEMSIM::apply(AXIBUS &bus) {
void AXIMEMSIM::apply(AXIBUS &bus) {
        // First, let's validate our inputs ..., and queue up our outputs
        // First, let's validate our inputs ..., and queue up our outputs
        bus.ar.ready = (!m_readfifo.full());
        bus.ar.ready = (!m_readfifo.full());
        bus.aw.ready = (!m_writefifo.full());
        bus.aw.ready = (!m_writefifo.full());
        bus.w.ready  = (!m_wdata.full());
        bus.w.ready  = (!m_wdata.full());
        if (bus.r.ready)
        if (bus.r.ready)
                bus.r.valid = false;
                bus.r.valid = false;
        if (bus.b.ready)
        if (bus.b.ready)
                bus.b.valid = false;
                bus.b.valid = false;
 
 
        if ((bus.ar.ready)&&(!m_readfifo.full())) {
        if ((bus.ar.ready)&&(!m_readfifo.full())) {
                assert(bus.ar.len  == 0);
                assert(bus.ar.len  == 0);
                assert(bus.ar.size  == 5);
                assert(bus.ar.size  == 5);
                assert(bus.ar.burst == 1);
                assert(bus.ar.burst == 1);
                assert(bus.ar.lock  == 0);
                assert(bus.ar.lock  == 0);
                assert(bus.ar.cache == 2);
                assert(bus.ar.cache == 2);
                assert(bus.ar.prot  == 2);
                assert(bus.ar.prot  == 2);
                assert(bus.ar.qos   == 0);
                assert(bus.ar.qos   == 0);
 
 
                m_readfifo.push(bus.ar.id, bus.ar.addr);
                m_readfifo.push(bus.ar.id, bus.ar.addr);
        }
        }
 
 
        if ((bus.aw.ready)&&(!m_writefifo.full())) {
        if ((bus.aw.ready)&&(!m_writefifo.full())) {
                assert(bus.aw.len   == 0);
                assert(bus.aw.len   == 0);
                assert(bus.aw.size  == 5);
                assert(bus.aw.size  == 5);
                assert(bus.aw.burst == 1);
                assert(bus.aw.burst == 1);
                assert(bus.aw.lock  == 0);
                assert(bus.aw.lock  == 0);
                assert(bus.aw.cache == 2);
                assert(bus.aw.cache == 2);
                assert(bus.aw.prot  == 2);
                assert(bus.aw.prot  == 2);
                assert(bus.aw.qos   == 0);
                assert(bus.aw.qos   == 0);
 
 
                m_awfifo.push(bus.aw.id, bus.aw.addr);
                m_awfifo.push(bus.aw.id, bus.aw.addr);
        }
        }
 
 
        if ((bus.w.ready)&&(!m_writedata.full())) {
        if ((bus.w.ready)&&(!m_writedata.full())) {
                m_writefifo.push(bus.aw.strb, bus.aw.data[0], bus.aw.data[1],
                m_writefifo.push(bus.aw.strb, bus.aw.data[0], bus.aw.data[1],
                        bus.aw.data[2], bus.aw.data[3]);
                        bus.aw.data[2], bus.aw.data[3]);
 
 
        if (m_respfifo[m_now].valid) {
        if (m_respfifo[m_now].valid) {
                if (m_respfifo[m_now].read) {
                if (m_respfifo[m_now].read) {
                        if ((!bus.r.valid)||(bus.r.ready)) {
                        if ((!bus.r.valid)||(bus.r.ready)) {
                                bus.r.data[0] = m_respfifo[m_now].data[0];
                                bus.r.data[0] = m_respfifo[m_now].data[0];
                                bus.r.data[1] = m_respfifo[m_now].data[1];
                                bus.r.data[1] = m_respfifo[m_now].data[1];
                                bus.r.data[2] = m_respfifo[m_now].data[2];
                                bus.r.data[2] = m_respfifo[m_now].data[2];
                                bus.r.data[3] = m_respfifo[m_now].data[3];
                                bus.r.data[3] = m_respfifo[m_now].data[3];
                                bus.r.valid = true;
                                bus.r.valid = true;
                                m_now++;
                                m_now++;
                        }
                        }
                } else if ((!bus.b.valid)||(bus.b.ready)) {
                } else if ((!bus.b.valid)||(bus.b.ready)) {
                        bus.b.resp = m_respfifo[m_now].resp;
                        bus.b.resp = m_respfifo[m_now].resp;
                        bus.b.id = m_respfifo[m_now].id;
                        bus.b.id = m_respfifo[m_now].id;
                        bus.b.valid = true;
                        bus.b.valid = true;
                        m_now++;
                        m_now++;
                }
                }
        }
        }
}
}
 
 
 
 

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.