Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit a04e5dca authored by Linux Build Service Account's avatar Linux Build Service Account Committed by Gerrit - the friendly Code Review server
Browse files

Merge "msm: VPU: Attach VPU SMMUs within fixed powerup sequence"

parents d235c1c3 01336344
Loading
Loading
Loading
Loading
+10 −1
Original line number Diff line number Diff line
@@ -810,6 +810,7 @@ static int ipc_cmd_sync_wait(struct vpu_sync_transact *ptrans, u32 timeout_ms,
		} else {
			/* local error */
			rc = ptrans->status;
			pr_err("Local IPC err %d\n", rc);
		}
	} else if (rc == 0) {
		/* timeout */
@@ -2051,6 +2052,12 @@ static void vpu_boot_work_handler(struct work_struct *work)
		goto powerup_fail;
	}

	rc = attach_vpu_iommus(ch_hal->res_orig);
	if (rc) {
		pr_err("could not attach VPU IOMMUs\n");
		goto err_iommu_attach;
	}

	/* boot up VPU and set callback */
	rc = vpu_hfi_start(chan_handle_msg, chan_handle_event);
	if (unlikely(rc)) {
@@ -2063,8 +2070,9 @@ static void vpu_boot_work_handler(struct work_struct *work)
	return;

err_hfi_start:
	detach_vpu_iommus(ch_hal->res_orig);
err_iommu_attach:
	vpu_hw_power_off(ch_hal);

powerup_fail:
	mutex_unlock(&ch_hal->pw_lock);

@@ -2142,6 +2150,7 @@ static void vpu_shutdown_work_handler(struct work_struct *work)
	mutex_lock(&ch_hal->pw_lock);

	vpu_hfi_stop();
	detach_vpu_iommus(ch_hal->res_orig);
	vpu_hw_power_off(ch_hal);

	/* disable HFI system and logging channels */
+18 −26
Original line number Diff line number Diff line
@@ -19,6 +19,7 @@
#include "vpu_configuration.h"
#include "vpu_translate.h"
#include "vpu_channel.h"
#include "vpu_ipc.h"

#ifdef CONFIG_MSM_VPU_IN_VCAP
extern int vpu_init_port_vcap(struct vpu_dev_session *session,
@@ -150,12 +151,15 @@ static void __sys_buffer_callback_handler(u32 sid, struct vpu_buffer *pbuf,
	session = vb2_get_drv_priv(pbuf->vb.vb2_queue);

	if (data) {
		pr_debug("ERROR (%d) buffer callback port %d buff %d\n",
				data, port, pbuf->vb.v4l2_buf.index);
		pr_debug("%s (%d) buffer callback session %d port %d buff %d\n",
			data == VPU_STS_EFRAMEUNPROCESSED ?
					"Unprocessed" : "Error",
			data, session->id, port, pbuf->vb.v4l2_buf.index);

		vb2_buffer_done(&pbuf->vb, VB2_BUF_STATE_ERROR);
	} else {
		pr_debug("GOOD buffer callback for port %d buff %d\n",
				port, pbuf->vb.v4l2_buf.index);
		pr_debug("Good buffer callback session %d port %d buff %d\n",
			session->id, port, pbuf->vb.v4l2_buf.index);

		/* update bytesused */
		port_info = &session->port_info[port];
@@ -175,43 +179,30 @@ static void __sys_buffer_callback_handler(u32 sid, struct vpu_buffer *pbuf,
 * Dynamic switch (on/off) of VPU hardware on first/last global client.
 * Function must be called with core->lock mutex held.
 */
static int __dynamic_vpu_hw_switch(struct vpu_dev_core *core, int on)
static int __vpu_hw_switch(struct vpu_dev_core *core, int on)
{
	int ret = 0;

	if (on) {
		if (core->global_client_count++ == 0) {

			pr_debug("Starting up VPU hardware\n");
			ret = vpu_hw_sys_start(__sys_event_callback_handler,
					__sys_buffer_callback_handler,
					(void *)core);
			if (ret) {
				pr_err("failed to start IPC system\n");
				core->global_client_count--;
				goto exit_hfi_init;
			}

			ret = attach_vpu_iommus(&core->resources);
			if (ret) {
				pr_err("could not attach VPU IOMMUs\n");
				pr_err("failed to start VPU hardware\n");
				core->global_client_count--;
				goto err_stop_sys;
			}
		}

	} else { /* off */
		if (--core->global_client_count == 0)
			goto hfi_deinit;
		if (--core->global_client_count == 0) {
			pr_debug("Shutting down VPU hardware\n");
			vpu_hw_sys_stop(0);
		}
	}

	goto exit_hfi_init; /* hfi system stays on */

hfi_deinit:
	pr_debug("Shutting down hfi IPC\n");
	detach_vpu_iommus(&core->resources);
err_stop_sys:
	vpu_hw_sys_stop(0);
exit_hfi_init:
	return ret;
}

@@ -251,7 +242,7 @@ static struct vpu_client *__create_client(struct vpu_dev_core *core,
	INIT_LIST_HEAD(&client->clients_entry);

	/* Initialize HFI on first client open */
	ret = __dynamic_vpu_hw_switch(core, 1);
	ret = __vpu_hw_switch(core, 1);
	if (ret) {
		devm_kfree(core->dev, client);
		goto err_client_create;
@@ -314,7 +305,7 @@ int vpu_close_client(struct vpu_client *client)
		vpu_detach_client(client);

	mutex_lock(&client->core->lock);
	__dynamic_vpu_hw_switch(client->core, 0);
	__vpu_hw_switch(client->core, 0);
	list_del_init(&client->clients_entry); /* remove from unattached list */
	mutex_unlock(&client->core->lock);

@@ -919,6 +910,7 @@ static int __check_user_planes(struct vb2_queue *vbq, struct v4l2_buffer *b)
		return 0;
	}

	pr_err("Invalid planes parameters\n");
	return -EINVAL;
}

+2 −1
Original line number Diff line number Diff line
/* Copyright (c) 2013, The Linux Foundation. All rights reserved.
/* Copyright (c) 2013-2014, The Linux Foundation. All rights reserved.
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License version 2 and
@@ -41,6 +41,7 @@
#define VPU_STS_EINVALIDCLIENTID                     21
#define VPU_STS_EINSUFFICIENTMEMAVAILABLE            22
#define VPU_STS_EBADSTATE                            23
#define VPU_STS_EFRAMEUNPROCESSED                    24

/* Bit fields */
#define VPU_IPC_BUFFER_RETURN_TO_HOST_BIT	0x0