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

Commit 58b70eb4 authored by Harshdeep Dhatt's avatar Harshdeep Dhatt Committed by Tarun Karra
Browse files

msm: kgsl: Add secure preemption support for A6XX



Allocate the secure preemption buffers and add their addresses
in preemption packets in order to preempt secure contexts.

Change-Id: I4cd21748a8e3f95b0e69e96919a66c735b98664d
Signed-off-by: default avatarHarshdeep Dhatt <hdhatt@codeaurora.org>
parent 1f40833f
Loading
Loading
Loading
Loading
+2 −1
Original line number Diff line number Diff line
@@ -822,7 +822,8 @@ static int _preemption_init(struct adreno_device *adreno_dev,
			rb->preemption_desc.gpuaddr);

	*cmds++ = 2;
	cmds += cp_gpuaddr(adreno_dev, cmds, 0);
	cmds += cp_gpuaddr(adreno_dev, cmds,
			rb->secure_preemption_desc.gpuaddr);

	/* Turn CP protection ON */
	*cmds++ = cp_type7_packet(CP_SET_PROTECTED_MODE, 1);
+31 −2
Original line number Diff line number Diff line
@@ -332,6 +332,16 @@ void a6xx_preemption_trigger(struct adreno_device *adreno_dev)
		upper_32_bits(next->preemption_desc.gpuaddr),
		FENCE_STATUS_WRITEDROPPED1_MASK);

	adreno_gmu_fenced_write(adreno_dev,
		ADRENO_REG_CP_CONTEXT_SWITCH_PRIV_SECURE_RESTORE_ADDR_LO,
		lower_32_bits(next->secure_preemption_desc.gpuaddr),
		FENCE_STATUS_WRITEDROPPED1_MASK);

	adreno_gmu_fenced_write(adreno_dev,
		ADRENO_REG_CP_CONTEXT_SWITCH_PRIV_SECURE_RESTORE_ADDR_HI,
		upper_32_bits(next->secure_preemption_desc.gpuaddr),
		FENCE_STATUS_WRITEDROPPED1_MASK);

	adreno_gmu_fenced_write(adreno_dev,
		ADRENO_REG_CP_CONTEXT_SWITCH_NON_PRIV_RESTORE_ADDR_LO,
		lower_32_bits(gpuaddr),
@@ -472,7 +482,8 @@ unsigned int a6xx_preemption_pre_ibsubmit(
	cmds += cp_gpuaddr(adreno_dev, cmds, rb->preemption_desc.gpuaddr);

	*cmds++ = SET_PSEUDO_REGISTER_SAVE_REGISTER_PRIV_SECURE_SAVE_ADDR;
	cmds += cp_gpuaddr(adreno_dev, cmds, 0);
	cmds += cp_gpuaddr(adreno_dev, cmds,
			rb->secure_preemption_desc.gpuaddr);

	if (context) {

@@ -591,6 +602,17 @@ static int a6xx_preemption_ringbuffer_init(struct adreno_device *adreno_dev,
	if (ret)
		return ret;

	ret = kgsl_allocate_user(device, &rb->secure_preemption_desc,
		A6XX_CP_CTXRECORD_SIZE_IN_BYTES,
		KGSL_MEMFLAGS_SECURE | KGSL_MEMDESC_PRIVILEGED);
	if (ret)
		return ret;

	ret = kgsl_iommu_map_global_secure_pt_entry(device,
				&rb->secure_preemption_desc);
	if (ret)
		return ret;

	ret = kgsl_allocate_global(device, &rb->perfcounter_save_restore_desc,
		A6XX_CP_PERFCOUNTER_SAVE_RESTORE_SIZE, 0,
		KGSL_MEMDESC_PRIVILEGED, "perfcounter_save_restore_desc");
@@ -664,6 +686,9 @@ static void a6xx_preemption_close(struct kgsl_device *device)
	FOR_EACH_RINGBUFFER(adreno_dev, rb, i) {
		kgsl_free_global(device, &rb->preemption_desc);
		kgsl_free_global(device, &rb->perfcounter_save_restore_desc);
		kgsl_iommu_unmap_global_secure_pt_entry(device,
				&rb->secure_preemption_desc);
		kgsl_sharedmem_free(&rb->secure_preemption_desc);
	}
}

@@ -731,16 +756,20 @@ int a6xx_preemption_context_init(struct kgsl_context *context)
{
	struct kgsl_device *device = context->device;
	struct adreno_device *adreno_dev = ADRENO_DEVICE(device);
	uint64_t flags = 0;

	if (!adreno_is_preemption_setup_enabled(adreno_dev))
		return 0;

	if (context->flags & KGSL_CONTEXT_SECURE)
		flags |= KGSL_MEMFLAGS_SECURE;

	/*
	 * gpumem_alloc_entry takes an extra refcount. Put it only when
	 * destroying the context to keep the context record valid
	 */
	context->user_ctxt_record = gpumem_alloc_entry(context->dev_priv,
			A6XX_CP_CTXRECORD_USER_RESTORE_SIZE, 0);
			A6XX_CP_CTXRECORD_USER_RESTORE_SIZE, flags);
	if (IS_ERR(context->user_ctxt_record)) {
		int ret = PTR_ERR(context->user_ctxt_record);

+3 −0
Original line number Diff line number Diff line
@@ -92,6 +92,8 @@ struct adreno_ringbuffer_pagetable_info {
 * @drawctxt_active: The last pagetable that this ringbuffer is set to
 * @preemption_desc: The memory descriptor containing
 * preemption info written/read by CP
 * @secure_preemption_desc: The memory descriptor containing
 * preemption info written/read by CP for secure contexts
 * @perfcounter_save_restore_desc: Used by CP to save/restore the perfcounter
 * values across preemption
 * @pagetable_desc: Memory to hold information about the pagetables being used
@@ -120,6 +122,7 @@ struct adreno_ringbuffer {
	struct kgsl_event_group events;
	struct adreno_context *drawctxt_active;
	struct kgsl_memdesc preemption_desc;
	struct kgsl_memdesc secure_preemption_desc;
	struct kgsl_memdesc perfcounter_save_restore_desc;
	struct kgsl_memdesc pagetable_desc;
	struct adreno_dispatcher_drawqueue dispatch_q;