1、计算过程
先将BCD码计数器清零,之后将二进制数和BCD码计数器统统左移,二进制数移出来的最高位放到BCD码计数器的最低位,如下表所示!
每一次移位之后都判断下,BCD码计数器的十、分以及个位是否大于4,如果任何一位(4bit)大于4,则对其加3,之后继续移位,如此下去,直到移位次数为二进制数的位数之后,停止移位,此时得到的BCD码计数值便是转换后的值。
2、实现
module bin2bcd(
input clk,
input rst_n,
input en,
input [7:0] data_bin,
output reg [11:0] data_bcd,
output reg data_bcd_valid
);
reg [2:0] state, next_state;
reg [3:0] num;
reg flag;
reg [11:0] bcd_buf;
reg [7:0] data_bin_reg;
parameter IDLE = 3'd1;
parameter SHIFT = 3'd2;
parameter JUDGE = 3'd3;
parameter ADD = 3'd4;
parameter DONE = 3'd5;
reg [1:0] wait_cnt;
always@(posedge clk or negedge rst_n)begin
if(~rst_n)begin
bcd_buf <= 12'd0;
data_bcd <= 12'd0;
state <= IDLE;
num <= 4'd0;
data_bcd_valid <= 0;
end
else begin
case(state)
IDLE:begin
num <= 4'd0;
data_bcd_valid <= 0;
data_bin_reg <= data_bin ;
bcd_buf <= 12'd0;
data_bcd <= 12'd0;
if(en)
state <= SHIFT;
else
state <= IDLE;
end
SHIFT:begin
bcd_buf <= bcd_buf << 1;
data_bin_reg <= data_bin_reg << 1;
bcd_buf[0] <= data_bin_reg[7];
num <= num + 4'd1;
if(num == 4'd7)begin
state <= DONE;
end
else
state <= JUDGE;
end
JUDGE:begin
if(bcd_buf[11:8]>4 || bcd_buf[7:4]>4 || bcd_buf[3:0]>4)
state <= ADD;
else
state <= SHIFT;
end
ADD:begin
if(bcd_buf[11:8]>4)
bcd_buf[11:8] <= bcd_buf[11:8] + 4'd3;
if(bcd_buf[7:4]>4)
bcd_buf[7:4] <= bcd_buf[7:4] + 4'd3;
if(bcd_buf[3:0]>4)
bcd_buf[3:0] <= bcd_buf[3:0] + 4'd3;
state <= SHIFT;
end
DONE:begin
state <= IDLE;
data_bcd <= bcd_buf;
data_bcd_valid <= 1'd1;
end
default:begin
bcd_buf <= bcd_buf;
data_bcd <= data_bcd;
data_bcd_valid <= 1'd0;
state <= IDLE;
num <= 3'd0;
end
endcase
end
end
endmodule
3、验证
module bcd_tb(
);
reg clk;
reg rst_n;
reg en;
reg [7:0] data_bin;
wire [11:0] data_bcd;
always #50 clk = ~clk;
initial begin
clk = 1;
rst_n = 0;
en = 0;
data_bin = 8'd0;
#200;
en = 1;
rst_n = 1;
data_bin = 8'b11110011;
#200000;
$stop;
end
bin2bcd u_bin2bcd(
.clk (clk ) ,
.rst_n (rst_n ) ,
.en (en ) ,
.data_bin (data_bin) ,
.data_bcd (data_bcd)
);
endmodule
以下是参考别人用于对比的数据,结果能对应上