SystemC中的端口和信号
芯片通过管脚与板上其它芯片或者元件通信,管脚有输入、输出和双向管脚。在Syst中,模块通过端口(Port)与其它模块通信。端口也分为输入(input)、输出(output)和双向端口(inout)。一个模块的端口或者通过信号(Signal)与其它模块的端口相连(其逻辑关系如图1),或者与子/父模块的端口直接相连(其逻辑关系如图2)。端口与信号的连接,以及端口和端口的直接连接在Syst中称作绑定。

图1 模块的端口通过信号相连
图2端口和端口直接相连
端口的数据类型可以是以下类型:
(1)常见C++数据类型,如long、int、char、short、float、double。
(2)SystemC专有数据类型,如sc_int<n>、sc_uint<n>、sc_bigint<n>、sc_biguint<n>、sc_bit、sc_log、sc_bv<n>、sc_lv<n>、sc_fixed、sc_ufixed、sc_fix、sc_ufix。
(3)用户自定义结构。如
- typedef struct _frame{
- unsigned short frame_control;
- unsigned short duration_id;
- char source_addr[6];
- char destination_addr[6];
- unsigned short sequence_control;
- char* body;
- unsigned fcs;
- } frame;
SystemC还支持抽象端口。假设接口direct_if的定义如下:
- class direct_if
- : public virtual sc_interface
- {
- public:
- // direct BUS/Slave interface
- virtual bool direct_read(int *data, unsigned int address) = 0;
- virtual bool direct_write(int *data, unsigned int address) = 0;
- }; // end class direct_if
- #endif
那么下面的代码定义了一个抽象端口:
sc_port<direct_if> arbiter_port;
SystemC的端口定义了与特定端口类型相关的方法,如read()和write()都是基本的端口类型sc_in,sc_out,sc_inout的方法。下面的语句是等效的。
mem[addr.read()]=wr_data.read();
mem[addr.read()]=wr_data;//C++编译器提供默认转换
而下面的语句是非法的:
mem[addr]=wr_data.read();
因为addr是sc_uint<8>类型,而数组的索引是unsigned int,C++编译器不能识别该默认转换。
SystemC端口的定义方法如下:
(1)输入端口:sc_in<端口数据类型> 端口名;
(2)输出端口:sc_out<端口数据类型> 端口名;
(3)双向端口:sc_inout<端口数据类型>端口名;
(4)特殊情况:时钟的定义可以如下sc_in_clk 时钟名字;
如sram8x256中的端口定义:
- sc_in_clk clk;
- sc_in<bool> wr_en;
- sc_in<sc_uint<8> > wr_data;
- sc_in<sc_uint<8> > addr;
- sc_out<sc_uint<8> > rd_data;
SystemC的端口和信号定义中大量的使用了模版类,如sc_in<sc_uint<8> > addr。端口和信号的类型在一对尖括号(<>)中表示。sc_unit<8>中的8代表数据只有8位。注意在声明中sc_in<sc_uint<8> >中间有一个额外的空格,这是必须的。
有时候需要声明一个端口向量,如计算机的数据和地址总线,这在SystemC中也是允许的,举例如下:
sc_in<sc_logic> a[32];
这句代码声明了a[0]到a[31]这32个端口,端口方向为输入,端口数据类型为sc_logic。信号也可以使用类似的办法声明:
sc_signal<sc_logic> addr[16];
上面这句代码声明了addr[0]到addr[15]这16个信号,信号类型为sc_logic。
- 上一篇:SystemC中的DELTA延迟
- 下一篇:Linux下安装SystemC