Explorar el Código

Merge 5b4eba2697a3fc2af81ac4cb09f6a4a2366fbccb on remote branch

Change-Id: I9534bec8a32b1e0bb540d17c8afd6b3f08774f79
Linux Build Service Account hace 1 año
padre
commit
5bda1752a1
Se han modificado 3 ficheros con 75 adiciones y 9 borrados
  1. 9 8
      hdcp/hdcp_smcinvoke.c
  2. 57 0
      qseecom/qseecom.c
  3. 9 1
      smcinvoke/smcinvoke.c

+ 9 - 8
hdcp/hdcp_smcinvoke.c

@@ -93,6 +93,12 @@ int load_app(char *app_name, struct Object *app_obj,
 	struct Object client_env = {NULL, NULL};
 	struct Object app_loader = {NULL, NULL};
 
+	buffer = firmware_request_from_smcinvoke(app_name, &size, &shm);
+	if (buffer == NULL) {
+		pr_err("firmware_request_from_smcinvoke failed\n");
+		return -EINVAL;
+	}
+
 	ret = get_client_env_object(&client_env);
 	if (ret) {
 		pr_err("get_client_env_object failed :%d\n", ret);
@@ -109,13 +115,6 @@ int load_app(char *app_name, struct Object *app_obj,
 		goto error;
 	}
 
-	buffer = firmware_request_from_smcinvoke(app_name, &size, &shm);
-	if (buffer == NULL) {
-		pr_err("firmware_request_from_smcinvoke failed\n");
-		ret = -EINVAL;
-		goto error;
-	}
-
 	ret = IAppLoader_loadFromBuffer(app_loader, (const void *)buffer, size,
 			app_controller_obj);
 	if (ret) {
@@ -537,7 +536,9 @@ static int hdcp2_app_load(struct hdcp2_smcinvoke_handle *handle)
 
 	ret = load_app(HDCPSRM_APP_NAME, &(handle->hdcpsrm_app_obj),
 		   &(handle->hdcpsrm_appcontroller_obj));
-	if (ret) {
+	if (ret == 16) {
+		pr_err("hdcpsrm TA already loaded\n");
+	} else if (ret) {
 		pr_err("hdcpsrm TA load failed :%d\n", ret);
 		goto error;
 	}

+ 57 - 0
qseecom/qseecom.c

@@ -12,6 +12,7 @@
 #include <linux/slab.h>
 #include <linux/module.h>
 #include <linux/fs.h>
+#include <linux/reboot.h>
 #include <linux/platform_device.h>
 #include <linux/debugfs.h>
 #include <linux/cdev.h>
@@ -379,6 +380,7 @@ struct qseecom_control {
 
 	struct list_head  unload_app_pending_list_head;
 	struct task_struct *unload_app_kthread_task;
+	struct notifier_block reboot_nb;
 	wait_queue_head_t unload_app_kthread_wq;
 	atomic_t unload_app_kthread_state;
 	bool no_user_contig_mem_support;
@@ -9270,6 +9272,47 @@ static void qseecom_release_ce_data(void)
 	}
 }
 
+static int qseecom_reboot_worker(struct notifier_block *nb, unsigned long val, void *data)
+{
+	struct qseecom_registered_listener_list *entry;
+
+	/* Mark all the listener as abort since system is going
+	 * for a reboot so every pending listener request should
+	 * be aborted.
+	 */
+	list_for_each_entry(entry,
+			&qseecom.registered_listener_list_head, list) {
+		entry->abort = 1;
+	}
+
+	/* stop CA thread waiting for listener response */
+	wake_up_interruptible_all(&qseecom.send_resp_wq);
+
+	/* Assumption is system going in reboot
+	 * every registered listener from userspace waiting
+	 * on event interruptible will receive interrupt as
+	 * TASK_INTERRUPTIBLE flag will be set for them
+	 */
+
+	return 0;
+}
+static int qseecom_register_reboot_notifier(void)
+{
+	int rc = 0;
+
+	/* Registering reboot notifier for resource cleanup at reboot.
+	 * Current implementation is for listener use case,
+	 * it can be extended to App also in case of any corner
+	 * case issue found.
+	 */
+
+	qseecom.reboot_nb.notifier_call = qseecom_reboot_worker;
+	rc = register_reboot_notifier(&(qseecom.reboot_nb));
+	if (rc)
+		pr_err("failed to register reboot notifier\n");
+	return rc;
+}
+
 static int qseecom_init_dev(struct platform_device *pdev)
 {
 	int rc = 0;
@@ -9324,6 +9367,19 @@ static int qseecom_init_dev(struct platform_device *pdev)
 		pr_err("Failed to initialize reserved mem, ret %d\n", rc);
 		goto exit_del_cdev;
 	}
+
+	rc = qseecom_register_reboot_notifier();
+	if (rc) {
+		pr_err("failed in registering reboot notifier %d\n", rc);
+		/* exit even if notifier registration fail.
+		 * Although, thats not a functional failure from qseecom
+		 * driver prespective but this registration
+		 * failure will cause more complex issue at the
+		 * time of reboot or possibly halt the reboot.
+		 */
+		goto exit_del_cdev;
+	}
+
 	return 0;
 
 exit_del_cdev:
@@ -9342,6 +9398,7 @@ static void qseecom_deinit_dev(void)
 {
 	kfree(qseecom.dev->dma_parms);
 	qseecom.dev->dma_parms = NULL;
+	unregister_reboot_notifier(&(qseecom.reboot_nb));
 	cdev_del(&qseecom.cdev);
 	device_destroy(qseecom.driver_class, qseecom.qseecom_device_no);
 	class_destroy(qseecom.driver_class);

+ 9 - 1
smcinvoke/smcinvoke.c

@@ -1520,7 +1520,15 @@ static void process_kernel_obj(void *buf, size_t buf_len)
 
 	switch (cb_req->hdr.op) {
 	case OBJECT_OP_MAP_REGION:
-		pr_err("Received a request to map memory region\n");
+		if (mem_obj_async_support) {
+			/* Mapping requests are not supposed to come
+			 * from TZ once memory object async support
+			 * is enabled.
+			 * If they are still coming, we would like to
+			 * know about it.
+			 */
+			pr_info("Received a request to map memory region\n");
+		}
 		cb_req->result = smcinvoke_process_map_mem_region_req(buf, buf_len);
 		break;
 	case OBJECT_OP_YIELD: