第3章ⅤHDL入门 实践表明,ⅤHDL入门的最有效的方法是通过具体电路实例引出对应的ⅤHDL表述, 通过这些有针对性的表述进而学习相关的语句语法,再通过多个类似实例的学习,逐步完 备VHDL的基本语法知识和提高电路的描述和设计能力。据此,全章通过数个简单、完整 而典型的ⅤHDL设计示例,使读者初步了解用VHDL表达和设计电路的方法,并对由此而 引出的ⅤHDL语言现象和语句规则能逐步趋向系统的了解 由于用硬件描述语言来对电子线路的表达和设计是EDA建模和实现技术中最基本和 最重要的方法,其它的许多方法都是建筑在这一基础之上的,如使用 MATLAB/DSP Builder 的设计方案、图形方式的状态机输入法、原理图输入法等等。因此ⅤHDL的学习在EDA 技术的掌握中具有十分重要的地位。 3.1简单组合电路的ⅤHDL描述 2选1多路选择器是典型的组合电路,本章以此电路的DL表述与设计为例,引出 相关的ⅤHDL结构、语句表述、数据规则和语法特点,并加以详细说明。 3.1.1多路选择器的VHDL描述 2选1多路选择器的电路模型,或元件图如图3-1所示。例3-1是其HDL的完整描述,即 可使用ⅤHDL综合器直接综合出实现即定功能的逻辑电路,对应的逻辑电路如图3-2所示,因 而可以认为是此多路选择器的内部电路结构 mux21a b 图3-1mux2la实体 图3-2mu21a结构体 注意,电路的功能可以是唯一的,但其电路的结构方式不是唯一的,它决定于综合器的基 本元件库的来源、优化方向和约束的选择、目标器件(指 FPGA/CPLD)的结构特点等等 图中,a和b分别为两个数据输入端的端口名,s为通道选择控制信号输入端的端口名,y 为输出端的端口名。“mux2la”是设计者为此器件取的名称(好的名称应该体现器件的基
第 3 章 VHDL 入门 实践表明,VHDL 入门的最有效的方法是通过具体电路实例引出对应的 VHDL 表述, 通过这些有针对性的表述进而学习相关的语句语法,再通过多个类似实例的学习,逐步完 备 VHDL 的基本语法知识和提高电路的描述和设计能力。据此,全章通过数个简单、完整 而典型的 VHDL 设计示例,使读者初步了解用 VHDL 表达和设计电路的方法,并对由此而 引出的 VHDL 语言现象和语句规则能逐步趋向系统的了解。 由于用硬件描述语言来对电子线路的表达和设计是 EDA 建模和实现技术中最基本和 最重要的方法,其它的许多方法都是建筑在这一基础之上的,如使用 MATLAB/DSP Builder 的设计方案、图形方式的状态机输入法、原理图输入法等等。因此 VHDL 的学习在 EDA 技术的掌握中具有十分重要的地位。 3.1 简单组合电路的 VHDL 描述 2 选 1 多路选择器是典型的组合电路,本章以此电路的 VHDL 表述与设计为例,引出 相关的 VHDL 结构、语句表述、数据规则和语法特点,并加以详细说明。 3.1.1 多路选择器的 VHDL 描述 2 选 1 多路选择器的电路模型,或元件图如图3-1所示。例3-1 是其 VHDL的完整描述,即 可使用 VHDL 综合器直接综合出实现即定功能的逻辑电路,对应的逻辑电路如图 3-2 所示,因 而可以认为是此多路选择器的内部电路结构。 图 3-1 mux21a 实体 图 3-2 mux21a 结构体 注意,电路的功能可以是唯一的,但其电路的结构方式不是唯一的,它决定于综合器的基 本元件库的来源、优化方向和约束的选择、目标器件(指 FPGA/CPLD)的结构特点等等。 图中,a和 b 分别为两个数据输入端的端口名,s 为通道选择控制信号输入端的端口名,y 为输出端的端口名。“mux21a”是设计者为此器件取的名称(好的名称应该体现器件的基
第3章VHDL入门 本功能特点)。 【例3-1】 ENTITY mux 21a PORt(a, b s:工NB工乎 y: OUT BIT END ENTITY mux21a ARCHITECTURE one oF mux21a Is BEGIN END ARCHITECTURE one 由例3-1可见,此电路的ⅤHDL描述由两大部分组成: (1)以关键词 ENTITY引导, END ENTITY mux21a结尾的语句部分,称为实体 VHDL的实体描述了电路器件的外部情况及各信号端口的基本性质,如信号流动的方向,流 动在其上的信号结构方式和数据类型等。图3-1可以认为是实体的图形表达 (2)以关键词 ARCHITECTURE引导, END ARCHITECTURE one结尾的语句部分 称为结构体。结构体负责描述电路器件的内部逻辑功能和电路结构。图3-2是此结构体的 某种可能的电路原理图表达。 在VHDL结构体中用于描述逻辑功能和电路结构的语句分为顺序语句和并行语句两部 分。顺序语句的执行方式类似于普通软件语言的程序执行方式,是按照语句的前后排列方 式逐条顺序执行的。而在结构体中的并行语句,无论有多少行语句,都是同时执行的,与 语句的前后次序无关(姑且暂时这样认为,以后将给予详细说明)。 例3-1中的逻辑描述是用 WHEN ELSE结构的并行语句表达的。它的含义是,当满足 条件s=0,即s为低电平时,a输入端的信号传送至y,否则即s为高电平时为输入端的 信号传送至y 也可以用其他的语句形式来描述以上相同的逻辑行为。例3-2中的功能描述语句都用 了并行语句,是用布尔方程的表达式来描述的。其中的“AND”、“OR”、“NOT”分别是“与”、 “或”、“非”的逻辑操作符号。 例3-3则给出了用顺序语句 IF THEN ELSE表达的功能描述 以上3例用不同的表达方式描述了相同的逻辑功能,其电路功能可以从图3-3的时序 波形( Quartus仿真波形)中看出,分别向a和b端输入两个不同频率的信号fa和fb(a> fb),当s为高电平时,y输出t,而当s为低电平时,y输出fa。显然,图3-3的波型证实 了ⅤHDL逻辑设计的正确性 注意,以上各例的实体和结构体分别是以“ END ENTITY XXX”和“END ARCHITECTUREⅹx”语句结尾的,这是符合VHDL的 IEEE STD10761993版的语法要 求的。若根据ⅤHDL87版本,即 IEEE STD10761987的语法要求,这两条结尾语句只需 写成“END,”或“ END XX”。但考虑到目前绝大多数常用的EDA工具中的ⅤHDL综合器 都兼容两种ⅤHDL版本的语法规则,且许多最新的VHDL方面的资料,仍然使用ⅤHDL87 版本语言规则,因此,出于实用的目的,对于以后出现的示例,不再特意指出VHDL两种 版本的语法差异处。但对于不同的EDA工具,仍需根据设计程序不同的ⅤDL版本表述
第 3 章 VHDL 入门 71 本功能特点)。 【例3-1】 ENTITY mux21a IS PORT ( a, b : IN BIT; s : IN BIT; y : OUT BIT ); END ENTITY mux21a; ARCHITECTURE one OF mux21a IS BEGIN y <= a WHEN s = '0' ELSE b ; END ARCHITECTURE one ; 由例 3-1 可见,此电路的 VHDL 描述由两大部分组成: (1) 以关键词 ENTITY 引导,END ENTITY mux21a 结尾的语句部分,称为实体。 VHDL 的实体描述了电路器件的外部情况及各信号端口的基本性质,如信号流动的方向,流 动在其上的信号结构方式和数据类型等。图 3-1 可以认为是实体的图形表达。 (2) 以关键词 ARCHITECTURE 引导,END ARCHITECTURE one 结尾的语句部分, 称为结构体。结构体负责描述电路器件的内部逻辑功能和电路结构。图 3-2 是此结构体的 某种可能的电路原理图表达。 在 VHDL 结构体中用于描述逻辑功能和电路结构的语句分为顺序语句和并行语句两部 分。顺序语句的执行方式类似于普通软件语言的程序执行方式,是按照语句的前后排列方 式逐条顺序执行的。而在结构体中的并行语句,无论有多少行语句,都是同时执行的,与 语句的前后次序无关(姑且暂时这样认为,以后将给予详细说明)。 例 3-1 中的逻辑描述是用 WHEN_ELSE 结构的并行语句表达的。它的含义是,当满足 条件 s ='0',即 s 为低电平时,a 输入端的信号传送至 y ,否则(即 s 为高电平时)b 输入端的 信号传送至 y。 也可以用其他的语句形式来描述以上相同的逻辑行为。例 3-2 中的功能描述语句都用 了并行语句,是用布尔方程的表达式来描述的。其中的“AND”、“OR”、“NOT”分别是“与”、 “或”、“非”的逻辑操作符号。 例 3-3 则给出了用顺序语句 IF_THEN_ELSE 表达的功能描述。 以上 3 例用不同的表达方式描述了相同的逻辑功能,其电路功能可以从图 3-3 的时序 波形(QuartusII 仿真波形)中看出,分别向 a 和 b 端输入两个不同频率的信号 fa 和 fb(fa > fb),当 s 为高电平时,y 输出 fb,而当 s 为低电平时,y 输出 fa。显然,图 3-3 的波型证实 了 VHDL 逻辑设计的正确性。 注意,以上各例的实体和结构体分别是以“ END ENTITY xxx ”和“ END ARCHITECTURE xx ”语句结尾的,这是符合 VHDL 的 IEEE STD 1076_1993 版的语法要 求的。若根据 VHDL’87 版本,即 IEEE STD 1076_1987 的语法要求,这两条结尾语句只需 写成“END;”或“END xx”。但考虑到目前绝大多数常用的 EDA 工具中的 VHDL 综合器 都兼容两种 VHDL 版本的语法规则,且许多最新的 VHDL 方面的资料,仍然使用 VHDL’87 版本语言规则,因此,出于实用的目的,对于以后出现的示例,不再特意指出 VHDL 两种 版本的语法差异处。但对于不同的 EDA 工具,仍需根据设计程序不同的 VHDL 版本表述
EDA技术与VHDL 在综合前作相应的设置。 【例3-2】 ENTITY mux21a IS PORt( a, b: IN BIT; s:工NB工乎 y: OUT BIT END ENTITY mux21 ARCHITECTURE one oF mux21a IS SIGNAL dr e: BIT BEGIN d < a AND (NOT S) y < d or e 【例3-3】 ENTITY mux21a I PORT( a, b, s: IN BIT y: OUT BIT END ENTITY mux21a ARCHITECTURE one oF mux21a Is BEGIN PROCESS(a,b, s) BEGIN IFs="0′THEN y < a ElSE <=b END IF; END PROCESS END ARCHITECTURE one p51m104m15第209m2m Ha酯e -B1puL000100LU10000001L0LU00u00100LU0D0U00 ULUL B1 pouooooL moon FUoODUDLUOOUDUOUn 图3-3mu21a功能时序波形 3.1.2相关语句结构和语法说明 以下将对例3-1至例3-3中出现的相关语句结构和语法含义作出说明 1.实体表达 VHDL完整的、可综合的程序结构必须能完整地表达一片专用集成电路ASIC器件的 端口结构和电路功能,即无论是一片74LS138还是一片CPU,都必须包含实体和结构体两
72 EDA 技术与 VHDL 在综合前作相应的设置。 【例 3-2】 ENTITY mux21a IS PORT ( a, b : IN BIT; s : IN BIT; y : OUT BIT ); END ENTITY mux21a; ARCHITECTURE one OF mux21a IS SIGNAL d,e : BIT; BEGIN d <= a AND (NOT S) ; e <= b AND s ; y <= d OR e ; END ARCHITECTURE one ; 【例 3-3】 ENTITY mux21a IS PORT ( a, b, s: IN BIT; y : OUT BIT ); END ENTITY mux21a; ARCHITECTURE one OF mux21a IS BEGIN PROCESS (a,b,s) BEGIN IF s = '0' THEN y <= a ; ELSE y <= b ; END IF; END PROCESS; END ARCHITECTURE one ; 图3-3 mux21a功能时序波形 3.1.2 相关语句结构和语法说明 以下将对例 3-1 至例 3-3 中出现的相关语句结构和语法含义作出说明: 1. 实体表达 VHDL 完整的、可综合的程序结构必须能完整地表达一片专用集成电路 ASIC 器件的 端口结构和电路功能,即无论是一片 74LS138 还是一片 CPU,都必须包含实体和结构体两
第3章VHDL入门 个最基本的语言结构。这里将含有完整程序结构(包含实体和结构体)的VHDL表述称为设 计实体。如前所述,实体描述的是电路器件的端口构成和信号属性,它的最简表式如下 【例3-4】 ENTITY e name Is poRt(p name port m data type p namei: port mi data type END ENTITY e name; 上式中, ENTITY、IS、PORT和 END ENTITY都是描述实体的关键词,在实体描述 中必须包含这些关键词。在编辑中,关键词不分大写和小写。 2.实体名 例3-4中的 e name是实体名,是标识符,具体取名由设计者自定。由于实体名实际上 表达的应该设计电路的器件名,所以最好根据相应电路的功能来确定,如4位二进制计数 器,实体名可取为 counter4b;8位二进制加法器,实体名可取为ader8b,等等。但应注意, 不应用数字或中文定义实体名,也不应用与EDA工具库中已定义好的元件名作为实体名 如or2、 latch等,且不能用数字起头的实体名,如74LSx 3.端口语句和端口信号名 描述电路的端口及其端口信号必须用端口语句PORT(別导,并在语句结尾处加分号 “;"。例3-4中的 p name是端口信号名,如例3-1中的端口信号名分别是a、b、s和y 4.端口模式 在例3-1的实体描述中,用IN和oU分别定义端口a、b和s为信号输入端口,y为信号 输出端口。一般,可综合的端口模式有四种,它们分别是“IN”、“oUr”、“ INOUT” 和“ BUFFER”,用于定义端口上数据的流动方向和方式: κIN:输入端口,定义的通道为单向只读模式。规定数据只能由此端口被读入实体。 κeOUI:输出端口,定义的通道为单向输出模式。规定数据只能通过此端口从实体 向外流出,或者说可以将实体中的数据向此端口赋值 κε INOUT:定义的通道确定为输入输出双向端口。即从端口的内部看,可以对此端 口进行赋值,或通过此端口读入外部的数据信息;而从端口的外部看,信号既可 由此端口流出,也可向此端口输入信号。如RAM的数据口,单片机的O口等 BUFFer:缓冲端口,其功能与 INOUT类似,区别在于当需要输入数据时,只允 许内部回读输出的信号,即允许反馈。如计数器设计,可将计数器输出的计数信 号回读,以作下一计数值的初值。与 INOUT模式相比, BUFFER回读的信号不是 由外部输入的,而是由内部产生,向外输出的信号 5.数据类型 例3-4中的data_type是数据类型名。例3-1中,端口信号a、b、s和y的数据类型都 定义为BIT。由于VHDL中任何一种数据对象的应用都必须严格限定其取值范围和数值类
第 3 章 VHDL 入门 73 个最基本的语言结构。这里将含有完整程序结构(包含实体和结构体)的 VHDL 表述称为设 计实体。如前所述,实体描述的是电路器件的端口构成和信号属性,它的最简表式如下: 【例 3-4】 ENTITY e_name IS PORT ( p_name : port_m data_type; ... p_namei : port_mi data_type ); END ENTITY e_name; 上式中,ENTITY、IS、PORT 和 END ENTITY 都是描述实体的关键词,在实体描述 中必须包含这些关键词。在编辑中,关键词不分大写和小写。 2. 实体名 例 3-4 中的 e_name 是实体名,是标识符,具体取名由设计者自定。由于实体名实际上 表达的应该设计电路的器件名,所以最好根据相应电路的功能来确定,如 4 位二进制计数 器,实体名可取为 counter4b;8 位二进制加法器,实体名可取为 adder8b,等等。但应注意, 不应用数字或中文定义实体名,也不应用与 EDA 工具库中已定义好的元件名作为实体名, 如 or2、latch 等,且不能用数字起头的实体名,如 74LSxx。 3. 端口语句和端口信号名 描述电路的端口及其端口信号必须用端口语句 PORT( )引导,并在语句结尾处加分号 “;”。例 3-4 中的 p_name 是端口信号名,如例 3-1 中的端口信号名分别是 a、b、s 和 y。 4. 端口模式 在例3-1的实体描述中,用IN和OUT分别定义端口a、b和s为信号输入端口,y为信号 输出端口。一般,可综合的端口模式有四种,它们分别是“IN”、“OUT”、“INOUT” 和“BUFFER”,用于定义端口上数据的流动方向和方式: ?? IN:输入端口,定义的通道为单向只读模式。规定数据只能由此端口被读入实体。 ?? OUT:输出端口,定义的通道为单向输出模式。规定数据只能通过此端口从实体 向外流出,或者说可以将实体中的数据向此端口赋值。 ?? INOUT:定义的通道确定为输入输出双向端口。即从端口的内部看,可以对此端 口进行赋值,或通过此端口读入外部的数据信息;而从端口的外部看,信号既可 由此端口流出,也可向此端口输入信号。如 RAM 的数据口,单片机的 I/O 口等。 ?? BUFFER:缓冲端口,其功能与 INOUT 类似,区别在于当需要输入数据时,只允 许内部回读输出的信号,即允许反馈。如计数器设计,可将计数器输出的计数信 号回读,以作下一计数值的初值。与 INOUT 模式相比,BUFFER 回读的信号不是 由外部输入的,而是由内部产生,向外输出的信号。 5. 数据类型 例 3-4 中的 data_type 是数据类型名。例 3-1 中,端口信号 a、b、s 和 y 的数据类型都 定义为 BIT。由于 VHDL 中任何一种数据对象的应用都必须严格限定其取值范围和数值类
EDA技术与ⅤHDL 型,即对其传输或存储的数据的类型要作明确的界定,因此,在ⅤHIDL设计中,必须预先 定义好要使用的数据类型,这对于大规模电路描述的排错是十分有益的。相关的数据类型 有 INTEGER类型、 BOOLEAN类型、 STD LOGIC类型和BIT类型等 BIT数据类型的信号规定的取值范围是逻辑位和0。在ⅤHDL中,逻辑位0和1的 表达必须加单引号,否则HDL综合器将0和1解释为整数数据类型 INTEGER BIT数据类型可以参与逻辑运算或算术运算,其结果仍是位的数据类型。ⅤHDL综合 器用一个二进制位表示BIl将例3-1中的端口信号a、b、s和y的数据类型都定义为BIr 表示:a、b、s和y的取值范围,或者说数据范围都被限定在逻辑位"l'和o的二值范围内 6.结构体表达 结构体的一般表达如例3-5所示。 【例3-5】 ARCHITECTURE arch name oF e name I [说明语句] BEGIN 功能描述语句) END ARCHITECTURE arch name 上式中, ARCHITECTURE、OF、IS、 BEGIN和 END ARCHITECTURE都是描述结构 体的关键词,在描述中必须包含它们。 arch name是结构体名,是标识符 说明语句]包括在结构体中,用以说明和定义数据对象、数据类型、元件调用声明等 等。[说明语句]并非是必须的,(功能描述语句)则不同,结构体中必须给出相应的电路功能 描述语句,可以是并行语句,顺序语句或它们的混合 般地,一个可综合的,完整的VHDL程序有比较固定的结构。设计实体中,一般首 先出现的是各类库及其程序包的使用声明,包括未以显式表达的工作库WORK库的使用声 明,然后是实体描述,最后是结构体描述,而在结构体中可以含有不同的逻辑表达语句结 构。如前所述,在此把一个完整的可综合的ⅤHDL程序设计构建为设计实体(独立的电路 功能结构),而其程序代码常被称为ⅵHIDL的RTL描述 7.赋值符号和数据比较符号 例3-1中的表达式y<=a表示输入端口a的数据向输出端口y传输;但也可以解释为信 号a向信号y赋值。在HDL仿真中赋值操作y<=a并非立即发生的,而是要经历一个模 拟器的最小分辨时间?后,才将a的值赋予y。在此不妨将?看成是实际电路存在的固有 延时量。ⅤHDL要求赋值符“<=”两边的信号的数据类型必须一致 例3-1中,条件判断语句 WHEN ELSE通过测定表式s=0的比较结果,以确定由 哪一端口向y赋值。条件语句 WHEN ELSE的判定依据是表式s=0′输出的结果。表式 中的等号“=”没有赋值的含义,只是一种数据比较符号。其表式输出结果的数据类型是布 尔数据类型 BOOLEAN。 BOOLEAN类型的取值分别是:true(真)和 false(伪)。即当s 为高电平时,表式s=0输出“ false”当s为低电平时,表式s=0输出“true”。 在ⅦHD综合器或仿真器中分别用1·和'0表达txue和 false。布尔数据不是数值,只
74 EDA 技术与 VHDL 型,即对其传输或存储的数据的类型要作明确的界定,因此,在 VHDL 设计中,必须预先 定义好要使用的数据类型,这对于大规模电路描述的排错是十分有益的。相关的数据类型 有 INTEGER 类型、BOOLEAN 类型、STD_LOGIC 类型和 BIT 类型等。 BIT 数据类型的信号规定的取值范围是逻辑位'1'和'0'。在 VHDL 中,逻辑位 0 和 1 的 表达必须加单引号,否则 VHDL 综合器将 0 和 1 解释为整数数据类型 INTEGER。 BIT 数据类型可以参与逻辑运算或算术运算,其结果仍是位的数据类型。VHDL 综合 器用一个二进制位表示 BIT。将例 3-1 中的端口信号 a、b、s 和 y 的数据类型都定义为 BIT 表示:a、b、s 和 y 的取值范围,或者说数据范围都被限定在逻辑位'1'和'0'的二值范围内。 6. 结构体表达 结构体的一般表达如例 3-5 所示。 【例 3-5】 ARCHITECTURE arch_name OF e_name IS [说明语句] BEGIN (功能描述语句) END ARCHITECTURE arch_name ; 上式中,ARCHITECTURE、OF、IS、BEGIN 和 END ARCHITECTURE 都是描述结构 体的关键词,在描述中必须包含它们。arch_name 是结构体名,是标识符。 [说明语句]包括在结构体中,用以说明和定义数据对象、数据类型、元件调用声明等 等。[说明语句]并非是必须的,(功能描述语句)则不同,结构体中必须给出相应的电路功能 描述语句,可以是并行语句,顺序语句或它们的混合。 一般地,一个可综合的,完整的 VHDL 程序有比较固定的结构。设计实体中,一般首 先出现的是各类库及其程序包的使用声明,包括未以显式表达的工作库 WORK 库的使用声 明,然后是实体描述,最后是结构体描述,而在结构体中可以含有不同的逻辑表达语句结 构。如前所述,在此把一个完整的可综合的 VHDL 程序设计构建为设计实体(独立的电路 功能结构),而其程序代码常被称为 VHDL 的 RTL 描述。 7. 赋值符号和数据比较符号 例 3-1 中的表达式 y<= a 表示输入端口 a 的数据向输出端口 y 传输;但也可以解释为信 号 a 向信号 y 赋值。在 VHDL 仿真中赋值操作 y<= a并非立即发生的,而是要经历一个模 拟器的最小分辨时间?后,才将 a 的值赋予 y 。在此不妨将? 看成是实际电路存在的固有 延时量。VHDL 要求赋值符“<=”两边的信号的数据类型必须一致。 例 3-1 中,条件判断语句 WHEN_ELSE 通过测定表式 s='0' 的比较结果,以确定由 哪一端口向 y 赋值。条件语句 WHEN_ELSE 的判定依据是表式 s='0' 输出的结果。表式 中的等号“=”没有赋值的含义,只是一种数据比较符号。其表式输出结果的数据类型是布 尔数据类型 BOOLEAN。BOOLEAN 类型的取值分别是:true(真)和 false(伪)。即当 s 为高电平时,表式 s='0' 输出“false”;当 s 为低电平时,表式 s ='0'输出“true”。 在 VHDL 综合器或仿真器中分别用'1'和'0'表达 true 和 false。布尔数据不是数值,只