⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 i2c.c

📁 zilog z80f91单片机的I2C接口函数
💻 C
字号:
/*
 * File       : i2c.c
 * Scope      : 
 *
 * Description:  This contains implementations for I2C protocol
 *
 *
 * Copyright 2003 ZiLOG Inc.  ALL RIGHTS RESERVED.
 *
 * This file contains unpublished confidential and proprietary information
 * of ZiLOG, Inc.
 * NO PART OF THIS WORK MAY BE DUPLICATED, STORED, PUBLISHED OR DISCLOSED 
 * IN ANY FORM WITHOUT THE PRIOR WRITTEN CONSENT OF ZiLOG, INC.
 * This is not a license and no use of any kind of this work is authorized
 * in the absence of a written license granted by ZiLOG, Inc. in ZiLOG's 
 * sole discretion 
 */


// IAR changed
#ifdef _IAR_CODE

#ifdef _EZ80F91
#include <ioez80f91.h>
#endif

#ifdef _EZ80F92
#include <ioez80f92.h>
#endif

#ifdef _EZ80F93
#include <ioez80f92.h>
#endif

#ifdef _EZ80L92
#include <ioez80l92.h>
#endif

#ifdef _EZ80190
#include <ioez80190.h>
#endif

#else
#include <ez80.h>
#endif

#include "i2c.h"
#include "ZTypes.h"
#include "ZSysgen.h"
#include "ZInterrupt.h"



extern RZK_THREADHANDLE_t i2cIntThreadHdl ;
extern void i2cisr(void) ;
extern I2C_CONFIG_t i2cConfigParams ;

/*
 * function name       : I2CDev_Init
 * function description: Initializes I2C1
 * Return values	   : VOID
 * Global variables affected/used: none
 */

VOID I2CDev_Init( VOID )
{
	/** select I2C1 from UZI1 */
#if 0
	UZI1_CTL = 0x03 ;
#endif 
	/** soft reset the I2C1 */
	I2C_SRR = I2C_SRESET ;

	/**
	 * set the clock register for configuring the I2C
	 * sampling frequency (Fsamp) and the I2C clock output
	 * frequency (Fscl)
	 * 
	 * The Fsamp should at least be 1MHz (for 100kbps) and
	 *  be 4 MHz (for 400kbps)
	 *
	 * For Fsamp=50 MHz, it would result in Fscl=416 KHz.
	 * and it turns out to: N=0 and M=11.
	 *
	 * CCR Register: field --0(1):M(11):N(0)
	 *               value --0:1011:000 = 0x58
	 */
	I2C_CCR = i2cConfigParams.speed ;//0x58 ;//0x05 ;

	/** set aak and enab bit */
	I2C_CTL =0x44 ;//0x44 ;

    if(i2cConfigParams.mode == I2C_SLAVE)
    {
		RZKInstallInterruptHandler( (RZK_FNP_ISR)i2cisr, I2C_VECTOR_OFFSET ) ;
		I2C_SAR = i2cConfigParams.selfAddr ;
    	I2C_CTL =	0xC4 ; 	    
    }

	/**
	 * configure port C pins for I2C1 transactions
	 * --in particular, PC0 and PC1 are configured as
	 *   SCL and SDA, respectively
	 */

	PC_ALT2 |= 0x03 ;
	PC_ALT1 &= 0xFC ;
	PC_DDR  |= 0x03 ;
	return ;

}/** end of I2C1_Init() */



/*
 * function name       : I2CDev_SendStart
 * function description: Send START condition and return the status to the caller
 * Return values	   : status /success or error
 * Global variables affected/used: none
 */


INT I2CDev_SendStart( VOID )
{
	UINT32 count = 0 ;
	INT status ;
	UINT8 temp ;

	/**
	 * Enter master transmit mode: send a start condition to begin
	 * the transmission
	 */
//	I2C_CTL &= 0x7F ;
	temp = I2C_CTL ;
	temp = temp | I2CMASK_SET_STA ;
	temp = temp & I2CMASK_CLR_IFLG ;
	I2C_CTL = temp ;


	/** poll on iflag */
	I2C_POLL_IFLG( count, COUNT_POLL_IFLG ) ;

	/** iflag set */
	if( I2C_CTL & I2CMASK_GET_IFLG )
	{
		/** START or repeated START transmitted */
		if( (I2C_SR == I2CSTAT_STARTTXD) || (I2C_SR == I2CSTAT_RPTDSTARTTXD) )
			status = I2CERR_SUCCESS ;
		/** START fail */
		else
			status = I2CERR_STARTFAIL ;

	}/** end 'iflag set' */

	/** timeout */
	else
	{
		status = I2CERR_TIMEOUT ;

	}/** end 'timeout' */
	return status ;
}/** end of I2C1_SendStart() */



/*
 * function name       : I2CDev_SendStart
 * function description: send stop condition
 * Return values	   : status /success or error
 * Global variables affected/used: none
 */

