標(biāo)題: C51單片機(jī)通過I2C對EEPROM進(jìn)行頁讀取的問題求助 [打印本頁]

作者: Calemnt    時間: 2018-11-13 07:58
標(biāo)題: C51單片機(jī)通過I2C對EEPROM進(jìn)行頁讀取的問題求助
我在嘗試移植教材上的程序時,發(fā)現(xiàn)在頁讀取EEPROM時,第9位應(yīng)答位假如直接置1或置0,就可以順利讀取,但由形參傳遞1或0給應(yīng)答位時,就只能讀到一串0,這是什么原因?



作者: 浮念    時間: 2018-11-13 11:02
你可以在論壇里面搜集一下,有很多現(xiàn)成的程序可以參考學(xué)習(xí)。要善用論壇的搜索功能。
作者: Calemnt    時間: 2018-11-13 12:16
浮念 發(fā)表于 2018-11-13 11:02
你可以在論壇里面搜集一下,有很多現(xiàn)成的程序可以參考學(xué)習(xí)。要善用論壇的搜索功能。

程序上我沒有太大的問題,這部分程序我也是移植后再自己重新編寫了的,主要就是想不明白為啥直接置位可以,用形參置位就出問題了,形參置位和直接置位有啥區(qū)別嗎?
作者: ahshmj    時間: 2018-11-13 15:53
怎么用圖形貼出來,而不用文本格式呢?別人想試一試程序還要照圖抄一遍?
作者: Calemnt    時間: 2018-11-13 17:35
ahshmj 發(fā)表于 2018-11-13 15:53
怎么用圖形貼出來,而不用文本格式呢?別人想試一試程序還要照圖抄一遍?

額,好吧,我把程序列出來
作者: Calemnt    時間: 2018-11-13 17:39
----------------------------------------------------------------主函數(shù)
#include <reg52.h>
#define u8 unsigned char
#define u16 unsigned int

extern void Int_Lcd();
extern void Lcd_Show(u8 x,u8 y,u8 *set);
extern void EE_Read(u8 *buf,u8 addr,u8 len);
extern void EE_Write(u8 *buf,u8 addr,u8 len);

void Str_Convert(u8 *str,u8 *src,u8 len);

void main()
{
        u8 buf[5]={5,2,8,6,1};
        u8 str[20];
       
        Int_Lcd();
//        EE_Write(buf,0x00,sizeof(buf));              //EEPROM寫入
        EE_Read(buf,0x00,sizeof(buf));          //EEPROM讀取
        Str_Convert(str,buf,sizeof(buf));       //字符串轉(zhuǎn)化函數(shù)
        Lcd_Show(0,0,str);                      //1cd1602顯示
        while(1);
}

void Str_Convert(u8 *str,u8 *src,u8 len)
{
        u8 tem;
        while(len--)
        {
                tem=*src>>4;
                if(tem<=9)
                        *str++=tem+'0';
                else
                        *str++=tem-10+'a';
                tem=*src&0x0f;
                if(tem<=9)
                        *str++=tem+'0';
                else
                        *str++=tem-10+'a';
                *str++=' ';
                src++;
        }
}
----------------------------------------------------------------LCD1602
#include <reg52.h>
#define u8 unsigned char
#define u16 unsigned int
#define LCD_DB P0

sbit LCD_RS=P2^6;
sbit LCD_RW=P2^5;
sbit LCD_E=P2^7;
       
void LCD_Wait_Ready()
{
        u8 sta;

        LCD_DB=0xff;
        LCD_RS=0;
        LCD_RW=1;
        do
        {
                LCD_E=1;
                sta=LCD_DB;
                LCD_E=0;
        }
        while(sta & 0x80);
}

void LCD_Write_Cmd(u8 cmd)
{
        LCD_Wait_Ready();
        LCD_RS=0;
        LCD_RW=0;
        LCD_DB=cmd;
        LCD_E=1;
        LCD_E=0;
}

void LCD_Write_Dat(u8 dat)
{
        LCD_Wait_Ready();
        LCD_RS=1;
        LCD_RW=0;
        LCD_DB=dat;
        LCD_E=1;
        LCD_E=0;
}

void Lcd_Set_Cursor(u8 x,u8 y)
{
        u8 addr;
        if(y==0)
                addr=0x00+x;
        else
                addr=0x40+x;
        LCD_Write_Cmd(addr | 0x80);
}

void Lcd_Show(u8 x,u8 y,u8 *str)
{
        Lcd_Set_Cursor(x,y);
        while(*str!='\0')
        {
                LCD_Write_Dat(*str++);
        }
}

