前言

  • SPI 介绍为搜集百度资料+个人理解
  • 其余为原创(有误请指正)
  • 集四种模式于一身

笔录草稿

SPI介绍

  • SPI 协议简介

    • SPI 协议是由摩托罗拉公司提出的通讯协议(Serial Peripheral Interface),即串行外围设备接口,是一种高速全双工的通信总线。
    • 是一个环形总线结构
      • 由 ss(cs)、sck、sdi、sdo 构成
      • 其时序主要是在 sck 的控制下,两个双向移位寄存器进行数据交换。
  • 物理线说明

    • SS

      • 从设备选择信号线,常称为片选信号线,也称为NSS、CS。
      • 用于选择从机。
    • SCK (Serial Clock)
      • 时钟信号线
      • 用于通讯数据同步。
    • MOSI (Master Output, Slave Input)
      • 主设备输出/从设备输入引脚。
      • 主机发出,从机接收。
    • MISO (Master Input,,Slave Output)
      • 主设备输入/从设备输出引脚。
      • 从机发出,主机接收。
  • SPI 四种模式

    • 请移步到下面章节学习
  • SPI的协议层

    • SPI协议定义了通讯的起始和停止信号、数据有效性、时钟同步等环节。
    • 基本通讯过程
    • 图解
      1. 标号1:NSS信号线由高变低,是SPI通讯的起始信号。
      2. 标号6:NSS信号由低变高,是SPI通讯的停止信号。
  • 简单时序图

  • 模式时序图

