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

📄 enc28j60.c

📁 单片机c语言程序设计100例--基于PIC+PROTEUS
💻 C
📖 第 1 页 / 共 5 页
字号:
#endif


#if defined(MAC_FILTER_BROADCASTS)
// NOTE: This code has NOT been tested.  See StackTsk.h's explanation
// of MAC_FILTER_BROADCASTS.
/******************************************************************************
 * Function:        void MACSetPMFilter(BYTE *Pattern, 
 *										BYTE *PatternMask, 
 *										WORD PatternOffset)
 *
 * PreCondition:    SPI bus must be initialized (done in MACInit()).
 * 					MACIsTxReady() must return TRUE
 *
 * Input:           *Pattern: Pointer to an intial pattern to compare against
 *					*PatternMask: Pointer to an 8 byte pattern mask which 
 *								  defines which bytes of the pattern are 
 *								  important.  At least one bit must be set.
 *					PatternOffset: Offset from the beginning of the Ethernet 
 *								   frame (1st byte of destination address), to
 *								   begin comparing with the given pattern.
 *
 * Output:          None
 *
 * Side Effects:    Contents of the TX buffer space are overwritten
 *
 * Overview:        MACSetPMFilter sets the hardware receive filters for: 
 *					CRC AND (Unicast OR Pattern Match).  As a result, only a 
 *					subset of the broadcast packets which are normally 
 *					received will be received.
 *
 * Note:            None
 *****************************************************************************/
void MACSetPMFilter(BYTE *Pattern, 
					BYTE *PatternMask, 
					WORD PatternOffset)
{
	WORD_VAL i;
	BYTE *MaskPtr;
	BYTE UnmaskedPatternLen;
	
	// Set the SPI write pointer and DMA startting address to the beginning of 
	// the transmit buffer
	BankSel(EWRPTL);
	WriteReg(EWRPTL, LOW(TXSTART));
	WriteReg(EWRPTH, HIGH(TXSTART));
	WriteReg(EDMASTL, LOW(TXSTART));
	WriteReg(EDMASTH, HIGH(TXSTART));

	// Fill the transmit buffer with the pattern to match against.  Only the 
	// bytes which have a mask bit of 1 are written into the buffer and will
	// subsequently be used for checksum computation.  
	MaskPtr = PatternMask;
	for(i.Val = 0x0100; i.v[0] < 64; i.v[0]++)
	{
		if( *MaskPtr & i.v[1] )
		{
			MACPut(*Pattern);
			UnmaskedPatternLen++;
		}
		Pattern++;
		
		i.v[1] <<= 1;
		if( i.v[1] == 0u )
		{
			i.v[1] = 0x01;
			MaskPtr++;
		}
	}

	// Calculate and set the DMA end address
	i.Val = TXSTART + (WORD)UnmaskedPatternLen - 1;
	WriteReg(EDMANDL, i.v[0]);
	WriteReg(EDMANDH, i.v[1]);

	// Calculate the checksum on the given pattern using the DMA module
	BFSReg(ECON1, ECON1_DMAST | ECON1_CSUMEN);
	while(ReadETHReg(ECON1).ECON1bits.DMAST);

	// Make certain that the PM filter isn't enabled while it is 
	// being reconfigured.
	BankSel(ERXFCON);
	WriteReg(ERXFCON, ERXFCON_UCEN | ERXFCON_CRCEN | ERXFCON_BCEN);

	// Get the calculated DMA checksum and store it in the PM 
	// checksum registers
	i.v[0] == ReadETHReg(EDMACSL).Val;
	i.v[1] == ReadETHReg(EDMACSH).Val;
	WriteReg(EPMCSL, i.v[0]);
	WriteReg(EPMCSH, i.v[0]);

	// Set the Pattern Match offset and 8 byte mask
	WriteReg(EPMOL, ((WORD_VAL*)&PatternOffset)->v[0]);
	WriteReg(EPMOH, ((WORD_VAL*)&PatternOffset)->v[1]);
	for(i.Val = EPMM0; i.Val <= EPMM7 ; i.Val++)
	{
		WriteReg(i.Val, *PatternMask++);
	}

	// Begin using the new Pattern Match filter instead of the 
	// broadcast filter
	WriteReg(ERXFCON, ERXFCON_UCEN | ERXFCON_CRCEN | ERXFCON_PMEN);
}//end MACSetPMFilter


/******************************************************************************
 * Function:        void MACDisablePMFilter(void)
 *
 * PreCondition:    SPI bus must be initialized (done in MACInit()).
 *
 * Input:           None
 *
 * Output:          None
 *
 * Side Effects:    None
 *
 * Overview:        MACDisablePMFilter disables the Pattern Match receive 
 *					filter (if enabled) and returns to the default filter 
 *					configuration of: CRC AND (Unicast OR Broadcast).
 *
 * Note:            None
 *****************************************************************************/
