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

📄 ser_arch.c

📁 基于三星S3C2410的串口驱动程序
💻 C
📖 第 1 页 / 共 5 页
字号:
			pInfoSerArch->fSW_EnTxINT = TRUE;

			pInfoSerArch->RestartTxForFlow = 1;
		}
	}
	EdbgOutputDebugString( "INTR_MODEM: mState=%x\r\n", pInfoSerArch->ModemStatus );
	return pInfoSerArch->ModemStatus;
}

#ifndef CANCEL_XYG_SER_RX

// ********************************************************************
// 声明:ULONG	SerArch_Recv( PVOID pHead, LPBYTE pBufDes, LONG* pnLenBuf )
// 参数:
//	IN pHead-ARCH信息
//	IN pBufDes-获取的数据
//	IN pnLenBuf-指定pBufDes的长度和实际获取数据的长度
// 返回值:
//	无
// 功能描述:处理接收中断
// 引用: 
// ********************************************************************
ULONG	SerArch_Recv( PVOID pHead, LPBYTE pBufRecv, LONG* pnLenBuf )
{
    PSERARCH_INFO	pInfoSerArch = (PSERARCH_INFO)pHead;
	DCB*			lpDCB;
    LONG			nLenRecv;
	LPBYTE			pBufEnd;

    BOOL			fRXFlag;
    UCHAR			cCharRx;
	
	//
	nLenRecv = RWBuf_ReadBuf( pInfoSerArch->lpRWBuf, pBufRecv, *pnLenBuf );
	*pnLenBuf = nLenRecv;
	if( !nLenRecv )
	{
		return 0;
	}
	//RETAILMSG(1,(TEXT("\r\n===========SerArch_Recv()===========\r\n")));
	lpDCB = pInfoSerArch->lpDCB;
	//是不是半工设备
	//if( pInfoSerArch->dwComFun == COM_SIR )
	//{
	//	EnterCriticalSection(&(pInfoSerArch->csTransmit));
	//}

	fRXFlag = FALSE;
	pBufEnd = pBufRecv + nLenRecv;
    while( pBufRecv<pBufEnd )
    {
		//读取数据
		cCharRx = *pBufRecv;
		pBufRecv ++;
		//RETAILMSG(1,(TEXT("\r\n [ %x ] \r\n"), cCharRx));
		
		//若是Dsr敏感,且Dsr是关的, 则 忽略数据
		if( lpDCB->fDsrSensitivity && !(pInfoSerArch->ModemStatus & MS_DSR_ON) )
		{
			//RETAILMSG( 1, (TEXT("\r\nxyg_Recv: 若是Dsr敏感,且Dsr是关的,则 忽略数据\r\n")) );
			continue;
		}
		else if (!cCharRx && lpDCB->fNull)//空字符  是不是要丢弃
		{
			//RETAILMSG( 1, (TEXT("\r\nxyg_Recv: 丢弃空字符\r\n")) );
			continue;
		}
		else
		{
			//出现事件字符EvtChar,通知WaitCommEvent
			if (cCharRx == lpDCB->EvtChar)
				fRXFlag = TRUE;
		}// for else <normal operation>
    }// for while

    if( fRXFlag )
	{
		//出现事件字符EvtChar,通知WaitCommEvent
		pInfoSerArch->lpfnEventNotify(pInfoSerArch->pHeadDrv, EV_RXFLAG);
	}

	//是不是半工设备
	//if( pInfoSerArch->dwComFun == COM_SIR )
	//{
	//	LeaveCriticalSection(&(pInfoSerArch->csTransmit));
	//}

	//EdbgOutputDebugString( "read=%d\r\n", (*pnLenBuf) );
	return 0;
}

#else

