设mysql 自定义数据类型型tim的定义语句为“TYPE tim IS ( sec, min, hours, day, moth, year;tim’LOW 属性值为

第五章 VHDL语言的主要描述语句-vhdl case语句
您现在的位置:&&>>&&>>&第五章 VHDL语言的主要描述语句
第五章 VHDL语言的主要描述语句来源:&&&&关键词:
  错误语句 END PROCESS; 2、WAIT UNTILWAIT UNTIL 语句的完整书写格式为:WAIT UNTIL 表达式; 当表达式的值为“真”时,进程被启动,否则进 程被挂起。 该语句在表达式中将建立一个隐式的敏感信号量 表,当表中的任何一个信号量发生变化时,就立即对 表达式进行一次评估。如果评估结果使表达式返回一 个“真”值,则进程脱离等待状态,继续执行下一个 语句。例如: WAIT UNTIL ((X*10)&100);在这个例子中,当信号量X的值大于或等于10时,进程 执行到该语句将被挂起;当X的值小于10时进程再次被 启动,继续执行WAIT 语句的后继语句。 举例例:用wait until语句描述时钟沿,实现D触发器 architecture rtl of begin process begin d iswait until clk'event and clk='1';q &= 3、WAIT FORWAIT FOR 语句的完整书写格式为: WAIT FOR 时间表达式; WAIT FOR 语句后面跟着的是时间表达式,当进程执 行到该语句时将被挂起,直到指定的等待时间到时, 进程再开始执行WAIT FOR 语句后继的语句。 例如: WAIT FOR 20 这个语句中时间表达式是一个常数值20ns,当进程执行 到该语句时将等待20ns。一旦20ns时间到,进程将执行 WAIT FOR 语句的后继语句。 例如: WAIT FOR (a*(b+c));此语句中,FOR后面是一个时间表达式,a*(b+c)是时 间量。WAIT FOR 语句在等待过程中,要对表达式进 行一次计算,计算结果返回的值就作为该语句的等待 时 间 。 例 如 ,a=2,b=50ns,c=70ns 。 那 么 WAIT FOR (a*(b+c)) 这 个 语 句 将 等 待 240ns , 也 就 是 说 该 语 句 和 WAIT FOR 240ns是等价的。 4、多条件WAIT语句在前面已叙述的3个WAIT语句中,等待的条件都是单 一的,要么是信号量,要么是布尔量,要么是时间量。实 际上WAIT语句还可以同时使用多个等待条件。例如: WAIT ON nmi,interrupt UNTIL ((nmi=TRUE) OR (interrupt=TRUE)) FOR 5上述语句等待的是3个条件: 第一,信号量nmi和interrupt任何一个有一次新的变化; 第二,信号量nmi或interrupt任何一个取值为“真”; 第三,该语句已等待5us。只要上述3个条件中一个或多个条件满足,进程将再次启动, 继续执行WAIT语句的后继语句。 应该注意的是,在多条件等待时,表达式的值至 少应包含一个信号量的值,例如:WAIT UNTIL (interrupt=TRUE) OR (old_clk=?1?); 如果该语句的interrupt和old_clk两个都是变量,而不是 信号量,那么,即使两个变量的值有新的改变,该语 句也不会对表达式进行评估和计算(事实上,在挂起 的进程中变量的值是不可能改变的)。这样,该等待 语句将变成无限的等待语句,包含该等待语句的进程 就不能再启动。在多种等待条件中,只有信号量变化 才能引起等待语  句表达式的一次新的评价和计算。 5、超时等待往往在所设计的程序模块中,等待语句所等待的 条件,在实际执行时不一定会碰到。这时,等待语句 通常要加一项超时等待项,以防止该等待语句进入无 限期的等待状态。但是,如果采用这种方法,应作适 当的处理,否则就会产生错误的行为。 超时等待举例ARCHITECTURE wait_example OF wait_example ISSINGAL sendB,sendA:STD_LOGIC; BEGIN sendA&=' 0 '; A:PROCESSBEGINWAIT UNTIL sendB=' 1 '; sendA&=' 1 ' AFTER 10 WAIT UNTIL sendB=' 0 '; sendA&=' 0 ' AFTER 10 END PTROCESS A; B:PROCESS BEGIN WAIT UNTIL sendA=' 0 ';sendB&=' 0 ' AFTER 10WAIT UNTIL sendA=' 1 '; sendB&=' 1' AFTER 10 END PTROCESS B; END wait_进程A执行到第一条wait 语句时处于无限期等待状态, 进程B执行到第二条wait语句 时处于无限期等待状态。两 个进程处于相互等待状态, 每个进程的等待条件都需要 对方继续执行。这种情况我 们称为“死锁”状态。为了 能够避免这种无限等待状态, 我们可以加入超时等待语句, 同时用ASSERT语句进行提示。 加入超时等待的语句ARCHITECTURE wait_example OF wait_example ISSINGAL sendB,sendA:STD_LOGIC; BEGIN sendA&=' 0 '; A:PROCESS B:PROCESS BEGIN WAIT UNTIL( sendA=' 0 ?) FOR 1 ASSERT(sendA=? 0?) REPORT”sendA timed out at ? 1? “ SEVERITY ERROR; sendB&=' 0 ' AFTER 10 WAIT UNTIL (sendA=' 1 ?) FOR 1BEGINWAIT UNTIL( sendB=' 1 ?) FOR 1 ASSERT(sendB=? 1 ?) REPORT”sendB timed out at ? 1? “ SEVERITY ERROR; sendA&=' 1 ' AFTER 10 WAIT UNTIL (sendB=' 0 ?) FOR 1 ASSERT(sendB=? 0 ?) REPORT”sendB timed out at ? 0? “ASSERT(sendA=? 0 ?)REPORT”sendA timed out at ? 0? “ SEVERITY ERROR sendB&=' 1' AFTER 10 END PTROCESS B; END wait_SEVERITY ERRORsendA&=' 0 ' AFTER 10 END PTROCESS A;如果条件不满足则等待1us之 后执行后续的程序,而不会无限 期等待。 5.1.2 断言语句(ASSERT)ASSERT语句主要用于程序仿真、调试中的人机对话,它可以 给出一个文字串作为警告和错误信息。ASSERT语句的书写格 式为: ASSERT 条件 [REPORT 输出信息] [SEVERITY 级别]; 如果条件为真则向下执行另一个语句,如果条件为假,则 输出错误信息和错误级别。REPORT后面的错误信息应用双引 号括起来。ASSERT语句给程序的调试和仿真带来极大的方便,这样的 语句一般只用于行为级仿真中,而不能进行逻辑综合。 例: ASSERT(sendB=? 1 ?) REPORT “sendB timed out at ? 1? ” SEVERITY ERROR;该断言语句的条件信号量是sendB=?1?。如果执行到该语句 时,信号量sendB=?0?,说明条件不满足,就会输出REPORT后 跟的文字串。该文字串说明,出现了超时等待错误。 SEVERITY 后 跟 的 错 误 等 级 告 诉 操  作 人 员 , 其 出 错 等 级 为 ERROR。 5.1.3 信号代入语句书写格式: 目的信号量&=信号量表达式; 意义:将右边信号量表达式的值赋给左边的目的信号 量。注意1)代入符号与小于等于的区别;2)代入符号两边信号量的类型和长度应一致;3)信号一般使用的场合及与变量的区别。 5.1.4 变量赋值语句书写格式: 目的变量:=表达式; 意义:表达式的值替代目的变量的值,立即有效。注意1)两边的数据类型必须相同; 2)目的变量的类型和范围及初值应事先给出; 3)右边的表达式可以是变量,信号或字符; 4)变量只在进程或子程序中使用,它无法传递到进 程之外。 补充:变量与信号的差异1)赋值方式的不同: 变量:= 表达式; 信号 & = 表达式; 2)硬件实现的功能不同: 信号代表电路单元、功能模块间的互联,代表实际的硬 件连线;变量代表电路单元内部的操作,代表暂 存 的临时数据。 3)有效范围的不同:信号:程序包、实体、结构体;全局量。 变量:进程、子程序;局部量。 4)赋值行为的不同: 信号赋值延迟更新数值;变量赋值立即更新数值; 补充举例:信号赋值与变量赋值的比较 信号赋值: architecture rtl of sig is signal a,b : std_ -- 定义信号 -- 在进程内部信号是延时更新,信号只有 begin 在整个过程执行完毕后(end process)才更新完 process(a, b) 成。此例中, a &= b先是b的初值赋给a,但a begin 的值并不是立即更新;所以在执行 b &= a a &= 时,a是先前的a,即是要将a的初始值 b &= 赋给b;当程序执行到end process时, 和b才更新完成,最终a和b值互换。 -- 结果是 a 和 b 的值互换 补充举例:信号赋值与变量赋值的比较 变量赋值: architecture rtl of var is begin process variable a,b:std_ -- 定义变量 begin 变量的赋值立即生效,a的值立即更新为b的初 a := 始值 b := 此时的a已经变为b的初值,于是就是将b的 初值代入 -- 结果是a和b的值都等于b的初值 补充:信号的多次赋值a. 一个进程:最后一次赋值有效architecture rtl of ex is signal a : std_ begin process(…) begin a &= … a &=-- 结果是a=c 补充:信号的多次赋值b. 多个进程:多源驱动 architecture rtl of ex is signal a : std_ begin process(…) begin a &= … process(…) begin a &= ... 线与、线或、三态-- 结果是信号a将由多个驱动源驱动注意进程语句(Process Statement)是 一个并发语句。在一个构造体内可 以有几个进程语句同时存在,各进 程语句是并发执行的。但是,在进 程内部所有语句应是顺序描述语句 5.  1.5 IF语句IF语句可用于选择器、比较器、编码器、译码器 状态机的设计,是VHDL语言中最基础、最常用的 语句。 IF语句根据制定的条件来确定语句执行顺序,共 有三种类型。 1、IF语句的门闩控制格式: IF 条件 THEN顺序处理语句; END IF;当程序执行到该IF语句时,就要判断IF语句所指定 的条件是否成立。如果条件成立,则执行顺序处理 语句;不成立则跳过IF语句所包含的顺序处理语句, 而向下执行IF语句的后续语句。这里的条件起到门 闩的控制作用。 D触发器的描述举例LIBRARY IEEE;USE IEEE.STD.LOGIC.1164.ALL; ENTITY dff IS PORT(clk,d : IN STD_LOGIC;注此例中,IF语句的条件是 时钟信号clk事件发生, 且时钟clk=?1?(时钟脉冲 上升沿到来)。只有在 这个时候d端信号值才赋 值给q端。当该条件不满 足时,q端维持原来的输 出值。q : OUT STD_LOGIC);END ARCHITECTURE rtl OF dff IS BEGIN PROCESS( clk ) BEGIN IF( clk?EVENT AND clk=? 1 ?) THENq&=d;END IF; END PROCESS; END 2、IF语句的二选择控制格式: IF 条件 THEN顺序处理语句;ELSE顺序处理语句;END IF;当条件满足时,则执行THEN和ELSE之间的顺序处 理语句;如不满足则执行ELSE和END IF之间的顺序 处理语句。 IF二选择控制举例二选一电路ARCHITECTURE BEGIN PROCESS( a, b, sel ) BEGIN IF ( sel =? 1 ? ) THEN rtl OF mux2 IS注此例中,二选一电路的 输入端为a和b,选择控制 端为sel,输出端为c。c&=ELSE c&=b; END IF; END PROCESS; END 格式: IF3、IF语句的多条件控制条件 THEN注在多选择控制的IF 语句中,设置了多个条 件。当某个条件满足时 就执行跟在该条件这后 的顺序处理语句, 如果条件都不满足则执 行ELSE和END IF之间 的语句。顺序处理语句; ELSIF 条件 THEN顺序处理语句;┄ELSIF 条件 THEN顺序处理语句; ELSE 顺序处理语句; END IF;IF语句的多选择控 制又称为IF语句的嵌套。 IF语句多条件控制语句举例四选一电路:LIBRARY IEEE; USE IEEE.STD_LOGIC_1164.ALL; ENTITY mux4 IS PORT ( input : IN STD_LOGIC_VECTOR ( 3 DOWNTO 0); sel : IN STD_LOGIC_VECTOR ( 1 DOWNTO 0); y: END mux4; ARCHITECTURE rtl OF mux4 IS BEGIN PROCESS( input, sel ) BEGIN OUT STD_LOGIC); ELSIF ( sel = “10” ) THEN y &= input ( 2 ); ELSE y &= input ( 3); END IF; END PROCESS; END注IF ( sel = “00” ) THENy &= input ( 0 ); ELSIF ( sel = “01” ) THEN y &= input ( 1 );if_then_elsif 语句中隐 含了优先级别的判断,最 先出现的条件优先级最高, 可用于设计具有优先级的 电路。如8-3优先级编码器。 3、IF语句小结(1)IF语句可以用于凡是可以进行条件控制的 逻辑电路设计。 (2)IF语句的条件判断的输出是布尔量,即是 “真”(true)或“假”(FALSE)。  因此在IF语句的 条件表达式中只能使用关系运算操作符(=,/=,&, &, &=, &=)及逻辑运算操作符的组合表达式。 5.1.6 CASE语句case 语句常用来描述总线或编码、译码行为。 可读性比if 语句强。 格式: CASE 表达式 IS WHEN 条件表达式=&顺序处理语句; END CASE; 当CASE 和 IS 之间的表达式的取值满足指定的条件表达式的 值时,程序将执行后跟的,由符号=&所指的顺序处理语句。 条件表达式的形式可以是: 1)一个值;2)多个值的“或” 关系;3)一个取值范围;4)表示其它所有的缺省值。 CASE语句中条件表达式四种不同的表达形式: WHEN 值=&顺序处理语句;------单个值WHEN 值| 值| 值| … | 值|=&顺序处理语句;-----多个值的“或” WHEN 值 TO 值=&顺序处理语句;-------一个取值范围WHEN OTHERS=&顺序处理语句;-------其它所有缺省值 CASE语句使用举例LIBRARY IEEE; USE IEEE.STD_LOGIC_1164.ALL; ENTITY mux4 IS PORT ( a, b, i0 ,i1, i2, i3 : IN STD_LOGIC;注1)前面例子中使用多选择控制 的IF语句来描述四选一选择器时, 发现 if_then_elsif 语句中隐含了 优先级别的判断,最先出现的条 件优先级最高。 1)而在使用CASE语句描述选择 器行为时,CASE语句没有值的 优先级,所有值是并行处理的; 2)WHEN后面的值应全部列出 来; 3)WHEN后面的值不能重复使 用。q : OUT STD_LOGIC);END mux4; ARCHITECTURE mux4_behave OF mux4 IS SIGNAL sel : STD_LOGIC_VECTOR( 1 DOWNTO 0); BEGIN sel&= b& PROCESS ( sel, i0, i1, i2, i3 ) BEGIN CASE sel IS WHEN “00”=&q&=i0; WHEN “01”=&q&=i1; WHEN “10”=&q&=i2; WHEN “11”=&q&=i3; END CASE; END PROCESS; END mux4_并 符 的 构 量置 用 连 成运 于 接 位算 位 而 矢 带有WHEN OTHERS项举例(3-8译码器)LIBRARY IEEE; USE IEEE.STD_LOGIC_1164.ALL; ENTITY decode3to8 IS PORT ( a, b, c, G1, G2A, G2B: IN STD_LOGIC; y : OUT STD_LOGIC_VECTOR( 7 DOWNTO 0)); END decode3to8; ARCHITECTURE rtl OF decode3to8 IS SIGNAL indata: STD_LOGIC_VECTOR( 2 DOWNTO 0); WHEN “100”=&y&=“”; WHEN “101”=&y&=“”;WHEN “110”=&y&=“”;WHEN OTHERS=&y&=“XXXXXXXX”; END CASE; ELSEY&=“”;END IF; END PROCESS; ENDBEGINindata&= c&b&a; PROCESS( indata, G1, G2A, G2B ) BEGIN注Indata是矢量数据,除了取“0”和“1”之外,还有可能 取值为“X” “Z” 和“U”等。 尽管这些取值在逻辑电路综 合时没有用,但在CASE语 句中必须将有可能的值都描 述出来,所以本例应加一相 WHEN OTHERS项。使它包 含所有缺省项。IF (G1=?1? AND G2A=?0? AND G2B=?0? ) THENCASE indata IS WHEN “000”=&y&=“”; WHEN “001”=&y&=“”; WHEN “010”=&y&=“”; WHEN “011”=&y&=“”; Case 语句使用注意事项CASE 表达式 IS WHEN   分支条件 =& 顺序处理语句; WHEN 分支条件 =& 顺序处理语句;┇ WHEN 分支条件 =& 顺序处理语句; END CASE;1)分支条件的值必须在表达式的取值范围内。 2)两个分支条件不能重叠。 3)CASE语句执行时必须选中,且只能选中一个分支条件。 4)如果没有others分支条件存在,则分支条件必须覆盖表达式所 有可能的值。 对std_logc, std_logic_vector数据类型要特别注意使用others分支 条件。 5.1.7 LOOP语句LOOP语句与其它高级语句中的循环语句一样, 使程序能进行有规则的循环,循环次数受迭代算法控 制。VHDL语言中常用来描述位片逻辑及迭代电路的 行为。 LOOP语句书写格式一般有两种:1)FOR循环 变量;2)WHILE条件。 1、FOR 循环变量书写格式如下[标号]:FOR 循环变量顺序处理语句;IN离散范围 LOOPEND LOOP [标号]; 循环变量的值在每次循环中都将发生变化;离散范围则表示循 环变量在循环过程中依次取值的范围。例如: sum:=0; ASUM: FOR i IN 1 TO 9 LOOP sum=i+ ----sum初始值为0 END LOOP ASUM; 该例中i是循环变量,它可取1,2,….,9共9个值,也就是 sum=i+sum的算式应循环计算9次。该程序的功能是对1~9的数 进行累加计算。 FOR循环举例LIBRARY IEEE; USE IEEE.STD_LOGIC_1164.ALL; ENTITY parity_check IS PORT ( a: IN STD_LOGIC_VECTOR (7 DOWNTO 0); y: OUT STD_LOGIC); END parity_ ARCHITECTURE rtl OF parity_check IS输入8位2进制代码注输出校验码1)本例实际是8位偶校 验电路BEGINPROCESS( a ) VARIABLE BEGIN tmp: STD_LOGIC;2)i是一个循环变量, 使用时无需先声明,也 不能代入信号量和变量。 3)进程内tmp是变量, tmp的值通过赋给信号y 而带出进程。奇偶校验位IN 0 TO 7 LOOPtep:= ?0?;FOR itmp:=tmp XOR a( i ); END LOOP;y&=END PROCESS; END对送进来的8位数每一位都与中间变量相 异或 补充:奇偶校验基础知识? 什么是奇偶校验电路? 利用奇(偶)校验方法进行检错的组合逻辑电路称为奇偶 校验器。 ? 奇偶校验的原理: 根据代码中全部位数相加的“和” 来进行奇校验或偶校验。 ? “和”操作的特点:偶数个1,它的和总是0;奇数个1, 它的和总是1。 ? 奇校验就是看2进制数的1的个数为奇数;偶校验相反, 就 是 看 2 进 制 数 中 1 的 个 数 为 偶 数 。 2、WHILE条件书写格式如下:[标号]: WHILE 条件 LOOP 顺序处理语句; END LOOP [标号];如果条件为“真” ,则进行循环;如果条件为“假”,则结束循 环。如: i:=1; --对1~9的数进行累加计算, sum:=0; 利用i&10的条件使程序结束循 sbcd: WHILE ( i&10 ) LOOP 环,通过i:=i+1实现循环变量 sum:= i+ 的递增。 --循环变量 i 需事先定义、赋 i:=i+1; 初值,并指定其变化方式  。END LOOP 例:用WHILE语句来描述奇偶校验电路LIBRARY IEEE; USE IEEE.STD_LOGIC_1164.ALL; ENTITY parity_check IS PORT ( a : IN STD_LOGIC_VECTOR (7 DOWNTO 0); y: OUT STD_LOGIC) ; END parity_ ARCHITECTURE behave OF parity_check IS BEGIN PROCESS( a ) VARIABLE temp : STD_LOGIC;在 WHILE-LOOP 语 句 中 的变量i要首先声明才能 使 用 , 这 一 点 和 FORLOOP语句中不一样。 循环变量 i 需事先定义、 赋初值,并指定其变化 方式。 一 般 使 用 FOR-LOOP 语 句比 WHILE-LOOP语句 更多。VARIABLE i : INTEGER;BEGIN temp :=?0?;i:= 0; WHILE (I&8 ) LOOPtemp:= temp XOR a( I );i:= i+1;END LOOP;y&=END PROCESS; END 5.1.8 NEXT语句在LOOP语句中用NEXT语句来跳出本次循环,格式为:NEXT [标号] [WHEN 条件];NEXT语句执行时将停止本次迭代,而转入下一次新的 迭代。“标号”为下次迭代的起始位置,而条件为NEXT 语句执行的条件。如果无“标号”也无条件,则只要执行到该语句就无条件跳出本次循环,从LOOP语句的起始位置进入下一次循环。 NEXT语句实际上是用于LOOP语句的内部循环控制。 NEXT 语句举例PROCESS( a, b) CONSTANT max_limit : INTEGER := 255; BEGINFOR i IN 0 TO max_limit LOOPIF (done( i )= TRUE ) THEN NEXT;ELSEdone ( i ):= TRUE ; END IF ;无“标号”也无条件,则只要执行 到该语句就无条件跳出本次循环q( i )&=a ( i )AND b( i );END LOOP; END PROCESS; 5.1.9 EXIT语句EXIT 语句用于结束循环状态,从LOOP语句中跳 出,结束LOOP语句的正常执行。格式:EXIT [标号] [WNEN 条件];如果EXIT后面没有跟“标号”和“WHEN条件”, 则程序执行到该语句时就无条件地从LOOP语句中跳出, 结束循环状态,继续执行LOOP语句后继的语句。 EXIT 语句举例PROCESS( a ) VARIABLE int_a : INTEGER; BEGIN int_a := FOR i IN 0 TO max_limit LOOP IF ( int_a&=0 ) THEN EXIT; ELSE本例中,如果 int_a小于或等于0时就 执 行 EXIT 语 句 , LOOP 语 句 执 行 结 束 。int_a :=int_a C1;q( i )&=3.1416/ REAL?( a*i ); END IF;y&=END PROCESS; EXIT 语句的三种书写格式1.EXIT 语 句 后 面 没 有 “ 循 环 标 号 ” 或 “ WHEN 条 件”,当执行到该语句时就跳出包含该EXIT语句的 循环。 2.EXIT语句后跟“LOOP语句的标号”,执行EXIT语 句时将跳到标号所说明的标号。 3. EXIT 语句后跟“WHEN 条件”语句,只有当条件 为真时才跳出循环,如果条件不为真则执行下一条语 句。 补充:EXIT 语句与NEXT语句比较 next语句与exit语句的格式与操作功能 非常相似; 区别是:next语句是跳向loop语句的起 始点,而exit语句则是跳向loop语句的 终点。 5.2 并发描述语句VHDL的并发语句用来描述一组并发行为,它是并 发执行的,与程序的书写顺序无关。 *进程语句(PROCESS)  ; *并发(CONCURRENT)信号代入语句; *条件(CONDITIONAL)信号代入语句; *选择(SELECTIVE)信号代入语句;*并发(CONCURRENT PROCEDURE)过程调用语句; *块(BLOCK)语句。 5.2.1 进程(PROCESS)语句各个进程之间是并发处理的,而在进程内部则是 按顺序处理的。在一个构造体内部可以有多个 PROCESS 语 句 同 时 并 发 执 行 。 PROCESS 语 句 是 VHDL语句中是基本的语句。 特点: 1、进程与进程,或其它并发语句之间的并发性; 2、进程内部的顺序性; 3、进程的启动与挂起,必须要有一个显式的敏感 信号量表或者包含一个WAIT语句; 4、进程与进程,或其它并发语句之间的通信。 5.2.2 并发信号代入语句代入语句(用符号“&=”)可以在进程内部使用,是按 顺序执行的;代入语句也可以在构造体内部的进程外使用, 那么这些代入语句之间是并发执行的。因些,一个并发信号 代入语句实际上是一个进程的缩写。 并发代入语句在仿真时刻同时运行,它表征了各个独立 器件的各自的独立操作。如: a&=b+c; ---分别描述加法器和乘法器行为。在实际系统中加 d&=e*f; 法器和乘法器是同时并发执行的。 代入符号“&=”的右边可以用算术表达式,也可以用逻 辑运算表达式,还可以用关系操作表达式。 PROCESS和并发代入语句ARCHITECTURE behave OF a_var ISBEGIN output&=a(i);END可以等效于: ARCHITECTURE behave OF a_var IS一个简单并行信号赋值BEGINPROCESS( a,i ) BEGIN语句是一个进程的缩写。output&=a(i);END PROCESS; END 5.2.3 条件信号代入语句 格式:目的信号量 &= 表达式1 WHEN 条件1 ELSE表达式2 WHEN 条件2 ELSE 表达式3 WHEN 条件3 ELSE ┆ ┆ ELSE表达式n;在每个表达式后面都跟有用“WHEN”所指定的条件,如果满 足该条件,则该表达式值代入目的信号量;如果条件不满足, 则再判断下一个表达式所指定的条件。最后一个表达式可以不 跟条件,即所有条件都不满足时 条件信号代入语句举例利用条件信号代入语句实现四选一逻辑电路。ENTITY mux4 IS PORT ( i0, i1, i2, i3, a, b : IN STD_LOGIC; q : OUT STD_LOGIC); END mux4; ARCHITECTURE rtl OF mux4 ISSIGNAL sel : STD_LOGIC_VECTOR ( 1 DOWNTO 0 );BEGIN sel&= b&a;q&= i0 WHEN sel=“00” ELSEq&= i1 WHEN sel=“01” ELSE q&= i2 WHEN sel=“10” ELSE q&= i3 WHEN sel=“11” ELSE ?X?; END 条件信号代入语句与IF语句的区别*IF语句只能在进程内部使用,而条件信号代入语句则可以 在进程内部也可以在进程之外。 *条件信号代入语句中的ELSE是必须的,而IF语句中的 ELSE可有可无;*条件信号代入语句不能进行嵌套,受制于没有自身值代 入的描述,不能生成锁存电路。*条件信号代  入语句所描述的电路与逻辑电路实际工作比 较相近,故一般设计都难以掌握。只有当进程语句、IF语句 和CASE语句难于描述时,才用条件信号代入语句。 条件信号赋值语句与进程中的多选择 if 语句等价:PROCESS(sela, selb, a, b, c)BEGINIF sela=‘1’ THEN q &= a WHEN sela = ?1? ELSE q &=b WHEN selb = ?1? ELSEc;ELSIF selb=‘1’ THENq &= ELSE q &= END IF;END PROCESS; 5.2.4 选择信号代入语句格式:WITH 表达式 SELECT目的信号量 &= 表达式1 WHEN 条件1, 表达式2 WHEN 条件2, ┆ 表达式n WHEN 条件n;注 1)不能有重叠的条件分支。2)最后条件可为 others。否则,其它条件 必须能包含表达式的所有可能值。 3)选择信号赋值语句与进程中的 case 语 句等价。 用选择信号代入语句实现四选一电路LIBRARY IEEE; USE IEEE.STD_LOGIC_1164.ALL; ENTITY mux IS PORT ( i0, i1, i2, i3, a, b : IN STD_LOGIC; q : OUT STD_LOGIC ); END ARCHITECTURE behave OF mux IS SIGNAL sel : INTEGER; BEGIN WITH sel SELECT sel&= 0 WHEN a=?0? AND b=?0? ELSE 1 WHEN a=?0? AND b=?1? ELSE2 WHEN a=?1? AND b=?0? ELSE3 WHEN a=?1? AND b=?1? ELSE 4; ENDq&=i0 WHEN 0,i1 WHEN 1, i2 WHEN 2 , i3 WHEN 3,条件信号代入语句, 根据a和b不同取值, 选择信号代入语句, 对信号sel代入值 根据sel的不同值来 完成选择功能?X? WHEN OTHERS; 选择信号赋值语句与进程中的 case 语句等价:PROCESS(sel, a, b, c, d) BEGIN CASE sel IS WHEN “00” =& q &= WHEN “01” =& q &= WHEN “10” =& q &= WHEN OTHERS =& q &= END CASE; END PROCESS;WITH sel SELECT q &= a WHEN “00”, b WHEN “01”, c WHEN “10”, d WHEN OTHERS; 5.2.5 并发过程调用语句并发过程调用(Concurent Procedure Call )语句 可以出现在构造体中,而且是一种可以在进程之外 执行的过程调用语句。有关过程的结构及书写方法 在前面已讲过,我们回顾一下。格式: PROCEDURE 过程名(参数1, 参数2, …) IS [定义语句]; BEGIN[顺序处理语句];END 过程名; 关于过程调用应注意的问题①并发过程调用语句是一个完整的语句,在它的前面可以加标号;②并发过程调用语句是应带有IN,OUT或者INOUT的参数,它们应列于过程名后跟的括号内;③并发过程调用可以有多个返回值,但这些返回值必须通过过程中所定义的输出参数带回。④并发过程调用语句实际上是一个过程调用进程的简写。⑤在过程中尽量不要出现自变量表中没有出现过的信号量,如果出现将会带来问题。 并发过程调用举例ARCHITECTURE … ARCHITECTURE … BEGIN vector_to_int (z, x_flag, q ) … END; BEGINPROCESS( z, q )BEGIN vector_to_int (z, x_flag, q ) … 并发过程调用是对位矢量Z 进行数值转化,使之成为十 EN  D PROCESS; 进制数整数q。 x_flag是标志 位,为“真”表明转换失败, END; 为“假”表明转换成功。左例中并发过程调用语句和右例的过程调用进程完全等效 5.2.6 块(BLOCK)语句BLOCK是一个并发执行语句,通常用于构造体的结 构化描述,其格式为:说明语句通常包括:标号: BLOCK 块头 {说明语句}; BEGIN {并发处理语句}; END BLOCK 标号名;*USE子句; *子程序说明及子程序体; *类型说明; *常数说明; *信号说明;*元件说明。 BLOCK语句的模块化设计举例设计一个CPU,为简化起见,假设这个CPU只 由ALU(算术逻辑单元)模块和REG8(寄存器)模 块组成。其中ALU模块和REG8模块的行为分别由 两个BLOCK语句来描述。每个模块相当于CPU电 原 理 图 中 的 子 原 理 图 ( REG8 模 块 中 又 由 8 个 REG1,REG2,…,REG8子模块组成)。在每个块内 能够有局部信号、数据类型、常数等说明。任何一 个客体可以在构造体中说明,也可以在块中说明。 ARCHITECTURE cpu_blk OF IS SIGNAL ibus, dbus : tw32; BEGIN ALU: BLOCK SIGNAL qbus : tw32; BEGIN ---ALU行为描述语句 END BLOCK ALU;ALU模块REG8: BLOCKSIGNAL zbus : tw32; BEGIN REG1: BLOCK ----REG1 行为描述语句 END BLOCK REG1; ----其它REG8行为描述语句 END BLOCK REG8; END cpu_子模块1REG模块 应用BLOCK语句应注意的问题1)由于BLOCK可以嵌套,内层BLOCK块能够使用外层BLOCK块所说明的 信号,而外层BLOCK块却不能够使用内层BLOCK块中所说明的信号。 2)BLOCK是一个独立的子结构,它可以包含PORT和GENERIC语句。3)不同的模块中使用相同的信号名,在语法上是合法的,而且这两个信号分 别在各自的说明区域有效。因此可以这样认为,它们是具有相同信号名各自 独立的信号。但是,为了能正确区分,我们通常取不同的名字,不至发生混 淆。如: BLK1: BLOCKSIGNAL qbus : tw32; BEGIN BLK2: BLOCK改为BLK2_qbusSIGNAL qbus : tw32;BEGIN -----BLK2语句 END BLOCK BLK2;-----BLK1语句END BLOCK BLK1; 5.3 其它语句和有关规定的说明 5.3.1 命名规则和注解的标记在VHDL语句中大小写是没有区别的,所有语句中用大写 字母或小写字母都可以,也可有大小写混合使用。但有两种情 况例外,这就是用单引号括起来的字符和用双引号括起来的字 符串,这时大写字母和小写字母是有区别的。在VHDL语言中所使用的名字(名称),如信号名、实体 名,构造体名、变量名等,在命名时应遵守如下规则:1)名字的最前面应该是英文字母; 2)能使用的字符只有英文字母、数字和下划线“_” ; 3)不能连续使用“_”符号,在名字的最后也不能使用“_” 。4)其注释从两个短划线“--”符号开始到该项末尾(回车、 换  行符)结束。 命名举例SIGNAL a_bus : STD_LOGIC_VECTOR( 7 DOWNTO 0 ); SIGNAL 302_bus : … --不能以数字开头SIGNAL
: … --@不能作为名称的字母SIGNAL a__bus : … --?_?不能连着使用 SIGNAL a_bus_ : … --?-?不能放在名称的最后。 5.3.2 ATTRIBUTE (属性)描述与定义语句VHDL语句中有属性预定义功能,该功能有许多重要的应 用,例如检出时钟边沿,完成定时检查,获得未约束的数据 类型的范围等。ATTRIBUTE语句可以从所指定的客体中获得 关心的数据或信息。如: TYPE number IS INTEGER RANGE 9 DOWNTO 0; 若想得到 number的最大值,则可用下面的语句:自定义一个叫“number” 的数据类型,它取值 9~0的整数i:= number?HIGH; --i=9而要得到最小值则可用: i:= number?LOW; --i=0通过预定义属性描述语句,可以得到客体的有关值、功 能、类型和范围。 1、数值类属性数值类属性用来得到数组、块或者一般数据的有关值。数值 类属性又分为3个子类:*一般数据的数值属性;*数组的数值属性; *块的数值属性。 1)一般数据的数值属性 一般数据的数值属性的书写格式为: 客体’ 属性名 一般数据的数值属性有以下4种: ? T?LEFT------得到数据类或子类区间的最左端的值; ? T?RIGHT------得到数据类或子类区间的最右端的值; ? T?HIGH------得到数据类或子类区间的最高端的值; ? T?LOW------得到数据类或子类区间的最低端的值;T为客体,代表一般数据类和子类的名称,符号“’”紧跟客体 后面,符号“’”后面是属性名。例:TYPE number IS 0 TO 9;i:=number?LEFT; -- i=0 i:=number?RIGHT; -- i=9 i:=number?HIGHT; -- i=9 i:=number?LOW; -- i=0 改为 9 DOWNTO 0, 则会怎样? 数值类属性不光适用于数字类型,而且该属性还可以适 用于任何标量类型。如: 枚举类型数据定义,数据的TYPE tim IS ( sec, min, hours, day, moth, year ); 序号值从左到右递增 SUBTYPE severse_tim IS tim RANGE moth DOWNTO tim1&=tim?LEFT; --得到sec tim2&=tim?RIGHT; --得到year tim3&=tim?HIGHT; --得到year 枚举类型数据 的数值属性 子类型的定义,注意数据 的区间用的是DOWNTOtim4&=tim?LOW; --得到sectim5&=reverse_tim?LEFT; --得到moth tim6&=reverse_tim?RIGHT; --得到mintim7&=reverse_tim?HIGHT; --得到mothtim8&=reverse_tim?LOW; --得到min在使用时,应注意方向,即是用DOWNTO 还是TO, LEFT和LOW,RIGHT和HIGHT是不一样的。 2)数组的数值属性数组的类属性只有一个即:T?LENGTH ,得到 给定数组的长度。例:PROCESS ( a )TYPE bit4 IS ARRAY ( 0 TO 3 ) of BIT ; TYPE bit_strange IS ARRAY ( 10 TO 20 )OF BIT ; VARIABLE len1, len2 : INTEGER; BEGIN len1:= bit4?LENGTH; --len1=4 len2:=bit_strange?LENGTH; --len2=11 END PROCESS; 一个包  含11个元素数组的定 义,其起始位位10和20. 一个包含4个元素数组的定 义该属性可用于任何标量类数组(如枚举类型)和多维的 标量类区间的数组。具体请同学们看书。 3)块的数值属性块的数据属性有两种:’STRUCTURE和’ BEHAVIOR。 这两种属性用于块和构造体,通过它们可以验证所说明的 块或构造体是用结构描述方式还是用行为方式来描述模块 的。这对设计人员检查程序是非常有用的。如果块有标号说明,或者构造体有构造体名说明,而且 在 块 和 构 造 体 中 不 存 在 COMPNENT 语 句 , 那 么 用 属 性’BEHAVIOR将得到“TRUE”的信息;如果在块和构造体中只有COMPONET语句或被动进程, 那么用属性’STRUCTURE将得到“TRUE”的信息。 2.函数类属性函数类属性是指属性以函数的形式,让设计人员得到 有关数据类型、数组、信号的某些信息。 函数类属性3种:①数据类型属性函数;②数组属性函 数;③信号属性函数。 1)数据类型属性函数 用数据类型属性函数可以得到有关数据类型的各种信 息。 例如,给出某类数据值的位置,那么利用位置函数属 性就可以得到该位置的数值。另外,利用其它相应属性 还可以得到某些值的左邻值各右邻值等等。 数据类型属性函数的6种属性函数?POS(x) --得到输入x值的位序号; ’VAL(x) --得到输入位置序号x的值;’SUCC(x) --得到输入x值的下一个值;’PRED(x) --得到输入x值前一个值; ’LEFTOF(x) --得到邻接输入x值的左边的值; ’RIGHTOF(x) --得到邻接输入x值右边的值。数据类型属性函数的一个典型应用就是将枚举 或物理类型的数据转换成整数。如将物理量uA转换成 整数的实例。 PACKAGE ohms_law IS TYPE current IS RANGE 0 TO 1000000 UNITS uA; mA=1000uA; A=1000mA; END UNITS; ENTITY calc_resistance IS PORT ( i: IN e: IN r: OUT resistance);对物理类型数据current(电流) 进行定义,基本单位为uA.END calc_ ARCHITECTURE behav OF calc_resistance IS BEGIN ohm_proc: PROCESS( i, e) BEGIN VARIABLE covi, cove, int_r : INTEGER; convi:=current?pos(i); END PROCESS; END将 输 入 电 流 值 ( i) 的 位置序号赋予变量 convi,例如输入电流值 为10uA,那么赋予变量 convi的值为10--以微安为单位的电流值 PACKAGE t_time IS TYPE time IS ( sec, min, hous, day, month, year); TYPE reverse_time IS time RANGE year DOWNTO END t_在包集合t_time中定义了两类枚 举数据类型.--得到time类型数据中day值的前一个值 --得到reverse_time类型数据中hous值的下一个值 --得到reverse_time类型数据中day值的前一个值time ?SUCC (hous) --得到time类型数据中hous值的下一个值 time?PRED (day )reverse_time?SUCC (hous ) reverse_time  ?PRED (day )time?RIGHTOF (hous )--得到time类型数据中hous值的右临值time ?LEFTOF (hous ) --得到time类型数据中hous值的 左临值 由上述可知,对于递增区间来说,下面的等式将成立: ’SUCC (x ) =?RIGHTOF (x ) ?PRED (x ) =?LEFTOF (x ) 对于递减区间来说,下面的等式将成立: ’SUCC (x ) =?LEFTOF (x )对于枚举类型数据的 递增区间中的某个值, 其下一个值等于右临 值,其前一个值等于 左邻值?PRED (x ) = ?RIGHTOF (x ) 2) 数组属性函数利用数组属性函数可得到数组的区间。在对数组的每一个元素 进行操作时,必须知道数组的区间。数组属性函数有4种:’RIGHT(n) --得到索引号为n的区间的右端位置号。’LEFT(n) --得到索引号为n的区间的左端位置号。 ’LOW(n) --得到索引号为n的区间低端位置号。 ’HIGHT(n) --得到索引号为n的区间的高端位置号。 数组属性函数定义中的索引号n就是多维数组中所定义的多维 区间序号,缺省值为n=1。当索引号取缺省值时,上面的数组 函数就代表对一维区间进行操作。 如果数组中的元素递增排列,存在如下关系:’LEFT(n) =?LOW(n)’LEFT(n) = ?HIGHT(n)?RIGHT(n) = ?HIGHT(n)?RIGHT(n) = ?LOW(n)如果数组中的元素递增排列,存在如下关系: 3)信号属性函数信号属性函数用来得到信号的行为信息。信号属性函数共有 5种:’EVENT --如果在当前一个相当小的时间间隔内,事件发生了, 那么,函数将返回个“真”的布尔量,否则就返回“假”。’ACTIVE --如果在当前一个相当小的时间间隔内,信号发生 了改变,那么,函数将返回个“真”的布尔量,否则就返回 “假”。 ’LAST_EVENT --该属性函数将返回一个时间值,即从信号前 一个事件发生到现在所经过的时间。 ’LAST_VALUE --该属性函数将返回一个值,即从信号最后一 次改变以前的值。’LAST_ACTIVE --该属性函数将返回一个时间值,即从信号 前一次改变到现在的时间。 (1)属性’EVENT和’LAST_VALUE属性’EVENT通常用于确定时钟信号的边沿,用它可 以检查信号是否处于某一个特殊的值,以及信号是否刚好已 发生变化。 发生事件:信号电平发生变化。 clk?EVENT clk=?1?clk?EVENT时钟信号的上升沿clk=?0? 时钟信号的下降沿 时钟信号的上升沿描述:clk?event and clk = ?1?时钟信号的下降沿描述:clk?event and clk = ?0?上升沿触发器描述举例: process(clk) begin if clk?event and clk = ?1? then q &=这个进程描述了D 触发器的工作原理, 当D触发器上升沿 到 来 时 , 将 d值 传 送给q。 在此例中,如果原 来的电平为“0”,那 么逻辑是正确,但 如果原来的电平时 不定  状态,这种描 述被认为是上升沿 就是错误。 为 了 避 免 clk=?X?( 不 定 状 态 ) 而 得 不 到 上 升 沿 , 通 常 用’LAST_VALUE属性,以确保时钟在上升沿还是在下 降沿,如:IF (clk?EVENT ) AND (clk=?1?) AND( clk?LAST_VALUE=?0? )THEN q&=d; END IF;该句保证时钟脉冲在变成 “1”电平之前一定是出于“0” 状态。 (2) 属性’LAST_EVENT用属性’LAST_EVENT可得到信号上各种事件发生以 来所经过的时间。该属性常用于检查定时时间,如检查建立 时间、保持时间和脉冲宽度等。用于检查建立时间和保持时 间的示例如下图所示。clk上升沿是时间检查的参 考沿。建立时间检查数据 输入信号从输入到clk上升 沿来到时不发生变化的时 间。保持时间检查时钟参考 沿后面的一段数据输入 信号不发生变化的时间。 LAST_EVENT属性对建立时间进行检查的实例ENTITY dff IS GENERIC (setup_time , hold_time : TIME ); PORT ( d, clk : IN STD_LOGIC; PROCESS( clk ) BEGIN IF ( clk=?1?) ANDq : OUT STD_LOGIC);BEGIN setup_check: PROCESS( clk ) BEGIN该进程在clk上升沿 (clk?EVENT ) THEN 时 执 行 ASSERT( 断 q&=d; 言)语句,并对建 END IF; 立时间进行检查, 看其是否大于或等 END PROCESS; 于规定的时间。END dff_IF ( clk=?1? ) AND ( clk?EVENT ) THEN ASSERT ( d?LAST_EVENT &=setup_time ) REPORT “ SETUP VIOLATION ” SEVERITY ERROR; END IF; END PROCESS setup_ ENDARCHITECTURE dff_behav OF dff ISBEGIN (3)属性’ACTIVE和’LAST_ACTIVE 属性’ACTIVE和’LAST_ACTIVE在信号发生转换或 事件发生(信号活跃)时被触发。’ACTIVE返回值为“TRUE”或“FALSE”。如果在当 前一个相当小的时间间隔内信号不活跃,则函数返回 “FALSE”,而如果活跃则返回“TRUE”。’LAST_ACTIVE返回一个时间值,即返回该信号从 前一次信号活跃到现在所经历的时间值。 信号活跃与事件发生的区别信号活跃:信号值的任何变化,如由‘0?变到‘1?是 一个信号活跃,而信号从‘0?变到‘0?也是一个信号 活跃,唯一的判断准则是发生了什么事。 事件发生:信号值的发生变化,如由‘0?变到‘1?是 一个事件,而‘0?变到‘0?则不是一个事件,原因是 信号值没有变。 3.信号类属性信号类属性用于产生一种特别的信号,这个特别的 信号是以所加属性的信号为基础而形成的。也就是说, 在这个特别信号中包含了所加属性的有关信息。信号类 属性有4种,它们是: S?DELAYED[(time)]:该属性将产生一个延时的信号,其 信号类型与该属性所加的信号相同,即以属性所加的信 号为参考信号,经括号内时间表达式所确定的时间延时 后所得的延迟信号。S?STABLE[(time)]:该属性可建立一个布尔信  号,在括号 的时间表达式所说明的时间内,若参考信号没有发生事 件,则该属性可得到“真”的结果。 S?QUIET[(time)]:该属性可建立一个布尔信号,在括号 内的时间表达式所说明的时间内,若参考信号没有发生转 换或其它事件,则属性可以得到“真”的结果。S?TRANSACTION:该属性可以建立一个BIT类型的信号, 当属性所加的信号发生转换或事件时,其值都将发生改变。 需要注意的是,上述的信号类属性不能用于子程序中,否 则程序在编译时会出现编译错误信息。 (1)属 性’DELAYED属性’DELAYED可以建立一个所加信号的延迟版本。 为实现同样的功能,也可以用传输延时语句 (TRANSPORT DELAY)。在使用传输延时语句时,传 输延时所产生的信号是一个新信号,它必须在程序中予以 说明。 在使用’DELAYED属性时,如果所说明的延时时间 事先未加定义,那么实际的延时时间就被赋为0ns。 属性’DELAYED还用于保持检查。具体见书P109例 5-34。 (2)属性’STABLE属性’STABLE用来确定信号(所产生的特别信号)对应的 有效电平(高电平“1”或低电平“0” ),它可以在一个指定 的时间间隔内,确定信号(原信号或输入信号)是否正好发 生改变或者没有发生改变(即信号活跃)。属性返回的值就 时信号(所产生的特别信号)本身的值,用它可以触发其它 的进程。LIBRARY IEEE;USE IEEE.STD_LOGIC_1164.ALL ENTITY pulse_gen IS ARCHITECTURE puls_gen OF pulse_gen IS BEGIN b&=a? STABLE(10ns); END pulse_ 当a没有发生改变时,b为高电平; 当a发生改变时,b由高电平变为低 电平,低电平持续时间为10ns(该 值由属性括号内的时间值确定)。PORT ( a : IN STD_LOGIC;b : OUT STD_LOGIC); END pulse_ ab上图所示,当波形a加到上页程序模块时,即可得到输出波形b。左图中,a在10ns和30ns各有一次改变,因而b在10ns和30ns各有10ns的低电平时间。在 55ns处和60ns处a又各有一次改变,但是,由于改变的间隔小于10ns,因此b 从55ns处开始到70ns处结束,将变为低电平。如果属性’STABLE后跟括号 中的时间值被说明为0ns或者未加说明,那么当a发生改变时,输出b在对应 的时间位置将产生Δ宽度的低电平,见右图。 属性’STABLE也可用于检测信号的上升沿,例如:IF (( clk?EVENT) AND (clk=?1?) AND ( clk?LAST_VALUE=?0? )) THEN --IF (NOT( clk?STABLE) AND (clk=?1?) AND ( clk?LAST_VALUE=?0? )) THEN---上述两种情况都可以检出上升沿,但是,在’EVENT情 况下,在内存有效利用及速度方面将更加有效。这是因为属 性’STABLE需要建立一个额外的信号,这将使其使用更多的 内存。 (3)属性’QUIT属性 ’QUIT 具有与 ’STABLE 相同的功能  ,但是, 属性’QUIT由所加信号上的电平值的改变所触发(事 件除外)。属性’QUIT将建立一个布尔信号,当所加 的信号没有发亮,或者在所说明的时间内没有发生事 件是,利用该属性可得到一个“真”的结果。 该属性常用于描述较复杂的一些信号值的变化, 如开关电平或者器件的值的解析。 (4)属性’TRANSACTION属性 ’TRANSACTION 将建立一个数据类型为BIT 的信号,当属性所加的信号每次从“1”或“0”发生改 变时,就触发该BIT信号翻转。该属性通常用于进程 调用。 4. 数据类型属性利用该属性可以得到数据类型的一个值。它仅仅是一种类 型属性,而且必须使用数据值类或函数类属性的值来表示。其 格式为: t?BASE 利用该属性可以得到数据t的类型或子类型,它仅仅作为 其它属性的前缀来使用。例:TYPE color IS (red, blue, green, yellow, brown, black ); SUBTYPE color_gun IS color RANGE red TO VARIABLE a : 则: 枚举类型数据定 义,数据的序号 值从左到右递增Color_gun?BASE 返 回 color 数 据 类 型,’RIGHT得到数据的最右端值 --a=black Color?BASE返回color_gun数据类型a:=color_gun?BASE?RIGHT;a:=color?BASE?LEFT; --a=red?succ(x)得到输入x值的下一个值 a:=color_gunBASE?SUCC(green); --a=yellow 5. 数据区间类属性在VHDL语言中有两类数据区间类属性,这两类 属性仅用于受约束的数组类型数据,并且可返回所选 择输入参数的索引区间。这两个属性是: a?RANGE[ (n)] 将返回一个由参数n值所指出的第n个数据区间。 a?REVERSE_RANGE[ (n)] 将返回一个次序颠倒的数据区间。 例:将一位矢量转换成整数的函数,程序中的循环次 数应由输入参数vect的位数来确定。 FUNCTION vector_to_int ( vect: STD_LOGIC_VECTOR)RETURN INTEGER IS VARIABLE result : INTEGER := 0;BEGINFOR i IN vect?RANGE LOOP result:= result*2;IF vect( i ) =?1? THENresult:= result +1; END IF;此例是一个函数语句。 函 数 内 部 使 用 了 FOR LOOP循环语句,循环次 数由输入参数vect的位数 确定。如vect是8位的位 矢量,vect?RANGE将返 回输入矢量的区间8。 ’ REVERSE_RANGE 类似于属性’RANGE , 所不同的仅仅是返回区 间的次序是颠倒的。END LOOP;RETURN END vector_to_ 6. 用户自定义的属性用户自定义的属性格式为: ATTRIBUTE 属性名: 数据子类型名;ATTRIBUTE 属性名 OF 目标名:目标集合 IS 公式;在对要使用的属性进行说明以后,就可以对数据类型、信号、 变量、实体、构造体、配置、子程序、元件、标号进行具体 的描述,如: ATTRIBUT max_area : REAL;ATTRIBUT max_area OF fifo : ENTITY IS 150.0;用户定义属性的值在仿真中是不能改变的,一般不能用 于逻辑综合。 7. GEN  ERATE语句GENERATE语句用来产生多个不同的结 构,它有FOR-GENERAT和IF-GENERATE两种使 用形式。生成语句的作用:复制建立 0 个或多个备份。(并 行 结构) FOR-GENERAT :采用一个离散的范围决定备份的数目。 IF-GENERATE :有条件地生成 0 个或 1 个备份。 FOR ┅ GENRATE 语句 语法:标号:FOR 循环变量 IN 范围{ 并发处理语句 }GENERATEEND GENERATE [标号];范围:整数表达式 to 整数表达式 整数表达式 downto 整数表达式 for --- loop 语句与 for ┅ generate 的比较: 例:用GENERATE语句生成4个D触发器组成的 移位寄存器端口a是移位寄存器的输入端,端口b是输出端,clk是输 出信号 ENTITY shift IS PORT ( a, clk : IN STD_LOGIC; b : OUT STD_LOGIC ); END ARCHITECTURE gen_shift OF shift IS COMPONENT dff PORT ( d, clk : IN STD_LOGIC; q : OUT STD_LOGIC);在构造体的说明部 分 有 COMPONENT 语句,对D触发器进 行了声明。 构造体中有两个并发 信号赋值语句和一个 FOR GENERATE 语 句。信号赋值语句将 内部信号z和输入端 口a和输出端口b连接 起 来 。 GENERATE 语句中利用元件例化 语句(位置映射方法) 产生4个D触发器。END COMPONENT;SIGNAL BEGIN z(0)&= g1: FOR i IN 0 z: STD_LOGIC_VECTOR (0 TO 4 );TO 3 GENERATEdffx: dff PORT MAP ( z (i), clk, z(i+1)); END GENERATE; b&=z(4); END gen_ IF ┅ GENERATE 语句语法:标号:IF 条件表达式 GENERATE{ 并行语句 }END GENERATE [标号];if 语句与 IF ┅ GENRATE 的区别: 1、IF ┅ GENERATE 没有类似于 IF 语句的 ELSE 或 ELSIF 分支语句。 2、if 语句是顺序语句,IF ┅ GENERATE为并 行语句。 FOR-GENERATE语句只能用于规则的构造体, 但由于在大多数情况下,电路的两端总是有不规则 性,无法用同一种结构表示。为解决这种不规则电 路的统一描述方法,就可采用IF-GENERATE语句。
本文★★网址:/yuedu/17175.html
好文大家读
上一篇文章:
下一篇文章:
Copyright &
All Rights Reserved.《》}

我要回帖

更多关于 c语言自定义数据类型 的文章

更多推荐

版权声明:文章内容来源于网络,版权归原作者所有,如有侵权请点击这里与我们联系,我们将及时删除。

点击添加站长微信