void MACDisablePMFilter(void)
{
	BankSel(ERXFCON);
	WriteReg(ERXFCON, ERXFCON_UCEN | ERXFCON_CRCEN | ERXFCON_BCEN);
	return;
}//end MACDisablePMFilter
#endif // end of MAC_FILTER_BROADCASTS specific code


/******************************************************************************
 * Function:        BYTE MACGet()
 *
 * PreCondition:    SPI bus must be initialized (done in MACInit()).
 * 					ERDPT must point to the place to read from.
 *
 * Input:           None
 *
 * Output:          Byte read from the ENC28J60's RAM
 *
 * Side Effects:    None
 *
 * Overview:        MACGet returns the byte pointed to by ERDPT and 
 *					increments ERDPT so MACGet() can be called again.  The 
 *					increment will follow the receive buffer wrapping boundary.
 *
 * Note:            None
 *****************************************************************************/
BYTE MACGet()
{
	BYTE Result;

	ENC_CS_IO = 0;
	ENC_SPI_IF = 0;
	ENC_SSPBUF = RBM;
	while(!ENC_SPI_IF);		// Wait until opcode/address is transmitted.
	Result = ENC_SSPBUF;
	ENC_SPI_IF = 0;
	ENC_SSPBUF = 0;				// Send a dummy byte to receive the register 
							//   contents.
	while(!ENC_SPI_IF);		// Wait until register is received.
	Result = ENC_SSPBUF;
	ENC_SPI_IF = 0;
	ENC_CS_IO = 1;

	return Result;
}//end MACGet


/******************************************************************************
 * Function:        WORD MACGetArray(BYTE *val, WORD len)
 *
 * PreCondition:    SPI bus must be initialized (done in MACInit()).
 * 					ERDPT must point to the place to read from.
 *
 * Input:           *val: Pointer to storage location
 *					len:  Number of bytes to read from the data buffer.
 *
 * Output:          Byte(s) of data read from the data buffer.
 *
 * Side Effects:    None
 *
 * Overview:        Burst reads several sequential bytes from the data buffer 
 *					and places them into local memory.  With SPI burst support, 
 *					it performs much faster than multiple MACGet() calls.
 *					ERDPT is incremented after each byte, following the same 
 *					rules as MACGet().
 *
 * Note:            None
 *****************************************************************************/
WORD MACGetArray(BYTE *val, WORD len)
{
	WORD i;
	BYTE Dummy;

	// Start the burst operation
	ENC_CS_IO = 0;
	ENC_SPI_IF = 0;
	ENC_SSPBUF = RBM;			// Send the Read Buffer Memory opcode.
	i = 0;		
	val--;
	while(!ENC_SPI_IF);		// Wait until opcode/address is transmitted.
	Dummy = ENC_SSPBUF;
	ENC_SPI_IF = 0;

	// Read the data
	while(i<len)
	{
		ENC_SSPBUF = 0;			// Send a dummy byte to receive a byte 
		i++;
		val++;
		while(!ENC_SPI_IF);	// Wait until byte is received.
		*val = ENC_SSPBUF;
		ENC_SPI_IF = 0;
	};

	// Terminate the burst operation
	ENC_CS_IO = 1;

	return i;
}//end MACGetArray


/******************************************************************************
 * Function:        void MACPut(BYTE val)
 *
 * PreCondition:    SPI bus must be initialized (done in MACInit()).
 * 					EWRPT must point to the location to begin writing.
 *
 * Input:           Byte to write into the ENC28J60 buffer memory
 *
 * Output:          None
 *
 * Side Effects:    None
 *
 * Overview:        MACPut outputs the Write Buffer Memory opcode/constant 
 *					(8 bits) and data to write (8 bits) over the SPI.  
 *					EWRPT is incremented after the write.
 *
 * Note:            None
 *****************************************************************************/
void MACPut(BYTE val)
{
	BYTE Dummy;

	ENC_CS_IO = 0;
	ENC_SPI_IF = 0;
	ENC_SSPBUF = WBM;			// Send the opcode and constant.
	while(!ENC_SPI_IF);		// Wait until opcode/constant is transmitted.
	Dummy = ENC_SSPBUF;
	ENC_SPI_IF = 0;
	ENC_SSPBUF = val;			// Send the byte to be writen.
	while(!ENC_SPI_IF);		// Wait until byte is transmitted.
	Dummy = ENC_SSPBUF;
	ENC_SPI_IF = 0;
	ENC_CS_IO = 1;
}//end MACPut


