久久久久久久999_99精品久久精品一区二区爱城_成人欧美一区二区三区在线播放_国产精品日本一区二区不卡视频_国产午夜视频_欧美精品在线观看免费

 找回密碼
 立即注冊

QQ登錄

只需一步,快速開始

搜索
查看: 1657|回復: 1
打印 上一主題 下一主題
收起左側

STC12C5A60S2單片機IIC控制PCA9698擴展IO 不運行了?

[復制鏈接]
跳轉到指定樓層
樓主
ID:958676 發表于 2021-8-3 18:25 | 只看該作者 回帖獎勵 |倒序瀏覽 |閱讀模式
單片機源程序如下:
#include        "STC12C5A60S2.h"//主控芯片的頭文件
/************************常用數據類型定義*************************/
#include <intrins.h>
/********************常用數據類型定義**********************/
#define u8  uint8_t
#define u16 uint16_t
#define u32 uint32_t
typedef unsigned char  uint8_t;
typedef unsigned int   uint16_t;
typedef unsigned long  uint32_t;
/*************************宏定義***************************/
//#define  _Nop()  _nop_()   //定義空指令
#define        PCA9698        0x40       //PCA9698地址
/*******************端口/引腳定義區域**********************/
sbit SDA=P3^7;            //模擬I2C數據傳送位
sbit SCL=P3^6;            //模擬I2C時鐘控制位
sbit BLUE=P4^6;
bit ack;                        //應答標志位
/*********************函數聲明區域*************************/
void Delay_MS(u16 Count);                //毫秒延遲函數
void   _Nop();   //定義空指令
void Start_I2c(void);                 //IIC起動總線函數
void Stop_I2c(void);                  //IIC結束總線函數
void SendByte(u8 c);                  //IIC字節發送函數
u8 RcvByte(void);                     //IIC字節接收函數
void Ack_I2c(bit a);                  //IIC應答函數
bit ISendByte(u8 sla,u8 c);//向無子地址器件發送字節數據函數
bit ISendStr(u8 sla,u8 suba,u8 *s,u8 no);
//向有子地址器件發送多字節數據函數
bit IRcvByte(u8 sla,u8 *c);//向無子地址器件讀字節數據函數
bit IRcvStr(u8 sla,u8 suba,u8 *s,u8 no);
//向有子地址器件接收多字節數據函數
//*********************主函數區域**************************/
void main(void)
{

        
  u8 All_ctrl[1]={0x80};
        //設置全組控制寄存器數組(這里為默認值)
        u8 Select_Mode[1]={0x12};
        //設置模式選擇寄存器(這里配置為應答時輸出改變 使能中斷響應)
        u8 GPIO_H[1]={0xff};
        //設置I/O端口狀態數組
        u8 GPIO_L[1]={0x00};
        //設置I/O端口狀態數組
  //u8 In_array[1]={0x7f};
        //設置I/O某端口號為中斷標志位
        Delay_MS(10);
        ISendStr(PCA9698,0X2A,Select_Mode,1);
        //配置模式選擇寄存器地址0x2A
  ISendStr(PCA9698,0X29,All_ctrl,1);
        //配置全組控制寄存器地址0X29
  ISendStr(PCA9698,0X28,GPIO_H,1);
        //配置輸出結構寄存器地址0X28(寫入1為默認推挽,0為開漏),這里配置為推挽
        //ISendStr(PCA9698,0X23,In_array,1);
        //0X23為中斷屏蔽地址寄存器,配置為使用PD8作為中斷標志位
        //當PD8端口狀態改變時中斷發生,中斷輸出引腳In變低電平
  //配置I/0口寄存器(設置為輸出/輸入,A~D組地址為0X18~0X1C)
        ISendStr(PCA9698,0X18,GPIO_L,1);//配置A組I/O為輸出
        ISendStr(PCA9698,0X19,GPIO_L,1);//配置B組I/O為輸出
        ISendStr(PCA9698,0X1A,GPIO_L,1);//配置C組I/O為輸出
        ISendStr(PCA9698,0X1B,GPIO_L,1);//配置D組I/O為輸出
        ISendStr(PCA9698,0X1C,GPIO_L,1);//配置E組I/O為輸出
        while(1)
        {
    //配置輸出端口寄存器(設置輸出相應的狀態,A~E組端口的地址為0X08~0X0C)        
                Delay_MS(500);
                ISendStr(PCA9698,0X08,GPIO_L,1);//A推挽輸出高電平
                ISendStr(PCA9698,0X09,GPIO_L,1);//B推挽輸出高電平
                ISendStr(PCA9698,0X0a,GPIO_L,1);//C推挽輸出高電平
          ISendStr(PCA9698,0X0b,GPIO_L,1);//D推挽輸出高電平
                ISendStr(PCA9698,0X0c,GPIO_L,1);//E推挽輸出高電平
                Delay_MS(500);//延遲閃爍
                ISendStr(PCA9698,0X08,GPIO_H,1);//A推挽輸出低電平
                ISendStr(PCA9698,0X09,GPIO_H,1);//B推挽輸出低電平
                ISendStr(PCA9698,0X0a,GPIO_H,1);//C推挽輸出低電平
    ISendStr(PCA9698,0X0b,GPIO_H,1);//D推挽輸出低電平
                ISendStr(PCA9698,0X0C,GPIO_H,1);//E推挽輸出低電平
        }
}
//***************************************************************/
//起動總線函數Start_I2c(void),無形參,無返回值
//***************************************************************/
void Start_I2c(void)
{
        SDA=1;    //發送起始條件的數據信號
        _Nop();
        SCL=1;
        _Nop();   //起始條件建立時間大于4.7us,延時
        _Nop();
        _Nop();
        _Nop();
        _Nop();   
        SDA=0;    //發送起始信號
        _Nop();   //起始條件鎖定時間大于4μs
        _Nop();
        _Nop();
        _Nop();
        _Nop();      
        SCL=0;   //鉗住I2C總線,準備發送或接收數據
        _Nop();
        _Nop();
}               
//***************************************************************/
//結束總線函數 Stop_I2c(void),無形參,無返回值
//***************************************************************/
void Stop_I2c(void)
{
        SDA=0;   //發送結束條件的數據信號
        _Nop();  //發送結束條件的時鐘信號
        SCL=1;   //結束條件建立時間大于4μs
        _Nop();
        _Nop();
        _Nop();
        _Nop();
        _Nop();
        SDA=1;   //發送I2C總線結束信號
        _Nop();
        _Nop();
        _Nop();
        _Nop();
}
//***************************************************************/
//IIC字節數據傳送函數SendByte(u8 c),有形參c,無返回值
//***************************************************************/
void  SendByte(u8 c)
{
        u8 BitCnt;
        for(BitCnt=0;BitCnt<8;BitCnt++)
        {
                //要傳送的數據長度為8位
                if((c<<BitCnt)&0x80)
                        SDA=1;     //判斷發送位
                else  
                        SDA=0;               
                _Nop();
                SCL=1;      //置時鐘線為高,通知被控器開始接收數據位
                _Nop();
                _Nop();     //保證時鐘高電平周期大于4μs
                _Nop();
                _Nop();
                _Nop();         
                SCL=0;
        }
        _Nop();
        _Nop();
        SDA=1;        //8位發送完后釋放數據線,準備接收應答位
        _Nop();
        _Nop();   
        SCL=1;
        _Nop();
        _Nop();
        _Nop();
        if(SDA==1)
                ack=0;     
        else
                ack=1;      //判斷是否接收到應答信號
        SCL=0;
        _Nop();
        _Nop();
}
//***************************************************************/
//IIC字節數據接收函數RcvByte(void),無形參,有返回值retc
//***************************************************************/
u8  RcvByte(void)
{
        u8 retc;
        u8 BitCnt;
        retc=0;
        SDA=1;       //置數據線為輸入方式
        for(BitCnt=0;BitCnt<8;BitCnt++)
        {
                _Nop();           
                SCL=0;           //置時鐘線為低,準備接收數據位
                _Nop();
                _Nop();         //時鐘低電平周期大于4.7μs
                _Nop();
                _Nop();
                _Nop();
                SCL=1;          //置時鐘線為高使數據線上數據有效
                _Nop();
                _Nop();
                retc=retc<<1;
                if(SDA==1)
                        retc=retc+1; //讀數據位,接收的數據位放入retc中
                _Nop();
                _Nop();
        }
        SCL=0;   
        _Nop();
        _Nop();
        return(retc);
}
//***************************************************************/
//IIC應答子函數Ack_I2c(bit a),有形參a,無返回值
//***************************************************************/
void Ack_I2c(bit a)
{
        if(a==0)
                SDA=0;     //在此發出應答或非應答信號
        else
                SDA=1;
        _Nop();
        _Nop();
        _Nop();      
        SCL=1;
        _Nop();
        _Nop();     //時鐘低電平周期大于4μs
        _Nop();
        _Nop();
        _Nop();  
        SCL=0;     //清時鐘線,鉗住I2C總線以便繼續接收*/
        _Nop();
        _Nop();   
}        
//***************************************************************/
//向無子地址器件發送字節數據函數 ISendByte(u8 sla,u8 c)
//有形參sla:地址;c:發送數據;無返回值
//***************************************************************/
bit ISendByte(u8 sla,u8 c)
{
        Start_I2c();         //啟動總線
        SendByte(sla);       //發送器件地址
        if(ack==0)
                return(0);
        SendByte(c);         //發送數據
        if(ack==0)
                return(0);
        Stop_I2c();          //結束總線
        return(1);
}        
//***************************************************************/
//向有子地址器件發送多字節數據函數ISendStr(u8 sla,u8 suba,u8 *s,u8 no)
//有形參sla:地址;suba:子地址;*s:數據數組;no:字節個數;有返回值1
//***************************************************************/
bit ISendStr(u8 sla,u8 suba,u8 *s,u8 no)
{
        u8 i;
        
        Start_I2c();          //啟動總線

        SendByte(sla);       //發送器件地址
        if(ack==0)
                return(0);

        SendByte(suba);      //發送器件子地址
        if(ack==0)
                return(0);
        
        for(i=0;i<no;i++)
        {   
                SendByte(*s);       //發送數據
                if(ack==0)return(0);
                s++;
        }
         
        Stop_I2c();          //結束總線
         
        return(1);
}        
//***************************************************************/
//向無子地址器件讀字節數據函數IRcvByte(u8 sla,u8 *c)
//有形參sla:地址;suba:發送數據;*c:;有返回值1
//***************************************************************/
bit IRcvByte(u8 sla,u8 *c)
{
        Start_I2c();        //啟動總線

        SendByte(sla+1);    //發送器件地址
        if(ack==0)
                return(0);

        *c=RcvByte();       //讀取數據
        Ack_I2c(1);         //發送非就答位
        Stop_I2c();         //結束總線
        return(1);
}        
//***************************************************************/
//向有子地址器件接收多字節數據函數IRcvStr(u8 sla,u8 suba,u8 *s,u8 no)
//有形參sla:地址;suba:子地址;*s:數據數組;no:字節個數;有返回值1
//***************************************************************/
bit IRcvStr(u8 sla,u8 suba,u8 *s,u8 no)
{
        u8 i;
        
        Start_I2c();           //啟動總線
        SendByte(sla);         //發送器件地址
        if(ack==0)
                return(0);
        SendByte(suba);        //發送器件子地址
        if(ack==0)
                return(0);        
        Start_I2c();
        SendByte(sla+1);
        if(ack==0)
                return(0);
        for(i=0;i<no-1;i++)
        {   
                *s=RcvByte();       //發送數據
                Ack_I2c(0);         //發送就答位
                s++;
        }
        *s=RcvByte();
        Ack_I2c(1);                             //發送非應位
        Stop_I2c();          //結束總線
        return(1);
}
/****************************************************************/
//延時函數delay(),有形參Count用于控制延時函數執行次數,無返回值
/****************************************************************/
void Delay_MS(u16 Count)
{
  u8 i,j;
  while (Count--)//Count形參控制延時次數
  {
    for(i=0;i<100;i++)
      for(j=0;j<40;j++);
  }
}
void _Nop()//1us
{
unsigned char i;
_nop_();
_nop_();
_nop_();
i=1;
while(--i);
}


