×
嵌入式 > 技术百科 > 详情

stm8s105调试I2C记录

发布时间:2020-06-17 发布时间:
|

最近由于AR项目中调试LCOS需要用到STM8S105的mcu,本次主要是使用模拟I2C。


1.IIC协议简介


 IIC协议这里只做简要介绍,详细介绍可以百度了解,协议相对简单,主要有开始位,停止位,应答位,非应答位。


开始位:当时钟为高,数据线由高变低


停止位:当时钟位高,数据线由低变高。


应答位:第9个时钟到来时,数据线为低。(这里第9个时钟,发送完一个字节,紧接着就是第9个时钟到来)


非应答位,第9个时钟到来时,数据线为高。


2.LCOS协议:


1.发送数据:


单数据发送: 开始位:写地址位(8bit):寄存器地址(16bit):数据(8bit):停止位

多字节发送:开始位:写地址(8bit):寄存器地址(16bit):数据(8bit*N):停止位

2.读取数据:


单字节读取:开始位:写地址(8bit):寄存器地址(16bit):开始位,读地址(8bit):读数据(8bit):停止位


单字节读取:开始位:写地址(8bit):寄存器地址(16bit):开始位,读地址(8bit):读数据(8bit*N):停止位


LCOS驱动源代码:


头文件



#ifndef OP02223_H_

#define OP02223_H_

 

#include "stm8s.h"

#include "stm8s_gpio.h"

 

//lcos driver i2c pin opt

#define LCOS_I2C_SDA_HIGH  GPIO_WriteHigh(GPIOC,GPIO_PIN_7)

#define LCOS_I2C_SDA_LOW   GPIO_WriteLow(GPIOC,GPIO_PIN_7)

#define LCOS_I2C_SCL_HIGH  GPIO_WriteHigh(GPIOC,GPIO_PIN_6)

#define LCOS_I2C_SCL_LOW   GPIO_WriteLow(GPIOC,GPIO_PIN_6)

#define LCOS_I2C_SDA_IN    GPIO_Init(GPIOC,GPIO_PIN_7,GPIO_MODE_IN_PU_NO_IT)

#define LCOS_I2C_SDA_OUT   GPIO_Init(GPIOC,GPIO_PIN_7,GPIO_MODE_OUT_OD_LOW_FAST)

#define LCOS_I2C_SDA_PIN_READ  GPIO_ReadInputPin(GPIOC,GPIO_PIN_7)

 

//LCOS device address

#define LCOS_L_ADDR (0xC8)

#define LCOS_R_ADDR (0xCA)

 

#define LCOS_ACK 1

#define LCOS_NO_ACK 0

 

void LCOS_delay(uint32_t us);

void LCOS_I2C_Start(void);

void LCOS_I2C_Stop(void);

void LCOS_I2C_Ack(void);

void LCOS_I2C_NoAck(void);

uint8_t LCOS_I2C_SendByte(uint8_t data);

uint8_t LCOS_I2C_RecvByte(void);

 

void OP02223_Init(void);

s32 OP02223_I2C_SingleWrite(uint8_t dev_addr,

                             uint16_t reg_addr,

uint8_t data);

s32 OP02223_I2C_BurstWrite(uint8_t dev_addr,

                            uint16_t reg_addr,

uint8_t *data,

uint32_t len);

s32 OP02223_I2C_SingleRead(uint8_t dev_addr,

uint16_t reg_addr,

uint8_t *readData);

s32 OP02223_I2C_BurstRead(uint8_t dev_addr,

uint16_t reg_addr,

uint8_t *readData,

 uint32_t readMaxLen);

源码:


void LCOS_delay(uint32_t us)

{

while(us--);

}

 

void LCOS_I2C_Start(void)

{

LCOS_I2C_SDA_HIGH;

LCOS_delay(5);

LCOS_I2C_SCL_HIGH;

LCOS_delay(5);

LCOS_I2C_SDA_LOW;

LCOS_delay(5);

LCOS_I2C_SCL_LOW;

LCOS_delay(5);

}

 

void LCOS_I2C_Stop(void)

{

LCOS_I2C_SDA_LOW;

LCOS_delay(5);

LCOS_I2C_SCL_HIGH;

LCOS_delay(5);

LCOS_I2C_SDA_HIGH;

LCOS_delay(5);

}

 

void LCOS_I2C_Ack(void)

