两个频率很接近,可以采 用下面程序产生我们要的波特率。
// 10 bits for the accumulator ([9:0]), and one extra bit for the accumulator carry-out ([10])
reg [10:0] acc;
// 11 bits total!
always @(posedge clk)
acc <= acc[9:0] + 59;
// use only 10 bits from the previous result, but save the full 11 bits
wire BaudTick = acc[10]; // so that the 11th bit is the carry-out
| 当系统时钟为2MHz的时候,计算得到的波特率的值为115234,与115200只有0.03%的误差。
我们怎么得到“59”呢,可以看下面的推导

其中Baud<<BaudGeneratorAccWidth,Baud左移BaudGeneratorAccWidth位,相当于Baud乘以2的BaudGeneratorAccWidth次方。
参照上面的程序与公式推导可以把程序修改如下:
parameter ClkFrequency = 25000000; // 25MHz
parameter Baud = 115200;
parameter BaudGeneratorAccWidth = 16;
parameter BaudGeneratorInc = (Baud<<BaudGeneratorAccWidth)/ClkFrequency;
reg [BaudGeneratorAccWidth:0] BaudGeneratorAcc;
always @(posedge clk)
BaudGeneratorAcc <= BaudGeneratorAcc[BaudGeneratorAccWidth-1:0] + BaudGeneratorInc;
wire BaudTick = BaudGeneratorAcc[BaudGeneratorAccWidth]; |
当要注意的是,上面程序中BaudGeneratorInc的计算公式出错,因为在Verilog语言中中间结果只能32位,而这个公式计算的结果超过了32位。所以要把这行改为
parameter BaudGeneratorInc = ((Baud<<(BaudGeneratorAccWidth-4))+(ClkFrequency>>5))/(ClkFrequency>>4); |

程序改变,得到的波 特率不变。
RS232发 送接收模块
可以参考下面文档,这里就不贴出来了。
http://attach.baisi.net/getattach.php?a=RS-232%B7%A2%CB%CD%C4%A3%BF%E9.rar&b=forumid_218%2F20080615_0eac2a17adb0faa0cae54LXO9jwRbJpE.rar&c=application%2Foctet-stream
RS232发送模块(Verilog)
RS232接收模块(Verilog)
以上程序均标注了J
调用串口发送接收模块
`timescale 1ns / 1ps
module serialfun(clk, RxD, TxD);
input clk;
//系统时钟
input RxD;
output TxD;
//////////////////////////////////////////////////
wire RxD_data_ready;
wire [7:0] RxD_data;
async_receiver deserializer(
//RS-232接收模块
.clk(clk),
.RxD(RxD),
.RxD_data_ready(RxD_data_ready),
//当接收到一个字节的数据时,"RxD_data_ready"有效一个周期
.RxD_data(RxD_data)
//接收一个字节数据
);
///////////////////////////////////////////////////
async_transmitter serializer(
//RS-232发送模块
.clk(clk),
.TxD(TxD),
.TxD_start(RxD_data_ready),
//"TxD_start"置位后开始传输
.TxD_data(RxD_data)
//发送一个字节数据
);
endmodule
这个程序的结果是在从计算机发送 八个字节到FPGA,FPGA再把这八个字节转发回计算机。
要注意是如果以十六进制发送的话,就要以十六进制显示,8个字节可以发送2个字符(0~F)。如果没选以十六进制发送的话,会以ASCII码发送,只能发送一个字符(一个字符的ASCII有8个字节)。 |