FPGA Verilog实现JK触发器 再实现模12加法计数器

  • Post author:
  • Post category:其他

 JK触发器,无法仿真,代码如下,按照老师PPT写的

`timescale 1ns / 1ps
module JKtrigger(Q,CLK,RESET,SET,J,K);
	input CLK,RESET,SET,J,K;
	output Q;
	reg Q;
	always @(posedge CLK or negedge RESET 
						or negedge SET) begin
		//异步复位与置位 触发器的复位和置位与时钟信号无关
		//按照逻辑表达式写就行
		if(RESET == 0)//低电平有效
			Q <= 0;
		else if(SET == 0)//低电平有效
			Q <= 1;
		else if(J == 0 && K == 1)//置0
		    Q <= 0;
		else if(J == 1 && K == 1)//翻转
			Q <= ~Q;
		else if(J == 1 && K == 0)//置1
			Q <= 1;
		else Q <= Q;//(J == 0 && K == 0)//保持
	end
endmodule

仿真文件:

`timescale 1ns / 1ps
module sim_JKtrigger();
	reg CLK = 0, SET = 1,RESET = 1, J = 0, K = 0;
	wire Q;
	always #5 CLK = ~CLK;
	always begin
		#6 J <= J+1;
		#7 K <= K+1;
	end
	always begin
		#12 RESET = ~RESET;
		#10 SET = ~SET;
		#17 $stop;
	end
	JKtrigger u1(Q,CLK,RESET,SET,J,K);
endmodule

 然后我把JK触发器的程序改了一下

`timescale 1ns / 1ps
module JKtrigger(Q,CLK,RESET,SET,J,K);
	input CLK,RESET,SET,J,K;
	output Q;
	reg Q;
	wire QB;
	always @(posedge CLK or negedge RESET 
						or negedge SET) begin
		//异步复位与置位 触发器的复位和置位与时钟信号无关
		if(RESET == 0)//低电平有效
			Q <= 0;
		else if(SET == 0)//低电平有效
			Q <= 1;
		//按照逻辑表达式写就行
		else Q <= (J&(~Q))|((~K)&Q);
		//上面逻辑表达式等价于下面的枚举,但是下面的不知有什么bug
		// else if(J == 0 && K == 1)//置0
		// 	Q <= 0;
		// else if(J == 1 && K == 1)//翻转
		// 	Q <= ~Q;
		// else if(J == 1 && K == 0)//置1
		// 	Q <= 1;
		// else Q <= Q;//(J == 0 && K == 0)//保持
	end
	assign QB = ~Q;
endmodule

然后就可以仿真了:(还是不知道为啥原来的不行)

红色的先是因为CLK没有到上升沿,SET RESET没有到下降沿(讲道理CLK到第一个上升沿应该就不是红的了,不知道为什么)

 修改后的:应该是正确的(其实不改仿真文件也没事,只是用这个来看设计文件是否正确的,不需要纠结这个红线)

`timescale 1ns / 1ps
module sim_JKtrigger();
	reg CLK,SET,RESET,J,K;
	wire Q;
	initial begin
			CLK = 0;
			SET = 1;
			RESET = 0;
			J = 0;
			K = 0;
	end
	always #5 CLK = ~CLK;
	always begin
		#6 J <= J+1;
		#7 K <= K+1;
	end
	always begin
		//这21nm里SET=0,RESET=1,每次CLK上升沿时会先判断到SET=0,则Q为1
		#21 begin
			SET = ~SET;
			RESET = ~RESET;
		end
		//这21nm里SET=1,RESET=0,每次CLK上升沿时会先判断到RESET=0,则Q为0
		#21 begin
			SET = ~SET;
			RESET = ~RESET;
		end 
		//这21nm里SET=1,RESET=1,每次CLK上升沿时会判断(J&(~Q))|((~K)&Q
		begin
			SET = 1;
			RESET = 1;
		end
		// #7 begin
		// 	SET = 0;
		// 	RESET = 1;
		// end
		// #7 begin
		// 	SET = 1;
		// 	RESET = 1;
		// end
		#200 $stop;
	end
	JKtrigger u1(Q,CLK,RESET,SET,J,K);
endmodule

解决上面问题的时候又出现了这个问题。

 参考了这个:意思就是把能关的都关了再仿真就行了。如何解决Vivado仿真时提示:另一个程序正在使用此文件 /behav/xsim/simulate.log_weixin_52027058的博客-CSDN博客_vivado另一个程序正在使用此文件,进程无法访问

