Commit 4c158b9a7d05973e6924835726a2358b383d622f

Authored by Harinarayan Bhatta
Committed by Tom Rini
1 parent 7e719ee7d8

arm: omap5: Add function to make an SMC call on cpu1

On DRA7xx platform, CPU Core 1 is not used in u-boot. However, in some
cases it is need to make secure API calls from Core 1. This patch adds
an assembly function to make a secure (SMC) call from CPU Core #1.

Signed-off-by: Harinarayan Bhatta <harinarayan@ti.com>
Signed-off-by: Andrew F. Davis <afd@ti.com>
Reviewed-by: Tom Rini <trini@konsulko.com>

Showing 3 changed files with 125 additions and 0 deletions Side-by-side Diff

arch/arm/include/asm/omap_common.h
... ... @@ -632,6 +632,7 @@
632 632 * security (HS) device variants by doing a specially-formed smc entry.
633 633 */
634 634 u32 omap_smc_sec(u32 service, u32 proc_id, u32 flag, u32 *params);
  635 +u32 omap_smc_sec_cpu1(u32 service, u32 proc_id, u32 flag, u32 *params);
635 636  
636 637 void enable_edma3_clocks(void);
637 638 void disable_edma3_clocks(void);
arch/arm/mach-omap2/omap5/Makefile
... ... @@ -15,4 +15,5 @@
15 15 obj-y += fdt.o
16 16 obj-$(CONFIG_IODELAY_RECALIBRATION) += dra7xx_iodelay.o
17 17 obj-$(CONFIG_TI_SECURE_DEVICE) += sec-fxns.o
  18 +obj-$(CONFIG_DRA7XX) += sec_entry_cpu1.o
arch/arm/mach-omap2/omap5/sec_entry_cpu1.S
  1 +/*
  2 + * Secure entry function for CPU Core #1
  3 + *
  4 + * (C) Copyright 2016
  5 + * Texas Instruments, <www.ti.com>
  6 + *
  7 + * Author :
  8 + * Harinarayan Bhatta <harinarayan@ti.com>
  9 + *
  10 + * SPDX-License-Identifier: GPL-2.0+
  11 + */
  12 +
  13 +#include <config.h>
  14 +#include <asm/arch/omap.h>
  15 +#include <asm/omap_common.h>
  16 +#include <linux/linkage.h>
  17 +
  18 +.arch_extension sec
  19 +
  20 +#if !defined(CONFIG_SYS_DCACHE_OFF)
  21 +.global flush_dcache_range
  22 +#endif
  23 +
  24 +#define AUX_CORE_BOOT_0 0x48281800
  25 +#define AUX_CORE_BOOT_1 0x48281804
  26 +
  27 +#ifdef CONFIG_DRA7XX
  28 +/* DRA7xx ROM code function "startup_BootSlave". This function is where CPU1
  29 + * waits on WFE, polling on AUX_CORE_BOOT_x registers.
  30 + * This address is same for J6 and J6 Eco.
  31 + */
  32 +#define ROM_FXN_STARTUP_BOOTSLAVE 0x00038a64
  33 +#endif
  34 +
  35 +/* Assembly core where CPU1 is woken up into
  36 + * No need to save-restore registers, does not use stack.
  37 + */
  38 +LENTRY(cpu1_entry)
  39 + ldr r4, =omap_smc_sec_cpu1_args
  40 + ldm r4, {r0,r1,r2,r3} @ Retrieve args
  41 +
  42 + mov r6, #0xFF @ Indicate new Task call
  43 + mov r12, #0x00 @ Secure Service ID in R12
  44 +
  45 + dsb
  46 + dmb
  47 + smc 0 @ SMC #0 to enter monitor mode
  48 +
  49 + b .Lend @ exit at end of the service execution
  50 + nop
  51 +
  52 + @ In case of IRQ happening in Secure, then ARM will branch here.
  53 + @ At that moment, IRQ will be pending and ARM will jump to Non Secure
  54 + @ IRQ handler
  55 + mov r12, #0xFE
  56 +
  57 + dsb
  58 + dmb
  59 + smc 0 @ SMC #0 to enter monitor mode
  60 +
  61 +.Lend:
  62 + ldr r4, =omap_smc_sec_cpu1_args
  63 + str r0, [r4, #0x10] @ save return value
  64 + ldr r4, =AUX_CORE_BOOT_0
  65 + mov r5, #0x0
  66 + str r5, [r4]
  67 + ldr r4, =ROM_FXN_STARTUP_BOOTSLAVE
  68 + sev @ Tell CPU0 we are done
  69 + bx r4 @ Jump back to ROM
  70 +END(cpu1_entry)
  71 +
  72 +/*
  73 + * u32 omap_smc_sec_cpu1(u32 service, u32 proc_id, u32 flag, u32 *params);
  74 + *
  75 + * Makes a secure ROM/PPA call on CPU Core #1 on supported platforms.
  76 + * Assumes that CPU #1 is waiting in ROM code and not yet woken up or used by
  77 + * u-boot.
  78 + */
  79 +ENTRY(omap_smc_sec_cpu1)
  80 + push {r4, r5, lr}
  81 + ldr r4, =omap_smc_sec_cpu1_args
  82 + stm r4, {r0,r1,r2,r3} @ Save args to memory
  83 +#if !defined(CONFIG_SYS_DCACHE_OFF)
  84 + mov r0, r4
  85 + mov r1, #CONFIG_SYS_CACHELINE_SIZE
  86 + add r1, r0, r1 @ dcache is not enabled on CPU1, so
  87 + blx flush_dcache_range @ flush the cache on args buffer
  88 +#endif
  89 + ldr r4, =AUX_CORE_BOOT_1
  90 + ldr r5, =cpu1_entry
  91 + str r5, [r4] @ Setup CPU1 entry function
  92 + ldr r4, =AUX_CORE_BOOT_0
  93 + mov r5, #0x10
  94 + str r5, [r4] @ Tell ROM to exit while loop
  95 + sev @ Wake up CPU1
  96 +.Lwait:
  97 + wfe @ Wait for CPU1 to finish
  98 + nop
  99 + ldr r5, [r4] @ Check if CPU1 is done
  100 + cmp r5, #0
  101 + bne .Lwait
  102 +
  103 + ldr r4, =omap_smc_sec_cpu1_args
  104 + ldr r0, [r4, #0x10] @ Retrieve return value
  105 + pop {r4, r5, pc}
  106 +ENDPROC(omap_smc_sec_cpu1)
  107 +
  108 +/*
  109 + * Buffer to save function arguments and return value for omap_smc_sec_cpu1
  110 + */
  111 +.section .data
  112 +omap_smc_sec_cpu1_args:
  113 +#if !defined(CONFIG_SYS_DCACHE_OFF)
  114 + .balign CONFIG_SYS_CACHELINE_SIZE
  115 + .rept CONFIG_SYS_CACHELINE_SIZE/4
  116 + .word 0
  117 + .endr
  118 +#else
  119 + .rept 5
  120 + .word 0
  121 + .endr
  122 +#endif
  123 +END(omap_smc_sec_cpu1_args)