diff --git a/arch/arm/cpu/armv8/imx8/Makefile b/arch/arm/cpu/armv8/imx8/Makefile index eaf6614..5876633 100644 --- a/arch/arm/cpu/armv8/imx8/Makefile +++ b/arch/arm/cpu/armv8/imx8/Makefile @@ -9,4 +9,5 @@ obj-y += clock.o obj-y += fsl_mu_hal.o obj-y += fuse.o obj-y += iomux.o +obj-y += partition.o obj-$(CONFIG_VIDEO_IMXDPUV1) += video_common.o diff --git a/arch/arm/cpu/armv8/imx8/partition.c b/arch/arm/cpu/armv8/imx8/partition.c new file mode 100644 index 0000000..3d8547d --- /dev/null +++ b/arch/arm/cpu/armv8/imx8/partition.c @@ -0,0 +1,198 @@ +/* + * Copyright 2018 NXP. + * + * SPDX-License-Identifier: GPL-2.0+ + */ +#include +#include +#include +#include +#include +#include +#include +#include +#include + +DECLARE_GLOBAL_DATA_PTR; + +#define SC_MAX_PARTS 32 + +struct scu_rm_part_data { + bool used; + bool isolated; + bool restricted; + bool grant; + sc_rm_did_t did; + sc_rm_pt_t self; + sc_rm_pt_t parent; + char *name; +}; + +static struct scu_rm_part_data rm_part_data[SC_MAX_PARTS]; + +static int do_part_alloc(int argc, char * const argv[]) +{ + sc_rm_pt_t parent_part, os_part; + sc_ipc_t ipc_handle; + sc_err_t err; + int i; + bool restricted = false, isolated = false, grant = false; + + for (i = 0; i < SC_MAX_PARTS; i++) { + if (!rm_part_data[i].used) + break; + } + + if (i == SC_MAX_PARTS) { + puts("No empty slots\n"); + return CMD_RET_FAILURE; + } + + ipc_handle = gd->arch.ipc_channel_handle; + + err = sc_rm_get_partition(ipc_handle, &parent_part); + if (err != SC_ERR_NONE) { + puts("sc_rm_get_partition failure\n"); + return CMD_RET_FAILURE; + } + + isolated = simple_strtoul(argv[0], NULL, 10); + restricted = simple_strtoul(argv[1], NULL, 10); + grant = simple_strtoul(argv[2], NULL, 10); + /* Refine here */ + err = sc_rm_partition_alloc(ipc_handle, &os_part, false, isolated, + restricted, grant, false); + if (err != SC_ERR_NONE) { + printf("sc_rm_partition_alloc failure %d\n", err); + return CMD_RET_FAILURE; + } + + err = sc_rm_set_parent(ipc_handle, os_part, parent_part); + if (err != SC_ERR_NONE) { + sc_rm_partition_free(ipc_handle, os_part); + return CMD_RET_FAILURE; + } + + + rm_part_data[i].self = os_part; + rm_part_data[i].parent = parent_part; + rm_part_data[i].used = true; + rm_part_data[i].restricted = restricted; + rm_part_data[i].isolated = isolated; + rm_part_data[i].grant = grant; + + printf("%s: os_part, %d: parent_part, %d\n", __func__, os_part, + parent_part); + + return CMD_RET_SUCCESS; +} + +static int do_part_free(int argc, char * const argv[]) +{ + sc_rm_pt_t os_part; + sc_ipc_t ipc_handle; + sc_err_t err; + ipc_handle = gd->arch.ipc_channel_handle; + + if (argc == 0) + return CMD_RET_FAILURE; + + os_part = simple_strtoul(argv[0], NULL, 10); + + err = sc_rm_partition_free(ipc_handle, os_part); + if (err != SC_ERR_NONE) { + printf("free partiiton %d err %d\n", os_part, err); + return CMD_RET_FAILURE; + } + + rm_part_data[os_part].used = false; + + return CMD_RET_SUCCESS; +} + +static int do_resource_assign(int argc, char * const argv[]) +{ + sc_rm_pt_t os_part; + sc_ipc_t ipc_handle; + sc_err_t err; + sc_rsrc_t resource; + sc_pad_t pad; + int i, flag; + + ipc_handle = gd->arch.ipc_channel_handle; + + if (argc < 3) + return CMD_RET_FAILURE; + + os_part = simple_strtoul(argv[0], NULL, 10); + flag = simple_strtoul(argv[1], NULL, 10); + if (flag) + pad = simple_strtoul(argv[2], NULL, 10); + else + resource = simple_strtoul(argv[2], NULL, 10); + + for (i = 0; i < SC_MAX_PARTS; i++) { + if ((rm_part_data[i].self == os_part) && rm_part_data[i].used) + break; + } + + if (i == SC_MAX_PARTS) { + puts("Not valid partition\n"); + return CMD_RET_FAILURE; + } + + if (flag) + err = sc_rm_assign_pad(ipc_handle, os_part, pad); + else + err = sc_rm_assign_resource(ipc_handle, os_part, resource); + if (err != SC_ERR_NONE) { + printf("assign resource/pad error %d\n", err); + return CMD_RET_FAILURE; + } + + printf("%s: os_part, %d, %d\n", __func__, os_part, + flag ? pad : resource); + + return CMD_RET_SUCCESS; +} + +static int do_part_list(int argc, char * const argv[]) +{ + int i; + + for (i = 0; i < SC_MAX_PARTS; i++) { + if (rm_part_data[i].used) + printf("part id: %d %d\n", rm_part_data[i].self, + rm_part_data[i].parent); + } + + return CMD_RET_SUCCESS; +} + +static int do_scu_rm(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[]) +{ + if (argc < 2) + return CMD_RET_USAGE; + + if (!strcmp(argv[1], "alloc")) + return do_part_alloc(argc - 2, argv + 2); + if (!strcmp(argv[1], "free")) + return do_part_free(argc - 2, argv + 2); + else if (!strcmp(argv[1], "assign")) + return do_resource_assign(argc - 2, argv + 2); + else if (!strcmp(argv[1], "print")) + return do_part_list(argc - 2, argv + 2); + + return CMD_RET_USAGE; +} + +U_BOOT_CMD( + scu_rm, CONFIG_SYS_MAXARGS, 1, do_scu_rm, + "scu partition function", + "\n" + "scu_rm alloc [isolated] [restricted] [grant]\n" + "scu_rm free pt\n" + "scu_rm assign pt 0 resource\n" + "scu_rm assign pt 1 pad\n" + "scu_rm print\n" +);