国产毛片a精品毛-国产毛片黄片-国产毛片久久国产-国产毛片久久精品-青娱乐极品在线-青娱乐精品

查看: 4474|回復(fù): 1
打印 上一主題 下一主題

CortexM0菜鳥(niǎo)之I2C主機(jī)中斷(第10天作業(yè))

[復(fù)制鏈接]
跳轉(zhuǎn)到指定樓層
樓主
發(fā)表于 2010-9-7 01:21:57 | 只看該作者 回帖獎(jiǎng)勵(lì) |倒序?yàn)g覽 |閱讀模式
關(guān)鍵詞: 菜鳥(niǎo) , 主機(jī) , 作業(yè)
菜農(nóng)此I2C模板應(yīng)用8年未嘗敗績(jī),大家可以和NXP例程對(duì)比,
俺就不公開(kāi)和NXP“PK”了~~~
//i2c.h
#include "main.h"
#ifndef __LPC11xxI2c_H__
#define __LPC11xxI2c_H__
#ifdef __cplusplus
extern "C" {
#endif
class I2cObj;
class I2cObj {//系統(tǒng)串口類
public:
    I2cObj(unsigned char I2CAddress = 0xa1);
private:
    inline void I2cInit(void);
public:
    inline void Start(void);
    inline void REStart(void);
    inline void Stop(void);
inline void Exit(void);
inline void Exec(void);
void SetAddress(unsigned char I2CAddress);
void WriteWait(void);
unsigned char ReadByte(unsigned char, unsigned char &);
unsigned char WriteByte(unsigned char, unsigned char);
public:
volatile bool Busy;
volatile unsigned int State;
volatile unsigned int Count;
volatile unsigned int MainCount, SubCount;
volatile unsigned char SubAddr;
volatile unsigned char MainComm, SubComm;
volatile unsigned char TxBuffer[16], RxBuffer[16];//接收數(shù)據(jù)緩沖區(qū)
};
extern "C" void __irq I2C_IRQHandler(void);
#ifdef __cplusplus
}
#endif
#endif//__LPC11xxI2c_H__

//i2c.cpp

#include "i2c.h"
extern "C" void __irq I2C_IRQHandler(void)
{
I2c.Exec();
}
I2cObj::I2cObj (unsigned char I2CAddress)
{
SubAddr = I2CAddress;
    I2cInit();
}
void I2cObj::I2cInit(void)
{
SYSCON.PRESETCTRL.Bits.I2C0_RST_N = 1;//復(fù)位I2C,否則死機(jī)
SYSCON.SYSAHBCLKCTRL.Bits.I2CCLK = 1;
//位域?qū)懛?br /> IOCON.PIO0_4.Bits.FUNC    = IOCON_SCL;//選擇PIO0.4為I2C_SCL
IOCON.PIO0_4.Bits.I2CMODE = IOCON_SCL_I2CMODE;//選擇PIO0.4為I2C_SCL
IOCON.PIO0_5.Bits.FUNC    = IOCON_SDA;//選擇PIO0.5為I2C_SCL
IOCON.PIO0_5.Bits.I2CMODE = IOCON_SDA_I2CMODE;//選擇PIO0.5為I2C_SDA
//寄存器寫(xiě)法
/*
IOCON.PIO0_4.Regs = (IOCON_SCL << IOCON_FUNC)
                   | (IOCON_SCL_I2CMODE << IOCON_I2CMODE);
IOCON.PIO0_5.Regs = (IOCON_SDA << IOCON_FUNC)
                   | (IOCON_SDA_I2CMODE << IOCON_I2CMODE);
*/
    I2C0.SCLL.Regs   = 0x00000180;
    I2C0.SCLH.Regs   = 0x00000180;
I2C0.CONCLR.Regs = (1 << STA) | (1 << SI);
I2C0.CONSET.Bits.I2EN = 1;
for (int i = 0; i < sizeof(TxBuffer); i ++) {
  TxBuffer = 0;
  RxBuffer = 0;
}
Exit();//通訊失敗
nVIC.ISER.Bits.I2C_IRQn = 1;
}
void I2cObj::SetAddress(unsigned char I2CAddress)
{
SubAddr = I2CAddress;
}
void I2cObj::Start(void)
{
Busy = true;
   State = I2C_START;//主機(jī)準(zhǔn)備發(fā)送啟始位
   Count = 0;//發(fā)送數(shù)據(jù)個(gè)數(shù)
I2C0.CONSET.Regs = (1 << I2EN) | (1 << STA);//設(shè)置使能起始標(biāo)志
}
void I2cObj::REStart(void)
{
Busy = true;
   State = I2C_REP_START;//主機(jī)準(zhǔn)備發(fā)送啟始位
   Count = 0;//發(fā)送數(shù)據(jù)個(gè)數(shù)
I2C0.CONCLR.Regs = (1 << STA) | (1 << SI) | (1 << AA);//清除標(biāo)志
I2C0.CONSET.Regs = (1 << I2EN) | (1 << STA);//設(shè)置使能起始標(biāo)志
}
void I2cObj::Stop(void)
{
Busy = false;
State = I2C_BUS_OK;//通訊成功
  I2C0.CONSET.Regs = (1 << I2EN) | (1 << STO);
I2C0.CONCLR.Regs = (1 << STA) | (1 << SI) | (1 << AA);
}
void I2cObj::Exit(void)
{
Busy = false;
State = I2C_BUS_ERROR;//通訊失敗
  I2C0.CONSET.Regs = (1 << I2EN) | (1 << STO);
I2C0.CONCLR.Regs = (1 << STA) | (1 << SI) | (1 << AA);
}
void I2cObj::WriteWait(void)
{
for(int i = 0; i < 18888; i ++)
{
  __nop();//延時(shí)等待寫(xiě)入完成
}
}
void I2cObj::Exec(void)
{
  switch(I2C0.STAT.Regs & 0xf8) {
    case I2C_START://主機(jī)收到自己發(fā)送的開(kāi)始信號(hào)
        if (State == I2C_START) {//本次中斷應(yīng)該接收TW_START信號(hào)
          I2C0.DAT.Regs = SubAddr & 0xfe;//發(fā)送子機(jī)地址(寫(xiě))
    State = I2C_MT_SLA_ACK;//Status下次I2C_MT_SLA_ACK
             I2C0.CONCLR.Regs = (1 << STA) | (1 << SI) | (1 << AA);//清除中斷標(biāo)志
     }
     else Exit();//通訊失敗
        break;
case I2C_REP_START://主機(jī)收到自己發(fā)送的重新開(kāi)始信號(hào)
        if (State == I2C_REP_START) {//本次中斷應(yīng)該接收TW_RESTART信號(hào)
          I2C0.DAT.Regs = SubAddr | 0x01;//發(fā)送子機(jī)地址(讀)
       State = I2C_MR_SLA_ACK;//Status下次I2C_MR_SLA_ACK
             I2C0.CONCLR.Regs = (1 << STA) | (1 << SI) | (1 << AA);//清除中斷標(biāo)志
     }
     else Exit();//通訊失敗
        break;
case I2C_MT_SLA_ACK://主發(fā)機(jī)接收到從機(jī)的地址應(yīng)答信號(hào)后發(fā)送命令
        if (State == I2C_MT_SLA_ACK) {//本次中斷應(yīng)該接收TW_MT_SLA_ACK信號(hào)
       State = I2C_MT_DATA_ACK;//Status下次應(yīng)該收TW_MT_DATA_ACK
             I2C0.DAT.Regs = SubComm;//發(fā)送子機(jī)命令
             I2C0.CONCLR.Regs = (1 << STA) | (1 << SI) | (1 << AA);//清除中斷標(biāo)志
     }
     else Exit();//通訊失敗
        break;
case I2C_MR_SLA_ACK://主收機(jī)接收到從機(jī)的地址應(yīng)答信號(hào)
        if ((State == I2C_MR_SLA_ACK) && SubCount) {//本次中斷應(yīng)該接收TW_MR_SLA_ACK信號(hào)
       State = I2C_MR_DATA_ACK;//Status下次應(yīng)該收TW_MR_DATA_ACK
             I2C0.CONCLR.Regs = (1 << STA) | (1 << SI);//清除中斷標(biāo)志,主機(jī)轉(zhuǎn)入接收狀態(tài)
    I2C0.CONSET.Bits.AA = 1;
     }
     else Exit();//通訊失敗
     break;
case I2C_MT_DATA_ACK://主收機(jī)接收到從機(jī)的數(shù)據(jù)應(yīng)答信號(hào)
        if ((State == I2C_MT_DATA_ACK) && (Count < MainCount)) {//本次中斷應(yīng)該接收TW_MT_DATA_ACK信號(hào)
          I2C0.DAT.Regs = TxBuffer[Count ++];//發(fā)送子機(jī)數(shù)據(jù)
             I2C0.CONCLR.Regs = (1 << STA) | (1 << SI) | (1 << AA);//清除中斷標(biāo)志
     }
     else {
          if ((State == I2C_MT_DATA_ACK) && (Count == MainCount) && (SubAddr & 1)) {//本次中斷應(yīng)該接收TW_MT_DATA_ACK信號(hào)
           REStart();//
    }
             else Stop();//通訊成功
     }
     break;
case I2C_MR_DATA_ACK:
        if ((State == I2C_MR_DATA_ACK) && (Count < SubCount)) {
          RxBuffer[Count ++] = I2C0.DAT.Regs;//接收子機(jī)數(shù)據(jù)
    if (Count < SubCount) {
               I2C0.CONCLR.Regs = (1 << STA) | (1 << SI);//主機(jī)轉(zhuǎn)入接收狀態(tài)
      I2C0.CONSET.Bits.AA = 1;
    }
    else {
               I2C0.CONCLR.Regs = (1 << STA) | (1 << SI) | (1 << AA);//清除中斷標(biāo)志,主機(jī)轉(zhuǎn)入接收狀態(tài)
      State = I2C_MR_DATA_NACK;//下次進(jìn)入I2C_MR_DATA_NACK,接收數(shù)據(jù)準(zhǔn)備完成
    }
     }
     else Exit();//通訊失敗
     break;
case I2C_MR_DATA_NACK://數(shù)據(jù)接收結(jié)束
        if ((State == I2C_MR_DATA_NACK) && (Count == SubCount)) {
       Stop();//通訊成功
     }
     else Exit();//通訊失敗
     break;
// case I2C_MT_DATA_NACK:
//     Exit();//通訊失敗
//     break;
default:
     Exit();//通訊失敗
  }
}
unsigned char I2cObj::ReadByte(unsigned char Address, unsigned char & Data)
{
SubAddr |= 0x01;
MainCount = 0;//發(fā)送0個(gè)數(shù)據(jù)(只讀)
//本程序?yàn)橥ㄓ肐2C,故發(fā)送器件后一般為命令,對(duì)EEPROM來(lái)說(shuō),命令實(shí)際是EEPROM地址
SubComm = Address;//讀出地址
SubCount = 1;//接收1個(gè)數(shù)據(jù)
Start();
while (Busy);
if (State == I2C_BUS_OK) {//通訊成功
  Data = RxBuffer[0];//取出一個(gè)字節(jié)
}
return State;//(讀出數(shù)據(jù)在RxBuffer[0]~RxBuffer[15])
}
unsigned char I2cObj::WriteByte(unsigned char Address, unsigned char Data)
{
SubAddr &= 0xfe;
MainCount = 1;//發(fā)送1個(gè)數(shù)據(jù)
//本程序?yàn)橥ㄓ肐2C,故發(fā)送器件后一般為命令,對(duì)EEPROM來(lái)說(shuō),命令實(shí)際是EEPROM地址
SubComm = Address;//寫(xiě)入地址
TxBuffer[0] = Data;//寫(xiě)入數(shù)據(jù)
SubCount = 0;//接收0個(gè)數(shù)據(jù)
Start();
while (Busy);
if (State == I2C_BUS_OK) {//通訊成功
  PortLed1.DATA.Bits.PinLed1 = 0;//LED1亮
}
return State;
}

