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

📄 csosfun.c

📁 EP9315开发板的Wince6.0的BSP包文件
💻 C
字号:
//**********************************************************************
//                                                                      
// Filename: CsOSFun.c
//                                                                      
// Description: 
//
// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF
// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO
// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A
// PARTICULAR PURPOSE.
//
// Use of this source code is subject to the terms of the Cirrus end-user
// license agreement (EULA) under which you licensed this SOFTWARE PRODUCT.
// If you did not accept the terms of the EULA, you are not authorized to 
// use this source code. For a copy of the EULA, please see the 
// EULA.RTF on your install media.
//
// Copyright(c) Cirrus Logic Corporation 2005, All Rights Reserved                       
//                                                                      
//**********************************************************************


#include "ndis4cs8950.h"
#include "cs8950hw.h"

extern WORD GetTheIndexOfAFreePakcet( PCHIP pChip);
extern WORD AddAFreePakcetToQ(PCHIP pChip, WORD index);

//****************************************************************************
// CrystalInterruptService()
//****************************************************************************
extern VOID CrystalInterruptService(
    OUT PBOOLEAN InterruptRecognized,
    OUT PBOOLEAN QueueDpc,
    IN  PVOID Context
    )

/*++

Routine Description:

    Interrupt service routine.  This routine only gets
    called during initial initialization of the adapter.

Arguments:

    InterruptRecognized - Boolean value which returns TRUE if the
        ISR recognizes the interrupt as coming from this adapter.

    QueueDpc - TRUE if a DPC should be queued.

    Context - Really a pointer to the adapter.

Return Value:

    Returns true if the card ISR is non-zero.

--*/

{


   NDIS_HANDLE MiniportAdapterContext = Context;
   VPM_SetupMiniContext;

      *InterruptRecognized = TRUE;
      *QueueDpc = TRUE;


   return;

}

//****************************************************************************
// CrystalInterruptService()
//****************************************************************************
VOID CrystalHandleInterrupt(
    IN NDIS_HANDLE MiniportAdapterContext
    )

/*++

Routine Description:

    This DPR routine is queued by the wrapper after every interrupt
    and also by other routines within the driver that notice that
    some deferred processing needs to be done.  It's main
    job is to call the interrupt processing code.

Arguments:

    MiniportAdapterContext - Really a pointer to the adapter.

Return Value:

    None.

--*/

{

   WORD  Result=TRUE;
   VPM_SetupMiniContext;


   if (pvMini_Context->CurrentState == NdisHardwareStatusInitializing) {
      return;
   } /* endif */


   while (Result) {  // Loop until ISR indicates there was nothing to do

      Result = VchipISR( pvMini_Context->pChip );

   } /* endwhile */

   return;

 }


//****************************************************************************
// CrystalTransferData()
//****************************************************************************
extern NDIS_STATUS CrystalTransferData(
    OUT PNDIS_PACKET  Packet,
    OUT PUINT  BytesTransferred,
    IN NDIS_HANDLE  MiniportAdapterHandle,
    IN NDIS_HANDLE  MacReceiveContext,
    IN UINT  ByteOffset,
    IN UINT  BytesToTransfer
    )

/*++

Routine Description:

    A protocol calls the CrystalTransferData request (indirectly via
    NdisTransferData) from within its Receive event handler
    to instruct the driver to copy the contents of the received packet
    a specified paqcket buffer.

Arguments:

    MiniportAdapterContext - Context registered with the wrapper, really
        a pointer to the VP context.

    MiniportReceiveContext - The context value passed by the driver on its call
    to NdisMEthIndicateReceive.  The driver can use this value to determine
    which packet, on which adapter, is being received.

    ByteOffset - An unsigned integer specifying the offset within the
    received packet at which the copy is to begin.  If the entire packet
    is to be copied, ByteOffset must be zero.

    BytesToTransfer - An unsigned integer specifying the number of bytes
    to copy.  It is legal to transfer zero bytes; this has no effect.  If
    the sum of ByteOffset and BytesToTransfer is greater than the size
    of the received packet, then the remainder of the packet (starting from
    ByteOffset) is transferred, and the trailing portion of the receive
    buffer is not modified.

    Packet - A pointer to a descriptor for the packet storage into which
    the MAC is to copy the received packet.

    BytesTransfered - A pointer to an unsigned integer.  The MAC writes
    the actual number of bytes transferred into this location.  This value
    is not valid if the return status is STATUS_PENDING.

Return Value:

    The function value is the status of the operation.


--*/

{
   FRAG   (*Frags)[MAX_FRAGS];
   UINT   ProtocolBufferCount;
   PNDIS_BUFFER  pProtocolBuffer;
   UINT   ProtocolTotalBufferLength;
   PUCHAR pProtocolVBuffer;
   ULONG  ProtocolVBufferLength;
   PUCHAR pSource;
   UINT   FragIndex=0;
   UINT   CurrentSize, CurrentFragSize;
   UINT   BytesLeftToCopy;
   UINT   BytesSkipped;
   PRECEIVE_CONTEXT pReceiveContext;
   PCHIP  pChip;

   pReceiveContext = (PVOID)MacReceiveContext;

	 if (BytesToTransfer>pReceiveContext->FrameSize) {
      *BytesTransferred = 0;
      return NDIS_STATUS_FAILURE;
   }

   pChip = pReceiveContext->pChip;

   Frags = (PVOID)pReceiveContext->pFrag;

   pSource = Frags[0]->pBuffer;
   CurrentFragSize = Frags[0]->BuffLength;

   NdisQueryPacket( Packet,
                    NULL,
                    &ProtocolBufferCount,
                    &pProtocolBuffer,
                    &ProtocolTotalBufferLength
                    );

   NdisQueryBuffer(
         pProtocolBuffer,
         &pProtocolVBuffer,
         &ProtocolVBufferLength
         );

   ByteOffset += VP_HEADERSIZE;
   // Find First frag from Byte Offset
   for (BytesSkipped=0;
        BytesSkipped < ByteOffset;
        BytesSkipped += Frags[FragIndex++]->BuffLength ) {
      if ((Frags[FragIndex]->BuffLength+BytesSkipped) > ByteOffset ) {
         pSource = Frags[FragIndex]->pBuffer + (ByteOffset-BytesSkipped);
         CurrentFragSize = Frags[FragIndex]->BuffLength - (ByteOffset-BytesSkipped);
         break;
      } /* endif */
   } /* endfor */
   // setup curfraglength

   for (*BytesTransferred = 0, FragIndex = 0,
        BytesLeftToCopy = BytesToTransfer;
        *BytesTransferred < BytesToTransfer ;
         BytesLeftToCopy-=CurrentSize,*BytesTransferred+=CurrentSize,
         ProtocolVBufferLength-=CurrentSize, CurrentFragSize-=CurrentSize) {

      if (FragIndex >= pReceiveContext->FragCount) {
         return NDIS_STATUS_FAILURE;
      }

      if (ProtocolVBufferLength == 0) {

          NdisGetNextBuffer(
                pProtocolBuffer,
                &pProtocolBuffer
                );
          NdisQueryBuffer(
                pProtocolBuffer,
                &pProtocolVBuffer,
                &ProtocolVBufferLength
                );
      } /* endif */

      if (CurrentFragSize == 0) {

         CurrentFragSize = Frags[++FragIndex]->BuffLength;
         pSource = Frags[FragIndex]->pBuffer;

      } /* endif */

      CurrentSize = BytesLeftToCopy;

      if ( Frags[FragIndex]->BuffLength < CurrentSize) {
         CurrentSize = Frags[FragIndex]->BuffLength;
      } /* endif */

      if ( ProtocolVBufferLength < CurrentSize) {
         CurrentSize = ProtocolVBufferLength;
      } /* endif */

      NdisMoveMemory(  pProtocolVBuffer, pSource, CurrentSize );
      pProtocolVBuffer += CurrentSize;
      pSource += CurrentSize;

   } /* endfor */

   return NDIS_STATUS_SUCCESS;
}

//****************************************************************************
// SendPacketToVChip()
//****************************************************************************
NDIS_STATUS SendPacketToVChip(PCHIP pChip, PNDIS_PACKET Packet)
{

    UINT         PhysicalBufferCount;
    UINT         VirtualBufferCount;
    PNDIS_BUFFER pNDISBuffer;
    PVOID        pVirtualBuffer;
    UINT         VirtualBufferLength;
    UINT         PacketLength;
    WORD         BufferHeld;
    WORD FragIndex = 0;

    PCD    pCD;
    BYTE  *pTxBuff;

    pCD    = pChip->pData;
	pTxBuff = pCD->TxBuff[pCD->TxReqIndex].pBuff;

    NdisQueryPacket( Packet,
                     &PhysicalBufferCount,
                     &VirtualBufferCount,
                     &pNDISBuffer,
                     &PacketLength
                     );

    if(pNDISBuffer == NULL) {
        DEBUGMSG(ZONE_ERROR,(TEXT("SendPacketToVChip Failed \n")));
       return NDIS_STATUS_FAILURE;
    } /* endif */
    if(PacketLength > 1514)  {
		 VchipSend( pChip,
                        (DWORD)Packet,
                        (WORD)PacketLength);
		 return NDIS_STATUS_SUCCESS;
    } /* endif */

    NdisQueryBuffer(
          pNDISBuffer,
          &pVirtualBuffer,
          &VirtualBufferLength
          );

    while (VirtualBufferCount--) {

       if ((pVirtualBuffer != NULL) && (VirtualBufferLength != 0)) {
	        NdisMoveMemory( pTxBuff, pVirtualBuffer, VirtualBufferLength);
    	    pTxBuff += VirtualBufferLength;
       } /* endif */

       if (VirtualBufferCount != 0) {
          NdisGetNextBuffer(
                pNDISBuffer,
                &pNDISBuffer
                );

          if (pNDISBuffer != NULL) {
             NdisQueryBuffer(
                   pNDISBuffer,
                   &pVirtualBuffer,
                   &VirtualBufferLength
                   );

          } else {
             pVirtualBuffer = NULL;
          } /* endif */
       } /* endif */
    } /* endwhile */

    BufferHeld = VchipSend( pChip,
                        (DWORD)Packet,
                        (WORD)PacketLength);

    if (BufferHeld) {
       return NDIS_STATUS_PENDING;
    } else {
       return NDIS_STATUS_SUCCESS;
    } /* endif */

};


//****************************************************************************
// CrystalSend()
//****************************************************************************
extern NDIS_STATUS CrystalSend(
    IN NDIS_HANDLE MiniportAdapterContext,
    IN PNDIS_PACKET Packet,
    IN UINT SendFlags
    )

/*++

Routine Description:

    The CrystalSend request instructs a driver to transmit a packet through
    the adapter onto the medium.

Arguments:

    MiniportAdapterContext - Context registered with the wrapper, really
        a pointer to the Virtual Protocol context.

    Packet - A pointer to a descriptor for the packet that is to be
    transmitted.

    SendFlags - Optional send flags

Return Value:

    The function value is the status of the operation.

--*/

{
    NDIS_STATUS  Status = NDIS_STATUS_SUCCESS;
    PTXQUEUEELEMENT pTxQueueElem;
    WORD LoopCount = 0;
    PNDIS_PACKET pTempTxPacket;
    PTXQUEUEELEMENT pTempTxQueueElem;

    VPM_SetupMiniContext;

    if ((pvMini_Context->CurrentState != NdisHardwareStatusReady) ||
        (pvMini_Context->CableConnected == NdisMediaStateDisconnected)) {

       return NDIS_STATUS_SUCCESS;
    }

    if (pvMini_Context->XmitQueueDepth >= pChip->Config.MaxTxCount) {

       return NDIS_STATUS_RESOURCES;
    }

    pTxQueueElem = (PVOID)&Packet->MiniportReserved;
    pvMini_Context->XmitQueueDepth++;


    if (pvMini_Context->TxQueueHead == NULL) {  // Queue Empty

       pvMini_Context->TxQueueHead = Packet;

    } else {                                    // Queue Not Empty


       // Run the Queue to the End
       for (pTempTxPacket=pvMini_Context->TxQueueHead,
              pTempTxQueueElem=(PVOID)&pTempTxPacket->MiniportReserved ;
            pTempTxQueueElem->NextPacket != NULL ;
            pTempTxPacket = pTempTxQueueElem->NextPacket,
              pTempTxQueueElem=(PVOID)&pTempTxPacket->MiniportReserved
              , LoopCount++
           ) {
         if ((DWORD)pTempTxPacket == (DWORD)Packet) {
            return NDIS_STATUS_INVALID_PACKET;
         }
       } /* endfor */

       // Put Current Element on the end of the queue
       pTempTxQueueElem->NextPacket = Packet;

    } /* endif */

    pTxQueueElem->NextPacket = NULL;
    pTxQueueElem->XmitRC = NDIS_STATUS_NOT_INDICATING;


    Status = SendPacketToVChip( pChip, Packet );

    if ((Status != NDIS_STATUS_PENDING) && (Status != NDIS_STATUS_SUCCESS))
    {

       pTxQueueElem->XmitRC = Status;
       // Dequeue the last element
       if (pvMini_Context->TxQueueHead == Packet) {
          pvMini_Context->TxQueueHead = NULL;
       } else {
          pTempTxQueueElem->NextPacket = NULL;
       } /* endif */
       pvMini_Context->XmitQueueDepth--;

    } else {


      if (pTxQueueElem->XmitRC == NDIS_STATUS_NOT_INDICATING)  {  // Send did not complete

         pTxQueueElem->XmitRC = Status = NDIS_STATUS_PENDING;

      } else {
         Status = pTxQueueElem->XmitRC;
      } /* endif */

    } /* endif */
    return Status;

}

//****************************************************************************
// CrystalSendPackets()
//****************************************************************************
extern VOID CrystalSendPackets(
         IN NDIS_HANDLE  MiniportAdapterContext,
         IN PPNDIS_PACKET  PacketArray,
         IN UINT  NumberOfPackets
         )
{
        UINT i;
        NDIS_STATUS Status;
 for (i=0; i<NumberOfPackets; i++, PacketArray++)
    {
       Status = CrystalSend( MiniportAdapterContext, *PacketArray, 0 );
       NDIS_SET_PACKET_STATUS(*PacketArray, Status );
    }

};

//****************************************************************************
// CrystalGetReturnedPacket(
//****************************************************************************
extern
VOID
CrystalGetReturnedPacket(
	IN NDIS_HANDLE  MiniportAdapterContext,
    IN PNDIS_PACKET pPacket
	)
{
    WORD index;
	WORD *pW;
    PCD   pCD;


	VPM_SetupMiniContext;
    pCD    = pChip->pData;

	/* Reinitialize the NDIS packet for later use. */
    //NdisReinitializePacket(pPacket);

	pW=(WORD *)pPacket->MiniportReserved;
    index=*pW;
	AddAFreePakcetToQ(pChip, index);
    pCD->numNdisPacketsIndicated--;

}


⌨️ 快捷键说明

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