18 19 SPI接口的74HC595驱动数码管实验

2024-02-15 04:28

本文主要是介绍18 19 SPI接口的74HC595驱动数码管实验,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

1. 串行移位寄存器原理(以四个移位寄存器为例)

1. 通过移位寄存器实现串转并:一个数据输入端口可得到四位并行数据。

通过给data输送0101数据,那么在经过四个时钟周期后,与data相连的四个寄存器的输出端口得到了0101这样的数据,然后我们将latch信号拉高,在下一个时钟周期,D0, D1, D2, D3同时分别获得了这四个数据1010。(其中DFF指D触发器,LATCH信号也可连接锁存器来控制输出)

2. 级联

级联:数据输出端口作为另外的移位寄存器数据端的输入。

2.使用74HC595驱动数码管

1. ACX720上不是直接用fpga的管脚驱动数码管的,而是用74HC595这样的一种串转并的串行移位寄存器来驱动的

2.1 74HC595端口图:

2.2 74HC595时序图

 2.3 74HC595时钟工作频率

取工作频率为12.5MHz。

3. 使用74HC595芯片驱动数码管的verilog代码实现

1.要完成的模块为hc595_driver,实现将16位并行数据转为串行数据发送至74HC595中,实现三线制控制数码管。因此我们的输入需遵循74HC595时序图。

3.1 设计代码

我们要输出shcp,stcp和ds,并满足它们的时序波形(照葫芦画瓢)。shcp的为最小的时间单元,我们可以根据它来作为其他信号波形的参照,但是切记不可将其作为门控时钟,我们只需要把这些要输出的信号当成普通信号,按照时序图上的时序输出即可。

1. shcp的时钟频率为12.5MHz,即一个周期为80ns,我们取半个周期为最小时间单元进行变化,即40ns。

2. 根据最小时间单元产生对应的节点,需要一个计数器记录这些节点(节点执行完开始下一次节点执行),产生节点后再在每个节点做相应的事情即可。

3. hc595_driver里的寄存器是从小到大排列的(0到15),即第0位数据最后进,放在最外面,第15位数据放在最里面。先进15,最后进0。

