• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2018, ARM Limited and Contributors. All rights reserved.
3  *
4  * SPDX-License-Identifier: BSD-3-Clause
5  */
6 
7 #include <arch.h>
8 #include <arch_helpers.h>
9 #include <assert.h>
10 #include <common/bl_common.h>
11 #include <common/debug.h>
12 #include <common/runtime_svc.h>
13 #include <errno.h>
14 #include <lib/mmio.h>
15 #include <lib/utils_def.h>
16 
17 #include <memctrl.h>
18 #include <pmc.h>
19 #include <tegra_private.h>
20 #include <tegra_platform.h>
21 #include <tegra_def.h>
22 
23 /*******************************************************************************
24  * PMC parameters
25  ******************************************************************************/
26 #define PMC_READ 			U(0xaa)
27 #define PMC_WRITE 			U(0xbb)
28 
29 /*******************************************************************************
30  * Tegra210 SiP SMCs
31  ******************************************************************************/
32 #define TEGRA_SIP_PMC_COMMANDS		U(0xC2FFFE00)
33 
34 /*******************************************************************************
35  * This function is responsible for handling all T210 SiP calls
36  ******************************************************************************/
plat_sip_handler(uint32_t smc_fid,uint64_t x1,uint64_t x2,uint64_t x3,uint64_t x4,const void * cookie,void * handle,uint64_t flags)37 int plat_sip_handler(uint32_t smc_fid,
38 		     uint64_t x1,
39 		     uint64_t x2,
40 		     uint64_t x3,
41 		     uint64_t x4,
42 		     const void *cookie,
43 		     void *handle,
44 		     uint64_t flags)
45 {
46 	uint32_t val, ns;
47 
48 	/* Determine which security state this SMC originated from */
49 	ns = is_caller_non_secure(flags);
50 	if (!ns)
51 		SMC_RET1(handle, SMC_UNK);
52 
53 	switch (smc_fid) {
54 	case TEGRA_SIP_PMC_COMMANDS:
55 
56 		/* check the address is within PMC range and is 4byte aligned */
57 		if ((x2 >= TEGRA_PMC_SIZE) || (x2 & 0x3))
58 			return -EINVAL;
59 
60 		/* pmc_secure_scratch registers are not accessible */
61 		if (((x2 >= PMC_SECURE_SCRATCH0) && (x2 <= PMC_SECURE_SCRATCH5)) ||
62 		    ((x2 >= PMC_SECURE_SCRATCH6) && (x2 <= PMC_SECURE_SCRATCH7)) ||
63 		    ((x2 >= PMC_SECURE_SCRATCH8) && (x2 <= PMC_SECURE_SCRATCH79)) ||
64 		    ((x2 >= PMC_SECURE_SCRATCH80) && (x2 <= PMC_SECURE_SCRATCH119)))
65 				return -EFAULT;
66 
67 		/* PMC secure-only registers are not accessible */
68 		if ((x2 == PMC_DPD_ENABLE_0) || (x2 == PMC_FUSE_CONTROL_0) ||
69 		    (x2 == PMC_CRYPTO_OP_0))
70 			return -EFAULT;
71 
72 		/* Perform PMC read/write */
73 		if (x1 == PMC_READ) {
74 			val = mmio_read_32((uint32_t)(TEGRA_PMC_BASE + x2));
75 			write_ctx_reg(get_gpregs_ctx(handle), CTX_GPREG_X1, val);
76 		} else if (x1 == PMC_WRITE) {
77 			mmio_write_32((uint32_t)(TEGRA_PMC_BASE + x2), (uint32_t)x3);
78 		} else {
79 			return -EINVAL;
80 		}
81 
82 		break;
83 
84 	default:
85 		ERROR("%s: unsupported function ID\n", __func__);
86 		return -ENOTSUP;
87 	}
88 
89 	return 0;
90 }
91