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

📄 hpna_2k.c

📁 HomePNA的Usb网卡驱动
💻 C
📖 第 1 页 / 共 2 页
字号:
        }

        pRcvBuf->dataLen = 0;

    }

    //
    // Free the packet and buffer pool handles for this device.
    //

    if (Device->hPacketPool)
    {
        NdisFreePacketPool(Device->hPacketPool);
        Device->hPacketPool = NULL;
    }

    if (Device->hBufferPool)
    {
        NdisFreeBufferPool(Device->hBufferPool);
        Device->hBufferPool = NULL;
    }

    if ( Device->fDeviceStarted )
    {
        ntstatus = StopDevice( Device ); 
    }

//    InterlockedExchange( &Device->fMediaBusy, FALSE ); 
//  InterlockedExchange( &Device->fIndicatedMediaBusy, FALSE ); 
    FreeWdmStuff( Device );

    return status;
}

/*****************************************************************************
*
*  Function:   MiniportHalt
*
*  Synopsis:   Deallocates resources when the NIC is removed and halts the
*              device.
*
*  Arguments:  Context - pointer to the ir device object
*
*  Returns:
*
*  Algorithm:  Mirror image of MiniportInitialize...undoes everything initialize
*              did.
*  Notes:
*
*  This routine runs at IRQL PASSIVE_LEVEL.
*
*  BUGBUG: Could MiniportReset fail and then MiniportHalt be called. If so, we need
*          to chech validity of all the pointers, etc. before trying to
*          deallocate.
*
*****************************************************************************/

VOID
MiniportHalt(
            IN NDIS_HANDLE Context
            )
{
    PUSB_DEVICE device;

    NTSTATUS ntstatus;

    device = CONTEXT_TO_DEV(Context);


    if ( TRUE == device->fPendingHalt ) {

        goto done;
    }

    //
    // Let the send completion and receive completion routine know that there
    // is a pending reset.
    //

    device->fPendingHalt = TRUE;

    UsbCommonShutdown( device );  //shutdown logic common to halt and reset; see below

    // We had better not have left any pending read, write, or control IRPS hanging out there!

    ASSERT( 0 == device->PendingIrpCount );

    ASSERT( FALSE == device->fSetpending );

    ASSERT( FALSE == device->fQuerypending );

    //
    // Free our own hpna device object.
    //

    MemFree(device, sizeof(USB_DEVICE));

done:


    return;
}

/*****************************************************************************
*
*  Function:   UsbCommonShutdown
*
*  Synopsis:   Deallocates resources when the NIC is removed and halts the
*              device. This is stuff common to USBHalt and USBReset and is called by both
*
*  Arguments:  device USB_DEVICE
*
*  Returns:
*
*  Algorithm:  Mirror image of USBInitialize...undoes everything initialize
*              did.
*
*  Notes:
*
*  This routine runs at IRQL PASSIVE_LEVEL.
*
*
*****************************************************************************/

VOID
UsbCommonShutdown(
            IN PUSB_DEVICE Device
            )
{

    NTSTATUS ntStatus;

   //
    // Sleep 50 milliseconds so pending io might finish normally
    //

    NdisMSleep(50000);    //


    // We want to wait until all pending receives and sends to the
    // device object. We cancel any
    // irps. Wait until sends and receives have stopped.
    //
    CancelPendingIo( Device );



    Device->fKillPassiveLevelThread = TRUE;

    KeSetEvent(&Device->EventPassiveThread, 0, FALSE);
    DbgPrint("halt!");
    while (Device->hPassiveThread != NULL)
    {
        //
        // Sleep 50 milliseconds.
        //

        NdisMSleep(50000);
    }


    Device->fKillPollingThread = TRUE;


    //ASSERT( NT_SUCCESS( ntstatus ) );

    while (Device->hPollingThread != NULL)
    {
        //
        // Sleep 50 milliseconds.
        //

        NdisMSleep(50000);
    }

    //
    // Deinitialize our own ir device object.
    //

    DeinitializeDevice(Device);


    Device->fDeviceStarted= FALSE;

    Device->NumDataErrors = 0;  //reset data error count


    return;
}
/*****************************************************************************
*
*  Function:   MiniportReset
*
*  Synopsis:   Resets the drivers software state.
*
*  Arguments:  AddressingReset - return arg. If set to TRUE, NDIS will call
*                                MiniportSetInformation to restore addressing
*                                information to the current values.
*              Context         - pointer to ir device object
*
*  Returns:    NDIS_STATUS_PENDING
*
*
*  Notes:
*
*
*****************************************************************************/

NDIS_STATUS
MiniportReset(
            OUT PBOOLEAN    AddressingReset,
            IN  NDIS_HANDLE MiniportAdapterContext
            )
{
    PUSB_DEVICE  device;
    NDIS_STATUS status = NDIS_STATUS_PENDING;
    NDIS_PHYSICAL_ADDRESS noMaxAddr = NDIS_PHYSICAL_ADDRESS_CONST(-1,-1);


    device = CONTEXT_TO_DEV(MiniportAdapterContext);

    if ( TRUE == device->fPendingReset ) {

        status = NDIS_STATUS_RESET_IN_PROGRESS ;
        goto done;
    }

    //
    // Let the send completion and receive completion routine know that there
    // is a pending reset.
    //

    device->fPendingReset = TRUE;

    *AddressingReset = TRUE;


     if ( FALSE == ScheduleWorkItem( device,
         ResetUsbDevice, NULL, 0)){
          status = NDIS_STATUS_FAILURE;
     }
 done:

    return status;
}

/*****************************************************************************
*
*  Function:   ResetUsbDevice
*
*  Synopsis: Callback for MiniportReset
*
*  Arguments:
*
*  Returns:
*
*
*  Notes:
*
*  The following elements of the ir device object outlast the reset:
*
*
*      pUsbDevObj
*
*      hNdisAdapter
*
*****************************************************************************/

