#ifndef _IIC_H
#define _IIC_H #include "stdio.h"
#include "stm32f1xx_hal.h" /* 定义控制 SDA SCL 的宏 标准库版
#define I2C_SDA_UP GPIO_SetBits (GPIOC,GPIO_PIN_8) //SDA高电平
#define I2C_SDA_LOW GPIO_ResetBits(GPIOC,GPIO_PIN_8) //SDA低电平
#define I2C_SCL_UP GPIO_SetBits (GPIOC,GPIO_PIN_9) //SCL高电平
#define I2C_SCL_LOW GPIO_ResetBits(GPIOC,GPIO_PIN_9) //SCL低电平
*/ /* 定义控制 SDA SCL 的宏 HAL库版 */ #define I2C_SDA_UP HAL_GPIO_WritePin(GPIOC,GPIO_PIN_8,GPIO_PIN_SET) //SDA高电平
#define I2C_SDA_LOW HAL_GPIO_WritePin(GPIOC,GPIO_PIN_8,GPIO_PIN_RESET) //SDA低电平
#define I2C_SCL_UP HAL_GPIO_WritePin(GPIOC,GPIO_PIN_9,GPIO_PIN_SET) //SCL高电平
#define I2C_SCL_LOW HAL_GPIO_WritePin(GPIOC,GPIO_PIN_9,GPIO_PIN_RESET) //SCL低电平 /* 获取 SDA SCL 引脚状态,标准库版也是用相同逻辑 */ #define I2C_SDA HAL_GPIO_ReadPin(GPIOC ,GPIO_PIN_8) //获取SDA引脚状态
#define I2C_SCL HAL_GPIO_ReadPin(GPIOC ,GPIO_PIN_9) //获取SCL引脚状态 void iic_stare(void); //* 开始信号
void i2c_ack(void); //* 应答信号
void I2C_No_ack(void); //* 非应答信号
void i2c_stop(void); //* 停止信号
char i2c_wit_ack(void); //* 等待应答
void i2c_send(uint8_t dat); //* 发送数据
uint8_t i2c_read(void); //* 接收数据 void SDA_OUT(void); //* SDA 设置为输出
void SDA_IN(void); //* SDA 设置为输入 void delay_us(uint32_t i); //*延时 #endif
/*****************************************************************************
* *
* File: 软件模拟IIC, HAL库版本,标准库也 *
* 可用,只需要做一些相对应修改即可 *
* *
*****************************************************************************/ #include "iic.h" /*******************************************************************************
* 函 数 名 : i2c_stare
* 函数功能 : iic开始信号,SCL高电平时,SDA出现一个下跳沿表示启动信号
* 输 入 : 无
* 输 出 : 无
*******************************************************************************/
void i2c_stare(void)
{
SDA_OUT();
I2C_SDA_UP;
I2C_SCL_UP;
delay_us();
I2C_SDA_LOW; //启动开始信号
delay_us();
I2C_SCL_LOW; //钳住I2C总线,准备发送或接收数据
} /*******************************************************************************
* 函 数 名 : i2c_stop
* 函数功能 : iic停止信号,SCL高电平时,SDA出现一个上跳沿表示停止信号
* 输 入 : 无
* 输 出 : 无
*******************************************************************************/
void i2c_stop(void)
{
SDA_OUT(); //sda线输出
I2C_SDA_LOW; //发送结束条件的数据信号
I2C_SCL_UP;
delay_us(); //结束条件建立时间大于4μ
I2C_SDA_UP; //发送I2C总线结束信号
delay_us();
I2C_SCL_LOW;
} /*******************************************************************************
* 函 数 名 : i2c_send
* 函数功能 : iic发送数据
* 输 入 : uint8_t dat,要发送的数据
* 输 出 : 无
*******************************************************************************/
void i2c_send(uint8_t dat)
{ unsigned char temp;
SDA_OUT();
for(temp=0x80;temp!=;temp>>=)
{
if((temp & dat)== )
{
I2C_SDA_LOW;
}
else
{
I2C_SDA_UP;
}
delay_us();
I2C_SCL_UP;
delay_us();
I2C_SCL_LOW;
}
} /*******************************************************************************
* 函 数 名 : i2c_read
* 函数功能 : iic接收数据
* 输 入 : 无
* 输 出 : 无
*******************************************************************************/
uint8_t i2c_read(void)
{
unsigned char temp;
unsigned char dat;
I2C_SDA_UP; //释放总线准备接收
SDA_IN();
for(temp=0x80;temp!=;temp>>=)
{
delay_us();
I2C_SCL_UP;
if(I2C_SDA==)
{
dat|=temp;
}
else
{
dat&=~temp;
}
I2C_SCL_LOW;
}
return dat;
} /*******************************************************************************
* 函 数 名 : i2c_wit_ack
* 函数功能 : iic等待应答
* 输 入 : 无
* 输 出 : 0/1,返回1表示无应答信号,返回0表示应答
*******************************************************************************/
char i2c_wit_ack(void)
{ uint8_t con=; I2C_SDA_UP; //释放数据线,准备接收应答
delay_us();
I2C_SCL_UP; //CPU驱动SCL = 1, 此时器件会返回ACK应答
SDA_IN();
delay_us(); while( I2C_SDA ) //CPU读取SDA口线状态
{
con++;
if(con>)
{
i2c_stop();
return ; //无应答信号
}
} I2C_SCL_LOW;
delay_us();
return ; //有应答
} /*******************************************************************************
* 函 数 名 : i2c_ack
* 函数功能 : iic应答信号
* 输 入 : 无
* 输 出 : 无
*******************************************************************************/
void i2c_ack(void)
{
SDA_OUT();
I2C_SDA_LOW;
delay_us();
I2C_SCL_UP; //CPU产生1个时钟
delay_us(); //时钟低电平周期大于4μ
I2C_SCL_LOW; //清时钟线,钳住I2C总线以便继续接收
delay_us();
I2C_SDA_UP; //CPU释放SDA总线
} /*******************************************************************************
* 函 数 名 : I2C_No_ack
* 函数功能 : iic非应答信号
* 输 入 : 无
* 输 出 : 无
*******************************************************************************/
void I2C_No_ack(void)
{
SDA_OUT();
I2C_SDA_UP;
delay_us();
I2C_SCL_UP;
delay_us();
I2C_SCL_LOW;
delay_us();
} /*******************************************************************************
* 函 数 名 : SDA_OUT
* 函数功能 : SDA 设置为输出
* 输 入 : 无
* 输 出 : 无
*******************************************************************************/
void SDA_OUT(void)
{ /* 标准库使用,修改端口引脚可用
GPIO_InitTypeDef GPIO_InitTypeStruct;
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB,ENABLE);
GPIO_InitTypeStruct.GPIO_Mode=GPIO_Mode_Out_PP;
GPIO_InitTypeStruct.GPIO_Pin=GPIO_Pin_7;
GPIO_InitTypeStruct.GPIO_Speed=GPIO_Speed_50MHz;
GPIO_Init(GPIOB,&GPIO_InitTypeStruct);
*/ /* HAL库使用,HAL库注意要把初始化函数的静态标记去掉 */
GPIO_InitTypeDef GPIO_InitStruct;
GPIO_InitStruct.Pin = SDA_Pin; //使用STM3cubemx是定义好的SDA_Pin为GPIO_PIN_8的标签
GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_PP;
GPIO_InitStruct.Pull = GPIO_NOPULL;
GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW;
HAL_GPIO_Init(GPIOC, &GPIO_InitStruct);
} /*******************************************************************************
* 函 数 名 : SDA_IN
* 函数功能 : SDA 设置为输入
* 输 入 : 无
* 输 出 : 无
*******************************************************************************/
void SDA_IN(void)
{ /* 标准库使用,修改端口引脚可用
GPIO_InitTypeDef GPIO_InitTypeStruct;
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB,ENABLE);
GPIO_InitTypeStruct.GPIO_Mode=GPIO_Mode_IN_FLOATING;
GPIO_InitTypeStruct.GPIO_Pin=GPIO_Pin_7;
GPIO_InitTypeStruct.GPIO_Speed=GPIO_Speed_50MHz;
GPIO_Init(GPIOB,&GPIO_InitTypeStruct);
*/ /* HAL库使用, HAL库注意要把初始化函数的静态标记去掉 */
GPIO_InitTypeDef GPIO_InitStruct;
GPIO_InitStruct.Pin = SDA_Pin ; //使用STM3cubemx是定义好的SDA_Pin为GPIO_PIN_8的标签
GPIO_InitStruct.Mode = GPIO_MODE_INPUT;
GPIO_InitStruct.Pull = GPIO_NOPULL;
GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW;
HAL_GPIO_Init(GPIOC, &GPIO_InitStruct);
} /*******************************************************************************
* 函 数 名 : delay_us
* 函数功能 : 延时函数,延时us
* 输 入 : i
* 输 出 : 无
*******************************************************************************/
void delay_us(uint32_t i)
{
uint32_t temp;
SysTick->LOAD=*i; //设置重装数值, 72MHZ时
SysTick->CTRL=0X01; //使能,减到零是无动作,采用外部时钟源
SysTick->VAL=; //清零计数器 do
{
temp=SysTick->CTRL; //读取当前倒计数值
}
while((temp&0x01)&&(!(temp&(<<)))); //等待时间到达 SysTick->CTRL=; //关闭计数器
SysTick->VAL=; //清空计数器
}