module hex8_2(clk,rstn,disp_data,sel,led
);parameter times = 50000; // 1msinput clk;input rstn;input [31:0]disp_data;output reg [7:0] sel;output reg [7:0] led;reg [15:0]div_cnt;always@(posedge clk or negedge rstn)if(!rstn)div_cnt <= 0;else if(div_cnt >= times - 1)div_cnt <= 0;elsediv_cnt <= div_cnt + 1'd1;//使能时钟  reg clk_lk;always@(posedge clk or negedge rstn)if(!rstn)clk_lk <= 0;else if(div_cnt == times - 1)clk_lk <= 1'd1;elseclk_lk <= 0;//cnt累加器reg [2:0] num_cnt;    always@(posedge clk_lk or negedge rstn)if(!rstn)num_cnt <= 0;else if(clk_lk == 1)num_cnt <= num_cnt + 1'd1;//三八译码器    always@(posedge clk or negedge rstn)if(!rstn)sel <= 0;else case(num_cnt)0:sel = 8'b0000_0001;1:sel = 8'b0000_0010;2:sel = 8'b0000_0100;3:sel = 8'b0000_1000;4:sel = 8'b0001_0000;5:sel = 8'b0010_0000;6:sel = 8'b0100_0000;7:sel = 8'b1000_0000;endcase//八选一多路器reg [3:0]disp_tmp;always@(posedge clk)case(num_cnt)0:disp_tmp = disp_data[3:0];1:disp_tmp = disp_data[7:4];2:disp_tmp = disp_data[11:8];3:disp_tmp = disp_data[15:12];4:disp_tmp = disp_data[19:16];5:disp_tmp = disp_data[23:20];6:disp_tmp = disp_data[27:24];7:disp_tmp = disp_data[31:28];endcase//四十六译码器 always@(posedge clk)case(disp_tmp)0:led = 8'hc0;1:led = 8'hf9;2:led = 8'ha4;3:led = 8'hb0;4:led = 8'h99;5:led = 8'h92;6:led = 8'h82;7:led = 8'hf8;8:led = 8'h80;9:led = 8'h90;4'ha:led = 8'h88;4'hb:led = 8'h83;4'hc:led = 8'hc6;4'hd:led = 8'ha1;4'he:led = 8'h86;4'hf:led = 8'h8e;  default:led = 8'hc0;endcaseendmodule
module hc595_driver(clk,rstn,data,s_en,shcp,stcp,ds  
);parameter times = 2; //40ns为最小刻度input clk;input rstn;input [15:0] data;input s_en;output reg shcp;output reg stcp;output reg ds;reg [15:0] r_data;always@(posedge clk)if(s_en)r_data <= data;//1.产生74hc595时序所需的最小时间单元reg [7:0] div_cnt;//脉冲信号wire sck_plus;assign sck_plus = div_cnt >= times - 1;always@(posedge clk or negedge rstn)if(!rstn)div_cnt <= 0;else if(div_cnt >= times - 1)div_cnt <= 0;elsediv_cnt <= div_cnt + 1'd1;//2.依据sck_plus做相对应的事情//先记录sck_plus的节点数reg [5:0]shcp_edge_counter;    always@(posedge clk or negedge rstn)if(!rstn)   shcp_edge_counter <= 0;else if(sck_plus) //sck_plus不是寄存器的输出    if(shcp_edge_counter == 32)            shcp_edge_counter <= 0;elseshcp_edge_counter <=  shcp_edge_counter + 1'd1;always@(posedge clk or negedge rstn)if(!rstn) beginshcp <= 0;stcp <= 0;ds <= 0;endelse case(shcp_edge_counter)0: begin shcp <= 0; ds <= r_data[15]; stcp <= 0; end1: shcp <= 1'd1;2: begin shcp <= 0; ds <= r_data[14]; end3: shcp <= 1'd1;4: begin shcp <= 0; ds <= r_data[13]; end5: shcp <= 1'd1;6: begin shcp <= 0; ds <= r_data[12]; end7: shcp <= 1'd1;8: begin shcp <= 0; ds <= r_data[11]; end9: shcp <= 1'd1;10: begin shcp <= 0; ds <= r_data[10]; end11: shcp <= 1'd1;12: begin shcp <= 0; ds <= r_data[9]; end13: shcp <= 1'd1;14: begin shcp <= 0; ds <= r_data[8]; end15: shcp <= 1'd1;16: begin shcp <= 0; ds <= r_data[7]; end17: shcp <= 1'd1;18: begin shcp <= 0; ds <= r_data[6]; end19: shcp <= 1'd1;20: begin shcp <= 0; ds <= r_data[5]; end21: shcp <= 1'd1;22: begin shcp <= 0; ds <= r_data[4]; end23: shcp <= 1'd1;24: begin shcp <= 0; ds <= r_data[3]; end25: shcp <= 1'd1;26: begin shcp <= 0; ds <= r_data[2]; end27: shcp <= 1'd1;28: begin shcp <= 0; ds <= r_data[1]; end29: shcp <= 1'd1;30: begin shcp <= 0; ds <= r_data[0]; end31: shcp <= 1'd1;32: begin shcp <= 0; stcp <= 1; ds <= 0; enddefault : beginshcp <= 0;stcp <= 0;ds <= 0;endendcaseendmodule

3.2 针对hc595_driver的仿真代码

