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

Commit 1b5ee0f2 authored by Liam Mark's avatar Liam Mark
Browse files

ion : Expose ION API to query buffer VM information



Allow ION clients to be able to determine the VM information associated
with an ION buffer, such as the VMIDs it is assigned to as well as the
VM permissions.

Change-Id: Id0be0b505bc84beff373e4e2ae16b71ec4f09d43
Signed-off-by: default avatarLiam Mark <lmark@codeaurora.org>
parent 55cb9664
Loading
Loading
Loading
Loading
+12 −1
Original line number Diff line number Diff line
// SPDX-License-Identifier: GPL-2.0-only
/*
 * Copyright (C) 2011 Google, Inc
 * Copyright (c) 2011-2018, The Linux Foundation. All rights reserved.
 * Copyright (c) 2011-2019, The Linux Foundation. All rights reserved.
 */

#include <linux/highmem.h>
@@ -438,3 +438,14 @@ bool msm_secure_v2_is_supported(void)
	return (scm_get_feat_version(FEATURE_ID_CP) >=
			MAKE_CP_VERSION(1, 1, 0));
}

u32 msm_secure_get_vmid_perms(u32 vmid)
{
	if (vmid == VMID_CP_SEC_DISPLAY)
		return PERM_READ;
	else if (vmid == VMID_CP_CDSP)
		return PERM_READ | PERM_WRITE | PERM_EXEC;
	else
		return PERM_READ | PERM_WRITE;
}
EXPORT_SYMBOL(msm_secure_get_vmid_perms);
+24 −1
Original line number Diff line number Diff line
/* SPDX-License-Identifier: GPL-2.0-only */
/*
 * Copyright (c) 2018, The Linux Foundation. All rights reserved.
 * Copyright (c) 2018-2019, The Linux Foundation. All rights reserved.
 */

#ifndef _ION_KERNEL_H
#define _ION_KERNEL_H

#include <linux/dma-buf.h>
#include <linux/bitmap.h>
#include "../uapi/ion.h"
#include "../uapi/msm_ion.h"

#ifdef CONFIG_ION

@@ -18,6 +20,16 @@
struct dma_buf *ion_alloc(size_t len, unsigned int heap_id_mask,
			  unsigned int flags);

static inline unsigned int ion_get_flags_num_vm_elems(unsigned int flags)
{
	unsigned long vm_flags = flags & ION_FLAGS_CP_MASK;

	return ((unsigned int)bitmap_weight(&vm_flags, BITS_PER_LONG));
}

int ion_populate_vm_list(unsigned long flags, unsigned int *vm_list,
			 int nelems);

#else

static inline struct dma_buf *ion_alloc(size_t len, unsigned int heap_id_mask,
@@ -26,5 +38,16 @@ static inline struct dma_buf *ion_alloc(size_t len, unsigned int heap_id_mask,
	return -ENOMEM;
}

static inline unsigned int ion_get_flags_num_vm_elems(unsigned int flags)
{
	return 0;
}

static inline int ion_populate_vm_list(unsigned long flags,
				       unsigned int *vm_list, int nelems)
{
	return -EINVAL;
}

#endif /* CONFIG_ION */
#endif /* _ION_KERNEL_H */
+8 −19
Original line number Diff line number Diff line
@@ -70,7 +70,7 @@ static int get_vmid(unsigned long flags)
	return vmid;
}

static int populate_vm_list(unsigned long flags, unsigned int *vm_list,
int ion_populate_vm_list(unsigned long flags, unsigned int *vm_list,
			 int nelems)
{
	unsigned int itr = 0;
@@ -148,14 +148,8 @@ int ion_hyp_assign_sg(struct sg_table *sgt, int *dest_vm_list,
		goto out;
	}

	for (i = 0; i < dest_nelems; i++) {
		if (dest_vm_list[i] == VMID_CP_SEC_DISPLAY)
			dest_perms[i] = PERM_READ;
		else if (dest_vm_list[i] == VMID_CP_CDSP)
			dest_perms[i] = PERM_READ | PERM_WRITE | PERM_EXEC;
		else
			dest_perms[i] = PERM_READ | PERM_WRITE;
	}
	for (i = 0; i < dest_nelems; i++)
		dest_perms[i] = msm_secure_get_vmid_perms(dest_vm_list[i]);

	ret = hyp_assign_table(sgt, &source_vmid, 1,
			       dest_vm_list, dest_perms, dest_nelems);
@@ -187,7 +181,7 @@ int ion_hyp_unassign_sg_from_flags(struct sg_table *sgt, unsigned long flags,
				 GFP_KERNEL);
	if (!source_vm_list)
		return -ENOMEM;
	ret = populate_vm_list(flags, source_vm_list, source_nelems);
	ret = ion_populate_vm_list(flags, source_vm_list, source_nelems);
	if (ret) {
		pr_err("%s: Failed to get secure vmids\n", __func__);
		goto out_free_source;
@@ -215,7 +209,7 @@ int ion_hyp_assign_sg_from_flags(struct sg_table *sgt, unsigned long flags,
		goto out;
	}

	ret = populate_vm_list(flags, dest_vm_list, dest_nelems);
	ret = ion_populate_vm_list(flags, dest_vm_list, dest_nelems);
	if (ret) {
		pr_err("%s: Failed to get secure vmid(s)\n", __func__);
		goto out_free_dest_vm;
@@ -263,19 +257,14 @@ int ion_hyp_assign_from_flags(u64 base, u64 size, unsigned long flags)
	}

	if ((flags & ~ION_FLAGS_CP_MASK) ||
	    populate_vm_list(flags, vmids, nr)) {
	    ion_populate_vm_list(flags, vmids, nr)) {
		pr_err("%s: Failed to parse secure flags 0x%lx\n", __func__,
		       flags);
		goto out;
	}

	for (i = 0; i < nr; i++)
		if (vmids[i] == VMID_CP_SEC_DISPLAY)
			modes[i] = PERM_READ;
		else if (vmids[i] == VMID_CP_CDSP)
			modes[i] = PERM_READ | PERM_WRITE | PERM_EXEC;
		else
			modes[i] = PERM_READ | PERM_WRITE;
		modes[i] = msm_secure_get_vmid_perms(vmids[i]);

	ret = hyp_assign_phys(base, size, &src_vm, 1, vmids, modes, nr);
	if (ret)
+9 −1
Original line number Diff line number Diff line
/* SPDX-License-Identifier: GPL-2.0-only */
/*
 * Copyright (c) 2015-2018, The Linux Foundation. All rights reserved.
 * Copyright (c) 2015-2019, The Linux Foundation. All rights reserved.
 */

#ifndef __QCOM_SECURE_BUFFER_H__
@@ -59,6 +59,8 @@ extern int hyp_assign_phys(phys_addr_t addr, u64 size,
			int *dest_vmids, int *dest_perms, int dest_nelems);
bool msm_secure_v2_is_supported(void);
const char *msm_secure_vmid_to_string(int secure_vmid);
u32 msm_secure_get_vmid_perms(u32 vmid);

#else
static inline int msm_secure_table(struct sg_table *table)
{
@@ -102,5 +104,11 @@ static inline const char *msm_secure_vmid_to_string(int secure_vmid)
{
	return "N/A";
}

static inline u32 msm_secure_get_vmid_perms(u32 vmid)
{
	return 0;
}

#endif
#endif