簡(jiǎn)介
BCD碼用4位二進(jìn)制數(shù)表示一個(gè)十進(jìn)制數(shù),最常用的BCD碼是8421碼,用4’b0000-4’b1001表示十進(jìn)制數(shù)字0-9,接下來默認(rèn)BCD碼就是8421碼。
在FPGA中使用數(shù)碼管時(shí),段選信號(hào)不好記,所以我們用BCD碼表示一個(gè)數(shù)碼管的數(shù)值,將BCD碼轉(zhuǎn)化為段選信號(hào)驅(qū)動(dòng)數(shù)碼管,數(shù)碼管驅(qū)動(dòng)可以這篇文章:74hc595驅(qū)動(dòng)數(shù)碼管。例如,當(dāng)我們想要6個(gè)數(shù)碼管顯示123456時(shí),只需要給數(shù)碼管驅(qū)動(dòng)模塊傳入{4’h1, 4’h2, 4’h3, 4’h4, 4’h5, 4’h6}即可。
但這樣做依然不夠方便,例如,當(dāng)我們采集到某個(gè)10bit二進(jìn)制數(shù)時(shí),想要將其顯示在數(shù)碼管上,該怎么辦?此時(shí)就需要進(jìn)行二進(jìn)制轉(zhuǎn)BCD碼的操作,最簡(jiǎn)單粗暴的方法為使用除法,但fpga中使用除法消耗資源過多,因此通常用加三移位法。
加三移位法
4位二進(jìn)制數(shù)取值范圍為0-15,為16進(jìn)制,而BCD碼為0-9,為10進(jìn)制,如果4位二進(jìn)制數(shù)逢十進(jìn)一,就能得到BCD碼,所以需要對(duì)大于9的4位二進(jìn)制數(shù)進(jìn)行+6強(qiáng)制進(jìn)位
加三移位法即上述方法的改進(jìn),占用更少的資源。由于4位二進(jìn)制數(shù)大于9時(shí)需要+6調(diào)整,那么其大于4時(shí),其左移后會(huì)大于9,所以左移前進(jìn)行+3調(diào)整,等同于左移后+6。
對(duì)于大于4位的二進(jìn)制數(shù),通過左移,每4位大于4的都+3調(diào)整,可將任意位的二進(jìn)制數(shù)轉(zhuǎn)化為BCD碼。
注意:最后一次左移后不需要調(diào)整,因?yàn)椴辉贂?huì)左移,任意4位大于4也沒關(guān)系
參考網(wǎng)上的例子,以8bit二進(jìn)制數(shù)8’hff為例:
0 1111 1111; //原數(shù)
1 0000 0001; //左移一次
2 0000 0011; //左移二次
3 0000 0111; //左移三次,檢查低四位>4?
3.1. 0000 1010; //大于4,加3進(jìn)行調(diào)整
4 0001 0101; //左移四次,檢查低四位>4?
4.1. 0001 1000; //大于4,加3進(jìn)行調(diào)整
5 0011 0001; //左移五次
6 0110 0011; //左移六次,檢查高四位>4?
6.1. 1001 0011; //大于4,加3進(jìn)行調(diào)整
7 1 0010 0111; //左移七次,檢查低四位>4?
7.1. 1 0010 1010; //大于4,加3進(jìn)行調(diào)整
8 10 0101 0101; //左移八次(得到BCD碼255)
更多細(xì)節(jié)可以看這篇文章:走近FPGA之二進(jìn)制轉(zhuǎn)BCD碼
RTL代碼與仿真
給大于4就+3這個(gè)操作編寫一個(gè)模塊Adder:
module Adder(
input [3:0] i_data,
output [3:0] o_data
);
assign o_data = (i_data > 4'h4) ? (i_data + 4'h3) : i_data;
endmodule
以10bit二進(jìn)制數(shù)轉(zhuǎn)BCD碼為例,其RTL圖如下所示:
首先,0和A9,A8,A7構(gòu)成了左移3次后的低4位,Adder1對(duì)其進(jìn)行+3調(diào)整,輸出o1,o1低3位與A6構(gòu)成了左移4次的低4位,同理Adder2的輸出o2的低3位與A5構(gòu)成了左移5次的低四位,后續(xù)Adder3~Adder7同理。第一層到第七層分別為左移3次到左移9次的調(diào)整,其它Adder的作用可以參考上述8位二進(jìn)制數(shù)轉(zhuǎn)BCD碼的流程。
根據(jù)上圖,可以輕易寫出10位二進(jìn)制轉(zhuǎn)BCD碼的RTL代碼:
module bin2bcd_10bit(
input [9:0] i_data,
output [15:0] o_bcd
);
//------------signals--------------
wire [3:0] o1, o2, o3, o4, o5, o6, o7, o8, o9, o10, o11, o12;
//------------function-------------
Adder Adder1 (
.i_data ({1'b0, i_data[9:7]}),
.o_data (o1)
);
Adder Adder2 (
.i_data ({o1[2:0], i_data[6]}),
.o_data (o2)
);
Adder Adder3 (
.i_data ({o2[2:0], i_data[5]}),
.o_data (o3)
);
Adder Adder4 (
.i_data ({o3[2:0], i_data[4]}),
.o_data (o4)
);
Adder Adder5 (
.i_data ({o4[2:0], i_data[3]}),
.o_data (o5)
);
Adder Adder6 (
.i_data ({o5[2:0], i_data[2]}),
.o_data (o6)
);
Adder Adder7 (
.i_data ({o6[2:0], i_data[1]}),
.o_data (o7)
);
Adder Adder8 (
.i_data ({1'b0, o1[3], o2[3], o3[3]}),
.o_data (o8)
);
Adder Adder9 (
.i_data ({o8[2:0], o4[3]}),
.o_data (o9)
);
Adder Adder10 (
.i_data ({o9[2:0], o5[3]}),
.o_data (o10)
);
Adder Adder11 (
.i_data ({o10[2:0], o6[3]}),
.o_data (o11)
);
Adder Adder12 (
.i_data ({1'b0, o8[3], o9[3], o10[3]}),
.o_data (o12)
);
assign o_bcd = {3'b000, o12, o11, o7, i_data[0]};
endmodule
編寫仿真tb,輸入20個(gè)隨機(jī)10位二進(jìn)制數(shù),輸出bcd碼的hex格式:
`timescale 1ps/1ps
`define CLK_CYCLE 20
module bin2bcd_8bit_tb;
//----------clk generate-----------
reg clk = 1'b1;
always #(`CLK_CYCLE/2) clk = ~clk;
//-----------signals---------------
reg rst_n = 1'b0;
reg [9:0] i_data = 10'd0;
wire [15:0] o_data;
//----------instantiation----------
bin2bcd_10bit inst_bin2bcd_10bit (
.i_data (i_data),
.o_bcd (o_data)
);
//-----------simulation------------
initial begin
// reset first
@(negedge clk) rst_n = 1'b1;
@(posedge clk);
$monitor("input(decimal): %d, output(hex): %h, time: %t", i_data, o_data, $time);
repeat(20) begin
i_data = $random;
#(`CLK_CYCLE);
end
// stop/finish
#(`CLK_CYCLE * 10) $finish;
end
endmodule
仿真結(jié)果如下:
可以看出20次二進(jìn)制數(shù)轉(zhuǎn)BCD碼都成功了,之后可以用該模塊加上數(shù)碼管譯碼模塊直接進(jìn)行10bit二進(jìn)制數(shù)的數(shù)碼管顯示。文章來源:http://www.zghlxwxcb.cn/news/detail-742074.html
16bit二進(jìn)制轉(zhuǎn)bcd碼也同理,其RTL圖如下:
可以看出組合邏輯非常多,有13層加三移位Adder,為了降低組合邏輯延時(shí),可以進(jìn)行流水線加速,這里就不具體展開了。文章來源地址http://www.zghlxwxcb.cn/news/detail-742074.html
到了這里,關(guān)于verilog實(shí)現(xiàn)二進(jìn)制轉(zhuǎn)BCD碼-加3移位法的文章就介紹完了。如果您還想了解更多內(nèi)容,請(qǐng)?jiān)谟疑辖撬阉鱐OY模板網(wǎng)以前的文章或繼續(xù)瀏覽下面的相關(guān)文章,希望大家以后多多支持TOY模板網(wǎng)!