移除设备

当要移除设备的时候,IO管理器发送IRP_MN_REMOVE_DEVICE 类型的IRP包,这是一个即插即用型的IRP包。通过调用即插即用例程来处理。

由于在Driver_Entry()函数中,将即插即用的函数和处理Pnp的MajorFunction进行了绑定,即:

pDriverObject->MajorFunction[IRP_MJ_PNP] =xxxPnp;

NTSTATUS xxxPnp(IN PDEVICE_OBJECT fdo,IN PIRP Irp)

{

         …

}

该函数前面都已经提到过,通过调用下面函数来完成:

NTSTATUS HandleRemoveDevice(PDEVICE_EXTENSION pdx, PIRP Irp)

{

         //释放分配的内存

         if(pdx->MemBar0)

                   MmUnmapIoSpace(pdx->MemBar0,pdx->nMem0);

         //设置寄存器状态

WRITE_REGISTER_ULONG((PULONG) &pdx->pHBARegs->Dma_wr_en,0x00000000);

//释放DMA资源

pdx->freeCommonBuffer()

//删除中断

IoDisconnectInterrupt(pdx->InterruptObject);

//将IRP_MN_REMOVE_DEVICE交给硬件处理

NTSTATUS status = ForwardAndWait(pdx,Irp);

//设置设备接口状态

         IoSetDeviceInterfaceState(&pdx->interfaceName, FALSE);

         //释放UNICODE字符串

         RtlFreeUnicodeString(&pdx->interfaceName);

 

         //调用IoDetachDevice()把fdo从设备栈中脱开:

         if (pdx->NextStackDevice)

                   IoDetachDevice(pdx->NextStackDevice);

 

         //删除设备对象fdo:

         IoDeleteDevice(pdx->fdo);

         //释放UNICODE字符串

//      RtlFreeUnicodeString(&pdx->devName);

         Irp->IoStatus.Status = status;

         IoCompleteRequest(Irp, IO_NO_INCREMENT);

return status

}

 

驱动需要对一些不做特殊处理的IRP包进行默认操作,对这类Pnp类型的操作可以提供一个这样的函数来处理:

NTSTATUS DefaultPnpHandler(PDEVICE_EXTENSION pdx, PIRP Irp)

{

         PAGED_CODE();

         KdPrint(("Enter DefaultPnpHandler\n"));

         IoSkipCurrentIrpStackLocation(Irp);

         KdPrint(("Leave DefaultPnpHandler\n"));

         return IoCallDriver(pdx->NextStackDevice, Irp);

}

通过IoCallDriver()直接交给PDO。

 

对于非Pnp类的操作,如IRP_MJ_CREATE、IRP_MJ_CLOSE、IRP_MJ_READ、IRP_MJ_WRITE,直接提供下面类似的默认处理函数:

NTSTATUS xxxCreate(IN PDEVICE_OBJECT fdo,IN PIRP Irp)

{

         PAGED_CODE();

         PDEVICE_EXTENSION pdx = (PDEVICE_EXTENSION) fdo->DeviceExtension;

         pdx->open_flag++;

         Irp->IoStatus.Status = STATUS_SUCCESS;

         Irp->IoStatus.Information = 0;         // no bytes xfered

         IoCompleteRequest( Irp, IO_NO_INCREMENT );

         return STATUS_SUCCESS;

}

 

 

你可能感兴趣的:(移除设备)