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

Commit 6c9cb2b1 authored by Dhaval Patel's avatar Dhaval Patel Committed by Gerrit - the friendly Code Review server
Browse files

drm/msm/sde: update scm call by checking all crtc state



scm call must be initiated after all crtc change the
state. SMMU context bank should also be attached or
detached based on all crtc state because they all share
single smmu context bank. Any SCM call out of sync
may cause the pre-mature context bank state and may
lead to invalid transaction request. This patch start
checking all context bank state before detaching secure
display and secure camera session.

Change-Id: I7ab96904a0f770408e2984efb580b0cae8abb65c
Signed-off-by: default avatarDhaval Patel <pdhaval@codeaurora.org>
parent 65ca63e7
Loading
Loading
Loading
Loading
+106 −57
Original line number Diff line number Diff line
@@ -2024,6 +2024,93 @@ void sde_crtc_timeline_status(struct drm_crtc *crtc)
	sde_fence_timeline_status(&sde_crtc->output_fence, &crtc->base);
}

static int _sde_crtc_detach_all_cb(struct sde_kms *sde_kms)
{
	u32 ret = 0;

	if (atomic_inc_return(&sde_kms->detach_all_cb) > 1)
		goto end;

	/* detach_all_contexts */
	ret = sde_kms_mmu_detach(sde_kms, false);
	if (ret) {
		SDE_ERROR("failed to detach all cb ret:%d\n", ret);
		goto end;
	}

	ret = _sde_crtc_scm_call(VMID_CP_SEC_DISPLAY);
	if (ret)
		goto end;

end:
	return ret;
}

static int _sde_crtc_attach_all_cb(struct sde_kms *sde_kms)
{
	u32 ret = 0;

	if (atomic_dec_return(&sde_kms->detach_all_cb) != 0)
		goto end;

	ret = _sde_crtc_scm_call(VMID_CP_PIXEL);
	if (ret)
		goto end;

	/* attach_all_contexts */
	ret = sde_kms_mmu_attach(sde_kms, false);
	if (ret) {
		SDE_ERROR("failed to attach all cb ret:%d\n", ret);
		goto end;
	}

end:
	return ret;
}

static int _sde_crtc_detach_sec_cb(struct sde_kms *sde_kms)
{
	u32 ret = 0;

	if (atomic_inc_return(&sde_kms->detach_sec_cb) > 1)
		goto end;

	/* detach secure_context */
	ret = sde_kms_mmu_detach(sde_kms, true);
	if (ret) {
		SDE_ERROR("failed to detach sec cb ret:%d\n", ret);
		goto end;
	}

	ret = _sde_crtc_scm_call(VMID_CP_CAMERA_PREVIEW);
	if (ret)
		goto end;

end:
	return ret;
}

static int _sde_crtc_attach_sec_cb(struct sde_kms *sde_kms)
{
	u32 ret = 0;

	if (atomic_dec_return(&sde_kms->detach_sec_cb) != 0)
		goto end;

	ret = _sde_crtc_scm_call(VMID_CP_PIXEL);
	if (ret)
		goto end;

	ret = sde_kms_mmu_attach(sde_kms, true);
	if (ret) {
		SDE_ERROR("failed to attach sec cb ret:%d\n", ret);
		goto end;
	}

end:
	return ret;
}

