1 /* 2 * Copyright (c) 2016-2019, ARM Limited and Contributors. All rights reserved. 3 * 4 * SPDX-License-Identifier: BSD-3-Clause 5 */ 6 7 #include <stdio.h> 8 9 #include <common/debug.h> 10 #include <common/runtime_svc.h> 11 #include <platform_def.h> 12 13 #include "generic-arm64-smcall.h" 14 15 #ifndef PLAT_ARM_GICD_BASE 16 #ifdef GICD_BASE 17 #define PLAT_ARM_GICD_BASE GICD_BASE 18 #define PLAT_ARM_GICC_BASE GICC_BASE 19 #ifdef GICR_BASE 20 #define PLAT_ARM_GICR_BASE GICR_BASE 21 #endif 22 #else 23 #error PLAT_ARM_GICD_BASE or GICD_BASE must be defined 24 #endif 25 #endif 26 27 #ifndef PLAT_ARM_GICR_BASE 28 #define PLAT_ARM_GICR_BASE SMC_UNK 29 #endif 30 31 int trusty_disable_serial_debug; 32 33 struct dputc_state { 34 char linebuf[128]; 35 unsigned l; 36 }; 37 38 static struct dputc_state dputc_state[2]; 39 40 static void trusty_dputc(char ch, int secure) 41 { 42 unsigned i; 43 struct dputc_state *s = &dputc_state[!secure]; 44 45 if (trusty_disable_serial_debug) 46 return; 47 48 s->linebuf[s->l++] = ch; 49 if (s->l == sizeof(s->linebuf) || ch == '\n') { 50 if (secure) 51 printf("secure os: "); 52 else 53 printf("non-secure os: "); 54 for (i = 0; i < s->l; i++) { 55 putchar(s->linebuf[i]); 56 } 57 if (ch != '\n') { 58 printf(" <...>\n"); 59 } 60 s->l = 0; 61 } 62 } 63 64 static uint64_t trusty_get_reg_base(uint32_t reg) 65 { 66 switch (reg) { 67 case SMC_GET_GIC_BASE_GICD: 68 return PLAT_ARM_GICD_BASE; 69 70 case SMC_GET_GIC_BASE_GICC: 71 return PLAT_ARM_GICC_BASE; 72 73 case SMC_GET_GIC_BASE_GICR: 74 return PLAT_ARM_GICR_BASE; 75 76 default: 77 NOTICE("%s(0x%x) unknown reg\n", __func__, reg); 78 return SMC_UNK; 79 } 80 } 81 82 static uintptr_t trusty_generic_platform_smc(uint32_t smc_fid, 83 u_register_t x1, 84 u_register_t x2, 85 u_register_t x3, 86 u_register_t x4, 87 void *cookie, 88 void *handle, 89 u_register_t flags) 90 { 91 switch (smc_fid) { 92 case SMC_FC_DEBUG_PUTC: 93 trusty_dputc(x1, is_caller_secure(flags)); 94 SMC_RET1(handle, 0); 95 96 case SMC_FC_GET_REG_BASE: 97 case SMC_FC64_GET_REG_BASE: 98 SMC_RET1(handle, trusty_get_reg_base(x1)); 99 100 default: 101 NOTICE("%s(0x%x, 0x%lx) unknown smc\n", __func__, smc_fid, x1); 102 SMC_RET1(handle, SMC_UNK); 103 } 104 } 105 106 /* Define a SPD runtime service descriptor for fast SMC calls */ 107 DECLARE_RT_SVC( 108 trusty_fast, 109 110 SMC_ENTITY_PLATFORM_MONITOR, 111 SMC_ENTITY_PLATFORM_MONITOR, 112 SMC_TYPE_FAST, 113 NULL, 114 trusty_generic_platform_smc 115 ); 116 117