// ********************************************************************
// 声明:ULONG	SerArch_Recv( PVOID pHead, LPBYTE pBufDes, LONG* pnLenBuf )
// 参数:
//	IN pHead-ARCH信息
//	IN pBufDes-获取的数据
//	IN pnLenBuf-指定pBufDes的长度和实际获取数据的长度
// 返回值:
//	无
// 功能描述:处理接收中断
// 引用: 
// ********************************************************************
ULONG	SerArch_Recv( PVOID pHead, LPBYTE pBufDes, LONG* pnLenBuf )
{
    PSERARCH_INFO	pInfoSerArch = (PSERARCH_INFO)pHead;
	volatile	PS2410_UART_REG	pUART;	//UART
	DCB*			lpDCB;
    LPBYTE			pBufRecv;
    LONG			nLenRecv;

    BOOL			fRXFlag;
    UCHAR			cCharRx;
	ULONG			rFifoStat;
	//BOOL			fNeedClearRTS;
	ULONG IntSubPndVal;//=0;
	
	//RETAILMSG(1,(TEXT("\r\n===========SerArch_Recv()===========\r\n")));
	lpDCB = pInfoSerArch->lpDCB;
	pUART = pInfoSerArch->pUART;
	//是不是半工设备
	//if( pInfoSerArch->dwComFun == COM_SIR )
	//{
	//	EnterCriticalSection(&(pInfoSerArch->csTransmit));
	//}


//	RETAILMSG(1,(TEXT("\r\n Ser_Query \r\n")));
		
	//fNeedClearRTS = TRUE;
	fRXFlag = FALSE;
	pBufRecv = pBufDes;
	nLenRecv = *pnLenBuf;
    while( nLenRecv )
    {
		//utsr0 = pUART->utsr0;
		IntSubPndVal  = *(pInfoSerArch->UART_INTSUBSRCPND);
		//查询 出错状态---溢出 | 奇偶 | 帧] 错误
		if(IntSubPndVal & (pInfoSerArch->bErrINT) )
		{
		//	//OEM_WriteDebugByte_ToWnd( 'e' );
			ser_CheckLine( pInfoSerArch, pUART );
		}
		//
		rFifoStat = pUART->rUFSTAT;//INREG(pInfoSerArch,rUFSTAT);
		//if( ((rFifoStat & 0x100) || ((rFifoStat & 0x0f) >= 12)) && fNeedClearRTS )
		//{
		//	CLEARREG(pInfoSerArch, rUMCON, SER2410_RTS);
		//	fNeedClearRTS = FALSE;
		//	//RETAILMSG(1,(TEXT("\r\n==SerArch_Recv(): CLEAR RTS=\r\n")));
		//}
		if( (rFifoStat & 0x100) || (rFifoStat & 0x0f) )
		{
			//读取数据
			cCharRx = *(pInfoSerArch->pUFRXH);
			//RETAILMSG(1,(TEXT("\r\n [ %x ] \r\n"), cCharRx));
	
			//若是Dsr敏感,且Dsr是关的, 则 忽略数据
			if( lpDCB->fDsrSensitivity && !(pInfoSerArch->ModemStatus & MS_DSR_ON) )
			{
				//RETAILMSG( 1, (TEXT("\r\nxyg_Recv: 若是Dsr敏感,且Dsr是关的,则 忽略数据\r\n")) );
				continue;
			}
			else if (!cCharRx && lpDCB->fNull)//空字符  是不是要丢弃
			{
				//RETAILMSG( 1, (TEXT("\r\nxyg_Recv: 丢弃空字符\r\n")) );
				continue;
			}
			else
			{
				//if( utsr1.pre )
				//{
				//	//出现错误,(fErrorChar && fParity)是否替代成ErrorChar
				//	if( lpDCB->fErrorChar && lpDCB->fParity)
				//		cCharRx = lpDCB->ErrorChar;
				//	else
				//		continue;
				//}
				//else
				{
					//出现事件字符EvtChar,通知WaitCommEvent
					if (cCharRx == lpDCB->EvtChar)
                        fRXFlag = TRUE;
					//出现,通知
					//if (cCharRx == lpDCB->EofChar)
					//	pInfoSerArch->CommStat.fEof = 1;
				}	
				
				*pBufRecv = cCharRx;
				pBufRecv ++;
				nLenRecv --;
			}// for else <normal operation>
		}// for if( utsr1.rne )
		else
		{
			int iii;
			break;
			for( iii=0; iii<6000; iii++ )
			{
				rFifoStat = pUART->rUFSTAT;//INREG(pInfoSerArch,rUFSTAT);
				if( (rFifoStat & 0x100) || (rFifoStat & 0x0f) )
				{
					break;
				}
			}
			if( iii>=6000 )
			{
				//usWait( 90 );
				break;
			}
		}
    }// for while
	//IOW_REG_BITWRITE(struct utsr0Bits,&pUART->utsr0,rid,1);
	//清除Pending串口中断
	ClearSubINTPnd(pInfoSerArch, pInfoSerArch->bRxINT ); //| pInfoSerArch->bErrINT
	//if ( *(pInfoSerArch->UART_INTSUBSRCPND) & ( pInfoSerArch->bRxINT | pInfoSerArch->bErrINT ) )
	//{
	//	;
	//}
	//else
	{
		ClearINTPnd(pInfoSerArch, pInfoSerArch->bINT);
	//	if ((*pInfoSerArch->UART_INTPND) & pInfoSerArch->bINT )
	//	{
	//		(*pInfoSerArch->UART_INTPND)		|= pInfoSerArch->bINT;
	//	}
	}
	//if( !fNeedClearRTS )
	//{
	//	SETREG(pInfoSerArch, rUMCON, SER2410_RTS);
	//}
#ifdef xyg_ser_sub_mask	
	//引发 接收中断
	EnINT(pInfoSerArch, pInfoSerArch->bINT);
	EnSubINT(pInfoSerArch, (pInfoSerArch->bRxINT|pInfoSerArch->bErrINT));
#endif

//	Debug_Arch();
    if( fRXFlag )
	{
		//出现事件字符EvtChar,通知WaitCommEvent
		pInfoSerArch->lpfnEventNotify(pInfoSerArch->pHeadDrv, EV_RXFLAG);
	}

	//是不是半工设备
	//if( pInfoSerArch->dwComFun == COM_SIR )
	//{
	//	LeaveCriticalSection(&(pInfoSerArch->csTransmit));
	//}

	(*pnLenBuf) = (LONG)(pBufRecv - pBufDes);
	//EdbgOutputDebugString( "read=%d\r\n", (*pnLenBuf) );
	return 0;
}