`timescale 1ns / 1psmodule hc595_driver_tb();reg clk;reg rstn;reg [15:0] data;reg s_en;wire shcp;wire stcp;wire ds;hc595_driver hc595_driver_inst(clk,rstn,data,s_en,shcp,stcp,ds  );initial clk = 1;always #10 clk = ~clk;initial beginrstn = 0;#201;rstn = 1;#200;s_en = 1;data = 16'h1357;#4000;s_en = 0;#200;s_en = 1;data = 16'h2468;#4000;s_en = 0;$stop;endendmodule

3.3 针对hc595_driver的仿真波形

 3.4 针对数码管的管脚约束文件

这篇关于18 19 SPI接口的74HC595驱动数码管实验的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/710428

相关文章

springboot下载接口限速功能实现

《springboot下载接口限速功能实现》通过Redis统计并发数动态调整每个用户带宽,核心逻辑为每秒读取并发送限定数据量,防止单用户占用过多资源,确保整体下载均衡且高效,本文给大家介绍spring... 目录 一、整体目标 二、涉及的主要类/方法✅ 三、核心流程图解(简化) 四、关键代码详解1️⃣ 设置

spring中的ImportSelector接口示例详解

《spring中的ImportSelector接口示例详解》Spring的ImportSelector接口用于动态选择配置类,实现条件化和模块化配置,关键方法selectImports根据注解信息返回... 目录一、核心作用二、关键方法三、扩展功能四、使用示例五、工作原理六、应用场景七、自定义实现Impor

MybatisPlus service接口功能介绍

《MybatisPlusservice接口功能介绍》:本文主要介绍MybatisPlusservice接口功能介绍,本文给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友... 目录Service接口基本用法进阶用法总结:Lambda方法Service接口基本用法MyBATisP

一文彻底搞懂Java 中的 SPI 是什么

《一文彻底搞懂Java中的SPI是什么》:本文主要介绍Java中的SPI是什么,本篇文章将通过经典题目、实战解析和面试官视角,帮助你从容应对“SPI”相关问题,赢得技术面试的加分项,需要的朋... 目录一、面试主题概述二、高频面试题汇总三、重点题目详解✅ 面试题1:Java 的 SPI 是什么?如何实现一个

Java中的Closeable接口及常见问题

《Java中的Closeable接口及常见问题》Closeable是Java中的一个标记接口,用于表示可以被关闭的对象,它定义了一个标准的方法来释放对象占用的系统资源,下面给大家介绍Java中的Clo... 目录1. Closeable接口概述2. 主要用途3. 实现类4. 使用方法5. 实现自定义Clos

java对接第三方接口的三种实现方式

《java对接第三方接口的三种实现方式》:本文主要介绍java对接第三方接口的三种实现方式,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教... 目录HttpURLConnection调用方法CloseableHttpClient调用RestTemplate调用总结在日常工作

Dubbo之SPI机制的实现原理和优势分析

《Dubbo之SPI机制的实现原理和优势分析》:本文主要介绍Dubbo之SPI机制的实现原理和优势,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教... 目录Dubbo中SPI机制的实现原理和优势JDK 中的 SPI 机制解析Dubbo 中的 SPI 机制解析总结Dubbo中

Java 的 Condition 接口与等待通知机制详解

《Java的Condition接口与等待通知机制详解》在Java并发编程里,实现线程间的协作与同步是极为关键的任务,本文将深入探究Condition接口及其背后的等待通知机制,感兴趣的朋友一起看... 目录一、引言二、Condition 接口概述2.1 基本概念2.2 与 Object 类等待通知方法的区别

SpringBoot实现接口数据加解密的三种实战方案

《SpringBoot实现接口数据加解密的三种实战方案》在金融支付、用户隐私信息传输等场景中,接口数据若以明文传输,极易被中间人攻击窃取,SpringBoot提供了多种优雅的加解密实现方案,本文将从原... 目录一、为什么需要接口数据加解密?二、核心加解密算法选择1. 对称加密(AES)2. 非对称加密(R

如何在Ubuntu上安装NVIDIA显卡驱动? Ubuntu安装英伟达显卡驱动教程

《如何在Ubuntu上安装NVIDIA显卡驱动?Ubuntu安装英伟达显卡驱动教程》Windows系统不同,Linux系统通常不会自动安装专有显卡驱动,今天我们就来看看Ubuntu系统安装英伟达显卡... 对于使用NVIDIA显卡的Ubuntu用户来说,正确安装显卡驱动是获得最佳图形性能的关键。与Windo