STM32模拟I2C通讯的驱动程序

news/2025/1/14 1:52:33/

目录

STM32模拟I2C通讯的驱动程序

开发环境

引脚连接

驱动程序


STM32模拟I2C通讯的驱动程序

开发环境
立创天空星开发板、主控芯片为STM32F407VxT6
引脚连接
使用stm32的PB9引脚模拟I2C时钟线SCL、PB8引脚模拟I2C数据线SDA
驱动程序
i2c.h文件如下:
#ifndef _I2C_H
#define _I2C_H#include "stm32f4xx.h"//端口宏定义
#define RCC_I2C_GPIO          RCC_AHB1Periph_GPIOB
#define PORT_I2C_GPIO         GPIOB#define GPIO_SDA             GPIO_Pin_8
#define GPIO_SCL             GPIO_Pin_9//设置SDA输出模式
#define SDA_OUT()   {        \GPIO_InitTypeDef  GPIO_InitStructure; \GPIO_InitStructure.GPIO_Pin = GPIO_SDA; \GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT; \GPIO_InitStructure.GPIO_OType = GPIO_OType_PP; \GPIO_InitStructure.GPIO_Speed = GPIO_Speed_100MHz; \GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_NOPULL; \GPIO_Init(PORT_I2C_GPIO, &GPIO_InitStructure); \}
//设置SDA输入模式
#define SDA_IN()    {        \GPIO_InitTypeDef  GPIO_InitStructure; \GPIO_InitStructure.GPIO_Pin = GPIO_SDA; \GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN; \GPIO_InitStructure.GPIO_OType = GPIO_OType_PP; \GPIO_InitStructure.GPIO_Speed = GPIO_Speed_100MHz; \GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_NOPULL; \GPIO_Init(PORT_I2C_GPIO, &GPIO_InitStructure); \}
//获取SDA引脚的电平
#define SDA_GET()       GPIO_ReadInputDataBit(PORT_I2C_GPIO, GPIO_SDA)//SDA与SCL输出高低电平
#define SDA(x)          GPIO_WriteBit(PORT_I2C_GPIO, GPIO_SDA, (x?Bit_SET:Bit_RESET) )
#define SCL(x)          GPIO_WriteBit(PORT_I2C_GPIO, GPIO_SCL, (x?Bit_SET:Bit_RESET) )//模拟I2C引脚初始化
void I2C_GPIO_Init(void);//I2C起始时序
void I2C_Start(void);//I2C停止时序
void I2C_Stop(void);//主机发送应答或者非应答信号
void I2C_Send_Ack(unsigned char ack);//主机等待从机应答
unsigned char I2C_WaitAck(void);//主机发送一个字节数据
void Send_Byte(uint8_t dat);//主机接收一个字节数据
unsigned char Read_Byte(void);#endif
i2c.c文件如下:
#include "i2c.h"/******************************************************************* 函 数 名 称:I2C_GPIO_Init* 函 数 说 明:模拟IIC引脚初始化* 函 数 形 参:无* 函 数 返 回:无* 备       注:无
******************************************************************/
void I2C_GPIO_Init(void)
{RCC_AHB1PeriphClockCmd(RCC_I2C_GPIO, ENABLE); // 使能GPIO时钟GPIO_InitTypeDef  GPIO_InitStructure;GPIO_InitStructure.GPIO_Pin = GPIO_SDA | GPIO_SCL;GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT;GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;GPIO_InitStructure.GPIO_Speed = GPIO_Speed_100MHz;GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_NOPULL;GPIO_Init(PORT_I2C_GPIO, &GPIO_InitStructure);
}/******************************************************************* 函 数 名 称:I2C_Start* 函 数 说 明:IIC起始时序* 函 数 形 参:无* 函 数 返 回:无* 备       注:无
******************************************************************/
void I2C_Start(void)
{SDA_OUT();SCL(1);SDA(0);SDA(1);delay_us(5);SDA(0);delay_us(5);SCL(0);
}/******************************************************************* 函 数 名 称:I2C_Stop* 函 数 说 明:I2C停止信号* 函 数 形 参:无* 函 数 返 回:无* 备       注:无
******************************************************************/
void I2C_Stop(void)
{SDA_OUT();SCL(0);SDA(0);SCL(1);delay_us(5);SDA(1);delay_us(5);
}/******************************************************************* 函 数 名 称:I2C_Send_Ack* 函 数 说 明:主机发送应答或者非应答信号* 函 数 形 参:0发送应答  1发送非应答* 函 数 返 回:无* 备       注:无
******************************************************************/
void I2C_Send_Ack(unsigned char ack)
{SDA_OUT();SCL(0);SDA(0);delay_us(5);if(!ack) SDA(0);else     SDA(1);SCL(1);delay_us(5);SCL(0);SDA(1);
}/******************************************************************* 函 数 名 称:I2C_WaitAck* 函 数 说 明:主机等待从机应答* 函 数 形 参:无* 函 数 返 回:0有应答  1超时无应答* 备       注:无
******************************************************************/
unsigned char I2C_WaitAck(void)
{char ack = 0;unsigned char ack_flag = 10;SCL(0);SDA(1);SDA_IN();SCL(1);while( (SDA_GET()==1) && ( ack_flag ) ){ack_flag--;delay_us(5);}if( ack_flag <= 0 ){I2C_Stop();return 1;	//应答超时返回1}else{SCL(0);SDA_OUT();}return ack;		//正常通讯返回应答
}/******************************************************************* 函 数 名 称:Send_Byte* 函 数 说 明:主机发送一个字节数据* 函 数 形 参:dat要发送的数据* 函 数 返 回:无* 备       注:无
******************************************************************/
void Send_Byte(uint8_t dat)
{int i = 0;SDA_OUT();SCL(0);//拉低时钟开始数据传输for( i = 0; i < 8; i++ ){SDA( (dat & 0x80) >> 7 );delay_us(1);SCL(1);delay_us(5);SCL(0);delay_us(5);dat<<=1;}
}/******************************************************************* 函 数 名 称:Read_Byte* 函 数 说 明:主机接收一个字节数据* 函 数 形 参:无* 函 数 返 回:接收到的数据* 备       注:无
******************************************************************/
unsigned char Read_Byte(void)
{unsigned char i,receive=0;SDA_IN();for(i=0;i<8;i++ ){SCL(0);delay_us(5);SCL(1);delay_us(5);receive<<=1;if(SDA_GET()){receive |= 1;}delay_us(5);}SCL(0);return receive;
}

​ ​


http://www.ppmy.cn/news/1554819.html

相关文章

MySQL | 尚硅谷 | 第10章_创建和管理表

MySQL笔记&#xff1a;第10章_创建和管理表 文章目录 MySQL笔记&#xff1a;第10章_创建和管理表MySQL笔记&#xff1a;第10章_创建和管理表 1. 基础知识1.1 一条数据存储的过程1.2 标识符命名规则1.3 MySQL中的数据类型 2. 创建和管理数据库2.1 创建数据库2.2 使用数据库2.3 修…

EasyPlayer.js播放器如何在iOS上实现低延时直播?

随着流媒体技术的迅速发展&#xff0c;H5流媒体播放器已成为现代网络视频播放的重要工具。其中&#xff0c;EasyPlayer.js播放器作为一款功能强大的H5播放器&#xff0c;凭借其全面的协议支持、多种解码方式以及跨平台兼容性&#xff0c;赢得了广泛的关注和应用。 那么要在iOS上…

178K⭐排名第一计算机面试笔记

&#x1f389;据说字节大佬于18年找工作时做的面试笔记&#xff0c;且斩获了bat、字节、华为、网易等大厂offer&#xff0c;该笔记被认为是极具价值的实战经验分享&#xff01; &#x1f310; CS-Notes&#xff0c;它为像我这样的程序员提供了一个全面的计算机科学知识库。这个…

STM32串口接收与发送(关于为什么接收不需要中断而发生需要以及HAL_UART_Transmit和HAL_UART_Transmit_IT的区别)

一、HAL_UART_Transmit和HAL_UART_Transmit_IT的区别 1. HAL_UART_Transmit_IT&#xff08;非阻塞模式&#xff09;&#xff1a; HAL_UART_Transmit_IT 是非阻塞的传输函数&#xff0c;也就是说&#xff0c;当你调用 HAL_UART_Transmit_IT 时&#xff0c;它不会等到数据完全发…

基于微信小程序的校园二手交易平台系统设计与开发ssm+论文源码调试讲解

第2章 程序开发技术 2.1 Mysql数据库 为了更容易理解Mysql数据库&#xff0c;接下来就对其具备的主要特征进行描述。 &#xff08;1&#xff09;首选Mysql数据库也是为了节省开发资金&#xff0c;因为网络上对Mysql的源码都已进行了公开展示&#xff0c;开发者根据程序开发需…

Pyside6 --Qt设计师--简单了解各个控件的作用之:Buttons

目录 一、BUttons1.1 包含1.2 不同按钮的解释 二、具体应用2.1 Push Button2.2 Tool Button2.3 Radio Button2.4 Check Box2.5 Command Link Button2.6 Dialog Button Box2.6.1 直接显示代码如下2.6.2 可以修改ok&#xff0c;cancel 的内容 今天学习一下工具箱里面的Buttons&am…

(SAST检测规则-8)连接字符串中的硬编码密码

严重等级&#xff1a;高危 缺陷详解&#xff1a; 在构建数据驱动的应用程序时&#xff0c;开发者通常需要通过数据库连接字符串与数据库进行交互。将敏感信息&#xff08;如密码、服务器IP地址或加密密钥&#xff09;硬编码在源代码中会带来以下风险&#xff1a; 信息暴露&a…

计算机视觉:学习指南

一、引言 计算机视觉作为人工智能领域的一个重要分支&#xff0c;致力于让计算机理解和解释视觉信息&#xff0c;近年来取得了令人瞩目的进展&#xff0c;广泛应用于安防监控、自动驾驶、图像编辑、医学影像分析等众多领域。从入门到精通计算机视觉需要系统地学习一系列知识和…