All of lore.kernel.org
 help / color / mirror / Atom feed
From: "Huang, Sean Z" <sean.z.huang@intel.com>
To: Intel-gfx@lists.freedesktop.org
Subject: [Intel-gfx] [RFC-v4 12/26] drm/i915/pxp: Implement ioctl action to terminate the session
Date: Tue,  1 Dec 2020 20:03:27 -0800	[thread overview]
Message-ID: <20201202040341.31981-13-sean.z.huang@intel.com> (raw)
In-Reply-To: <20201202040341.31981-1-sean.z.huang@intel.com>

Implement the PXP ioctl action to allow user space driver to
terminate the hardware session and cleanup its software session
state. PXP sends the session termination command to GPU once
receves this ioctl action.

Signed-off-by: Huang, Sean Z <sean.z.huang@intel.com>
---
 drivers/gpu/drm/i915/pxp/intel_pxp.c    |   7 +
 drivers/gpu/drm/i915/pxp/intel_pxp_sm.c | 190 ++++++++++++++++++++++++
 drivers/gpu/drm/i915/pxp/intel_pxp_sm.h |   5 +
 3 files changed, 202 insertions(+)

diff --git a/drivers/gpu/drm/i915/pxp/intel_pxp.c b/drivers/gpu/drm/i915/pxp/intel_pxp.c
index 91ace0f49b5f..3856e1060d11 100644
--- a/drivers/gpu/drm/i915/pxp/intel_pxp.c
+++ b/drivers/gpu/drm/i915/pxp/intel_pxp.c
@@ -57,6 +57,13 @@ int i915_pxp_ops_ioctl(struct drm_device *dev, void *data, struct drm_file *drmf
 			ret = pxp_sm_mark_protected_session_in_play(i915, params->session_type,
 								    params->pxp_tag);
 
+		} else if (params->req_session_state == PXP_SM_REQ_SESSION_TERMINATE) {
+			ret = pxp_sm_terminate_protected_session_safe(i915, 0,
+								      params->session_type,
+								      params->pxp_tag);
+
+			if (!intel_pxp_sm_is_any_type0_session_in_play(i915, PROTECTION_MODE_ALL))
+				intel_pxp_destroy_user_ctx_list(i915);
 		} else {
 			ret = -EINVAL;
 			goto end;
diff --git a/drivers/gpu/drm/i915/pxp/intel_pxp_sm.c b/drivers/gpu/drm/i915/pxp/intel_pxp_sm.c
index f41e50911688..65b89728251d 100644
--- a/drivers/gpu/drm/i915/pxp/intel_pxp_sm.c
+++ b/drivers/gpu/drm/i915/pxp/intel_pxp_sm.c
@@ -802,6 +802,174 @@ static int issue_hw_terminate_for_session(struct drm_i915_private *i915, int ses
 	return ret;
 }
 
+/**
+ * terminate_protected_session - To terminate an active HW session and free its entry.
+ * @i915: i915 device handle.
+ * @context_id: context identifier of the requestor. only relevant if do_safety_check is true.
+ * @session_type: type of the session to be terminated. One of enum pxp_session_types.
+ * @session_index: session index of the session to be terminated.
+ * @do_safety_check: if enabled the context Id sent by the caller is
+ *                   matched with the one associated with the terminated
+ *                   session entry.
+ *
+ * Return: 0 means terminate is successful, or didn't find the desired session.
+ */
+static int terminate_protected_session(struct drm_i915_private *i915, int context_id,
+				       int session_type, int session_index,
+				       bool do_safety_check)
+{
+	int ret;
+	struct pxp_protected_session *current_session, *n;
+
+	lockdep_assert_held(&i915->pxp.ctx->ctx_mutex);
+
+	switch (session_type) {
+	case SESSION_TYPE_TYPE0:
+		list_for_each_entry_safe(current_session, n,
+					 pxp_session_list(i915, SESSION_TYPE_TYPE0),
+					 session_list) {
+			if (current_session->session_index == session_index) {
+				if (do_safety_check && current_session->context_id != context_id) {
+					ret = -EPERM;
+					drm_err(&i915->drm, "Failed to %s due to invalid context_id=[%d]\n",
+						__func__, context_id);
+					goto end;
+				}
+
+				ret = issue_hw_terminate_for_session(i915, session_type,
+								     session_index);
+				if (ret) {
+					drm_err(&i915->drm, "Failed to issue_hw_terminate_for_session()\n");
+					goto end;
+				}
+
+				ret = pxp_set_pxp_tag(i915, session_type, session_index,
+						      PROTECTION_MODE_NONE);
+				if (ret) {
+					drm_err(&i915->drm, "Failed to pxp_set_pxp_tag()\n");
+					goto end;
+				}
+
+				list_del(&current_session->session_list);
+				kfree(current_session);
+				return 0;
+			}
+		}
+		return 0;
+
+	case SESSION_TYPE_TYPE1:
+		list_for_each_entry_safe(current_session, n,
+					 pxp_session_list(i915, SESSION_TYPE_TYPE1),
+					 session_list) {
+			if (current_session->session_index == session_index) {
+				if (do_safety_check && current_session->context_id != context_id) {
+					ret = -EPERM;
+					drm_err(&i915->drm, "Failed to %s due to invalid context_id=[%d]\n",
+						__func__, context_id);
+					goto end;
+				}
+
+				ret = issue_hw_terminate_for_session(i915, session_type,
+								     session_index);
+				if (ret) {
+					drm_err(&i915->drm, "Failed to issue_hw_terminate_for_session()\n");
+					goto end;
+				}
+
+				ret = pxp_set_pxp_tag(i915, session_type, session_index,
+						      PROTECTION_MODE_NONE);
+				if (ret) {
+					drm_err(&i915->drm, "Failed to pxp_set_pxp_tag()\n");
+					goto end;
+				}
+
+				list_del(&current_session->session_list);
+				kfree(current_session);
+				return 0;
+			}
+		}
+		return 0;
+
+	default:
+		return -EINVAL;
+	}
+end:
+	return ret;
+}
+
+/**
+ * pxp_sm_terminate_protected_session_safe - to terminate an active HW session and free its entry.
+ * @i915: i915 device handle.
+ * @context_id: context identifier of the requestor.
+ * @session_type: type of the session to be terminated. One of enum pxp_session_types.
+ * @session_id: session id identifier of the session to be terminated.
+ *
+ * For safety, the context Id sent by the caller is matched with the
+ * one associated with the terminated session entry.  * Terminate is
+ * only issued if context Ids match. Rejected otherwise This function
+ * is intended to be called from the ioctl.
+ *
+ * Return: status. 0 means terminate is successful.
+ */
+int pxp_sm_terminate_protected_session_safe(struct drm_i915_private *i915, int context_id,
+					    int session_type, int session_id)
+{
+	int ret;
+	int session_type_in_id;
+	int session_idx;
+
+	ret = pxp_get_session_index(i915, session_id, &session_idx, &session_type_in_id);
+	if (ret) {
+		drm_err(&i915->drm, "Failed to pxp_get_session_index\n");
+		return ret;
+	}
+
+	if (session_type != session_type_in_id) {
+		drm_err(&i915->drm, "Failed to session_type and session_type_in_id don't match\n");
+		return -EINVAL;
+	}
+
+	ret = terminate_protected_session(i915, context_id, session_type, session_idx, true);
+
+	return ret;
+}
+
+/**
+ * pxp_sm_terminate_protected_session_unsafe - To terminate an active HW session and free its entry.
+ * @i915: i915 device handle.
+ * @session_type: type of the session to be terminated. One of enum pxp_session_types.
+ * @session_id: session id identifier of the session to be terminated.
+ *
+ * No safety; the context Id sent by the caller is not matched with
+ * the one associated with the terminated session entry. This function
+ * is NOT intended to be called from the ioctl. Kernel administration
+ * purposes only.
+ *
+ * Return: status. 0 means terminate is successful.
+ */
+int pxp_sm_terminate_protected_session_unsafe(struct drm_i915_private *i915, int session_type,
+					      int session_id)
+{
+	int ret;
+	int session_idx;
+	int session_type_in_id;
+
+	ret = pxp_get_session_index(i915, session_id, &session_idx, &session_type_in_id);
+	if (ret) {
+		drm_err(&i915->drm, "Failed to pxp_get_session_index\n");
+		return ret;
+	}
+
+	if (session_type != session_type_in_id) {
+		drm_err(&i915->drm, "Failed to session_type and session_type_in_id don't match\n");
+		return -EINVAL;
+	}
+
+	ret = terminate_protected_session(i915, -1, session_type, session_idx, false);
+
+	return ret;
+}
+
 int pxp_sm_set_kcr_init_reg(struct drm_i915_private *i915)
 {
 	int ret;
@@ -812,3 +980,25 @@ int pxp_sm_set_kcr_init_reg(struct drm_i915_private *i915)
 
 	return ret;
 }
+
+/**
+ * intel_pxp_sm_is_any_type0_session_in_play - To check if there is a type0 "in play" session.
+ * @i915: i915 device handle.
+ * @protection_mode: check for specified protection mode of the session
+ *
+ * Return: True if at least one alive session in "session in play" state, false otherwise.
+ */
+bool intel_pxp_sm_is_any_type0_session_in_play(struct drm_i915_private *i915, int protection_mode)
+{
+	struct pxp_protected_session *session, *n;
+
+	list_for_each_entry_safe(session, n, pxp_session_list(i915, SESSION_TYPE_TYPE0),
+				 session_list) {
+		if (protection_mode == PROTECTION_MODE_ALL)
+			return true;
+		else if (protection_mode == session->protection_mode)
+			return true;
+	}
+
+	return false;
+}
diff --git a/drivers/gpu/drm/i915/pxp/intel_pxp_sm.h b/drivers/gpu/drm/i915/pxp/intel_pxp_sm.h
index 1b3173bca281..a68e1d109437 100644
--- a/drivers/gpu/drm/i915/pxp/intel_pxp_sm.h
+++ b/drivers/gpu/drm/i915/pxp/intel_pxp_sm.h
@@ -105,6 +105,11 @@ int intel_pxp_sm_reserve_session(struct drm_i915_private *i915, struct drm_file
 				 u32 *pxp_tag);
 int pxp_sm_mark_protected_session_in_play(struct drm_i915_private *i915, int session_type,
 					  u32 session_id);
+int pxp_sm_terminate_protected_session_safe(struct drm_i915_private *i915, int context_id,
+					    int session_type, int session_id);
+int pxp_sm_terminate_protected_session_unsafe(struct drm_i915_private *i915, int session_type,
+					      int session_id);
 int pxp_sm_set_kcr_init_reg(struct drm_i915_private *i915);
+bool intel_pxp_sm_is_any_type0_session_in_play(struct drm_i915_private *i915, int protection_mode);
 
 #endif /* __INTEL_PXP_SM_H__ */
-- 
2.17.1

_______________________________________________
Intel-gfx mailing list
Intel-gfx@lists.freedesktop.org
https://lists.freedesktop.org/mailman/listinfo/intel-gfx

  parent reply	other threads:[~2020-12-02  4:04 UTC|newest]

Thread overview: 32+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2020-12-02  4:03 [Intel-gfx] [RFC-v4 00/26] Introduce Intel PXP component Huang, Sean Z
2020-12-02  4:03 ` [Intel-gfx] [RFC-v4 01/26] drm/i915/pxp: " Huang, Sean Z
2020-12-02  4:03 ` [Intel-gfx] [RFC-v4 02/26] drm/i915/pxp: Enable PXP irq worker and callback stub Huang, Sean Z
2020-12-02  4:03 ` [Intel-gfx] [RFC-v4 03/26] drm/i915/pxp: Add PXP context for logical hardware states Huang, Sean Z
2020-12-02  4:03 ` [Intel-gfx] [RFC-v4 04/26] drm/i915/pxp: set KCR reg init during the boot time Huang, Sean Z
2020-12-02  4:03 ` [Intel-gfx] [RFC-v4 05/26] drm/i915/pxp: Implement ioctl action to set the user space context Huang, Sean Z
2020-12-02  4:03 ` [Intel-gfx] [RFC-v4 06/26] drm/i915/pxp: Add PXP-related registers into allowlist Huang, Sean Z
2020-12-02  4:03 ` [Intel-gfx] [RFC-v4 07/26] drm/i915/pxp: Read register to check hardware session state Huang, Sean Z
2020-12-02  4:03 ` [Intel-gfx] [RFC-v4 08/26] drm/i915/pxp: Implement funcs to get/set PXP tag Huang, Sean Z
2020-12-02  4:03 ` [Intel-gfx] [RFC-v4 09/26] drm/i915/pxp: Implement ioctl action to reserve session slot Huang, Sean Z
2020-12-02  4:03 ` [Intel-gfx] [RFC-v4 10/26] drm/i915/pxp: Implement ioctl action to set session in play Huang, Sean Z
2020-12-02  4:03 ` [Intel-gfx] [RFC-v4 11/26] drm/i915/pxp: Func to send hardware session termination Huang, Sean Z
2020-12-02  4:03 ` Huang, Sean Z [this message]
2020-12-02  4:03 ` [Intel-gfx] [RFC-v4 13/26] drm/i915/pxp: Enable ioctl action to query PXP tag Huang, Sean Z
2020-12-02  4:03 ` [Intel-gfx] [RFC-v4 14/26] drm/i915/pxp: Destroy all type0 sessions upon teardown Huang, Sean Z
2020-12-02  4:03 ` [Intel-gfx] [RFC-v4 15/26] drm/i915/pxp: Termiante the session upon app crash Huang, Sean Z
2020-12-02  4:03 ` [Intel-gfx] [RFC-v4 16/26] drm/i915/pxp: Enable PXP power management Huang, Sean Z
2020-12-02  4:03 ` [Intel-gfx] [RFC-v4 17/26] drm/i915/pxp: Implement funcs to create the TEE channel Huang, Sean Z
2020-12-02  4:03 ` [Intel-gfx] [RFC-v4 18/26] drm/i915/pxp: Implement ioctl action to send TEE commands Huang, Sean Z
2020-12-02  4:03 ` [Intel-gfx] [RFC-v4 19/26] drm/i915/pxp: Create the arbitrary session after boot Huang, Sean Z
2020-12-02  4:03 ` [Intel-gfx] [RFC-v4 20/26] drm/i915/pxp: Add i915 trace logs for PXP operations Huang, Sean Z
2020-12-02  4:03 ` [Intel-gfx] [RFC-v4 21/26] drm/i915/pxp: Expose session state for display protection flip Huang, Sean Z
2020-12-02  4:03 ` [Intel-gfx] [RFC-v4 22/26] mei: pxp: export pavp client to me client bus Huang, Sean Z
2020-12-02  4:03 ` [Intel-gfx] [RFC-v4 23/26] drm/i915/uapi: introduce drm_i915_gem_create_ext Huang, Sean Z
2020-12-02  4:03 ` [Intel-gfx] [RFC-v4 24/26] drm/i915/pxp: User interface for Protected buffer Huang, Sean Z
2020-12-04 14:24   ` Lionel Landwerlin
2020-12-04 18:56     ` Huang, Sean Z
2020-12-02  4:03 ` [Intel-gfx] [RFC-v4 25/26] drm/i915/pxp: Add plane decryption support Huang, Sean Z
2020-12-02  4:03 ` [Intel-gfx] [RFC-v4 26/26] drm/i915/pxp: Enable the PXP ioctl for protected session Huang, Sean Z
2020-12-02  4:18 ` [Intel-gfx] ✗ Fi.CI.CHECKPATCH: warning for Introduce Intel PXP component (rev4) Patchwork
2020-12-02  4:48 ` [Intel-gfx] ✓ Fi.CI.BAT: success " Patchwork
2020-12-02  7:08 ` [Intel-gfx] ✓ Fi.CI.IGT: " Patchwork

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20201202040341.31981-13-sean.z.huang@intel.com \
    --to=sean.z.huang@intel.com \
    --cc=Intel-gfx@lists.freedesktop.org \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.