Solo por diversión, quería diseñar y simular flip-flops tipo D utilizando solo lógica combinatoria en Verilog (o SystemVerilog). Estoy usando el uso de Verilator para la simulación.
Mi intento inicial, que utiliza un diseño clásico de seis NAND, parece funcionar bien, y ha pasado todas las pruebas. Mi segundo intento, basado en un tipo JK de cuatro NAND, no está funcionando. La salida no permanece bloqueada durante el nivel positivo del reloj, y para algunas pruebas la simulación ni siquiera converge.
P: Sé que no es normal u óptimo, pero ¿es razonable diseñar flip-flops usando lógica combinacional en Verilog? Si es así, ¿hay algún problema con mi segundo diseño?
Éste funciona:
module dff( input clk, input D, output Q );
wire a, sn, rn, b, Qn;
always_comb // captures D @( posedge clk )
begin
a = !(b&sn);
sn = !(a&clk);
rn = !(sn&b&clk);
b = !(rn&D);
Q = !(sn&Qn);
Qn = !(rn&Q);
end
endmodule
Este no funciona:
module dff( input clk, input D, output Q );
wire J=D, K=!D;
wire sn, rn, qn;
always_comb // captures D @( posedge clk ), but fails to hold
begin
sn = !(J&clk&qn);
rn = !(K&clk&Q);
Q = !(sn&qn);
qn = !(rn&Q);
end
endmodule
En un esfuerzo por eliminar bloqueo de asignación y listas de sensibilidad , reimplementé el enfoque basado en JK de la siguiente manera, pero las formas de onda de salida no se vieron afectadas por esta diferencia.
module dff( input clk, input D, output Q );
wire J=D, K=!D;
wire sn, rn, qn;
assign sn = !(J&clk&qn);
assign rn = !(K&clk&Q);
assign Q = !(sn&qn);
assign qn = !(rn&Q);
endmodule
Nota: basé el diseño de éstos en las descripciones y diagramas aquí .