www.pudn.com > s3c2443_test_code.zip > IIC.c


;/********************************************************************* 
;* Project Name : mDirac III 
;* 
;* Copyright 2005 by Samsung Electronics, Inc. 
;* All rights reserved. 
;* 
;* Project Description : 
;* This software is only for verifying functions of the mDirac III 
;* Anybody can use this code without our permission. 
;********************************************************************** 
;* 
;*	Description	:	Code for the basic function for IIC. 
;*					It can support write and read mode with 7-bit addresses 
;*					Can make the 10-bit address write and read mode 
;*					with assemble these functions. 
;*	 
;*	History 
;*			R0.0 (2005.9.30) : Y.C.Kwon draft 
;* 
;**********************************************************************/ 
 
#include "System.h" 
 
 
#define	SlaveRX			(0) 
#define	SlaveTX			(1) 
#define	MasterRX		(2) 
#define	MasterTX		(3) 
 
 
static volatile char *IIC_BUFFER; 
static volatile unsigned int IIC_PT; 
static unsigned int IIC_DATALEN; 
static volatile unsigned char IIC_STAT; 
 
 
void __irq IIC_Int( void) 
{ 
	IIC_STAT = rIICSTAT; 
 
	switch( (IIC_STAT>>6)&0x3) { 
 
	case SlaveRX	:	break; 
 
	case SlaveTX	:	break; 
 
	case MasterRX	:	if (IIC_PT>0) 
							IIC_BUFFER[IIC_PT-1] = rIICDS; 
 
						IIC_PT++; 
 
						if (IIC_PT==IIC_DATALEN) 
							rIICCON 	&=  ~(1<<7); 
						else if (IIC_PT>IIC_DATALEN) 
							rIICSTAT	=	0x90;			//	Stop Master Rx condition 
 
						rIICCON &= ~(1<<4);					//	Clear pending bit to resume 
						break; 
 
	case MasterTX	:	if (IIC_PT>4)/freq)>0xf) { 
		clk_prescaler	=	1; 
		clk_divider		=	(PCLK>>9)/freq;		//	PCLK/512/freq 
	} else { 
		clk_prescaler	=	0; 
		clk_divider		=	(PCLK>>4)/freq;		//	PCLK/16/freq 
	} 
 
    pISR_IIC = (unsigned)IIC_Int; 
	rINTMSK &= ~(BIT_IIC); 
 
	//	Prescaler IICCLK=PCLK/16, Enable interrupt, Transmit clock value Tx clock=IICCLK/16 
	rIICCON		=	(clk_prescaler<<6) | (1<<5) | (clk_divider&0xf); 
 
	rIICADD		=	0x10;							//	Slave address = [7:1] 
	rIICSTAT	=	0x10;                  			//	IIC bus data output enable(Rx/Tx) 
	rIICLC		=	0;		 						//	SDA Filter disable 
} 
 
 
void IIC_close( void) 
{ 
	rINTMSK |= BIT_IIC; 
 
	rIICSTAT = 0x0;                    		//	IIC bus data output disable(Rx/Tx) 
} 
 
//	Write Mode Format with 7-bit addresses 
void IIC_Write( unsigned char SlaveAddr, char *Data, unsigned int n) 
{ 
	while(rIICSTAT&(1<<5));					//	Wait until IIC bus is free. 
 
	IIC_BUFFER	=	Data; 
	IIC_PT		=	0; 
	IIC_DATALEN	=	n; 
 
	rIICCON 	|=  (1<<7); 
	rIICDS		=	SlaveAddr; 
	rIICSTAT	=	0xF0;					//	Master Tx Start. 
} 
 
//	Read Mode Format with 7-bit addresses 
void IIC_Read( unsigned char SlaveAddr, char *Data, unsigned int n) 
{ 
	while(rIICSTAT&(1<<5));					//	Wait until IIC bus is free. 
 
	IIC_BUFFER	=	Data; 
	IIC_PT		=	0; 
	IIC_DATALEN	=	n; 
 
	rIICCON 	|=  (1<<7); 
	rIICDS		=	SlaveAddr; 
	rIICSTAT	=	0xB0;					//	Master Rx Start 
} 
 
void IIC_Wait( void)						//	Waiting for the command takes effect. 
{											//	But not for IIS bus free. 
	while(IIC_PT<=IIC_DATALEN); 
} 
 
unsigned char IIC_Status( void)						//	Return IIC Status Register value at last interrupt occur. 
{ 
	return	IIC_STAT; 
} 
 
 
//****************************************************************// 
//*	Basic test code for Serial EEPROM with the basic functions. 
//****************************************************************// 
 
#define	EEPROMSlaveAddr		0xa0 
 
void WrSerialEEPROM( char Addr, char Data) 
{ 
	char D[2]; 
 
	D[0]=Addr; 
	D[1]=Data; 
	IIC_Write( EEPROMSlaveAddr, D, 2); 
 
	do	{									//	Polling for an ACK signal from SerialEEPROM. 
		IIC_Write( EEPROMSlaveAddr, NULL, 0); 
		IIC_Wait(); 
	} while(IIC_Status()&0x1); 
} 
 
void RdSerialEEPROM( char Addr, char *Data) 
{ 
	IIC_Write( EEPROMSlaveAddr, &Addr, 1); 
	IIC_Read( EEPROMSlaveAddr, Data, 1); 
	IIC_Wait();								//	Waiting for read complete. 
} 
 
void Test_IIC( void) 
{ 
    unsigned int i; 
    char D; 
 
    printf("[ IIC Test using Serial EEPROM ]\n"); 
 
	IIC_open(200000);	//	Serial EEPROM IIC clk = 200KHz 
 
 
    printf("\nWrite (0xff) and read back from EEPROM\n"); 
     
    for(i=0;i<256;i++) { 
        D=0; 
        WrSerialEEPROM(i,0xff); 
        RdSerialEEPROM(i,&D); 
        printf("%02x ",D); 
        if ((i&0xf)==0xf) printf("\n"); 
    } 
 
    printf("\nWrite (0~255) and read back from EEPROM\n"); 
     
    for(i=0;i<256;i++) { 
        D=0; 
        WrSerialEEPROM(i,i); 
        RdSerialEEPROM(i,&D); 
        printf("%02x ",D); 
        if ((i&0xf)==0xf) printf("\n"); 
    } 
 
    IIC_close(); 
}