JK搞好了,封装成一个IP核,待会用在模12加法计数器。下面这个有介绍ip核的,也是我们第一个vivado实验。

vivado.2020-Verilog两个半加器实现一个全加器-数字逻辑实验-IP核的使用_玛卡巴卡-的博客-CSDN博客_verilog加法器ip核

同学说这个可以用,先放着。

FPGA/数字IC笔记——Verilog实现N进制计数器_DengFengLai123的博客-CSDN博客_verilog8进制计数器

老师PPT里的东西(为啥就这么点)

 

初版,不行:

`timescale 1ns / 1ps
module Mod2_Addition_Counter(Q[3:0],CLK,SET);
	input CLK,SET;
	output [3:0]Q ;

	JKtrigger_0 u0(Q[0],CLK,~(Q[3] && Q[2]),SET,1,1);
	JKtrigger_0 u1(Q[1],Q[0],~(Q[3] && Q[2]),SET,1,1);
	JKtrigger_0 u2(Q[2],Q[1],~(Q[3] && Q[2]),SET,1,1);
	JKtrigger_0 u3(Q[3],Q[2],~(Q[3] && Q[2]),SET,1,1);

endmodule

 仿真文件:

`timescale 1ns / 1ps
module sim_Mod2_Addition_Counter();
	reg CLK,SET;
	wire [3:0]Q;
	initial begin
		CLK = 1;
		SET = 1;
	end
	always #5 CLK <= ~CLK;
	Mod2_Addition_Counter m2(Q[3:0],CLK,SET);
endmodule

 又看了一下这个:

数电实验 jk触发器实现计数器与倒计时器_哔哩哔哩_bilibili

发现Q是有输出的,原程序的思路是如果记到12(但是原程序写的可能是到13)就触发一次RESET,使得全部置0,不知为何有问题。

原程序是异步的,不行,先换同步试试:(至于这个为什么是这样的,要用逻辑式分析了)

`timescale 1ns / 1ps
module Mod2_Addition_Counter(Q[3:0],CLK,SET,RESET);
	input CLK,SET,RESET;
	output [3:0]Q ;

	// JKtrigger_0 u0(Q[0],CLK,~(Q[3] && Q[2]),SET,1,1);
	// JKtrigger_0 u1(Q[1],Q[0],~(Q[3] && Q[2]),SET,1,1);
	// JKtrigger_0 u2(Q[2],Q[1],~(Q[3] && Q[2]),SET,1,1);
	// JKtrigger_0 u3(Q[3],Q[2],~(Q[3] && Q[2]),SET,1,1);

	// JKtrigger_0 u0(Q[0],CLK,RESET,SET,1,1);
	// JKtrigger_0 u1(Q[1],CLK,RESET,SET,Q[0],Q[0]);
	// JKtrigger_0 u2(Q[2],CLK,RESET,SET,(~Q[2])&Q[1]&Q[0],Q[1]|Q[0]);
	// JKtrigger_0 u3(Q[3],CLK,RESET,SET,Q[2]&Q[1]&Q[0],Q[1]&Q[0]);

	JKtrigger_0 u0(Q[0],CLK,RESET,SET,1,1);
	JKtrigger_0 u1(Q[1],CLK,RESET,SET,Q[0],Q[0]);
	JKtrigger_0 u2(Q[2],CLK,RESET,SET,(~Q[3])&Q[1]&Q[0],Q[1]&Q[0]);
	JKtrigger_0 u3(Q[3],CLK,RESET,SET,Q[2]&Q[1]&Q[0],Q[1]&Q[0]);
endmodule

仿真:

`timescale 1ns / 1ps
module sim_Mod2_Addition_Counter();
	reg RESET,CLK,SET;
	wire [3:0]Q;
	initial begin
		CLK = 1;
		SET = 1;
		RESET = 1;
		#1 SET = 0;
		#1 SET = 1;
		#1 RESET = 0;
		#1 RESET = 1;
	end
	always #5 CLK <= ~CLK;
	Mod2_Addition_Counter m1(Q,CLK,SET,RESET);
endmodule

 仿真结果:

 建立方法:(有点乱…)

之中还遇到这个问题,就是程序写错了

【FPGA】vivado Error:‘launch_simulation‘failed due to earlier errors._WindK77D的博客-CSDN博客


版权声明:本文为qq_60790894原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。