.h文件
#ifndef __BSP_IIC_H__
#define __BSP_IIC_H__
#include "stm32f4xx.h"
//#include "i2c_soft.h"
typedef enum
{
ADDR_WIDE_8 = 0, //地址为8位宽度
ADDR_WIDE_16 = 1, //地址为16位宽度
} IIC_Addr_Type;
typedef struct IIC_Type
{
//属性
uint32_t RCC_SCL_APB2Periph;
uint32_t RCC_SDA_APB2Periph;
GPIO_TypeDef* GPIOx_SCL;
GPIO_TypeDef* GPIOx_SDA;
uint16_t SCL_Pin_x;
uint16_t SDA_Pin_x;
//操作
uint8_t (*IIC_Init)(const struct IIC_Type*); //IIC_Init
uint8_t (*IIC_Start)(const struct IIC_Type*); //IIC_Start
uint8_t (*IIC_Stop)(const struct IIC_Type*); //IIC_Stop
uint8_t (*IIC_Wait_Ack)(const struct IIC_Type*); //IIC_Wait_ack,返回wait失败或是成功
uint8_t (*IIC_Ack)(const struct IIC_Type*); //IIC_Ack,IIC发送ACK信号
uint8_t (*IIC_NAck)(const struct IIC_Type*); //IIC_NAck,IIC发送NACK信号
uint8_t (*IIC_Send_Byte)(const struct IIC_Type*,uint8_t); //IIC_Send_Byte,入口参数为要发送的字节
uint8_t (*IIC_Read_Byte)(const struct IIC_Type*); //IIC_Send_Byte
uint8_t (*delay_us)(uint32_t); //us延时
}IIC_TypeDef;
// #ifndef ADDR_WIDE_8
// #define ADDR_WIDE_8 0
// #endif
// #ifndef ADDR_WIDE_16
// #define ADDR_WIDE_16 1
// #endif
typedef struct EEPROM_Type
{
IIC_TypeDef IIC;
//属性
uint32_t RCC_Lock_APB2Periph; //LOCK引脚时钟
GPIO_TypeDef* GPIOx_Lock;
uint16_t Lock_Pin_x;
uint8_t addr_wide; //ADDR_WIDE_8 - 8地址宽度;ADDR_WIDE_16 -- 16地址宽度
uint8_t device_addr; //设备地址
uint16_t page_size; //页大小
uint32_t max_size; //最大字节
uint8_t (*EEProm_Init)(const struct EEPROM_Type*); //初始化IIC
uint8_t (*EEProm_Soft_Reset)(const struct EEPROM_Type*); //EEPROM软件复位
uint8_t (*EEProm_Unlock)(const struct EEPROM_Type*); //EEPROM解锁
uint8_t (*EEProm_Lock)(const struct EEPROM_Type*); //EEPROM上锁
uint8_t (*EEProm_NRead)(const struct EEPROM_Type*, uint32_t, uint8_t*, uint16_t); //EEPROM读取N个字节
uint8_t (*EEProm_NWrite)(const struct EEPROM_Type*, uint32_t, uint8_t*, uint16_t); //EEPROM写入N个字节
}EEPROM_Type_t;
void BL24CM1A_Init(void);
uint8_t BL24CM1A_Write_Data(uint32_t WriteAddress, uint8_t* pBuffer, uint16_t length);
uint8_t BL24CM1A_Read_Data(uint32_t readaddress, uint8_t* pBuffer, uint16_t length);
#endif /* __BSP_IIC_*/
.c
#include "bsp_iic.h"
#include "sys_timer.h"
#include "global_includes.h"
#ifndef true
#define true 1
#endif
#ifndef false
#define false 0
#endif
#define IIC_DELAY_us 5
//设置SCL电平
static void IIC_SCL(const struct IIC_Type* IIC_Type_t,int n)
{
if(n == 1)
{
GPIO_SetBits(IIC_Type_t->GPIOx_SCL, IIC_Type_t->SCL_Pin_x);
}
else
{
GPIO_ResetBits(IIC_Type_t->GPIOx_SCL, IIC_Type_t->SCL_Pin_x);
}
}
//设置SDA电平
static void IIC_SDA(const struct IIC_Type* IIC_Type_t,int n)
{
if(n == 1)
{
GPIO_SetBits(IIC_Type_t->GPIOx_SDA, IIC_Type_t->SDA_Pin_x);
}
else
{
GPIO_ResetBits(IIC_Type_t->GPIOx_SDA, IIC_Type_t->SDA_Pin_x);
}
}
//读取SDA电平
static uint8_t READ_SDA(const struct IIC_Type* IIC_Type_t)
{
return GPIO_ReadInputDataBit(IIC_Type_t->GPIOx_SDA,IIC_Type_t->SDA_Pin_x); //读取SDA电平
}
//初始化
static uint8_t IIC_Init_t(const struct IIC_Type* IIC_Type_t)
{
RCC_AHB1PeriphClockCmd(IIC_Type_t->RCC_SCL_APB2Periph, ENABLE);
RCC_AHB1PeriphClockCmd(IIC_Type_t->RCC_SDA_APB2Periph, ENABLE);
GPIO_InitTypeDef GPIO_InitStructure;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT;
GPIO_InitStructure.GPIO_OType = GPIO_OType_OD;
GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP;
GPIO_InitStructure.GPIO_Pin = IIC_Type_t->SDA_Pin_x;
GPIO_Init(IIC_Type_t->GPIOx_SDA, &GPIO_InitStructure);
GPIO_InitStructure.GPIO_Pin = IIC_Type_t->SCL_Pin_x;
GPIO_Init(IIC_Type_t->GPIOx_SCL, &GPIO_InitStructure);
IIC_SCL(IIC_Type_t, 1);
IIC_SDA(IIC_Type_t, 1);
return true;
}
//起始信号
static uint8_t IIC_Start_t(const struct IIC_Type* IIC_Type_t)
{
IIC_SDA(IIC_Type_t, 1);
IIC_SCL(IIC_Type_t, 1);
IIC_Type_t->delay_us(IIC_DELAY_us);
if(!READ_SDA(IIC_Type_t))
{
return false; //SDA线为低电平则总线忙,退出
}
IIC_SDA(IIC_Type_t, 0);
IIC_Type_t->delay_us(IIC_DELAY_us);
if(READ_SDA(IIC_Type_t))
{
return false; //SDA线为高电平则总线出错,退出
}
IIC_SCL(IIC_Type_t, 0);
IIC_Type_t->delay_us(IIC_DELAY_us);
return true;
}
//停止信号
static uint8_t IIC_Stop_t(const struct IIC_Type* IIC_Type_t)
{
IIC_SCL(IIC_Type_t, 0);
IIC_Type_t->delay_us(IIC_DELAY_us);
IIC_SDA(IIC_Type_t, 0);
IIC_Type_t->delay_us(IIC_DELAY_us);
IIC_SCL(IIC_Type_t, 1);
IIC_Type_t->delay_us(IIC_DELAY_us);
IIC_SDA(IIC_Type_t, 1);
IIC_Type_t->delay_us(IIC_DELAY_us);
}
static uint8_t IIC_Wait_Ack_t(const struct IIC_Type* IIC_Type_t)
{
uint8_t i;
IIC_SCL(IIC_Type_t, 0);
IIC_Type_t->delay_us(IIC_DELAY_us);
IIC_SDA(IIC_Type_t, 1);
IIC_Type_t->delay_us(IIC_DELAY_us);
IIC_SCL(IIC_Type_t, 1);
IIC_Type_t->delay_us(IIC_DELAY_us);
for(i = 0; i < 30; i++)
{
if(READ_SDA(IIC_Type_t))
{
IIC_Type_t->delay_us(IIC_DELAY_us);
}
else
{
break;
}
}
IIC_SCL(IIC_Type_t, 0);
if(i >= 30)
{
IIC_Type_t->IIC_Stop(IIC_Type_t);
return false;
}
return true;
}
/**************************************************************************
*功能 :IICack
*函数名 : I2C_Ack
*输入 :iic(iic序号)
*返回 :无
**************************************************************************/
static uint8_t IIC_Ack_t(const struct IIC_Type* IIC_Type_t)
{
IIC_SCL(IIC_Type_t, 0);
IIC_Type_t->delay_us(IIC_DELAY_us);
IIC_SDA(IIC_Type_t, 0);
IIC_Type_t->delay_us(IIC_DELAY_us);
IIC_SCL(IIC_Type_t, 1);
IIC_Type_t->delay_us(IIC_DELAY_us);
IIC_SCL(IIC_Type_t, 0);
IIC_Type_t->delay_us(IIC_DELAY_us);
}
/**************************************************************************
*功能 :IICnoack
*函数名 : I2C_NoAck
*输入 :iic(iic序号)
*返回 :无
**************************************************************************/
static uint8_t IIC_NAck_t(const struct IIC_Type* IIC_Type_t)
{
IIC_SCL(IIC_Type_t, 0);
IIC_Type_t->delay_us(IIC_DELAY_us);
IIC_SDA(IIC_Type_t, 1);
IIC_Type_t->delay_us(IIC_DELAY_us);
IIC_SCL(IIC_Type_t, 1);
IIC_Type_t->delay_us(IIC_DELAY_us);
IIC_SCL(IIC_Type_t, 0);
IIC_Type_t->delay_us(IIC_DELAY_us);
}
static uint8_t IIC_Send_Byte_t(const struct IIC_Type* IIC_Type_t, uint8_t SendByte)
{
uint8_t i = 8;
while(i--)
{
IIC_SCL(IIC_Type_t, 0);
IIC_Type_t->delay_us(IIC_DELAY_us);
if(SendByte & 0x80)
{
IIC_SDA(IIC_Type_t, 1);
}
else
{
IIC_SDA(IIC_Type_t, 0);
}
SendByte <<= 1;
IIC_Type_t->delay_us(IIC_DELAY_us);
IIC_SCL(IIC_Type_t, 1);
IIC_Type_t->delay_us(IIC_DELAY_us);
}
IIC_SCL(IIC_Type_t, 0);
}
static uint8_t IIC_Read_Byte_t(const struct IIC_Type* IIC_Type_t)
{
uint8_t i = 8;
uint8_t ReceiveByte = 0;
IIC_SDA(IIC_Type_t, 1);
while(i--)
{
ReceiveByte <<= 1;
IIC_SCL(IIC_Type_t, 0);
IIC_Type_t->delay_us(IIC_DELAY_us);
IIC_SCL(IIC_Type_t, 1);
IIC_Type_t->delay_us(IIC_DELAY_us);
if(READ_SDA(IIC_Type_t))
{
ReceiveByte |= 0x01;
}
}
IIC_SCL(IIC_Type_t, 0);
return ReceiveByte;
}
static uint8_t EEProm_Unlock_t(const struct EEPROM_Type* EEPROM_Type_t)
{
GPIO_ResetBits(EEPROM_Type_t->GPIOx_Lock, EEPROM_Type_t->Lock_Pin_x);
}
static uint8_t EEProm_Lock_t(const struct EEPROM_Type* EEPROM_Type_t)
{
GPIO_SetBits(EEPROM_Type_t->GPIOx_Lock, EEPROM_Type_t->Lock_Pin_x);
}
uint8_t EEProm_Init_t(const struct EEPROM_Type* EEPROM_Type_t)
{
RCC_AHB1PeriphClockCmd(EEPROM_Type_t->RCC_Lock_APB2Periph, ENABLE);
GPIO_InitTypeDef GPIO_InitStructure;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT;
GPIO_InitStructure.GPIO_OType = GPIO_OType_OD;
GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP;
GPIO_InitStructure.GPIO_Pin = EEPROM_Type_t->Lock_Pin_x;
GPIO_Init(EEPROM_Type_t->GPIOx_Lock, &GPIO_InitStructure);
EEPROM_Type_t->IIC.IIC_Init(&EEPROM_Type_t->IIC);
return true;
}
uint8_t EEProm_Soft_Reset_t(const struct EEPROM_Type* EEPROM_Type_t)
{
IIC_SDA(&EEPROM_Type_t->IIC, 1);
IIC_SCL(&EEPROM_Type_t->IIC, 1);
EEPROM_Type_t->IIC.delay_us(IIC_DELAY_us);
IIC_SDA(&EEPROM_Type_t->IIC, 0);
EEPROM_Type_t->IIC.delay_us(IIC_DELAY_us);
IIC_SCL(&EEPROM_Type_t->IIC, 0);
for(uint8_t i = 0; i < 9; i++)
{
IIC_SCL(&EEPROM_Type_t->IIC, 1);
EEPROM_Type_t->IIC.delay_us(IIC_DELAY_us);
IIC_SDA(&EEPROM_Type_t->IIC, 1);
EEPROM_Type_t->IIC.delay_us(IIC_DELAY_us);
IIC_SCL(&EEPROM_Type_t->IIC, 0);
EEPROM_Type_t->IIC.delay_us(IIC_DELAY_us);
}
IIC_SDA(&EEPROM_Type_t->IIC, 1);
IIC_SCL(&EEPROM_Type_t->IIC, 1);
EEPROM_Type_t->IIC.delay_us(IIC_DELAY_us);
IIC_SDA(&EEPROM_Type_t->IIC, 0);
EEPROM_Type_t->IIC.delay_us(IIC_DELAY_us);
IIC_SCL(&EEPROM_Type_t->IIC, 0);
EEPROM_Type_t->IIC.delay_us(IIC_DELAY_us);
IIC_SDA(&EEPROM_Type_t->IIC, 0);
EEPROM_Type_t->IIC.delay_us(IIC_DELAY_us);
IIC_SCL(&EEPROM_Type_t->IIC, 1);
EEPROM_Type_t->IIC.delay_us(IIC_DELAY_us);
IIC_SDA(&EEPROM_Type_t->IIC, 1);
EEPROM_Type_t->IIC.delay_us(IIC_DELAY_us);
}
uint8_t EEProm_Soft_Read(const struct EEPROM_Type* EEPROM_Type_t, uint32_t ReadAddress, uint8_t* pBuffer, uint16_t length)
{
uint8_t block = 0;
uint8_t addr_h = 0;
uint8_t addr_l = 0;
EEPROM_Type_t->EEProm_Soft_Reset(EEPROM_Type_t);
if(!EEPROM_Type_t->IIC.IIC_Start(&EEPROM_Type_t->IIC))
{
return false;
}
if(EEPROM_Type_t->addr_wide == ADDR_WIDE_16)
{
block = ((ReadAddress >> 16) << 1);
}
else
{
block = ((ReadAddress >> 8) << 1);
}
addr_h = (ReadAddress >> 8);
addr_l = ReadAddress;
EEPROM_Type_t->IIC.IIC_Send_Byte(&EEPROM_Type_t->IIC, EEPROM_Type_t->device_addr & 0xfe | block); //设置高起始地址+器件地址
if(!EEPROM_Type_t->IIC.IIC_Wait_Ack(&EEPROM_Type_t->IIC))
{
EEPROM_Type_t->IIC.IIC_Stop(&EEPROM_Type_t->IIC);
return false;
}
if(EEPROM_Type_t->addr_wide == ADDR_WIDE_16)
{
EEPROM_Type_t->IIC.IIC_Send_Byte(&EEPROM_Type_t->IIC, addr_h); //设置低起始地址
EEPROM_Type_t->IIC.IIC_Wait_Ack(&EEPROM_Type_t->IIC);
}
EEPROM_Type_t->IIC.IIC_Send_Byte(&EEPROM_Type_t->IIC, addr_l); //设置低起始地址
if(!EEPROM_Type_t->IIC.IIC_Wait_Ack(&EEPROM_Type_t->IIC))
{
EEPROM_Type_t->IIC.IIC_Stop(&EEPROM_Type_t->IIC);
return false;
}
EEPROM_Type_t->EEProm_Soft_Reset(EEPROM_Type_t);
EEPROM_Type_t->IIC.IIC_Start(&EEPROM_Type_t->IIC);
EEPROM_Type_t->IIC.IIC_Send_Byte(&EEPROM_Type_t->IIC, EEPROM_Type_t->device_addr | 0x01 | block); //设置高起始地址+器件地址
if(!EEPROM_Type_t->IIC.IIC_Wait_Ack(&EEPROM_Type_t->IIC))
{
EEPROM_Type_t->IIC.IIC_Stop(&EEPROM_Type_t->IIC);
return false;
}
while(length)
{
*pBuffer = EEPROM_Type_t->IIC.IIC_Read_Byte(&EEPROM_Type_t->IIC);
if(length == 1)
{
EEPROM_Type_t->IIC.IIC_NAck(&EEPROM_Type_t->IIC);
}
else
{
EEPROM_Type_t->IIC.IIC_Ack(&EEPROM_Type_t->IIC);
}
pBuffer++;
length--;
}
EEPROM_Type_t->IIC.IIC_Stop(&EEPROM_Type_t->IIC);
return true;
}
uint8_t EEProm_Soft_Write(const struct EEPROM_Type* EEPROM_Type_t, uint32_t WriteAddress, uint8_t* pBuffer, uint16_t length)
{
uint16_t i;
uint8_t block = 0;
uint8_t addr_h = 0;
uint8_t addr_l = 0;
EEPROM_Type_t->EEProm_Soft_Reset(EEPROM_Type_t);
if(!EEPROM_Type_t->IIC.IIC_Start(&EEPROM_Type_t->IIC))
{
return false;
}
if(EEPROM_Type_t->addr_wide == ADDR_WIDE_16)
{
block = ((WriteAddress >> 16) << 1);
}
else
{
block = ((WriteAddress >> 8) << 1);
}
addr_h = (WriteAddress >> 8);
addr_l = WriteAddress;
EEPROM_Type_t->IIC.IIC_Send_Byte(&EEPROM_Type_t->IIC, EEPROM_Type_t->device_addr & 0xfe | block); //设置高起始地址+器件地址
if(!EEPROM_Type_t->IIC.IIC_Wait_Ack(&EEPROM_Type_t->IIC))
{
EEPROM_Type_t->IIC.IIC_Stop(&EEPROM_Type_t->IIC);
return false;
}
if(EEPROM_Type_t->addr_wide == ADDR_WIDE_16)
{
EEPROM_Type_t->IIC.IIC_Send_Byte(&EEPROM_Type_t->IIC, addr_h); //设置低起始地址
EEPROM_Type_t->IIC.IIC_Wait_Ack(&EEPROM_Type_t->IIC);
}
EEPROM_Type_t->IIC.IIC_Send_Byte(&EEPROM_Type_t->IIC, addr_l); //设置低起始地址
if(!EEPROM_Type_t->IIC.IIC_Wait_Ack(&EEPROM_Type_t->IIC))
{
EEPROM_Type_t->IIC.IIC_Stop(&EEPROM_Type_t->IIC);
return false;
}
for(i = 0; i < length; i++)
{
EEPROM_Type_t->IIC.IIC_Send_Byte(&EEPROM_Type_t->IIC, *pBuffer);
if(!EEPROM_Type_t->IIC.IIC_Wait_Ack(&EEPROM_Type_t->IIC))
{
EEPROM_Type_t->IIC.IIC_Stop(&EEPROM_Type_t->IIC);
return false;
}
pBuffer++;
}
EEPROM_Type_t->IIC.IIC_Stop(&EEPROM_Type_t->IIC);
//注意:因为这里要等待EEPROM写完,可以采用查询或延时方式(10ms)
EEPROM_Type_t->IIC.delay_us(10000);
return true;
}
uint8_t EEProm_Soft_Write_Data(const struct EEPROM_Type* EEPROM_Type_t, uint32_t WriteAddress, uint8_t* pBuffer, uint16_t length)
{
uint8_t ret = false;
if(((WriteAddress + length) > EEPROM_Type_t->max_size || length == 0))
{
return false;
}
uint32_t NumOfPage = 0, NumOfSingle = 0, Addr = 0, count = 0;
Addr = WriteAddress % EEPROM_Type_t->page_size; //写入地址是开始页的第几位
count = EEPROM_Type_t->page_size - Addr; //在开始页要写入的个数
EEPROM_Type_t->EEProm_Unlock(EEPROM_Type_t);
if(count >= length) // 该页剩余的空间可以容下需要写入的数据量
{
if(EEProm_Soft_Write(EEPROM_Type_t, WriteAddress, pBuffer, length) == false) //写一页的数据
{
goto ret_return;
}
ret = true;
}
else
{
NumOfPage = (length - count) / EEPROM_Type_t->page_size;
NumOfSingle = (length - count) % EEPROM_Type_t->page_size;
if(EEProm_Soft_Write(EEPROM_Type_t, WriteAddress, pBuffer, count) == false)
{
goto ret_return;
}
WriteAddress += count;
pBuffer += count;
while(NumOfPage--) // 写页
{
if(EEProm_Soft_Write(EEPROM_Type_t, WriteAddress, pBuffer, EEPROM_Type_t->page_size) == false)
{
goto ret_return;
}
WriteAddress += EEPROM_Type_t->page_size;
pBuffer += EEPROM_Type_t->page_size;
}
if(NumOfSingle != 0) // 剩下的不足一页
{
if(EEProm_Soft_Write(EEPROM_Type_t, WriteAddress, pBuffer, NumOfSingle) == false)
{
goto ret_return;
}
}
ret = true;
}
ret_return:
EEPROM_Type_t->EEProm_Lock(EEPROM_Type_t);
return ret;
}
uint8_t EEProm_NWrite_t(const struct EEPROM_Type* EEPROM_Type_t, uint32_t WriteAddress, uint8_t* pBuffer, uint16_t length)
{
uint8_t i;
for(i = 0; i < 3; i++)
{
if(EEProm_Soft_Write_Data(EEPROM_Type_t, WriteAddress, pBuffer, length) == true)
{
return true;
}
}
return false;
}
/****************************************************************************************
*函数名称: IIC_Soft_Read_Data
*
*函数说明: 模拟iic读数据函数
****************************************************************************************/
uint8_t EEProm_NRead_t(const struct EEPROM_Type* EEPROM_Type_t, uint32_t readaddress, uint8_t* pBuffer, uint16_t length)
{
uint8_t ret = false;
if(((readaddress + length) > EEPROM_Type_t->max_size || length == 0))
{
return false;
}
EEPROM_Type_t->EEProm_Unlock(EEPROM_Type_t);
ret = EEProm_Soft_Read(EEPROM_Type_t, readaddress, pBuffer, length);
EEPROM_Type_t->EEProm_Lock(EEPROM_Type_t);
return ret;
}
uint8_t delay_us_t(uint32_t us)
{
sys_timer_usDelay(us);
}
EEPROM_Type_t BL24CM1A =
{
.IIC = {
.RCC_SCL_APB2Periph = RCC_AHB1Periph_GPIOB,
.RCC_SDA_APB2Periph = RCC_AHB1Periph_GPIOB,
.GPIOx_SCL = GPIOB,
.GPIOx_SDA = GPIOB,
.SCL_Pin_x = GPIO_Pin_4,
.SDA_Pin_x = GPIO_Pin_5,
.IIC_Init = IIC_Init_t,
.IIC_Start = IIC_Start_t,
.IIC_Stop = IIC_Stop_t,
.IIC_Wait_Ack = IIC_Wait_Ack_t,
.IIC_Ack = IIC_Ack_t,
.IIC_NAck = IIC_NAck_t,
.IIC_Send_Byte = IIC_Send_Byte_t,
.IIC_Read_Byte = IIC_Read_Byte_t,
.delay_us = delay_us_t,
},
.RCC_Lock_APB2Periph = RCC_AHB1Periph_GPIOB,
.GPIOx_Lock = GPIOB,
.Lock_Pin_x = GPIO_Pin_3,
.addr_wide = ADDR_WIDE_16,
.device_addr = 0xA0,
.page_size = 128,
.max_size = 131072,
.EEProm_Init = EEProm_Init_t,
.EEProm_Soft_Reset = EEProm_Soft_Reset_t,
.EEProm_Unlock = EEProm_Unlock_t,
.EEProm_Lock = EEProm_Lock_t,
.EEProm_NRead = EEProm_NRead_t,
.EEProm_NWrite = EEProm_NWrite_t,
};
void BL24CM1A_Init(void)
{
BL24CM1A.EEProm_Init(&BL24CM1A);
}
uint8_t BL24CM1A_Write_Data(uint32_t WriteAddress, uint8_t* pBuffer, uint16_t length)
{
BL24CM1A.EEProm_NWrite(&BL24CM1A, WriteAddress, pBuffer, length);
}
uint8_t BL24CM1A_Read_Data(uint32_t readaddress, uint8_t* pBuffer, uint16_t length)
{
BL24CM1A.EEProm_NRead(&BL24CM1A, readaddress, pBuffer, length);
}