{

LCOS_I2C_SDA_LOW;

LCOS_delay(5);

LCOS_I2C_SCL_HIGH;

LCOS_delay(5);

LCOS_I2C_SCL_LOW;

LCOS_delay(5);

}

 

void LCOS_I2C_NoAck(void)

{

LCOS_I2C_SDA_HIGH;

LCOS_delay(5);

LCOS_I2C_SCL_HIGH;

LCOS_delay(5);

LCOS_I2C_SCL_LOW;

LCOS_delay(5);

}

 

uint8_t LCOS_I2C_SendByte(uint8_t data)

{

uint8_t status = 0;

uint8_t i = 0;

for (i=0; i < 8; i++)

{

if (data &0x80){

LCOS_I2C_SDA_HIGH;

}

else{

LCOS_I2C_SDA_LOW;

}

LCOS_I2C_SCL_HIGH;

LCOS_delay(5);

LCOS_I2C_SCL_LOW;

LCOS_delay(5);

data <<=1;

}

   LCOS_I2C_SCL_LOW;

LCOS_delay(5);

LCOS_I2C_SDA_IN;

LCOS_delay(5);

LCOS_I2C_SCL_HIGH;

// LCOS_delay(5);

if (!LCOS_I2C_SDA_PIN_READ){

status = LCOS_ACK;

}

else{

status = LCOS_NO_ACK;

}

LCOS_delay(5);

LCOS_I2C_SCL_LOW;

LCOS_delay(5);

LCOS_I2C_SDA_OUT;

LCOS_delay(5);

return status;

}

 

uint8_t LCOS_I2C_RecvByte(void)

{

uint8_t i =0;

uint8_t recvData = 0;

//LCOS_I2C_SDA_HIGH;

LCOS_I2C_SDA_IN;

LCOS_delay(5);

for (i=0; i < 8; i++)

{

recvData <<= 1;

LCOS_I2C_SCL_HIGH;

LCOS_delay(2);

if (LCOS_I2C_SDA_PIN_READ){

recvData |= 0x01;

}

// else{

// recvData &= 0xfe;

// }

LCOS_delay(5);

LCOS_I2C_SCL_LOW;

LCOS_delay(5);

}

LCOS_I2C_SDA_OUT;

LCOS_delay(5);

return recvData;

}

 

static void OP02223_SetReg(void)

{

    uint16_t addr = 0;

uint8_t setValue = 0;

volatile s32 i = 0;

for (i = 3; i < sizeof(reg_value);i++)

{

OP02223_I2C_SingleWrite(LCOS_L_ADDR,i,reg_value[i]);

// printf("device_addr:%x,reg_addr:%x,setValue:%x.rn"

//       ,LCOS_L_ADDR,i,reg_value[i]);

// OP02223_I2C_SingleRead(LCOS_L_ADDR,i,&setValue);

// printf("device_addr:%x,reg_addr:%x,setValue:%x.rn"

//       ,LCOS_L_ADDR,i,setValue);

OP02223_I2C_SingleWrite(LCOS_R_ADDR,i,reg_value[i]);

// printf("device_addr:%x,reg_addr:%x,setValue:%x.rn"

//       ,LCOS_R_ADDR,i,reg_value[i]);

// OP02223_I2C_SingleRead(LCOS_R_ADDR,i,&setValue);

// printf("device_addr:%x,reg_addr:%x,setValue:%x.rn"

//       ,LCOS_L_ADDR,i,setValue);

//printf("------------------------------------------------rn");

}

 

 return;

}

 

static void OP02223_Test_Deal(void)

{

 LCOS_delay(200);

GPIO_Init(GPIOC,GPIO_PIN_6|GPIO_PIN_7,GPIO_MODE_IN_PU_NO_IT);

 LCOS_delay(200);

}

 

void OP02223_Init(void)

{

GPIO_DeInit(GPIOD); 

   GPIO_DeInit(GPIOC);  

GPIO_Init(GPIOD,GPIO_PIN_3,GPIO_MODE_IN_PU_NO_IT);//输入

GPIO_Init(GPIOC,GPIO_PIN_1|GPIO_PIN_3|GPIO_PIN_6|GPIO_PIN_7,GPIO_MODE_OUT_PP_LOW_FAST);

//LCOS_delay(100);

//while (!GPIO_ReadInputPin(GPIOD,GPIO_PIN_3)); //PD3=1

/* while (1)

{

if (GPIO_ReadInputPin(GPIOD,GPIO_PIN_3))

{

break;

}

else

{

 delay(1);

}

}*/

// GPIO_WriteHigh(GPIOC,GPIO_PIN_1);

LCOS_delay(200);

GPIO_WriteLow(GPIOC,GPIO_PIN_1);

GPIO_WriteLow(GPIOC,GPIO_PIN_3);

LCOS_delay(200);

LCOS_I2C_SDA_HIGH;

LCOS_I2C_SCL_HIGH;

LCOS_delay(200);

 

   OP02223_SetReg();

// OP02223_Test_Deal();

}

 

