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

📄 conn1.c

📁 关于devicenet的源代码。micorchip公司的
💻 C
📖 第 1 页 / 共 2 页
字号:
			{
				// Remember the header
				uConn1.rx.header = header.byte;; 
				
				// Get the count		
				uConn1.rx.len = CANGetRxCnt();
		
				// Copy the message to the connection buffer
				CANGetRxDataTyp0(uConn1RxBuffer);
			
				// Indicate message has been received (located in conn.c)	
				_rxFlag.bits.expl = 1;
		
				// Put the connection into the established state
				uConn1.attrib.state = _STATE_ESTABLISHED;
				_establishFlags.bits.expl = 1;
				
				// Reset the connection wdt
				uConn1.timer.word = uConn1.attrib.expected_packet_rate.word << 2;
			}
		}
	}
	
	// Release the hardware to continue receiving
	CANRead();
}



 
/*********************************************************************
 * Function:        void _Conn1TxOpenEvent(void)
 *
 * PreCondition:    none
 *
 * Input:       	none	
 *                  
 * Output:      	none
 *
 * Side Effects:    none
 *
 * Overview:        Process
 *
 * Note:            This event occurs when the buffer is available 
 *					for this connection instance to transmit.
 ********************************************************************/
void _Conn1TxOpenEvent(void)
{
	BYTE header;
	unsigned char *pTxData;
	
	// Get the pointer to the CAN transmit buffer
	pTxData = CANGetTxDataPtr();

	// If acknowledge requested then force fragment processing
	if (uConn1.tx.fragFlags.bits.TXFLAG_SEND_ACK == 1)
	{
		header.bits.b7 = 1;
	}
	
	// Else get the header from top level
	else
	{
		header.byte = *uConn1TxBuffer;
	}
	
#if	FRAGMENTATION_ACK
	// If fragmented
	if (header.bits.b7)
	{
		// If in the send ack state as a result of a receive then
		if (uConn1.tx.fragFlags.bits.TXFLAG_SEND_ACK == 1)
		{
			// Copy the header and the fragment count (header should be 
			// the same as the received header)
			*pTxData = uConn1.rx.header; pTxData++;
			*pTxData = uConn1.rx.oldFrag | 0xC0; pTxData++;

			// Send a success ack 
			if (uConn1.tx.fragFlags.bits.TXFLAG_ACK_STAT == 0)
			{
				*pTxData = _FRAG_SUCCESS;
			}
			// or send an error ack
			else
			{
				*pTxData = _FRAG_TOO_MUCH;
			}
			
			// Set the length of the message
			CANPutTxCnt(3);
		}	
		else 

		// If a resend has been requested
		if (uConn1.tx.fragFlags.bits.TXFLAG_TX_AGAIN == 1)
		{
			// Copy the header
			*pTxData = *uConn1TxBuffer; pTxData++;
			
			// Copy the last fragment
			*pTxData = uConn1.tx.oldFrag;
			
			// Copy 6 bytes of the packet
			CANPutTxDataTyp2(uConn1TxBuffer + uConn1.tx.index);
		}
		else
		
		// If the first fragmented transmit progress has been started already
		if (uConn1.tx.fragFlags.bits.TXFLAG_TX_START == 1)
		{
			// Copy the header
			*pTxData = *uConn1TxBuffer; pTxData++;
			
			// Adjust the fragment byte
			uConn1.tx.oldFrag++;
			
			// Adjust the index
			uConn1.tx.index += 7;
			
			// If last fragment
			if (uConn1.tx.len < 7)
			{
				// Indicate the last fragment has been queued to send
				uConn1.tx.fragFlags.bits.TXFLAG_TX_FIN = 1;
				
				// Set the type
				uConn1.tx.oldFrag = (uConn1.tx.oldFrag & 0x3F) | 0xC0;  
				
				// Set the length of the message
				CANPutTxCnt(uConn1.tx.len + 2);
				
				// Adjust the length
				uConn1.tx.len = 0;
			}
			
			// Middle fragment
			else
			{
				// Set the type
				uConn1.tx.oldFrag = (uConn1.tx.oldFrag & 0x3F) | 0x80;
				
				// Set the length of the message
				CANPutTxCnt(8);
				
				// Adjust the length
				uConn1.tx.len -= 6;
			}
			
			// Copy the fragment info
			*pTxData = uConn1.tx.oldFrag;
			
			// Copy 6 bytes of the packet
			CANPutTxDataTyp2(uConn1TxBuffer + uConn1.tx.index);
		}

		// Transmit has not been started, so que the first message
		else
		{
			// Copy the header
			*pTxData = *uConn1TxBuffer; pTxData++;
			
			// Set the frag byte to first fragment 
			*pTxData = uConn1.tx.oldFrag = 0;
			
			// Set the index
			uConn1.tx.index = 1;
			
			// Copy the first 6 bytes of the packet
			CANPutTxDataTyp2(uConn1TxBuffer + 1);
				
			// Adjust the length by 7, i.e. header and 6 data bytes
			uConn1.tx.len = uConn1.tx.len - 7;
					
			// Set the length of the message
			CANPutTxCnt(8);
			
			// Indicate the first message has been started
			uConn1.tx.fragFlags.bits.TXFLAG_TX_START = 1;
		}
	}
#else
	// If fragmented
	if (header.bits.b7)
	{
		// If in the send ack state as a result of a receive then
		if (uConn1.tx.fragFlags.bits.TXFLAG_SEND_ACK == 1)
		{
			// Copy the header and the fragment count (header should be 
			// the same as the received header)
			*pTxData = uConn1.rx.header; pTxData++;
			*pTxData = uConn1.rx.oldFrag | 0xC0; pTxData++;

			// Send a success ack 
			if (uConn1.tx.fragFlags.bits.TXFLAG_ACK_STAT == 0)
			{
				*pTxData = _FRAG_SUCCESS;
			}
			// or send an error ack
			else
			{
				*pTxData = _FRAG_TOO_MUCH;
			}
			
			// Set the length of the message 
			CANPutTxCnt(3);
		}
		else
		{
			//Clear the transmit flag to open access to the write buffer
			_txFlag.bits.expl = 0;
			return;
		}
	}
#endif  


	// else process a non-fragmented message
	else
	{
		// Copy the message to the hardware buffer
		CANPutTxDataTyp0(uConn1TxBuffer);
		
		// Set the length of the message
		CANPutTxCnt(uConn1.tx.len);
	}	
	
	//Clear the transmit flag to open access to the write buffer
	_txFlag.bits.expl = 0;
	// Request the hardware to queue the message to send
	CANSend(1);
}


/*********************************************************************
 * Function:        void _Conn1TxEvent(void)
 *
 * PreCondition:    
 *
 * Input:       	none
 *                  
 * Output:      	none
 *
 * Side Effects:    
 *
 * Overview:        Process data for this connection.
 *
 * Note:            This event occurs when the buffer has successfully
 *					placed the requested data on the bus.
 ********************************************************************/
void _Conn1TxEvent(void)
{
	BYTE header;
	unsigned char *pTxData;
	
		 
	// If acknowledge requested then force fragment processing
	if (uConn1.tx.fragFlags.bits.TXFLAG_SEND_ACK == 1)
	{
		header.bits.b7 = 1;
	}
	
	// Else get the header from top level
	else
	{
		header.byte = *uConn1TxBuffer;
	}	
		
	// If fragmented
	if (header.bits.b7)
	{
		// If in the send ack state as a result of a receive then
		if (uConn1.tx.fragFlags.bits.TXFLAG_SEND_ACK == 1)
		{
			// Remove the send ack request
			uConn1.tx.fragFlags.bits.TXFLAG_SEND_ACK = 0;
		}
		
	#if	FRAGMENTATION_ACK
		else

		// If a resend has been requested
		if (uConn1.tx.fragFlags.bits.TXFLAG_TX_AGAIN == 1)
		{
			// Start the acknowledge timer
			uConn1.tx.fragFlags.bits.TXFLAG_TX_TIMER_EN = 1;
		}
		else

		// If the last transmission has been sent
		if (uConn1.tx.fragFlags.bits.TXFLAG_TX_FIN == 1)
		{
			// Set flag indicating all data has been placed on the bus
			_txFinFlags.bits.expl = 1;
		}
		else

		// If the first fragmented transmit progress has been started already
		if (uConn1.tx.fragFlags.bits.TXFLAG_TX_START == 1)
		{
			// Start the acknowledge timer
			uConn1.tx.fragFlags.bits.TXFLAG_TX_TIMER_EN = 1;
		}
	#endif
	}
	
	// Not fragmented
	else
	{
		// Set flag indicating data has been placed on the bus
		_txFinFlags.bits.expl = 1;
	}
}





/*********************************************************************
 * Function:        unsigned char _Conn1ExplicitEvent(void)
 *
 * PreCondition:    
 *
 * Input:       	none	
 *                  
 * Output:      	status
 *
 * Side Effects:    
 *
 * Overview:        Handle explicit messaging
 *
 * Note:            None
 ********************************************************************/
unsigned char _Conn1ExplicitEvent(void)
{
	switch(mRouteGetServiceID())
   	{
   		case SRVS_GET_ATTRIB_SINGLE:
   			return (_Conn1GetAttrib());
   		case SRVS_SET_ATTRIB_SINGLE:
   			return (_Conn1SetAttrib());
   	   	default:
   			mRoutePutError(ERR_SERVICE_NOT_SUPPORTED);
   			break;
   	}
		
	return (1);
}


/*********************************************************************
 * Function:        unsigned char _Conn1GetAttrib()
 *
 * PreCondition:    
 *
 * Input:       	none
 *                  
 * Output:      	status
 *
 * Side Effects:    
 *
 * Overview:        Handle explicit messaging
 *
 * Note:            None
 ********************************************************************/
