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

📄 hdlcinit.c

📁 s3c4510的开发板snds100的源代码。
💻 C
📖 第 1 页 / 共 3 页
字号:
/*************************************************************************/
/*                                                                       */
/* FILE NAME                                      VERSION                */
/*                                                                       */
/*      hdlcinit.c                          KS32C5000(A)   : version 1.0 */
/*                                                                       */
/* COMPONENT                                                             */
/*                                                                       */
/*                                                                       */
/* DESCRIPTION                                                           */
/*                                                                       */
/*              HDLC(high level data link control) function define.      */
/*                                                                       */
/* AUTHOR                                                                */
/*                                                                       */
/*                                                                       */
/* DATA STRUCTURES                                                       */
/*                                                                       */
/*                                                                       */
/* FUNCTIONS                                                             */
/*                                                                       */
/*                                                                       */
/* DEPENDENCIES                                                          */
/*                                                                       */
/*                                                                       */
/* HISTORY                                                               */
/*                                                                       */
/*         NAME            DATE                    REMARKS               */
/*                                                                       */
/*      hbahn           09-15-1998      Created initial version 1.0      */
/*      hbahn           06-05-1999      Modified version 1.0             */
/*                                                                       */
/*************************************************************************/
#include <stdarg.h>
#include <stdio.h>
#include <ctype.h>
#include <string.h>
#include "snds.h"
#include "sysconf.h"
#include "uart.h"
#include "pollio.h"
#include "timer.h"
#include "isr.h"
#include "hdlc.h"

// Global variable for HDLC Channel A test
volatile U32	gHCon0 = BRGEN | TxRTS | TxDTR ;
#ifdef LITTLE
volatile U32	gHCon1 = F4WM | TxLittle | RxLittle | DTxMAINC | DRxMAINC | \
			DRxSTOPTC | BRGCLK_MCLK | DPLLCLK_MCLK ;
#else
volatile U32	gHCon1 = F4WM | DTxMAINC | DRxMAINC | DRxSTOPTC | BRGCLK_MCLK |\
			DPLLCLK_MCLK ;
#endif
volatile U32	gHintEn= HDLCIE | TxIE | RxIE ;

// Global variable for HDLC Tx/Rx Status report
pHdlcTxStatus 	gHdlcTxStatus[HDLCPORTNUM] ; 
pHdlcRxStatus 	gHdlcRxStatus[HDLCPORTNUM] ; 
pHdlcDPLLStatus gHdlcDPLLStatus[HDLCPORTNUM] ; 

// HDLC Device entry point
HDLC_Device_Entry  HDLC_Dev[HDLCPORTNUM] ;


// HDLC Frame Buffer Descriptor and Data Buffer
sBufferDescriptor	TxBDABase[HDLCPORTNUM][MaxTxBufferDescriptor] ;
sBufferDescriptor	RxBDABase[HDLCPORTNUM][MaxRxBufferDescriptor] ;
sHDLCFrame 		TxBABase[HDLCPORTNUM][MaxTxBufferDescriptor] ;
sHDLCFrame 		RxBABase[HDLCPORTNUM][MaxRxBufferDescriptor] ;

// Global variable for buffer descriptor
volatile U32 gCTxBDPtr[HDLCPORTNUM], pCTxBDPtr[HDLCPORTNUM] ;
volatile U32 gCRxBDPtr[HDLCPORTNUM], pCRxBDPtr[HDLCPORTNUM] ;

// Global variable for transmit frame by interrupt mode
volatile U8 *ModeInt_TxDataBuffer[HDLCPORTNUM] ;
volatile U32 ModeInt_TxDataSize[HDLCPORTNUM] ;

volatile U32 *ModeInt_RxDataBuffer[HDLCPORTNUM] ;
volatile U32 ModeInt_RxDataSize[HDLCPORTNUM] ;
volatile U8 *HDLCTXFIFOT, *HDLCTXFIFOC ;

U8 *TempBuf[1520] ;

/*
 *  Function : HdlcInitialize
 *  Description : HDLC controller initialize
 */
void HdlcInitialize(void)
{
	HDLC_Device_Entry  *Dev_entry[HDLCPORTNUM] ;
	int 	channel;

	Disable_Int(nHDLCA_INT);
	Disable_Int(nHDLCB_INT);


	// Step 1. Set HDLC channel A initialize parameter
	Dev_entry[HDLCA] = (HDLC_Device_Entry *)&HDLC_Dev[HDLCA] ; 
	Dev_entry[HDLCA]->HDLC_Port		= HDLCA ;
	Dev_entry[HDLCA]->HDLC_Baud		= 64000 ;
	Dev_entry[HDLCA]->HDLC_Data_format	= DF_NRZ ;
	Dev_entry[HDLCA]->HDLC_Tx_Mode		= MODE_DMA ;
	Dev_entry[HDLCA]->HDLC_Rx_Mode 		= MODE_DMA ;
	Dev_entry[HDLCA]->HDLC_Tx_Output_Clk	= TxOCLK_BRG1 ;
	Dev_entry[HDLCA]->HDLC_Tx_Clk		= TxCLK_BRG1 ;
	Dev_entry[HDLCA]->HDLC_Rx_Clk		= RxCLK_RXC ;
	Dev_entry[HDLCA]->HDLC_Station_Addr 	= HDLC_STATION_ADDR ;

	// Tx clock polarity, only for KS32C5000A, 
	// when set 0 the polarity is same as KS32C5000
	Dev_entry[HDLCA]->HDLC_Tx_Clk_Pos 	= TxCNEG ;

	// Rx clock polarity, only for KS32C5000A, 
	// when set 1 the polarity is same as KS32C5000
	Dev_entry[HDLCA]->HDLC_Rx_Clk_Pos 	= RxCPOS ;	


	// Step 2. Set HDLC channel B initialize parameter
	Dev_entry[HDLCB] = (HDLC_Device_Entry *)&HDLC_Dev[HDLCB] ; 
	Dev_entry[HDLCB]->HDLC_Port		= HDLCB ;
	Dev_entry[HDLCB]->HDLC_Baud		= 64000 ;
	Dev_entry[HDLCB]->HDLC_Data_format	= DF_NRZ ;
	Dev_entry[HDLCB]->HDLC_Tx_Mode		= MODE_DMA ;
	Dev_entry[HDLCB]->HDLC_Rx_Mode		= MODE_DMA ;
	Dev_entry[HDLCB]->HDLC_Tx_Output_Clk	= TxOCLK_BRG1 ;
	Dev_entry[HDLCB]->HDLC_Tx_Clk		= TxCLK_BRG1 ;
	Dev_entry[HDLCB]->HDLC_Rx_Clk		= RxCLK_RXC ;
	Dev_entry[HDLCB]->HDLC_Station_Addr 	= HDLC_STATION_ADDR ;

	// Tx clock polarity, only for KS32C5000A, 
	// when set 0 the polarity is same as KS32C5000
	Dev_entry[HDLCB]->HDLC_Tx_Clk_Pos 	= TxCNEG ;

	// Rx clock polarity, only for KS32C5000A, 
	// when set 1 the polarity is same as KS32C5000
	Dev_entry[HDLCB]->HDLC_Rx_Clk_Pos 	= RxCPOS ;	


	// Step 3. Initialize each HDLC port
	for(channel=HDLCA ; channel<=HDLCB ; channel++)
	{
		if ( !HdlcPortInit(Dev_entry[channel]) )
			Print("\n HDLC channel [%d] initialize error",channel) ;
	}

	// Step 4. Setup Interrupt for HDLC 
	SysSetInterrupt(nHDLCA_INT, HDLCA_isr );
	SysSetInterrupt(nHDLCB_INT, HDLCB_isr );

	// Step 5. Enable HDLC interrupt
	Enable_Int(nHDLCA_INT);
	Enable_Int(nHDLCB_INT);

}

/*
 *  Function : HdlcPortInit
 *  Description : HDLC Port initialize
 */
