FPGA ad9226数据采集串口发送讨论

用ad7606芯片做ad采集的时候,我用参考代码去采集,感觉太慢了,想提高速率,代码分七个模块,一个数据采集模块ad,一个ad测试模块ad7606,一个数据转换模块volt_cal,一个16进制转10进制模块bcd,一个时钟分频模块clkdiv,一个顶层模块ad7606test,一个串口发送模块uart,一个串口发送中引用的例化模块uarttx 最后尝试改变分频时钟并提高比特率(原来是9600),数据的采集速度有所提升。
ad7606:“timescale 1ns / 1ps
//////////////////////////////////////////////////////////////////////////////////
// Module Name: ad7606
//////////////////////////////////////////////////////////////////////////////////
module ad7606(
input clk, //50mhz
input rst_n,

input [15:0]        ad_data,            //ad7606 采样数据
input               ad_busy,            //ad7606 忙标志位 

input first_data, //ad7606 第一个数据标志位
output [2:0] ad_os, //ad7606 过采样倍率选择
output reg ad_cs, //ad7606 AD cs
output reg ad_rd, //ad7606 AD data read
output reg ad_reset, //ad7606 AD reset
output reg ad_convstab, //ad7606 AD convert start

output reg [15:0] ad_ch1,              //AD第1通道的数据
output reg [15:0] ad_ch2,              //AD第2通道的数据
output reg [15:0] ad_ch3,              //AD第3通道的数据
output reg [15:0] ad_ch4,              //AD第4通道的数据
output reg [15:0] ad_ch5,              //AD第5通道的数据
output reg [15:0] ad_ch6,              //AD第6通道的数据
output reg [15:0] ad_ch7,              //AD第7通道的数据
output reg [15:0] ad_ch8               //AD第8通道的数据  



);

reg [15:0] cnt;
reg [5:0] i;
reg [3:0] state;

parameter IDLE=4’d0;
parameter AD_CONV=4’d1;
parameter Wait_1=4’d2;
parameter Wait_busy=4’d3;
parameter READ_CH1=4’d4;
parameter READ_CH2=4’d5;
parameter READ_CH3=4’d6;
parameter READ_CH4=4’d7;
parameter READ_CH5=4’d8;
parameter READ_CH6=4’d9;
parameter READ_CH7=4’d10;
parameter READ_CH8=4’d11;
parameter READ_DONE=4’d12;

assign ad_os=3’b000;

//AD 复位电路
always@(posedge clk)
begin
if(cnt<16’hffff) begin
cnt<=cnt+1;
ad_reset<=1’b1;
end
else
ad_reset<=1’b0;
end

always @(posedge clk)
begin
if (ad_reset==1’b1) begin
state<=IDLE;
ad_ch1<=0;
ad_ch2<=0;
ad_ch3<=0;
ad_ch4<=0;
ad_ch5<=0;
ad_ch6<=0;
ad_ch7<=0;
ad_ch8<=0;
ad_cs<=1’b1;
ad_rd<=1’b1;
ad_convstab<=1’b1;
i<=0;
end
else begin
case(state)
IDLE: begin
ad_cs<=1’b1;
ad_rd<=1’b1;
ad_convstab<=1’b1;
if(i==20) begin
i<=0;
state<=AD_CONV;
end
else
i<=i+1’b1;
end
AD_CONV: begin
if(i==2) begin //等待2个clock
i<=0;
state<=Wait_1;
ad_convstab<=1’b1;
end
else begin
i<=i+1’b1;
ad_convstab<=1’b0; //启动AD转换
end
end
Wait_1: begin
if(i==5) begin //等待5个clock, 等待busy信号为高
i<=0;
state<=Wait_busy;
end
else
i<=i+1’b1;
end
Wait_busy: begin
if(ad_busy==1’b0) begin //等待busy信号为低
i<=0;
state<=READ_CH1;
end
end
READ_CH1: begin
ad_cs<=1’b0; //cs信号有效
if(i==3) begin
ad_rd<=1’b1;
i<=0;
ad_ch1<=ad_data; //读CH1
state<=READ_CH2;
end
else begin
ad_rd<=1’b0;
i<=i+1’b1;
end
end
READ_CH2: begin
if(i==3) begin
ad_rd<=1’b1;
i<=0;
ad_ch2<=ad_data; //读CH2
state<=READ_CH3;
end
else begin
ad_rd<=1’b0;
i<=i+1’b1;
end
end
READ_CH3: begin
if(i==3) begin
ad_rd<=1’b1;
i<=0;
ad_ch3<=ad_data; //读CH3
state<=READ_CH4;
end
else begin
ad_rd<=1’b0;
i<=i+1’b1;
end
end
READ_CH4: begin
if(i==3) begin
ad_rd<=1’b1;
i<=0;
ad_ch4<=ad_data; //读CH4
state<=READ_CH5;
end
else begin
ad_rd<=1’b0;
i<=i+1’b1;
end
end
READ_CH5: begin
if(i==3) begin
ad_rd<=1’b1;
i<=0;
ad_ch5<=ad_data; //读CH5
state<=READ_CH6;
end
else begin
ad_rd<=1’b0;
i<=i+1’b1;
end
end
READ_CH6: begin
if(i==3) begin
ad_rd<=1’b1;
i<=0;
ad_ch6<=ad_data; //读CH6
state<=READ_CH7;
end
else begin
ad_rd<=1’b0;
i<=i+1’b1;
end
end
READ_CH7: begin
if(i==3) begin
ad_rd<=1’b1;
i<=0;
ad_ch7<=ad_data; //读CH7
state<=READ_CH8;
end
else begin
ad_rd<=1’b0;
i<=i+1’b1;
end
end
READ_CH8: begin
if(i==3) begin
ad_rd<=1’b1;
i<=0;
ad_ch8<=ad_data; //读CH8
state<=READ_DONE;
end
else begin
ad_rd<=1’b0;
i<=i+1’b1;
end
end
READ_DONE:begin
ad_rd<=1’b1;
ad_cs<=1’b1;
state<=IDLE;
end
default: state<=IDLE;
endcase
end

