分享个人觉得有意思的知识:
-
什么样的时钟 会输入到 锁相环里
-
锁相环框图 VCO 控制电压控制频率 DS182 可以查看 VCO 范围
a. 先生成高频 的 VCO
b. 再通过 倍频和分频 产生具体各路时钟
c. -
怎么控制 输出频率?XAPP888
a. high time 是VCO 高电平 持续周期
b. low time 是 VCO 低电平持续周期
c. no count 是 VCO时钟周期的计数
d. edge 将high time 再扩展半个vco 周期 ,可以用来奇数分频 变成 50%占空比
e. high time 和 low time的 和 是 分频值 -
控制相位
b. 八个可变调节 以 45°为步长
c. 如果需要 20°就需要使用delay time
d. vco 频率越高,分频系数越高,相位越精细,如果是 10分频那么VCO输出一周期就是便宜360/10 = 36° -
小数分频
-
时序图:
- 代码:
此代码 配置 其中的一个时钟输出,首先读出对于寄存器,然后设置,再读出对比寄存器值,观察是否设置成功,可以使用 LED 观察现象。
代码分享
`timescale 1ns / 1ps
module drp(input i_clk ,input i_rst ,output [6 :0] o_daddr , output o_dclk , output o_den , output [15:0] o_din ,output o_dwe , input [15:0] i_dout , input i_drdy ,output o_mmcm_rst );localparam P_CLKOUT0_REG1_ADDR = 16'h08 ;
localparam [5 :0] P_HIGN_TIME = 6'd10 ;
localparam [5 :0] P_LOW_TIME = 6'd10 ;localparam P_ST_IDLE = 0 ,P_ST_RST = 1 ,P_ST_RREG = 2 ,P_ST_WRDY = 3 ,P_ST_SET = 4 ,P_ST_WAIT_RDY = 5 ,P_ST_2RREG = 6 ,P_ST_2WRDY = 7 ,P_ST_END = 8 ;reg [7 :0] r_st_current ;
reg [7 :0] r_st_next ;
reg [15:0] r_st_cnt ;reg [6 :0] ro_daddr ;
reg ro_dclk ;
reg ro_den ;
reg [15:0] ro_din ;
reg ro_dwe ;
reg ro_mmcm_rst ;
(* MARK_DEBUG = "TRUE" *)reg [15:0] r_clkout0_reg1 ;
(* MARK_DEBUG = "TRUE" *)reg [15:0] r_clkout0_2reg1 ;
reg [1 :0] r_rdy ;assign o_daddr = ro_daddr ;
assign o_dclk = ro_dclk ;
assign o_den = ro_den ;
assign o_din = ro_din ;
assign o_dwe = ro_dwe ;
assign o_mmcm_rst = ro_mmcm_rst ;always@(posedge i_clk,posedge i_rst)
beginif(i_rst)r_st_current <= P_ST_IDLE;else r_st_current <= r_st_next;
endalways@(*)
begincase(r_st_current)P_ST_IDLE : r_st_next = r_st_cnt == 20000 ? P_ST_RST : P_ST_IDLE ;P_ST_RST : r_st_next = r_st_cnt == 20 ? P_ST_RREG : P_ST_RST ;P_ST_RREG : r_st_next = P_ST_WRDY;P_ST_WRDY : r_st_next = r_rdy[1] ? P_ST_SET : P_ST_WRDY ;P_ST_SET : r_st_next = P_ST_WAIT_RDY;P_ST_WAIT_RDY : r_st_next = r_rdy[1] ? P_ST_2RREG : P_ST_WAIT_RDY;P_ST_2RREG : r_st_next = P_ST_2WRDY;P_ST_2WRDY : r_st_next = r_rdy[1] ? P_ST_END : P_ST_2WRDY;P_ST_END : r_st_next = P_ST_END;default : r_st_next = P_ST_IDLE;endcase
endalways@(posedge i_clk,posedge i_rst)
beginif(i_rst)r_st_cnt <= 'd0;else if(r_st_current != r_st_next)r_st_cnt <= 'd0;else r_st_cnt <= r_st_cnt + 1;
endalways@(posedge i_clk,posedge i_rst)
beginif(i_rst)ro_mmcm_rst <= 'd0;else if(r_st_current == P_ST_END)ro_mmcm_rst <= 'd0;else if(r_st_current == P_ST_RST)ro_mmcm_rst <= 'd1;else ro_mmcm_rst <= ro_mmcm_rst;
endalways@(posedge i_clk,posedge i_rst)
beginif(i_rst) beginro_daddr <= 'd0;ro_den <= 'd0;ro_din <= 'd0;ro_dwe <= 'd0;end else if(r_st_current == P_ST_RREG || r_st_current == P_ST_2RREG) begin ro_daddr <= P_CLKOUT0_REG1_ADDR;ro_den <= 'd1;ro_din <= 'd0;ro_dwe <= 'd0;end else if(r_st_current == P_ST_SET) begin ro_daddr <= P_CLKOUT0_REG1_ADDR;ro_den <= 'd1;ro_din <= (r_clkout0_reg1 | 16'b0000_1111_1111_1111) & {4'b1111,P_HIGN_TIME,P_LOW_TIME};ro_dwe <= 'd1;end else beginro_daddr <= 'd0;ro_den <= 'd0;ro_din <= 'd0;ro_dwe <= 'd0;end
endalways@(posedge i_clk,posedge i_rst)
beginif(i_rst)r_rdy <= 'd0;else r_rdy <= {r_rdy[0],i_drdy};
endalways@(posedge i_clk,posedge i_rst)
beginif(i_rst)r_clkout0_reg1 <= 'd0;else if(r_st_current == P_ST_WRDY && i_drdy)r_clkout0_reg1 <= i_dout;else r_clkout0_reg1 <= r_clkout0_reg1;
endalways@(posedge i_clk,posedge i_rst)
beginif(i_rst)r_clkout0_2reg1 <= 'd0;else if(r_st_current == P_ST_2WRDY && i_drdy)r_clkout0_2reg1 <= i_dout;else r_clkout0_2reg1 <= r_clkout0_2reg1;
end
endmodule