1.移位寄存器代码
module ex_shift(
input wire lvds_clk,
input wire rst,
input wire lvds_d,
output reg [7:0] lvds_o
);
reg [7:0] shift_reg; //用于存储串转并的数据
reg [2:0] cnt;
reg s_flag_dy1,s_flag_dy2;
reg s_flag;
//位拼接符:{7'b1010_000,3'b010} ---> 10'b1010_000_010
always @ (posedge lvds_clk or negedge rst)
if(rst == 1'b0)
shift_reg <= 'd0;
else
shift_reg <= {lvds_d,shift_reg[7:1]};
//第一个时钟周期{0000_0001lvds_d1}
//第二个时钟周期{0000_00lvds_d1 lvds_d2}
//……
//第八个时钟周期{lvds_d1 d2 …… d8}
always @ (posedge lvds_clk or negedge rst)
if(rst == 1'b0)
cnt <= 'd0;
else
cnt <= cnt + 1'b1;
always @ (cnt) //如何写全敏感列表:条件列表里的所有变量+赋值语句右边的所有变量
if(cnt == 3'd7)
s_flag <= 1'b1;
else
s_flag <= 1'b0; //这个分支条件需要写全,否则会生成锁存器,导致延时时间不固定
always @ (posedge lvds_clk)
{s_flag_dy2,s_flag_dy1} <= {s_flag_dy1,s_flag};
always @ (posedge lvds_clk or negedge rst)
if(rst == 1'b0)
lvds_o <= 'd0;
else if(s_flag == 1'b1)
lvds_o <= shift_reg;
endmodule
2.测试文件
`timescale 1ns/1ns
module tb_ex_shift;
reg lvds_clk,rst;
reg [0:0] mem1x16 [15:0]; //声明memory变量,位宽1bit,深度16bit
reg lvds_d;
wire [7:0] lvds_o;
reg [3:0] i_30;
initial begin
lvds_clk <= 0;
rst <= 0;
#100;
rst <= 1;
end
initial begin
$readmemb ("./data.txt",mem1x16); //将data.txt中的文件初始化到mem1x16中,"./data.txt"是目录
end
initial begin
#100;
lvds_send();
end
ex_shift ex_shift_inst(
.lvds_clk(lvds_clk),
.rst(rst),
.lvds_d(lvds_d),
.lvds_o(lvds_o)
);
task lvds_send();
integer i;
begin
for(i=0;i<255;i=i+1)
begin
@(posedge lvds_clk);
lvds_d <= mem1x16[i[3:0]];
i_30 <= i[3:0]; //将数据循环的读出来
end
end
endtask
endmodule
3.do文件自动化仿真
- 建立库
- 映射库到物理目录
- 编译源代码
- 启动仿真器
- 运行仿真
自动化仿真的TCL语言语法:
- vlib:建立库——vlib libname
- vmap:映射逻辑库名,将逻辑库名映射到库路径——vmap work libname
- vdir:显示指定库的内容——vdir -lib libname
- vlog:编译verilog源代码,库名缺省编译到work本地库,文件按顺序编译——vlog -work libname name.v
#此处是注释
#退出当前的仿真工程
quit -sim
#清空命令行显示信息
.main clear
#创建根目录
vlib lib
#在根目录下创建work文件
vlib ./lib/work
#映射到根目录./lib/work
vmap work ./lib/work
#编译work逻辑库中的,一个./是当前目录,./../是当前目录向上翻
vlog -work work ./tb_ex_shift.v
vlog -work work ./../ex_shife.v
#启动仿真,优化参数.启动tb顶层文件
vsim -voptargs=+acc work.tb_ex_shift
#添加波形
add wave -divider {tb_ex_shift}
add wave tb_ex_shift/lvds_d
add wave tb_ex_shift/lvds_o
add wave tb_ex_shift/i_30
add wave tb_ex_shift/lvds_clk
add wave tb_ex_shift/rst
#*是通配符,匹配所有信号
add wave -divider {ex_shift}
add wave tb_ex_shift/ex_shift_inst/*
run 100us
在modelsim中运行.do文件:do run .do