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

📄 pnp.c

📁 虚拟Scsi Disk源程序 版权归原作者
💻 C
📖 第 1 页 / 共 3 页
字号:
        Irp->IoStatus.Status = STATUS_SUCCESS;
        IoSkipCurrentIrpStackLocation (Irp);
        
        status = IoCallDriver(deviceExtension->LowerDeviceObject, Irp);

        // Adjust the active I/O count
        VScsiDiskReleaseRemoveLock(deviceExtension);

        VScsiDiskDebugPrint(DBG_PNP, DBG_TRACE, __FUNCTION__"--. IRP %p STATUS %x", Irp, status);

        return status;

   case IRP_MN_REMOVE_DEVICE:

        // The Plug & Play system has dictated the removal of this device.  We
        // have no choice but to detach and delete the device object.

        if (deviceExtension->PnpState != PnpStateSurpriseRemoved)
        {
            // flush pending io list
            VScsiDiskInvalidateIo(&deviceExtension->IoLock, STATUS_NO_SUCH_DEVICE);

            VScsiDiskFreeResources(deviceExtension);
        }

        // Update our PnP state
        deviceExtension->PnpState = PnpStateRemoved;

        VScsiDiskReleaseRemoveLock(deviceExtension);
        VScsiDiskWaitForSafeRemove(deviceExtension);

        ExAcquireFastMutex(&deviceExtension->PdoListLock);
        
        while (!IsListEmpty(&deviceExtension->PdoListHead))
        {
            listEntry = RemoveHeadList(&deviceExtension->PdoListHead);
            pdoExtension = CONTAINING_RECORD(listEntry, VSCSIDISK_PDO_DEVICE_EXTENSION, PdoListEntry);

            if (pdoExtension->PnpState == PnpStateSurpriseRemoved)
            {
                InitializeListHead(&pdoExtension->PdoListEntry);
                pdoExtension->ParentDeviceObject = NULL;
                pdoExtension->DeleteOnRemove = TRUE;
            }
            else
            {
                //*****************************************************************
                //*****************************************************************
                // TODO: Free all the resources allocated
                // for PDO
                //*****************************************************************
                //*****************************************************************
                if (pdoExtension->HardwareId != NULL)
                {
                    ExFreePool(pdoExtension->HardwareId);
                    pdoExtension->HardwareId = NULL;
                }

                IoDeleteDevice(pdoExtension->DeviceObject);
            }
        }

        ExReleaseFastMutex(&deviceExtension->PdoListLock);

        // Send the remove IRP down the stack.
        Irp->IoStatus.Status = STATUS_SUCCESS;
        IoSkipCurrentIrpStackLocation (Irp);
        status = IoCallDriver (deviceExtension->LowerDeviceObject, Irp);

        // Detach our device object from the device stack
        IoDetachDevice(deviceExtension->LowerDeviceObject);

        // free power work item
        IoFreeWorkItem(deviceExtension->PowerWorkItem);

        // attempt to delete our device object
        IoDeleteDevice(deviceExtension->DeviceObject);

        VScsiDiskDebugPrint(DBG_PNP, DBG_TRACE, __FUNCTION__"--. IRP %p STATUS %x", Irp, status);

        return status;

    case IRP_MN_QUERY_CAPABILITIES:

        // Check the device capabilities struct
        deviceCapabilities = 
            irpStack->Parameters.DeviceCapabilities.Capabilities;

        if (deviceCapabilities->Version != 1 ||
            deviceCapabilities->Size < sizeof(DEVICE_CAPABILITIES))
        {
            // We don't support this version. Fail the request
            break;
        }

        // Pass the IRP down
        status = VScsiDiskSubmitIrpSync(deviceExtension->LowerDeviceObject, Irp);

        // Lower drivers have finished their operation, so now
        // we can finish ours.
        if (NT_SUCCESS(status)) 
        {
            //*****************************************************************
            //*****************************************************************
            // TODO: Override the device capabilities 
            //       set by the underlying drivers here.
            //*****************************************************************
            //*****************************************************************
        }
		//add by zhu  2005-05-18
		deviceCapabilities->HardwareDisabled = FALSE;
		deviceCapabilities->UniqueID=FALSE;
		deviceCapabilities->Address=0;
		deviceCapabilities->UINumber=0;
		//end add by zhu
        break;

    case IRP_MN_QUERY_PNP_DEVICE_STATE:

        // Pass the IRP down because the modification to the Irp is done
        // on the way up.
        status = VScsiDiskSubmitIrpSync(deviceExtension->LowerDeviceObject, Irp);

        //*****************************************************************
        //*****************************************************************
        // TODO:  Handle any necessary state changes here.  This isn't 
        //        often necessary, but an example of what might need to 
        //        be done here would be to set the 
        //        PNP_DEVICE_DONT_DISPLAY_IN_UI bit in the PNP_DEVICE_STATE 
        //        bit field in order to hide this device in DeviceManager
        //*****************************************************************
        //*****************************************************************

        status = STATUS_SUCCESS;
        break;
    case IRP_MN_QUERY_DEVICE_RELATIONS:
        if (irpStack->Parameters.QueryDeviceRelations.Type == BusRelations)
        {
            ExAcquireFastMutex(&deviceExtension->PdoListLock);

            pdoCount = 0;
            for (listEntry = deviceExtension->PdoListHead.Flink;
                 listEntry != &deviceExtension->PdoListHead;
                 listEntry = listEntry->Flink)
            {
                pdoExtension = CONTAINING_RECORD(listEntry, VSCSIDISK_PDO_DEVICE_EXTENSION, PdoListEntry);

                if (pdoExtension->IsExist)
                {
                    ++pdoCount;
                }
            }

            oldDeviceRelations = (PDEVICE_RELATIONS)Irp->IoStatus.Information;
            if (oldDeviceRelations != NULL)
            {
                if (pdoCount == 0)
                {
                    ExReleaseFastMutex(&deviceExtension->PdoListLock);

                    IoSkipCurrentIrpStackLocation(Irp);
                    status = IoCallDriver(deviceExtension->LowerDeviceObject, Irp);

                    // Adjust our active I/O count
                    VScsiDiskReleaseRemoveLock(deviceExtension);

                    VScsiDiskDebugPrint(DBG_PNP, DBG_TRACE, __FUNCTION__"--. IRP %p STATUS %x", Irp, status);

                    return status;
                }
                else
                {
                    oldCount = oldDeviceRelations->Count;
                }
            }
            else
            {
                oldCount = 0;
            }

            newDeviceRelations = 
                (PDEVICE_RELATIONS)ExAllocatePoolWithTag(
                                    PagedPool,
                                    sizeof(DEVICE_RELATIONS) + (pdoCount + oldCount)*sizeof(PDEVICE_OBJECT),
                                    VSCSIDISK_POOL_TAG
                                    );

            if (newDeviceRelations == NULL)
            {
                ExReleaseFastMutex(&deviceExtension->PdoListLock);

                status = STATUS_INSUFFICIENT_RESOURCES;
                break;
            }

            if (oldCount != 0)
            {
                RtlCopyMemory(
                    newDeviceRelations->Objects, 
                    oldDeviceRelations->Objects, 
                    oldCount*sizeof(PDEVICE_OBJECT)
                    );
            }

            newDeviceRelations->Count = pdoCount + oldCount;

            for (listEntry = deviceExtension->PdoListHead.Flink;
                 listEntry != &deviceExtension->PdoListHead;
                 listEntry = listEntry->Flink)
            {
                pdoExtension = CONTAINING_RECORD(listEntry, VSCSIDISK_PDO_DEVICE_EXTENSION, PdoListEntry);

                if (pdoExtension->IsExist)
                {
                    newDeviceRelations->Objects[oldCount] = pdoExtension->DeviceObject;    
                    ObReferenceObject(pdoExtension->DeviceObject);
                    ++oldCount;
                }
                else
                {
                    pdoExtension->DeleteOnRemove = TRUE;
                }
            }

            if (oldDeviceRelations != NULL)
            {
                ExFreePool(oldDeviceRelations);
            }

            Irp->IoStatus.Information = (ULONG_PTR)newDeviceRelations;

            ExReleaseFastMutex(&deviceExtension->PdoListLock);

            Irp->IoStatus.Status = STATUS_SUCCESS;
            IoSkipCurrentIrpStackLocation(Irp);
            status = IoCallDriver(deviceExtension->LowerDeviceObject, Irp);

            // Adjust our active I/O count
            VScsiDiskReleaseRemoveLock(deviceExtension);

            VScsiDiskDebugPrint(DBG_PNP, DBG_TRACE, __FUNCTION__"--. IRP %p STATUS %x", Irp, status);

            return status;
        }
        else
        {
            IoSkipCurrentIrpStackLocation(Irp);
            status = IoCallDriver(deviceExtension->LowerDeviceObject, Irp);

            // Adjust our active I/O count
            VScsiDiskReleaseRemoveLock(deviceExtension);

            VScsiDiskDebugPrint(DBG_PNP, DBG_TRACE, __FUNCTION__"--. IRP %p STATUS %x", Irp, status);

            return status;
        }

        break;

    case IRP_MN_QUERY_RESOURCES:
        IoSkipCurrentIrpStackLocation(Irp);
        status = IoCallDriver(deviceExtension->LowerDeviceObject, Irp);

        // Adjust our active I/O count
        VScsiDiskReleaseRemoveLock(deviceExtension);

        VScsiDiskDebugPrint(DBG_PNP, DBG_TRACE, __FUNCTION__"--. IRP %p STATUS %x", Irp, status);

        return status;

    case IRP_MN_QUERY_RESOURCE_REQUIREMENTS:
        IoSkipCurrentIrpStackLocation(Irp);
        status = IoCallDriver(deviceExtension->LowerDeviceObject, Irp);

        // Adjust our active I/O count
        VScsiDiskReleaseRemoveLock(deviceExtension);

        VScsiDiskDebugPrint(DBG_PNP, DBG_TRACE, __FUNCTION__"--. IRP %p STATUS %x", Irp, status);

        return status;

    case IRP_MN_QUERY_DEVICE_TEXT:
/*      IoSkipCurrentIrpStackLocation(Irp);
        status = IoCallDriver(deviceExtension->LowerDeviceObject, Irp);

        // Adjust our active I/O count
        VScsiDiskReleaseRemoveLock(deviceExtension);

        VScsiDiskDebugPrint(DBG_PNP, DBG_TRACE, __FUNCTION__"--. IRP %p STATUS %x", Irp, status);

        return status;*/
		{
            PIO_STACK_LOCATION  irpStack = IoGetCurrentIrpStackLocation(Irp);
		    if(irpStack==NULL)
                break;
		    switch (irpStack->Parameters.QueryDeviceText.DeviceTextType)
		    {
		    case DeviceTextDescription:
			    if (Irp->IoStatus.Information == (ULONG_PTR)NULL)
			    {
				    PWCHAR     pInformation;
					int size = sizeof(BUS_FDO_NAME);

					pInformation = (PWCHAR)ExAllocatePoolWithTag(
                                    PagedPool,
                                    size,
                                    VSCSIDISK_POOL_TAG
                                    );

			        if (pInformation != NULL)
				    {
						RtlZeroMemory(pInformation, size);

⌨️ 快捷键说明

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