unsigned char _Conn1GetAttrib(void)
{
	UINT	work;

	switch (mRouteGetAttributeID())
	{
		case	_ATTRIB_STATE:
			mRoutePutByte(uConn1.attrib.state);
			break;
		case	_ATTRIB_INSTANCE_TYPE:
			mRoutePutByte(0);
			break;
		case	_ATTRIB_CLASS_TRIGGER:
			mRoutePutByte(0x83);
			break;
		case 	_ATTRIB_PRODUCED_CID:
			work.word = (uConn1.attrib.produced_cid.word >> 5);
			mRoutePutByte(work.bytes.LSB);
			mRoutePutByte(work.bytes.MSB);
			break;
		case	_ATTRIB_CONSUMED_CID:
			work.word = (uConn1.attrib.consumed_cid.word >> 5);
			mRoutePutByte(work.bytes.LSB);
			mRoutePutByte(work.bytes.MSB);
			break;	
		case 	_ATTRIB_INITIAL_COMM_CHAR:
			mRoutePutByte(0x21);
			break;
		case	_ATTRIB_PRODUCED_CONN_SIZE:
			mRoutePutByte(uConn1.tx.lenMax);
			mRoutePutByte(0);
			break;
		case	_ATTRIB_CONSUMED_CONN_SIZE:
			mRoutePutByte(uConn1.rx.lenMax);
			mRoutePutByte(0);
			break;
		case	_ATTRIB_EXPECTED_RATE:
			mRoutePutByte(uConn1.attrib.expected_packet_rate.bytes.LSB);
			mRoutePutByte(uConn1.attrib.expected_packet_rate.bytes.MSB);
			break;
		case	_ATTRIB_WDT_ACTION:
			mRoutePutByte(uConn1.attrib.wdt_action);
			break;
		case	_ATTRIB_PRODUCED_CONN_PATH_LEN:
		case	_ATTRIB_CONSUMED_CONN_PATH_LEN:
			mRoutePutByte(0);
			mRoutePutByte(0);
			break;
		case	_ATTRIB_PRODUCED_CONN_PATH:
		case	_ATTRIB_CONSUMED_CONN_PATH:
			break;
		default:
			mRoutePutError(ERR_ATTRIB_NOT_SUPPORTED);
			break;
	}
	return(1);
}




/*********************************************************************
 * Function:        unsigned char _Conn1SetAttrib(void)
 *
 * PreCondition:    
 *
 * Input:       	none
 *                  
 * Output:      	status
 *
 * Side Effects:    
 *
 * Overview:        Handle explicit messaging
 *
 * Note:            None
 ********************************************************************/
unsigned char _Conn1SetAttrib(void)
{
	unsigned char 	work;

	switch (mRouteGetAttributeID())
	{	
		case	_ATTRIB_EXPECTED_RATE:
			// Read in the requested packet rate
			uConn1.attrib.expected_packet_rate.bytes.LSB = mRouteGetByte();
			uConn1.attrib.expected_packet_rate.bytes.MSB = mRouteGetByte();

			// Get the ls bits
			work = uConn1.attrib.expected_packet_rate.bytes.LSB & (TICK_RESOLUTION - 1);

			// Remove the ls bits from desired resolution
			uConn1.attrib.expected_packet_rate.bytes.LSB &= (~(TICK_RESOLUTION - 1));
			
			// Round up if necessary
			if (work) uConn1.attrib.expected_packet_rate.word += (TICK_RESOLUTION);

			// Return the value actually used
			mRoutePutByte(uConn1.attrib.expected_packet_rate.bytes.LSB);
			mRoutePutByte(uConn1.attrib.expected_packet_rate.bytes.MSB);

			// Set the timer 4x (section 5-4.4.2)
			uConn1.timer.word = uConn1.attrib.expected_packet_rate.word << 2; 
			break;
			
		case	_ATTRIB_WDT_ACTION:
			work = mRouteGetByte();
			if ((work == _WDT_ACTION_DEFERRED) || (work == _WDT_ACTION_AUTO_DELETE))
			{
				uConn1.attrib.wdt_action = work;
			}
			else
			{
				mRoutePutError(ERR_INVALID_ATTRIB_VALUE);
			}
			break;
		

		case	_ATTRIB_PRODUCED_CONN_SIZE:
		case	_ATTRIB_CONSUMED_CONN_SIZE:
		case	_ATTRIB_STATE:
		case	_ATTRIB_INSTANCE_TYPE:
		case	_ATTRIB_CLASS_TRIGGER:
		case 	_ATTRIB_PRODUCED_CID:
		case	_ATTRIB_CONSUMED_CID:
		case 	_ATTRIB_INITIAL_COMM_CHAR:
		case	_ATTRIB_PRODUCED_CONN_PATH_LEN:
		case	_ATTRIB_PRODUCED_CONN_PATH:
		case	_ATTRIB_CONSUMED_CONN_PATH_LEN:
		case	_ATTRIB_CONSUMED_CONN_PATH:
			mRoutePutError(ERR_ATTRIB_NOT_SETTABLE);
			break;
			
		default:
			mRoutePutError(ERR_ATTRIB_NOT_SUPPORTED);
			break;
	}
	return(1);
}




⌨️ 快捷键说明

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