5 Verilog进阶篇:时序逻辑1

VL5 信号发生器

描述

题目描述:

请编写一个信号发生器模块,根据波形选择信号wave_choise发出相应的波形:wave_choice=0时,发出方波信号;wave_choice=1时,发出锯齿波信号;wave_choice=2时,发出三角波信号。

       模块的接口信号图如下:

模块的时序图如下:

题意整理

       实现不同波形的输出可以使用case语句,以wave_choise作为case语句的cans.根据wave_choise的值输出不同的波形。以0为最低值,20为最高值为例(可以根据需要具体修改)。根据不同波形的需要,产生相应的数据:

       方波:产生占空比50%的方波,输出0保持20个时钟,输出20保持20个时钟。

       锯齿波:输出数据从0按照步长1递增至20,再从20跳变到0,再依次递增,以此循环。

       三角波:输出数据从0按照步长1递增至20,再从20递减到0,以此循环。

题解主体

       首先是方波的实现,较为简单,只需要设置一个计数器,使输出保持20个时钟为0,跳变为20,再保持20个时钟。依次循环。可以按照如下的过程实现:cnt每个时钟加一,当cnt=19时,将wave的值置为0,同时cnt置为0;当cnt=9时,将wave的值置为20。

                     reg [4:0]cnt;

                            if (cnt == 5'd19)

                                   begin    

                                          wave <= 5'd0;

                                          cnt <= 5'd0;

                                   end

                            else if(cnt == 5'd9)

                                   begin    

                                          wave <= 5'd20;

                                          cnt <= cnt + 1'd1;

                                   end

                            else

                                   begin

                                          wave <= wava;

                                          cnt <= cnt + 1'd1;

                                   end

       锯齿波的实现,即输出信号由0每次加一递增到20,然后从20跳变到0。可以按照如下的过程实现:当wave=20,将wave的值置为0,其余时刻,wave加一。

                            if (wave == 5'd20)

                                   begin

                                          wave <= 5'd0;

                                   end

                            else

                                   begin

                                          wave <= wava + 1'd1;

                                   end

       三角波的实现,类似于锯齿波,但当wave达到20时,不是跳变到0,而是以一为步长递减到0。可以设置一个指示信号up,当up的值是1时,wave每个时钟加一。当up的值为0时,则减一。

                            if (wave == 5'd20)

                                   begin

                                          wave <= wave - 1'd1;

                                          up = 1'd0;

                                   end

                            else if (wave = 5'd0)

                                   begin

                                          wave <= wava - 1'd1;

                                          up = 1'd1;

                                   end

                            else if (up)

                                   begin

                                          wave <= wava + 1'd1;

                                   end

                            else

                                   begin

                                          wave <= wava - 1'd1;

                                   end

`timescale 1ns/1ns
module signal_generator(
	input clk,
	input rst_n,
	input [1:0] wave_choise,
	output reg [4:0]wave
	);

	reg [4:0]cnt;
	reg up;
	always @(posedge clk or negedge rst_n)
		if (!rst_n)
			begin 
				wave <= 5'd0;
				cnt <= 5'd0;
			end
		else case (wave_choise)
		2'b00:				//产生方波,保持0十个时钟,保持20十个时钟
			begin
				if (cnt == 5'd19)
					begin	
						wave <= 5'd0;
						cnt <= 5'd0;
					end
				else if(cnt == 5'd9)
					begin	
						wave <= 5'd20;
						cnt <= cnt + 1'd1;
					end
				else
					begin
						wave <= wave;
						cnt <= cnt + 1'd1;
					end
			end
		2'b01:				//产生锯齿,0递增到20
			begin
				if (wave == 5'd20)
					begin
						wave <= 5'd0;
					end
				else 
					begin
						wave <= wave + 1'd1;
					end
			end
		2'b10:
			begin
				if (wave == 5'd20)
					begin
						wave <= wave - 1'd1;
						up = 1'd0;
					end
				else if (wave == 5'd0)
					begin
						wave <= wave - 1'd1;
						up = 1'd1;
					end
				if (up)
					begin
						wave <= wave + 1'd1;
					end
				else 
					begin
						wave <= wave - 1'd1;
					end
			end
		default:
			begin
				wave <= 1'b0;
			end
	endcase
endmodule

VL6 数据串转并电路 ***

描述

实现串并转换电路,输入端输入单bit数据,每当本模块接收到6个输入数据后,输出端输出拼接后的6bit数据。本模块输入端与上游的采用valid-ready双向握手机制,输出端与下游采用valid-only握手机制。数据拼接时先接收到的数据放到data_b的低位。

电路的接口如下图所示。valid_a用来指示数据输入data_a的有效性,valid_b用来指示数据输出data_b的有效性;ready_a用来指示本模块是否准备好接收上游数据,本模块中一直拉高;clk是时钟信号;rst_n是异步复位信号。

接口时序示意图

题意整理

本题要求实现将6个单bit输入数据拼接之后输出。

时序图含有的信息较多,观察时序图需要注意:

l  data_b是在已接收到6个数据后下一个时钟产生输出;

l  本模块与上游采用valid_ready握手机制,当valid_a拉低,表示与上游握手未成功,则此时data_a的数据无效,不存入本模块当中;

l  本模块与下游采用valid_only握手机制,这是一种单向指示性握手机制,已接收到6个数据后,valid_b拉高一个时钟周期,指示输出数据有效性

题解主体

要实现6个单bit输入数据的拼接,要用1个寄存器将先到达的数据缓存。当上游握手成功,将输入数据进寄存器,先收到的数据放在低位;当缓存好6个输入数据,valid_b拉高,输出data_b。

需要计数器来计数接收到的数据数量,计数器在0-5之间循环。计数器初始值是0,每接收一个数据,计数器加1,当计数器再次循环到0时,表示已经接收到6个数据,可以输出拼接结果。

Verilog代码如下:

reg [5:0]       data_reg;
reg [2:0]       data_cnt;

always @(posedge clk or negedge rst_n ) begin
       if(!rst_n)
              ready_a <= 'd0;
       else
              ready_a <= 1'd1;
end

always @(posedge clk or negedge rst_n ) begin
       if(!rst_n)
              data_cnt <= 'd0;
       else if(valid_a && ready_a)
              data_cnt <= (data_cnt == 3'd5) ? 'd0 : (data_cnt + 1'd1);
end

always @(posedge clk or negedge rst_n ) begin
       if(!rst_n)
              data_reg <= 'd0;
       else if(valid_a && ready_a)
              data_reg <= {data_a, data_reg[5:1]};
end


always @(posedge clk or negedge rst_n ) begin
       if(!rst_n)begin
              valid_b <= 'd0;
              data_b <= 'd0;
       end
       else if(data_cnt == 3'd5)begin
              valid_b <= 1'd1;
              data_b <= {data_a, data_reg[5:1]};
       end
       else
              valid_b <= 'd0;
end

VL7 数据累加输出***

描述

实现串行输入数据累加输出,输入端输入8bit数据,每当模块接收到4个输入数据后,输出端输出4个接收到数据的累加结果。输入端和输出端与上下游的交互采用valid-ready双向握手机制。要求上下游均能满速传输时,数据传输无气泡,不能由于本模块的设计原因产生额外的性能损失。

电路的接口如下图所示。valid_a用来指示数据输入data_in的有效性,valid_b用来指示数据输出data_out的有效性;ready_a用来指示本模块是否准备好接收上游数据,ready_b表示下游是否准备好接收本模块的输出数据;clk是时钟信号;rst_n是异步复位信号。

接口时序示意图

 

输入描述:

    input                 clk         ,   
    input                 rst_n        ,
    input        [7:0]    data_in        ,
    input                valid_a        ,
    input                 ready_b        

输出描述:

     output                 ready_a        ,
     output    reg            valid_b        ,
    output  reg [9:0]     data_out

 

题意整理

本题要求实现将4个输入数据累加之后输出,模块与上下游采用valid-ready双向握手机制。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值