int HdlcPortInit(HDLC_Device_Entry *Device)
{	
	U32	TxInterruptEnableFlag ;
	U32	RxInterruptEnableFlag ;
	U32	channel ;
	channel = Device->HDLC_Port ;

	// Step 1. Reset HDLC Controller and HDLC DMA
	HCON0(channel) = TxRS | RxRS | DTxRS | DRxRS ;

	// Step 2. Set Station address
	// This register only used when enable RxASEN. Now, we didn't use
	HSADR(channel) = Device->HDLC_Station_Addr ;

	// Step 3. Set Baud Rate Generater constant value
	HBRGTC(channel)= fMCLK/(2*Device->HDLC_Baud)-1;

	// Step 4. Set Preamble value for NRZ code
	HPRMB(channel) = HDLC_PREAMBLE ;

	// Step 5. Set HDLC Control Register 1 
	HCON1(channel) = gHCon1 | \
			Device->HDLC_Data_format |\
			Device->HDLC_Tx_Output_Clk |\
			Device->HDLC_Tx_Clk |\
			Device->HDLC_Rx_Clk ;

	// Step 6. Set HDLC Control Register 0 
	// Baud-rate Generator Enable, DPLL Enable, Tx/Rx Enable
	HCON0(channel) = gHCon0 | \
			Device->HDLC_Tx_Clk_Pos | \
			Device->HDLC_Rx_Clk_Pos ;

	// Step 7. Tx, and Rx Buffer descriptor initialize
	TxBDInitialize(channel) ;
	RxBDInitialize(channel) ;

	// Step 8. Enable HDLC Transmit controller
	HDLC_Tx_Enable(channel);

	// Step 9. Setup HDLC and HDMA for receive operation
	HDLC_Rx_init(channel) ;

	// Step 10. Set HDLC Interrupt enable register
	if ( Device->HDLC_Tx_Mode == MODE_DMA )
		TxInterruptEnableFlag = DTxIE | TxUIE | DTxABIE | DTxSTOPIE ;
	else
		TxInterruptEnableFlag = TxUIE ;

	if ( Device->HDLC_Rx_Mode == MODE_DMA ) 
		RxInterruptEnableFlag = DRxIE | RxABIE | RxFERRIE | RxOVIE | \
					DRxSTOPIE | DRxABIE ;
	else
		RxInterruptEnableFlag = RxABIE | RxFERRIE | RxOVIE | RxFAIE | RxFVIE ;
	
	gHintEn |= TxInterruptEnableFlag | RxInterruptEnableFlag ;
	HINTEN(channel) = gHintEn ;

	// Step 11. Clear HDLC Status
	HSTAT(channel) |= HSTAT(channel) ;

	return 1 ;
}

/*
 * Function : void TxBDInitialize(U32 channel) ;
 * Description : Initialize Tx buffer descriptor area-buffers.
 */
void TxBDInitialize(U32 channel)
{	
	sBufferDescriptor *pBufferDescriptor;
	sBufferDescriptor *pStartBufferDescriptor;
	sBufferDescriptor *pLastBufferDescriptor = NULL;
	U32 BufferDataAddr;
	U32 i;

	// Get Buffer descriptor's base address.   
	// +0x4000000 is for setting this area to non-cacheable area. 
	gCTxBDPtr[channel] = (U32)TxBDABase[channel] + NonCache ;
	pCTxBDPtr[channel] = (U32)TxBDABase[channel] + NonCache ;

	// Get Transmit buffer base address.
	HDMATXMA(channel) = BufferDataAddr = (U32)TxBABase[channel] + NonCache ;

	// Generate linked list.
	pBufferDescriptor = (sBufferDescriptor *) gCTxBDPtr[channel];
	pStartBufferDescriptor = pBufferDescriptor;

	for(i=0; i < MaxTxBufferDescriptor; i++)  {
		if(pLastBufferDescriptor == NULL)
			pLastBufferDescriptor = pBufferDescriptor;
		else  	pLastBufferDescriptor->NextBufferDescriptor = (U32)pBufferDescriptor;

		pBufferDescriptor->BufferDataPtr = 
			(U32)(BufferDataAddr & BOwnership_CPU);
		pBufferDescriptor->StatusField = (U32)0x0;
		pBufferDescriptor->LengthField = (U32)0x0;
		pBufferDescriptor->NextBufferDescriptor = NULL;

		pLastBufferDescriptor = pBufferDescriptor;
		pBufferDescriptor++;
		BufferDataAddr += sizeof(sHDLCFrame);
	} // end for loop

	// Make Buffer descriptor to ring buffer type.     
	pBufferDescriptor--; 
	pBufferDescriptor->NextBufferDescriptor = (U32)pStartBufferDescriptor;
}