end

endmodule

volt_cal:“timescale 1ns / 1ps
//////////////////////////////////////////////////////////////////////////////////
// Module Name: volt_cal
//////////////////////////////////////////////////////////////////////////////////
module volt_cal(
input clk, //50mhz
input ad_reset,

input [15:0] ad_ch1,              //AD第1通道的数据
input [15:0] ad_ch2,              //AD第2通道的数据
input [15:0] ad_ch3,              //AD第3通道的数据
input [15:0] ad_ch4,              //AD第4通道的数据
input [15:0] ad_ch5,              //AD第5通道的数据
input [15:0] ad_ch6,              //AD第6通道的数据
input [15:0] ad_ch7,              //AD第7通道的数据
input [15:0] ad_ch8,              //AD第8通道的数据   


output [19:0] ch1_dec,             //AD第1通道的十进制电压数据
output [19:0] ch2_dec,             //AD第1通道的十进制电压数据 
output [19:0] ch3_dec,             //AD第1通道的十进制电压数据
output [19:0] ch4_dec,             //AD第1通道的十进制电压数据 
output [19:0] ch5_dec,             //AD第1通道的十进制电压数据
output [19:0] ch6_dec,             //AD第1通道的十进制电压数据 
output [19:0] ch7_dec,             //AD第1通道的十进制电压数据
output [19:0] ch8_dec,             //AD第1通道的十进制电压数据 

output reg [7:0] ch1_sig,          //AD第1通道的数据正负字符
output reg [7:0] ch2_sig,          //AD第2通道的数据正负字符  
output reg [7:0] ch3_sig,          //AD第1通道的数据正负字符
output reg [7:0] ch4_sig,          //AD第2通道的数据正负字符  
output reg [7:0] ch5_sig,          //AD第1通道的数据正负字符
output reg [7:0] ch6_sig,          //AD第2通道的数据正负字符  
output reg [7:0] ch7_sig,          //AD第1通道的数据正负字符
output reg [7:0] ch8_sig           //AD第2通道的数据正负字符  


);

reg [15:0] ch1_reg;
reg [15:0] ch2_reg;
reg [15:0] ch3_reg;
reg [15:0] ch4_reg;
reg [15:0] ch5_reg;
reg [15:0] ch6_reg;
reg [15:0] ch7_reg;
reg [15:0] ch8_reg;

reg [31:0] ch1_data_reg;
reg [31:0] ch2_data_reg;
reg [31:0] ch3_data_reg;
reg [31:0] ch4_data_reg;
reg [31:0] ch5_data_reg;
reg [31:0] ch6_data_reg;
reg [31:0] ch7_data_reg;
reg [31:0] ch8_data_reg;

reg [31:0] ch1_vol;
reg [31:0] ch2_vol;
reg [31:0] ch3_vol;
reg [31:0] ch4_vol;
reg [31:0] ch5_vol;
reg [31:0] ch6_vol;
reg [31:0] ch7_vol;
reg [31:0] ch8_vol;

//AD 电压换算
always @(posedge clk)
begin
if(ad_reset == 1’b1) begin
ch1_reg<=0;
ch2_reg<=0;
ch3_reg<=0;
ch4_reg<=0;
ch5_reg<=0;
ch6_reg<=0;
ch7_reg<=0;
ch8_reg<=0;
end
else begin
//////////CH1数据/////////////
if(ad_ch1[15]==1’b1) begin //如果是负电压
ch1_reg<=16’hffff-ad_ch1+1’b1;
ch1_sig <= 45; //’-’ asic码
end
else begin
ch1_reg<=ad_ch1;
ch1_sig<=43; //’+’ asic码
end

