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

📄 misc.c

📁 驱动开发,经过测试可以直接编译后使用,编译使用DDK中的build工具
💻 C
📖 第 1 页 / 共 3 页
字号:
--*/
{
   PNDIS_BUFFER    pPktBuffer;
   PVOID           pPktBufferVA, pDstBufferVA;
   UINT            uiBufSize, uiTotalLen, uiMdlSizeLeft;
   UINT            uiCopySize, uiTotalBytesCopied;

   NdisGetFirstBufferFromPacket(pPkt,
      &pPktBuffer,
      &pPktBufferVA,
      &uiBufSize,
      &uiTotalLen);

   ASSERT(pPktBuffer && (0 != uiBufSize));

   uiTotalBytesCopied  = 0;

   uiMdlSizeLeft = MmGetMdlByteCount(pIrp->MdlAddress);

   pDstBufferVA = MmGetSystemAddressForMdlSafe(pIrp->MdlAddress, NormalPagePriority);
   if(pDstBufferVA != NULL && uiMdlSizeLeft != 0)
   {
      while(pPktBuffer)
      {
         uiCopySize = (uiMdlSizeLeft < uiBufSize) ? uiMdlSizeLeft :uiBufSize;
   
         // copy the data
         NdisMoveMemory(pDstBufferVA, pPktBufferVA, uiCopySize);
   
         pDstBufferVA         = (PVOID) ((PCHAR)pDstBufferVA + uiCopySize);
         uiTotalBytesCopied  += uiCopySize;
   
         uiMdlSizeLeft       -= uiCopySize;
   
         if(uiMdlSizeLeft <= 0)
            break;
   
         // get the next buffer
         NdisGetNextBuffer(pPktBuffer, &pPktBuffer);
   
         // get details of the new buffer
         if(pPktBuffer)
            NdisQueryBuffer(pPktBuffer, &pPktBufferVA, &uiBufSize);
      }
   }

   return uiTotalBytesCopied;
}

VOID AtmSmRecvReturnTimerFunction (
   IN  PVOID                   SystemSpecific1,
   IN  PVOID                   FunctionContext,
   IN  PVOID                   SystemSpecific2,
   IN  PVOID                   SystemSpecific3
   )
/*++

Routine Description:

    This timer function, checks to see there are any buffered packets that has
    been around for a while.  If so it gives the packet back to the miniport
    driver.
    It queues itself back if there are anymore packets in the queue

    We use NdisGetSystemUpTime, since that is all the resolution we want

Arguments:

    SystemSpecific1 -   Not used
    FunctionContext -   Adapter
    SystemSpecific2 -   Not used
    SystemSpecific3 -   Not used

Return Value:

    None.

--*/
{
   PATMSM_ADAPTER  pAdapt = (PATMSM_ADAPTER)FunctionContext;
   ULONG           ulTime;
   BOOLEAN         bShouldQueueTimerAgain = FALSE;

   ACQUIRE_ADAPTER_GEN_LOCK(pAdapt);

   pAdapt->fRecvTimerQueued = FALSE;

   NdisGetSystemUpTime(&ulTime);


   // check if any packets have been sitting around for long
   // if so, return them

   while(pAdapt->pRecvPktNext)
   {

      PPROTO_RSVD     pPRsvd;
      PNDIS_PACKET    pPkt;

      pPkt    = pAdapt->pRecvPktNext;
      pPRsvd  = GET_PROTO_RSVD(pPkt);

      if((ulTime - pPRsvd->ulTime) >= RECV_BUFFERING_TIME)
      {

         pAdapt->pRecvPktNext    = pPRsvd->pPktNext;

         if(pAdapt->pRecvLastPkt == pPkt)
            pAdapt->pRecvLastPkt = NULL;

         DbgVeryLoud(("Returning a packet that was buffered too long\n"));

         pAdapt->ulRecvPktsCount--;

         // release the recv queue lock
         RELEASE_ADAPTER_GEN_LOCK(pAdapt);

         // return the packet to the miniport
         NdisReturnPackets(&pPkt, 1);

         ACQUIRE_ADAPTER_GEN_LOCK(pAdapt);

      }
      else
      {

         // time hasn't expired for this packet
         ulTime = RECV_BUFFERING_TIME - (ulTime - pPRsvd->ulTime);

         bShouldQueueTimerAgain = TRUE;

         break;
      }
   }

   if(bShouldQueueTimerAgain)
   {

      SET_ADAPTER_RECV_TIMER(pAdapt, ulTime);
   }

   RELEASE_ADAPTER_GEN_LOCK(pAdapt);

   return;
}

VOID AtmSmConnectToPMPDestinations(
   IN  PATMSM_VC           pVc
   )
/*++

Routine Description:

    This will make a call to the destination in PMP case.  It will MakeCall
    to the first member.  Subsequent destinations are added using AddParty.

Arguments:

    pVc           - Ptr to a PMP Vc

Return Value:

    None

--*/
{
   PATMSM_ADAPTER          pAdapt        = (PATMSM_ADAPTER)pVc->pAdapt;
   BOOLEAN                 bLockReleased = FALSE;
   PCO_CALL_PARAMETERS     pCallParameters;
   NDIS_HANDLE             ProtocolVcContext;
   NDIS_HANDLE             ProtocolPartyContext;
   NDIS_STATUS             Status;
   PATMSM_PMP_MEMBER       pMember;

   TraceIn(AtmSmConnectToPMPDestinations);

   ASSERT(VC_TYPE_PMP_OUTGOING == pVc->VcType);

   ACQUIRE_ADAPTER_GEN_LOCK(pAdapt);

   do
   {    // break off loop

      // First find any member addresses that is not yet connected
      for(pMember = pVc->pPMPMembers; pMember; pMember = pMember->pNext)
         if(ATMSM_GET_MEMBER_STATE(pMember) == ATMSM_MEMBER_IDLE)
            break;

         // if there are no - more members to be connected then get out
      if(!pMember)
      {
         break;
      }

      ProtocolVcContext    = (NDIS_HANDLE)pVc;
      ProtocolPartyContext = (NDIS_HANDLE)pMember;

      //
      // First see if we have connected 1 or more members
      //
      if(0 == pVc->ulNumActiveMembers)
      {
         // No one is connected yet, so do a MakeCall

         ASSERT(ATMSM_GET_VC_STATE(pVc) != ATMSM_VC_ACTIVE);

         if(NULL == pVc->NdisVcHandle)
         {

            Status = NdisCoCreateVc(
                        pAdapt->NdisBindingHandle,
                        pAdapt->NdisAfHandle,
                        (NDIS_HANDLE)pVc,
                        &pVc->NdisVcHandle
                        );

            if(NDIS_STATUS_SUCCESS != Status)
            {

               break;
            }

            DbgVeryLoud(("AddMembers: Created VC, VC %x, NdisVcHandle %x\n",
               pVc, pVc->NdisVcHandle));
         }

         ASSERT(NULL != pVc->NdisVcHandle);

         pCallParameters = AtmSmPrepareCallParameters(pAdapt, 
                              &pMember->HwAddr, 
                              TRUE,
                              TRUE);
         if(pCallParameters == (PCO_CALL_PARAMETERS)NULL)
         {

            Status = NdisCoDeleteVc(pVc->NdisVcHandle);
            ASSERT(NDIS_STATUS_SUCCESS == Status);

            pVc->NdisVcHandle = NULL;
            Status = NDIS_STATUS_RESOURCES;

            break;
         }

         ATMSM_SET_VC_STATE(pVc, ATMSM_VC_SETUP_IN_PROGRESS);

         ATMSM_SET_MEMBER_STATE(pMember, ATMSM_MEMBER_CONNECTING);

         pVc->ulNumConnectingMembers++;

         RELEASE_ADAPTER_GEN_LOCK(pAdapt);
         bLockReleased = TRUE;

         Status = NdisClMakeCall(
                     pVc->NdisVcHandle,
                     pCallParameters,
                     ProtocolPartyContext,
                     &pMember->NdisPartyHandle
                     );

         if(NDIS_STATUS_PENDING != Status)
         {

            AtmSmMakeCallComplete(
               Status,
               ProtocolVcContext,
               pMember->NdisPartyHandle,
               pCallParameters
               );
         }

      }
      else
      {
         // we have atleast one connected member, add the rest using AddParty

         ASSERT(NULL != pVc->NdisVcHandle);

         pCallParameters = AtmSmPrepareCallParameters(pAdapt, 
                              &pMember->HwAddr, 
                              FALSE,
                              TRUE);
         if(pCallParameters == (PCO_CALL_PARAMETERS)NULL)
         {

            Status = NDIS_STATUS_RESOURCES;
            break;
         }


         ATMSM_SET_VC_STATE(pVc, ATMSM_VC_ADDING_PARTIES);

         ATMSM_SET_MEMBER_STATE(pMember, ATMSM_MEMBER_CONNECTING);

         pVc->ulNumConnectingMembers++;

         RELEASE_ADAPTER_GEN_LOCK(pAdapt);
         bLockReleased = TRUE;

         Status = NdisClAddParty(
                     pVc->NdisVcHandle,
                     ProtocolPartyContext,
                     pCallParameters,
                     &pMember->NdisPartyHandle
                     );

         if(NDIS_STATUS_PENDING != Status)
         {

            AtmSmAddPartyComplete(
               Status,
               ProtocolPartyContext,
               pMember->NdisPartyHandle,
               pCallParameters
               );
         }

      }

   }while(FALSE);

   if(!bLockReleased)
   {

      RELEASE_ADAPTER_GEN_LOCK(pAdapt);
   }


   if(pVc->ulNumActiveMembers && 
      (pVc->ulNumActiveMembers == pVc->ulNumTotalMembers))
   {

      PIRP pIrp;

      //
      //  1 or more members are connected, send any packets pending on the VC.
      //
      ACQUIRE_ADAPTER_GEN_LOCK(pAdapt);

      DbgInfo(("PMP VC 0x%x connected - %u members\n", pVc, 
         pVc->ulNumActiveMembers));

      ATMSM_SET_VC_STATE(pVc, ATMSM_VC_ACTIVE);

      // now complete IRP that started this connect call
      pIrp = pVc->pConnectIrp;
      pVc->pConnectIrp = NULL;

      ASSERT(pIrp);

      // remove the Vc from the inactive list
      RemoveEntryList(&pVc->List);

      // insert the vc into the active list
      InsertHeadList(&pAdapt->ActiveVcHead, &pVc->List);

      RELEASE_ADAPTER_GEN_LOCK(pAdapt);

      if(pIrp)
      {

         pIrp->IoStatus.Status = STATUS_SUCCESS;

         // now set the connect context
         *(PHANDLE)(pIrp->AssociatedIrp.SystemBuffer) = (HANDLE)pVc;
         pIrp->IoStatus.Information = sizeof(HANDLE);

         IoCompleteRequest(pIrp, IO_NETWORK_INCREMENT);
      }

      AtmSmSendQueuedPacketsOnVc(pVc);

   }
   else
   {

      if(0 == pVc->ulNumTotalMembers)
      {

         // now complete IRP that started this connect call
         PIRP pIrp = pVc->pConnectIrp;

         pVc->pConnectIrp = NULL;

         ASSERT(pIrp);

         if(pIrp)
         {

            pIrp->IoStatus.Status = STATUS_UNSUCCESSFUL;

            pIrp->IoStatus.Information = 0;

            IoCompleteRequest(pIrp, IO_NETWORK_INCREMENT);
         }

         DbgInfo(("PMP VC 0x%x failed to connect any members\n", pVc));

         // Cleanup the VC - remove the reference added at create
         AtmSmDereferenceVc(pVc);
      }
   }

   TraceOut(AtmSmConnectToPMPDestinations);
}

