上节介绍了数据对象的含义,并介绍了数据对象中变量的声明与使用范围。本节介绍使用最广泛的一种数据对象–信号(signal)。信号的使用范围最广,如果在Architecture的声明区域内定义,可以在Architecture的整个范围内使用,即全局可见。当然随着声明的区域不同,信号也有一定的可见范围。在VHDL语言规范中,信号可以综合成组合电路的连线类型,用于不同逻辑电路之间值的转递,也可以综合成时序电路的触发器模型,这一特性与system verilog中的logic数据对象类似。在Verilog语言中有wire与reg两种类型与之对应,见Verilog 变量声明与数据类型。在 VHDL中信号及其相关的操作,如信号赋值语句 ,决断函数(resolved function) ,延时语句等很好地描述了硬件系统的许多基本特征。
1. 信号声明
信号定义的语句格式与变量非常相似 ,信号定义也可以设置初始值 ,格式如下:
SIGNAL 信号名 数据类型:= 初始值;
或 SIGNAL 信号名 数据类型;
同样 信号初始值的设置不是必需的, 而且初始值仅在 VHDL 的行为仿真中有效, 与变量相比信号的硬件特征更为明显 ,它具有全局性特征 。例如 :在程序包中定义的信号对于所有调用此程序包的设计实体都是可见。 在实体中定义的信号在其对应的结构体中都是可见的, 实际上在entity中声明的端口除了具有方向外其特性与signal一致,是隐含的signal类型,而实体可以通过配置与多个构造体相关联,因此实体中声明的端口可以在多个构造体内可见。信号定义如下实例:
SIGNAL temp : STD_LOGIC := ‘0’ ; — 声明了单值信号temp, STD_LOGIC类型,初始值为字符’0’;
SIGNAL flaga, flagb : BIT ; — 声明了两个单值信号flaga,flagb,BIT类型,无初始值;
SIGNAL data : STD_LOGIC_VECTOR(15 DOWNTO 0 ) ; — 声明了矢量信号data, STD_LOGIC_VECTOR, 无初始值;
SIGNAL a : INTEGER RANGE 0 TO 15; –声明了整形信号a, 范围从0到15;
信号的使用和定义范围是实体(端口), 结构体和程序包(package), 在进程和子程序中不允许声明信号。 信号可以有多个驱动源, 但必须将此信号的数据类型定义为决断性数据类型。见std_logic与std_ulogic的区别。
2. 信号赋值
信号赋值为”<=”, 左边为信号名,右边为赋值表达式。信号采用如下格式:
信号名 <= 表达式;
例:
sum <= ci XOR a XOR b;
co <= (a AND b) OR (ci AND (a XOR b));
co_tmp[0]<= co;
表达式可以为是一个逻辑,算数或字符串等运算表达式,也可以是其它的数据对象,如其它信号,变量或常数等。在信号的赋值语句中还可以插入延时,成为延时赋值语句,如:
b <= a after 20 ns; –将a的值延迟20 ns赋值给 b;
延时赋值语句中的延时部分,只在仿真时有效,综合时自动忽略。
3. 信号的使用
-
连线
信号最常用的方式是等效成连线,如:
co <= (a AND b) OR (ci AND (a XOR b));
co_tmp[0]<= co and d;
上面的等效电路如图1所示,co可以看成一段连线,起到信号传递的作用。

图1
- 元件之间的信号传递
由于可以把已设计的实体文件例化成元件 在构造体中使用,元件之间的信号交互除了与本实体的端口交互外,信号是相互传递信息的惟一途径。将1位全加器例化到4位全加器的设计实例中,使用了信号为元件之间信息交互。
|
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 |
entity full_addition4 is generic( WIDTH_IN: integer:=4; WIDTH_OUT: integer:=4 ); port ( ci : in bit; a : in bit_vector(WIDTH_IN-1 downto 0); b : in bit_vector(WIDTH_IN-1 downto 0); sum : out bit_vector(WIDTH_OUT-1 downto 0); co : out bit ); end full_addition4; ARCHITECTURE arch_fadd4 of full_addition4 is signal co_tmp : bit_vector(WIDTH_IN-1 downto 0); --signal co_tmp used for signal propagate among different components --SIGNAL d1,d2,d3,d4,d5 : INTEGER RANGE 0 TO 255; component full_addition1 generic( WIDTH_IN : integer; WIDTH_OUT : integer ); port ( ci : in bit; a : in bit; b : in bit; sum : out bit; co : out bit ); end component; begin -- sum <= ci XOR a XOR b; -- co <= (a AND b) OR (ci AND (a XOR b)); full_addition1_inst0 : full_addition1 generic map( WIDTH_IN => 1, WIDTH_OUT => 1 ) port map( ci => ci, a => a(0), b => b(0), sum => sum(0), co =>co_tmp(0) ); full_addition1_inst1 :full_addition1 generic map( WIDTH_IN => 1, WIDTH_OUT => 1 ) port map( ci => co_tmp(0), a => a(1), b => b(1), sum => sum(1), co =>co_tmp(1) ); full_addition1_inst2 : full_addition1 generic map( WIDTH_IN => 1, WIDTH_OUT => 1 ) port map( ci => co_tmp(1), a => a(2), b => b(2), sum => sum(2), co =>co_tmp(2) ); full_addition1_inst3 : full_addition1 generic map( WIDTH_IN => 1, WIDTH_OUT => 1 ) port map( ci => co_tmp(2), a => a(3), b => b(3), sum => sum(3), co =>co_tmp(3) ); co<=co_tmp(3); end arch_fadd4; |
- 等效成触发器
在进程中,如果敏感量是时钟属性,则信号会等效成触发器模型。如:
|
1 2 3 4 5 6 7 8 9 10 11 12 13 |
PROCESS (clk) VARIABLE cnt : INTEGER RANGE 0 TO 255; BEGIN IF (clk'EVENT AND clk = '1') THEN IF clear = '0' THEN cnt := 0; ELSE cnt := cnt + 1; END IF; END IF; qc <= cnt; END PROCESS; |
关于时序电路的设计,以及process 的使用将在process章节中讲解。