SWM32系列教程7-I2C及其应用

2023-10-30

72ca8b6f150583353d76767fff07b128.jpeg

SWM32S单片机有2个I2C外设,其特点如下:

    1. 支持最高1MHZ速率主机模式

    2. 支持最高400KHZ速率从机模式

    3. 支持7位或10位地址

    4. 波特率可配置

    5. 支持中断功能

今天就以驱动电容触摸芯片GT911为例,介绍一下I2C模块的使用。

配置I2C之前,首先要配置一下端口映射,这里使用GPIOA9和GPIOA10,使能端口上拉功能(注意该单片机不是所有端口支持内部上拉功能)。

然后配置I2C为主机模式,地址为7位,时钟频率400K,不使能中断。程序如下:

void i2c_initialization(void)
{
  I2C_InitStructure I2C_initStruct;


  PORT_Init(PORTA, PIN10, FUNMUX0_I2C0_SCL, 1);  //GPIOA.10配置为I2C0 SCL引脚
  PORT->PORTA_PULLU |= (1 << PIN10);        //必须使能上拉,用于模拟开漏
  PORT_Init(PORTA, PIN9, FUNMUX1_I2C0_SDA, 1);  //GPIOA.9配置为I2C0 SDA引脚
  PORT->PORTA_PULLU |= (1 << PIN9);        //必须使能上拉,用于模拟开漏


  I2C_initStruct.Master = 1;
  I2C_initStruct.Addr7b = 1;
  I2C_initStruct.MstClk = 400000;
  I2C_initStruct.MstIEn = 0;
  I2C_Init(I2C0, &I2C_initStruct);


  I2C_Open(I2C0);
}

再看一下I2C结构体的定义,里面还有一些从机的成员变量。从机模式用的比较少,这里就不做介绍了。

typedef struct {
  uint8_t  Master;    //1 主机模式
  uint8_t  Addr7b;    //1 7位地址     0 10位地址


  uint32_t MstClk;    //主机传输时钟频率
  uint8_t  MstIEn;    //主机模式中断使能


  uint16_t SlvAddr;    //从机地址
  uint8_t  SlvRxEndIEn;  //从机接收完成中断使能
  uint8_t  SlvTxEndIEn;  //从机发送完成中断使能
  uint8_t  SlvSTADetIEn;  //从机检测到起始中断使能
  uint8_t  SlvSTODetIEn;  //从机检测到终止中断使能
  uint8_t  SlvRdReqIEn;  //从机接收到读请求中断使能
  uint8_t  SlvWrReqIEn;  //从机接收到写请求中断使能
} I2C_InitStructure;

I2C读写相关的函数有以下几个。顺便说一句,官方的库函数基本上都有中文注释,这一点比较友好。

uint8_t I2C_Start(I2C_TypeDef * I2Cx, uint8_t addr);
void I2C_Stop(I2C_TypeDef * I2Cx);
uint8_t I2C_Write(I2C_TypeDef * I2Cx, uint8_t data);
uint8_t I2C_Read(I2C_TypeDef * I2Cx, uint8_t ack);

使用时,按照芯片定义的时序调用相关函数即可。

一般的I2C器件写数据流程为:

  1. 启动I2C,发送器件地址

  2. 发送寄存器地址(如果是EEPROM,则是存储地址)

  3. 发送寄存器数据(如果是EEPROM,则是存储的数据)

  4. 停止I2C

读数据流程为:

  1. 启动I2C,发送器件地址

  2. 发送寄存器地址(如果是EEPROM,则是存储地址)

  3. 重新启动I2C,发送器件地址

  4. 读取寄存器数据(前面读取发送ACK,最后一次发送NACK)

  5. 停止I2C

GT911读写寄存器函数如下:

//功能说明:  读GT911寄存器
static uint8_t GT911_RdReg(uint16_t reg, uint8_t *buf, uint8_t len)
{
    uint8_t i;
    uint8_t ack;


    ack = I2C_Start(I2C0, (DEV_ADDR << 1) | 0);
    if (ack == 0)
        goto rd_fail;


    ack = I2C_Write(I2C0, reg >> 8);
    if (ack == 0)
        goto rd_fail;


    ack = I2C_Write(I2C0, reg & 0XFF);
    if (ack == 0)
        goto rd_fail;


    ack = I2C_Start(I2C0, (DEV_ADDR << 1) | 1); //ReStart
    if (ack == 0)
        goto rd_fail;


    for (i = 0; i < len - 1; i++)
    {
        buf[i] = I2C_Read(I2C0, 1);
    }
    buf[i] = I2C_Read(I2C0, 0);


    I2C_Stop(I2C0);
    delay();
    return 1;


rd_fail:
    I2C_Stop(I2C0);
    delay();
    return 0;
}
//功能说明:  写GT911寄存器
static uint8_t GT911_WrReg(uint16_t reg, uint8_t *buf, uint8_t len)
{
    uint8_t i;
    uint8_t ack;


    ack = I2C_Start(I2C0, (DEV_ADDR << 1) | 0);
    if (ack == 0)
        goto wr_fail;


    ack = I2C_Write(I2C0, reg >> 8);
    if (ack == 0)
        goto wr_fail;


    ack = I2C_Write(I2C0, reg & 0XFF);
    if (ack == 0)
        goto wr_fail;


    for (i = 0; i < len; i++)
    {
        ack = I2C_Write(I2C0, buf[i]);
        if (ack == 0)
            goto wr_fail;
    }


    I2C_Stop(I2C0);
    delay();
    return 1;


wr_fail:
    I2C_Stop(I2C0);
    delay();
    return 0;
}

推荐阅读:

UART波特率对时钟精度的要求有多高?

PCB大电流设计方法简介

超级电容有什么用?

   欢迎关注公众号"嵌入式技术开发",大家可以后台给我留言沟通交流。如果觉得该公众号对你有所帮助,也欢迎推荐分享给其他人。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

SWM32系列教程7-I2C及其应用 的相关文章

随机推荐

  • Unity3D 鼠标控制角色移动与奔跑

    最新补充 一般在做鼠标选择时是从摄像机向目标点发送一条射线 然后取得射线与对象相交的点来计算3D目标点 后来在开发中发现了一个问题 射线被别的对象挡住了 就是如果主角的前面有别的游戏对象挡着 此时如果使用射线的原理 鼠标选择被档的对象 这样
  • Java高效开发-远程debug

    1 前言 这怎么回事 在本地还好好 放到服务器就不行了 这该怎么排查 日志也看不出来啥呀 日常开发中经常会出现这种问题 这时候就可以尝试idea远程debug的模式试试 2 使用 1 环境 idea2021 2 idea配置 重点 将自动生
  • 解决Could not find artifact com.oracle:ojdbc7:pom:12.1.0.2 的方案

    1 试了很多方法 不行 2 最终方案 使用私服nexus解决 3 idea创建maven项目 引入lib文件夹 3 1 打包后上传到私服 坐标为
  • Windows10+Python3.6+创建虚拟环境+pycharm+mySQL+flask (一)

    1 安装Python3 6 首先下载python3 6 https www python org getit 在官网上 下下来之后可以在你的下载路径里面找到 我是64位的操作系统 双击安装 这里注意一下要选择 Add Python3 6 t
  • umi——02——mook和反向代理(跨域)

    1 测试mock的简单使用 首先我们在mock文件夹创建一个文件 文件名随便取 写上这样一段代码 代表Get请求 在登录组件Login中发起请求 启动项目 并在项目的url地址输入 users 就可以看到 2 登录案例 api js exp
  • Linux磁盘配额配置

    磁盘配额配置 1 理解磁盘配额的作用 2 掌握磁盘配额工具 3 掌握磁盘配额配置的方法 任务 账号为user 密码为123456的用户磁盘限额情况如下 user用户能够取得80KB的磁盘使用量 hard 文件数量为5个 只要容量使用超过30
  • java 文件下载进度条_下载文件时显示动态的进度条(前端easyUI,后台java)

    最近有点闲 我们的架构师让我在文件下载时显示进度条 咳咳 自从组里来了前端妹纸后 好久没写前端代码了 架构师推荐的用监听器 链接找不到了 实现得有点复杂 我没太看懂 继续百度 看到了 在下载时计算进度 然后把进度放到session中 另外写
  • 查看哪个进程占用了8005端口,并杀死占用端口的进程。

    查看哪个进程占用了8005端口 netstat ano findstr 8005 返回进程号 通过进程号杀死占用端口的进程 taskkill PID 19288 F 杀死该进程 F是强制删除
  • C++—返回值优化

    返回值优化 Return value optimization 缩写为RVO 是C 的一项编译优化技术 即删除保持函数返回值的临时对象 这可能会省略两次复制构造函数 当一个函数返回一个对象实例 一个临时对象将被创建并通过复制构造函数把目标对
  • 这些Android面试题,成就你高薪就业。

    前言 这些题目都是面试必答题 看看你还有哪些是没有掌握到的 1 说下你所知道的设计模式与使用场景 建造者模式 观察者模式 代理模式 门面模式 单例模式 生产者消费者模式 2 Java语言的特点与OOP思想 这个通过对比来描述 比如面向对象和
  • Leetcode 95. 不同的二叉搜索树 II

    文章目录 题目 代码 9 21 首刷看解析 题目 Leetcode 95 不同的二叉搜索树 II 代码 9 21 首刷看解析 class Solution public vector
  • vue实现动态路由--后台返回路由表(并解决页面刷新,路由找不到的问题)

    先大致说一下自己的思路 其实后台返回的权限表跟我们前端自己配置的路由格式是差不多的 格式可以跟后台沟通 我们需要做的是根据后台返回的路由 然后进行遍历 生成一个本地的路由表 然后利用Router addRouters 这个方法 把我们新生成
  • Jmeter-Android手机端脚本录制

    温馨提示 电脑和手机在同一网络段上 1 打开Jmeter工具 新建一个HTTP代理服务器 2 然后再新建一个线程组 3 在线程组中添加录制控制器 4 打开模拟器 设置 WiFi 长按 修改网络
  • 辅助模块加速收敛,精度大幅提升 移动端实时的NanoDet-Plus来了

    Nanodet目标检测模型完成自动捡球机器人 从零开始 带你用Nanodet目标检测模型完成自动捡球机器人 古月居 开源地址 https github com Coolog Nanodet Robot PathPlanning 作者提出 N
  • 技术分享|SQL和 NoSQL数据库之间的差异:MySQL(VS)MongoDB

    技术分享 SQL和 NoSQL数据库之间的差异 什么是SQL和NoSQL 一 什么是SQL 二 什么是NoSQL SQL VS NoSQL 针对SQL和NoSQL的区别 将基于不同的方面进行比较 MySQL VS MongoDB 在当今市场
  • forEach()退出循环的方法

    在for循环中退出循环有3种方式 return 终止 break 退出整个循环 continue 退出当次循环 forEach 只能识别上面三种退出循环中的return 其它都识别不了 且return在forEach 中相当于continu
  • ThreadLocal失效

    在JDK中 解决线程冲突问题 有两种解决方案 l 给临界区加锁 l 本地化临界区 第一种解决方案的典型代表是Synchonized 第二种的典型代表是ThreadLocal 而CopyOnWrite是这两种方案的融合 ThreadLocal
  • Arduino通过L298N红板控制板控制直流电机

    在Arduino论坛上看到很多人都做过智能小车 有两轮的 有四轮的 功能也是多种多样 有寻迹 壁障 无线遥控 红外遥控的 其实小车就是个底盘或者载体 然后可以根据需要向小车上加功能模块 于是我在淘宝上买了一个四轮小车的架子 里面包括四个轮子
  • python解包的概念_如何以编程方式为解包结构?

    我试图用Python读取和解析一个二进制文件 在 问题是文件中的数据可以是little endian或big endian格式 也可以是32位或64位的值 在文件头中有几个字节指定数据格式和大小 假设我已经读过这些 并且知道格式和大小 然后
  • SWM32系列教程7-I2C及其应用

    SWM32S单片机有2个I2C外设 其特点如下 支持最高1MHZ速率主机模式 支持最高400KHZ速率从机模式 支持7位或10位地址 波特率可配置 支持中断功能 今天就以驱动电容触摸芯片GT911为例 介绍一下I2C模块的使用 配置I2C之