VOID I2CDev_SendStop( VOID )
{
	UINT8 temp ;

	temp = I2C_CTL ;
	temp = temp | I2CMASK_SET_STP ;
	temp = temp & I2CMASK_CLR_IFLG ;
	I2C_CTL = temp ;

//	I2C_SRR = I2C1_SRESET ;
	return ;
}/** end of I2C_SendStop() */


/*
 * function name       : I2CDev_Close
 * function description: Close the I2C communication by soft-resetting the setup
 * Return values	   : status /success or error
 * Global variables affected/used: none
 */

INT I2CDev_Close( VOID )
{
	/** soft reset the I2C1 */
//	I2C_SRR = I2C1_SRESET ;

	/**
	 * Make sure the reset has happened by checking the
	 * STA, STP and IFLG bits for zeros
	 */
	if( I2C_CTL & I2CMASK_SRESET_CONFIRM )
		return I2CERR_CLOSEFAIL ;

	return I2CERR_SUCCESS ;
	
}/** end of I2C1_Close() */


/*
 * function name       : I2CDev_TransmitDataByte
 * function description: transmits the given data byte over the I2C bus
 * Return values	   : status /success or error
 * Global variables affected/used: none
 */


INT I2CDev_TransmitDataByte( INT8 data )
{
	UINT32 count = 0 ;
	INT status ;

//	I2C_CTL |= 0x80 ;

	/** place the data byte to be transmitted in the data register */
	I2C_DR = data ;

	/** clear iflag bit to transmit the data byte */
	I2C_ClearIFlag() ;

	/** poll on iflag to see if the data byte transfer is complete */
	I2C_POLL_IFLG( count, COUNT_POLL_IFLG ) ;

	/** iflag is set */
	if( I2C_CTL & I2CMASK_GET_IFLG )
	{
		UINT8 ch = I2C_SR ;
		switch( ch )
		{
		case I2CSTAT_DATABYTETXDMMODE_ACKRXD:
			{
				status = I2CERR_SUCCESS ;
				break ;
			}

		case I2CSTAT_DATABYTETXDMMODE_ACKNRXD:
			{
				status = I2CERR_DATABYTETXDMMODE_ACKNRXD ;
				break ;
			}

		case I2CSTAT_SLAWTXD_ACKRXD:
			{
				status = I2CERR_SUCCESS ;
				break ;
			}
		case I2CSTAT_SLARTXD_ACKRXD:
			{
				status = I2CERR_SUCCESS ;
				break ;
			}
		case I2CSTAT_SLDATATXD_ACKRXD:
			{
				status = I2CERR_SUCCESS ;
				break ;
			}

		default:
			{
				status = I2CERR_FAILURE ;
				break ;
			}

		}/** end of 'switch' */

	}/** end 'iflag set' */

	/** timeout */
	else
	{
		status = I2CERR_TIMEOUT ;

	}/** end 'timeout' */
	


	return status ;

}/** end of I2C1_TransmitDataByte() */



/*
 * function name       : I2CDev_ReceiveDataByte
 * function description: receives a data byte over the I2C bus
 * Return values	   : status /success or error
 * Global variables affected/used: none
 */


INT I2CDev_ReceiveDataByte( INT8 *data )
{
	UINT32 count = 0 ;
	INT status ;

	/** poll on iflag */
	I2C_POLL_IFLG( count, COUNT_POLL_IFLG ) ;

	/** iflag is set */
	if( I2C_CTL & I2CMASK_GET_IFLG )
	{
		while( (I2C_SR == I2CSTAT_SLARTXD_ACKRXD) && (count < COUNT_POLL_SR) ) count++ ;

		/** read the data */
		*data = I2C_DR ;
		
		/** data byte received, ack transmitted */
		if( I2C_SR == I2CSTAT_DATABYTERXDMMODE_ACKTXD )
		{
			status = I2CERR_SUCCESS ;

		}/** end 'data received, ack transmitted' */

		else if( I2C_SR == I2CSTAT_SLDATARXD_ACKTXD )
		{
			status = I2CERR_SUCCESS ;

		}/** end 'data received, ack transmitted in slave mode' */

		else if( I2C_SR == I2CSTAT_SLAWRXD_ACKTXD )
		{
			status = I2CERR_SUCCESS ;

		}/** end 'data received, ack transmitted in slave mode' */

		/** data byte received, not ack transmitted */
		else if( I2C_SR == I2CSTAT_DATABYTERXDMMODE_NACKTXD )
		{
			status = I2CERR_DATABYTERXDMMODE_NACKTXD ;

		}/** end 'data received, not ack transmitted' */

		/** arbitration lost */
		else if( I2C_SR == I2CSTAT_ARBLOST )
		{
			status = I2CERR_ARBLOST ;

		}/** end 'arb lost' */

		/** unknown error */
		else
		{
			status = I2CERR_FAILURE ;

		}/** end 'unknown' error */

	}/** end 'iflag set' */

	/** timeout */
	else
	{
		status = I2CERR_TIMEOUT ;
	}/** end 'timeout' */
	
	return status ;

}/** end of I2C1_ReceiveDataByte() */

/** end of file */




⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -