static void do_flush(device_extension* Vcb) { LIST_ENTRY rollback; InitializeListHead(&rollback); FsRtlEnterFileSystem(); ExAcquireResourceExclusiveLite(&Vcb->tree_lock, TRUE); if (Vcb->need_write) do_write(Vcb, &rollback); free_trees(Vcb); clear_rollback(&rollback); ExReleaseResourceLite(&Vcb->tree_lock); FsRtlExitFileSystem(); }
static NTSTATUS pnp_query_remove_device(PDEVICE_OBJECT DeviceObject, PIRP Irp) { device_extension* Vcb = DeviceObject->DeviceExtension; NTSTATUS Status; LIST_ENTRY rollback; ExAcquireResourceExclusiveLite(&Vcb->fcb_lock, TRUE); if (Vcb->root_fileref && Vcb->root_fileref->fcb && (Vcb->root_fileref->fcb->open_count > 0 || has_open_children(Vcb->root_fileref))) { Status = STATUS_ACCESS_DENIED; goto end; } Status = send_disks_pnp_message(Vcb, IRP_MN_QUERY_REMOVE_DEVICE); if (!NT_SUCCESS(Status)) { WARN("send_disks_pnp_message returned %08x\n", Status); goto end; } Vcb->removing = TRUE; InitializeListHead(&rollback); acquire_tree_lock(Vcb, TRUE); if (Vcb->write_trees > 0) do_write(Vcb, &rollback); clear_rollback(&rollback); release_tree_lock(Vcb, TRUE); Status = STATUS_SUCCESS; end: ExReleaseResourceLite(&Vcb->fcb_lock); return Status; }