该代码,标准库可用,HAL库也可用,只需要代码做一些修改即可!

STM32 软件模拟 IIC 代码,标准库、HAL库可用的更多相关文章

  1. stm32软件模拟IIC读取PX4FLOW光流传感器数据

    这段时间在做全国光电设计大赛,用到了px4的px4flow光流传感器,用软件模拟iic读取数据不定期会导致px4flow死机,查了资料和光流的源码,发现这个光流用了stm32的硬件iic,所以对软件模 ...

  2. STM32 实现内部Flash的读写(HAL库版)

    Flash 中文名字叫闪存,是一种长寿命的非易失性(断电数据不丢失)的存储器.可以对称为块的存储器单元块进行擦写和再编程,在进行写入操作之前必须先执行擦除.一个Nand Flash由多个块(Block ...

  3. GPIO软件模拟IIC时序

    一.MPU6050中的IIC时序 1.1 START和STOP SDA和SCL在高电平时,SDA拉低表示START.SCL拉低,表示可以传输数据. SDA和SCL在低电平时,SDA拉高表示STOP. ...

  4. STM32 的 printf() 函数串口重定向(HAL库标准库都适用)

    1.建立工程 2.核心:添加新文件usar_fputc.c (名字随便自己命名),把文件添加到项目中去 #include "stdio.h" #include "stm3 ...

  5. 51单片机下实现软件模拟IIC通信

    1.IIC协议简易概述 IIC全称Inter-Integrated Circuit (集成电路总线),是由PHILIPS公司在80年代开发的两线式串行总线,用于连接微控制器及其外围设备.IIC属于半双 ...

  6. 软件模拟IIC实现EEPROM

    ....妈的太难.    反正就是控制引脚的高低电平 实现数据的读取....参考 I2C的协议层和物理层的那个几个图,个个信号产生的电平 自己看源码去把. 头疼

  7. STM32之HAL库、标准外设库、LL库(STM32 Embedded Software)-(转载)

    STM32 Embedded Software  工作以来一直使用ST的STM32系列芯片,ST为开发者提供了非常方便的开发库.到目前为止,有标准外设库(STD库).HAL库.LL库 三种.前两者都是 ...

  8. STM32,下载HAL库写的代码后J-Link识别不到芯片,必须要按住复位才能下载?

    问题描述:最近在学STM32的HAL库,据说可以统一STM32江湖,前途无量.最近一段时间参照STM32CubeMX和原子的资料自己学着建了两个HAL库的工程模板,F4的还好说,F1的出现了一个玄学问 ...

  9. STM32 之 HAL库(固件库) _

    1 STM32的三种开发方式 通常新手在入门STM32的时候,首先都要先选择一种要用的开发方式,不同的开发方式会导致你编程的架构是完全不一样的.一般大多数都会选用标准库和HAL库,而极少部分人会通过直 ...

随机推荐

  1. mybatis3中几个@Provider的使用方式

    Mybatis的原身是ibatis,现在已经脱离了apache基金会,新官网是http://www.mybatis.org/.Mybatis3中增加了使用注解来配置Mapper的新特性,这里主要介绍@ ...

  2. RobotFrameWork+APPIUM实现对安卓APK的自动化测试----第二篇【原理】

    http://blog.csdn.net/deadgrape/article/details/50574459 接着上一篇,我们开始聊聊APPIUM的框架和运行模式.废话不多说直接上图. 1.首先自动 ...

  3. mysql点滴_02程序中运行sql语句报字符集问题解决

    程序中运行  "SELECT t.EVENT_TYPE_ID FROM RATABLE_EVENT_TYPE t WHERE t.NAME='帐期末费用转移事件'"  报错 错误码 ...

  4. 王立平--Object-c

    object-c通常写作objective-c或者obj-c,是依据C语言所衍生出来的语言.继承了C语言的特性,是扩充C的面向对象编程语言. 它主要使用于MacOSX和GNUstep这两个使用Open ...

  5. NDK历史版本

    https://developer.android.google.cn/ndk/downloads/older_releases.html https://developer.android.goog ...

  6. mysql事务的开启

    mysql事务的开启 对于一个MYSQL数据库(InnoDB),事务的开启与提交模式无非下面这两种情况: 1>若参数autocommit=0,事务则在用户本次对数据进行操作时自动开启,在用户执行 ...

  7. Linux uname 命令 打印系统信息

    转自:https://www.jb51.net/LINUXjishu/417626.html 1.概述 打印系统信息 2.命令格式 uname [OPTION]... 3.常用命令参数 打印一些系统信 ...

  8. Ubuntu16.04系统安装搜狗输入法

    前言:正常双击.deb软件包安装搜狗输入法会有bug,需要按照下面操作进行消除错误. 一.下载搜狗输入法Linux版软件包 下载地址为:http://pinyin.sogou.com/linux/ , ...

  9. VS自动注释——GhostDoc

    直接上图片,使用步骤是按顺序来的: 安装就不多说了,直接下一步,下一步.直接讲讲如何自定义注释规则 软件下载链接:http://pan.baidu.com/s/1dF5TSel 密码:peuz 链接: ...

  10. linux安装lua

    1,下载lua源码wget http://www.lua.org/ftp/lua-5.3.3.tar.gz或curl -R -O http://www.lua.org/ftp/lua-5.3.3.ta ...