VOID AtmSmConnectPPVC(
   IN  PATMSM_VC           pVc
   )
/*++

Routine Description:

    This will make a call to the destination in PP case.  It will MakeCall
    to the destination.

Arguments:

    pVc           - Ptr to a PP Vc

Return Value:

    None

--*/
{
   PATMSM_ADAPTER          pAdapt        = (PATMSM_ADAPTER)pVc->pAdapt;
   BOOLEAN                 bLockReleased = FALSE;
   PCO_CALL_PARAMETERS     pCallParameters;
   NDIS_HANDLE             ProtocolVcContext;
   NDIS_STATUS             Status;

   TraceIn(AtmSmConnectPPVC);

   ASSERT(VC_TYPE_PP_OUTGOING == pVc->VcType);

   ACQUIRE_ADAPTER_GEN_LOCK(pAdapt);

   do
   {    // break off loop

      ProtocolVcContext    = (NDIS_HANDLE)pVc;

      ASSERT(ATMSM_GET_VC_STATE(pVc) != ATMSM_VC_ACTIVE);

      ASSERT(NULL == pVc->NdisVcHandle);

      if(NULL == pVc->NdisVcHandle)
      {

         Status = NdisCoCreateVc(
                     pAdapt->NdisBindingHandle,
                     pAdapt->NdisAfHandle,
                     (NDIS_HANDLE)pVc,
                     &pVc->NdisVcHandle
                     );

         if(NDIS_STATUS_SUCCESS != Status)
         {

            break;
         }

         DbgVeryLoud(("Connect: Created VC, VC %x, NdisVcHandle %x\n",
            pVc, pVc->NdisVcHandle));
      }

      ASSERT(NULL != pVc->NdisVcHandle);

      pCallParameters = AtmSmPrepareCallParameters(pAdapt, 
                           &pVc->HwAddr, 
                           TRUE,
                           FALSE);
      if(pCallParameters == (PCO_CALL_PARAMETERS)NULL)
      {

         Status = NdisCoDeleteVc(pVc->NdisVcHandle);
         pVc->NdisVcHandle = NULL;

         Status = NDIS_STATUS_RESOURCES;
         break;
      }

      ATMSM_SET_VC_STATE(pVc, ATMSM_VC_SETUP_IN_PROGRESS);

      RELEASE_ADAPTER_GEN_LOCK(pAdapt);
      bLockReleased = TRUE;

      Status = NdisClMakeCall(
                  pVc->NdisVcHandle,
                  pCallParameters,
                  NULL,
                  NULL
                  );

      if(NDIS_STATUS_PENDING != Status)
      {

         AtmSmMakeCallComplete(
            Status,
            ProtocolVcContext,
            NULL,
            pCallParameters
            );
      }

   }while(FALSE);

   if(!bLockReleased)
   {

      RELEASE_ADAPTER_GEN_LOCK(pAdapt);
   }


   TraceOut(AtmSmConnectPPVC);
}



⌨️ 快捷键说明

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