URL
https://opencores.org/ocsvn/async_sdm_noc/async_sdm_noc/trunk
Subversion Repositories async_sdm_noc
Compare Revisions
- This comparison shows the changes necessary to convert path
/async_sdm_noc/branches/init
- from Rev 42 to Rev 43
- ↔ Reverse comparison
Rev 42 → Rev 43
/vc/tb/rtdriver.cpp
0,0 → 1,317
/* |
Asynchronous SDM NoC |
(C)2011 Wei Song |
Advanced Processor Technologies Group |
Computer Science, the Univ. of Manchester, UK |
|
Authors: |
Wei Song wsong83@gmail.com |
|
License: LGPL 3.0 or later |
|
The port driver between NI and router. |
|
History: |
02/05/2010 Initial version. <wsong83@gmail.com> |
03/06/2011 Remove the sc_unit datatype to support data width larger than 64. <wsong83@gmail.com> |
|
*/ |
|
#include "rtdriver.h" |
|
RTDriver::RTDriver(sc_module_name mname) |
: sc_module(mname), |
NI2P("NI2P"), |
P2NI("P2NI"), |
rtia("rtia"), |
rtic("rtic"), |
rtica("rtica"), |
rtoa("rtoa"), |
rtoc("rtoc"), |
rtoca("rtoca"), |
IPD("VCIP"), |
OPD("VCOP") |
{ |
SC_METHOD(IPdetect); |
sensitive << rtia; |
|
SC_METHOD(OPdetect); |
sensitive << rtod[0] << rtod[1] << rtod[2] << rtod[3] << rtovc << rtoft; |
|
SC_METHOD(Creditdetect); |
for(unsigned int i = 0; i<SubChN; i++) { |
sensitive << CPa[i]; |
sensitive << out_cred[i]; |
} |
sensitive << rtic << rtoca; |
|
SC_THREAD(send); |
SC_THREAD(recv); |
|
rtinp_sig = false; |
rtoutp_sig = false; |
|
sc_spawn_options th_opt; |
for(unsigned int i=0; i<SubChN; i++) |
sc_spawn(sc_bind(&RTDriver::credit, this, i), NULL, &th_opt); |
} |
|
void RTDriver::IPdetect() { |
sc_logic ack_lv_high, ack_lv_low; // the sc_logic ack |
|
ack_lv_high = rtia.read(); |
ack_lv_low = rtia.read(); |
|
if(ack_lv_high.is_01() && ack_lv_high.to_bool()) |
rtinp_sig = true; |
|
if(ack_lv_low.is_01() && (!ack_lv_low.to_bool())) |
rtinp_sig = false; |
} |
|
void RTDriver::OPdetect() { |
sc_lv<ChBW*4> data_lv; // the ORed data |
sc_logic data_lv_high, data_lv_low; |
|
data_lv = rtod[0].read() | rtod[1].read() | rtod[2].read() | rtod[3].read(); |
data_lv_high = data_lv.and_reduce() & rtovc.read().or_reduce() & rtoft.read().or_reduce(); |
data_lv_low = data_lv.or_reduce() | rtovc.read().or_reduce() | rtoft.read().or_reduce(); |
|
if(data_lv_high.is_01() && data_lv_high.to_bool()) |
rtoutp_sig = true; |
|
if(data_lv_high.is_01() && (!data_lv_low.to_bool())) |
rtoutp_sig = false; |
} |
|
void RTDriver::Creditdetect() { |
sc_lv<SubChN> mic; // the local input credit |
sc_lv<SubChN> mica; // the local input credit ack |
sc_lv<SubChN> moc; // the local output credit; |
sc_lv<SubChN> moca; // the local output credit ack; |
|
mic = rtic.read(); |
moca = rtoca.read(); |
|
for(unsigned int i=0; i<SubChN; i++) { |
CP[i].write(mic[i].is_01()? mic[i].to_bool():false); |
out_cred_ack[i] = moca[i].is_01()? moca[i].to_bool():false; |
mica[i] = CPa[i].read(); |
moc[i] = out_cred[i]; |
} |
|
rtica.write(mica); |
rtoc.write(moc); |
} |
|
void RTDriver::send() { |
FLIT mflit; // the local flit buffer |
unsigned int i, j; // local loop index |
sc_lv<ChBW*4> mdata[4]; // local data copy |
sc_lv<SubChN> mvc; // local vcn |
sc_lv<3> mft; // local flit type |
|
// initialize the output ports |
mdata[0] = 0; |
mdata[1] = 0; |
mdata[2] = 0; |
mdata[3] = 0; |
mvc = 0; |
mft = 0; |
|
|
rtid[0].write(mdata[0]); |
rtid[1].write(mdata[1]); |
rtid[2].write(mdata[2]); |
rtid[3].write(mdata[3]); |
rtivc.write(mvc); |
rtift.write(mft); |
|
while(true) { |
mflit = NI2P->read(); // read in the flit |
|
// write the flit |
if(mflit.ftype == F_HD) { |
// the target address |
mdata[mflit.addrx&0x3][0] = SC_LOGIC_1; |
mdata[(mflit.addrx&0xc)>>2][1] = SC_LOGIC_1; |
mdata[mflit.addry&0x3][2] = SC_LOGIC_1; |
mdata[(mflit.addry&0xc)>>2][3] = SC_LOGIC_1; |
|
for(i=0,j=4; i<(ChBW-1)*4; i++, j++) { |
switch((mflit[i/4] >> ((i%4)*2)) & 0x3) { |
case 0: mdata[0][j] = SC_LOGIC_1; break; |
case 1: mdata[1][j] = SC_LOGIC_1; break; |
case 2: mdata[2][j] = SC_LOGIC_1; break; |
case 3: mdata[3][j] = SC_LOGIC_1; break; |
} |
} |
} else { |
for(i=0; i<ChBW*4; i++) { |
switch((mflit[i/4] >> ((i%4)*2)) & 0x3) { |
case 0: mdata[0][i] = SC_LOGIC_1; break; |
case 1: mdata[1][i] = SC_LOGIC_1; break; |
case 2: mdata[2][i] = SC_LOGIC_1; break; |
case 3: mdata[3][i] = SC_LOGIC_1; break; |
} |
} |
} |
|
// flit type |
switch(mflit.ftype) { |
case F_HD: mft[0] = SC_LOGIC_1; break; |
case F_DAT: mft[1] = SC_LOGIC_1; break; |
case F_TL: mft[2] = SC_LOGIC_1; break; |
default: |
} |
|
// VC number |
mvc[mflit.vcn] = SC_LOGIC_1; |
|
// write to the port |
rtid[0].write(mdata[0]); |
rtid[1].write(mdata[1]); |
rtid[2].write(mdata[2]); |
rtid[3].write(mdata[3]); |
rtivc.write(mvc); |
rtift.write(mft); |
|
// wait for the router to capture the data |
wait(rtinp_sig.posedge_event()); |
wait(0.2, SC_NS); // a delay to avoid data override |
|
// clear the data |
mdata[0] = 0; |
mdata[1] = 0; |
mdata[2] = 0; |
mdata[3] = 0; |
mvc = 0; |
mft = 0; |
|
rtid[0].write(mdata[0]); |
rtid[1].write(mdata[1]); |
rtid[2].write(mdata[2]); |
rtid[3].write(mdata[3]); |
rtivc.write(mvc); |
rtift.write(mft); |
|
// wait for the input port be ready again |
wait(rtinp_sig.negedge_event()); |
wait(0.2, SC_NS); // a delay to avoid data override |
} |
} |
|
void RTDriver::recv() { |
FLIT mflit; // the local flit buffer |
sc_lv<ChBW*4> mdata[4]; // local data copy |
sc_lv<SubChN> mvc; // local vc number |
sc_lv<3> mft; // local flit type |
sc_logic mack = SC_LOGIC_0; // local copy of ack |
sc_lv<4> dd; // the current 1-of-4 data under process |
unsigned int i, j; // local loop index |
|
// initialize the ack signal |
rtoa.write(mack); |
|
while(true) { |
// clear the flit |
mflit.clear(); |
|
// wait for an incoming flit |
wait(rtoutp_sig.posedge_event()); |
|
// analyse the flit |
mdata[0] = rtod[0].read(); |
mdata[1] = rtod[1].read(); |
mdata[2] = rtod[2].read(); |
mdata[3] = rtod[3].read(); |
mft = rtoft.read(); |
mvc = rtovc.read(); |
|
switch(mft.to_uint()) { |
case 1: mflit.ftype = F_HD; break; |
case 2: mflit.ftype = F_DAT; break; |
case 4: mflit.ftype = F_TL; break; |
default: mflit.ftype = F_IDLE; // shoudle not happen |
} |
|
if(mflit.ftype == F_HD) { |
// fetch the address |
dd[0] = mdata[0][0]; dd[1] = mdata[1][0]; dd[2] = mdata[2][0]; dd[3] = mdata[3][0]; |
mflit.addrx |= (c1o42b(dd.to_uint()) << 0); |
dd[0] = mdata[0][1]; dd[1] = mdata[1][1]; dd[2] = mdata[2][1]; dd[3] = mdata[3][1]; |
mflit.addrx |= (c1o42b(dd.to_uint()) << 2); |
dd[0] = mdata[0][2]; dd[1] = mdata[1][2]; dd[2] = mdata[2][2]; dd[3] = mdata[3][2]; |
mflit.addry |= (c1o42b(dd.to_uint()) << 0); |
dd[0] = mdata[0][3]; dd[1] = mdata[1][3]; dd[2] = mdata[2][3]; dd[3] = mdata[3][3]; |
mflit.addry |= (c1o42b(dd.to_uint()) << 2); |
|
// fill in data |
for(i=1; i<ChBW; i++) { |
for(j=0; j<4; j++) { |
dd[0] = mdata[0][i*4+j]; |
dd[1] = mdata[1][i*4+j]; |
dd[2] = mdata[2][i*4+j]; |
dd[3] = mdata[3][i*4+j]; |
mflit[i-1] |= c1o42b(dd.to_uint()) << j*2; |
} |
} |
} else{ |
for(i=0; i<ChBW; i++) { |
for(j=0; j<4; j++) { |
dd[0] = mdata[0][i*4+j]; |
dd[1] = mdata[1][i*4+j]; |
dd[2] = mdata[2][i*4+j]; |
dd[3] = mdata[3][i*4+j]; |
mflit[i] |= c1o42b(dd.to_uint()) << j*2; |
} |
} |
} |
|
// get the binary vc number |
unsigned int fvcn = mvc.to_uint(); |
while(fvcn != 0) { |
mflit.vcn += 1; |
fvcn >>= 1; |
} |
|
// send the flit to the NI |
P2NI->write(mflit); |
|
wait(0.2, SC_NS); // a delay to avoid data override |
rtoa.write(~mack); // notify that data is captured |
|
// wait for the data withdrawal |
wait(rtoutp_sig.negedge_event()); |
wait(0.2, SC_NS); // a delay to avoid data override |
rtoa.write(mack); // notify that data is captured |
|
} |
} |
|
void RTDriver::credit(unsigned int dd) { |
out_cred[dd] = false; |
|
while(true){ |
wait(out_cred_ack[dd].posedge_event()); |
wait(0.2, SC_NS); |
|
out_cred[dd] = true; |
|
wait(out_cred_ack[dd].negedge_event()); |
wait(0.2, SC_NS); |
|
out_cred[dd] = false; |
} |
} |
|
|
unsigned int RTDriver::c1o42b(unsigned int dd) { |
switch(dd) { |
case 1: return 0; |
case 2: return 1; |
case 4: return 2; |
case 8: return 3; |
default: return 0xff; |
} |
} |
/vc/tb/rtdriver.h
0,0 → 1,73
/* |
Asynchronous SDM NoC |
(C)2011 Wei Song |
Advanced Processor Technologies Group |
Computer Science, the Univ. of Manchester, UK |
|
Authors: |
Wei Song wsong83@gmail.com |
|
License: LGPL 3.0 or later |
|
The port driver between NI and router. |
|
History: |
27/04/2010 Initial version. <wsong83@gmail.com> |
03/06/2011 Remove the sc_unit datatype to support data width larger than 64. <wsong83@gmail.com> |
|
*/ |
|
#ifndef RT_DRIVER_H_ |
#define RT_DRIVER_H_ |
|
#include "define.h" |
#include <systemc.h> |
#include "pdu_def.h" |
|
SC_MODULE(RTDriver) { |
|
public: |
// port with network interface |
sc_port<sc_fifo_in_if<FLIT> > NI2P; |
sc_port<sc_fifo_out_if<FLIT> > P2NI; |
sc_out<bool> CP [SubChN]; |
sc_in<bool > CPa [SubChN]; |
|
// signals from interface to router |
sc_out<sc_lv<ChBW*4> > rtid [4]; |
sc_out<sc_lv<3> > rtift; |
sc_out<sc_lv<SubChN> > rtivc; |
sc_in<sc_logic> rtia; |
sc_in<sc_lv<SubChN> > rtic; |
sc_out<sc_lv<SubChN> > rtica; |
|
sc_in<sc_lv<ChBW*4> > rtod [4]; |
sc_in<sc_lv<3> > rtoft; |
sc_in<sc_lv<SubChN> > rtovc; |
sc_out<sc_logic> rtoa; |
sc_out<sc_lv<SubChN> > rtoc; |
sc_in<sc_lv<SubChN> > rtoca; |
|
// local variable |
sc_signal<bool> out_cred; /* the input credit */ |
sc_signal<bool> out_cred_ack; /* the input credit ack */ |
|
|
SC_HAS_PROCESS(RTDriver); |
RTDriver(sc_module_name name); |
|
void IPdetect(); // Method to detect the router input port |
void OPdetect(); // Method to detect the router output port |
void Creditdetect(); // Method to detect the credit ports |
void send(); // thread of sending a flit |
void recv(); // thread to recveive a flit |
void credit(unsigned int); // handle the output credit |
|
sc_signal<bool> rtinp_sig; // fire when the router input port is ready for a new flit |
sc_signal<bool> rtoutp_sig; // fire when the router output port has a new flit |
|
unsigned int c1o42b(unsigned int); // convert 1-of-4 to binary |
}; |
|
|
#endif |
/vc/syn/script/compile.tcl
15,7 → 15,7
# 31/05/2009 Initial version. <wsong83@gmail.com> |
|
set rm_top router |
set rm_para "VCN=>2, DW=>8, PD=>1" |
set rm_para "VCN=>2, DW=>8, PD=>2" |
|
# working directory |
if {[file exists work ] && [file isdirectory work ]} { |
64,4 → 64,4
|
report_constraints |
report_area |
exit |
exit |