VOID
ResetUsbDevice(
    IN PUSB_WORK_ITEM  pWorkItem
)

{
    NDIS_STATUS         status = NDIS_STATUS_FAILURE;

    PUSB_DEVICE device = (PUSB_DEVICE) pWorkItem->pDevice;

    FreeWorkItem(pWorkItem);

    UsbCommonShutdown( device );  //shutdown logic common to halt and reset; see above

    status = InitializeDevice(device);  //this MUST succeed

    if (status != NDIS_STATUS_SUCCESS)
    {
        status = NDIS_STATUS_FAILURE;

        goto done;
    }

    //
    // Initialize receive loop.
    //

    status = InitializeReceive(device);

    if (status != NDIS_STATUS_SUCCESS)
    {
        status = NDIS_STATUS_FAILURE;

        goto done;
    }

    if (status != STATUS_SUCCESS)
    {
        NdisWriteErrorLogEntry(device->hNdisAdapter,
                               NDIS_ERROR_CODE_ADAPTER_NOT_FOUND,
                               1,
                               status);
        status = NDIS_STATUS_HARD_ERRORS;
        goto done;
    }


done:
    NdisMResetComplete(
            device->hNdisAdapter,
            (NDIS_STATUS)status,
            TRUE
            );

    device->fPendingReset         = FALSE;


}

/*****************************************************************************
*
*  Function:   MiniportSend
*
*  Synopsis:   Send a packet to the USB driver and add the sent irp and io context to
*              To the pending send queue; this que is really just needed for possible later error cancellation
*
*
*  Arguments:  MiniportAdapterContext - pointer to current ir device object
*              pPacketToSend          - pointer to packet to send
*              Flags                  - any flags set by protocol
*
*  Returns:    NDIS_STATUS_PENDING - This is generally what we should
*                                    return. We will call NdisMSendComplete
*                                    when the USB driver completes the
*                                    send.
*              STATUS_UNSUCCESSFUL - The packet was invalid.
*
*  Unsupported returns:
*              NDIS_STATUS_SUCCESS  - We should never return this since
*                                     results will always be pending from
*                                     the USB driver.
*              NDIS_STATUS_RESOURCES-This indicates to the protocol that the
*                                    device currently has no resources to complete
*                                    the request. The protocol will resend
*                                    the request when it receives either
*                                    NdisMSendResourcesAvailable or
*                                    NdisMSendComplete from the device.
*
*    Notes: This routine delegates all the real work to SendPacket in rwir.c
*
*
*****************************************************************************/

NDIS_STATUS
MiniportSend(
           IN NDIS_HANDLE  MiniportAdapterContext,//就是初始化时用SetAttributEx的USB_DEVICE device
           IN PNDIS_PACKET pPacketToSend,
           IN UINT         Flags
           )
{
    NDIS_STATUS status;
    //PNDIS_USB_PACKET_INFO packetInfo; 
    PUSB_DEVICE device = ( PUSB_DEVICE ) MiniportAdapterContext;

	if (  device->RcvBuffersInUse >= (NUM_RCV_BUFS -2)  )
	{
        //
        // fail the packet until we're caught up
        status = NDIS_STATUS_FAILURE;
        goto done;
    }
    //如果端点为Stall状态
    if( TRUE == device->fPendingWriteClearStall ) {

        status = NDIS_STATUS_FAILURE;
        goto done;
    }

    //packetInfo = GetPacketInfo(pPacketToSend); 

    status =  ( NDIS_STATUS ) SendPacket(
                device,
                pPacketToSend,
                Flags,
                CONTEXT_NDIS_PACKET
                );
done:

    return status;
}


/*
PNDIS_USB_PACKET_INFO   oob
GetPacketInfo(
    PNDIS_PACKET packet
)
{
    MEDIA_SPECIFIC_INFORMATION *mediaInfo;
    UINT size;
    NDIS_GET_PACKET_MEDIA_SPECIFIC_INFO(packet, &mediaInfo, &size);
    return (PNDIS_USB_PACKET_INFO)mediaInfo->ClassInformation;
}
*/

//indicate RcvBuffer is full
VOID
IndicateMediaBusy(
       IN PUSB_DEVICE Device
    )
{

    NdisMIndicateStatus(
       Device->hNdisAdapter,
       NDIS_STATUS_MEDIA_BUSY,
       NULL,
       0
       );

    NdisMIndicateStatusComplete(
       Device->hNdisAdapter,
       );

}








/*****************************************************************************
*
*  Function:   MemAlloc
*
*  Synopsis:   allocates a block of memory using NdisAllocateMemory
*
*  Arguments:  size - size of the block to allocate
*
*  Returns:    a pointer to the allocated block of memory
*
*
*****************************************************************************/
PVOID MemAlloc(UINT size)
{
    PVOID                 memptr;
    NDIS_PHYSICAL_ADDRESS noMaxAddr = NDIS_PHYSICAL_ADDRESS_CONST(-1,-1);
    NDIS_STATUS           status;


    status = NdisAllocateMemoryWithTag(&memptr, size, USB_TAG);

    if (status != NDIS_STATUS_SUCCESS)
    {
        memptr = NULL;
    }


    return memptr;
}

/*****************************************************************************
*
*  Function:   MemFree
*
*  Synopsis:   frees a block of memory allocated by MemAlloc
*
*  Arguments:  memptr - memory to free
*              size   - size of the block to free
*
*
*****************************************************************************/

VOID
MemFree(
            PVOID memptr,
            UINT size
            )
{

    NdisFreeMemory(memptr, size, 0);

}

⌨️ 快捷键说明

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