關于IIC通信詳解及PCF8563芯片顯示時間數據
這一節,我們的程序代碼主要是將PCF8563芯片采集到的時間數據顯示在數碼管上,但是在完成這個任務之前,我們先來看下IIC協議,了解這個協議很重要,沒辦法,IIC確實讓人稀里糊涂的,先把PCF8563部分的代碼貼出來,然后我們對照PCF8563的數據手冊來看IIC的底層讀寫是怎么實現的。代碼如下:解釋看下面文字,我們的重點不是PCF8563這個芯片,而是IIC協議,這個代碼也是我整理網上的,先把數據手冊上傳
PCF8563數據手冊.pdf
(630.02 KB, 下載次數: 233)
2018-10-13 09:41 上傳
點擊文件名下載附件
- /*******************************************************************************
- * 文件名:PCF8563.c
- * 描 述:工程c模塊文件
- * 功 能:底層模塊文件
- * 作者:MADE BY DA HE TAO
- * 版本號:1.0.4(2015.03.02)
- *******************************************************************************/
- #define _PCF8563_C
- #include "main.h"
- /*******************************************************************************
- * 文件名:變量定義
- * 描 述:
- * 功 能:
- * 作 者:大核桃
- * 版本號:1.0.1(2017.05.23)
- *******************************************************************************/
- uint8 buffer[7];//數據存儲緩存
- sTime CurTime;
- /*******************************************************************************
- * 文件名:void IIC_Delay()
- * 描 述:
- * 功 能:
- * 作 者:大核桃
- * 版本號:1.0.1(2017.03.03)
- *******************************************************************************/
- void IIC_Delay()
- {
- _nop_();
- _nop_();
- _nop_();
- _nop_();
- _nop_();
- _nop_();
- }
- /*******************************************************************************
- * 文件名:void IIC_Start(void)
- * 描 述: IIC啟動
- * 功 能:
- * 作 者:大核桃
- * 版本號:1.0.1(2017.03.03)
- *******************************************************************************/
- void IIC_Start(void)
- {
- IIC_SDA = 1; //為SDA下降啟動做準備
- IIC_SCL = 1; //在SCL高電平時,SDA為下降沿時候總線啟動
- IIC_Delay();
- IIC_SDA = 0; //突變,總線啟動
- IIC_Delay();
- IIC_SCL = 0;
- IIC_Delay();
- }
- /*******************************************************************************
- * 文件名:void IIC_Stop(void)
- * 描 述: IIC停止
- * 功 能:
- * 作 者:大核桃
- * 版本號:1.0.1(2017.03.03)
- *******************************************************************************/
- void IIC_Stop(void)
- {
- IIC_SDA = 0; //為SDA上升做準備
- IIC_Delay();
- IIC_SCL = 1; //在SCL高電平時,SDA為上升沿時候總線停止
- IIC_Delay();
- IIC_SDA = 1; //突變,總線停止
- IIC_Delay();
- }
- /*******************************************************************************
- * 文件名:void IIC_Ack(u8 a)
- * 描 述: 主機向從機發送應答信號
- * 功 能:0:應答信號 1:非應答信號
- * 作 者:大核桃
- * 版本號:1.0.1(2017.03.03)
- *******************************************************************************/
- void IIC_Ack(bit a)
- {
- if(a) IIC_SDA = 1; //放上應答信號電平
- else IIC_SDA = 0;
- IIC_Delay();
- IIC_SCL = 1; //為SCL下降做準備
- IIC_Delay();
- IIC_SCL = 0; //突變,將應答信號發送過去
- IIC_Delay();
- }
- /*******************************************************************************
- * 文件名:u8 IIC_Write_Byte(u8 dat)
- * 描 述: 向IIC總線發送一個字節數據
- * 功 能:dat:要發送的數據 ack:返回應答信號
- * 作 者:大核桃
- * 版本號:1.0.1(2017.03.03)
- *******************************************************************************/
- uint8 IIC_Write_Byte(uint8 dat)
- {
- uint8 iic_ack=0; //iic應答標志
- uint8 mask = 0;
- // for(i = 0;i < 8;i++)
- // {
- // if(dat & 0x80) IIC_SDA = 1; //判斷發送位,先發送高位
- // else IIC_SDA = 0;
- // IIC_Delay();
- // IIC_SCL = 1; //為SCL下降做準備
- // IIC_Delay();
- // IIC_SCL = 0; //突變,將數據位發送過去
- // dat<<=1; //數據左移一位
- // } //字節發送完成,開始接收應答信號
- for(mask = 0x80; mask!= 0x00; mask >>= 1)
- {
- if(mask & dat)
- {
- IIC_SDA = 1;
- }
- else
- {
- IIC_SDA = 0;
- }
- IIC_Delay();
- IIC_SCL = 1; //為SCL下降做準備
- IIC_Delay();
- IIC_SCL = 0; //突變,將數據位發送過去
- }
- IIC_SDA = 1; //釋放數據線
- IIC_Delay();
- IIC_SCL = 1; //為SCL下降做準備
- IIC_Delay();
- //字節發送完成,開始接收應答信號
-
- iic_ack |= IIC_SDA; //讀入應答位
- IIC_SCL = 0;
- return iic_ack; //返回應答信號
- }
- /*******************************************************************************
- * 文件名:u8 IIC_Read_Byte(void)
- * 描 述: 從IIC總線上讀取一個字節數據
- * 功 能:x:讀取到的數據
- * 作 者:大核桃
- * 版本號:1.0.1(2017.03.03)
- *******************************************************************************/
- uint8 IIC_Read_Byte(void)
- {
- uint8 x=0;
- uint8 mask;
- IIC_SDA = 1; //首先置數據線為高電平
- // for(i = 0;i < 8;i++)
- // {
- // x <<= 1; //讀入數據,高位在前
- // IIC_Delay();
- // IIC_SCL = 1; //突變
- // IIC_Delay();
- //
- // if(IIC_SDA)
- // x |= 0x01; //收到高電平
- //
- // IIC_SCL = 0;
- // IIC_Delay();
- // } //數據接收完成
- for(mask = 0x80; mask != 0x00; mask >>= 1)
- {
- IIC_Delay();
- IIC_SCL = 1; //突變
- IIC_Delay();
- if(IIC_SDA)
- {
- x |= mask;
- }
- else
- {
- x &= ~mask;//
- }
- IIC_SCL = 0;
- IIC_Delay();
- }
- IIC_SCL = 0;
- return x; //返回讀取到的數據
- }
- /*******************************************************************************
- * 文件名:static unsigned char RTC_BinToBcd2(unsigned char BINValue)
- * 描 述: 將BIN轉換為BCD
- * 功 能:
- * 作 者:大核桃
- * 版本號:1.0.1(2017.03.03)
- *******************************************************************************/
- static unsigned char RTC_BinToBcd2(unsigned char BINValue)
- {
- unsigned char bcdhigh = 0;
-
- while (BINValue >= 10)
- {
- bcdhigh++;
- BINValue -= 10;
- }
-
- return ((unsigned char)(bcdhigh << 4) | BINValue);
- }
- /*******************************************************************************
- * 文件名:static unsigned char RTC_Bcd2ToBin(unsigned char BCDValue)
- * 描 述: 將BCD轉換為BIN
- * 功 能:
- * 作 者:大核桃
- * 版本號:1.0.1(2017.03.03)
- *******************************************************************************/
- static unsigned char RTC_Bcd2ToBin(unsigned char BCDValue)
- {
- unsigned char tmp = 0;
-
- tmp = ((unsigned char)(BCDValue & (unsigned char)0xF0) >> (unsigned char)0x04) * 10;
- return (tmp + (BCDValue & (unsigned char)0x0F));
- }
- /*******************************************************************************
- * 文件名:void PCF8563_Write_Byte(unsigned char REG_ADD, unsigned char dat)
- * 描 述: PCF8563某寄存器寫入一個字節數據
- * 功 能:REG_ADD:要操作寄存器地址 dat: 要寫入的數據
- * 作 者:大核桃
- * 版本號:1.0.1(2017.03.03)
- *******************************************************************************/
- void PCF8563_Write_Byte(unsigned char REG_ADD, unsigned char dat)
- {
- IIC_Start();
- if(!(IIC_Write_Byte(0xa2))) //發送寫命令并檢查應答位
- {
- IIC_Write_Byte(REG_ADD);
- IIC_Write_Byte(dat); //發送數據
- }
- IIC_Stop();
- }
- /*******************************************************************************
- * 文件名:unsigned char PCF8563_Read_Byte(unsigned char REG_ADD)
- * 描 述: PCF8563某寄存器讀取一個字節數據
- * 功 能:REG_ADD:要操作寄存器地址 讀取得到的寄存器的值
- * 作 者:大核桃
- * 版本號:1.0.1(2017.03.03)
- *******************************************************************************/
- unsigned char PCF8563_Read_Byte(unsigned char REG_ADD)
- {
- unsigned char ReData;
-
- IIC_Start();
- if(!(IIC_Write_Byte(0xa2))) //發送寫命令并檢查應答位
- {
- IIC_Write_Byte(REG_ADD); //確定要操作的寄存器
- IIC_Start(); //重啟總線
- IIC_Write_Byte(0xa3); //發送讀取命令
- ReData = IIC_Read_Byte(); //讀取數據
- IIC_Ack(1); //發送非應答信號結束數據傳送
- }
- IIC_Stop();
- return ReData;
- }
- /*******************************************************************************
- * 文件名:void PCF8563_Write_nByte(unsigned char REG_ADD, unsigned char num, unsigned char *pBuff)
- * 描 述: PCF8563寫入多組數據
- * 功 能:REG_ADD:要操作寄存器起始地址 num: 寫入數據數量 *WBuff: 寫入數據緩存
- * 作 者:大核桃
- * 版本號:1.0.1(2017.03.03)
- *******************************************************************************/
- void PCF8563_Write_nByte(unsigned char REG_ADD, unsigned char num, unsigned char *pBuff)
- {
- unsigned char i = 0;
-
- IIC_Start();
- if(!(IIC_Write_Byte(0xa2))) //發送寫命令并檢查應答位
- {
- IIC_Write_Byte(REG_ADD); //定位起始寄存器地址
- for(i = 0;i < num;i++)
- {
- IIC_Write_Byte(*pBuff); //寫入數據
- pBuff++;
- }
- }
- IIC_Stop();
- }
- /*******************************************************************************
- * 文件名:void PCF8563_Read_nByte(unsigned char REG_ADD, unsigned char num, unsigned char *pBuff)
- * 描 述: PCF8563讀取多組數據
- * 功 能:REG_ADD:要操作寄存器起始地址 num: 寫入數據數量 *WBuff: 讀取數據緩存
- * 作 者:大核桃
- * 版本號:1.0.1(2017.03.03)
- *******************************************************************************/
- void PCF8563_Read_nByte(unsigned char REG_ADD, unsigned char num, unsigned char *pBuff)
- {
- unsigned char i = 0;
-
- IIC_Start();
- if(!(IIC_Write_Byte(0xa2))) //發送寫命令并檢查應答位
- {
- IIC_Write_Byte(REG_ADD); //定位起始寄存器地址
- IIC_Start(); //重啟總線
- IIC_Write_Byte(0xa3); //發送讀取命令
- for(i = 0;i < num;i++)
- {
- *pBuff = IIC_Read_Byte(); //讀取數據
- if(i == (num - 1)) IIC_Ack(1); //發送非應答信號
- else IIC_Ack(0); //發送應答信號
- pBuff++;
- }
- }
- IIC_Stop();
- }
- /*******************************************************************************
- * 文件名:void SetRealTime(sTime* time)
- * 描 述: PCF8563設置時間信息
- * 功 能:
- * 作 者:大核桃
- * 版本號:1.0.1(2017.03.03)
- *******************************************************************************/
- void SetRealTime(sTime* time)
- {
- //
- //拷貝數據
- time->mon &= ~PCF_Century_SetBitC;
- buffer[0] = time->sec;
- buffer[1] = time->min;
- buffer[2] = time->hour;
- buffer[3] = time->day;
- buffer[4] = time->week;
- buffer[5] = time->mon;
- buffer[6] = time->year;
- //寫入數據到寄存器
- //
- PCF8563_Write_nByte(PCF8563_Address_Seconds, 7, buffer);
- }
- /*******************************************************************************
- * 文件名:void GetRealTime(sTime* time)
- * 描 述: PCF8563讀取時間信息
- * 功 能:
- * 作 者:大核桃
- * 版本號:1.0.1(2017.03.03)
- *******************************************************************************/
- void GetRealTime(sTime* time)
- {
- PCF8563_Read_nByte(PCF8563_Address_Seconds, 7, buffer); //讀取寄存器數值
- buffer[0] &= PCF8563_Shield_Seconds; //屏蔽無效位
- buffer[1] &= PCF8563_Shield_Minutes;
- buffer[2] &= PCF8563_Shield_Hours;
- buffer[3] &= PCF8563_Shield_Days;
- buffer[4] &= PCF8563_Shield_WeekDays;
- buffer[5] &= PCF8563_Shield_Months_Century;
- buffer[6] &= PCF8563_Shield_Years;
-
- time->year = buffer[6];
- time->mon = buffer[5];
- time->week = buffer[4];
- time->day = buffer[3];
- time->hour = buffer[2];
- time->min = buffer[1];
- time->sec = buffer[0];
- }
- /*******************************************************************************
- * 文件名: void PCF8563Init(void)
- * 描 述: PCF8563初始化時間
- * 功 能:
- * 作 者:大核桃
- * 版本號:1.0.1(2017.05.23)
- *******************************************************************************/
- void PCF8563Init(void)
- {
- sTime code InitTime[] = {0x17,0x06,0x21, 0x22,0x11,0x00,0x03}; //年月日時分秒星期
- SetRealTime(&InitTime);
- }
復制代碼 打開器件的數據手冊
關于IIC的起始信號和停止信號的定義
從上圖可以看出,在SCL高電平的時候,SDA由高電平到低電平的跳變作為START信號
/*******************************************************************************
- * 文件名:void IIC_Start(void)
- * 描 述: IIC啟動
- * 功 能:
- * 作 者:大核桃
- * 版本號:1.0.1(2017.03.03)
- *******************************************************************************/
- void IIC_Start(void)
- {
- IIC_SDA = 1; //為SDA下降啟動做準備
- IIC_SCL = 1; //在SCL高電平時,SDA為下降沿時候總線啟動
- IIC_Delay();
- IIC_SDA = 0; //突變,總線啟動
- IIC_Delay();
- IIC_SCL = 0;
- IIC_Delay();
- }
復制代碼 再來看停止信號的定義
在SCL為高電平的時候,SDA由低電平到高電平的跳變作為停止信號
- /*******************************************************************************
- * 文件名:void IIC_Stop(void)
- * 描 述: IIC停止
- * 功 能:
- * 作 者:大核桃
- * 版本號:1.0.1(2017.03.03)
- *******************************************************************************/
- void IIC_Stop(void)
- {
- IIC_SDA = 0; //為SDA上升做準備
- IIC_Delay();
- IIC_SCL = 1; //在SCL高電平時,SDA為上升沿時候總線停止
- IIC_Delay();
- IIC_SDA = 1; //突變,總線停止
- IIC_Delay();
- }
復制代碼 看著時序圖很容易就能夠理解的。
接下來我們看下位傳輸的示意圖
從上圖可以看出,SCL為高電平的時候,SDA上的數據被認為是有效的,是可以被讀取或者寫入的,SCL為低電平的時候,SDA的數據是不穩定的,可以任意變化。
關于應答信號和非應答信號
IIC規定應答信號是0,非應答信號是1,如下圖所示這樣,相關程序如下:
- /*******************************************************************************
- * 文件名:void IIC_Ack(u8 a)
- * 描 述: 主機向從機發送應答信號
- * 功 能:0:應答信號 1:非應答信號
- * 作 者:大核桃
- * 版本號:1.0.1(2017.03.03)
- *******************************************************************************/
- void IIC_Ack(bit a)
- {
- if(a) IIC_SDA = 1; //放上應答信號電平
- else IIC_SDA = 0;
- IIC_Delay();
- IIC_SCL = 1; //為SCL下降做準備
- IIC_Delay();
- IIC_SCL = 0; //突變,將應答信號發送過去
- IIC_Delay();
- }
復制代碼
請注意這個子函數不是用來寫字節使用的,是單片機讀數據專用的,啥意思呢?單片機寫字節的時候,是從機返回的應答位,是PCF8563主動返回的,這里的主動相當于是一個按鍵信號,這里的IO是作為按鍵輸入了,不再是輸出信號,這也解釋了為什么很多人寫代碼,總要加一個拉高等于釋放的解釋,什么是釋放?從51單片機IO的結構上判斷,如下圖所示,內部總線寫一個0,在寫鎖存器的幫助下,Q會輸出一個0,Q~輸出一個1,MOS管導通,拉低到低電位,如果內部總線寫一個1,MOS不導通,那么IO會被上拉電阻拉到高電平。這就是IO的輸出0或者1的過程。我們再來看一下輸入信號,
如果你輸出一個0,那么單片機還能夠讀取外部信號嗎?不可能的,因為一直都是0的,就算你按下按鍵也是百搭的,所以必須要拉高,釋放掉,這樣按鍵按下的時候才會在單片機讀引腳信號的幫助下被寫入內部總線上。這下應該明白了吧?
剛才我們說了寫字節要返回的應答位,那么上面這個子函數是讀字節的,誰來讀?當然是單片機來讀啊,也就是說單片機每讀取一個字節,都要向PCF8563發送一個應答位,表示我還要讀你的數據,PCF8563這邊的地址都是自動累加的,不需要管,等到單片機不想讀了,發送一個非應答信號1,結束通信,這就是應答和非應答的由來。
接下來我們再來看下IIC總線讀寫字節函數,這個很有參考意義,因為不管是啥協議,不是從高位開始讀寫就是從低位開始讀寫,具體的時序可能不一樣,但是這個實現的過程是比較有參考意義的,先來看IIC總線寫字節函數,代碼如下
- /*******************************************************************************
- * 文件名:u8 IIC_Write_Byte(u8 dat)
- * 描 述: 向IIC總線發送一個字節數據
- * 功 能:dat:要發送的數據 ack:返回應答信號
- * 作 者:大核桃
- * 版本號:1.0.1(2017.03.03)
- *******************************************************************************/
- uint8 IIC_Write_Byte(uint8 dat)
- {
- uint8 iic_ack=0; //iic應答標志
- uint8 mask = 0;
- // for(i = 0;i < 8;i++)
- // {
- // if(dat & 0x80) IIC_SDA = 1; //判斷發送位,先發送高位
- // else IIC_SDA = 0;
- // IIC_Delay();
- // IIC_SCL = 1; //為SCL下降做準備
- // IIC_Delay();
- // IIC_SCL = 0; //突變,將數據位發送過去
- // dat<<=1; //數據左移一位
- // } //字節發送完成,開始接收應答信號
- for(mask = 0x80; mask!= 0x00; mask >>= 1)
- {
- if(mask & dat)
- {
- IIC_SDA = 1;
- }
- else
- {
- IIC_SDA = 0;
- }
- IIC_Delay();
- IIC_SCL = 1; //為SCL下降做準備
- IIC_Delay();
- IIC_SCL = 0; //突變,將數據位發送過去
- }
- IIC_SDA = 1; //釋放數據線
- IIC_Delay();
- IIC_SCL = 1; //為SCL下降做準備
- IIC_Delay();
- //字節發送完成,開始接收應答信號
-
- iic_ack |= IIC_SDA; //讀入應答位
- IIC_SCL = 0;
- return iic_ack; //返回應答信號
- }
復制代碼 看到被注釋掉的那部分了嗎?和沒有被注釋掉的那部分的作用是一樣一樣的,這個我們先不管他,對于寫單個字節,IIC是這么規定的,先從高位開始讀寫,每寫入一個字節,從機要返回一個應答位,這里的主機指的是單片機,這里的從機指的是采用IIC接口的器件,比如AT24C02,PCF8563等等,也就是說單片機寫入PCF8563某寄存器一個字節后,PCF8563要主動返回一個應答位,這個應答位是0來表示,非應答位用1來表示,實現過程看前邊關于IO的解釋。上面這2種寫字節是一樣的,先來看第一種,我們要讀一個字節,總共8位數據,那么,新建一個循環,先從高位開始發,那么,就這樣寫,如果data數據的最高位是1,那么IIC_SDA就是1,否則IIC_SDA就是0,然后就是拉高IIC_SCL讓數據保持穩定,讓總線來接收這個信號,結束完之后,數據左移就可以了,直到把8位數據發送完畢,就是這樣。
再來看下面這種寫法
- for(mask = 0x80; mask!= 0x00; mask >>= 1)
- {
- if(mask & dat)
- {
- IIC_SDA = 1;
- }
- else
- {
- IIC_SDA = 0;
- }
- IIC_Delay();
- IIC_SCL = 1; //為SCL下降做準備
- IIC_Delay();
- IIC_SCL = 0; //突變,將數據位發送過去
- }
復制代碼 這種寫法是移位,先讀高位,讓位移動,而不是讓數據移動,正好移動8次,這個寫法很好,推薦給大家,很容易讓人理解,寫完8個循環之后,拉高SDA,準備讀取SDA輸入的信號,就是這樣。同樣的讀字節函數,請自我分析完成,一樣的道理。
- IIC_SDA = 1; //釋放數據線
- IIC_Delay();
- IIC_SCL = 1; //為SCL下降做準備
- IIC_Delay();
- //字節發送完成,開始接收應答信號
-
- iic_ack |= IIC_SDA; //讀入應答位
- IIC_SCL = 0;
- return iic_ack; //返回應答信號
復制代碼 再來看下要操作PCF8563這個芯片,要遵循下面這個時序,先來看代碼
- /*******************************************************************************
- * 文件名:void PCF8563_Write_Byte(unsigned char REG_ADD, unsigned char dat)
- * 描 述: PCF8563某寄存器寫入一個字節數據
- * 功 能:REG_ADD:要操作寄存器地址 dat: 要寫入的數據
- * 作 者:大核桃
- * 版本號:1.0.1(2017.03.03)
- *******************************************************************************/
- void PCF8563_Write_Byte(unsigned char REG_ADD, unsigned char dat)
- {
- IIC_Start();
- if(!(IIC_Write_Byte(0xa2))) //發送寫命令并檢查應答位
- {
- IIC_Write_Byte(REG_ADD);
- IIC_Write_Byte(dat); //發送數據
- }
- IIC_Stop();
- }
復制代碼
從上圖可以看出一個完整的寫模式包括 起始信號+設備地址+應答信號+數據地址+應答信號+數據+應答信號+停止信號 組成,每寫入一個字節,PCF8563都要返回一個應答信號0,表示我正確的接收了,相當于一個回執。PCF8563的寫設備地址固定是0XA2,通過程序,可以很容易的理解上面的代碼了。
再來看下PCF8563讀單個字節函數
- /*******************************************************************************
- * 文件名:unsigned char PCF8563_Read_Byte(unsigned char REG_ADD)
- * 描 述: PCF8563某寄存器讀取一個字節數據
- * 功 能:REG_ADD:要操作寄存器地址 讀取得到的寄存器的值
- * 作 者:大核桃
- * 版本號:1.0.1(2017.03.03)
- *******************************************************************************/
- unsigned char PCF8563_Read_Byte(unsigned char REG_ADD)
- {
- unsigned char ReData;
-
- IIC_Start();
- if(!(IIC_Write_Byte(0xa2))) //發送寫命令并檢查應答位
- {
- IIC_Write_Byte(REG_ADD); //確定要操作的寄存器
- IIC_Start(); //重啟總線
- IIC_Write_Byte(0xa3); //發送讀取命令
- ReData = IIC_Read_Byte(); //讀取數據
- IIC_Ack(1); //發送非應答信號結束數據傳送
- }
- IIC_Stop();
- return ReData;
- }
復制代碼 我們看下他的時序圖:
注意PCF8563讀寄存器字節的設備地址固定0XA3,按照時序圖,很容易就能夠理解這段代碼的。
寫多個字節和讀多個字節的函數也是比較容易的,唯一要注意的是時序圖中的解釋,ack from master 和ack from slave 這個一定要理解明白,寫字節對應的是slave,是主機寫,從機返回應答,from master 是讀字節,是主機發出應答或者非應答,從機響應。
- /*******************************************************************************
- * 文件名:void PCF8563_Write_nByte(unsigned char REG_ADD, unsigned char num, unsigned char *pBuff)
- * 描 述: PCF8563寫入多組數據
- * 功 能:REG_ADD:要操作寄存器起始地址 num: 寫入數據數量 *WBuff: 寫入數據緩存
- * 作 者:大核桃
- * 版本號:1.0.1(2017.03.03)
- *******************************************************************************/
- void PCF8563_Write_nByte(unsigned char REG_ADD, unsigned char num, unsigned char *pBuff)
- {
- unsigned char i = 0;
-
- IIC_Start();
- if(!(IIC_Write_Byte(0xa2))) //發送寫命令并檢查應答位
- {
- IIC_Write_Byte(REG_ADD); //定位起始寄存器地址
- for(i = 0;i < num;i++)
- {
- IIC_Write_Byte(*pBuff); //寫入數據
- pBuff++;
- }
- }
- IIC_Stop();
- }
- /*******************************************************************************
- * 文件名:void PCF8563_Read_nByte(unsigned char REG_ADD, unsigned char num, unsigned char *pBuff)
- * 描 述: PCF8563讀取多組數據
- * 功 能:REG_ADD:要操作寄存器起始地址 num: 寫入數據數量 *WBuff: 讀取數據緩存
- * 作 者:大核桃
- * 版本號:1.0.1(2017.03.03)
- *******************************************************************************/
- void PCF8563_Read_nByte(unsigned char REG_ADD, unsigned char num, unsigned char *pBuff)
- {
- unsigned char i = 0;
-
- IIC_Start();
- if(!(IIC_Write_Byte(0xa2))) //發送寫命令并檢查應答位
- {
- IIC_Write_Byte(REG_ADD); //定位起始寄存器地址
- IIC_Start(); //重啟總線
- IIC_Write_Byte(0xa3); //發送讀取命令
- for(i = 0;i < num;i++)
- {
- *pBuff = IIC_Read_Byte(); //讀取數據
- if(i == (num - 1)) IIC_Ack(1); //發送非應答信號
- else IIC_Ack(0); //發送應答信號
- pBuff++;
- }
- }
- IIC_Stop();
- }
復制代碼 好了,就到這里吧,這個程序的結果是寫入PCF8563時間信息,PCF8563讀取到的時間信息顯示在數碼管上。
代碼上傳
011 PCF8563顯示時鐘.rar
(201.48 KB, 下載次數: 300)
2018-10-13 11:19 上傳
點擊文件名下載附件
|