8段4位数码管verilator模拟
seg.v
module seg(input wire clk,input wire rst_n,output wire[7:0] SEG,output wire[3:0] SEL
);reg[7:0] digit[0:15] = '{8'h3f, 8'h06, 8'h5b, 8'h4f, 8'h66, 8'h6d, 8'h7d,8'h07,8'h7f,8'h6f, 8'h77, 8'h7c, 8'h39, 8'h5e, 8'h79, 8'h71};reg[31:0] cnt = 32'h0000000000;always @(posedge clk or negedge rst_n) beginif (!rst_n)cnt <= 32'h00000000;elsecnt <= cnt + 1;
endreg[1:0] shift;assign shift = cnt[16:15];assign SEL = 4'b0001 << shift;
assign SEG = digit[4'(cnt[31:20]>>shift*4)];endmodule
转接
seg_adaptor.v
module seg_adaptor(input wire clk,input wire[7:0] SEG,input wire[3:0] SEL
);
import "DPI-C" function void print(byte seg, byte sel);
reg[3:0] state = 4'b0001 ;always @(posedge clk)if (state != SEL) beginprint(byte'(SEG),byte'(SEL));state <= SEL;endendmodule
tb
top.v
module top;
wire[7:0] seg;
wire[3:0] sel;
reg clk = 1'b0;
reg rst_n = 1'b0;initial begin#10 rst_n = 1'b1;forever #1 clk = ~clk;
endseg seg1(.clk(clk),.rst_n(rst_n),.SEG(seg),.SEL(sel));seg_adaptor adaptor1(.clk(clk),.SEG(seg),.SEL(sel));endmodule
print.h
#ifdef __cplusplus
extern "C"{
#endifvoid print(char seg, char sel);#ifdef __cplusplus
}
#endif
print.c
#define DIGIT_NUM 4
#include <stdio.h>
#include <stdbool.h>
#include <unistd.h>
#include "svdpi.h"
#include "print.h"static inline void prt(unsigned char data,int bit,char c) {if(data&(1<<bit)) putchar(c);else putchar(' ');
}static inline void printu(unsigned char data, int b1, int b2, int b3)
{prt(data,b1,'|') ;prt(data,b2,'_') ;prt(data,b3,'|') ;}void printd(unsigned char data){printf("\x1b[C"); //前进一格prt(data,0,'_');printf("\x1b[B\x1b[2D"); //下移一格后退两格printu(data,5,6,1);printf("\x1b[B\x1b[3D"); //下移一格后退三格printu(data,4,3,2);prt(data,7,'.');
}void print(char sg, char sel) {unsigned char seg = (unsigned char ) sg;static int init = 0;if (init == 0) {printf("\n\n\n");init = 1;printf("\x1b[?25l"); //隐藏光标}unsigned char c = sel;for(int i = 7; i >= 0; i--)if(sel&(1<<i)) {printf("\x1b[2A\x1b[%dG",(DIGIT_NUM-i-1)*4+1); //上移两行定位printd(seg);}fflush(stdout);
}
Makefile
.PHONY:cleanVERILATOR = verilatorOUTDIR=out
VERILATOR_FLAGS = -Wall -top top -Mdir $(OUTDIR) -cc -binary -build -j 2default: runrun: print.c top.v seg.v seg_adaptor.v$(VERILATOR) $(VERILATOR_FLAGS) $^./$(OUTDIR)/Vtoprc: #restore cursor visibility@echo -ne "\x1b[?25h"clean:-rm -rf $(OUTDIR)
make
ctrl c 退出后光标会隐藏
恢复光标显示
make rc
已上传github
git clone https://github.com/yses/fpgasim