static void usbd_irpcancel(device_object *dobj, irp *ip) { device_t dev = IRP_NDIS_DEV(ip); struct ndis_softc *sc = device_get_softc(dev); struct ndisusb_ep *ne = IRP_NDISUSB_EP(ip); if (ne == NULL) { ip->irp_cancel = TRUE; IoReleaseCancelSpinLock(ip->irp_cancelirql); return; } /* * Make sure that the current USB transfer proxy is * cancelled and then restarted. */ NDISUSB_LOCK(sc); usbd_transfer_stop(ne->ne_xfer[0]); usbd_transfer_start(ne->ne_xfer[0]); NDISUSB_UNLOCK(sc); ip->irp_cancel = TRUE; IoReleaseCancelSpinLock(ip->irp_cancelirql); }
VOID NTAPI BeepCancel(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp) { /* Check if this is the current request */ if (Irp == DeviceObject->CurrentIrp) { /* Clear it */ DeviceObject->CurrentIrp = NULL; /* Release the cancel lock and start the next packet */ IoReleaseCancelSpinLock(Irp->CancelIrql); IoStartNextPacket(DeviceObject, TRUE); } else { /* Otherwise, remove the packet from the queue and relelase the lock */ KeRemoveEntryDeviceQueue(&DeviceObject->DeviceQueue, &Irp->Tail.Overlay.DeviceQueueEntry); IoReleaseCancelSpinLock(Irp->CancelIrql); } /* Complete the request */ Irp->IoStatus.Status = STATUS_CANCELLED; Irp->IoStatus.Information = 0; IoCompleteRequest (Irp, IO_NO_INCREMENT); }
static PNPFS_CCB NpfsFindListeningServerInstance(PNPFS_FCB Fcb) { PLIST_ENTRY CurrentEntry; PNPFS_WAITER_ENTRY Waiter; KIRQL oldIrql; PIRP Irp; CurrentEntry = Fcb->WaiterListHead.Flink; while (CurrentEntry != &Fcb->WaiterListHead) { Waiter = CONTAINING_RECORD(CurrentEntry, NPFS_WAITER_ENTRY, Entry); Irp = CONTAINING_RECORD(Waiter, IRP, Tail.Overlay.DriverContext); if (Waiter->Ccb->PipeState == FILE_PIPE_LISTENING_STATE) { DPRINT("Server found! CCB %p\n", Waiter->Ccb); IoAcquireCancelSpinLock(&oldIrql); if (!Irp->Cancel) { if (IoSetCancelRoutine(Irp, NULL) != NULL) { IoReleaseCancelSpinLock(oldIrql); return Waiter->Ccb; } } IoReleaseCancelSpinLock(oldIrql); } CurrentEntry = CurrentEntry->Flink; } return NULL; }
NTSTATUS NTAPI BeepCleanup(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp) { KIRQL OldIrql, CancelIrql; PKDEVICE_QUEUE_ENTRY Packet; PIRP CurrentIrp; /* Raise IRQL and acquire the cancel lock */ KeRaiseIrql(DISPATCH_LEVEL, &OldIrql); IoAcquireCancelSpinLock(&CancelIrql); /* Get the current IRP */ CurrentIrp = DeviceObject->CurrentIrp; DeviceObject->CurrentIrp = NULL; while (CurrentIrp) { /* Clear its cancel routine */ (VOID)IoSetCancelRoutine(CurrentIrp, NULL); /* Cancel the IRP */ CurrentIrp->IoStatus.Status = STATUS_CANCELLED; CurrentIrp->IoStatus.Information = 0; /* Release the cancel lock and complete it */ IoReleaseCancelSpinLock(CancelIrql); IoCompleteRequest(CurrentIrp, IO_NO_INCREMENT); /* Reacquire the lock and get the next queue packet */ IoAcquireCancelSpinLock(&CancelIrql); Packet = KeRemoveDeviceQueue(&DeviceObject->DeviceQueue); if (Packet) { /* Get the IRP */ CurrentIrp = CONTAINING_RECORD(Packet, IRP, Tail.Overlay.DeviceQueueEntry); } else { /* No more IRPs */ CurrentIrp = NULL; } } /* Release lock and go back to low IRQL */ IoReleaseCancelSpinLock(CancelIrql); KeLowerIrql(OldIrql); /* Complete the IRP */ Irp->IoStatus.Status = STATUS_SUCCESS; Irp->IoStatus.Information = 0; IoCompleteRequest(Irp, IO_NO_INCREMENT); /* Stop and beep and return */ HalMakeBeep(0); return STATUS_SUCCESS; }
NTSTATUS Notification_Recieve(NOTIFICATION_QUEUE *queue, PIRP irp) { PIO_STACK_LOCATION irpstack = IoGetCurrentIrpStackLocation(irp); KIRQL irq; if(irpstack->Parameters.DeviceIoControl.OutputBufferLength != sizeof(PGNOTIFICATION)) { irp->IoStatus.Status = STATUS_BUFFER_TOO_SMALL; irp->IoStatus.Information = 0; IoCompleteRequest(irp, IO_NO_INCREMENT); return STATUS_BUFFER_TOO_SMALL; } KeAcquireSpinLock(&queue->lock, &irq); if(IsListEmpty(&queue->notification_list)) { PGIRPNODE *irpnode; KIRQL crirq; irpnode = ExAllocateFromNPagedLookasideList(&queue->lookaside); InitializeListHead(&irpnode->entry); irpnode->irp = irp; //irp->Tail.Overlay.DriverContext[0] = irpnode; InsertTailList(&queue->irp_list, &irpnode->entry); IoMarkIrpPending(irp); IoAcquireCancelSpinLock(&crirq); #pragma warning(push) #pragma warning(disable:4311 4312) //IoSetCancelRoutine generates warnings in 32-bit due to silly macroisms. IoSetCancelRoutine(irp, Notification_OnCancel); #pragma warning(pop) IoReleaseCancelSpinLock(crirq); KeReleaseSpinLock(&queue->lock, irq); return STATUS_PENDING; } else { PGNOTIFYNODE *notifynode = (PGNOTIFYNODE*)RemoveHeadList(&queue->notification_list); PGNOTIFICATION *notification = irp->AssociatedIrp.SystemBuffer; RtlCopyMemory(notification, ¬ifynode->notification, sizeof(PGNOTIFICATION)); ExFreeToNPagedLookasideList(&queue->lookaside, notifynode); --queue->queued; KeReleaseSpinLock(&queue->lock, irq); irp->IoStatus.Status = STATUS_SUCCESS; irp->IoStatus.Information = sizeof(PGNOTIFICATION); IoCompleteRequest(irp, IO_NO_INCREMENT); return STATUS_SUCCESS; } }
VOID ParCancel( IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp ) /*++ Routine Description: This is the cancel routine for this driver. Arguments: DeviceObject - Supplies the device object. Irp - Supplies the I/O request packet. Return Value: None. --*/ { RemoveEntryList(&Irp->Tail.Overlay.ListEntry); IoReleaseCancelSpinLock(Irp->CancelIrql); Irp->IoStatus.Information = 0; Irp->IoStatus.Status = STATUS_CANCELLED; IoCompleteRequest(Irp, IO_NO_INCREMENT); }
/////////////////////////////////////////////////////////////////////////////////////////////////// // testdrvQueueCancelRoutine // Cancel routine used for queue IRPs while in the queue // // Arguments: // IN DeviceObject // Device object for our device // // IN Irp // IRP to be cancelled // // Return Value: // none // VOID testdrvQueueCancelRoutine( IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp ) { KIRQL oldIrql; PTESTDRV_QUEUE queue; // release the system cancel spinlock oldIrql = Irp->CancelIrql; IoReleaseCancelSpinLock(DISPATCH_LEVEL); // get our queue from the IRP queue = (PTESTDRV_QUEUE)Irp->Tail.Overlay.DriverContext[0]; ASSERT(queue != NULL); // grab the queue protection KeAcquireSpinLockAtDpcLevel(&queue->QueueLock); // remove our IRP from the queue RemoveEntryList(&Irp->Tail.Overlay.ListEntry); // drop the queue protection KeReleaseSpinLock(&queue->QueueLock, oldIrql); // cancel the IRP Irp->IoStatus.Status = STATUS_CANCELLED; Irp->IoStatus.Information = 0; IoCompleteRequest(Irp, IO_NO_INCREMENT); return; }
/////////////////////////////////////////////////////////////////////////////////////////////////// // testdrvListCancelRoutine // Cancel routine used for our cancel safe IRP list // // Arguments: // IN DeviceObject // Device object for our device // // IN Irp // IRP to be cancelled // // Return Value: // none // VOID testdrvListCancelRoutine( IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp ) { KIRQL oldIrql; PTESTDRV_LIST list; oldIrql = Irp->CancelIrql; // release the system cancel spinlock IoReleaseCancelSpinLock(DISPATCH_LEVEL); // get our list context from the IRP list = (PTESTDRV_LIST)Irp->Tail.Overlay.DriverContext[0]; // grab the list protection KeAcquireSpinLockAtDpcLevel(&list->ListLock); // remove our IRP from the list RemoveEntryList(&Irp->Tail.Overlay.ListEntry); // drop the list protection KeReleaseSpinLock(&list->ListLock, oldIrql); // cancel the IRP Irp->IoStatus.Status = STATUS_CANCELLED; Irp->IoStatus.Information = 0; IoCompleteRequest(Irp, IO_NO_INCREMENT); return; }
/* * @implemented */ VOID MountMgrNotify(IN PDEVICE_EXTENSION DeviceExtension) { PIRP Irp; KIRQL OldIrql; LIST_ENTRY CopyList; PLIST_ENTRY NextEntry; /* Increase the epic number */ DeviceExtension->EpicNumber++; InitializeListHead(&CopyList); /* Copy all the pending IRPs for notification */ IoAcquireCancelSpinLock(&OldIrql); while (!IsListEmpty(&(DeviceExtension->IrpListHead))) { NextEntry = RemoveHeadList(&(DeviceExtension->IrpListHead)); Irp = CONTAINING_RECORD(NextEntry, IRP, Tail.Overlay.ListEntry); InsertTailList(&CopyList, &(Irp->Tail.Overlay.ListEntry)); } IoReleaseCancelSpinLock(OldIrql); /* Then, notifiy them one by one */ while (!IsListEmpty(&CopyList)) { NextEntry = RemoveHeadList(&CopyList); Irp = CONTAINING_RECORD(NextEntry, IRP, Tail.Overlay.ListEntry); *((PULONG)Irp->AssociatedIrp.SystemBuffer) = DeviceExtension->EpicNumber; Irp->IoStatus.Information = sizeof(DeviceExtension->EpicNumber); IoCompleteRequest(Irp, IO_NO_INCREMENT); } }
static VOID NTAPI IopCsqCancelRoutine( _Inout_ PDEVICE_OBJECT DeviceObject, _Inout_ _IRQL_uses_cancel_ PIRP Irp) { PIO_CSQ Csq; KIRQL Irql; /* First things first: */ IoReleaseCancelSpinLock(Irp->CancelIrql); /* We could either get a context or just a csq */ Csq = (PIO_CSQ)Irp->Tail.Overlay.DriverContext[3]; if(Csq->Type == IO_TYPE_CSQ_IRP_CONTEXT) { PIO_CSQ_IRP_CONTEXT Context = (PIO_CSQ_IRP_CONTEXT)Csq; Csq = Context->Csq; /* clean up context while we're here */ Context->Irp = NULL; } /* Now that we have our CSQ, complete the IRP */ Csq->CsqAcquireLock(Csq, &Irql); Csq->CsqRemoveIrp(Csq, Irp); Csq->CsqReleaseLock(Csq, Irql); Csq->CsqCompleteCanceledIrp(Csq, Irp); }
VOID Ik220FilterCancelQueued(IN PDEVICE_OBJECT PDevObj, IN PIRP PIrp) /*++ Routine Description: This routine will be used cancel irps on the stalled queue. Arguments: PDevObj - Pointer to the device object. PIrp - Pointer to the Irp to cancel Return Value: None. --*/ { PIK220_DEVICE_EXTENSION pDevExt = PDevObj->DeviceExtension; PIO_STACK_LOCATION pIrpSp = IoGetCurrentIrpStackLocation(PIrp); PIrp->IoStatus.Status = STATUS_CANCELLED; PIrp->IoStatus.Information = 0; RemoveEntryList(&PIrp->Tail.Overlay.ListEntry); IoReleaseCancelSpinLock(PIrp->CancelIrql); }
static void Notification_OnCancel(PDEVICE_OBJECT device, PIRP irp) { KIRQL irq; NOTIFICATION_QUEUE *queue = &((PBINTERNAL*)device->DeviceExtension)->queue; LIST_ENTRY *iter; int found = 0; DbgPrint("pbfilter: Canceling IRP...\n"); KeAcquireSpinLock(&queue->lock, &irq); for(iter = queue->irp_list.Flink; iter != &queue->irp_list; iter = iter->Flink) { PBIRPNODE *irpnode = (PBIRPNODE*)iter; if(irpnode->irp == irp) { RemoveEntryList(iter); ExFreeToNPagedLookasideList(&queue->lookaside, irpnode); found = 1; break; } } KeReleaseSpinLock(&queue->lock, irq); // if it wasn't found, it has already been dequeued and handled. if(found) { DbgPrint("pbfilter: IRP found, completing.\n"); irp->IoStatus.Status = STATUS_CANCELLED; irp->IoStatus.Information = 0; IoCompleteRequest(irp, IO_NO_INCREMENT); } IoReleaseCancelSpinLock(irp->CancelIrql); }
VOID NTAPI CancelQueued(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp) { PDEVICE_EXTENSION deviceExtension; KIRQL oldIrql; FreeBT_DbgPrint(3, ("FBTUSB: CancelQueued: Entered\n")); deviceExtension = (PDEVICE_EXTENSION) DeviceObject->DeviceExtension; oldIrql = Irp->CancelIrql; // Release the cancel spin lock IoReleaseCancelSpinLock(Irp->CancelIrql); // Acquire the queue lock KeAcquireSpinLockAtDpcLevel(&deviceExtension->QueueLock); // Remove the cancelled Irp from queue and release the lock RemoveEntryList(&Irp->Tail.Overlay.ListEntry); KeReleaseSpinLock(&deviceExtension->QueueLock, oldIrql); // complete with STATUS_CANCELLED Irp->IoStatus.Status = STATUS_CANCELLED; Irp->IoStatus.Information = 0; IoCompleteRequest(Irp, IO_NO_INCREMENT); FreeBT_DbgPrint(3, ("FBTUSB: CancelQueued: Leaving\n")); return; }
VOID Bus_CancelIrp(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp) { PPDO_DEVICE_DATA pdoData = (PPDO_DEVICE_DATA) DeviceObject->DeviceExtension; PLIST_ENTRY le = NULL; PIRP cancelIrp = NULL; KIRQL irql; Bus_KdPrint(("Bus_CancelIrp : %p", Irp)); IoReleaseCancelSpinLock(Irp->CancelIrql); KeAcquireSpinLock(&pdoData->PendingQueueLock, &irql); for (le = pdoData->PendingQueue.Flink; le != &pdoData->PendingQueue; le = le->Flink) { PPENDING_IRP lr = CONTAINING_RECORD(le, PENDING_IRP, Link); cancelIrp = lr->Irp; if (cancelIrp->Cancel && cancelIrp == Irp) { Bus_KdPrint(("PendingQueue : %p", cancelIrp)); RemoveEntryList(le); break; } cancelIrp = NULL; } if (cancelIrp == NULL) { for (le = pdoData->HoldingQueue.Flink; le != &pdoData->HoldingQueue; le = le->Flink) { PPENDING_IRP lr = CONTAINING_RECORD(le, PENDING_IRP, Link); cancelIrp = lr->Irp; if (cancelIrp->Cancel && cancelIrp == Irp) { Bus_KdPrint(("HoldingQueue : %p", cancelIrp)); RemoveEntryList(le); break; } cancelIrp = NULL; } } KeReleaseSpinLock(&pdoData->PendingQueueLock, irql); if (cancelIrp) { cancelIrp->IoStatus.Status = STATUS_CANCELLED; cancelIrp->IoStatus.Information = 0; IoCompleteRequest(cancelIrp, IO_NO_INCREMENT); } }
static NTAPI void manager_irp_cancel( PDEVICE_OBJECT DeviceObject, PIRP Irp) { co_manager_t *manager; co_manager_open_desc_t opened = NULL; bool_t myIRP = PFALSE; fixme_IoSetCancelRoutine(Irp, NULL); manager = (co_manager_t *)DeviceObject->DeviceExtension; if (manager) { opened = (typeof(opened))(Irp->Tail.Overlay.DriverContext[0]); if (opened) { myIRP = opened->os->irp == Irp; opened->os->irp = NULL; } } Irp->IoStatus.Status = STATUS_CANCELLED; Irp->IoStatus.Information = 0; IoReleaseCancelSpinLock(Irp->CancelIrql); IoCompleteRequest(Irp, IO_NO_INCREMENT); if (myIRP) { co_manager_close(manager, opened); } }
static VOID NTAPI ReadIrpCancel(PDEVICE_OBJECT DeviceObject, PIRP Irp) { PIO_STACK_LOCATION IrpSp = IoGetCurrentIrpStackLocation(Irp); PNDISUIO_ADAPTER_CONTEXT AdapterContext = IrpSp->FileObject->FsContext; PNDISUIO_PACKET_ENTRY PacketEntry; /* Release the cancel spin lock */ IoReleaseCancelSpinLock(Irp->CancelIrql); /* Indicate a 0-byte packet on the queue to cancel the read */ PacketEntry = ExAllocatePool(NonPagedPool, sizeof(NDISUIO_PACKET_ENTRY)); if (PacketEntry) { PacketEntry->PacketLength = 0; ExInterlockedInsertHeadList(&AdapterContext->PacketList, &PacketEntry->ListEntry, &AdapterContext->Spinlock); KeSetEvent(&AdapterContext->PacketReadEvent, IO_NO_INCREMENT, FALSE); } }
/*! * \brief Cancel routine for RDF_CARD_TRACKING.<br> * <br> * \param [in] pDeviceObject Caller-supplied pointer to a DEVICE_OBJECT structure. This is the device object for the target device, previously created by the driver's AddDevice routine. * \param [in] pIrp Caller-supplied pointer to an IRP structure that describes the I/O operation to be canceled. * * \retval STATUS_CANCELLED */ NTSTATUS VR_RDF_Cancel(IN PDEVICE_OBJECT pDeviceObject, IN PIRP pIrp) { dbg_log("VR_RDF_Cancel start"); PDEVICE_EXTENSION pDeviceExtension = (PDEVICE_EXTENSION)pDeviceObject->DeviceExtension; PSMARTCARD_EXTENSION pSmartcardExtension = &pDeviceExtension->smartcardExtension; // The reader driver must complete the request as soon as it detects that a smart // card has been inserted or removed. The reader driver completes the request by // calling IoCompleteRequest, after which, the reader driver must set the NotificationIrp // member of SmartcardExtension -> OsData back to NULL to inform the driver library // that the reader driver can accept further smart card tracking requests. // http://msdn2.microsoft.com/en-us/library/ms801317.aspx pSmartcardExtension->OsData->NotificationIrp = NULL; pIrp->IoStatus.Information = 0; pIrp->IoStatus.Status = STATUS_CANCELLED; // The I/O manager calls IoAcquireCancelSpinLock before calling a driver's Cancel routine, // so the Cancel routine must call IoReleaseCancelSpinLock at some point. // The routine should not hold the spin lock longer than necessary. // http://msdn2.microsoft.com/en-us/library/ms795319.aspx IoReleaseCancelSpinLock(pIrp->CancelIrql); IoCompleteRequest(pIrp, IO_NO_INCREMENT); // The Cancel routine must set the I/O status block's Status member to STATUS_CANCELLED, // and set its Information member to zero. The routine must then complete the specified // IRP by calling IoCompleteRequest. dbg_log("VR_RDF_Cancel end - status: 0x%08X", STATUS_CANCELLED); return STATUS_CANCELLED; }
PIRP SoundRemoveFromCancellableQ( PLIST_ENTRY QueueHead ) /*++ Routine Description: Remove the Irp to the queue and remove the cancel routine under the protection of the cancel spin lock. Arguments: QueueHead - the queue to remove it from Return Value: The Irp at the head of the queue or NULL if the queue is empty. --*/ { KIRQL OldIrql; PIRP Irp; LIST_ENTRY ListNode; // // Get the cancel spin lock so we can mess with the cancel stuff // IoAcquireCancelSpinLock(&OldIrql); if (IsListEmpty(QueueHead)) { Irp = NULL; } else { PLIST_ENTRY ListNode; ListNode = RemoveHeadList(QueueHead); Irp = CONTAINING_RECORD(ListNode, IRP, Tail.Overlay.ListEntry); // // Remove the cancel routine // IoSetCancelRoutine(Irp, NULL); } // // Free the spin lock // IoReleaseCancelSpinLock(OldIrql); // // Return IRP (if any) // return Irp; }
NTSTATUS DispPrepareIrpForCancel( PTRANSPORT_CONTEXT Context, PIRP Irp, PDRIVER_CANCEL CancelRoutine) /* * FUNCTION: Prepare an IRP for cancellation * ARGUMENTS: * Context = Pointer to context information * Irp = Pointer to an I/O request packet * CancelRoutine = Routine to be called when I/O request is cancelled * RETURNS: * Status of operation */ { KIRQL OldIrql; PIO_STACK_LOCATION IrpSp; PTRANSPORT_CONTEXT TransContext; TI_DbgPrint(DEBUG_IRP, ("Called.\n")); IrpSp = IoGetCurrentIrpStackLocation(Irp); TransContext = (PTRANSPORT_CONTEXT)IrpSp->FileObject->FsContext; IoAcquireCancelSpinLock(&OldIrql); if (!Irp->Cancel && !TransContext->CancelIrps) { (void)IoSetCancelRoutine(Irp, CancelRoutine); IoReleaseCancelSpinLock(OldIrql); TI_DbgPrint(DEBUG_IRP, ("Leaving (IRP at 0x%X can now be cancelled).\n", Irp)); return STATUS_SUCCESS; } /* IRP has already been cancelled */ IoReleaseCancelSpinLock(OldIrql); Irp->IoStatus.Status = STATUS_CANCELLED; Irp->IoStatus.Information = 0; TI_DbgPrint(DEBUG_IRP, ("Leaving (IRP was already cancelled).\n")); return Irp->IoStatus.Status; }
VOID NTAPI USBSTOR_Cancel( IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp) { PFDO_DEVICE_EXTENSION FDODeviceExtension; // // get FDO device extension // FDODeviceExtension = (PFDO_DEVICE_EXTENSION)DeviceObject->DeviceExtension; // // sanity check // ASSERT(KeGetCurrentIrql() == DISPATCH_LEVEL); ASSERT(FDODeviceExtension->Common.IsFDO); // // acquire irp list lock // KeAcquireSpinLockAtDpcLevel(&FDODeviceExtension->IrpListLock); // // remove the irp from the list // RemoveEntryList(&Irp->Tail.Overlay.ListEntry); // // release irp list lock // KeReleaseSpinLockFromDpcLevel(&FDODeviceExtension->IrpListLock); // // now release the cancel lock // IoReleaseCancelSpinLock(Irp->CancelIrql); // // set cancel status // Irp->IoStatus.Status = STATUS_CANCELLED; // // now cancel the irp // USBSTOR_QueueTerminateRequest(DeviceObject, Irp); IoCompleteRequest(Irp, IO_NO_INCREMENT); // // start the next one // USBSTOR_QueueNextRequest(DeviceObject); }
void ssh_interceptor_iodevice_cancel_queued_ioctl(PDEVICE_OBJECT device, PIRP irp) { SshInterceptorIoDevice io_dev; SshIoctlCancelFunction cancel_fn = NULL_FNPTR; void *cancel_context; SshIoctlCancelID cancel_id; Boolean cancelled = FALSE; PLIST_ENTRY entry; /* Cancel processing is protected by queue-specific lock, not by the (one and only) system-wide Cancel lock */ IoReleaseCancelSpinLock(irp->CancelIrql); io_dev = SSH_NTDEV_TO_SSHDEV(device); NdisAcquireSpinLock(&io_dev->ioctl_req_list_lock); entry = io_dev->active_ioctl_req_list.Flink; while (entry != &io_dev->active_ioctl_req_list) { SshIoDeviceIoctlRequest ioctl; SshIoDeviceIoctlHandler handler; ioctl = CONTAINING_RECORD(entry, SshIoDeviceIoctlRequestStruct, private_data.link); if (ioctl->private_data.irp == irp) { handler = ioctl->public_data.context; cancel_fn = handler->cancel_fn; cancel_context = handler->context; cancel_id = ioctl->public_data.cancel_id; break; } entry = entry->Flink; } NdisReleaseSpinLock(&io_dev->ioctl_req_list_lock); if (cancel_fn != NULL_FNPTR) { cancelled = (*cancel_fn)(cancel_context, cancel_id); } if (cancelled == FALSE) { /* We have a bug somewhere if we end up here */ SSH_NOTREACHED; } }
/* Cancel routine for queued read operations initiated by user-mode daemons. */ void ssh_interceptor_iodevice_cancel_queued_read(PDEVICE_OBJECT device, PIRP irp) { SshInterceptorIoDevice io_dev; PLIST_ENTRY entry, next_entry; LIST_ENTRY cancelled_irps; /* Cancel processing is protected by queue-specific lock, not by the (one and only) system-wide Cancel lock */ IoReleaseCancelSpinLock(irp->CancelIrql); io_dev = SSH_NTDEV_TO_SSHDEV(device); NdisInitializeListHead(&cancelled_irps); SSH_DEBUG(SSH_D_MIDSTART, ("ssh_interceptor_iodevice_cancel_queued_read()")); /* Find and dequeue all canceled IRPs (not just the one given as argument). Complete the IRPs after releasing the spin lock. */ NdisAcquireSpinLock(&io_dev->read_queue_lock); entry = io_dev->read_queue.Flink; while (entry && (entry != &io_dev->read_queue)) { next_entry = entry->Flink; irp = CONTAINING_RECORD(entry, IRP, Tail.Overlay.ListEntry); if (irp->Cancel) { RemoveEntryList(entry); InsertTailList(&cancelled_irps, entry); } entry = next_entry; } NdisReleaseSpinLock(&io_dev->read_queue_lock); while (!IsListEmpty(&cancelled_irps)) { entry = RemoveHeadList(&cancelled_irps); irp = CONTAINING_RECORD(entry, IRP, Tail.Overlay.ListEntry); irp->IoStatus.Status = STATUS_CANCELLED; irp->IoStatus.Information = 0; IoCompleteRequest(irp, IO_NO_INCREMENT); SSH_DEBUG(SSH_D_NICETOKNOW, ("IoCompleteRequest(irp = 0x%p, status = STATUS_CANCELLED)", irp)); }; }
VOID SoundRemoveAndComplete( PDEVICE_OBJECT pDO, PIRP Irp ) /*++ Routine Description: Removes the Irp from any queue it's on Completes it as cancelled. Arguments: Irp - the Irp Cancellable - If it is to be made cancellable Return Value: None. Notes: This routine is called with the cancel spin lock held --*/ { dprintf2(("Cancelling Irp from cancel routine")); // // Remove the Irp from the queue // RemoveEntryList(&Irp->Tail.Overlay.ListEntry); // // Release the cancel spin lock // IoReleaseCancelSpinLock(Irp->CancelIrql); // // Set status and complete // Irp->IoStatus.Status = STATUS_CANCELLED; IoCompleteRequest(Irp, IO_NO_INCREMENT); }
//---------------------------------------------------------------------------- NTSTATUS NTCheckSetCancelRoutine( IN PIRP pIrp, IN PVOID CancelRoutine, IN PDEVICE pDevice ) /*++ Routine Description; This Routine sets the cancel routine for an Irp. Arguments; status - a completion status for the Irp Return Value; NTSTATUS - status of the request --*/ { NTSTATUS status; IpxPrint1("CheckSetCancelRoutine: Entered. Irp = (%lx)\n", pIrp); // // Check if the irp was cancelled yet and if not, then set the // irp cancel routine. // IoAcquireCancelSpinLock(&pIrp->CancelIrql); if (pIrp->Cancel) { pIrp->IoStatus.Status = STATUS_CANCELLED; status = STATUS_CANCELLED; } else { // setup the cancel routine IoMarkIrpPending(pIrp); IoSetCancelRoutine(pIrp,CancelRoutine); status = STATUS_SUCCESS; } IoReleaseCancelSpinLock(pIrp->CancelIrql); return(status); }
/*! * \brief Entry point for RDF_CARD_TRACKING.<br> * <br> * The RDF_CARD_TRACKING callback function installs an event handler to track every time a card is inserted in or removed from a card reader. * <br> * \param [in] pSmartcardExtension A pointer to the smart card extension, SMARTCARD_EXTENSION, of the device. * * \retval STATUS_PENDING Smart card tracking has started. */ NTSTATUS VR_RDF_CardTracking(IN PSMARTCARD_EXTENSION pSmartcardExtension) { dbg_log("VR_RDF_CardTracking start"); KIRQL cancelIrql; // The corresponding WDM driver library adds a pointer to the request // in SmartcardExtension->OsData->NotificationIrp. // http://msdn2.microsoft.com/en-us/library/ms801317.aspx IoAcquireCancelSpinLock(&cancelIrql); IoSetCancelRoutine(pSmartcardExtension->OsData->NotificationIrp, VR_RDF_Cancel); IoReleaseCancelSpinLock(cancelIrql); dbg_log("VR_RDF_CardTracking end - status: 0x%08X", STATUS_PENDING); return STATUS_PENDING; }
VOID NdisprotCancelRead( IN PDEVICE_OBJECT pDeviceObject, IN PIRP pIrp ) /*++ Routine Description: Cancel a pending read IRP. We unlink the IRP from the open context queue and complete it. Arguments: pDeviceObject - pointer to our device object pIrp - IRP to be cancelled Return Value: None --*/ { PNDISPROT_OPEN_CONTEXT pOpenContext; UNREFERENCED_PARAMETER(pDeviceObject); IoReleaseCancelSpinLock(pIrp->CancelIrql); pOpenContext = (PNDISPROT_OPEN_CONTEXT) pIrp->Tail.Overlay.DriverContext[0]; NPROT_STRUCT_ASSERT(pOpenContext, oc); NPROT_ACQUIRE_LOCK(&pOpenContext->Lock, FALSE); NPROT_REMOVE_ENTRY_LIST(&pIrp->Tail.Overlay.ListEntry); pOpenContext->PendedReadCount--; NPROT_RELEASE_LOCK(&pOpenContext->Lock, FALSE); DEBUGP(DL_INFO, ("CancelRead: Open %p, IRP %p\n", pOpenContext, pIrp)); pIrp->IoStatus.Status = STATUS_CANCELLED; pIrp->IoStatus.Information = 0; IoCompleteRequest(pIrp, IO_NO_INCREMENT); NPROT_DEREF_OPEN(pOpenContext); // Cancel removed pended Read }
VOID DriverCancelCurrentReadIrp(IN PDEVICE_OBJECT DeviceObject, IN PIRP pIrp) { PDEVICE_EXTENSION pExtension = (PDEVICE_EXTENSION)DeviceObject->DeviceExtension; KIRQL OldIrql; IoReleaseCancelSpinLock(pIrp->CancelIrql); KeAcquireSpinLock(&pExtension->WriteSpinLock, &OldIrql); pExtension->pReadIrp = NULL; KeReleaseSpinLock(&pExtension->WriteSpinLock, OldIrql); pIrp->IoStatus.Status = STATUS_CANCELLED; IoCompleteRequest(pIrp, IO_NO_INCREMENT); }
VOID SecLabCancelIrp(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp) { IoReleaseCancelSpinLock(Irp->CancelIrql); // If this is our queued read, then unqueue it NdisAcquireSpinLock(&ReadIrpLock); if( Irp==ReadIrp) { ReadIrp = NULL; ReadCount=0; } NdisReleaseSpinLock(&ReadIrpLock); // Whatever Irp it is, just cancel it CompleteIrp(Irp,STATUS_CANCELLED,0); }
NTSTATUS IRPFinish( PIRP Irp, NTSTATUS Status ) { KIRQL OldIrql; Irp->IoStatus.Status = Status; if( Status == STATUS_PENDING ) IoMarkIrpPending( Irp ); else { IoAcquireCancelSpinLock(&OldIrql); (void)IoSetCancelRoutine( Irp, NULL ); IoReleaseCancelSpinLock(OldIrql); IoCompleteRequest( Irp, IO_NETWORK_INCREMENT ); } return Status; }
VOID DriverCancelWaitIrp(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp) { KdPrint(("DriverCancelWaitIrp\n")); PDEVICE_EXTENSION pExtension = (PDEVICE_EXTENSION)DeviceObject->DeviceExtension; KIRQL OldIrql; IoReleaseCancelSpinLock(Irp->CancelIrql); KeAcquireSpinLock(&pExtension->IoctlSpinLock, &OldIrql); pExtension->pWaitIrp = NULL; KeReleaseSpinLock(&pExtension->IoctlSpinLock, OldIrql); Irp->IoStatus.Status = STATUS_CANCELLED; IoCompleteRequest(Irp, IO_NO_INCREMENT); }