/******************************************************************************
 * Function:        void MACPutArray(BYTE *val, WORD len)
 *
 * PreCondition:    SPI bus must be initialized (done in MACInit()).
 * 					EWRPT must point to the location to begin writing.
 *
 * Input:           *val: Pointer to source of bytes to copy.
 *					len:  Number of bytes to write to the data buffer.
 *
 * Output:          None
 *
 * Side Effects:    None
 *
 * Overview:        MACPutArray writes several sequential bytes to the 
 *					ENC28J60 RAM.  It performs faster than multiple MACPut()
 *					calls.  EWRPT is incremented by len.
 *
 * Note:            None
 *****************************************************************************/
void MACPutArray(BYTE *val, WORD len)
{
	BYTE Dummy;

	// Select the chip and send the proper opcode
	ENC_CS_IO = 0;
	ENC_SPI_IF = 0;
	ENC_SSPBUF = WBM;			// Send the Write Buffer Memory opcode
	while(!ENC_SPI_IF);		// Wait until opcode/constant is transmitted.
	Dummy = ENC_SSPBUF;
	ENC_SPI_IF = 0;

	// Send the data
	while(len)
	{
		ENC_SSPBUF = *val;		// Start sending the byte
		val++;				// Increment after writing to ENC_SSPBUF to increase speed
		len--;				// Decrement after writing to ENC_SSPBUF to increase speed
		while(!ENC_SPI_IF);	// Wait until byte is transmitted
		Dummy = ENC_SSPBUF;
		ENC_SPI_IF = 0;
	};

	// Terminate the burst operation
	ENC_CS_IO = 1;
}//end MACPutArray


/******************************************************************************
 * Function:        static void SendSystemReset(void)
 *
 * PreCondition:    SPI bus must be initialized (done in MACInit()).
 *
 * Input:           None
 *
 * Output:          None
 *
 * Side Effects:    None
 *
 * Overview:        SendSystemReset sends the System Reset SPI command to 
 *					the Ethernet controller.  It resets all register contents 
 *					(except for ECOCON) and returns the device to the power 
 *					on default state.
 *
 * Note:            None
 *****************************************************************************/
static void SendSystemReset(void)
{
	BYTE Dummy;

	ENC_CS_IO = 0;
	ENC_SPI_IF = 0;
	ENC_SSPBUF = SR;
	while(!ENC_SPI_IF);		// Wait until the command is transmitted.
	Dummy = ENC_SSPBUF;
	ENC_SPI_IF = 0;
	ENC_CS_IO = 1;
}//end SendSystemReset


/******************************************************************************
 * Function:        REG ReadETHReg(BYTE Address)
 *
 * PreCondition:    SPI bus must be initialized (done in MACInit()).
 * 					Bank select bits must be set corresponding to the register 
 * 					to read from.
 *
 * Input:           5 bit address of the ETH control register to read from.
 *					  The top 3 bits must be 0.
 *
 * Output:          Byte read from the Ethernet controller's ETH register.
 *
 * Side Effects:    None
 *
 * Overview:        ReadETHReg sends the 8 bit RCR opcode/Address byte over 
 *					the SPI and then retrives the register contents in the 
 *					next 8 SPI clocks.
 *
 * Note:            This routine cannot be used to access MAC/MII or PHY 
 *					registers.  Use ReadMACReg() or ReadPHYReg() for that 
 *					purpose.  
 *****************************************************************************/
static REG ReadETHReg(BYTE Address)
{
	REG r;

	// Select the chip and send the Read Control Register opcode/address
	ENC_CS_IO = 0;
	ENC_SPI_IF = 0;
	ENC_SSPBUF = RCR | Address;	
		
	while(!ENC_SPI_IF);		// Wait until the opcode/address is transmitted
	r.Val = ENC_SSPBUF;
	ENC_SPI_IF = 0;
	ENC_SSPBUF = 0;				// Send a dummy byte to receive the register 
							//   contents
	while(!ENC_SPI_IF);		// Wait until the register is received
	r.Val = ENC_SSPBUF;
	ENC_SPI_IF = 0;
	ENC_CS_IO = 1;

	return r;
}//end ReadETHReg


/******************************************************************************
 * Function:        REG ReadMACReg(BYTE Address)
 *
 * PreCondition:    SPI bus must be initialized (done in MACInit()).
 * 					Bank select bits must be set corresponding to the register 
 * 					to read from.
 *
 * Input:           5 bit address of the MAC or MII register to read from.
 *					  The top 3 bits must be 0.
 *
 * Output:          Byte read from the Ethernet controller's MAC/MII register.
 *

⌨️ 快捷键说明

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