📄 sc2410_usb_ser.c
字号:
// Protect the following from collision on hardware registers.
// In particular, we can't let anyone else do SC2410_USB_ accesses between
// time we set the read address and time we do the actual read in
// the loop below.
EnterCriticalSection(&(pHWHead->HwRegCritSec));
fRXFlag = SC2410_USB_RxIntHandler(pHWHead, pRxBuffer, pBufflen);
LeaveCriticalSection(&(pHWHead->HwRegCritSec));
// if we saw one (or more) EVT chars, then generate an event
if( fRXFlag )
EvaluateEventFlag( pHWHead->pMddHead, EV_RXFLAG );
#ifdef DEBUG
if( ZONE_RXDATA )
CELOGDATA(1, CELID_RAW_UCHAR, pRxOrig, (WORD)*pBufflen, 1, CELZONE_MISC);
#endif
DEBUGMSG(1, (TEXT("--SerRxIntr - rx %d, drop %d.\r\n"),
*pBufflen,
pHWHead->DroppedBytes));
RetVal = pHWHead->DroppedBytes;
pHWHead->DroppedBytes = 0;
return RetVal;
}
/*************************************************************************
@doc OEM
@func PVOID | SerGetRxStart | This routine returns the start of the
hardware receive buffer. See SerGetRxBufferSize.
@rdesc The return value is a pointer to the start of the device
receive buffer.
*************************************************************************/
static
PVOID SerGetRxStart( PVOID pHead ) // @parm PVOID returned by Serinit.
{
DEBUGMSG(1, (TEXT("SerGetRxStart\r\n")));
return NULL;
}
/*************************************************************************
@doc OEM
@func ULONG | SerGetInterruptType | This function is called
by the MDD whenever an interrupt occurs. The return code
is then checked by the MDD to determine which of the four
interrupt handling routines are to be called.
@rdesc This routine returns a bitmask indicating which interrupts
are currently pending.
*************************************************************************/
static
INTERRUPT_TYPE SerGetInterruptType( PVOID pHead ) // Pointer to hardware head
{
PSER_INFO pHWHead = (PSER_INFO)pHead;
INTERRUPT_TYPE interrupts=0;
DEBUGMSG(1, (TEXT("++SerGetInterruptType 0x%X\r\n"), pHead));
//Jonathan01_0915 Start
//RETAILMSG(1,(TEXT("::: SerGetInterruptType start\r\n")));
if(!((!(s2410IOP->rGPGDAT & (0x1 << 1))) && (s2410IOP->rGPGDAT & (0x1 << 8))) || pDriverGlobals->misc.USBCableEvent == 0)
{
pHWHead->ModemStatus &= ~MS_RLSD_ON;
EvaluateEventFlag(pHWHead->pMddHead, EV_RLSD);
if(hUSBAcInIntr) SetEvent(hUSBAcInIntr); //edyeh1108
//RETAILMSG(1,(TEXT("::: SerGetInterruptType startA\r\n")));
}
else if(pDriverGlobals->misc.USBCableEvent == 2)
{
pDriverGlobals->misc.USBCableEvent = 1;
pHWHead->ModemStatus &= ~MS_RLSD_ON;
EvaluateEventFlag(pHWHead->pMddHead, EV_RLSD);
Sleep(3000);
s2410IOP->rGPJDAT |= (0x1 << 9);
if(hUSBAcInIntr) SetEvent(hUSBAcInIntr); //edyeh1108
//RETAILMSG(1,(TEXT("::: SerGetInterruptType startB\r\n")));
}
//Jonathan01_0915 end
/*jocky 0308
else{ //edyeh1108, AC-in
if(hUSBAcInIntr) SetEvent(hUSBAcInIntr);
}
*///jocky0308
//RETAILMSG(1,(TEXT("::: SerGetInterruptType end\r\n")));
interrupts = SC2410_USB_GetInterruptType(pHWHead);
if (INTR_LINE & interrupts)
{
pHWHead->dConfIdx = 0;
SignalRemoval(pHWHead);
}
#ifdef POLL_FOR_DISCONNECT
//interrupts = HW_GetInterruptType(pHWHead);
//RETAILMSG(1, (TEXT("interrupts = 0x%x\r\n"), interrupts));
if (interrupts)
{
pHWHead->wSOFStableCnt = 0;
//RETAILMSG(1, (TEXT("pHWHead->wSOFStableCnt = 0x%x\r\n"), pHWHead->wSOFStableCnt));
}
else if (pHWHead->dConfIdx && (pHWHead->wPrevSOF == pHWHead->wSOF))
{
if (++pHWHead->wSOFStableCnt > SOF_STABLE_MAX)
{
//RETAILMSG(1, (TEXT("DCD Dropped due to: wSOFStableCnt: %u\r\n"), pHWHead->wSOFStableCnt));
pHWHead->dConfIdx = 0;
SignalRemoval(pHWHead);
}
}
#endif
DEBUGMSG (1, (TEXT("--SerGetInterruptType 0x%X, 0x%X\r\n"),
pHead, interrupts));
//RETAILMSG(1,(TEXT("::: SerGetInterruptType end\r\n")));
return interrupts;
}
/*************************************************************************
@doc OEM
@func ULONG | SerModemIntr | This routine is called from the MDD
whenever INTR_MODEM is returned by SerGetInterruptType.
@rdesc None
*************************************************************************/
static
VOID SerModemIntr( PVOID pHead ) // Hardware Head
{
PSER_INFO pHWHead = (PSER_INFO)pHead;
DWORD dwModemStatus;
dwModemStatus = pHWHead->ModemStatus;
DEBUGMSG(1, (TEXT("+++SerModemIntr\r\n")));
SC2410_USB_DoEndpoint0(pHWHead, &dwModemStatus);
if ( pHWHead->dConfIdx )
{
if ( pHWHead->cOpenCount)
{
// If open, notify app of any control line changes.
DEBUGMSG(1, (TEXT("Modem Status %2.2X <> %2.2X\r\n"),
pHWHead->ModemStatus, dwModemStatus));
if( (pHWHead->ModemStatus & MS_DSR_ON) != (dwModemStatus & MS_DSR_ON) )
EvaluateEventFlag(pHWHead->pMddHead, EV_DSR);
if( (pHWHead->ModemStatus & MS_CTS_ON) != (dwModemStatus & MS_CTS_ON) )
EvaluateEventFlag(pHWHead->pMddHead, EV_CTS);
if( (pHWHead->ModemStatus & MS_RLSD_ON) != (dwModemStatus & MS_RLSD_ON) )
EvaluateEventFlag(pHWHead->pMddHead, EV_RLSD);
} else {
// If RLSD transitioned to active, we need to generate event.
if( (dwModemStatus & MS_RLSD_ON) && !(pHWHead->ModemStatus & MS_RLSD_ON) )
{
if ( IsAPIReady(SH_WMGR) )
{
CeEventHasOccurred (NOTIFICATION_EVENT_RS232_DETECTED, NULL);
}
DEBUGMSG (0, (TEXT("Indicated RS232 Cable Event\r\n")));
}
}
}
pHWHead->ModemStatus = dwModemStatus;
DEBUGMSG(1, (TEXT("---SerModemIntr\r\n")));
}
/*************************************************************************
@doc OEM
@func ULONG | SerLineIntr | This routine is called from the MDD
whenever INTR_LINE is returned by SerGetInterruptType.
@rdesc None
*************************************************************************/
static
VOID SerLineIntr( PVOID pHead ) // Hardware Head
{
PSER_INFO pHWHead = (PSER_INFO)pHead;
DEBUGMSG(1, (TEXT("SerLineIntr\r\n")));
// USB serial doesn't have a concept of anything like the LSR.
// But since a bus reset is what we sort of equate to DCD, I use
// this routine to handle USB reset conditions.
// Note that by the time we get here with an SC2410_USB , we are actually
//plugged back into the bus. I added some polling code to try and detect
// detaches sooner
SC2410_USB_LineIntHandler(pHWHead); // Re-initialize the hardware
}
/*************************************************************************
@doc OEM
@func ULONG | SerGetRxBufferSize | This function returns
the size of the hardware buffer passed to the interrupt
initialize function. It would be used only for devices
which share a buffer between the MDD/PDD and an ISR.
@rdesc This routine always returns 0 for 16550 UARTS.
**************************************************************************/
static
ULONG SerGetRxBufferSize( PVOID pHead )
{
DEBUGMSG(1, (TEXT("SerGetRxBufferSize\r\n")));
//return 10280;
return 17920;//jocky
}
/*************************************************************************
@doc OEM
@func ULONG | SerTXIntr | This routine is called from the new MDD
whenever INTR_TX is returned by SerGetInterruptType. It is
responsible for loading up the TX FIFO with next block of data.
@rdesc None
**************************************************************************/
static
VOID SerTxIntr( PVOID pHead, // Hardware Head
PUCHAR pTxBuffer, // @parm Pointer to receive buffer
ULONG *pBuffLen ) // @parm In = max bytes to transmit,
// out = bytes transmitted
{
PSER_INFO pHWHead = (PSER_INFO)pHead;
DEBUGMSG(1, (TEXT("SerTxIntr+\r\n")));
pHWHead->CommErrors &= ~CE_TXFULL;
SC2410_USB_TxIntHandler(pHWHead, pTxBuffer, pBuffLen);
DEBUGMSG(1, (TEXT("SerTxIntr-, %d bytes\r\n"), *pBuffLen));
}
/*************************************************************************
@doc OEM
@func BOOL | SerPowerOff | Called by driver to turn off power to
serial port.
Not exported to users, only to driver.
@rdesc This routine returns a status.
************************************************************************/
static
BOOL SerPowerOff( PVOID pHead ) // @parm PVOID returned by SerInit.
{
PSER_INFO pHWHead = (PSER_INFO)pHead;
pHWHead->cOpenCount = 0;
//RETAILMSG(1,(TEXT("USB : SerPowerOff \r\n")));
/*
if ( pHWHead->cOpenCount )
{
EvaluateEventFlag( pHWHead->pMddHead, EV_RXFLAG );
}
return (TRUE);
*/
return HW_PowerOff(pHead);
}
/*************************************************************************
@doc OEM
@func BOOL | SerPowerOn |
Called by driver to turn on power to serial port.
Not exported to users, only to driver.
@rdesc This routine returns a status.
************************************************************************/
static
BOOL SerPowerOn( PVOID pHead ) // @parm PVOID returned by SerInit.
{
PSER_INFO pHWHead = (PSER_INFO)pHead;
//RETAILMSG(1,(TEXT("USB : SerPowerOn \r\n")));
return HW_PowerOn(pHead);
}
/*************************************************************************
@doc OEM
@func void | SerClearDtr | This routine clears DTR.
@rdesc None.
**************************************************************************/
static
VOID SerClearDTR( PVOID pHead ) // @parm PVOID returned by HWinit.
{
DEBUGMSG(1, (TEXT("SerClearDTR, 0x%X\r\n"), pHead));
// We don't support DTR emulation.
}
/*************************************************************************
@doc OEM
@func VOID | SerSetDTR | This routine sets DTR.
@rdesc None.
**************************************************************************/
static
VOID SerSetDTR( PVOID pHead ) // @parm PVOID returned by HWinit.
{
DEBUGMSG(1, (TEXT("SerSetDTR, 0x%X\r\n"), pHead));
// We don't support DTR emulation.
}
/*************************************************************************
@doc OEM
@func VOID | SerClearRTS | This routine clears RTS.
@rdesc None.
**************************************************************************/
static
VOID SerClearRTS( PVOID pHead ) // @parm PVOID returned by HWinit.
{
DEBUGMSG(1, (TEXT("SerClearRTS, 0x%X\r\n"), pHead));
// We don't support RTS emulation.
}
/*************************************************************************
@doc OEM
@func VOID | SerSetRTS | This routine sets RTS.
@rdesc None.
**************************************************************************/
static
VOID SerSetRTS( PVOID pHead ) // @parm PVOID returned by HWinit.
{
DEBUGMSG(1, (TEXT("SerSetRTS, 0x%X\r\n"), pHead));
// We don't support RTS emulation.
}
/*************************************************************************
@doc OEM
@func BOOL | SerEnableIR | This routine enables ir.
Not exported to users, only to driver.
@rdesc Returns TRUE if successful, FALSEotherwise.
**************************************************************************/
static
BOOL SerEnableIR( PVOID pHead, // @parm PVOID returned by Serinit.
ULONG BaudRate ) // @parm PVOID returned by HWinit.
{
PSER_INFO pHWHead = (PSER_INFO)pHead;
DEBUGMSG(1, (TEXT("SerEnableIR, 0x%X\r\n"), pHead));
// We don't support an IR mode, so fail.
return (FALSE);
}
/*************************************************************************
@doc OEM
@func BOOL | SerDisableIR | This routine disable the ir.
Not exported to users, only to driver.
@rdesc Returns TRUE if successful, FALSEotherwise.
**************************************************************************/
static
BOOL SerDisableIR( PVOID pHead ) // @parm PVOID returned by Serinit.
{
PSER_INFO pHWHead = (PSER_INFO)pHead;
DEBUGMSG(1, (TEXT("SerDisableIR, 0x%X\r\n"), pHead));
// We don't support an IR mode. But don't fail, in case
// someone calls this redundantly to ensure that we are
// in wired mode, which is what we support.
return (TRUE);
}
/*************************************************************************
@doc OEM
@func VOID | SerClearBreak | This routine clears break.
@rdesc None.
*************************************************************************/
static
VOID SerClearBreak( PVOID pHead ) // @parm PVOID returned by HWinit.
{
DEBUGMSG(1, (TEXT("SerClearBreak, 0x%X\r\n"), pHead));
// We don't have a concept of break over USB serial
}
/*************************************************************************
@doc OEM
@func VOID | SerSetBreak | This routine sets break.
@rdesc None.
*************************************************************************/
static
VOID SerSetBreak( PVOID pHead ) // @parm PVOID returned by HWinit.
{
DEBUGMSG(1, (TEXT("SerSetBreak, 0x%X\r\n"), pHead));
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -