博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
格雷码原理与Verilog实现
阅读量:5911 次
发布时间:2019-06-19

本文共 2189 字,大约阅读时间需要 7 分钟。

格雷码原理    

    格雷码是一个叫弗兰克*格雷的人在1953年发明的,最初用于通信。格雷码是一种循环二进制码或者叫作反射二进制码。格雷码的特点是从一个数变为相邻的一个数时,只有一个数据位发生跳变,由于这种特点,就可以避免二进制编码计数组合电路中出现的亚稳态。格雷码常用于通信,FIFO或者RAM地址寻址计数器中。

    如二进制计数编码从0到F的计数过程如下:

    

十进制

二进制

格雷码

十进制

二进制

格雷码

0

0000

0000

8

1000

1100

1

0001

0001

9

1001

1101

2

0010

0011

10

1010

1111

3

0011

0010

11

1011

1110

4

0100

0110

12

1100

1010

5

0101

0111

13

1101

1011

6

0110

0101

14

1110

1001

7

0111

0100

15

1111

1000

    当从7变为8时,4位二进制数都发生跳变,这就很可能会发生亚稳态。而采用格雷码,就可以编码4位二进制数都同时发生跳变,导致出现的亚稳态,就算出现亚稳态,最多也就一位出现错误。

格雷码转二进制

    观察上表可知,格雷码转二进制是从左边第二位起,将每位与左边一位二进制码的值异或,作为该位二进制码后的值(最左边一位依然不变)。

 

module gray_to_bin(

gray_in,

bin_out

);

parameter data_width = 4;

 

input [data_width-1:0] gray_in;

output [data_width-1:0] bin_out;

reg [data_width-1:0] bin_out;

always @(gray_in)

begin

bin_out[3] = gray_in[3];

bin_out[2] = gray_in[2]^bin_out[3];

bin_out[1] = gray_in[1]^bin_out[2];

bin_out[0] = gray_in[0]^bin_out[1];

end

endmodule

 

二进制转格雷码

    从最右边一位起,依次将每一位与左边一位异或(XOR),作为对应格雷码该位的值,最左边一位不变。

 

 

module bin_to_gray(

bin_in,

gray_out

);

parameter data_width = 4;

 

input [data_width-1:0] bin_in;

output [data_width-1:0] gray_out;

 

assign gray_out = (bin_in >> 1) ^ bin_in;

 

endmodule

 

格雷码计数器原理

    格雷码计数器,采用三个模块进行设计,格雷码转二进制、加法器、二进制转格雷码。

格雷码转二进制将格雷码转换为二进制,并将值输出用于加法器进行加法运算,然后将加法运算结果通过二进制转格雷码转换为格雷码,最后将格雷码进行输出,同时将结果输出到格雷码转二进制作为输入,形成一个计数功能。

 

顶层设计

module gray_counter(

clk,

reset_n,

// gray_in,

gray_out

);

parameter data_width = 4;

 

input clk;

input reset_n;

// input [data_width-1:0] gray_in;

output [data_width-1:0] gray_out;

 

//格雷码转二进制

wire [data_width-1:0] bin_out;

gray_to_bin gray_to_bin_1(

.gray_in (gray_wire),

.bin_out (bin_out)

);

//二进制加一

wire [data_width-1:0] bin_add_wire;

assign bin_add_wire = bin_out + 1'b1;

//二进制转格雷码

wire [data_width-1:0] gray_wire;

reg [data_width-1:0] gray_out;

bin_to_gray bin_to_gray_1(

.bin_in (bin_add_wire),

.gray_out (gray_wire)

);

 

always @(posedge clk or negedge reset_n)

begin

if(reset_n == 1'b0)

begin

gray_out <= {data_width{1'b0}};

end

else

begin

gray_out <= gray_wire;

end

end

endmodule

RTL视图,与设计框图一致

 

实验结果

 

    经过与上表对比,验证了功能的正确性。

 

大西瓜FPGA-->https://daxiguafpga.taobao.com

 

博客资料、代码、图片、文字等属大西瓜FPGA所有,切勿用于商业! 若引用资料、代码、图片、文字等等请注明出处,谢谢!

 

每日推送不同科技解读,原创深耕解读当下科技,敬请关注微信公众号“科乎”。

转载于:https://www.cnblogs.com/logic3/p/5609919.html

你可能感兴趣的文章
linux 下压缩大批量文件
查看>>
CSS设计模式
查看>>
常见问题解决
查看>>
java容器类1:Collection,List,ArrayList,LinkedList深入解读
查看>>
mysql 数据库修改名字
查看>>
Anagram
查看>>
BIT软件需求工程与UML建模课程第三周工作总结
查看>>
hdu 1330
查看>>
Android C2DM学习 - 云端推送
查看>>
微信开发https服务搭建
查看>>
Error No matching provisioning profiles found
查看>>
理解JavaScript中的回调函数
查看>>
2016-11-10试题解题报告
查看>>
排序算法的稳定性
查看>>
vim的基础操作
查看>>
AFSoundManager
查看>>
HLG 1360 Leyni的国家III【并查集】
查看>>
hdu4625 JZPTREE(斯特林数+dp)
查看>>
linux网络编程涉及的函数
查看>>
三列布局
查看>>