技术热线: 4007-888-234

PIC:以C 语言完成读写24LCxx系列的EEPROM

更新时间: 2019-03-26
阅读量:2023

PIC:以C 语言完成读写24LCxx系列的EEPROM

//************************************************************************ //* Using I2C Master Mode for access Slave (EEPRM) //* //* Written by: Richard Yang //* Sr. Corporate Application Engineer //* Microchip Technology Inc. //* Date: Oct. 3nd '2002 //* Revision: 1.00 //* Language tools : MPLAB-C18 v2.09.13 //* MPLINK v3.10 //* MPLAB-IDE v6.00.17 & ICD2 //************************************************************************ /* Include Header files */

#include #include // Load I2C Header file from defult direct #include #include "P18LCD.h" // Load P18LCD Header file form current working direct

/* Declare the Function Prototype */

void Initialize_I2C_Master(void); void EE_Page_Write(unsigned char,unsigned char,unsigned char,unsigned char *); void EE_SEQU_Read(unsigned char,unsigned char,unsigned char,unsigned char *); void EEPROM_Write(unsigned char,unsigned char,unsigned char); void EEPROM_ACK(unsigned char); unsigned char EEPROM_Read(unsigned char,unsigned char); void I2C_Done(void); void Initialize_Timer2(void); void isr_high_direct(void); void isr_high(void);

#pragma romdata My_romdata=0x1000 const rom far unsigned char LCD_MSG1[]="SW2: Byte Write "; const rom far unsigned char LCD_MSG2[]="SW6: Random Read"; const rom far unsigned char LCD_MSG3[]="Byte Write Mode "; const rom far unsigned char LCD_MSG4[]="Random Read Mode"; const rom far unsigned char LCD_MSG5[]="Sended: "; const rom far unsigned char LCD_MSG6[]="Send: "; const rom unsigned char I2C_Write_Buffer[]="Microchip Technology"; #pragma romdata

/* Define following array in data memory */

unsigned char I2C_Read_Buffer [32];

/* define following variable in data memory at Access Bank */ #pragma udata access My_RAM near unsigned char Debounce; near unsigned char Send_Addr; near unsigned char Send_Data; near unsigned char Send_Length; near unsigned char Read_Data; near unsigned char P_SW2; near unsigned char P_SW6; #pragma udata

#define Page_Length 8 #define SW2 PORTAbits.RA4 #define SW6 PORTEbits.RE1 #define Bounce_Time 6 #define EE_CMD 0xA0

//*********************************************************** /* */ /* Main Program */ /* */ //***********************************************************