/*
 * Function : void RxBDInitialize(U32 channel) ;
 * Description : Initialize Rx buffer descriptor area-buffers.
 */
void RxBDInitialize(U32 channel)
{	
	sBufferDescriptor *pBufferDescriptor;
	sBufferDescriptor *pStartBufferDescriptor;
	sBufferDescriptor *pLastBufferDescriptor = NULL;
	U32 BufferDataAddr;
	U32 i;

	// Get Buffer descriptor's base address.  
	// +0x4000000 is for setting this area to non-cacheable area. 
	gCRxBDPtr[channel] = (U32)RxBDABase[channel] + NonCache ;
	pCRxBDPtr[channel] = (U32)RxBDABase[channel] + NonCache ;
	
	// Get Transmit buffer base address.  
	HDMARXMA(channel) = BufferDataAddr = (U32)RxBABase[channel] + NonCache ;

	// Generate linked list. 
	pBufferDescriptor = (sBufferDescriptor *) gCRxBDPtr[channel];
	pStartBufferDescriptor = pBufferDescriptor;
	
	for(i=0; i < MaxRxBufferDescriptor; i++)  {
		if(pLastBufferDescriptor == NULL)
			pLastBufferDescriptor = pBufferDescriptor;
		else  	pLastBufferDescriptor->NextBufferDescriptor = (U32)pBufferDescriptor;

		pBufferDescriptor->BufferDataPtr =
			(U32)(BufferDataAddr | BOwnership_DMA | NonCache );
		pBufferDescriptor->StatusField = (U32)0x0;
		pBufferDescriptor->LengthField = (U32)0x0;
		pBufferDescriptor->NextBufferDescriptor = NULL;
		
		pLastBufferDescriptor = pBufferDescriptor;
		pBufferDescriptor++;
		BufferDataAddr += sizeof(sHDLCFrame); 
	} // end for loop
      
	// Make Buffer descriptor to ring buffer type.     
	pBufferDescriptor--; 
	pBufferDescriptor->NextBufferDescriptor = (U32)pStartBufferDescriptor;
}


/*
 *  Function : HDMA_Tx_init
 *  Description : HDMA Tx DMA initialize
 */
void HDMA_Tx_init(U32 channel, U32 TxDB, int Size)
{
	// Initialize HDLC transmit DMA for transmit operation
	HDMATXMA(channel) 	= TxDB ;
	HDMATXCNT(channel) 	= Size ;
}

/*
 *  Function : HDLC_Rx_init
 *  Description : HDLC Rx initialize
 *  return 1 : HDLC receive initialize ok
 *  return 0 : HDLC receive initialize fail
 */
int HDLC_Rx_init(U32 channel)
{
	sBufferDescriptor 	*CRxBDPtr ;
	HDLC_Device_Entry  	*Dev ;
	U32			DataBuffer;

	// Step 1. Get HDLC device entry pointer
	Dev = (HDLC_Device_Entry *)&HDLC_Dev[channel] ; 

	// Step 2. Get receive buffer pointer from global variable
	CRxBDPtr = (sBufferDescriptor *)gCRxBDPtr[channel] ;
	DataBuffer = (U32)CRxBDPtr->BufferDataPtr ;

	// Step 3. Check Rx DMA ownership

⌨️ 快捷键说明

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