void Int_Lcd()
{
        LCD_Write_Cmd(0x38);
        LCD_Write_Cmd(0x0c);
        LCD_Write_Cmd(0x06);
        LCD_Write_Cmd(0x01);
}
----------------------------------------------------------------I2C
#include <reg52.h>
#include <intrins.h>
#define u8 unsigned char
#define u16 unsigned int

sbit SCL=P2^1;
sbit SDA=P2^0;
sbit LED1=P0^0;
sbit LED2=P0^1;

void Dealy()
{
        u8 i;
       
        for(i=0;i<10;i++)
                _nop_();
}

void I2C_Start()
{
        SDA=1;
        SCL=1;
        Dealy();
        SDA=0;
        Dealy();
        SCL=0;
        Dealy();
}

void I2C_Stop()
{
        SCL=0;
        SDA=0;
        Dealy();
        SCL=1;
        Dealy();
        SDA=1;
        Dealy();
}

bit I2C_Write(u8 dat)         //I2C寫入
{
        bit ack;
        u8 mask;
       
        for(mask=0x80;mask>0;mask>>=1)
        {
                if((mask & dat)==0)
                        SDA=0;
                else
                        SDA=1;
                Dealy();
                SCL=1;
                Dealy();
                SCL=0;
                Dealy();
        }
        SDA=1;
        Dealy();
        SCL=1;
        ack=SDA;
        Dealy();
        SCL=0;
        Dealy();
        return (~ack);
}

u8 I2C_Read(bit ack)         //I2C讀取
{
        u8 dat,i;
       
        SDA=1;
        Dealy();             //延時10us
        for(i=0;i<8;i++)
        {
                SCL=1;
                Dealy();
                dat<<=1;
                dat |= SDA;
                Dealy();
                SCL=0;
                Dealy();
        }
        SDA=ack;     //SDA由形參ack控制
        Dealy();
        SCL=1;
        Dealy();
        SCL=0;
        Dealy();
        return dat;
}

u8 I2C_ReadACK()
{
        u8 dat,i;
       
        SDA=1;
        Dealy();         //延時10us
        for(i=0;i<8;i++)
        {
                SCL=1;
                Dealy();
                dat<<=1;
                dat |= SDA;
                Dealy();
                SCL=0;
                Dealy();
        }
        SDA=0;      //SDA直接置0
        Dealy();
        SCL=1;
        Dealy();
        SCL=0;
        Dealy();
        return dat;
}

u8 I2C_ReadNAK()
{
        u8 dat,i;
       
        SDA=1;
        Dealy();
        for(i=0;i<8;i++)
        {
                SCL=1;
                Dealy();
                dat<<=1;
                dat |= SDA;
                Dealy();
                SCL=0;
                Dealy();
        }
        SDA=1;       //SDA直接置1
        Dealy();
        SCL=1;
        Dealy();
        SCL=0;
        Dealy();
        return dat;
}
----------------------------------------------------------------EEPROM
#include <reg52.h>
#define u8 unsigned char
#define u16 unsigned int

extern void I2C_Start();
extern void I2C_Stop();
extern bit I2C_Write(u8 dat);
extern bit I2C_Read(bit ack);
extern u8 I2C_ReadACK();
extern u8 I2C_ReadNAK();

void EE_Read(u8 *buf,u8 addr,u8 len)       //EEPROM讀取,len讀取長度
{
        do
        {
                I2C_Start();
                if(I2C_Write(0x50<<1))
                        break;
                I2C_Stop();
        }
        while(1);
        I2C_Write(addr);            //寫入讀取的起始地址
        I2C_Start();
        I2C_Write((0x50<<1)|0x01);
        while(len>1)
        {
                *buf++=I2C_Read(0);       //應(yīng)答位置0
//                *buf++=I2C_ReadACK();
                len--;
        }
        *buf=I2C_Read(1);           //應(yīng)答位置1
//        *buf=I2C_ReadNAK();
        I2C_Stop();
}

void EE_Write(u8 *buf,u8 addr,u8 len)       //EEPROM寫入
{
        while(len>0)
        {
                do
                {
                        I2C_Start();
                        if(I2C_Write(0x50<<1))
                                break;
                        I2C_Stop();
                }
                while(1);
                I2C_Write(addr);
                while(len>0)
                {
                        I2C_Write(*buf++);
                        len--;
                        addr++;
                        if((addr&0x07)==0)
                                break;
                }
                I2C_Stop();       
        }
}
作者: Calemnt    時間: 2018-11-13 22:11
ahshmj 發(fā)表于 2018-11-13 15:53
怎么用圖形貼出來,而不用文本格式呢?別人想試一試程序還要照圖抄一遍?

大佬求幫忙看看
作者: zl2168    時間: 2018-11-14 08:23
實例49  讀寫AT24C02




歡迎光臨 (http://www.torrancerestoration.com/bbs/) Powered by Discuz! X3.1