示例#1
0
/**
 * ibmvtpm_crq_send_init - Send a CRQ initialize message
 * @ibmvtpm:	vtpm device struct
 *
 * Return value:
 *	0 - Success
 *	Non-zero - Failure
 */
static int ibmvtpm_crq_send_init(struct ibmvtpm_dev *ibmvtpm)
{
	int rc;

	rc = ibmvtpm_send_crq(ibmvtpm->vdev, INIT_CRQ_CMD, 0);
	if (rc != H_SUCCESS)
		dev_err(ibmvtpm->dev,
			"ibmvtpm_crq_send_init failed rc=%d\n", rc);

	return rc;
}
示例#2
0
/**
 * tpm_ibmvtpm_send - Send tpm request
 * @chip:	tpm chip struct
 * @buf:	buffer contains data to send
 * count:	size of buffer
 *
 * Return value:
 *	Number of bytes sent
 */
static int tpm_ibmvtpm_send(struct tpm_chip *chip, u8 *buf, size_t count)
{
	struct ibmvtpm_dev *ibmvtpm = dev_get_drvdata(&chip->dev);
	struct ibmvtpm_crq crq;
	__be64 *word = (__be64 *)&crq;
	int rc, sig;

	if (!ibmvtpm->rtce_buf) {
		dev_err(ibmvtpm->dev, "ibmvtpm device is not ready\n");
		return 0;
	}

	if (count > ibmvtpm->rtce_size) {
		dev_err(ibmvtpm->dev,
			"Invalid size in send: count=%zd, rtce_size=%d\n",
			count, ibmvtpm->rtce_size);
		return -EIO;
	}

	if (ibmvtpm->tpm_processing_cmd) {
		dev_info(ibmvtpm->dev,
		         "Need to wait for TPM to finish\n");
		/* wait for previous command to finish */
		sig = wait_event_interruptible(ibmvtpm->wq, !ibmvtpm->tpm_processing_cmd);
		if (sig)
			return -EINTR;
	}

	spin_lock(&ibmvtpm->rtce_lock);
	ibmvtpm->res_len = 0;
	memcpy((void *)ibmvtpm->rtce_buf, (void *)buf, count);
	crq.valid = (u8)IBMVTPM_VALID_CMD;
	crq.msg = (u8)VTPM_TPM_COMMAND;
	crq.len = cpu_to_be16(count);
	crq.data = cpu_to_be32(ibmvtpm->rtce_dma_handle);

	/*
	 * set the processing flag before the Hcall, since we may get the
	 * result (interrupt) before even being able to check rc.
	 */
	ibmvtpm->tpm_processing_cmd = true;

	rc = ibmvtpm_send_crq(ibmvtpm->vdev, be64_to_cpu(word[0]),
			      be64_to_cpu(word[1]));
	if (rc != H_SUCCESS) {
		dev_err(ibmvtpm->dev, "tpm_ibmvtpm_send failed rc=%d\n", rc);
		rc = 0;
		ibmvtpm->tpm_processing_cmd = false;
	} else
		rc = count;

	spin_unlock(&ibmvtpm->rtce_lock);
	return rc;
}
示例#3
0
/**
 * ibmvtpm_crq_get_version - Send a CRQ request to get vtpm version
 *			   - Note that this is vtpm version and not tpm version
 * @ibmvtpm:	vtpm device struct
 *
 * Return value:
 *	0 - Success
 *	Non-zero - Failure
 */
static int ibmvtpm_crq_get_version(struct ibmvtpm_dev *ibmvtpm)
{
	struct ibmvtpm_crq crq;
	u64 *buf = (u64 *) &crq;
	int rc;

	crq.valid = (u8)IBMVTPM_VALID_CMD;
	crq.msg = (u8)VTPM_GET_VERSION;

	rc = ibmvtpm_send_crq(ibmvtpm->vdev, buf[0], buf[1]);
	if (rc != H_SUCCESS)
		dev_err(ibmvtpm->dev,
			"ibmvtpm_crq_get_version failed rc=%d\n", rc);

	return rc;
}
示例#4
0
/**
 * ibmvtpm_crq_get_rtce_size - Send a CRQ request to get rtce size
 * @ibmvtpm:	vtpm device struct
 *
 * Return value:
 *	0 - Success
 *	Non-zero - Failure
 */
static int ibmvtpm_crq_get_rtce_size(struct ibmvtpm_dev *ibmvtpm)
{
	struct ibmvtpm_crq crq;
	u64 *buf = (u64 *) &crq;
	int rc;

	crq.valid = (u8)IBMVTPM_VALID_CMD;
	crq.msg = (u8)VTPM_GET_RTCE_BUFFER_SIZE;

	rc = ibmvtpm_send_crq(ibmvtpm->vdev, buf[0], buf[1]);
	if (rc != H_SUCCESS)
		dev_err(ibmvtpm->dev,
			"ibmvtpm_crq_get_rtce_size failed rc=%d\n", rc);

	return rc;
}
示例#5
0
/**
 * tpm_ibmvtpm_suspend - Suspend
 * @dev:	device struct
 *
 * Return value:
 *	0
 */
static int tpm_ibmvtpm_suspend(struct device *dev)
{
	struct ibmvtpm_dev *ibmvtpm = ibmvtpm_get_data(dev);
	struct ibmvtpm_crq crq;
	u64 *buf = (u64 *) &crq;
	int rc = 0;

	crq.valid = (u8)IBMVTPM_VALID_CMD;
	crq.msg = (u8)VTPM_PREPARE_TO_SUSPEND;

	rc = ibmvtpm_send_crq(ibmvtpm->vdev, buf[0], buf[1]);
	if (rc != H_SUCCESS)
		dev_err(ibmvtpm->dev,
			"tpm_ibmvtpm_suspend failed rc=%d\n", rc);

	return rc;
}
/**
 * tpm_ibmvtpm_send - Send tpm request
 * @chip:	tpm chip struct
 * @buf:	buffer contains data to send
 * count:	size of buffer
 *
 * Return value:
 *	Number of bytes sent
 */
static int tpm_ibmvtpm_send(struct tpm_chip *chip, u8 *buf, size_t count)
{
	struct ibmvtpm_dev *ibmvtpm;
	struct ibmvtpm_crq crq;
	__be64 *word = (__be64 *)&crq;
	int rc;

	ibmvtpm = (struct ibmvtpm_dev *)TPM_VPRIV(chip);

	if (!ibmvtpm->rtce_buf) {
		dev_err(ibmvtpm->dev, "ibmvtpm device is not ready\n");
		return 0;
	}

	if (count > ibmvtpm->rtce_size) {
		dev_err(ibmvtpm->dev,
			"Invalid size in send: count=%ld, rtce_size=%d\n",
			count, ibmvtpm->rtce_size);
		return -EIO;
	}

	spin_lock(&ibmvtpm->rtce_lock);
	memcpy((void *)ibmvtpm->rtce_buf, (void *)buf, count);
	crq.valid = (u8)IBMVTPM_VALID_CMD;
	crq.msg = (u8)VTPM_TPM_COMMAND;
	crq.len = cpu_to_be16(count);
	crq.data = cpu_to_be32(ibmvtpm->rtce_dma_handle);

rc = ibmvtpm_send_crq(ibmvtpm->vdev, be64_to_cpu(word[0]),
		      be64_to_cpu(word[1]));
	if (rc != H_SUCCESS) {
		dev_err(ibmvtpm->dev, "tpm_ibmvtpm_send failed rc=%d\n", rc);
		rc = 0;
	} else
		rc = count;

	spin_unlock(&ibmvtpm->rtce_lock);
	return rc;
}