//*********************************************************?
//*??????????? 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? */
#i nclude
#i nclude
#i nclude
#i nclude "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
}
//***********************************************
//*???????? Sequential Read from EEPROM???????????????
//*
//*?? - ctrl : Control Byte of EEPROM?
//*?? - addr : Location of EEPROM???
//*?? - length : Read counter
//*?? - *dptr : Store EEPROM data to RAM
//*
//***********************************************
void EE_SEQU_Read(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 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
?while (length!=0)
?{
? *dptr=ReadI2C();?? // Enable I2C Receiver & Store EEPROM data to Point buffer
? I2C_Done();
? dptr++;
? length--;
???
? if (length==0) NotAckI2C();
? else AckI2C();??? // Continue read next data, send a acknowledge to EEPROM
?
? I2C_Done();
?}
??? 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;
}
評論
查看更多