void main(void) { ADCON1=0b00000110; // Disable A/D Function TRISAbits.TRISA4=1; // Set SW2 for input TRISEbits.TRISE1=1; // Set SW6 for Input Initialize_Timer2( ); Initialize_I2C_Master( ); OpenLCD( ); if (SW2 & SW6)Debounce=0; else Debounce = Bounce_Time; while(1) { LCD_Set_Cursor(0,0); // Put LCD Cursor on (0,0) putrsLCD(LCD_MSG1); LCD_Set_Cursor(1,0); // Put LCD Cursor on (1,0) putrsLCD(LCD_MSG2); P_SW2=P_SW6=0; 

Send_Addr=0; while(1) { if (P_SW2) { P_SW2=0; Debounce = Bounce_Time; LCD_Set_Cursor(0,0); // Put LCD Cursor on (0,0) putrsLCD(LCD_MSG3); LCD_Set_Cursor(1,0); // Put LCD Cursor on (0,0) putrsLCD(LCD_MSG5); do { while (!P_SW2); P_SW2=0; LCD_Set_Cursor(1,8); Send_Data=I2C_Write_Buffer[Send_Addr]; EEPROM_Write(EE_CMD,Send_Addr,Send_Data); puthexLCD(EE_CMD); putcLCD(' '); puthexLCD(Send_Addr); putcLCD(' '); puthexLCD(Send_Data); EEPROM_ACK(EE_CMD); Send_Addr++; } while (I2C_Write_Buffer[Send_Addr]!=0x00); break; } if (P_SW6) { P_SW6=0; Debounce = Bounce_Time; 

LCD_Set_Cursor(0,0); // Put LCD Cursor on (0,0) putrsLCD(LCD_MSG4); LCD_Set_Cursor(1,0); // Put LCD Cursor on (0,0) putrsLCD(LCD_MSG6); while(1) { if (P_SW6) { P_SW6=0; LCD_Set_Cursor(1,5); Read_Data = EEPROM_Read(EE_CMD,Send_Addr); puthexLCD(EE_CMD); putcLCD(' '); puthexLCD(Send_Addr); putcLCD(' '); puthexLCD(EE_CMD); putcLCD(' '); puthexLCD(Read_Data); Send_Addr++; } if (P_SW2) break; } if (P_SW2) break; } if (P_SW2) { P_SW2=0; break; } } } } //************************************************ //* #pragma Interrupt Declarations * //* * //* Function: isr_high_direct * //* - Direct execution to the actual * //* high-priority interrupt code. * //************************************************ #pragma code isrhighcode = 0x0008

void isr_high_direct(void) { _asm //begin in-line assembly goto isr_high //go to isr_high function _endasm //end in-line assembly } #pragma code

//************************************************ //* Function: isr_high(void) * //* High priority interrupt for Timer2 * //************************************************ #pragma interrupt isr_high

void isr_high(void) { PIR1bits.TMR2IF=0; // Clear Timer2 interrupt Flag if (Debounce==0) { if (!SW2) { P_SW2=1; Debounce =Bounce_Time; } if (!SW6) { P_SW6=1; Debounce =Bounce_Time; } } else if (SW2 & SW6)Debounce--; else Debounce =Bounce_Time; } #pragma code

//*********************************************** //* Write a Byte to EEPROM //* - ctrl : Control Byte of EEPROM //* - addr : Location of EEPROM //* - data : Data Byte of EEPROM //***********************************************

void Initialize_Timer2(void) {

RCONbits.IPEN=1; // Enable Interrupt Priority bit IPR1bits.TMR2IP=1; // Set Timer2 for High Priority INTCONbits.GIEH=1; // Enable High Priority Interrupt

OpenTimer2 (TIMER_INT_ON // Turn On the Timer2 with Interrupt & T2_PS_1_4 // (4Mhz/4) [4*10*(99+1)] = 4mS */ & T2_POST_1_10);

PR2 = 99; }

//*********************************************** //* Write a Byte to EEPROM * //* - ctrl : Control Byte of EEPROM * //* - addr : Location of EEPROM * //* - data : Data Byte of EEPROM * //*********************************************** void EEPROM_Write(unsigned char ctrl,unsigned char addr,unsigned char data) { IdleI2C(); // ensure module is idle StartI2C(); // Start condition I2C_Done(); // Wait Start condition completed and clear SSPIF flag 

WriteI2C(ctrl); // Write Control+Write to EEPROM & Check BF flag while(SSPCON2bits.ACKSTAT); // wait until received the Acknowledge from EEPROM I2C_Done(); // Clear SSPIF flag

WriteI2C(addr); // Write Address to EEPROM while(SSPCON2bits.ACKSTAT); // wait until received the Acknowledge from EEPROM I2C_Done();

WriteI2C(data); // Write Data to EEPROM while(SSPCON2bits.ACKSTAT); // wait until received the Acknowledge from EEPROM I2C_Done();

StopI2C(); // Stop condition I2C_Done(); // Wait the Stop condition completed }

//*********************************************** //* Pae Write to EEPROM //* //* - ctrl : Control Byte of EEPROM //* - addr : Location of EEPROM //* - length : Write counter //* - *dptr : RAM point --> EEPROM //* //*********************************************** void EE_Page_Write(unsigned char ctrl,unsigned char addr,unsigned char length,unsigned char *dptr) { IdleI2C(); // ensure module is idle StartI2C(); // Start condition I2C_Done(); // Wait Start condition completed WriteI2C(ctrl); // Write Control+Write to EEPROM & Check BF flag while(SSPCON2bits.ACKSTAT); // wait until received the Acknowledge from EEPROM I2C_Done(); // Clear SSPIF flag

WriteI2C(addr); // Write Address to EEPROM while(SSPCON2bits.ACKSTAT); // wait until received the Acknowledge from EEPROM I2C_Done();

while (length!=0) // Check write completed ? { WriteI2C(*dptr); // Write data to EEPROM while(SSPCON2bits.ACKSTAT); // wait until received the Acknowledge from EEPROM I2C_Done(); dptr++; // Point to next byte length--; } StopI2C(); // Stop condition I2C_Done(); // Wait the Stop condition completed } //*********************************************** //* EEPROM Acknowledge Polling * //* -- The routine will polling the ACK * //* response from EEPROM * //* -- ACK=0 return * //* -- ACK=1 send Restart & loop check * //*********************************************** void EEPROM_ACK(unsigned char ctrl) { unsigned char i;

IdleI2C(); // ensure module is idle StartI2C(); // Start condition I2C_Done(); // Wait Start condition completed

WriteI2C(ctrl); // Write Control to EEPROM (WRITE) I2C_Done(); // Clear SSPIF flag

while (SSPCON2bits.ACKSTAT) // test for Acknowledge from EEPROM { for (i=0;i<100;i++); // Delay for next Repet-Start

RestartI2C(); // initiate Repet-Start condition I2C_Done(); // Wait Repet-Start condition completed

WriteI2C(ctrl); // Write Control to EEPROM (WRITE) I2C_Done(); // Clear SSPIF flag } StopI2C(); // send STOP condition I2C_Done(); // wait until stop condition is over }

//*********************************************** //* Random Read a Byte from EEPROM * //* - ctrl : Control Byte of EEPROM (Write) * //* (Ctrl +1 ) : Read Command * //* - addr : Address Byte of EEPROM * //* - Return : Read Data from EEPROM * //*********************************************** unsigned char 

EEPROM_Read(unsigned char ctrl,unsigned char addr) { unsigned char f; IdleI2C(); // ensure module is idle StartI2C(); // Start condition I2C_Done(); // Wait Start condition completed

WriteI2C(ctrl); // Write Control to EEPROM while(SSPCON2bits.ACKSTAT); // test for ACK condition, if received I2C_Done(); // Clear SSPIF flag

WriteI2C(addr); // Write Address to EEPROM while(SSPCON2bits.ACKSTAT); // test for ACK condition, if received I2C_Done(); // Clear SSPIF flag

RestartI2C(); // initiate Restart condition I2C_Done();

WriteI2C(ctrl+1); // Write Control to EEPROM while(SSPCON2bits.ACKSTAT); // test for ACK condition, if received I2C_Done(); // Clear SSPIF flag

f=ReadI2C(); // Enable I2C Receiver & wait BF=1 until received data I2C_Done(); // Clear SSPIF flag

NotAckI2C(); // Genarate Non_Acknowledge to EEPROM I2C_Done(); StopI2C(); // send STOP condition I2C_Done(); // wait until stop condition is over

return(f); // Return Data from EEPROM }

StopI2C(); // send STOP condition I2C_Done(); // wait until stop condition is over }

//*********************************************** //* Check I2C action that is completed * //*********************************************** void I2C_Done(void) { while (!PIR1bits.SSPIF); // Completed the action when the SSPIF is Hi. PIR1bits.SSPIF=0; // Clear SSPIF }

//************************************************ //* Initial I2C Master Mode with 7 bits Address * //* Clock Speed : 100KHz @4MHz * //************************************************ void Initialize_I2C_Master(void) { OpenI2C(MASTER,SLEW_ON); SSPADD= 9; }