Beispiel #1
0
static ssize_t tpm_read(struct file *file, char __user *buf,
			size_t size, loff_t *off)
{
	struct file_priv *priv = file->private_data;
	ssize_t ret_size;
	int rc;

	del_singleshot_timer_sync(&priv->user_read_timer);
	flush_work(&priv->work);
	ret_size = atomic_read(&priv->data_pending);
	if (ret_size > 0) {	/* relay data */
		ssize_t orig_ret_size = ret_size;
		if (size < ret_size)
			ret_size = size;

		mutex_lock(&priv->buffer_mutex);
		rc = copy_to_user(buf, priv->data_buffer, ret_size);
		memset(priv->data_buffer, 0, orig_ret_size);
		if (rc)
			ret_size = -EFAULT;

		mutex_unlock(&priv->buffer_mutex);
	}

	atomic_set(&priv->data_pending, 0);

	return ret_size;
}
Beispiel #2
0
/*
 * Called on file close
 */
void tpm_common_release(struct file *file, struct file_priv *priv)
{
	flush_work(&priv->async_work);
	del_singleshot_timer_sync(&priv->user_read_timer);
	flush_work(&priv->timeout_work);
	file->private_data = NULL;
	priv->response_length = 0;
}
Beispiel #3
0
/*
 * Called on file close
 */
static int tpm_release(struct inode *inode, struct file *file)
{
	struct file_priv *priv = file->private_data;

	del_singleshot_timer_sync(&priv->user_read_timer);
	flush_work(&priv->work);
	file->private_data = NULL;
	atomic_set(&priv->data_pending, 0);
	clear_bit(0, &priv->chip->is_open);
	kfree(priv);
	return 0;
}
Beispiel #4
0
/*
 * caller should make sure no race with other threads
 */
static
void ctx_clear_timer_kr(struct ptlrpc_cli_ctx *ctx)
{
        struct gss_cli_ctx_keyring *gctx_kr = ctx2gctx_keyring(ctx);
        struct timer_list          *timer = gctx_kr->gck_timer;

        if (timer == NULL)
                return;

        CDEBUG(D_SEC, "ctx %p, key %p\n", ctx, gctx_kr->gck_key);

        gctx_kr->gck_timer = NULL;

        del_singleshot_timer_sync(timer);

        OBD_FREE_PTR(timer);
}
Beispiel #5
0
/*
 * See if the other side has responded to a partition deactivate request
 * from us. Though we requested the remote partition to deactivate with regard
 * to us, we really only need to wait for the other side to disengage from us.
 */
int
xpc_partition_disengaged(struct xpc_partition *part)
{
	short partid = XPC_PARTID(part);
	int disengaged;

	disengaged = !xpc_partition_engaged(partid);
	if (part->disengage_timeout) {
		if (!disengaged) {
			if (time_is_after_jiffies(part->disengage_timeout)) {
				/* timelimit hasn't been reached yet */
				return 0;
			}

			/*
			 * Other side hasn't responded to our deactivate
			 * request in a timely fashion, so assume it's dead.
			 */

			dev_info(xpc_part, "deactivate request to remote "
				 "partition %d timed out\n", partid);
			xpc_disengage_timedout = 1;
			xpc_assume_partition_disengaged(partid);
			disengaged = 1;
		}
		part->disengage_timeout = 0;

		/* cancel the timer function, provided it's not us */
		if (!in_interrupt())
			del_singleshot_timer_sync(&part->disengage_timer);

		DBUG_ON(part->act_state != XPC_P_AS_DEACTIVATING &&
			part->act_state != XPC_P_AS_INACTIVE);
		if (part->act_state != XPC_P_AS_INACTIVE)
			xpc_wakeup_channel_mgr(part);

		xpc_cancel_partition_deactivation_request(part);
	}
	return disengaged;
}
Beispiel #6
0
ssize_t tpm_common_read(struct file *file, char __user *buf,
			size_t size, loff_t *off)
{
	struct file_priv *priv = file->private_data;
	ssize_t ret_size = 0;
	int rc;

	mutex_lock(&priv->buffer_mutex);

	if (priv->response_length) {
		priv->response_read = true;

		ret_size = min_t(ssize_t, size, priv->response_length);
		if (!ret_size) {
			priv->response_length = 0;
			goto out;
		}

		rc = copy_to_user(buf, priv->data_buffer + *off, ret_size);
		if (rc) {
			memset(priv->data_buffer, 0, TPM_BUFSIZE);
			priv->response_length = 0;
			ret_size = -EFAULT;
		} else {
			memset(priv->data_buffer + *off, 0, ret_size);
			priv->response_length -= ret_size;
			*off += ret_size;
		}
	}

out:
	if (!priv->response_length) {
		*off = 0;
		del_singleshot_timer_sync(&priv->user_read_timer);
		flush_work(&priv->timeout_work);
	}
	mutex_unlock(&priv->buffer_mutex);
	return ret_size;
}
Beispiel #7
0
static void prism2sta_disconnect_usb(struct usb_interface *interface)
{
	wlandevice_t *wlandev;

	wlandev = (wlandevice_t *)usb_get_intfdata(interface);
	if (wlandev != NULL) {
		LIST_HEAD(cleanlist);
		hfa384x_usbctlx_t *ctlx, *temp;
		unsigned long flags;

		hfa384x_t *hw = wlandev->priv;

		if (!hw)
			goto exit;

		spin_lock_irqsave(&hw->ctlxq.lock, flags);

		p80211netdev_hwremoved(wlandev);
		list_splice_init(&hw->ctlxq.reapable, &cleanlist);
		list_splice_init(&hw->ctlxq.completing, &cleanlist);
		list_splice_init(&hw->ctlxq.pending, &cleanlist);
		list_splice_init(&hw->ctlxq.active, &cleanlist);

		spin_unlock_irqrestore(&hw->ctlxq.lock, flags);

		/* There's no hardware to shutdown, but the driver
		 * might have some tasks or tasklets that must be
		 * stopped before we can tear everything down.
		 */
		prism2sta_ifstate(wlandev, P80211ENUM_ifstate_disable);

		del_singleshot_timer_sync(&hw->throttle);
		del_singleshot_timer_sync(&hw->reqtimer);
		del_singleshot_timer_sync(&hw->resptimer);

		/* Unlink all the URBs. This "removes the wheels"
		 * from the entire CTLX handling mechanism.
		 */
		usb_kill_urb(&hw->rx_urb);
		usb_kill_urb(&hw->tx_urb);
		usb_kill_urb(&hw->ctlx_urb);

		tasklet_kill(&hw->completion_bh);
		tasklet_kill(&hw->reaper_bh);

		cancel_work_sync(&hw->link_bh);
		cancel_work_sync(&hw->commsqual_bh);

		/* Now we complete any outstanding commands
		 * and tell everyone who is waiting for their
		 * responses that we have shut down.
		 */
		list_for_each_entry(ctlx, &cleanlist, list)
			complete(&ctlx->done);

		/* Give any outstanding synchronous commands
		 * a chance to complete. All they need to do
		 * is "wake up", so that's easy.
		 * (I'd like a better way to do this, really.)
		 */
		msleep(100);

		/* Now delete the CTLXs, because no-one else can now. */
		list_for_each_entry_safe(ctlx, temp, &cleanlist, list)
			kfree(ctlx);

		/* Unhook the wlandev */
		unregister_wlandev(wlandev);
		wlan_unsetup(wlandev);

		usb_put_dev(hw->usb);

		hfa384x_destroy(hw);
		kfree(hw);

		kfree(wlandev);
	}

exit:
	usb_set_intfdata(interface, NULL);
}