Circuito Divisor de Frecuencia
Fig1. Salida del Divisor |
Saludos
cordiales, en
esta entrada, veremos como describir un circuito divisor de frecuencia con dispositivos biestables. Este trabajo
complementa el avance académico para la materia de Sistemas Digitales II,
siendo requisito que el lector ya tenga conocimientos básicos sobre el diseño
de circuitos digitales, lenguaje verilog y dispositivos lógicos programables.
Para elaborar el código del modulo y llevar a cabo pruebas de funcionamiento, utilizaremos uno de los siguientes programas:
Es un circuito que permite incrementar en múltiplos de dos el periodo de una señal del reloj, donde la relación para este incremento en la señal de salida dependerá del numero de biestables conectados en serie.
Por ejemplo si conectamos dos Flip Flop JK en serie, tal como se observa en la imagen, la relación de salida con respecto a la entrada en el divisor sera 1:4.
Fig2. Circuito Divisor 1:4 |
Fig3. Diagrama de tiempo, Divisor 1:4 |
Descripción del Circuito Divisor
Si modificamos el circuito anterior adicionando un biestable, como se muestran en la figura 4, la salida de este ahora tendrá una relación 1:8 con respecto a la señal del reloj.
Fig4. Circuito Divisor 1:8 | |
input clk, rstn;
output s;
wire q0, q1, q2, jk1, jk2;
FFJKC ff0(clk, 1, 1, rstn, q0);
FFJKC ff1(clk, jk1, jk1, rstn, q1);
input clk, j, k, clrn;
always @(posedge clk or negedge clrn)
if(clrn == 0) q <= 0;
else
case({j,k})
2'b00 : q <= q;
2'b01 : q <= 0;
2'b10 : q <= 1;
2'b11 : q <= ~q;
endcase
endmodule
Fig5. Comportamiento del divisor 1:8 |
input clk, rstn;
output s;
reg [2:0] q; //Registro de 3 bit
assign s = q[2]; //Asigna el bit MSB
always @(posedge clk or negedge rstn)
if(rstn == 0) q <= 0;
else q <= q + 1; //Incrementa el registro
endmodule
Tomando como referencia el código anterior del circuito divisor, y haciendo algunas modificaciones, podemos implementar fácilmente un circuito contador con secuencia truncada para conseguir cualquier frecuencia final de salida. El siguiente modulo llamado drv_clock permite definir como parámetro la frecuencia del reloj y la frecuencia deseada en la salida.
module drv_clock(clk, rstn, clko);
input clk, rstn; //Entrada de reloj principal
output reg clko; //Salida de reloj
parameter SYSFREQ = 50000000; //Frecuencia principal en Hz
parameter OUTFREQ = 1000000; //Frecuencia de salida en Hz
localparam halfOUTFREQ = (SYSFREQ/OUTFREQ)/2;
localparam WIDTH = $clog2(halfOUTFREQ); //Medio ciclo
reg [WIDTH-1:0] cnt; //Contador para medio ciclo OUTFREQ
always @(posedge clk or negedge rstn)
if(!rstn)
begin
clko <= 0;
cnt <= 0;
end
else
begin
if(cnt < (halfOUTFREQ-1)) //medio ciclo
cnt <= cnt + 1'd1;
else
begin
clko = ~clko; //Conmutación de salida
cnt <= 0;
end
end
endmodule
El modulo previo describe un circuito divisor 1:50, con esto es posible obtener una frecuencia de 1 MHz(OUTFREQ) si la entrada es de 50 MHz(SYSFREQ), los parámetros definidos permiten determinar la capacidad del registro contador durante la sintetización del circuito. para este caso la función verilog $log2 nos devolverá un valor entero de 5, con la que se dimensionara el registro contador
module dvr_clock_tb;
reg clk, rstn;
wire out;
drv_clock #(.SYSFREQ(24000000), .OUTFREQ(1000000))
inst0(clk, rstn, out);
initial begin
clk = 0; rstn = 0;
forever #1 clk = ~clk; //Conmuta cada 10ns
end
initial begin
#1 rstn = 1; //Desactiva luego de 10ns
end
endmodule
pablinzte@gmail.com / pablinza@me.com
Pablo Cesar Zárate.
No hay comentarios:
Publicar un comentario