#endif

// ********************************************************************
// 声明:BOOL	ser_CheckFlowOff( PSERARCH_INFO pInfoSerArch )
// 参数:
//	IN pInfoSerArch-ARCH信息
// 返回值:
//	成功返回TRUE
// 功能描述:检查流控制
// 引用: 
// ********************************************************************
//check wether flow switch is validate
BOOL	ser_CheckFlowOff( PSERARCH_INFO pInfoSerArch )
{
	pInfoSerArch->FlowOffCTS = 0;
	pInfoSerArch->FlowOffDSR = 0;
	if( !(pInfoSerArch->ModemStatus & MS_CTS_ON) && pInfoSerArch->lpDCB->fOutxCtsFlow )
		pInfoSerArch->FlowOffCTS = 1;
	if( !(pInfoSerArch->ModemStatus & MS_DSR_ON) && pInfoSerArch->lpDCB->fOutxDsrFlow )
		pInfoSerArch->FlowOffDSR = 1;
	return( pInfoSerArch->FlowOffDSR || pInfoSerArch->FlowOffCTS );
}

// ********************************************************************
// 声明:ULONG	SerArch_Send( PVOID pHead, LPBYTE pBufSrc, LONG* pnLenBuf )
// 参数:
//	IN pHead-ARCH信息
//	IN pBufSrc-发送数据的BUFFER
//	IN pnLenBuf-发送数据的BUFFER的长度
// 返回值:
//	成功返回发送的个数
// 功能描述:发送数据
// 引用: 
// ********************************************************************
ULONG	SerArch_Send( PVOID pHead, LPBYTE pBufSrc, LONG* pnLenBuf )
{
	volatile PSERARCH_INFO	pInfoSerArch = (PSERARCH_INFO)pHead;
	LPBYTE			pBufSrc_B;
	DWORD			nLenSend;
	ULONG        rFifoStat, TxFifoCnt;
	unsigned int tmpreg;
	//unsigned int FifoModeReg;

	//硬件握手---判断是否可以发送数据(由对方的Dsr/Cts来控制)
	//if( !*pnLenBuf || ((pInfoSerArch->dwOpt & OPT_MODEM) && ser_CheckFlowOff(pInfoSerArch)) )
	if( !*pnLenBuf || ser_CheckFlowOff(pInfoSerArch) )
	{
		//EdbgOutputDebugString( "硬件握手 xyg --fail...\r\n" );
		*pnLenBuf = 0;
		//WRITE_BITFIELD(struct utcr3Bits,&pInfoSerArch->pUART->utcr3,tie,0);

		//停止 发送中断
		DisEnSubINT(pInfoSerArch, pInfoSerArch->bTxINT);
		pInfoSerArch->fSW_EnTxINT = FALSE;
		//清除Pending串口中断
		ClearSubINTPnd(pInfoSerArch, pInfoSerArch->bTxINT );
		ClearINTPnd(pInfoSerArch, pInfoSerArch->bINT);
		//if ((*pInfoSerArch->UART_INTPND) & pInfoSerArch->bINT )
		//{
		//	(*pInfoSerArch->UART_INTPND)		|= pInfoSerArch->bINT;
		//}

		return 0;
	}

	//准备发送数据
	pBufSrc_B= pBufSrc;
	//nLenSend = *pnLenBuf;

	//开始发送数据
	EnterCriticalSection(&(pInfoSerArch->csTransmit));
	//FifoModeReg = INREG(pInfoSerArch, rUFCON);
	rFifoStat = INREG(pInfoSerArch,rUFSTAT);
	TxFifoCnt = ((rFifoStat & SER2410_FIFOCNT_MASK_TX) >> 4);
	if (!(rFifoStat & SER2410_FIFOFULL_TX) && (TxFifoCnt < (SER2410_FIFO_DEPTH_TX-1))) 
	{
		nLenSend = (unsigned char)(SER2410_FIFO_DEPTH_TX-TxFifoCnt);
		if( nLenSend>*pnLenBuf )
		{
			nLenSend=*pnLenBuf;
		}
	}
	else
	{
		nLenSend = 0;
	}

	//RETAILMSG(1,(TEXT("\r\nnLenSend = [ %d ]\r\n"), nLenSend));
	while( nLenSend )
	{
		//检查硬件是否出错,并进入正常状态
		//utsr0 = pUART->utsr0;
		//if( (utsr0.eif) || (utsr0.rbb) || (utsr0.reb) )
		//	ser_CheckLine(pInfoSerArch, pUART);
		//判断硬件是否忙
		//if (FifoModeReg&0x1) // FIFO Mode enabled.
		{
			tmpreg = INREG(pInfoSerArch, rUFSTAT);
			//tmpreg & 0x200 == 1  ->  Fifo full -> waiting...
			//tmpreg & 0xf0 == 0 -> There is no data to send -> break loop.
			//RETAILMSG(1,(TEXT("\r\ntmpreg = [ %d ]\r\n"), tmpreg));
			if ( (tmpreg & 0x200) == 0x200 )
			{
				// //RETAILMSG(DEBUGMODE, (TEXT("SL_TxInt :  fifo full : tmpreg = %x \r\n"), tmpreg));
				break;
			}
		}
		//else
		//{
		//	tmpreg = INREG(pInfoSerArch, rUTRSTAT);
		//	if ( !(tmpreg & 0x2) )
		//		break;
		//}
		//传输数据
		*(pInfoSerArch->pUFTXH) = *pBufSrc;	//发送数据
		pBufSrc ++;
		nLenSend--;
	}

	// 在传输完毕之后,如果是FIFO模式,则需要进行善后处理
	//if (FifoModeReg & 0x1) // FIFO Mode enabled.
	{
		unsigned int cnt = 0;
		while ( 1 )
		{
			//#define INREG(pInfo, reg) (pInfo->s2410SerReg->reg)
			tmpreg = INREG(pInfoSerArch, rUFSTAT);	//获取状态值,循环进行判断
			// //RETAILMSG(DEBUGMODE, (TEXT("SL_TxInt : Waiting till tx buffer empty :  tmpreg = %x \r\n"), tmpreg));
			if ( (tmpreg & 0xf0) == 0) break; // waitint to empty the tx buffer empty...
			if ( cnt++ > 600000 )
			{
				SETREG(pInfoSerArch,rUFCON,0x4);    // tx, rx fifo reset
				break;
			}
		}
	}

	//WRITE_BITFIELD(struct utcr3Bits,&pUART->utcr3,tie,1);	//
	//清除Pending串口中断
	ClearSubINTPnd(pInfoSerArch, pInfoSerArch->bTxINT ); //| pInfoSerArch->bErrINT
	ClearINTPnd(pInfoSerArch, pInfoSerArch->bINT);
	//if ((*pInfoSerArch->UART_INTPND) & pInfoSerArch->bINT )
	//{
	//	(*pInfoSerArch->UART_INTPND)		|= pInfoSerArch->bINT;
	//}
	//引发 发送中断
	//EnINT(pInfoSerArch, pInfoSerArch->bINT);
	EnSubINT(pInfoSerArch, pInfoSerArch->bTxINT);
	pInfoSerArch->fSW_EnTxINT = TRUE;

	LeaveCriticalSection(&(pInfoSerArch->csTransmit));
	
	(*pnLenBuf) = (LONG)(pBufSrc - pBufSrc_B);
	//RETAILMSG( 1,(TEXT("\r\nTX=[ %d ]\r\n"), *pnLenBuf));
	return 0;
}

// 

⌨️ 快捷键说明

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