Index: trunk/modules/vci_block_device_tsar/caba/source/src/vci_block_device_tsar.cpp
===================================================================
--- trunk/modules/vci_block_device_tsar/caba/source/src/vci_block_device_tsar.cpp	(revision 374)
+++ trunk/modules/vci_block_device_tsar/caba/source/src/vci_block_device_tsar.cpp	(revision 374)
@@ -0,0 +1,684 @@
+/* -*- c++ -*-
+ *
+ * SOCLIB_LGPL_HEADER_BEGIN
+ * 
+ * This file is part of SoCLib, GNU LGPLv2.1.
+ * 
+ * SoCLib is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU Lesser General Public License as published
+ * by the Free Software Foundation; version 2.1 of the License.
+ * 
+ * SoCLib is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ * 
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with SoCLib; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+ * 02110-1301 USA
+ * 
+ * SOCLIB_LGPL_HEADER_END
+ *
+ * Copyright (c) UPMC, Lip6, Asim
+ *         alain.greiner@lip6.fr april 2011
+ *
+ * Maintainers: alain
+ */
+
+#include <stdint.h>
+#include <iostream>
+#include <fcntl.h>
+#include "vci_block_device_tsar.h"
+
+namespace soclib { namespace caba {
+
+#define tmpl(t) template<typename vci_param> t VciBlockDeviceTsar<vci_param>
+
+using namespace soclib::caba;
+using namespace soclib::common;
+
+////////////////////////
+tmpl(void)::transition()
+{
+    if(p_resetn.read() == false) 
+    {
+        r_initiator_fsm = M_IDLE;
+        r_target_fsm    = T_IDLE;
+        r_irq_enable    = true;
+        r_go            = false;
+        return;
+    } 
+
+    //////////////////////////////////////////////////////////////////////////////
+    // The Target FSM controls the following registers:
+    // r_target_fsm, r_irq_enable, r_nblocks, r_buf adress, r_lba, r_go, r_read
+    //////////////////////////////////////////////////////////////////////////////
+
+    switch(r_target_fsm) {
+    ////////////
+    case T_IDLE:
+    {
+        if ( p_vci_target.cmdval.read() ) 
+        { 
+            r_srcid = p_vci_target.srcid.read();
+            r_trdid = p_vci_target.trdid.read();
+            r_pktid = p_vci_target.pktid.read();
+            sc_dt::sc_uint<vci_param::N> address = p_vci_target.address.read();
+            bool                  read    = (p_vci_target.cmd.read() == vci_param::CMD_READ);
+            uint32_t              cell    = (uint32_t)((address & 0x1F)>>2);
+
+            if     ( !read && !m_segment.contains(address) )      r_target_fsm = T_WRITE_ERROR;
+            else if(  read && !m_segment.contains(address) )      r_target_fsm = T_READ_ERROR;
+            else if( !read && !p_vci_target.eop.read() )          r_target_fsm = T_WRITE_ERROR;
+            else if(  read && !p_vci_target.eop.read() )          r_target_fsm = T_READ_ERROR;
+            else if( !read && (cell == BLOCK_DEVICE_BUFFER) )     r_target_fsm = T_WRITE_BUFFER;
+            else if(  read && (cell == BLOCK_DEVICE_BUFFER) )     r_target_fsm = T_READ_BUFFER;
+            else if( !read && (cell == BLOCK_DEVICE_COUNT) )      r_target_fsm = T_WRITE_COUNT;
+            else if(  read && (cell == BLOCK_DEVICE_COUNT) )      r_target_fsm = T_READ_COUNT;
+            else if( !read && (cell == BLOCK_DEVICE_LBA) )        r_target_fsm = T_WRITE_LBA;
+            else if(  read && (cell == BLOCK_DEVICE_LBA) )        r_target_fsm = T_READ_LBA;
+            else if( !read && (cell == BLOCK_DEVICE_OP) )         r_target_fsm = T_WRITE_OP;
+            else if(  read && (cell == BLOCK_DEVICE_STATUS) )     r_target_fsm = T_READ_STATUS;
+            else if( !read && (cell == BLOCK_DEVICE_IRQ_ENABLE) ) r_target_fsm = T_WRITE_IRQEN;
+            else if(  read && (cell == BLOCK_DEVICE_IRQ_ENABLE) ) r_target_fsm = T_READ_IRQEN;
+            else if(  read && (cell == BLOCK_DEVICE_SIZE) )       r_target_fsm = T_READ_SIZE;
+            else if(  read && (cell == BLOCK_DEVICE_BLOCK_SIZE) ) r_target_fsm = T_READ_BLOCK;
+        }
+        break;
+    }
+    ////////////////////
+    case T_WRITE_BUFFER:
+    {
+        if ( r_initiator_fsm == M_IDLE )  r_buf_address = (uint32_t)p_vci_target.wdata.read();
+        if ( p_vci_target.rspack.read() ) r_target_fsm = T_IDLE;
+        break;
+    }
+    ///////////////////
+    case T_WRITE_COUNT:
+    {
+        if ( r_initiator_fsm == M_IDLE )  r_nblocks = (uint32_t)p_vci_target.wdata.read();
+        if ( p_vci_target.rspack.read() ) r_target_fsm = T_IDLE;
+        break;
+    }
+    /////////////////
+    case T_WRITE_LBA:
+    {
+        if ( r_initiator_fsm == M_IDLE )  r_lba = (uint32_t)p_vci_target.wdata.read();
+        if ( p_vci_target.rspack.read() ) r_target_fsm = T_IDLE;
+        break;
+    }
+    ////////////////
+    case T_WRITE_OP:
+    {
+        if ( r_initiator_fsm == M_IDLE ) 
+        {
+            if ( (uint32_t)p_vci_target.wdata.read() == BLOCK_DEVICE_READ )
+            {
+                r_read = true;
+                r_go = true;
+            }
+            else if ( (uint32_t)p_vci_target.wdata.read() == BLOCK_DEVICE_WRITE)
+            {
+                r_read = false;
+                r_go = true;
+            }
+        }
+        if ( p_vci_target.rspack.read() ) r_target_fsm = T_IDLE;
+        break;
+    }
+    ///////////////////
+    case T_WRITE_IRQEN:
+    {
+        r_irq_enable = (p_vci_target.wdata.read() != 0);
+        if ( p_vci_target.rspack.read() ) r_target_fsm = T_IDLE;
+        break;
+    }
+    ///////////////////
+    case T_READ_BUFFER:
+    case T_READ_COUNT:
+    case T_READ_LBA:
+    case T_READ_IRQEN:
+    case T_READ_SIZE:
+    case T_READ_BLOCK:
+    case T_READ_ERROR:
+    case T_WRITE_ERROR:
+    {
+        if ( p_vci_target.rspack.read() ) r_target_fsm = T_IDLE;
+        break;
+    }
+    ///////////////////
+    case T_READ_STATUS:
+    {
+        if ( p_vci_target.rspack.read() ) 
+        {
+            r_target_fsm = T_IDLE;
+            if( (r_initiator_fsm == M_READ_SUCCESS ) ||
+                (r_initiator_fsm == M_READ_ERROR   ) ||
+                (r_initiator_fsm == M_WRITE_SUCCESS) ||
+                (r_initiator_fsm == M_WRITE_ERROR  ) ) r_go = false;
+        }
+        break;
+    }
+    } // end switch target fsm
+	
+    //////////////////////////////////////////////////////////////////////////////
+    // The initiator FSM executes a loop, transfering one block per iteration.
+    // Each block is split in bursts, and the number of bursts depends
+    // on the memory buffer alignment on a burst boundary:
+    // - If buffer aligned, all burst have the same length (m_flits_per burst)
+    //   and the number of bursts is (m_bursts_per_block).
+    // - If buffer not aligned, the number of bursts is (m_bursts_per_block + 1)
+    //   and first and last burst are shorter, because all flits in a burst 
+    //   must be contained in a single cache line.
+    //   first burst => nflits = m_flits_per_burst - offset
+    //   last  burst => nflits = offset
+    //   other burst => nflits = m_flits_per_burst
+    //////////////////////////////////////////////////////////////////////////////
+
+    switch( r_initiator_fsm.read() ) {
+    ////////////
+    case M_IDLE: 	// check buffer alignment to compute the number of bursts
+    {
+        if ( r_go.read() ) 
+        {
+            r_index         = 0;
+            r_block_count   = 0;
+            r_burst_count   = 0;
+            r_flit_count    = 0;
+            r_latency_count = m_latency;
+
+            // compute r_burst_offset (zero when buffer aligned)
+            r_burst_offset = (r_buf_address.read()>>2) % m_flits_per_burst;
+
+            // start tranfer
+            if ( r_read.read() ) 	r_initiator_fsm = M_READ_BLOCK;
+            else                    r_initiator_fsm = M_WRITE_BURST;
+        }
+        break;
+    } 
+    //////////////////
+    case M_READ_BLOCK:  // read one block from disk after waiting m_latency cycles
+    {
+        if ( r_latency_count.read() == 0 )
+        {
+            r_latency_count = m_latency;
+            ::lseek(m_fd, (r_lba + r_block_count)*m_flits_per_block*4, SEEK_SET);
+            if( ::read(m_fd, r_local_buffer, m_flits_per_block*4) < 0 )  
+            {
+                r_initiator_fsm = M_READ_ERROR;
+            }
+            else   
+            {
+                r_burst_count   = 0;
+                r_flit_count    = 0;
+                r_initiator_fsm = M_READ_BURST;
+            }
+        }
+        else
+        {
+            r_latency_count = r_latency_count.read() - 1;
+        }
+        break;
+    }
+    //////////////////
+    case M_READ_BURST:  // Compute the number of flits in the burst
+    {
+        uint32_t offset = r_burst_offset.read();
+
+        if ( offset )                  // buffer not aligned
+        {
+            if ( r_burst_count.read() == 0 ) r_burst_nflits = m_flits_per_burst - offset;
+            else if ( r_burst_count.read() == m_bursts_per_block ) r_burst_nflits = offset;
+            else r_burst_nflits = m_flits_per_burst;
+        }
+        else                           // buffer aligned
+        {
+            r_burst_nflits = m_flits_per_burst;
+        }
+        r_initiator_fsm =  M_READ_CMD;
+        break;
+    }
+    ////////////////
+    case M_READ_CMD:	// Send a multi-flits VCI WRITE command
+    {
+        if ( p_vci_initiator.cmdack.read() )
+        {
+            if ( r_flit_count == (r_burst_nflits.read() - 1) ) // last flit in a burst
+            {
+                r_initiator_fsm = M_READ_RSP;
+                r_flit_count = 0;
+            }
+            else                                               // not the last flit
+            {
+                r_flit_count = r_flit_count.read() + 1;
+            }
+
+            // compute next flit address and next local buffer index
+            r_buf_address = r_buf_address.read() + 4;
+            r_index       = r_index.read() + 1;
+        }
+        break;
+    }
+    ////////////////
+    case M_READ_RSP: 	// Wait a single flit VCI WRITE response
+    {
+        if ( p_vci_initiator.rspval.read() )
+        {
+            bool aligned = (r_burst_offset.read() == 0);
+
+            if ( (p_vci_initiator.rerror.read()&0x1) != 0 ) 
+            {
+                r_initiator_fsm = M_READ_ERROR;
+            }
+            else if ( (not aligned and (r_burst_count.read() == m_bursts_per_block)) or 
+                      (aligned and (r_burst_count.read() == (m_bursts_per_block-1))) )
+            {
+                if ( r_block_count.read() == (r_nblocks.read()-1) ) // last burst of last block 
+                {
+                    r_initiator_fsm = M_READ_SUCCESS;
+                }
+                else                                              // last burst not last block
+                {
+                    r_index          = 0;
+                    r_burst_count    = 0;
+                    r_block_count    = r_block_count.read() + 1;
+                    r_initiator_fsm  = M_READ_BLOCK;
+                }
+            }
+            else                                                // not the last burst
+            {
+                r_burst_count = r_burst_count.read() + 1;
+                r_initiator_fsm = M_READ_BURST;
+            }
+        }
+        break;
+    }
+    ///////////////////
+    case M_READ_SUCCESS:
+    case M_READ_ERROR:
+    {
+        if( !r_go ) r_initiator_fsm = M_IDLE;
+        break;
+    }
+    ///////////////////
+    case M_WRITE_BURST:  // Compute the number of flits in the burst
+    {
+        uint32_t offset = r_burst_offset.read();
+
+        if ( offset )                  // buffer not aligned
+        {
+            if ( r_burst_count.read() == 0 ) r_burst_nflits = m_flits_per_burst - offset;
+            else if ( r_burst_count.read() == m_bursts_per_block ) r_burst_nflits = offset;
+            else r_burst_nflits = m_flits_per_burst;
+        }
+        else                           // buffer aligned
+        {
+            r_burst_nflits = m_flits_per_burst;
+        }
+        r_initiator_fsm =  M_WRITE_CMD;
+        break;
+    }
+    /////////////////
+    case M_WRITE_CMD:	// This is actually a single flit VCI READ command
+    {
+	    if ( p_vci_initiator.cmdack.read() ) r_initiator_fsm = M_WRITE_RSP;
+        break;
+    }
+    /////////////////
+    case M_WRITE_RSP:	// This is actually a multi-flits VCI READ response
+    {
+        bool aligned = (r_burst_offset.read() == 0);
+
+        if ( p_vci_initiator.rspval.read() )
+        {
+            r_local_buffer[r_index.read()] = (uint32_t)p_vci_initiator.rdata.read();
+            r_index = r_index.read() + 1;
+
+            if ( p_vci_initiator.reop.read() )  // last flit of the burst
+            {
+	        r_flit_count  = 0;
+                r_buf_address = r_buf_address.read() + (r_burst_nflits.read()<<2); 
+
+	        if( (p_vci_initiator.rerror.read()&0x1) != 0 ) 
+                {
+                    r_initiator_fsm = M_WRITE_ERROR;
+                }
+                else if ( (not aligned and (r_burst_count.read() == m_bursts_per_block)) or 
+                          (aligned and (r_burst_count.read() == (m_bursts_per_block-1))) ) // last burst
+                {
+                    r_initiator_fsm  = M_WRITE_BLOCK;
+                }
+                else                                          // not the last burst
+                {
+                    r_burst_count = r_burst_count.read() + 1;
+                    r_initiator_fsm = M_WRITE_BURST;
+                }
+            }
+            else
+            {
+	            r_flit_count = r_flit_count.read() + 1;
+            }
+        }
+        break;
+    }
+    ///////////////////
+    case M_WRITE_BLOCK:		// write a block to disk after waiting m_latency cycles
+    {
+        if ( r_latency_count == 0 )
+        {
+            r_latency_count = m_latency;
+            ::lseek(m_fd, (r_lba + r_block_count)*m_flits_per_block*vci_param::B, SEEK_SET);
+            if( ::write(m_fd, r_local_buffer, m_flits_per_block*vci_param::B) < 0 )
+            {
+                r_initiator_fsm = M_WRITE_ERROR; 
+            }
+            else if ( r_block_count.read() == r_nblocks.read() - 1 ) 
+            {
+                r_initiator_fsm = M_WRITE_SUCCESS; 
+            }
+            else
+            {
+                r_burst_count    = 0;
+		r_index          = 0;
+                r_block_count    = r_block_count.read() + 1;
+                r_initiator_fsm = M_WRITE_BURST;
+            }
+        } 
+        else
+        {
+            r_latency_count = r_latency_count - 1;
+        }
+        break;
+    }
+    /////////////////////
+    case M_WRITE_SUCCESS:
+    case M_WRITE_ERROR:
+    {
+        if( !r_go ) r_initiator_fsm = M_IDLE;
+        break;
+    }
+    } // end switch r_initiator_fsm
+}  // end transition
+
+//////////////////////
+tmpl(void)::genMoore()
+{
+    // p_vci_target port   
+    p_vci_target.rsrcid = (sc_dt::sc_uint<vci_param::S>)r_srcid.read();
+    p_vci_target.rtrdid = (sc_dt::sc_uint<vci_param::T>)r_trdid.read();
+    p_vci_target.rpktid = (sc_dt::sc_uint<vci_param::P>)r_pktid.read();
+    p_vci_target.reop   = true;
+
+    switch(r_target_fsm) {
+    case T_IDLE:
+        p_vci_target.cmdack = true;
+        p_vci_target.rspval = false;
+        break;
+    case T_READ_STATUS:
+        p_vci_target.cmdack = false;
+        p_vci_target.rspval = true;
+        if     (r_initiator_fsm == M_IDLE)          p_vci_target.rdata = BLOCK_DEVICE_IDLE;
+        else if(r_initiator_fsm == M_READ_SUCCESS)  p_vci_target.rdata = BLOCK_DEVICE_READ_SUCCESS;
+        else if(r_initiator_fsm == M_WRITE_SUCCESS) p_vci_target.rdata = BLOCK_DEVICE_WRITE_SUCCESS;
+        else if(r_initiator_fsm == M_READ_ERROR)   	p_vci_target.rdata = BLOCK_DEVICE_READ_ERROR;
+        else if(r_initiator_fsm == M_WRITE_ERROR)  	p_vci_target.rdata = BLOCK_DEVICE_WRITE_ERROR;
+        else                                    	p_vci_target.rdata = BLOCK_DEVICE_BUSY;
+        p_vci_target.rerror = VCI_READ_OK;
+        break;
+    case T_READ_BUFFER:
+        p_vci_target.cmdack = false;
+        p_vci_target.rspval = true;
+        p_vci_target.rdata  = (uint32_t)r_buf_address.read();
+        p_vci_target.rerror = VCI_READ_OK;
+        break;
+    case T_READ_COUNT:
+        p_vci_target.cmdack = false;
+        p_vci_target.rspval = true;
+        p_vci_target.rdata = (uint32_t)r_nblocks.read();
+        p_vci_target.rerror = VCI_READ_OK;
+        break;
+    case T_READ_LBA:
+        p_vci_target.cmdack = false;
+        p_vci_target.rspval = true;
+        p_vci_target.rdata = (uint32_t)r_lba.read();
+        p_vci_target.rerror = VCI_READ_OK;
+        break;
+    case T_READ_IRQEN:
+        p_vci_target.cmdack = false;
+        p_vci_target.rspval = true;
+        p_vci_target.rdata = (uint32_t)r_irq_enable.read();
+        p_vci_target.rerror = VCI_READ_OK;
+        break;
+    case T_READ_SIZE:
+        p_vci_target.cmdack = false;
+        p_vci_target.rspval = true;
+        p_vci_target.rdata = (uint32_t)m_device_size;
+        p_vci_target.rerror = VCI_READ_OK;
+        break;
+    case T_READ_BLOCK:
+        p_vci_target.cmdack = false;
+        p_vci_target.rspval = true;
+        p_vci_target.rdata = (uint32_t)m_flits_per_block*vci_param::B;
+        p_vci_target.rerror = VCI_READ_OK;
+        break;
+    case T_READ_ERROR:
+        p_vci_target.cmdack = false;
+        p_vci_target.rspval = true;
+        p_vci_target.rdata = 0;
+        p_vci_target.rerror = VCI_READ_ERROR;
+        break;
+    case T_WRITE_ERROR:
+        p_vci_target.cmdack = false;
+        p_vci_target.rspval = true;
+        p_vci_target.rdata = 0;
+        p_vci_target.rerror = VCI_WRITE_ERROR;
+        break;
+    default:
+        p_vci_target.cmdack = false;
+        p_vci_target.rspval = true;
+        p_vci_target.rdata = 0;
+        p_vci_target.rerror = VCI_WRITE_OK;
+        break;
+    } // end switch target fsm
+
+    // p_vci_initiator port
+    p_vci_initiator.srcid  = (sc_dt::sc_uint<vci_param::S>)m_srcid;
+    p_vci_initiator.trdid  = 0;
+    p_vci_initiator.contig = true;
+    p_vci_initiator.cons   = false;
+    p_vci_initiator.wrap   = false;
+    p_vci_initiator.cfixed = false;
+    p_vci_initiator.clen   = 0;
+
+    switch (r_initiator_fsm) {
+    case M_WRITE_CMD:		// It is actually a single flit VCI read command
+        p_vci_initiator.rspack  = false;
+        p_vci_initiator.cmdval  = true;
+        p_vci_initiator.address = (sc_dt::sc_uint<vci_param::N>)r_buf_address.read();
+        p_vci_initiator.cmd     = vci_param::CMD_READ;
+        p_vci_initiator.pktid   = TYPE_READ_DATA_UNC; // or _MISS ?
+        p_vci_initiator.wdata   = 0;
+        p_vci_initiator.be      = (uint32_t)0xF;
+        p_vci_initiator.plen    = (sc_dt::sc_uint<vci_param::K>)(r_burst_nflits.read()<<2);
+        p_vci_initiator.eop     = true;
+        break;
+    case M_READ_CMD:		// It is actually a multi-flits VCI WRITE command 
+        p_vci_initiator.rspack  = false;
+        p_vci_initiator.cmdval  = true;
+        p_vci_initiator.address = (sc_dt::sc_uint<vci_param::N>)r_buf_address.read(); 
+        p_vci_initiator.cmd     = vci_param::CMD_WRITE;
+        p_vci_initiator.pktid   = TYPE_WRITE;
+        p_vci_initiator.wdata   = (uint32_t)r_local_buffer[r_index.read()];
+        p_vci_initiator.be      = 0xF;
+        p_vci_initiator.plen    = (sc_dt::sc_uint<vci_param::K>)(r_burst_nflits.read()<<2);
+        p_vci_initiator.eop     = ( r_flit_count.read() == (r_burst_nflits.read() - 1) );
+        break;
+    case M_READ_RSP:
+    case M_WRITE_RSP:
+        p_vci_initiator.rspack  = true;
+        p_vci_initiator.cmdval  = false;
+        break;
+    default:
+        p_vci_initiator.rspack  = false;
+        p_vci_initiator.cmdval  = false;
+        break;
+    }
+
+    // IRQ signal
+    if(((r_initiator_fsm == M_READ_SUCCESS)    ||
+			    (r_initiator_fsm == M_WRITE_SUCCESS)   ||
+			    (r_initiator_fsm == M_READ_ERROR)      ||
+			    (r_initiator_fsm == M_WRITE_ERROR) ) &&  r_irq_enable) p_irq = true;
+    else			                               p_irq = false;
+} // end GenMoore()
+
+//////////////////////////////////////////////////////////////////////////////
+tmpl(/**/)::VciBlockDeviceTsar( sc_core::sc_module_name              name, 
+                                  const soclib::common::MappingTable   &mt,
+                                  const soclib::common::IntTab         &srcid,
+                                  const soclib::common::IntTab         &tgtid,
+                                  const std::string                    &filename,
+                                  const uint32_t                       block_size,
+                                  const uint32_t                       burst_size,
+                                  const uint32_t                       latency)
+
+: caba::BaseModule(name),
+	m_segment(mt.getSegment(tgtid)),
+	m_srcid(mt.indexForId(srcid)),
+	m_flits_per_block(block_size/vci_param::B),
+	m_flits_per_burst(burst_size/vci_param::B),
+	m_bursts_per_block(block_size/burst_size),
+	m_latency(latency),
+	p_clk("p_clk"),
+	p_resetn("p_resetn"),
+	p_vci_initiator("p_vci_initiator"),
+	p_vci_target("p_vci_target"),
+	p_irq("p_irq") 
+{
+	SC_METHOD(transition);
+	sensitive_pos << p_clk;
+
+	SC_METHOD(genMoore);
+	sensitive_neg << p_clk;
+
+	if( (block_size != 64 )  && 
+        (block_size != 128)  && 
+        (block_size != 256)  && 
+        (block_size != 512)  && 
+        (block_size != 1024) &&
+        (block_size != 2048) && 
+        (block_size != 4096) )
+	{
+		std::cout << "Error in component VciBlockDeviceTsar : " << name << std::endl;
+		std::cout << "The block size must be 128, 256, 512, 1024, 2048 or 4096 bytes" << std::endl;
+		exit(1);
+	}
+	if( (burst_size != 1 ) && 
+		(burst_size != 2 ) && 
+		(burst_size != 4 ) && 
+		(burst_size != 8 ) && 
+		(burst_size != 16) && 
+		(burst_size != 32) && 
+		(burst_size != 64) )
+	{
+		std::cout << "Error in component VciBlockDeviceTsar : " << name << std::endl;
+		std::cout << "The burst size must be 1, 2, 4, 8, 16, 32 or 64 bytes" << std::endl;
+		exit(1);
+	}
+	if ( m_segment.size() < 32 ) 
+	{
+		std::cout << "Error in component VciBlockDeviceTsar : " << name << std::endl;
+		std::cout << "The size of the segment cannot be smaller than 32 bytes" << std::endl;
+		exit(1);
+	}
+	if ( (m_segment.baseAddress() & 0x0000001F) != 0 ) 
+	{
+		std::cout << "Error in component VciBlockDeviceTsar : " << name << std::endl;
+		std::cout << "The base address of the segment must be multiple of 32 bytes" << std::endl;
+		exit(1);
+	}
+	if ( vci_param::B != 4 )
+	{
+		std::cout << "Error in component VciBlockDeviceTsar : " << name << std::endl;
+		std::cout << "The VCI data fields must have 32 bits" << std::endl;
+		exit(1);
+	}
+	m_fd = ::open(filename.c_str(), O_RDWR);
+	if ( m_fd < 0 ) 
+	{
+		std::cout << "Error in component VciBlockDeviceTsar : " << name << std::endl;
+		std::cout << "Unable to open file " << filename << std::endl;
+		exit(1);
+	}
+	m_device_size = lseek(m_fd, 0, SEEK_END) / block_size;
+	if ( m_device_size > ((uint64_t)1<<32) ) 
+	{
+		std::cout << "Warning: block device " << name << std::endl;
+		std::cout << "The file " << filename << std::endl;
+		std::cout << "has more blocks than addressable with the 32 bits PIBUS address" << std::endl;
+		m_device_size = ((uint64_t)1<<32);
+	}
+
+	r_local_buffer = new uint32_t[m_flits_per_block];
+
+} // end constructor
+
+//////////////////////////
+tmpl(void)::print_trace()
+{
+	const char* initiator_str[] = {
+		"IDLE",
+
+		"READ_BLOCK",
+		"READ_BURST",
+		"READ_CMD",
+		"READ_RSP",
+		"READ_TEST",
+		"READ_SUCCESS",
+		"READ_ERROR",
+
+		"WRITE_BURST",
+		"WRITE_CMD",
+		"WRITE_RSP",
+		"WRITE_BLOCK",
+		"WRITE_SUCCESS",
+		"WRITE_ERROR",
+	};
+	const char* target_str[] = {
+		"IDLE        ",
+		"WRITE_BUFFER",
+		"READ_BUFFER ",
+		"WRITE_COUNT ",
+		"READ_COUNT  ",
+		"WRITE_LBA   ",
+		"READ_LBA    ",
+		"WRITE_OP    ",
+		"READ_STATUS ",
+		"WRITE_IRQEN ",
+		"READ_IRQEN  ",
+		"READ_SIZE   ",
+		"READ_BLOCK  ",
+		"READ_ERROR  ",
+		"WRITE_ERROR ",
+	};
+
+	std::cout << "BDEV_TGT : " << target_str[r_target_fsm.read()] 
+		  << "  BDEV_INI : " << initiator_str[r_initiator_fsm.read()] 
+		  << "  block = " << r_block_count.read() 
+		  << "  burst = " << r_burst_count.read() 
+		  << "  flit  = " << r_flit_count.read() <<std::endl; 
+}
+
+
+}} // end namespace
+
+// Local Variables:
+// tab-width: 4
+// c-basic-offset: 4
+// c-file-offsets:((innamespace . 0)(inline-open . 0))
+// indent-tabs-mode: nil
+// End:
+
+// vim: filetype=cpp:expandtab:shiftwidth=4:tabstop=4:softtabstop=4
+
Index: trunk/modules/vci_block_device_tsar/caba/source/src/vci_block_device_tsar_v4.cpp
===================================================================
--- branches/v4/modules/vci_block_device_tsar_v4/caba/source/src/vci_block_device_tsar_v4.cpp	(revision 371)
+++ 	(revision )
@@ -1,684 +1,0 @@
-/* -*- c++ -*-
- *
- * SOCLIB_LGPL_HEADER_BEGIN
- * 
- * This file is part of SoCLib, GNU LGPLv2.1.
- * 
- * SoCLib is free software; you can redistribute it and/or modify it
- * under the terms of the GNU Lesser General Public License as published
- * by the Free Software Foundation; version 2.1 of the License.
- * 
- * SoCLib is distributed in the hope that it will be useful, but
- * WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
- * Lesser General Public License for more details.
- * 
- * You should have received a copy of the GNU Lesser General Public
- * License along with SoCLib; if not, write to the Free Software
- * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
- * 02110-1301 USA
- * 
- * SOCLIB_LGPL_HEADER_END
- *
- * Copyright (c) UPMC, Lip6, Asim
- *         alain.greiner@lip6.fr april 2011
- *
- * Maintainers: alain
- */
-
-#include <stdint.h>
-#include <iostream>
-#include <fcntl.h>
-#include "vci_block_device_tsar_v4.h"
-
-namespace soclib { namespace caba {
-
-#define tmpl(t) template<typename vci_param> t VciBlockDeviceTsarV4<vci_param>
-
-using namespace soclib::caba;
-using namespace soclib::common;
-
-////////////////////////
-tmpl(void)::transition()
-{
-    if(p_resetn.read() == false) 
-    {
-        r_initiator_fsm = M_IDLE;
-        r_target_fsm    = T_IDLE;
-        r_irq_enable    = true;
-        r_go            = false;
-        return;
-    } 
-
-    //////////////////////////////////////////////////////////////////////////////
-    // The Target FSM controls the following registers:
-    // r_target_fsm, r_irq_enable, r_nblocks, r_buf adress, r_lba, r_go, r_read
-    //////////////////////////////////////////////////////////////////////////////
-
-    switch(r_target_fsm) {
-    ////////////
-    case T_IDLE:
-    {
-        if ( p_vci_target.cmdval.read() ) 
-        { 
-            r_srcid = p_vci_target.srcid.read();
-            r_trdid = p_vci_target.trdid.read();
-            r_pktid = p_vci_target.pktid.read();
-            sc_dt::sc_uint<vci_param::N> address = p_vci_target.address.read();
-            bool                  read    = (p_vci_target.cmd.read() == vci_param::CMD_READ);
-            uint32_t              cell    = (uint32_t)((address & 0x1F)>>2);
-
-            if     ( !read && !m_segment.contains(address) )      r_target_fsm = T_WRITE_ERROR;
-            else if(  read && !m_segment.contains(address) )      r_target_fsm = T_READ_ERROR;
-            else if( !read && !p_vci_target.eop.read() )          r_target_fsm = T_WRITE_ERROR;
-            else if(  read && !p_vci_target.eop.read() )          r_target_fsm = T_READ_ERROR;
-            else if( !read && (cell == BLOCK_DEVICE_BUFFER) )     r_target_fsm = T_WRITE_BUFFER;
-            else if(  read && (cell == BLOCK_DEVICE_BUFFER) )     r_target_fsm = T_READ_BUFFER;
-            else if( !read && (cell == BLOCK_DEVICE_COUNT) )      r_target_fsm = T_WRITE_COUNT;
-            else if(  read && (cell == BLOCK_DEVICE_COUNT) )      r_target_fsm = T_READ_COUNT;
-            else if( !read && (cell == BLOCK_DEVICE_LBA) )        r_target_fsm = T_WRITE_LBA;
-            else if(  read && (cell == BLOCK_DEVICE_LBA) )        r_target_fsm = T_READ_LBA;
-            else if( !read && (cell == BLOCK_DEVICE_OP) )         r_target_fsm = T_WRITE_OP;
-            else if(  read && (cell == BLOCK_DEVICE_STATUS) )     r_target_fsm = T_READ_STATUS;
-            else if( !read && (cell == BLOCK_DEVICE_IRQ_ENABLE) ) r_target_fsm = T_WRITE_IRQEN;
-            else if(  read && (cell == BLOCK_DEVICE_IRQ_ENABLE) ) r_target_fsm = T_READ_IRQEN;
-            else if(  read && (cell == BLOCK_DEVICE_SIZE) )       r_target_fsm = T_READ_SIZE;
-            else if(  read && (cell == BLOCK_DEVICE_BLOCK_SIZE) ) r_target_fsm = T_READ_BLOCK;
-        }
-        break;
-    }
-    ////////////////////
-    case T_WRITE_BUFFER:
-    {
-        if ( r_initiator_fsm == M_IDLE )  r_buf_address = (uint32_t)p_vci_target.wdata.read();
-        if ( p_vci_target.rspack.read() ) r_target_fsm = T_IDLE;
-        break;
-    }
-    ///////////////////
-    case T_WRITE_COUNT:
-    {
-        if ( r_initiator_fsm == M_IDLE )  r_nblocks = (uint32_t)p_vci_target.wdata.read();
-        if ( p_vci_target.rspack.read() ) r_target_fsm = T_IDLE;
-        break;
-    }
-    /////////////////
-    case T_WRITE_LBA:
-    {
-        if ( r_initiator_fsm == M_IDLE )  r_lba = (uint32_t)p_vci_target.wdata.read();
-        if ( p_vci_target.rspack.read() ) r_target_fsm = T_IDLE;
-        break;
-    }
-    ////////////////
-    case T_WRITE_OP:
-    {
-        if ( r_initiator_fsm == M_IDLE ) 
-        {
-            if ( (uint32_t)p_vci_target.wdata.read() == BLOCK_DEVICE_READ )
-            {
-                r_read = true;
-                r_go = true;
-            }
-            else if ( (uint32_t)p_vci_target.wdata.read() == BLOCK_DEVICE_WRITE)
-            {
-                r_read = false;
-                r_go = true;
-            }
-        }
-        if ( p_vci_target.rspack.read() ) r_target_fsm = T_IDLE;
-        break;
-    }
-    ///////////////////
-    case T_WRITE_IRQEN:
-    {
-        r_irq_enable = (p_vci_target.wdata.read() != 0);
-        if ( p_vci_target.rspack.read() ) r_target_fsm = T_IDLE;
-        break;
-    }
-    ///////////////////
-    case T_READ_BUFFER:
-    case T_READ_COUNT:
-    case T_READ_LBA:
-    case T_READ_IRQEN:
-    case T_READ_SIZE:
-    case T_READ_BLOCK:
-    case T_READ_ERROR:
-    case T_WRITE_ERROR:
-    {
-        if ( p_vci_target.rspack.read() ) r_target_fsm = T_IDLE;
-        break;
-    }
-    ///////////////////
-    case T_READ_STATUS:
-    {
-        if ( p_vci_target.rspack.read() ) 
-        {
-            r_target_fsm = T_IDLE;
-            if( (r_initiator_fsm == M_READ_SUCCESS ) ||
-                (r_initiator_fsm == M_READ_ERROR   ) ||
-                (r_initiator_fsm == M_WRITE_SUCCESS) ||
-                (r_initiator_fsm == M_WRITE_ERROR  ) ) r_go = false;
-        }
-        break;
-    }
-    } // end switch target fsm
-	
-    //////////////////////////////////////////////////////////////////////////////
-    // The initiator FSM executes a loop, transfering one block per iteration.
-    // Each block is split in bursts, and the number of bursts depends
-    // on the memory buffer alignment on a burst boundary:
-    // - If buffer aligned, all burst have the same length (m_flits_per burst)
-    //   and the number of bursts is (m_bursts_per_block).
-    // - If buffer not aligned, the number of bursts is (m_bursts_per_block + 1)
-    //   and first and last burst are shorter, because all flits in a burst 
-    //   must be contained in a single cache line.
-    //   first burst => nflits = m_flits_per_burst - offset
-    //   last  burst => nflits = offset
-    //   other burst => nflits = m_flits_per_burst
-    //////////////////////////////////////////////////////////////////////////////
-
-    switch( r_initiator_fsm.read() ) {
-    ////////////
-    case M_IDLE: 	// check buffer alignment to compute the number of bursts
-    {
-        if ( r_go.read() ) 
-        {
-            r_index         = 0;
-            r_block_count   = 0;
-            r_burst_count   = 0;
-            r_flit_count    = 0;
-            r_latency_count = m_latency;
-
-            // compute r_burst_offset (zero when buffer aligned)
-            r_burst_offset = (r_buf_address.read()>>2) % m_flits_per_burst;
-
-            // start tranfer
-            if ( r_read.read() ) 	r_initiator_fsm = M_READ_BLOCK;
-            else                    r_initiator_fsm = M_WRITE_BURST;
-        }
-        break;
-    } 
-    //////////////////
-    case M_READ_BLOCK:  // read one block from disk after waiting m_latency cycles
-    {
-        if ( r_latency_count.read() == 0 )
-        {
-            r_latency_count = m_latency;
-            ::lseek(m_fd, (r_lba + r_block_count)*m_flits_per_block*4, SEEK_SET);
-            if( ::read(m_fd, r_local_buffer, m_flits_per_block*4) < 0 )  
-            {
-                r_initiator_fsm = M_READ_ERROR;
-            }
-            else   
-            {
-                r_burst_count   = 0;
-                r_flit_count    = 0;
-                r_initiator_fsm = M_READ_BURST;
-            }
-        }
-        else
-        {
-            r_latency_count = r_latency_count.read() - 1;
-        }
-        break;
-    }
-    //////////////////
-    case M_READ_BURST:  // Compute the number of flits in the burst
-    {
-        uint32_t offset = r_burst_offset.read();
-
-        if ( offset )                  // buffer not aligned
-        {
-            if ( r_burst_count.read() == 0 ) r_burst_nflits = m_flits_per_burst - offset;
-            else if ( r_burst_count.read() == m_bursts_per_block ) r_burst_nflits = offset;
-            else r_burst_nflits = m_flits_per_burst;
-        }
-        else                           // buffer aligned
-        {
-            r_burst_nflits = m_flits_per_burst;
-        }
-        r_initiator_fsm =  M_READ_CMD;
-        break;
-    }
-    ////////////////
-    case M_READ_CMD:	// Send a multi-flits VCI WRITE command
-    {
-        if ( p_vci_initiator.cmdack.read() )
-        {
-            if ( r_flit_count == (r_burst_nflits.read() - 1) ) // last flit in a burst
-            {
-                r_initiator_fsm = M_READ_RSP;
-                r_flit_count = 0;
-            }
-            else                                               // not the last flit
-            {
-                r_flit_count = r_flit_count.read() + 1;
-            }
-
-            // compute next flit address and next local buffer index
-            r_buf_address = r_buf_address.read() + 4;
-            r_index       = r_index.read() + 1;
-        }
-        break;
-    }
-    ////////////////
-    case M_READ_RSP: 	// Wait a single flit VCI WRITE response
-    {
-        if ( p_vci_initiator.rspval.read() )
-        {
-            bool aligned = (r_burst_offset.read() == 0);
-
-            if ( (p_vci_initiator.rerror.read()&0x1) != 0 ) 
-            {
-                r_initiator_fsm = M_READ_ERROR;
-            }
-            else if ( (not aligned and (r_burst_count.read() == m_bursts_per_block)) or 
-                      (aligned and (r_burst_count.read() == (m_bursts_per_block-1))) )
-            {
-                if ( r_block_count.read() == (r_nblocks.read()-1) ) // last burst of last block 
-                {
-                    r_initiator_fsm = M_READ_SUCCESS;
-                }
-                else                                              // last burst not last block
-                {
-                    r_index          = 0;
-                    r_burst_count    = 0;
-                    r_block_count    = r_block_count.read() + 1;
-                    r_initiator_fsm  = M_READ_BLOCK;
-                }
-            }
-            else                                                // not the last burst
-            {
-                r_burst_count = r_burst_count.read() + 1;
-                r_initiator_fsm = M_READ_BURST;
-            }
-        }
-        break;
-    }
-    ///////////////////
-    case M_READ_SUCCESS:
-    case M_READ_ERROR:
-    {
-        if( !r_go ) r_initiator_fsm = M_IDLE;
-        break;
-    }
-    ///////////////////
-    case M_WRITE_BURST:  // Compute the number of flits in the burst
-    {
-        uint32_t offset = r_burst_offset.read();
-
-        if ( offset )                  // buffer not aligned
-        {
-            if ( r_burst_count.read() == 0 ) r_burst_nflits = m_flits_per_burst - offset;
-            else if ( r_burst_count.read() == m_bursts_per_block ) r_burst_nflits = offset;
-            else r_burst_nflits = m_flits_per_burst;
-        }
-        else                           // buffer aligned
-        {
-            r_burst_nflits = m_flits_per_burst;
-        }
-        r_initiator_fsm =  M_WRITE_CMD;
-        break;
-    }
-    /////////////////
-    case M_WRITE_CMD:	// This is actually a single flit VCI READ command
-    {
-	    if ( p_vci_initiator.cmdack.read() ) r_initiator_fsm = M_WRITE_RSP;
-        break;
-    }
-    /////////////////
-    case M_WRITE_RSP:	// This is actually a multi-flits VCI READ response
-    {
-        bool aligned = (r_burst_offset.read() == 0);
-
-        if ( p_vci_initiator.rspval.read() )
-        {
-            r_local_buffer[r_index.read()] = (uint32_t)p_vci_initiator.rdata.read();
-            r_index = r_index.read() + 1;
-
-            if ( p_vci_initiator.reop.read() )  // last flit of the burst
-            {
-	        r_flit_count  = 0;
-                r_buf_address = r_buf_address.read() + (r_burst_nflits.read()<<2); 
-
-	        if( (p_vci_initiator.rerror.read()&0x1) != 0 ) 
-                {
-                    r_initiator_fsm = M_WRITE_ERROR;
-                }
-                else if ( (not aligned and (r_burst_count.read() == m_bursts_per_block)) or 
-                          (aligned and (r_burst_count.read() == (m_bursts_per_block-1))) ) // last burst
-                {
-                    r_initiator_fsm  = M_WRITE_BLOCK;
-                }
-                else                                          // not the last burst
-                {
-                    r_burst_count = r_burst_count.read() + 1;
-                    r_initiator_fsm = M_WRITE_BURST;
-                }
-            }
-            else
-            {
-	            r_flit_count = r_flit_count.read() + 1;
-            }
-        }
-        break;
-    }
-    ///////////////////
-    case M_WRITE_BLOCK:		// write a block to disk after waiting m_latency cycles
-    {
-        if ( r_latency_count == 0 )
-        {
-            r_latency_count = m_latency;
-            ::lseek(m_fd, (r_lba + r_block_count)*m_flits_per_block*vci_param::B, SEEK_SET);
-            if( ::write(m_fd, r_local_buffer, m_flits_per_block*vci_param::B) < 0 )
-            {
-                r_initiator_fsm = M_WRITE_ERROR; 
-            }
-            else if ( r_block_count.read() == r_nblocks.read() - 1 ) 
-            {
-                r_initiator_fsm = M_WRITE_SUCCESS; 
-            }
-            else
-            {
-                r_burst_count    = 0;
-		r_index          = 0;
-                r_block_count    = r_block_count.read() + 1;
-                r_initiator_fsm = M_WRITE_BURST;
-            }
-        } 
-        else
-        {
-            r_latency_count = r_latency_count - 1;
-        }
-        break;
-    }
-    /////////////////////
-    case M_WRITE_SUCCESS:
-    case M_WRITE_ERROR:
-    {
-        if( !r_go ) r_initiator_fsm = M_IDLE;
-        break;
-    }
-    } // end switch r_initiator_fsm
-}  // end transition
-
-//////////////////////
-tmpl(void)::genMoore()
-{
-    // p_vci_target port   
-    p_vci_target.rsrcid = (sc_dt::sc_uint<vci_param::S>)r_srcid.read();
-    p_vci_target.rtrdid = (sc_dt::sc_uint<vci_param::T>)r_trdid.read();
-    p_vci_target.rpktid = (sc_dt::sc_uint<vci_param::P>)r_pktid.read();
-    p_vci_target.reop   = true;
-
-    switch(r_target_fsm) {
-    case T_IDLE:
-        p_vci_target.cmdack = true;
-        p_vci_target.rspval = false;
-        break;
-    case T_READ_STATUS:
-        p_vci_target.cmdack = false;
-        p_vci_target.rspval = true;
-        if     (r_initiator_fsm == M_IDLE)          p_vci_target.rdata = BLOCK_DEVICE_IDLE;
-        else if(r_initiator_fsm == M_READ_SUCCESS)  p_vci_target.rdata = BLOCK_DEVICE_READ_SUCCESS;
-        else if(r_initiator_fsm == M_WRITE_SUCCESS) p_vci_target.rdata = BLOCK_DEVICE_WRITE_SUCCESS;
-        else if(r_initiator_fsm == M_READ_ERROR)   	p_vci_target.rdata = BLOCK_DEVICE_READ_ERROR;
-        else if(r_initiator_fsm == M_WRITE_ERROR)  	p_vci_target.rdata = BLOCK_DEVICE_WRITE_ERROR;
-        else                                    	p_vci_target.rdata = BLOCK_DEVICE_BUSY;
-        p_vci_target.rerror = VCI_READ_OK;
-        break;
-    case T_READ_BUFFER:
-        p_vci_target.cmdack = false;
-        p_vci_target.rspval = true;
-        p_vci_target.rdata  = (uint32_t)r_buf_address.read();
-        p_vci_target.rerror = VCI_READ_OK;
-        break;
-    case T_READ_COUNT:
-        p_vci_target.cmdack = false;
-        p_vci_target.rspval = true;
-        p_vci_target.rdata = (uint32_t)r_nblocks.read();
-        p_vci_target.rerror = VCI_READ_OK;
-        break;
-    case T_READ_LBA:
-        p_vci_target.cmdack = false;
-        p_vci_target.rspval = true;
-        p_vci_target.rdata = (uint32_t)r_lba.read();
-        p_vci_target.rerror = VCI_READ_OK;
-        break;
-    case T_READ_IRQEN:
-        p_vci_target.cmdack = false;
-        p_vci_target.rspval = true;
-        p_vci_target.rdata = (uint32_t)r_irq_enable.read();
-        p_vci_target.rerror = VCI_READ_OK;
-        break;
-    case T_READ_SIZE:
-        p_vci_target.cmdack = false;
-        p_vci_target.rspval = true;
-        p_vci_target.rdata = (uint32_t)m_device_size;
-        p_vci_target.rerror = VCI_READ_OK;
-        break;
-    case T_READ_BLOCK:
-        p_vci_target.cmdack = false;
-        p_vci_target.rspval = true;
-        p_vci_target.rdata = (uint32_t)m_flits_per_block*vci_param::B;
-        p_vci_target.rerror = VCI_READ_OK;
-        break;
-    case T_READ_ERROR:
-        p_vci_target.cmdack = false;
-        p_vci_target.rspval = true;
-        p_vci_target.rdata = 0;
-        p_vci_target.rerror = VCI_READ_ERROR;
-        break;
-    case T_WRITE_ERROR:
-        p_vci_target.cmdack = false;
-        p_vci_target.rspval = true;
-        p_vci_target.rdata = 0;
-        p_vci_target.rerror = VCI_WRITE_ERROR;
-        break;
-    default:
-        p_vci_target.cmdack = false;
-        p_vci_target.rspval = true;
-        p_vci_target.rdata = 0;
-        p_vci_target.rerror = VCI_WRITE_OK;
-        break;
-    } // end switch target fsm
-
-    // p_vci_initiator port
-    p_vci_initiator.srcid  = (sc_dt::sc_uint<vci_param::S>)m_srcid;
-    p_vci_initiator.trdid  = 0;
-    p_vci_initiator.contig = true;
-    p_vci_initiator.cons   = false;
-    p_vci_initiator.wrap   = false;
-    p_vci_initiator.cfixed = false;
-    p_vci_initiator.clen   = 0;
-
-    switch (r_initiator_fsm) {
-    case M_WRITE_CMD:		// It is actually a single flit VCI read command
-        p_vci_initiator.rspack  = false;
-        p_vci_initiator.cmdval  = true;
-        p_vci_initiator.address = (sc_dt::sc_uint<vci_param::N>)r_buf_address.read();
-        p_vci_initiator.cmd     = vci_param::CMD_READ;
-        p_vci_initiator.pktid   = TYPE_READ_DATA_UNC; // or _MISS ?
-        p_vci_initiator.wdata   = 0;
-        p_vci_initiator.be      = (uint32_t)0xF;
-        p_vci_initiator.plen    = (sc_dt::sc_uint<vci_param::K>)(r_burst_nflits.read()<<2);
-        p_vci_initiator.eop     = true;
-        break;
-    case M_READ_CMD:		// It is actually a multi-flits VCI WRITE command 
-        p_vci_initiator.rspack  = false;
-        p_vci_initiator.cmdval  = true;
-        p_vci_initiator.address = (sc_dt::sc_uint<vci_param::N>)r_buf_address.read(); 
-        p_vci_initiator.cmd     = vci_param::CMD_WRITE;
-        p_vci_initiator.pktid   = TYPE_WRITE;
-        p_vci_initiator.wdata   = (uint32_t)r_local_buffer[r_index.read()];
-        p_vci_initiator.be      = 0xF;
-        p_vci_initiator.plen    = (sc_dt::sc_uint<vci_param::K>)(r_burst_nflits.read()<<2);
-        p_vci_initiator.eop     = ( r_flit_count.read() == (r_burst_nflits.read() - 1) );
-        break;
-    case M_READ_RSP:
-    case M_WRITE_RSP:
-        p_vci_initiator.rspack  = true;
-        p_vci_initiator.cmdval  = false;
-        break;
-    default:
-        p_vci_initiator.rspack  = false;
-        p_vci_initiator.cmdval  = false;
-        break;
-    }
-
-    // IRQ signal
-    if(((r_initiator_fsm == M_READ_SUCCESS)    ||
-			    (r_initiator_fsm == M_WRITE_SUCCESS)   ||
-			    (r_initiator_fsm == M_READ_ERROR)      ||
-			    (r_initiator_fsm == M_WRITE_ERROR) ) &&  r_irq_enable) p_irq = true;
-    else			                               p_irq = false;
-} // end GenMoore()
-
-//////////////////////////////////////////////////////////////////////////////
-tmpl(/**/)::VciBlockDeviceTsarV4( sc_core::sc_module_name              name, 
-                                  const soclib::common::MappingTable   &mt,
-                                  const soclib::common::IntTab         &srcid,
-                                  const soclib::common::IntTab         &tgtid,
-                                  const std::string                    &filename,
-                                  const uint32_t                       block_size,
-                                  const uint32_t                       burst_size,
-                                  const uint32_t                       latency)
-
-: caba::BaseModule(name),
-	m_segment(mt.getSegment(tgtid)),
-	m_srcid(mt.indexForId(srcid)),
-	m_flits_per_block(block_size/vci_param::B),
-	m_flits_per_burst(burst_size/vci_param::B),
-	m_bursts_per_block(block_size/burst_size),
-	m_latency(latency),
-	p_clk("p_clk"),
-	p_resetn("p_resetn"),
-	p_vci_initiator("p_vci_initiator"),
-	p_vci_target("p_vci_target"),
-	p_irq("p_irq") 
-{
-	SC_METHOD(transition);
-	sensitive_pos << p_clk;
-
-	SC_METHOD(genMoore);
-	sensitive_neg << p_clk;
-
-	if( (block_size != 64 )  && 
-        (block_size != 128)  && 
-        (block_size != 256)  && 
-        (block_size != 512)  && 
-        (block_size != 1024) &&
-        (block_size != 2048) && 
-        (block_size != 4096) )
-	{
-		std::cout << "Error in component VciBlockDeviceTsarV4 : " << name << std::endl;
-		std::cout << "The block size must be 128, 256, 512, 1024, 2048 or 4096 bytes" << std::endl;
-		exit(1);
-	}
-	if( (burst_size != 1 ) && 
-		(burst_size != 2 ) && 
-		(burst_size != 4 ) && 
-		(burst_size != 8 ) && 
-		(burst_size != 16) && 
-		(burst_size != 32) && 
-		(burst_size != 64) )
-	{
-		std::cout << "Error in component VciBlockDeviceTsarV4 : " << name << std::endl;
-		std::cout << "The burst size must be 1, 2, 4, 8, 16, 32 or 64 bytes" << std::endl;
-		exit(1);
-	}
-	if ( m_segment.size() < 32 ) 
-	{
-		std::cout << "Error in component VciBlockDeviceTsarV4 : " << name << std::endl;
-		std::cout << "The size of the segment cannot be smaller than 32 bytes" << std::endl;
-		exit(1);
-	}
-	if ( (m_segment.baseAddress() & 0x0000001F) != 0 ) 
-	{
-		std::cout << "Error in component VciBlockDeviceTsarV4 : " << name << std::endl;
-		std::cout << "The base address of the segment must be multiple of 32 bytes" << std::endl;
-		exit(1);
-	}
-	if ( vci_param::B != 4 )
-	{
-		std::cout << "Error in component VciBlockDeviceTsarV4 : " << name << std::endl;
-		std::cout << "The VCI data fields must have 32 bits" << std::endl;
-		exit(1);
-	}
-	m_fd = ::open(filename.c_str(), O_RDWR);
-	if ( m_fd < 0 ) 
-	{
-		std::cout << "Error in component VciBlockDeviceTsarV4 : " << name << std::endl;
-		std::cout << "Unable to open file " << filename << std::endl;
-		exit(1);
-	}
-	m_device_size = lseek(m_fd, 0, SEEK_END) / block_size;
-	if ( m_device_size > ((uint64_t)1<<32) ) 
-	{
-		std::cout << "Warning: block device " << name << std::endl;
-		std::cout << "The file " << filename << std::endl;
-		std::cout << "has more blocks than addressable with the 32 bits PIBUS address" << std::endl;
-		m_device_size = ((uint64_t)1<<32);
-	}
-
-	r_local_buffer = new uint32_t[m_flits_per_block];
-
-} // end constructor
-
-//////////////////////////
-tmpl(void)::print_trace()
-{
-	const char* initiator_str[] = {
-		"IDLE",
-
-		"READ_BLOCK",
-		"READ_BURST",
-		"READ_CMD",
-		"READ_RSP",
-		"READ_TEST",
-		"READ_SUCCESS",
-		"READ_ERROR",
-
-		"WRITE_BURST",
-		"WRITE_CMD",
-		"WRITE_RSP",
-		"WRITE_BLOCK",
-		"WRITE_SUCCESS",
-		"WRITE_ERROR",
-	};
-	const char* target_str[] = {
-		"IDLE        ",
-		"WRITE_BUFFER",
-		"READ_BUFFER ",
-		"WRITE_COUNT ",
-		"READ_COUNT  ",
-		"WRITE_LBA   ",
-		"READ_LBA    ",
-		"WRITE_OP    ",
-		"READ_STATUS ",
-		"WRITE_IRQEN ",
-		"READ_IRQEN  ",
-		"READ_SIZE   ",
-		"READ_BLOCK  ",
-		"READ_ERROR  ",
-		"WRITE_ERROR ",
-	};
-
-	std::cout << "BDEV_TGT : " << target_str[r_target_fsm.read()] 
-		  << "  BDEV_INI : " << initiator_str[r_initiator_fsm.read()] 
-		  << "  block = " << r_block_count.read() 
-		  << "  burst = " << r_burst_count.read() 
-		  << "  flit  = " << r_flit_count.read() <<std::endl; 
-}
-
-
-}} // end namespace
-
-// Local Variables:
-// tab-width: 4
-// c-basic-offset: 4
-// c-file-offsets:((innamespace . 0)(inline-open . 0))
-// indent-tabs-mode: nil
-// End:
-
-// vim: filetype=cpp:expandtab:shiftwidth=4:tabstop=4:softtabstop=4
-