SPI四种模式 **

  • 四种模式由 CPOLCPHA 组合区分
  • CPOL
    • 时钟极性
    • 是指SPI通讯设备处于空闲状态时,SCK信号线的电平信号
    • 0
      • SCK 空闲状态为 低电平
    • 1
      • SCK 空闲状态为 高电平
  • CPHA
    • 时钟相位
    • 是指数据的采样的时刻
    • 0
      • MOSI或MISO数据线上的信号将会在SCK时钟线的“奇数边沿”被采样。(即是第一个边沿)
      • 这种模式适合那种从设备一旦被片选后就输出数据到MISO线上。
    • 1
      • 数据线在SCK的“偶数边沿”采样。(即是第二个边沿)
      • 这种模式适合那种从设备被片选后还需要一个时钟才能 输出数据到MISO线上。
  • 四种模式(CPOL, CPHA
    • 模式 0:(0, 0

      • SCK空闲为 低电平,数据在SCK的 上升沿 被采样
    • 模式 1:(0, 1
      • SCK空闲为 低电平,数据在SCK的 下降沿 被采样
    • 模式 2:(1, 0
      • SCK空闲为 高电平,数据在SCK的 下降沿 被采样
    • 模式 3:(1, 1
      • SCK空闲为 高电平,数据在SCK的 上升沿 被采样

SPI 驱动框架 **

框架

  • 实现方法参考 I2C设备驱动拆解
  • 自己先在写出四种模式的读写时序,便会发现以下规律
  • 读写的逻辑差不多都一样,只是 SCK 信号线出现的位置及高低电平会因不同模式而不同。(这里我就不分别写出4种模式的单独实现了,直接上规律表,然后实现统一的源码
R/W CPOL CPHA 位置1-SCK 位置2-SCK 位置3-SCK 位置4-SCK
R 0 0 X 0 1 0
R 0 1 X 1 0 0
R 1 0 X 1 0 1
R 1 1 X 0 1 1
- - - - - - -
W 0 0 X 0 1 0
W 0 1 0 1 0 X
W 1 0 X 1 0 1
W 1 1 1 0 1 X

由上规律得出 支持四种模式的 SPI 读写源码

  • SPI 写函数
/**
* @brief SPI 写函数
* @param
* @retval
* @author lzm
*/
void spiWriteOneByte(eSPI_ID id, unsigned char data)
{
unsigned char i;
const spi_t * spi = &spiDriverElem[id]; // 位置1
if(spi->CPHA){
spiOut(spi->sckGpiox, spi->sckPin, spi->CPOL);
} for(i=0; i<8; i++)
{
// 位置2
spiOut(spi->sckGpiox, spi->sckPin, (spi->CPOL != spi->CPHA));
if(data & 0x80){
spiMosiOutHi(spi);
}
else{
spiMosiOutLo(spi);
}
data <<= 1;
spi->delayUsFun(spi->readDelayUsCnt);
// 位置3
spiOut(spi->sckGpiox, spi->sckPin, (spi->CPOL == spi->CPHA));
}
// 位置4
if(!(spi->CPHA)){
spiOut(spi->sckGpiox, spi->sckPin, spi->CPOL);
}
}
  • SPI 读函数
/**
* @brief SPI 读函数
* @param
* @retval
* @author lzm
*/
unsigned char spiReadOneByte(eSPI_ID id)
{
unsigned char i;
unsigned char ret;
const spi_t * spi = &spiDriverElem[id]; // 位置1 for(i=0; i<8; i++)
{
// 位置2
spiOut(spi->sckGpiox, spi->sckPin, (spi->CPOL != spi->CPHA));
ret <<= 1;
if(spiMisoIn(spi))
ret |= 0x01;
else
ret &= 0xfe;
spi->delayUsFun(spi->readDelayUsCnt);
// 位置3
spiOut(spi->sckGpiox, spi->sckPin, (spi->CPOL == spi->CPHA));
}
// 位置4
spiOut(spi->sckGpiox, spi->sckPin, spi->CPOL);
return ret;
}
  • SPI 读写函数
/**
* @brief SPI 读写一体函数
* @param
* @retval
* @author lzm
*/
unsigned char spiRWOneByte(eSPI_ID id, unsigned char data)
{
unsigned char i;
unsigned char ret;
const spi_t * spi = &spiDriverElem[id]; // 位置1
if(spi->CPHA){
spiOut(spi->sckGpiox, spi->sckPin, spi->CPOL);
} for(i=0; i<8; i++)
{
// 位置2
spiOut(spi->sckGpiox, spi->sckPin, (spi->CPOL != spi->CPHA));
if(data & 0x80){
spiMosiOutHi(spi);
}
else{
spiMosiOutLo(spi);
}
data <<= 1;
spi->delayUsFun(spi->readDelayUsCnt);
// 位置3
spiOut(spi->sckGpiox, spi->sckPin, (spi->CPOL == spi->CPHA));
ret <<= 1;
if(spiMisoIn(spi))
ret |= 0x01;
else
ret &= 0xfe;
spi->delayUsFun(spi->readDelayUsCnt);
}
// 位置4
if(!(spi->CPHA)){
spiOut(spi->sckGpiox, spi->sckPin, spi->CPOL);
}
}

框架-SPI四种模式+通用设备驱动实现的更多相关文章

  1. 【框架】SPI四种模式+通用设备驱动实现-源码

    目录 前言 bsp_spi.c bsp_spi.h bsp_flash.c bsp_flash.h 前言 SPI 介绍为搜集百度资料+个人理解 其余为原创(有误请指正) 集四种模式于一身 demo 采 ...

  2. 小知识:SPI四种模式区别【转】

    转自:http://home.eeworld.com.cn/my/space-uid-80086-blogid-119198.html spi四种模式SPI的相位(CPHA)和极性(CPOL)分别可以 ...

  3. SPI 四种模式

    SPI时钟极性CPOL, = 0表示在没有数据传输时为低电平,= 1表示没有数据传输时为高电平. SPI时钟相位CPHA,= 0表示时钟的第一个沿更新数据.第二个沿锁存数据,= 1表示时钟的第一个沿锁 ...

  4. Asp.net的sessionState四种模式配置方案

    sessionState节点的配置 web.config关于sessionState节点的配置方案,sessionState有四种模式:off,inProc,StateServer,SqlServer ...

  5. 大量数据也不在话下,Spring Batch并行处理四种模式初探

    1 前言 欢迎访问南瓜慢说 www.pkslow.com获取更多精彩文章! Spring相关文章:Springboot-Cloud 前面写了一篇文章<通过例子讲解Spring Batch入门,优 ...

  6. Hibernate 查询MatchMode的四种模式

    Hibernate 查询MatchMode的四种模式 MatchMode.START:字符串在最前面的位置.相当于"like 'key%'" MatchMode.END:字符串在最 ...

  7. Android 文件访问权限的四种模式

    Linux文件的访问权限* 在Android中,每一个应用是一个独立的用户* drwxrwxrwx* 第1位:d表示文件夹,-表示文件* 第2-4位:rwx,表示这个文件的拥有者(创建这个文件的应用) ...

  8. 对称加密和分组加密中的四种模式(ECB、CBC、CFB、OFB)

    一. AES对称加密: AES加密 分组 二. 分组密码的填充 分组密码的填充 e.g.: PKCS#5填充方式 三. 流密码:   四. 分组密码加密中的四种模式: 3.1 ECB模式 优点: 1. ...

  9. OAuth2简易实战(一)-四种模式

    1. OAuth2简易实战(一)-四种模式 1.1. 授权码授权模式(Authorization code Grant) 1.1.1. 流程图 1.1.2. 授权服务器配置 配置授权服务器中 clie ...

随机推荐

  1. 接口鉴权,提供给第三方调用的接口,进行sign签名

    //场景:公司要跟第三方公司合作,提供接口给对方对接,这样需要对接口进行授权,不然任何人都可以调我们公司的接口,会导致安全隐患: 思路: 在每个接口请求参数都带上ApiKey 和sign签名: 我们在 ...

  2. 常见加密算法的 JS 实现

    前言 为破解前端加密做准备,先了解一些常见的加密算法 分类 对称加密 采用单钥密码系统的加密方法,同一个密钥可以同时用作信息的加密和解密,这种加密方法称为对称加密,也称为单密钥加密. DES DES ...

  3. Windows 无法验证此设备所需的驱动程序的数字签名”的问题

    转载: 1.https://jingyan.baidu.com/article/375c8e19c2b25b25f2a229a3.html 2. https://jingyan.baidu.com/a ...

  4. 给Python IDLE添加行号显示

    转载:https://blog.csdn.net/howard2005/article/details/104112297 文章目录一.引出问题1.Spyder编辑Python程序能显示行号2.Pyt ...

  5. 使用HTML的基本结构创建网页

    1.       网页的扩展名--html或htm 2.       如何新建网页? 步骤1: 在电脑的空白处,右键选择-->新建--文本文档 步骤2: 把txt的扩展名,改成html或htm, ...

  6. 为了省钱,我用1天时间把PHP学了!

    作者:小傅哥 博客:https://bugstack.cn 沉淀.分享.成长,让自己和他人都能有所收获! 一.前言 你在通往架构师的路上吗? 程序员这个行业就像是在不断的打怪升级,突破每一阶段的瓶颈期 ...

  7. xxe 新手学习记录

    在做某题时遇到了xxe漏洞,学习+记录 这里因为环境暂时关了,现在复现不了,所以在网络上又找到了一些xxe题目环境 这里有 PikaChu靶场里的xxe环境,这个环境可以在BUUCTF里开,但是这里我 ...

  8. MonkeyRunner+Python自动化测试一

    MonkeyRunner介绍 1.monkeyrunner 工具提供了一个 API,用于编写可从 Android 代码外部控制 Android 设备或模拟器的程序.使用 monkeyrunner,您可 ...

  9. markdown的基本使用

    1.什么是markdown? markdown是一种轻量级的标记语言 可以转换为html/xhtml和其它格式 可读.直观.学习成本低 当你学会使用markdown编写文档时,你会感觉自己发现了一个新 ...

  10. C语言实现和 *.ini文件。

    本文之前由于技术不到位,写的比较挫,最近花了大半天时间写了一个高级点的版本. 这里是我写的代码,已经上传到github了.跳转到github 主要是使用了链表保存ini文件的内容,在程序运行最初会初始 ...