**************************************************************************************/
#include "dw8051.h"
#include "ExLigReg.h"
#include "ExLigLib.h"
#include "delay.h"
#include "func.h"
//=====================================================================
extern void _nop_ (void);
#define nop() _nop_()
//#define XBYTE ((unsigned char volatile xdata *)0)
//=====================================================================
#define IO_RST 0x08
//----------------------------------------------------------------------
//----------------------------------------------------------------------
//按键定义
//----------------------------------------------------------------------
//----------------------------------------------------------------------
//指示定义区
//----------------------------------------------------------------------
//----------------------------------------------------------------------
//-------------------------------------------------------------
//-------------------------------------------------------------
//IIC
//------------------------------------------------------------
#define voltage_ROM 0x10
#define k1_ROM 0x30
//#define voltage_ROM 0x80
//-------------------------------------------------------------
#define IIC_SDA BIT7 //定义I2C数据线(P67)
#define IIC_SCL BIT6 //定义I2C时钟线(P66)
#define IIC_OE P6OE
#define IIC_IE P6IE
#define IIC_ID P6ID
#define IIC_OD P6OD
#define SDA_1 (IIC_OD |=IIC_SDA) //SDA = 1
#define SDA_0 (IIC_OD &=~IIC_SDA) //SDA = 0
#define SCL_1 (IIC_OD |=IIC_SCL) //SCL = 1
#define SCL_0 (IIC_OD &=~IIC_SCL) //SCL = 0
#define EN_SCL_OUT (IIC_OE &=~IIC_SCL) //开SCL输出
#define EN_SDA_IN (IIC_IE |=IIC_SDA) //定义数据线SDA输入
#define EN_SDA_OUT (IIC_OE &=~IIC_SDA) //定义数据线SDA输出
#define DISEN_SDA_OUT (IIC_OE |=IIC_SDA) // 禁止SDA输出
//====================================================================
#define biancheng_addr 0x6b0 //编程内容、时间保存地址,每次8字节,共3次,一个校验位,25字节
////////////////////////////////////////////////////////////////////////////////////
#ifndef Data_Translate
//--------LCD--------------------------------------------------
//===========key==========================================
//------------------------------------------------------------------------
#else
//=============================================================
//--------------------------------------------------------
//=================================================================
#endif
//===================================================================
//IIC总线短延时
//-------------------------------------------------------------------
void IIC_delay(void)
{
nop();
nop();
nop();
nop();
nop();
}
//--------------------------------------------------------------
//启动总线函数:启动I2C总线,即发送I2C起始条件
//--------------------------------------------------------------
void Start_I2c(void)
{
EN_SCL_OUT;
EN_SDA_OUT;
SCL_0;
IIC_delay();
SDA_1;
IIC_delay();
IIC_delay();
SCL_1;
IIC_delay();
IIC_delay();
SDA_0;
IIC_delay();
SCL_0;
DISEN_SDA_OUT; //关闭SDA输出
}
//---------------------------------------------------------------
//结束I2C总线,发送结束条件
//--------------------------------------------------------------
void Stop_I2c(void)
{
EN_SCL_OUT;//
EN_SDA_OUT; //
SCL_0;
IIC_delay();
SDA_0;
IIC_delay();
IIC_delay();
SCL_1;
IIC_delay();
IIC_delay();
SDA_1;
IIC_delay();
SCL_0;
DISEN_SDA_OUT; // //关闭SDA输出
}
//----------------------------------------------------------------
// 字节数据接收函数
// 用来接收从器件传来的数据,并判断总线错误(不发应答信号)
//----------------------------------------------------------------
unsigned char RcvByte(void)
{
unsigned char temp,BitCnt;
temp=0;
DISEN_SDA_OUT; //关闭SDA输出
EN_SDA_IN; //置数据线为输入方式
EN_SCL_OUT;
IIC_delay();
for(BitCnt=0;BitCnt<8;BitCnt++)
{
temp=temp<<1;
IIC_delay();
SCL_1; //置时钟线上为高使数据线上数据有效
IIC_delay();
IIC_delay();
if(IIC_ID&IIC_SDA)temp=temp+1;//读数据位,接收的数据位放入retc中
IIC_delay();
SCL_0;
}
IIC_delay();
return(temp);
}
//--------------------------------------------------------------------------------
void Ack_I2c(unsigned char sign)
{
EN_SCL_OUT;//
EN_SDA_OUT; //
if(sign==0) //在此发出应答或非应答信号
SDA_0;
else
SDA_1; //发送非应答位
IIC_delay();
IIC_delay();
SCL_1; //时钟低电平周期大于4us
IIC_delay();
IIC_delay();
SCL_0; //清时钟线,钳住I2C总线以便继续接收
DISEN_SDA_OUT; // //关闭SDA输出
}
//--------------------------------------------------------------------
unsigned char SendByte(unsigned char c)
{
unsigned char BitCnt,ack;
EN_SCL_OUT;
EN_SDA_OUT;
for(BitCnt=0;BitCnt<8;BitCnt++)
{
if((c&0x80)==0x80)
SDA_1;
else
SDA_0;
IIC_delay();
IIC_delay();
SCL_1; //置数据线为高,通知被控器开始接收数据位
IIC_delay();
IIC_delay();
SCL_0;
IIC_delay();
IIC_delay();
c<<=1;
}
DISEN_SDA_OUT; // //关闭SDA输出
EN_SDA_IN; // //8位发送完后释放数据线,准备接收应答位
IIC_delay();
IIC_delay();
SCL_1;
IIC_delay();
IIC_delay();
if(IIC_ID&IIC_SDA)
ack=0;
else
ack=1;
IIC_delay();
SCL_0;
return(ack);
}
//=================================================================================
unsigned char Read24c16(unsigned int suba,unsigned char *s,unsigned char length)
{
unsigned char i,ack;
Start_I2c(); //启动总线
ack=SendByte(0xa0+2*(suba/256)); //发送器件从地址(写)
if (ack==0)
{
Stop_I2c(); //结束总线
return(0xAA); //器件无应答返回操作失败
}
ack=SendByte((unsigned char)suba); //发送器件子地址
if(ack==0)
{
Stop_I2c(); //结束总线
return(0xAA); //器件无应答返回操作失败
}
Start_I2c(); //启动总线
// ack=SendByte(0xA1+2*(suba/256)); //发送器件从地址(读)
ack=SendByte(0xA1);
if (ack==0)
{
Stop_I2c(); //结束总线
return(0xAA); //器件无应答返回操作失败
}
for(i=0;i<length;i++)
{
*s = RcvByte();
s++;
if(i<length-1)
Ack_I2c(0);
else
Ack_I2c(1);
}
Stop_I2c(); //结束总线
return(0); //返回操作成功
}
//==================================================================================
//在同一个页内写16个字节数据
// suba 首地址, *s 写入的数据,length 写入字节的个数
//-------------------------------------------------------------------------------------
unsigned char Write24c16(unsigned int suba,unsigned char *s,unsigned char length)
{
unsigned char i,ack;
Start_I2c(); //启动总线
ack=SendByte(0xA0+2*(suba/256)); //发送(写)器件地址
if (ack==0)
{
Stop_I2c(); //结束总线
return(0xAA); //器件无应答返回操作失败
}
ack=SendByte((unsigned char)suba); //发送器件子地址
if (ack==0)
{
Stop_I2c(); //结束总线
return(0xAA); //器件无应答返回操作失败
}
// for(i=0,ack==1;((i<length)&&(ack==1));i++)
for(i=0;((i<length)&&(ack==1));i++)
{
ack=SendByte(*s); //发送数据
s++;
}
if(i!=length)
{
Stop_I2c(); //结束总线
return(0xAA); //器件无应答返回操作失败
}
Stop_I2c(); //结束总线
return(0); //返回操作成功
}
void SmgDispay(void)
{
unsigned char i;
Start_I2c();
SendByte(0x40);
Ack_I2c();
Stop_I2c();
Start_I2c();
SendByte(0xc0);
for(i=0;i<6;i++)
{
SendByte(0xff);
Ack_I2c();
}
Stop_I2c();
Start_I2c();
SendByte(0x8f);
Ack_I2c();
Stop_I2c();
}
void main()
{
Init_Port();
SetPLL(SETPLL_3_2M);//设置3.2M的MCU时钟,单独调试(F11)此函数会失去调试连接
ClearWDT();
SmgDispay();
while(1)
{
Led_Twin(4);
ClearWDT();
delayms(500);//加上面灭灯时的300ms所以,间隔为1.8s
delayms(500);
delayms(500);
ClearWDT();
}
} |