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

📄 io2w.c

📁 美国模拟混合器件领导厂商Silabs 芯科实验室 收音机系列 源码
💻 C
字号:
//-----------------------------------------------------------------------------
// Includes
//-----------------------------------------------------------------------------
#include <c8051f320.h>        
#include <stddef.h>       
#include "typedefs.h"

//-----------------------------------------------------------------------------
// Defines
//-----------------------------------------------------------------------------
#define READ	1
#define WRITE	0

#define IO2W_ADDRESS 0x20

//-----------------------------------------------------------------------------
// Global variables
//-----------------------------------------------------------------------------
sbit RSTB     = P1^3;
sbit SENB     = P1^2;
sbit SCLK     = P1^1;
sbit SDIO     = P0^7;


//-----------------------------------------------------------------------------
// Function prototypes
//-----------------------------------------------------------------------------

void wait_us(u16 us);
void wait_ns(u16 ns);
void _nop_(void);


//-----------------------------------------------------------------------------
// Externals
//-----------------------------------------------------------------------------



//-----------------------------------------------------------------------------
// This is used just for debugging to detect when the si470x is not responding.
// The 470x should always ack 2-wire transactions.  If it does not, there is a
// hardware problem that must be resolved.
//-----------------------------------------------------------------------------
static void die(void)
{
 	_nop_ ();		// put breakpoint here during debug.
}		   

//-----------------------------------------------------------------------------
// Send a 2-wire stop.
//-----------------------------------------------------------------------------
static void io2w_stop(void)
{
	SCLK = 0;
	wait_us(2);											// tf:IN + tLOW
	SDIO = 0;
	wait_us(1);
	SCLK = 1;
	wait_us(1);											// tf:IN + tSU:STO
	SDIO = 1;
}


//-----------------------------------------------------------------------------
// Send a 2-wire start and address byte.
//
// Inputs:
//		io2w_address:  Address of device to access.  LSB will be set to 
//			indicate a read, cleared to indicate a write.
//
//-----------------------------------------------------------------------------
static void io2w_start (u8 io2w_address)
{
	i8 i; 
	
	// issue the START condition
	wait_us(1);											// tSU:STA
	SDIO = 0;
	wait_us(1);											// tHD:STA
	SCLK = 0;

	// issue the control word (7 bit chip address + R/W* bit)
	// Note that tr:IN + tLOW + tf:IN + tHIGH = 2500 ns = 400 kHz
	for (i=7; i>=0; i--) 
	{
		SCLK = 0;
		wait_us(1);										// tf:IN
		SDIO = ((io2w_address >> i) & 0x01);
		wait_us(1);										// tLOW
		SCLK = 1;
		wait_us(1);										// tf:IN + tHIGH
	}
	// check the acknowledge
	SCLK = 0;
	SDIO = 1;
	wait_us(2);											// tf:IN + tLOW
	SCLK = 1;
	wait_us(1);											// tf:IN + tHIGH
	if (SDIO != 0)
		die(); 	// ack not received.  This should never happen. Device isn't responding.
}	


//-----------------------------------------------------------------------------
// Write one byte of data.
//
// Inputs:
//		wrdata:  Byte to be written
//
//-----------------------------------------------------------------------------
static void io2w_write_byte (u8 wrdata)
{
	i8 i;	
	
	for (i=7; i>=0; i--)
	{
		SCLK = 0;
		wait_us(1);									// tf:IN
		SDIO = ((wrdata >> i) & 0x01); 
		wait_us(2);									// tLOW
		SCLK = 1;
		wait_us(1);									// tf:IN + tHIGH
	}
	// check the acknowledge
	SCLK = 0;
	SDIO = 1;									// Configure P0^7(SDIO) as a digital input
	wait_us(2);									// tf:IN + tLOW
	SCLK = 1;
	wait_us(1);									// tf:IN + tHIGH
	if (SDIO != 0) 
		die(); 	// ack not received.  This should never happen. Device isn't responding.
}



//-----------------------------------------------------------------------------
// Read one byte of data.
//
// Inputs:
//		remaining bytes:  Zero value indicates an ack will not be sent.
//
// Outputs:
// 		Returns byte read
//
//-----------------------------------------------------------------------------
static u8 io2w_read_byte (u8 remaining_bytes)
{
	i8 i;	  
	u8 rddata=0;
		   
		for (i=7; i>=0; i--)
		{
			SCLK = 0;
			SDIO = 1;								// Configure P0^7(SDIO) as a digital input
			wait_us(1);									// tf:IN
			wait_us(2);									// tLOW
			SCLK = 1;
			wait_us(1);									// tf:IN + tHIGH
			rddata = ((rddata << 1) | SDIO);  // reads start at word address 0xa
		}
		// set the acknowledge
		SCLK = 0;
		if (remaining_bytes == 0) 
			SDIO = 1;
		else 
			SDIO = 0;
		wait_us(2);									// tf:IN + tLOW
		SCLK = 1;
		wait_us(1);									// tf:IN + tHIGH

		return rddata;
}



//-----------------------------------------------------------------------------
// Sends 2-wire start, writes an array of data, sends 2-wire stop.
//
// Inputs:
//		lastreg:    Last register to be written
//		reg_array:  Source array for data to be written
//
//-----------------------------------------------------------------------------
void io2w_write (u8 lastreg, u16 *reg_array) 
{
	u8 reg = 2;

	// issue the START condition with address lsb cleared for writes
	io2w_start(IO2W_ADDRESS); 	
	
	// loop writing pairs of bytes
	do
	{
	    io2w_write_byte ((u8)(reg_array[reg]>>8));
		io2w_write_byte ((u8)(reg_array[reg]&0xff));
		reg = (reg + 1) & 0xf;
	} while (reg != ((lastreg+1)&0xf));
	
	// issue the STOP condition
	io2w_stop();
}


//-----------------------------------------------------------------------------
// Sends 2-wire start, reads an array of data, sends 2-wire stop.
// 
// Inputs:
//		lastreg:    Last register to be read
//		reg_array:  Destination array for data read
//
//-----------------------------------------------------------------------------
void io2w_read (u8 lastreg, u16 *reg_array) 
{
	u8 reg = 10;

	// issue the START condition with address lsb set for reads
	io2w_start(IO2W_ADDRESS | 0x01);
	
	// loop reading pairs of bytes
	do
	{
		u16 shadow_high = io2w_read_byte(1);
		u8  shadow_low  = io2w_read_byte(lastreg-reg);

		reg_array[reg] = shadow_high*256 + shadow_low;
		reg = (reg + 1) & 0xf;
	} while (reg != ((lastreg+1)&0xf));
	
	// issue the STOP condition
	io2w_stop();
}

⌨️ 快捷键说明

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