zoukankan      html  css  js  c++  java
  • TQ2440之I2C操作

     开启IIC时钟:

     CLKCON |= (1<<10)|(1<<13); //开启串口0时钟

     中断服务程序:

    void  IRQ_Handler(void) __irq //irq中断函数
    {
        switch(INTOFFSET)
        {
            case 27:
            irq_IIC();//中断处理程序
            break;
        }
    }

     中断处理函数:

    void irq_IIC(void)
    {
        unsigned int iicSt,i;
    
        SRCPND = BIT_IIC;          //Clear pending bit
        INTPND = BIT_IIC;
        iicSt   = IICSTAT; 
        
        if(iicSt & 0x8){}           //When bus arbitration is failed.
        if(iicSt & 0x4){}           //When a slave address is matched with IICADD
        if(iicSt & 0x2){}           //When a slave address is 0000000b
        if(iicSt & 0x1){}           //When ACK isn't received
    
        switch(_iicMode)
        {
           case POLLACK:
               _iicStatus = iicSt;      //0xf0
               break;
    
           case RDDATA:
               if((_iicDataCount--)==0)
               {
                   _iicData[_iicPt++] = IICDS;
                
                   IICSTAT = 0x90;                 //Stop MasRx condition     1001 0000
                   IICCON  = 0xaf;                 //Resumes IIC operation.
                   Delay(1);                        //Wait until stop condtion is in effect.
                                                    //Too long time... 
                                                    //The pending bit will not be set after issuing stop condition.
                   break;    
               }      
               _iicData[_iicPt++] = IICDS;         //The last data has to be read with no ack.
    
               if((_iicDataCount)==0)
                   IICCON = 0x2f;                  //Resumes IIC operation with NOACK.  
               else 
                   IICCON = 0xaf;                  //Resumes IIC operation with ACK
                   break;
    
            case WRDATA:
                if((_iicDataCount--)==0)
                {
                    IICSTAT = 0xd0;                //Stop MasTx condition 
                    IICCON  = 0xaf;                //Resumes IIC operation.  1010 1111
                    Delay(1);                       //Wait until stop condtion is in effect.
                           //The pending bit will not be set after issuing stop condition.
                    break;    
                }
                IICDS = _iicData[_iicPt++];        //_iicData[0] has dummy.  发送接收数据移位寄存器
                for(i=0;i<10;i++);                  //for setup time until rising edge of IICSCL
                IICCON = 0xaf;                     //resumes IIC operation.
                break;
    
            case SETRDADDR:
    //          Uart_Printf("[ S%d ]",_iicDataCount);
                if((_iicDataCount--)==0)
                    break;                          //IIC operation is stopped because of IICCON[4]    
                IICDS = _iicData[_iicPt++];
                for(i=0;i<10;i++);                  //For setup time until rising edge of IICSCL
                IICCON = 0xaf;                     //Resumes IIC operation.
                break;
    
            default:
                break;      
        }
    }

    写一个字节函数:

    void Wr24C080(unsigned char slvAddr,unsigned char addr,unsigned char data)
    {
        _iicMode      = WRDATA;
        _iicPt        = 0;
        _iicData[0]   = (unsigned char)addr;
        _iicData[1]   = data;
        _iicDataCount = 2;
        
        IICDS   = slvAddr;                 //0xa0
        IICSTAT = 0xf0;                    //MasTx,Start
          //Clearing the pending bit isn't needed because the pending bit has been cleared.
        
        while(_iicDataCount!=-1);
    
        _iicMode = POLLACK;
    
        while(1)
        {
            IICDS     = slvAddr;
            _iicStatus = 0x100;
            IICSTAT   = 0xf0;              //MasTx,Start
            IICCON    = 0xaf;              //Resumes IIC operation. 
               
            while(_iicStatus==0x100);
               
            if(!(_iicStatus&0x1))
                break;                      //When ACK is received
        }
        IICSTAT = 0xd0;                    //Stop MasTx condition 
        IICCON  = 0xaf;                    //Resumes IIC operation. 
        Delay(1);                           //Wait until stop condtion is in effect.
           //Write is completed.
    }

    读一个字节函数:

    void Rd24C080(unsigned char slvAddr,unsigned char addr,unsigned char *data)
    {
        _iicMode      = SETRDADDR;
        _iicPt        = 0;
        _iicData[0]   = (unsigned char)addr;
        _iicDataCount = 1;
    
        IICDS   = slvAddr;
        IICSTAT = 0xf0;                    //MasTx,Start  
          //Clearing the pending bit isn't needed because the pending bit has been cleared.
        while(_iicDataCount!=-1);
    
        _iicMode      = RDDATA;
        _iicPt        = 0;
        _iicDataCount = 1;
        
        IICDS        = slvAddr;
        IICSTAT      = 0xb0;               //MasRx,Start
        IICCON       = 0xaf;               //Resumes IIC operation.   
        while(_iicDataCount!=-1);
    
        *data = _iicData[1];
    }

    IIC测试程序:

    void Test_Iic(void)
    {
        unsigned int i,j,save_E,save_PE;
        static unsigned char data[256];
    
        Uart_Printf("\n\rIIC Test(Interrupt) using AT24C02\n\r");
    
        save_E   = GPECON;
        save_PE  = GPEUP;
        GPEUP  |= 0xc000;                  //Pull-up disable
        GPECON |= 0xa0000000;                //GPE15:IICSDA , GPE14:IICSCL 
    
        //pISR_IIC = (unsigned)IicInt;
        INTMSK &= ~(BIT_IIC);
    
          //Enable ACK, Prescaler IICCLK=PCLK/16, Enable interrupt, Transmit clock value Tx clock=IICCLK/16
          // If PCLK 50.7MHz, IICCLK = 3.17MHz, Tx Clock = 0.198MHz
        IICCON = (1<<7) | (0<<6) | (1<<5) | (0xf);
    
        IICADD  = 0x10;                    //2440 slave address = [7:1]
        IICSTAT = 0x10;                    //IIC bus data output enable(Rx/Tx)
        IICLC = (1<<2)|(1);                  // Filter enable, 15 clocks SDA output delay       added by junon
        
        Uart_Printf("\rWrite test data into AT24C02\n");
    
        for(i=0;i<256;i++)
            Wr24C080(0xa0,(unsigned char)i,i);//字节写
               
        for(i=0;i<256;i++)
            data[i] = 0;
    
        Uart_Printf("\rRead test data from AT24C02\n");
        
        for(i=0;i<256;i++)
            Rd24C080(0xa0,(unsigned char)i,&(data[i])); //选择读时序
    
            //Line changed 0 ~ f
        for(i=0;i<16;i++)
        {
                    Uart_Printf("\r");
            for(j=0;j<16;j++)
                Uart_Printf("%2x ",data[i*16+j]);
            Uart_Printf("\n");
        }
        INTMSK |= BIT_IIC;    
        GPEUP  = save_PE;
        GPECON = save_E;
    }
  • 相关阅读:
    【编译原理】文法解析算法以及左递归消除算法
    【编译原理】 DFA词法分析和递归下降语法分析代码
    编译原理 第三章 词法分析(下)
    详解KMP算法
    编译原理 第三章 词法分析(上)
    ExtJs4.0入门错误
    致好友的一封信
    解析Xml四种方法
    Spring AOP实现原理
    Spring Ioc知识整理
  • 原文地址:https://www.cnblogs.com/zpehome/p/2823578.html
Copyright © 2011-2022 走看看