s32 OP02223_I2C_SingleWrite(uint8_t dev_addr,

                             uint16_t reg_addr,

uint8_t data)

{

uint8_t status;

uint32_t i = 0;

   uint8_t buf[4] = {0};

buf[0] = dev_addr;

buf[1] = reg_addr>>8;

buf[2] = (uint8_t)(reg_addr&0xFF);

buf[3] = data;

LCOS_I2C_Start();

for (i = 0; i <4; i++)

{

   status = LCOS_I2C_SendByte(buf[i]);

if (!status)//1error,0ok.

{

// I2C_Stop(LCOS_I2C);

return -1;

}

}

// status = sendByteNoAck(LCOS_I2C,buf[3]);

// status = sendByte(LCOS_I2C,buf[3]);

LCOS_I2C_Stop();

return 0;

}

 

s32 OP02223_I2C_BurstWrite(uint8_t dev_addr,

                            uint16_t reg_addr,

uint8_t *data,

uint32_t len)

{

bool status;

uint32_t i = 0;

   uint8_t buf[3] = {0};

buf[0] = dev_addr;

buf[1] = reg_addr>>8;

buf[2] = (uint8_t)(reg_addr&0xFF);

LCOS_I2C_Start();

for (i = 0; i < 3; i++)

{

   status = LCOS_I2C_SendByte(buf[i]);

if (status)//1error,0ok.

{

return -1;

}

}

for (i = 0; i < len; i++)

{

status = LCOS_I2C_SendByte(data[i]);

if (!status)//1error,0ok.

{

return -1;

}

}

// I2C_NoAck(LCOS_I2C);

LCOS_I2C_Stop();

return 0;

}

 

s32 OP02223_I2C_SingleRead(uint8_t dev_addr,

uint16_t reg_addr,

uint8_t *readData)

{

bool status;

uint32_t i = 0;

   uint8_t buf[3] = {0};

buf[0] = dev_addr;

buf[1] = reg_addr>>8;

buf[2] = (uint8_t)(reg_addr&0xFF);

LCOS_I2C_Start();

for (i = 0; i < 3; i++)

{

   status = LCOS_I2C_SendByte(buf[i]);

if (!status)//1error,0ok.

{

return -1;

}

}

 

LCOS_I2C_Start();//restart i2c

status = LCOS_I2C_SendByte(dev_addr+1);//send read address

if (!status)//1error,0ok.

{

return -1;

}

*readData = LCOS_I2C_RecvByte();

LCOS_I2C_NoAck();

LCOS_I2C_Stop();

return 0;

}

s32 OP02223_I2C_BurstRead(uint8_t dev_addr,

uint16_t reg_addr,

uint8_t *readData,

uint32_t readMaxLen)

{

bool status;

uint32_t i = 0;

   uint8_t buf[3] = {0};

buf[0] = dev_addr;

buf[1] = reg_addr>>8;

buf[2] = (uint8_t)(reg_addr&0xFF);

LCOS_I2C_Start();

for (i = 0; i < 3; i++)

{

   status = LCOS_I2C_SendByte(buf[i]);

if (!status)//1error,0ok.

{

return -1;

}

}

LCOS_I2C_Start();//restart i2c

status = LCOS_I2C_SendByte(dev_addr+1);//send read address

if (status)//1error,0ok.

{

return -1;

}

for (i=0; i

{

   *(readData+i) = LCOS_I2C_RecvByte();

LCOS_I2C_Ack();

   }

if (i == readMaxLen-1)

{  

   *(readData+i) = LCOS_I2C_RecvByte();

 LCOS_I2C_NoAck();

   }

LCOS_I2C_Stop();

return 0;

}

相对来说比较简单基础,完毕。


以此开始,记录自己工作中的点滴,加深写作能力。



『本文转载自网络,版权归原作者所有,如有侵权请联系删除』

热门文章 更多
实时控制.安全.如何加速实现未来工厂落地?