分享到:  QQ好友和群QQ好友和群 QQ空間QQ空間 騰訊微博騰訊微博 騰訊朋友騰訊朋友
收藏收藏1 分享淘帖 頂 踩
回復

使用道具 舉報

沙發
ID:958676 發表于 2021-8-3 18:28 | 只看該作者
STC89C52上可以,移植到STC12C5A60S2上就不行了,_Nop重新定義以上,機器周期,還是無效
回復

使用道具 舉報

您需要登錄后才可以回帖 登錄 | 立即注冊

本版積分規則

手機版|小黑屋|51黑電子論壇 |51黑電子論壇6群 QQ 管理員QQ:125739409;技術交流QQ群281945664

Powered by 單片機教程網

快速回復 返回頂部 返回列表
主站蜘蛛池模板: 夜夜艹| 国产真实乱对白精彩久久小说 | 欧美综合网 | 中文字幕日韩欧美 | 亚洲精品一区在线 | 岛国毛片 | 欧美视频免费 | 成人免费网站视频 | 欧美三区在线观看 | 国产九一精品 | 日本不卡免费新一二三区 | 91精品国产乱码久久久久久久久 | 高清视频一区二区三区 | 国产精品视频在线播放 | 91五月天| 国产精品乱码一区二区三区 | 九色综合网 | 欧美在线一区二区三区四区 | 国产激情视频在线观看 | 日韩不卡一区二区 | 本地毛片| 黄色成人国产 | 久久久高清 | 99精品欧美一区二区三区综合在线 | 性福视频在线观看 | 久久久久国产一级毛片高清网站 | 91视频www.| 中文字幕精品一区久久久久 | 99精品在线观看 | 久草福利 | 一区二区视频 | 国产性色视频 | h视频免费在线观看 | 精品自拍视频在线观看 | 亚洲欧洲日韩精品 中文字幕 | 欧美日韩综合视频 | 日韩一区二区三区在线观看 | 国产一区二区在线免费视频 | 国产一区二区三区色淫影院 | 日韩精品在线播放 | 日本午夜一区二区三区 |