vhdl变量除法_VHDL语法总结以及编码风格(二)
本教程使用最新的VHDL標準VHDL-2008,該標準可以提高設計人員的工作效率,并且適合用于數字設計入門課程。目前大多數編譯器都支持VHDL-2008,但可能默認使用早期版本,所以在編譯VHDL-2008之前,修改EDA設置。為了保持簡潔準確的描述,VHDL教程使用拓展的巴科斯范式注釋。尖括號<>內的內容為必選項,::=是“被定義為”的意思,豎線|表示任選一個,{}大括號內的內容為可重復0至無數次的項,[]內的內容為可選項。(不過不需要過度關注這些,每個講解都帶有例子)
一、注釋、標識符和關鍵字
? ? ? 在VHDL中,單行注釋前面帶有(--)。VHDL-2008引入了多行注釋,即以/*開頭,以*/結束。
? ? ? ? VHDL中的關鍵字和標識符不區分大小寫。
? ? ? ? 標識符必須以字母開頭,并且可以包含任意數量的字母、數字(0-9)和下劃線。
? ? ? ? 末尾字符不能為下劃線。
? ? ? ? VHDL中定義的關鍵字不能作為標識符。
? ? ? ? 不允許出現兩個連續的下劃線。
例如:
合法標識符:Mux3、state_next
非法標識符:-Deal(起始不能為非英文字母)30Q(起始不能為數字)For(關鍵字不能作為標識符)
VHDL-2008定義了115個關鍵字,相比較其它編程語言算是很多了,但在學習時,不需要學習那么多,常用的一些知道即可。
二、類型
VHDL是一種強類型語言,每一個變量在使用前都必須聲明類型。下圖是一些相對常用的VHDL-2008關鍵字。
2.1 Std_logic
VHDL設計中常用的類型是std_logic。std_logic類型的信號或變量表示其值是單比特的。在電子電路中,使用電壓來表示0和1的邏輯值。在VHDL規范中,這些邏輯值可以用std_logic值0或1來表示。
2.2 Boolean
邏輯比較操作的結果被預定義為boolean,與std_logic不一樣的是,它的值為“真
“或”假“。當需要boolean時,VHDL-2008可以自動將一個std_logic轉化為boolean類型。
2.3 Integer
Integer(整數)和std_logic_vector類型不一樣,它的數值范圍為
Integer通常用來定義參數,比如一個多比特的std_logic_vector信號的寬度。Integer類型通常不用來存儲電路計算得到的數據。Integer類型采用十進制書寫方式,使用數字0-9。例如,數值100就寫成100(不需要加引號)
2.4 Std_logic_vector
VHDL使用std_logic_vector類型來表示多比特信號,它由std_logic構成的數組。要完全指定std_logic_vector類型,必須包含索引范圍。
例如:std_logic_vector(2 downto 0)是一個3比特std_logic_vector,索引值是從2到0。
2.5 子類型
如果一個定義的std_logic_vector類型出現的次數很多,給它一個名字會方便編碼,用戶定義的子類型就可以實現這一功能。
如下:subtype <名稱> is <子類型> ;
例如:subtype?state_type is std_logic_vector( 2 downto?0 );
聲明一個名叫 state_type的子類型,它的數據類型是3比特的std_logic_vector。
2.6 枚舉類型
VHDL提供了如下語法來定義枚舉數據類型:
type<名稱> is( <枚舉元素名稱> {, <枚舉元素名稱>} );
例如:type?state_type is ( SA, SB, SC, SD );
聲明了一個state_type的新類型,其值可以為SA、SB、SC或SD。
2.7 數組和記錄類型
VHDL提供兩個可以將數據類型集合起來的復合類型:數組和記錄。數組適合定義存儲器,定義一個數組類型的語法如下:
type<數組名稱> is array(<索引范圍>) of <子類型>;
例如:type?mem_type is array(0 to 255) of?std_logic_vector(15 downto?0);
聲明了一個新的數據類型,名字為?mem_type,它由256個16比特的類型為std_logic_vector(15 downto?0)的數構成的數組。
如果mem_type的類型為memory,那么memory(0)指的就是memory中的第一個字,類型為std_logic_vector(15 downto?0)。
VHDL中的記錄類型與C語言中的struct有些類似,可以將相關的信號集合到一根信號總線上。記錄類型的另一個作用就是在一個進程內用一個信號賦值語句對邏輯組合塊的所有輸出進行賦值。聲明一個記錄類型的語法如下:
type<記錄名稱> is record
<元素聲明>
{<元素聲明>}
end record;
其中,
<元素聲明>::= <名稱> {, <名稱> } : <子類型> ;
例如:
type?inst_type?is
????record
????opcode?:?std_logic_vector(6?downto?0);
????dst????:?std_logic_vector?(2?downto?0);
????src1???:?std_logic_vector(2?downto?0);
????src2???:?std_logic_vector(2?downto?0);
????end?record;
聲明了一個inst_type的記錄類型,它包含4個元素,分別是opcode、dst、src1和src2
從記錄中提取元素時,應該使用“.”。例如上面的記錄類型,如果inst_type的類型為inst的信號,那么提取元素opcode需要使用這樣的結構inst.opcode。
三 庫、包集合和使用多文件
類型std_logic_vector和std_logic不是VHDL語言的一部分,而是IEEE正式認可的標準包集合。為了在設計中使用std_logic_vector和std_logic必須添加行“library?ieee;”和“use ieee.std_logic_1164.all;”
四 設計實體
硬件設計的VHDL語言由具有一定層次的VHDL設計實體構成。設計實體定義了硬件快的接口以及內部結構。每個設計實體由兩部分組成:實體聲明和結構體。實體聲明包含輸入和輸出信號的端口聲明列表;結構體包含聲明部分(各種聲明)和結構體描述部分(包含一系列并行處理語句)。設計實體的邏輯由并發語句實現。如下:
entity?<實體名稱>?is
????????[?generic(?<類屬常量>?);?]
????????port(?<端口聲明 >?);
????????end?<實體聲明>;
????????architecture?<應用名稱或者叫結構名稱>?of?<實體名稱>?is
????????<類型聲明>
????????<常量聲明>
????????<元件聲明>
????????<內部信號聲明>
????????begin
????????<并發語句>
end?<應用名稱或者叫結構名稱>;
實體聲明以關鍵字entity開始,它通過端口的聲明列表來規定硬件設計內部和外部之間的接口。實體聲明還可以通過改變類屬常量的值來改變設計實體。可以使用關鍵字generic(英文意思是:通用的)在實體聲明中聲明類屬常量,該聲明可有可無(看設計需要)。
類屬常量最常用于參數化一個設計實體的輸入和輸出的位寬。端口說明語句描述了一個設計實體的輸入輸出,端口的模式表示信號是輸入(in)、輸出(out)、可讀的輸出(buffer)和雙向信號(inout)。
結構體以關鍵字architecture開始,它分為聲明部分和描述部分。聲明部分包含對結構體的聲明,描述部分包含實現邏輯功能的并發語句。這兩個部分由關鍵字begin分隔開。
聲明部分可能包含類型、常數、元件和內部信號聲明。
元件聲明可以通過例化,在一個設計實體的結構體中使用另一個設計實體。元件聲明的語句類似于實體聲明:
? ? ? ? ? ? ?component<元件聲明>i
? ? ? ? ? ? ? ? ? ?[ generic( <類屬常量> );?
?port( <端口聲明> );
?end component;
五、操作符和表達式
第一行中的“??”運算符是乘方運算符。邏輯運算符“not”是按位操作的,因此not 4b"1001"的結果是4b"0110"
第二三行中乘法(?),除法(/), 模 (mod), 加(+),減法(-),和并置運算符用于位連接(&)
第四行包含移位和循環移位運算符。移位運算符 (sll,srl, sla, sra)以“s”開始,后跟方向(左移為“l”,右移“r”),如果是邏輯移位,則最后為“l”(logic)。如果是算數移位,那么最后為“a”(arithmetic)。關鍵字ror表示向右循環移位(rotate to the right),rol表示向左循環移位(rotate to the left)。
第五行包含比較運算符,它們操作的對象是類型相同的兩個操作數,并產生類型為boolean的結果。“=”(等于),“/=”(不等于),<(小于),>(大于),<=(小于等于),>=(大于等于)
第六行中是邏輯運算符,and(與),or(或),nand(與非),nor(或非),xor(異或),xnor(異或非)。
第七行,VHDL-2008中的條件運算符“??”將std_logic的值轉化為boolean。
六、并發語句
6.1并發條件賦值
<信號名字> <= <表達式> when<條件> else
{ <表達式> when<條件> else}
<表達式>;
例:
Enc <=??"11" wheninput(3) = ’1’ else
"10" wheninput(2) = ’1’ else
"01" wheninput(1) = ’1’ else
"00";
當input(3)等于1時,Enc被賦予值“1”。如果input(3)不等于1,而input(2)等于1時,Enc被賦予值“10”。如果input(3)不等于1,input(2)不等于1,而input(1)等于1時,Enc被賦予值“01”。在所有其它情況下,Enc被賦值為“00”。這里注意,這個結構有嚴格的執行順序和優先級,僅有上一個語句不成立才會進入下一語句執行。
6.2 并發選擇信號賦值
并發選擇信號語句的形式如下:
with<信號名稱1>select
<信號名稱2> <= { <表達式 > when<選擇>, }
<表達式> when others;
例:
with?sel select
output <= in_a when2d"3",
in_b when2d"1" | 2d"2",
in_c when others;
例子描述了一個四路復用器構建的組合邏輯電路。該電路具有in_a, in_b,in_c,和sel四個輸入信號。如果sel等于2d"3",則將in_a值賦給output,如果sel值等于2d"1"或2d"2",那么把in_b值賦給output。其它情況,則將in_c賦給output。
注:條件信號賦值和選擇信號賦值之間區別,選擇信號賦值中的選擇條件是不允許重疊的,而條件信號賦值中的條件是可以重疊的。條件信號賦值中的條件是按照順序有優先級的。選擇信號的賦值的選擇條件必須是一個常數,而條件信號賦值的條件可以是任意一個表達式。
6.3 元件例化
元件例化語句形式如下
<元件實例名>: <元件> [ generic map( <關聯列表> ) ] port map( <關聯列表> );
上例中的generic map部分是可選的。如果存在這個語句,那么generic map可以改變被例化的設計實體中的generic所聲明的常量。簡單來講,generic map可以覆蓋掉被例化實體的generic聲明。
總結:原文英文版(Digital Design Using VHDL A Systems Approach),大多數內容來自該書,但也作了部分的刪減,也從其它教程中進行添加。下一期會把基本的語法結束,然后開始更新編碼風格。最近的計劃是時序和狀態機(交通燈)
友情鏈接:關于FPGA的其它文章
有問題可以在公眾號后臺留言
關注公眾號:AriesOpenFPGA
經典驛站:
庭有枇杷樹,吾妻死之年所手植也,今已亭亭如蓋矣
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?————歸有光
總結
以上是生活随笔為你收集整理的vhdl变量除法_VHDL语法总结以及编码风格(二)的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: python控制台动画_Python真神
- 下一篇: 小红书最新用户量数据_小红书估值高达60