//////////CH2数据/////////////
if(ad_ch2[15]==1'b1) begin                      //如果是负电压
    ch2_reg<=16'hffff-ad_ch2+1'b1;
     ch2_sig <= 45;                                //'-' asic码
 end     
 else begin
   ch2_reg<=ad_ch2;
     ch2_sig<=43;                                  //'+' asic码       
 end    

//////////CH3数据/////////////        
if(ad_ch3[15]==1'b1) begin                      //如果是负电压
    ch3_reg<=16'hffff-ad_ch3+1'b1;
     ch3_sig <= 45;                                //'-' asic码
 end     
 else begin
   ch3_reg<=ad_ch3;
     ch3_sig<=43;                                  //'+' asic码       
 end    

//////////CH4数据/////////////
if(ad_ch4[15]==1'b1) begin                      //如果是负电压
    ch4_reg<=16'hffff-ad_ch4+1'b1;
     ch4_sig <= 45;                                //'-' asic码
 end     
 else begin
   ch4_reg<=ad_ch4;
     ch4_sig<=43;                                  //'+' asic码       
 end    

//////////CH5数据/////////////
if(ad_ch5[15]==1'b1) begin                      //如果是负电压
    ch5_reg<=16'h7ffff-ad_ch5+1'b1;
     ch5_sig <= 45;                                //'-' asic码
 end     
 else begin
   ch5_reg<=ad_ch5;
     ch5_sig<=43;                                  //'+' asic码       
 end    

//////////CH6数据/////////////         
if(ad_ch6[15]==1'b1) begin                      //如果是负电压
    ch6_reg<=16'hffff-ad_ch6+1'b1;
     ch6_sig <= 45;                                //'-' asic码
 end     
 else begin
   ch6_reg<=ad_ch6;
     ch6_sig<=43;                                  //'+' asic码       
 end    

//////////CH7数据/////////////         
if(ad_ch7[15]==1'b1) begin                      //如果是负电压
    ch7_reg<=16'h7ffff-ad_ch7+1'b1;
     ch7_sig <= 45;                                //'-' asic码
 end     
 else begin
   ch7_reg<=ad_ch7;
     ch7_sig<=43;                                  //'+' asic码       
 end    

//////////CH8数据/////////////         
if(ad_ch8[15]==1'b1) begin                      //如果是负电压
    ch8_reg<=16'hffff-ad_ch8+1'b1;
     ch8_sig <= 45;                                //'-' asic码
 end     
 else begin
   ch8_reg<=ad_ch8;
     ch8_sig<=43;                                  //'+' asic码       
 end         

end  

end

//AD 电压换算(1 LSB = 5V / 32758 = 0.15mV
always @(posedge clk)
begin
if(ad_reset == 1’b1) begin
ch1_data_reg<=0;
ch2_data_reg<=0;
ch3_data_reg<=0;
ch4_data_reg<=0;
ch5_data_reg<=0;
ch6_data_reg<=0;
ch7_data_reg<=0;
ch8_data_reg<=0;
ch1_vol<=0;
ch2_vol<=0;
ch3_vol<=0;
ch4_vol<=0;
ch5_vol<=0;
ch6_vol<=0;
ch7_vol<=0;
ch8_vol<=0;
end
else begin
ch1_data_reg<=ch1_reg * 50000;
ch2_data_reg<=ch2_reg * 50000;
ch3_data_reg<=ch3_reg * 50000;
ch4_data_reg<=ch4_reg * 50000;
ch5_data_reg<=ch5_reg * 50000;
ch6_data_reg<=ch6_reg * 50000;
ch7_data_reg<=ch7_reg * 50000;
ch8_data_reg<=ch8_reg * 50000;

     ch1_vol<=ch1_data_reg >>15;
     ch2_vol<=ch2_data_reg >>15;
     ch3_vol<=ch3_data_reg >>15;
     ch4_vol<=ch4_data_reg >>15;
     ch5_vol<=ch5_data_reg >>15;
     ch6_vol<=ch6_data_reg >>15;
     ch7_vol<=ch7_data_reg >>15;
     ch8_vol<=ch8_data_reg >>15;
 end    

end

//16进制转化为十进制的
bcd bcd1_ist(
.hex (ch1_vol[15:0]),
.dec (ch1_dec),
.clk (clk)
);

//16进制转化为十进制的
bcd bcd2_ist(
.hex (ch2_vol[15:0]),
.dec (ch2_dec),
.clk (clk)
);

//16进制转化为十进制的
bcd bcd3_ist(
.hex (ch3_vol[15:0]),
.dec (ch3_dec),
.clk (clk)
);

//16进制转化为十进制的
bcd bcd4_ist(
.hex (ch4_vol[15:0]),
.dec (ch4_dec),
.clk (clk)
);

//16进制转化为十进制的
bcd bcd5_ist(
.hex (ch5_vol[15:0]),
.dec (ch5_dec),
.clk (clk)
);

//16进制转化为十进制的
bcd bcd6_ist(
.hex (ch6_vol[15:0]),
.dec (ch6_dec),
.clk (clk)
);

//16进制转化为十进制的
bcd bcd7_ist(
.hex (ch7_vol[15:0]),
.dec (ch7_dec),
.clk (clk)
);

//16进制转化为十进制的
bcd bcd8_ist(
.hex (ch8_vol[15:0]),
.dec (ch8_dec),
.clk (clk)
);

endmodule

bcd:`module bcd(clk,
hex,
dec);

input clk;
input [16:0] hex;
output [19:0] dec;

wire [15:0] rrhex;
reg [3:0] rhex[3:0];

reg [18:0] rhexd;
reg [13:0] rhexc;
reg [9:0] rhexb;
reg [3:0] rhexa;

reg [5:0] resa,resb,resc,resd;
reg [3:0] rese;

assign rrhex = hex[16] ? ~hex[15:0]+1’b1 : hex[15:0]; //去符号
assign dec = {rese,resd[3:0],resc[3:0],resb[3:0],resa[3:0]};

always@(posedge clk) //第一级寄存器
begin
rhex[3] <= rrhex[15:12];
rhex[2] <= rrhex[11:8];
rhex[1] <= rrhex[7:4];
rhex[0] <= rrhex[3:0];
end

always@(posedge clk) //高4bit译码
begin
case(rhex[3])
4’h0: rhexd <= 19’h00000;
4’h1: rhexd <= 19’h04096; //0x1000 -> 4096 (十进制)
4’h2: rhexd <= 19’h08192; //0x2000 -> 8192 (十进制)
4’h3: rhexd <= 19’h12288; //0x3000 -> 12288 (十进制)
4’h4: rhexd <= 19’h16384; //0x4000 -> 16384 (十进制)
4’h5: rhexd <= 19’h20480; //0x5000 -> 20480 (十进制)
4’h6: rhexd <= 19’h24576; //0x6000 -> 24576 (十进制)
4’h7: rhexd <= 19’h28672; //0x7000 -> 28672 (十进制)
4’h8: rhexd <= 19’h32768; //0x8000 -> 32768 (十进制)
4’h9: rhexd <= 19’h36864; //0x9000 -> 36864 (十进制)
4’ha: rhexd <= 19’h40960; //0xa000 -> 40960 (十进制)
4’hb: rhexd <= 19’h45056; //0xb000 -> 45056 (十进制)
4’hc: rhexd <= 19’h49152; //0xc000 -> 49152 (十进制)
4’hd: rhexd <= 19’h53248; //0xd000 -> 53248 (十进制)
4’he: rhexd <= 19’h57344; //0xe000 -> 57344 (十进制)
4’hf: rhexd <= 19’h61440; //0xf000 -> 61440 (十进制)
default: rhexd <= 19’h00000;
endcase
end

always@(posedge clk) //次高4bit译码
begin
case(rhex[2])
4’h0: rhexc <= 14’h0000;
4’h1: rhexc <= 14’h0256; //0x100 -> 256 (十进制)
4’h2: rhexc <= 14’h0512; //0x200 -> 512 (十进制)
4’h3: rhexc <= 14’h0768; //0x300 -> 768 (十进制)
4’h4: rhexc <= 14’h1024; //0x400 -> 1024 (十进制)
4’h5: rhexc <= 14’h1280; //0x500 -> 1280 (十进制)
4’h6: rhexc <= 14’h1536; //0x600 -> 1536 (十进制)
4’h7: rhexc <= 14’h1792; //0x700 -> 1792 (十进制)
4’h8: rhexc <= 14’h2048; //0x800 -> 2048 (十进制)
4’h9: rhexc <= 14’h2304; //0x900 -> 2304 (十进制)
4’ha: rhexc <= 14’h2560; //0xA00 -> 2560 (十进制)
4’hb: rhexc <= 14’h2816; //0xB00 -> 2816 (十进制)
4’hc: rhexc <= 14’h3072; //0xC00 -> 3072 (十进制)
4’hd: rhexc <= 14’h3328; //0xD00 -> 3328 (十进制)
4’he: rhexc <= 14’h3584; //0xE00 -> 3584 (十进制)
4’hf: rhexc <= 14’h3840; //0xF00 -> 3840 (十进制)
default: rhexc <= 14’h0000;
endcase
end

always@(posedge clk)
begin
case(rhex[1])
4’h0: rhexb <= 10’h000;
4’h1: rhexb <= 10’h016;
4’h2: rhexb <= 10’h032;
4’h3: rhexb <= 10’h048;
4’h4: rhexb <= 10’h064;
4’h5: rhexb <= 10’h080;
4’h6: rhexb <= 10’h096;
4’h7: rhexb <= 10’h112;
4’h8: rhexb <= 10’h128;
4’h9: rhexb <= 10’h144;
4’ha: rhexb <= 10’h160;
4’hb: rhexb <= 10’h176;
4’hc: rhexb <= 10’h192;
4’hd: rhexb <= 10’h208;
4’he: rhexb <= 10’h224;
4’hf: rhexb <= 10’h240;
default: rhexb <= 10’h000;
endcase
end

always@(posedge clk)
begin
rhexa <= rhex[0];
end

always@(posedge clk) //每个结果按同级单个bcd码相加,高一级的bcd码要加上低一级的进位,也就是高出4位的部分
begin
resa = addbcd4(rhexa[3:0],rhexb[3:0],rhexc[3:0], rhexd[3:0]);
resb = addbcd4(resa[5:4], rhexb[7:4],rhexc[7:4], rhexd[7:4]);
resc = addbcd4(resb[5:4], rhexb[9:8],rhexc[11:8], rhexd[11:8]);
resd = addbcd4(resc[5:4], 4’h0, rhexc[13:12],rhexd[15:12]);
rese = resd[5:4] + rhexd[18:16];
end

function [5:0] addbcd4;
input [3:0] add1,add2,add3,add4;
begin
addbcd4 = add1 + add2 + add3 + add4;
if(addbcd4 > 6’h1d) //>29 最低有一个可能出现0xf,但由二进制转换而来的数在这里不会出现大于40的情况
addbcd4 = addbcd4 + 5’h12;
else if(addbcd4 > 5’h13) //>19对结果加12
addbcd4 = addbcd4 + 4’hc;
else if(addbcd4 > 4’h9) //>9对结果加6
addbcd4 = addbcd4 + 4’h6;
end
endfunction

endmodule

uart:“timescale 1ns / 1ps
//////////////////////////////////////////////////////////////////////////////////
//////////////////////////////////////////////////////////////////////////////////
module uart(
input clk50, //50Mhz clock
input reset_n,

          input [19:0] ch1_dec,
          input [19:0] ch2_dec,
          input [19:0] ch3_dec,
          input [19:0] ch4_dec,
          input [19:0] ch5_dec,
          input [19:0] ch6_dec,
          input [19:0] ch7_dec,
          input [19:0] ch8_dec,           

       input [7:0] ch1_sig,
       input [7:0] ch2_sig,
       input [7:0] ch3_sig,
       input [7:0] ch4_sig,
       input [7:0] ch5_sig,
       input [7:0] ch6_sig,
       input [7:0] ch7_sig,
       input [7:0] ch8_sig,


       output tx              
);

/**********************************/
//存储待发送的串口信息
/**********************************/
reg [7:0] uart_ad [113:0]; //存储发送的ASIC字符

always @(clk)
begin //定义发送的字符
if(uart_stat==3’b000) begin
uart_ad[0]<=65; //存储字符 A
uart_ad[1]<=68; //存储字符 D
uart_ad[2]<=49; //存储字符 1
uart_ad[3]<=58; //存储字符 :
uart_ad[4]<=ch1_sig; //存储字符 正负
uart_ad[5]<=ch1_dec[19:16] + 48; //存储字符 个位
uart_ad[6]<=46; //存储字符 .
uart_ad[7]<=ch1_dec[15:12] + 48; //存储字符 小数点后一位
uart_ad[8]<=ch1_dec[11:8] + 48; //存储字符 小数点后二位
uart_ad[9]<=ch1_dec[7:4] + 48; //存储字符 小数点后三位
uart_ad[10]<=ch1_dec[3:0] + 48; //存储字符 小数点后四位
uart_ad[11]<=86; //存储字符 V
uart_ad[12]<=32; //存储字符 空格
uart_ad[13]<=32; //存储字符 空格

     uart_ad[14]<=65;                           //存储字符 A 
     uart_ad[15]<=68;                           //存储字符 D
     uart_ad[16]<=50;                           //存储字符 2
     uart_ad[17]<=58;                           //存储字符 : 
     uart_ad[18]<=ch2_sig;                      //存储字符 正负        
     uart_ad[19]<=ch2_dec[19:16] + 48;          //存储字符 个位                          
     uart_ad[20]<=46;                           //存储字符 . 
     uart_ad[21]<=ch2_dec[15:12] + 48;          //存储字符 小数点后一位
     uart_ad[22]<=ch2_dec[11:8] + 48;           //存储字符 小数点后二位
     uart_ad[23]<=ch2_dec[7:4] + 48;            //存储字符 小数点后三位
     uart_ad[24]<=ch2_dec[3:0] + 48;            //存储字符 小数点后四位
     uart_ad[25]<=86;                           //存储字符 V
     uart_ad[26]<=32;                           //存储字符 空格
     uart_ad[27]<=32;                           //存储字符 空格

     uart_ad[28]<=65;                           //存储字符 A 
     uart_ad[29]<=68;                           //存储字符 D
     uart_ad[30]<=51;                           //存储字符 3
     uart_ad[31]<=58;                           //存储字符 : 
     uart_ad[32]<=ch3_sig;                      //存储字符 正负        
     uart_ad[33]<=ch3_dec[19:16] + 48;          //存储字符 个位                          
     uart_ad[34]<=46;                           //存储字符 . 
     uart_ad[35]<=ch3_dec[15:12] + 48;          //存储字符 小数点后一位
     uart_ad[36]<=ch3_dec[11:8] + 48;           //存储字符 小数点后二位
     uart_ad[37]<=ch3_dec[7:4] + 48;            //存储字符 小数点后三位
     uart_ad[38]<=ch3_dec[3:0] + 48;            //存储字符 小数点后四位
     uart_ad[39]<=86;                           //存储字符 V
     uart_ad[40]<=32;                           //存储字符 空格
     uart_ad[41]<=32;                           //存储字符 空格    

     uart_ad[42]<=65;                           //存储字符 A 
     uart_ad[43]<=68;                           //存储字符 D
     uart_ad[44]<=52;                           //存储字符 4
     uart_ad[45]<=58;                           //存储字符 : 
     uart_ad[46]<=ch4_sig;                      //存储字符 正负        
     uart_ad[47]<=ch4_dec[19:16] + 48;          //存储字符 个位                          
     uart_ad[48]<=46;                           //存储字符 . 
     uart_ad[49]<=ch4_dec[15:12] + 48;          //存储字符 小数点后一位
     uart_ad[50]<=ch4_dec[11:8] + 48;           //存储字符 小数点后二位
     uart_ad[51]<=ch4_dec[7:4] + 48;            //存储字符 小数点后三位
     uart_ad[52]<=ch4_dec[3:0] + 48;            //存储字符 小数点后四位
     uart_ad[53]<=86;                           //存储字符 V
     uart_ad[54]<=32;                           //存储字符 空格
     uart_ad[55]<=32;                           //存储字符 空格

     uart_ad[56]<=65;                           //存储字符 A 
     uart_ad[57]<=68;                           //存储字符 D
     uart_ad[58]<=53;                           //存储字符 5
     uart_ad[59]<=58;                           //存储字符 : 
     uart_ad[60]<=ch5_sig;                      //存储字符 正负        
     uart_ad[61]<=ch5_dec[19:16] + 48;          //存储字符 个位                          
     uart_ad[62]<=46;                           //存储字符 . 
     uart_ad[63]<=ch5_dec[15:12] + 48;          //存储字符 小数点后一位
     uart_ad[64]<=ch5_dec[11:8] + 48;           //存储字符 小数点后二位
     uart_ad[65]<=ch5_dec[7:4] + 48;            //存储字符 小数点后三位
     uart_ad[66]<=ch5_dec[3:0] + 48;            //存储字符 小数点后四位
     uart_ad[67]<=86;                           //存储字符 V
     uart_ad[68]<=32;                           //存储字符 空格
     uart_ad[69]<=32;                           //存储字符 空格

     uart_ad[70]<=65;                           //存储字符 A 
     uart_ad[71]<=68;                           //存储字符 D
     uart_ad[72]<=54;                           //存储字符 6
     uart_ad[73]<=58;                           //存储字符 : 
     uart_ad[74]<=ch6_sig;                      //存储字符 正负        
     uart_ad[75]<=ch6_dec[19:16] + 48;          //存储字符 个位                          
     uart_ad[76]<=46;                           //存储字符 . 
     uart_ad[77]<=ch6_dec[15:12] + 48;          //存储字符 小数点后一位
     uart_ad[78]<=ch6_dec[11:8] + 48;           //存储字符 小数点后二位
     uart_ad[79]<=ch6_dec[7:4] + 48;            //存储字符 小数点后三位
     uart_ad[80]<=ch6_dec[3:0] + 48;            //存储字符 小数点后四位
     uart_ad[81]<=86;                           //存储字符 V
     uart_ad[82]<=32;                           //存储字符 空格
     uart_ad[83]<=32;                           //存储字符 空格

     uart_ad[84]<=65;                           //存储字符 A 
     uart_ad[85]<=68;                           //存储字符 D
     uart_ad[86]<=55;                           //存储字符 7
     uart_ad[87]<=58;                           //存储字符 : 
     uart_ad[88]<=ch7_sig;                      //存储字符 正负        
     uart_ad[89]<=ch7_dec[19:16] + 48;          //存储字符 个位                          
     uart_ad[90]<=46;                           //存储字符 . 
     uart_ad[91]<=ch7_dec[15:12] + 48;          //存储字符 小数点后一位
     uart_ad[92]<=ch7_dec[11:8] + 48;           //存储字符 小数点后二位
     uart_ad[93]<=ch7_dec[7:4] + 48;            //存储字符 小数点后三位
     uart_ad[94]<=ch7_dec[3:0] + 48;            //存储字符 小数点后四位
     uart_ad[95]<=86;                           //存储字符 V
     uart_ad[96]<=32;                           //存储字符 空格
     uart_ad[97]<=32;                           //存储字符 空格   

     uart_ad[98]<=65;                           //存储字符 A 
     uart_ad[99]<=68;                           //存储字符 D
     uart_ad[100]<=56;                          //存储字符 8
     uart_ad[101]<=58;                          //存储字符 : 
     uart_ad[102]<=ch8_sig;                     //存储字符 正负        
     uart_ad[103]<=ch8_dec[19:16] + 48;         //存储字符 个位                          
     uart_ad[104]<=46;                          //存储字符 . 
     uart_ad[105]<=ch8_dec[15:12] + 48;         //存储字符 小数点后一位
     uart_ad[106]<=ch8_dec[11:8] + 48;          //存储字符 小数点后二位
     uart_ad[107]<=ch8_dec[7:4] + 48;           //存储字符 小数点后三位
     uart_ad[108]<=ch8_dec[3:0] + 48;           //存储字符 小数点后四位
     uart_ad[109]<=86;                          //存储字符 V
     uart_ad[110]<=32;                          //存储字符 空格
     uart_ad[111]<=32;                          //存储字符 空格       

     uart_ad[112]<=10;                          //换行符
     uart_ad[113]<=13;                          //回车符 
end  

end

/**********************************/
//串口发送时间字符串uart_ad[0]~uart_ad[113]
/**********************************/
reg [15:0] uart_cnt;
reg [2:0] uart_stat;

reg [7:0] txdata; //串口发送字符
reg wrsig; //串口发送有效信号

reg [8:0] k;

reg [15:0] Time_wait;

always @(posedge clk )
begin
if(!reset_n) begin
uart_cnt<=0;
uart_stat<=3’b000;
k<=0;
end
else begin
case(uart_stat)
3’b000: begin
if (Time_wait == 16’hffff) begin //两条发送字符串之间的间隔时间
uart_stat<=3’b001;
Time_wait<=0;
end
else begin
uart_stat<=3’b000;
Time_wait<=Time_wait + 1’b1;
end
end
3’b001: begin
if (k == 113 ) begin //发送第114个字符
if(uart_cnt ==0) begin
txdata <= uart_ad[113];
uart_cnt <= uart_cnt + 1’b1;
wrsig <= 1’b1;
end
else if(uart_cnt ==254) begin//一个字节发送为168个时钟,这里等待255个时钟,保证一个数据发送完成
uart_cnt <= 0;
wrsig <= 1’b0;
uart_stat <= 3’b010;
k <= 0;
end
else begin
uart_cnt <= uart_cnt + 1’b1;
wrsig <= 1’b0;
end
end
else begin //发送前113个字符
if(uart_cnt ==0) begin
txdata <= uart_ad[k];
uart_cnt <= uart_cnt + 1’b1;
wrsig <= 1’b1;
end
else if(uart_cnt ==254) begin//一个字节发送为168个时钟,这里等待255个时钟,保证一个数据发送完成
uart_cnt <= 0;
wrsig <= 1’b0;
k <= k + 1’b1;
end
else begin
uart_cnt <= uart_cnt + 1’b1;
wrsig <= 1’b0;
end
end
end
3’b010: begin //发送finish
uart_stat <= 3’b000;
end
default:uart_stat <= 3’b000;
endcase
end
end

/**产生串口时钟***/
clkdiv u0 (
.clk50 (clk50),
.clkout (clk) //串口发送时钟,波特率9600的16倍
);

/***串口发送程序**/
uarttx u1 (
.clk (clk),
.datain (txdata),
.wrsig (wrsig),
.idle (idle),
.tx (tx)
);

endmodule

uarttx:“timescale 1ns / 1ps
//////////////////////////////////////////////////////////////////////////////////
// Module Name: uarttx //
//////////////////////////////////////////////////////////////////////////////////
module uarttx(clk, datain, wrsig, idle, tx);
input clk; //UART时钟
input [7:0] datain; //需要发送的数据
input wrsig; //发送命令,上升沿有效
output idle; //线路状态指示,高为线路忙,低为线路空闲
output tx; //发送数据信号
reg idle, tx;
reg send;
reg wrsigbuf, wrsigrise;
reg presult;
reg[7:0] cnt; //计数器
parameter paritymode = 1’b0;

//检测发送命令是否有效
always @(posedge clk)
begin
wrsigbuf <= wrsig;
wrsigrise <= (~wrsigbuf) & wrsig;
end

always @(posedge clk)
begin
if (wrsigrise && (~idle)) //当发送命令有效且线路为空闲时,启动新的数据发送进程
begin
send <= 1’b1;
end
else if(cnt == 8’d168) //一帧资料发送结束
begin
send <= 1’b0;
end
end

always @(posedge clk)
begin
if(send == 1’b1) begin
case(cnt) //产生起始位
8’d0: begin
tx <= 1’b0;
idle <= 1’b1;
cnt <= cnt + 8’d1;
end
8’d16: begin
tx <= datain[0]; //发送数据0位
presult <= datain[0]^paritymode;
idle <= 1’b1;
cnt <= cnt + 8’d1;
end
8’d32: begin
tx <= datain[1]; //发送数据1位
presult <= datain[1]^presult;
idle <= 1’b1;
cnt <= cnt + 8’d1;
end
8’d48: begin
tx <= datain[2]; //发送数据2位
presult <= datain[2]^presult;
idle <= 1’b1;
cnt <= cnt + 8’d1;
end
8’d64: begin
tx <= datain[3]; //发送数据3位
presult <= datain[3]^presult;
idle <= 1’b1;
cnt <= cnt + 8’d1;
end
8’d80: begin
tx <= datain[4]; //发送数据4位
presult <= datain[4]^presult;
idle <= 1’b1;
cnt <= cnt + 8’d1;
end
8’d96: begin
tx <= datain[5]; //发送数据5位
presult <= datain[5]^presult;
idle <= 1’b1;
cnt <= cnt + 8’d1;
end
8’d112: begin
tx <= datain[6]; //发送数据6位
presult <= datain[6]^presult;
idle <= 1’b1;
cnt <= cnt + 8’d1;
end
8’d128: begin
tx <= datain[7]; //发送数据7位
presult <= datain[7]^presult;
idle <= 1’b1;
cnt <= cnt + 8’d1;
end
8’d144: begin
tx <= presult; //发送奇偶校验位
presult <= datain[0]^paritymode;
idle <= 1’b1;
cnt <= cnt + 8’d1;
end
8’d160: begin
tx <= 1’b1; //发送停止位
idle <= 1’b1;
cnt <= cnt + 8’d1;
end
8’d168: begin
tx <= 1’b1;
idle <= 1’b0; //一帧资料发送结束
cnt <= cnt + 8’d1;
end
default: begin
cnt <= cnt + 8’d1;
end
endcase
end
else begin
tx <= 1’b1;
cnt <= 8’d0;
idle <= 1’b0;
end
end
endmodule

clkdiv:“timescale 1ns / 1ps
//////////////////////////////////////////////////////////////////////////////////
// Module Name: clkdiv
//////////////////////////////////////////////////////////////////////////////////
module clkdiv(clk50, clkout);
input clk50; //系统时钟
output clkout; //采样时钟输出
reg clkout;
reg [15:0] cnt;

always @(posedge clk50) //分频进程
begin
if(cnt == 16’d162)
begin
clkout <= 1’b1;
cnt <= cnt + 16’d1;
end
else if(cnt == 16’d325)
begin
clkout <= 1’b0;
cnt <= 16’d0;
end
else
begin
cnt <= cnt + 16’d1;
end
end
endmodule

ad采集:“timescale 1ns / 1ps
//////////////////////////////////////////////////////////////////////////////////
//AD9226输出数据的高位为Bit0,数据需要颠倒
//////////////////////////////////////////////////////////////////////////////////
module ad(
input ad_clk,
input [11:0] ad1_in,
input [11:0] ad2_in,

         output reg [11:0] ad_ch1,
         output reg [11:0] ad_ch2

);

//AD CH1通道数据颠倒
always @(posedge ad_clk)
begin
ad_ch1[11] <= ad1_in[0];
ad_ch1[10] <= ad1_in[1];
ad_ch1[9] <= ad1_in[2];
ad_ch1[8] <= ad1_in[3];
ad_ch1[7] <= ad1_in[4];
ad_ch1[6] <= ad1_in[5];
ad_ch1[5] <= ad1_in[6];
ad_ch1[4] <= ad1_in[7];
ad_ch1[3] <= ad1_in[8];
ad_ch1[2] <= ad1_in[9];
ad_ch1[1] <= ad1_in[10];
ad_ch1[0] <= ad1_in[11];
end

//AD CH2通道数据颠倒
always @(posedge ad_clk)
begin
ad_ch2[11] <= ad2_in[0];
ad_ch2[10] <= ad2_in[1];
ad_ch2[9] <= ad2_in[2];
ad_ch2[8] <= ad2_in[3];
ad_ch2[7] <= ad2_in[4];
ad_ch2[6] <= ad2_in[5];
ad_ch2[5] <= ad2_in[6];
ad_ch2[4] <= ad2_in[7];
ad_ch2[3] <= ad2_in[8];
ad_ch2[2] <= ad2_in[9];
ad_ch2[1] <= ad2_in[10];
ad_ch2[0] <= ad2_in[11];
end

endmodule

最后有什么好的方法可以一起讨论。

你可能感兴趣的:(FPGA,教育)