//讀LM75
I2c.SetAddress(0x90);//設(shè)置LM75器件地址
I2c.WriteByte(1, Data);//寫(xiě)配置命令1
I2c.ReadByte(0, Data);//讀溫度命令0
Uart.Send(Data);
//讀寫(xiě)AT24C16
I2c.SetAddress(0xa0);//設(shè)置AT24C16器件地址
for (int i = 1; i < 16; i ++)//延時(shí)
{
  I2c.WriteByte(i, i);//寫(xiě)入EEPROM一個(gè)字節(jié)
  I2c.WriteWait();//延時(shí)等待寫(xiě)入完成
  I2c.ReadByte(i, Data);//讀出EEPROM一個(gè)字節(jié)
  Uart.Send(Data);
}

HotPower@163.com  2010.9.6 23:58 于雁塔菜地

菜農(nóng)通訊工具:

新浪網(wǎng)頁(yè)版:http://t.sina.com.cn/hotpower
新浪手機(jī)版:http://t.sina.cn/hotpower

網(wǎng) 易微 博:http://t.163.com/hotpower
騰訊QQ:    1270688699

菜農(nóng)郵箱:     HotPower@163.com
菜農(nóng)導(dǎo)航: http://www.hotpage.net.cn/



沙發(fā)
發(fā)表于 2010-9-10 16:08:28 | 只看該作者
頂一個(gè)

本版積分規(guī)則

關(guān)于我們  -  服務(wù)條款  -  使用指南  -  站點(diǎn)地圖  -  友情鏈接  -  聯(lián)系我們
電子工程網(wǎng) © 版權(quán)所有   京ICP備16069177號(hào) | 京公網(wǎng)安備11010502021702
快速回復(fù) 返回頂部 返回列表
主站蜘蛛池模板: 日韩欧美网 | 性夜影院午夜看片 | 97在线观看成人免费视频 | 四虎成人影院 | 中文字幕日韩在线 | 成人四虎影院 | 免费片 | 性刺激免费视频观看在线观看 | 国产免费爽爽视频免费可以看 | 失乐园在线观看 | 欧美ww| 成都4片p高清完整版hd | 久久精品视频免费观看 | 日韩中文在线视频 | 精品黑人一区二区三区 | 五月香婷婷 | 国产免费一级片 | 一区二区三区成人 | 免费看的| 99热在线看 | 51久久 | 成视频年人黄网站免费动漫 | 久久网免费视频 | 青青草原.comav | 欧美日本综合一区二区三区 | 欧美一区二区三区免费高 | 偷拍同志老头小便oldman | 亚洲第一区二区快射影院 | 最近手机中文字幕1页 | 日本欧美国产精品 | 国产在线精品一区二区三区 | 亚洲精品视频在线观看免费 | 久久性感视频 | 欧美在线视频不卡 | 日韩在线视频免费不卡一区 | 最近韩国高清免费观看视频大全 | 亚洲免费在线播放 | 久久综合性 | 国产一区二区三区免费视频 | 国产aⅴ一区二区 | 影院亚洲|