Esempio n. 1
0
/*------------------------------------------------------------------------*
 *	usb_proc_drain
 *
 * This function will tear down an USB process, waiting for the
 * currently executing command to return.
 *
 * NOTE: If the structure pointed to by "up" is all zero,
 * this function does nothing.
 *------------------------------------------------------------------------*/
void
usb_proc_drain(struct usb_process *up)
{
	/* check if not initialised */
	if (up->up_mtx == NULL)
		return;
	/* handle special case with Giant */
	if (up->up_mtx != &Giant)
		mtx_assert(up->up_mtx, MA_NOTOWNED);

	mtx_lock(up->up_mtx);

	/* Set the gone flag */

	up->up_gone = 1;

	while (up->up_ptr) {

		/* Check if we need to wakeup the USB process */

		if (up->up_msleep || up->up_csleep) {
			up->up_msleep = 0;
			up->up_csleep = 0;
			cv_signal(&up->up_cv);
		}
		/* Check if we are still cold booted */

		if (cold) {
#ifndef __rtems__
			USB_THREAD_SUSPEND(up->up_ptr);
			printf("WARNING: A USB process has "
			    "been left suspended\n");
			break;
#else /* __rtems__ */
                        BSD_ASSERT(0);
#endif /* __rtems__ */
		}
		cv_wait(&up->up_cv, up->up_mtx);
	}
	/* Check if someone is waiting - should not happen */

	if (up->up_dsleep) {
		up->up_dsleep = 0;
		cv_broadcast(&up->up_drain);
		DPRINTF("WARNING: Someone is waiting "
		    "for USB process drain!\n");
	}
	mtx_unlock(up->up_mtx);
}
Esempio n. 2
0
/*------------------------------------------------------------------------*
 *	usb_proc_drain
 *
 * This function will tear down an USB process, waiting for the
 * currently executing command to return.
 *
 * NOTE: If the structure pointed to by "up" is all zero,
 * this function does nothing.
 *------------------------------------------------------------------------*/
void
usb_proc_drain(struct usb_process *up)
{
	/* check if not initialised */
	if (up->up_lock == NULL)
		return;
#if 0 /* XXX */
	/* handle special case with Giant */
	if (up->up_mtx != &Giant)
		mtx_assert(up->up_mtx, MA_NOTOWNED);
#else
	KKASSERT(!lockowned(up->up_lock));
	lockmgr(up->up_lock, LK_EXCLUSIVE);
#endif

	/* Set the gone flag */

	up->up_gone = 1;

	while (up->up_ptr) {

		/* Check if we need to wakeup the USB process */

		if (up->up_msleep || up->up_csleep) {
			up->up_msleep = 0;
			up->up_csleep = 0;
			cv_signal(&up->up_cv);
		}
		/* Check if we are still cold booted */

		if (cold) {
			USB_THREAD_SUSPEND(up->up_ptr);
			kprintf("WARNING: A USB process has "
			    "been left suspended\n");
			break;
		}
		cv_wait(&up->up_cv, up->up_lock);
	}
	/* Check if someone is waiting - should not happen */

	if (up->up_dsleep) {
		up->up_dsleep = 0;
		cv_broadcast(&up->up_drain);
		DPRINTF("WARNING: Someone is waiting "
		    "for USB process drain!\n");
	}
	lockmgr(up->up_lock, LK_RELEASE);
}