/**
 * sde_crtc_secure_ctrl - Initiates the operations to swtich  between secure
 *                       and non-secure mode
@@ -2063,85 +2150,47 @@ int sde_crtc_secure_ctrl(struct drm_crtc *crtc, bool post_commit)
		/* Bail out */
		return 0;

	mutex_lock(&sde_kms->secure_transition_lock);
	/* Secure UI use case enable */
	switch (smmu_state->state) {
	case DETACH_ALL_REQ:
		/* detach_all_contexts */
		ret = sde_kms_mmu_detach(sde_kms, false);
		if (ret) {
			SDE_ERROR("crtc: %d, failed to detach %d\n",
					crtc->base.id, ret);
			goto error;
		}

		ret = _sde_crtc_scm_call(VMID_CP_SEC_DISPLAY);
		if (ret)
			goto error;

		ret = _sde_crtc_detach_all_cb(sde_kms);
		if (!ret)
			smmu_state->state = DETACHED;
		break;
	/* Secure UI use case disable */
	case ATTACH_ALL_REQ:
		ret = _sde_crtc_scm_call(VMID_CP_PIXEL);
		if (ret)
			goto error;

		/* attach_all_contexts */
		ret = sde_kms_mmu_attach(sde_kms, false);
		if (ret) {
			SDE_ERROR("crtc: %d, failed to attach %d\n",
					crtc->base.id,
					ret);
			goto error;
		}

		ret = _sde_crtc_attach_all_cb(sde_kms);
		if (!ret)
			smmu_state->state = ATTACHED;

		break;
	/* Secure preview enable */
	case DETACH_SEC_REQ:
		/* detach secure_context */
		ret = sde_kms_mmu_detach(sde_kms, true);
		if (ret) {
			SDE_ERROR("crtc: %d, failed to detach %d\n",
					crtc->base.id,
					ret);
			goto error;
		}

		ret = _sde_crtc_detach_sec_cb(sde_kms);
		if (!ret)
			smmu_state->state = DETACHED_SEC;
		ret = _sde_crtc_scm_call(VMID_CP_CAMERA_PREVIEW);
		if (ret)
			goto error;

		break;

	/* Secure preview disable */
	case ATTACH_SEC_REQ:
		ret = _sde_crtc_scm_call(VMID_CP_PIXEL);
		if (ret)
			goto error;

		ret = sde_kms_mmu_attach(sde_kms, true);
		if (ret) {
			SDE_ERROR("crtc: %d, failed to attach %d\n",
					crtc->base.id,
					ret);
			goto error;
		}
		ret = _sde_crtc_attach_sec_cb(sde_kms);
		if (!ret)
			smmu_state->state = ATTACHED;
		break;
	default:
		SDE_ERROR("crtc:%d invalid smmu state:%d transition type:%d\n",
			crtc->base.id, smmu_state->state,
			smmu_state->transition_type);
		break;
	}
	mutex_unlock(&sde_kms->secure_transition_lock);

	SDE_DEBUG("crtc: %d, old_state %d new_state %d\n", crtc->base.id,
			old_smmu_state,
			smmu_state->state);
	smmu_state->transition_type = NONE;

error:
	smmu_state->transition_type = NONE;
	smmu_state->transition_error = ret ? true : false;

	SDE_EVT32(DRMID(crtc), smmu_state->state, smmu_state->transition_type,
			smmu_state->transition_error, ret,
			SDE_EVTLOG_FUNC_EXIT);
+4 −0
Original line number Diff line number Diff line
@@ -3021,6 +3021,10 @@ static int sde_kms_hw_init(struct msm_kms *kms)
	dev->mode_config.max_width = sde_kms->catalog->max_display_width;
	dev->mode_config.max_height = sde_kms->catalog->max_display_height;

	mutex_init(&sde_kms->secure_transition_lock);
	atomic_set(&sde_kms->detach_sec_cb, 0);
	atomic_set(&sde_kms->detach_all_cb, 0);

	/*
	 * Support format modifiers for compression etc.
	 */
+5 −1
Original line number Diff line number Diff line
/*
 * Copyright (c) 2015-2017, The Linux Foundation. All rights reserved.
 * Copyright (c) 2015-2018, The Linux Foundation. All rights reserved.
 * Copyright (C) 2013 Red Hat
 * Author: Rob Clark <robdclark@gmail.com>
 *
@@ -226,6 +226,10 @@ struct sde_kms {
	void **dp_displays;

	bool has_danger_ctrl;

	atomic_t detach_sec_cb;
	atomic_t detach_all_cb;
	struct mutex secure_transition_lock;
};

struct vsync_info {