tlk: 10/24 update
Dennis Huang [Fri, 10 Oct 2014 23:37:10 +0000 (16:37 -0700)]
- Improve resource releasing when unloading tasks.
- Support task update
- pass tsec carveout base/size via argc/argv to hdcp_service
- PSCI support for CPU suspend/on/off
- stage T132 AARCH64 trampoline code
- Fix dependencies
- handle T132 trampoline to AARCH64
- add support for public vs. TA login type
- improve VPR region checking
- enable non-priv access to CNTVCT
- add version support
- Check GPU reset before resizing VPR
- add persistent membuf param support
- align syscalls and TA setup to new libc
- support for new secure storage protocol
- Remove lib/monitor, old arch code, and p/t/monitor
- Build tos.img from external monitor bin/lib
- Split up platform_p.h into extra headers
- fix 64-bit address usage during memmap
- cleanup mem map handling
- Flush the task mem region from cache before starting it.
- Deal with the 8 bit range of context_id value.
- use SMC_TOS_PREEMPT_BY_IRQ for interrupt handling
- use SMC_TOS_PREEMPT_BY_FS for SS
- add tsec service.
- platform: tegra: common: fix timer name

Change-Id: I4791508e1e8b25b5781880acd5cb3e60c0dea2d0
Reviewed-on: http://git-master/r/563017
Reviewed-by: Automatic_Commit_Validation_User
Reviewed-by: Dennis Huang <denhuang@nvidia.com>
Tested-by: Dennis Huang <denhuang@nvidia.com>

114 files changed:
Android.mk
README
arch/arm/arm/arch.c
arch/arm/arm/mmu.c
arch/arm/arm/mmu_ldesc.c
arch/arm/arm/mmu_sdesc.c
arch/arm/arm/task.c
arch/arm/include/arch/arm/cache-l2x0.h [new file with mode: 0644]
arch/arm/include/arch/arm/mmu.h
arch/arm/rules.mk
build [new file with mode: 0755]
include/arch/task.h
include/kernel/boot_params.h
include/kernel/task.h
include/lib/monitor/monitor_vector.h
include/lib/ote/ote_protocol.h
include/malloc.h
kernel/boot.c
kernel/ote_intf.c
kernel/syscall.c
kernel/task.c
kernel/task_load.c
kernel/task_unload.c
lib/libc/malloc.c
lib/monitor/arm64/monitor_cpu.S [deleted file]
lib/version/rules.mk [new file with mode: 0644]
lib/version/version.c [new file with mode: 0644]
lib/version/version.mk [new file with mode: 0644]
make/build.mk
makefile
platform/tegra/common/boot_secondary.S
platform/tegra/common/interrupts.c
platform/tegra/common/platform.c
platform/tegra/common/pm.c
platform/tegra/common/timer.c
platform/tegra/common/tz.c
platform/tegra/include/platform/memmap.h
platform/tegra/include/platform/platform_cpu.h [copied from platform/tegra/tegra3/tz.c with 64% similarity]
platform/tegra/include/platform/platform_p.h
platform/tegra/include/platform/platform_ta.h [copied from platform/tegra/tegra3/tz.c with 64% similarity]
platform/tegra/include/platform/platform_tos.h [copied from platform/tegra/tegra3/tz.c with 64% similarity]
platform/tegra/rules.mk
platform/tegra/tegra3/platform.c [deleted file]
platform/tegra/tegra3/rules.mk [deleted file]
platform/tegra/tegra4/platform.c
secure_monitor/Android.mk [new file with mode: 0644]
secure_monitor/arch/arm/include/arch/arm.h [new file with mode: 0644]
secure_monitor/arch/arm/include/arch/arm/ops.h [new file with mode: 0644]
secure_monitor/arch/arm/include/arch/defines.h [copied from platform/tegra/tegra3/tz.c with 64% similarity]
secure_monitor/arch/arm/rules.mk [new file with mode: 0644]
secure_monitor/build/Makefile.package [new file with mode: 0644]
secure_monitor/build/Makefile.secure_monitor [new file with mode: 0644]
secure_monitor/include/arch/ops.h [new file with mode: 0644]
secure_monitor/include/asm.h [copied from platform/tegra/tegra3/tz.c with 64% similarity]
secure_monitor/include/assert.h [copied from platform/tegra/tegra3/tz.c with 65% similarity]
secure_monitor/include/compiler.h [new file with mode: 0644]
secure_monitor/include/debug.h [new file with mode: 0644]
secure_monitor/include/endian.h [new file with mode: 0644]
secure_monitor/include/err.h [copied from lib/monitor/arm64/include/psci.h with 55% similarity]
secure_monitor/include/lib/monitor/monitor_vector.h [new file with mode: 0644]
secure_monitor/include/malloc.h [copied from platform/tegra/tegra3/tz.c with 64% similarity]
secure_monitor/include/platform.h [copied from lib/monitor/common/debug.c with 54% similarity]
secure_monitor/include/platform/debug.h [copied from platform/tegra/tegra3/tz.c with 64% similarity]
secure_monitor/include/platform/interrupts.h [copied from platform/tegra/tegra3/tz.c with 64% similarity]
secure_monitor/include/printf.h [copied from lib/monitor/common/debug.c with 52% similarity]
secure_monitor/include/reg.h [copied from lib/monitor/arm64/include/psci.h with 52% similarity]
secure_monitor/include/stdbool.h [copied from platform/tegra/tegra3/tz.c with 64% similarity]
secure_monitor/include/stddef.h [copied from platform/tegra/tegra3/tz.c with 64% similarity]
secure_monitor/include/stdint.h [copied from lib/monitor/arm64/include/psci.h with 51% similarity]
secure_monitor/include/stdlib.h [copied from lib/monitor/arm64/include/psci.h with 59% similarity]
secure_monitor/include/string.h [new file with mode: 0644]
secure_monitor/include/sys/types.h [new file with mode: 0644]
secure_monitor/lib/libc/string/arch/arm/rules.mk [new file with mode: 0644]
secure_monitor/lib/monitor/arm64/cache_helpers.S [new file with mode: 0644]
secure_monitor/lib/monitor/arm64/include/arm64/asm.h [moved from lib/monitor/arm64/include/arm64/asm.h with 90% similarity]
secure_monitor/lib/monitor/arm64/include/arm64/mmu_ldesc.h [moved from lib/monitor/arm64/include/arm64/mmu_ldesc.h with 100% similarity]
secure_monitor/lib/monitor/arm64/include/arm64/monitor_macros.h [moved from lib/monitor/arm64/include/arm64/monitor_macros.h with 100% similarity]
secure_monitor/lib/monitor/arm64/include/psci.h [moved from lib/monitor/arm64/include/psci.h with 72% similarity]
secure_monitor/lib/monitor/arm64/monitor-onesegment.ld [moved from lib/monitor/arm64/monitor-onesegment.ld with 100% similarity]
secure_monitor/lib/monitor/arm64/monitor_cpu.S [new file with mode: 0644]
secure_monitor/lib/monitor/arm64/monitor_fastcall.S [moved from lib/monitor/arm64/monitor_fastcall.S with 97% similarity]
secure_monitor/lib/monitor/arm64/monitor_lib.S [moved from lib/monitor/arm64/monitor_lib.S with 92% similarity]
secure_monitor/lib/monitor/arm64/monitor_mmu.S [moved from lib/monitor/arm64/monitor_mmu.S with 99% similarity]
secure_monitor/lib/monitor/arm64/monitor_start.S [moved from lib/monitor/arm64/monitor_start.S with 81% similarity]
secure_monitor/lib/monitor/arm64/monitor_vector.S [copied from lib/monitor/arm64/monitor_vector.S with 51% similarity]
secure_monitor/lib/monitor/arm64/secure_callback.S [moved from lib/monitor/arm64/monitor_vector.S with 64% similarity]
secure_monitor/lib/monitor/common/debug.c [moved from lib/monitor/common/debug.c with 100% similarity]
secure_monitor/lib/monitor/common/printf.c [moved from lib/monitor/common/printf.c with 100% similarity]
secure_monitor/lib/monitor/rules.mk [moved from lib/monitor/rules.mk with 77% similarity]
secure_monitor/make/build.mk [new file with mode: 0644]
secure_monitor/make/compile.mk [new file with mode: 0644]
secure_monitor/make/macros.mk [new file with mode: 0644]
secure_monitor/make/module.mk [new file with mode: 0644]
secure_monitor/makefile [new file with mode: 0644]
secure_monitor/platform/rules.mk [new file with mode: 0644]
secure_monitor/platform/tegra/include/platform/memmap.h [new file with mode: 0644]
secure_monitor/platform/tegra/include/platform/platform_monitor.h [copied from platform/tegra/tegra3/tz.c with 64% similarity]
secure_monitor/platform/tegra/include/platform/platform_sip.h [copied from platform/tegra/tegra3/tz.c with 64% similarity]
secure_monitor/platform/tegra/include/platform/tegra4/memmap_ext.h [copied from platform/tegra/tegra3/tz.c with 68% similarity]
secure_monitor/platform/tegra/monitor/debug.c [moved from platform/tegra/monitor/debug.c with 100% similarity]
secure_monitor/platform/tegra/monitor/interrupts.c [moved from platform/tegra/monitor/interrupts.c with 88% similarity]
secure_monitor/platform/tegra/monitor/memory.c [moved from platform/tegra/monitor/memory.c with 79% similarity]
secure_monitor/platform/tegra/monitor/platform.c [moved from platform/tegra/monitor/platform.c with 82% similarity]
secure_monitor/platform/tegra/monitor/platform_psci.c [new file with mode: 0644]
secure_monitor/platform/tegra/monitor/psci.c [moved from platform/tegra/monitor/psci.c with 67% similarity]
secure_monitor/platform/tegra/monitor/rules.mk [moved from platform/tegra/monitor/rules.mk with 86% similarity]
secure_monitor/platform/tegra/rules.mk [new file with mode: 0644]
secure_monitor/platform/tegra/tegra4/rules.mk [new file with mode: 0644]
secure_monitor/target/t124/include/target/debugconfig.h [copied from platform/tegra/tegra3/tz.c with 64% similarity]
secure_monitor/target/t124/rules.mk [new file with mode: 0644]
secure_monitor/target/t132/include/target/debugconfig.h [moved from platform/tegra/tegra3/tz.c with 64% similarity]
secure_monitor/target/t132/rules.mk [new file with mode: 0644]
secure_monitor/tools/gen_tos_part_img.py [new file with mode: 0755]
target/t132/rules.mk

index fd3fc16..97f8c68 100644 (file)
 
 # Define module tlk.
 # tlk: Compile the tlk kernel and generate tos.img.
-
 ifeq (tlk,$(SECURE_OS_BUILD))
 
+# tos.img is considered to be 32-bit
+ifneq (,$(TARGET_2ND_ARCH))
+LOCAL_2ND_ARCH_VAR_PREFIX := $(TARGET_2ND_ARCH_VAR_PREFIX)
+endif
+
+ifeq (t124,$(TARGET_TEGRA_VERSION))
+# Don't pull in the module, but instead pull in the static library
+MONBIN :=
+MONLIB := $(call intermediates-dir-for,STATIC_LIBRARIES,libmonitor,,,$(LOCAL_2ND_ARCH_VAR_PREFIX))/libmonitor.a
+else
+MONBIN := $(call intermediates-dir-for,EXECUTABLES,monitor.bin,,,$(LOCAL_2ND_ARCH_VAR_PREFIX))/monitor.bin
+MONLIB :=
+endif # (t124,$(TARGET_TEGRA_VERSION))
+
 LOCAL_PATH := $(call my-dir)
 
 include $(CLEAR_VARS)
@@ -34,11 +47,6 @@ LOCAL_MODULE := tos.img
 LOCAL_MODULE_CLASS := EXECUTABLES
 LOCAL_UNINSTALLABLE_MODULE := true
 
-# tos.img is considered to be 32-bit
-ifneq (,$(TARGET_2ND_ARCH))
-LOCAL_2ND_ARCH_VAR_PREFIX := $(TARGET_2ND_ARCH_VAR_PREFIX)
-endif
-
 TLK_INTERMEDIATES := $(call intermediates-dir-for,$(LOCAL_MODULE_CLASS),$(LOCAL_MODULE),,,$(LOCAL_2ND_ARCH_VAR_PREFIX))
 TLK_PROJECT := tegra
 
@@ -61,6 +69,11 @@ TASK_MODULES := \
        tlkstoragedemo_task \
        secure_rtc
 
+ifeq ($(filter t210,$(TARGET_TEGRA_VERSION)), $(TARGET_TEGRA_VERSION))
+TASK_MODULES += \
+       tsec_service
+endif
+
 # daemon to handle storage requests in Android user space
 DAEMON := tlk_daemon
 
@@ -70,7 +83,7 @@ KEYSTORE_CLIENT := keystore.tegra
 # Get actual task executables from list of task modules
 TASK_EXECUTABLES := \
        $(foreach task,$(TASK_MODULES), \
-               $(abspath $(call intermediates-dir-for,EXECUTABLES,$(task),,,$(LOCAL_2ND_ARCH_VAR_PREFIX))/$(task)))
+               $(call intermediates-dir-for,EXECUTABLES,$(task),,,$(LOCAL_2ND_ARCH_VAR_PREFIX))/$(task))
 
 ifeq ($(TARGET_ARCH),arm64)
 LK_TOOLCHAIN_PREFIX := prebuilts/gcc/$(HOST_PREBUILT_TAG)/arm/arm-eabi-4.8/bin/arm-eabi-
@@ -87,14 +100,16 @@ $(LK_BIN): PRIVATE_CUSTOM_TOOL_ARGS := PROJECT=$(TLK_PROJECT) \
                TOOLCHAIN_PREFIX=$(abspath $(LK_TOOLCHAIN_PREFIX)) \
                TOOLCHAIN_PREFIX64=$(abspath $(LK_TOOLCHAIN_PREFIX64)) \
                PREFIX=$(abspath $(TLK_INTERMEDIATES)) \
-               TASKS="$(TASK_EXECUTABLES)" \
-               LK_IMAGE=$(abspath $(TOSIMAGE)) \
+               TASKS="$(foreach task,$(TASK_EXECUTABLES), $(abspath $(task)))" \
+               MONBIN=$(abspath $(MONBIN)) \
+               MONLIB=$(abspath $(MONLIB)) \
+               TOSIMAGE=$(abspath $(TOSIMAGE)) \
                -C $(LOCAL_PATH)
 $(LK_BIN): PRIVATE_MODULE := $(LOCAL_MODULE)
 # Depend on tasks when we are doing a full build.
 # For one shot builds, (mm, mmm) do not.
 ifeq (,$(ONE_SHOT_MAKEFILE))
-$(LK_BIN): $(TASK_MODULES) $(DAEMON) $(KEYSTORE_CLIENT)
+$(LK_BIN): $(TASK_EXECUTABLES) $(DAEMON) $(KEYSTORE_CLIENT) $(MONLIB) $(MONBIN)
 endif
 $(LK_BIN):
        @echo "target Generated: $(PRIVATE_MODULE)"
@@ -118,10 +133,10 @@ LK_BIN :=
 TOSIMAGE :=
 TASK_MODULES :=
 TASK_EXECUTABLES :=
-PREREQ_FILES :=
-GEN :=
 DAEMON :=
 KEYSTORE_CLIENT :=
+MONBIN :=
+MONLIB :=
 LK_TOOLCHAIN_PREFIX :=
 LK_TOOLCHAIN_PREFIX64 :=
 
diff --git a/README b/README
index 048e2dd..6370216 100644 (file)
--- a/README
+++ b/README
 
 - To make tlk image, including 1 and 2,
   cd tlk
-  TARGET=<platform> make -e
+  ./build <platform>
   # <platform> could be either "t124" or "t132"
 
-- The result binary will be "build-<platform>/tos.img"
+- The result binary will be "../build-<platform>/lk"
 
 - Item 3 and 4 will be relased in source as example only.  They will not be part of the final image.
 
index 6a2d682..aee8f38 100644 (file)
@@ -87,6 +87,11 @@ void arch_early_init(void)
        /* write PMUSERENR to enable performance monitor access */
        reg = 0x1;
        __asm__ volatile("mcr   p15, 0, %0, c9, c14, 0" :: "r" (reg));
+
+       /* enable non-priv CNTVCT access (set CNTKCTL.PL0VCTEN) */
+       __asm__ volatile("mrc   p15, 0, %0, c14, c1, 0" : "=r" (reg));
+       reg |= (1 << 1);
+       __asm__ volatile("mcr   p15, 0, %0, c14, c1, 0" :: "r" (reg));
 #endif
 }
 
index cf9b7a8..5a225d9 100644 (file)
@@ -76,6 +76,14 @@ void arm_mmu_unmap_upage(task_t *taskp, addr_t vaddr)
        arm_mmu_desc_unmap_page(taskp->page_table, vaddr, taskp->context_id);
 }
 
+/* after all pages in a task have been unmapped call this to deallocate the
+ * task page tables.
+ */
+void arm_mmu_dealloc_upagetable(task_t *taskp)
+{
+       arm_mmu_desc_dealloc_upgtbl(&taskp->page_table);
+}
+
 status_t arm_mmu_set_attrs_task_init(task_map_t *mptr)
 {
        mptr->map_attrs = calloc(1, sizeof(arm_phys_attrs_t));
index 132a719..18e2fd8 100644 (file)
@@ -220,7 +220,7 @@ void arm_mmu_desc_map_page(vaddr_t vaddr, paddr_t paddr, paddr_t *pgtbl,
                /* alloc level 3 page table */
                level_3 = arm_mmu_desc_alloc_pgtbl(LEVEL_3);
                if (level_3 == NULL) {
-                       dprintf(CRITICAL, "unable to allocate LEVEL_2 page table\n");
+                       dprintf(CRITICAL, "unable to allocate LEVEL_3 page table\n");
                        halt();
                }
 
@@ -299,6 +299,30 @@ void arm_mmu_desc_unmap_page(paddr_t pgtbl, vaddr_t vaddr, uint32_t asid)
        arm_invalidate_tlb_byaddr_asid(vaddr, asid);
 }
 
+void arm_mmu_desc_dealloc_upgtbl(paddr_t *pgtbl)
+{
+       u_int idx;
+       uint64_t *page_table;
+       paddr_t level3;
+
+       if (pgtbl && *pgtbl) {
+               page_table = (uint64_t *)physical_to_virtual(*pgtbl);
+
+               /* free LEVEL_3 tables */
+               for (idx = 0; idx <= MMU_MEMORY_TTBR_L2_INDEX_MASK; idx++) {
+                       if (page_table[idx]) {
+                               level3 = page_table[idx] & MMU_MEMORY_TABLE_ADDR_MASK;
+                               free_memalign((void *)physical_to_virtual(level3));
+                               page_table[idx] = 0;
+                       }
+               }
+
+               /* free the LEVEL_2_USER table */
+               free_memalign((void *)page_table);
+               *pgtbl = 0;
+       }
+}
+
 #if !defined(ARM_USE_MMU_RELOC)
 static void arm_mmu_desc_map_block(addr_t paddr, addr_t vaddr, uint flags)
 {
index 0b833ae..e262134 100644 (file)
@@ -263,6 +263,32 @@ void arm_mmu_desc_unmap_page(paddr_t pgtbl, vaddr_t vaddr, uint32_t asid)
         arm_invalidate_tlb_byaddr_asid(vaddr, asid);
 }
 
+void arm_mmu_desc_dealloc_upgtbl(paddr_t *pgtbl)
+{
+       u_int idx;
+       u_int *page_table;
+        u_int *level_2;
+
+       if (pgtbl && *pgtbl) {
+
+               /* L1 table virtual addr */
+               page_table = (u_int *)physical_to_virtual(*pgtbl);
+
+               /* free all LEVEL_2 tables referred to in LEVEL_1_USER table */
+               for (idx = 0; idx <= MMU_MEMORY_TTBR0_L1_INDEX_MASK; idx++) {
+                       if (page_table[idx]) {
+                               level_2 = (u_int *)(page_table[idx] & ~(MMU_MEMORY_TTBR_L2_SIZE - 1));
+                               free_memalign((void *)physical_to_virtual((paddr_t)level_2));
+                               page_table[idx] = 0;
+                       }
+               }
+
+               /* free the LEVEL_1_USER table */
+               free_memalign((void *)page_table);
+               *pgtbl = 0;
+       }
+}
+
 #if !defined(ARM_USE_MMU_RELOC)
 static void arm_mmu_desc_map_section(addr_t paddr, addr_t vaddr, uint flags)
 {
index 1aec32b..302dc7e 100644 (file)
 #include <arch/arm/mmu.h>
 #include <kernel/task.h>
 #include <kernel/thread.h>
+#include <kernel/boot_params.h>
 #include <platform.h>
 #include <platform/platform_p.h>
 
-#define TASK_ARGS_SPACE                (3 * 16)
+#define TASK_ARGS_SPACE                (4 * 16)
 
 static void arch_task_set_usermode(thread_t *thread)
 {
@@ -88,7 +89,7 @@ static void arch_task_unmap(task_t *taskp, task_map_t *mptr)
        }
 }
 
-task_map_t *arch_task_map_memory(task_t *task, addr_t addr, u_int size, u_int flags)
+task_map_t *arch_task_map_memory(task_t *task, uint64_t addr, u_int size, u_int flags)
 {
        task_map_t *mptr;
        u_int npages, align, offset;
@@ -206,9 +207,16 @@ task_map_t *arch_task_setup_mmio(task_t *task, u_int id, addr_t paddr, u_int siz
 
 void arch_task_unmap_memory(task_t *task, task_map_t *mptr)
 {
-       /* if non-contig, free the pagelist */
-       if ((mptr->flags & TM_PHYS_CONTIG) == 0)
-               free(mptr->u_phys.pagelist);
+       if (mptr) {
+               /* if non-contig, free the pagelist */
+               if ((mptr->flags & TM_PHYS_CONTIG) == 0)
+                       free(mptr->u_phys.pagelist);
+               else {
+                       /* contig memory: need to free it if allocated with memalign() */
+                       if (mptr->flags & TM_PHYS_ALLOCATED)
+                               free_memalign((void *)physical_to_virtual(mptr->u_phys.contig));
+               }
+       }
 
        /* If the task pages are not yet mapped (e.g. error while loading a task)
         * the page table does not yet exist.
@@ -223,14 +231,101 @@ void arch_task_unmap_memory(task_t *task, task_map_t *mptr)
        free(mptr);
 }
 
+/* Arm architecture ASID (Address Space IDentifier) range defines the max
+ * allowed context_id value to be 255
+ */
+#define ARCH_ASID_MAX_VALUE 254
+#define ARCH_ASID_INVALID_VALUE (ARCH_ASID_MAX_VALUE + 1)
+
+/* bit masks for context id table values
+ */
+#define ARCH_ASID_IN_USE 0x01  /* context id value in use */
+
+/* Table of reserved context id (ASID) values
+ * Indices 0 or 255 are not used as context_id
+ */
+static char context_id_table[255];
+
+static void arch_task_release_context_id(uint32_t cid)
+{
+       if (cid < 1 || cid > ARCH_ASID_MAX_VALUE)
+               return;
+
+       enter_critical_section();
+
+       context_id_table[cid] &= ~ARCH_ASID_IN_USE;
+
+       exit_critical_section();
+}
+
+/*
+ * Searches unused CONTEXT_ID values after the Arm TTBR register ASID field
+ * would wrap.
+ *
+ * ASID value 255 is used for error handling in the border case of having 254
+ * active tasks and a new task load is attempted. Zero is not used for tasks.
+ */
+static u_int arch_task_get_context_id()
+{
+       u_int asid = 0;
+       static u_int next_id = 1;
+       uint32_t i = 0;
+
+       while (asid == 0) {
+
+               enter_critical_section();
+
+               for (i = next_id; i <= ARCH_ASID_MAX_VALUE; i++) {
+                       if ((context_id_table[i] & ARCH_ASID_IN_USE) == 0) {
+                               asid = i;
+                               context_id_table[i] |= ARCH_ASID_IN_USE;
+                               break;
+                       }
+               }
+
+               exit_critical_section();
+
+               if (asid == 0) {
+                       /* if did not scan from 1 redo loop once */
+                       if (next_id != 1) {
+                               next_id = 1;
+                               continue;
+                       }
+
+                       /*
+                        * Currently unsupported to have more
+                        * than ARCH_ASID_MAX_VALUE secure
+                        * tasks active at the same time.
+                        *
+                        * This value will get trapped by the
+                        * caller and task loading fails.
+                        *
+                        * Need to unload at least one tasks before
+                        * a new task can be loaded.
+                        *
+                        * The failed partially loaded task will get
+                        * auto-unloaded by the error handling.
+                        */
+                       dprintf(CRITICAL, "Too many secure tasks -- out of context id values\n");
+                       asid = ARCH_ASID_INVALID_VALUE;
+               }
+       }
+
+       if (asid >= ARCH_ASID_MAX_VALUE)
+               next_id = 1;
+       else
+               next_id = asid + 1;
+
+       return asid;
+}
+
 bool arch_task_init(thread_t *thread, task_t *task)
 {
-       static u_int context_id;
        task_map_t *mptr;
        uint32_t stack_top_off;
        vaddr_t arg_base;
        uint32_t *args;
-       Elf32_auxv_t *auxv;
+       uint32_t argc = 0;
 
        /* setup/clean user stack (reduced as libc expects args at sp) */
        stack_top_off = task->stack_map->size - TASK_ARGS_SPACE;
@@ -244,21 +339,15 @@ bool arch_task_init(thread_t *thread, task_t *task)
        arg_base = physical_to_virtual(task->stack_map->u_phys.contig) + stack_top_off;
        args = (uint32_t *)arg_base;
 
-       *args++ = 0x0;          /* argc */
-       *args++ = 0x0;          /* argv */
-       *args++ = 0x0;          /* envp */
-
-       /* add AT_RANDOM auxv tag/value */
-       auxv = (Elf32_auxv_t *)args;
-       args += 2;
+       /* return value = argc */
+       argc = get_boot_args(task, args + 1);
 
-       auxv->a_type = AT_RANDOM;
-       auxv->a_un.a_val = task->sp + ((vaddr_t)args - arg_base);
+       *args++ = argc;         /* argc */
+       args += argc;           /* increment past end of argv[] */
+       *args++ = 0x0;          /* envp */
 
-       *args++ = platform_get_rand32();
-       *args++ = platform_get_rand32();
-       *args++ = platform_get_rand32();
-       *args++ = platform_get_rand32();
+       /* ensure all args fit */
+       ASSERT(args <= (uint32_t *)(arg_base + TASK_ARGS_SPACE));
 
 #if ARM_WITH_NEON
        /* alloc per-thread (and NS world) vfp context */
@@ -269,10 +358,12 @@ bool arch_task_init(thread_t *thread, task_t *task)
 
        thread->arch.task = task;
        arch_task_set_usermode(thread);
-
-       task->context_id = ++context_id;
         list_add_tail(&task->thread_node, &thread->task_node);
 
+       task->context_id = arch_task_get_context_id();
+       if (task->context_id == ARCH_ASID_INVALID_VALUE)
+               return false;
+
        /* create pagetable entries for boot time mappings */
        list_for_every_entry(&task->map_list, mptr, task_map_t, node) {
                if (arm_mmu_set_attrs_task_init(mptr) != NO_ERROR)
@@ -282,3 +373,23 @@ bool arch_task_init(thread_t *thread, task_t *task)
 
        return true;
 }
+
+void arch_task_killed(task_t *task)
+{
+       if (task) {
+               arch_task_release_context_id(task->context_id);
+       }
+}
+
+void arch_task_thread_killed(thread_t *thread)
+{
+       if (thread) {
+#if ARM_WITH_NEON
+               /* Need to free the NEON context when thread dies */
+               if (thread->arch.fpctx) {
+                       free(thread->arch.fpctx);
+                       thread->arch.fpctx = NULL;
+               }
+#endif
+       }
+}
diff --git a/arch/arm/include/arch/arm/cache-l2x0.h b/arch/arm/include/arch/arm/cache-l2x0.h
new file mode 100644 (file)
index 0000000..d75fd0e
--- /dev/null
@@ -0,0 +1,81 @@
+/*
+ * Copyright (c) 2012, NVIDIA CORPORATION. All rights reserved
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining
+ * a copy of this software and associated documentation files
+ * (the "Software"), to deal in the Software without restriction,
+ * including without limitation the rights to use, copy, modify, merge,
+ * publish, distribute, sublicense, and/or sell copies of the Software,
+ * and to permit persons to whom the Software is furnished to do so,
+ * subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
+ * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
+ * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
+ * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
+ * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ */
+#ifndef __ARM_CACHE_L2X0_H
+#define __ARM_CACHE_L2X0_H
+
+#define L2X0_CACHE_ID                  0x000
+#define   L2X0_CACHE_ID_REV_MASK       (0x3f)
+#define   L2X0_CACHE_ID_PART_MASK      (0xf << 6)
+#define   L2X0_CACHE_ID_PART_L210      (1 << 6)
+#define   L2X0_CACHE_ID_PART_L220      (2 << 6)
+#define   L2X0_CACHE_ID_PART_L310      (3 << 6)
+#define L2X0_CACHE_TYPE                        0x004
+#define L2X0_CTRL                      0x100
+#define L2X0_AUX_CTRL                  0x104
+#define   L2X0_AUX_CTRL_WAY_SIZE_MASK  (0x7 << 17)
+#define L2X0_TAG_LATENCY_CTRL          0x108
+#define L2X0_DATA_LATENCY_CTRL         0x10C
+#define L2X0_EVENT_CNT_CTRL            0x200
+#define L2X0_EVENT_CNT1_CFG            0x204
+#define L2X0_EVENT_CNT0_CFG            0x208
+#define L2X0_EVENT_CNT1_VAL            0x20C
+#define L2X0_EVENT_CNT0_VAL            0x210
+#define L2X0_INTR_MASK                 0x214
+#define L2X0_MASKED_INTR_STAT          0x218
+#define L2X0_RAW_INTR_STAT             0x21C
+#define L2X0_INTR_CLEAR                        0x220
+#define L2X0_CACHE_SYNC                        0x730
+#define L2X0_DUMMY_REG                 0x740
+#define L2X0_INV_LINE_PA               0x770
+#define L2X0_INV_WAY                   0x77C
+#define L2X0_CLEAN_LINE_PA             0x7B0
+#define L2X0_CLEAN_LINE_IDX            0x7B8
+#define L2X0_CLEAN_WAY                 0x7BC
+#define L2X0_CLEAN_INV_LINE_PA         0x7F0
+#define L2X0_CLEAN_INV_LINE_IDX                0x7F8
+#define L2X0_CLEAN_INV_WAY             0x7FC
+
+#define REV_PL310_R2P0                 4
+#define REV_PL310_R3P1_50              7
+
+/*
+ * The lockdown registers repeat 8 times for L310, the L210 has only one
+ * D and one I lockdown register at 0x0900 and 0x0904.
+ */
+#define L2X0_LOCKDOWN_WAY_D_BASE       0x900
+#define L2X0_LOCKDOWN_WAY_I_BASE       0x904
+#define L2X0_LOCKDOWN_STRIDE           0x08
+#define L2X0_ADDR_FILTER_START         0xC00
+#define L2X0_ADDR_FILTER_END           0xC04
+#define L2X0_TEST_OPERATION            0xF00
+#define L2X0_LINE_DATA                 0xF10
+#define L2X0_LINE_TAG                  0xF30
+#define L2X0_DEBUG_CTRL                        0xF40
+#define L2X0_PREFETCH_CTRL             0xF60
+#define L2X0_POWER_CTRL                        0xF80
+#define   L2X0_DYNAMIC_CLK_GATING_EN   (1 << 1)
+#define   L2X0_STNDBY_MODE_EN          (1 << 0)
+
+void l2x0_setup(void);
+
+#endif
index 4944281..e8b03df 100644 (file)
@@ -94,6 +94,7 @@ void arm_mmu_map_kpage(vaddr_t vaddr, paddr_t paddr, task_map_t *mptr);
 void arm_mmu_unmap_section(addr_t vaddr);
 void arm_mmu_map_upage(task_t *taskp, vaddr_t vaddr, paddr_t paddr, task_map_t *mptr);
 void arm_mmu_unmap_upage(task_t *taskp, addr_t vaddr);
+void arm_mmu_dealloc_upagetable(task_t *taskp);
 void arm_mmu_translate_range(nsaddr_t vaddr, paddr_t *pagelist, task_map_t *mptr);
 paddr_t arm_mmu_virt_to_phys(nsaddr_t vaddr, bool ns, bool priv);
 status_t arm_mmu_set_attrs_task_init(task_map_t *mptr);
@@ -103,6 +104,7 @@ void arm_mmu_desc_set_default_task(arm_phys_attrs_t *attrs);
 void arm_mmu_desc_map_page(vaddr_t vaddr, paddr_t paddr, paddr_t *pgtbl,
                            tmflags_t flags, arm_phys_attrs_t *attrs);
 void arm_mmu_desc_unmap_page(paddr_t pgtbl, vaddr_t vaddr, uint32_t asid);
+void arm_mmu_desc_dealloc_upgtbl(paddr_t *pgtbl);
 vaddr_t arm_mmu_desc_get_max_user_space();
 #if !defined(ARM_USE_MMU_RELOC)
 void arm_mmu_desc_config_mmu()
index 28491ac..70f8f52 100644 (file)
@@ -79,7 +79,8 @@ MODULE_SRCS += \
        $(LOCAL_DIR)/arm/mmu.c \
        $(LOCAL_DIR)/arm/task.c \
        $(LOCAL_DIR)/arm/thread.c \
-       $(LOCAL_DIR)/arm/dcc.S
+       $(LOCAL_DIR)/arm/dcc.S \
+       $(LOCAL_DIR)/arm/cache-l2x0.c
 
 # The monitor support is provided either as a separate binary when
 # WITH_MONITOR_BIN = true, or as part of the secureos image when
diff --git a/build b/build
new file mode 100755 (executable)
index 0000000..d102198
--- /dev/null
+++ b/build
@@ -0,0 +1,30 @@
+#!/bin/sh
+
+FAILED=""
+MONLIB=false
+TARGET_ARCH=arm64
+TOOLS_PATH=../tools/aarch64-linux-android-4.8
+
+if [ -d "$TOOLS_PATH" ]; then
+       echo Tools found
+else
+       echo fatal error !!!
+       echo Tools not found, please put the tool to the path $TOOLS_PATH
+       exit 1
+fi
+if [ "$1" = "t124" ]; then
+       MONLIB=true
+       TARGET_ARCH=arm
+fi
+cd secure_monitor
+echo PROJECT=tegra TARGET=$1 TARGET_ARCH=$TARGET_ARCH MONITOR_LIBRARY=$MONLIB STANDALONE_MONITOR=false nice make -j4 -e || FAILED="$FAILED $1"
+PROJECT=tegra TARGET=$1 TARGET_ARCH=$TARGET_ARCH MONITOR_LIBRARY=$MONLIB STANDALONE_MONITOR=false nice make -j4 -e || FAILED="$FAILED $1"
+cd ..
+echo PROJECT=tegra TARGET=$1 TARGET_ARCH=$TARGET_ARCH nice make -j4 -e || FAILED="$FAILED $1"
+PROJECT=tegra TARGET=$1 TARGET_ARCH=$TARGET_ARCH nice make -j4 -e || FAILED="$FAILED $1"
+
+if [ "$FAILED" != "" ]; then
+       echo
+       echo some projects have failed to build:
+       echo $FAILED
+fi
index 2c334d8..a434025 100644 (file)
@@ -29,8 +29,10 @@ struct task_map;
 
 bool arch_task_init(struct thread *thread, struct task *task);
 void arch_task_set_context(struct thread *thread);
-struct task_map *arch_task_map_memory(struct task *task, addr_t addr, u_int size, u_int flags);
+struct task_map *arch_task_map_memory(struct task *task, uint64_t addr, u_int size, u_int flags);
 struct task_map *arch_task_setup_mmio(struct task *task, u_int id, addr_t paddr, u_int size);
 void arch_task_unmap_memory(struct task *task, struct task_map *mptr);
+void arch_task_thread_killed(struct thread *thread);
+void arch_task_killed(struct task *task);
 
 #endif
index b668ee7..2f34311 100644 (file)
@@ -25,6 +25,7 @@
 #define __BOOT_PARAMS_H
 
 #include <sys/types.h>
+#include <kernel/task.h>
 
 #define BOOT_PARAM_HEADER      'TFBP'
 #define CMDLINE_START          "[Global]"
@@ -37,6 +38,7 @@
 #define CMDLINE_DEVICE_UID1    "config.uid1"
 #define CMDLINE_DEVICE_UID2    "config.uid2"
 #define CMDLINE_DEVICE_UID3    "config.uid3"
+#define CMDLINE_TSEC_CARVEOUT  "tsec"
 
 #define DEVICE_UID_SIZE_WORDS  4
 #define PARAM_NAME_LEN         64              // in bytes
@@ -57,5 +59,6 @@ typedef struct {
 
 void save_boot_params(unsigned int, uint32_t);
 void parse_cmdline(void);
+int get_boot_args(task_t *task, uint32_t *args);
 
 #endif
index 04cc2ce..3c55815 100644 (file)
@@ -48,6 +48,7 @@ typedef enum {
        TM_NS_MEM_PRIV  = (1 << 22),
        TM_SEC_VA       = (1 << 23),
        TM_KERN_VA      = (1 << 24),
+       TM_PHYS_ALLOCATED = (1 << 28),
        TM_KERN_SEC_VA  = (1 << 29),
        TM_IO           = (1 << 30),
 } tmflags_t;
@@ -93,6 +94,7 @@ typedef struct
 typedef enum {
        TASK_STATE_UNKNOWN = 0,
        TASK_STATE_INIT,
+       TASK_STATE_STARTING,
        TASK_STATE_ACTIVE,
        TASK_STATE_BLOCKED,
        TASK_STATE_TERMINATED
@@ -172,20 +174,31 @@ task_t *task_find_task_by_index(uint32_t index);
 /*! Return a pointer to const char C-string PREFIXtasknameSUFFIX if task has a name,
  * otherwise return pointer to "".
  *
- * PREFIX and SUFFIX may be NULL (treated as empty strings).
+ * On entry buf is a pointer to memory area of length buflen characters.
  *
- * BUF must be at least length(PREFIX)+OTE_TASK_NAME_MAX_LENGTH+length(SUFFIX), buffer length in BUFLEN.
+ * \param task[in]     get taskname from here
+ * \param prefix[in]   added before task name, if not null
+ * \param suffix[in]   added after task name, if not null
+ * \param buf[in/out]  if task has a name, will contain "prefixTASKNAMEsuffix" C-string
+ * \param buflen[in]   buf length (must be long enough to contain prefix, task name, suffix and nul)
  */
 const char *task_get_name_str(const task_t *task, const char *prefix, const char *suffix,
                              char *buf, uint32_t buflen);
 
-/*! Log the uuid of TASKP at dprintf LEVEL with optional PREFIX string.
+/*! Log the uuid && name of taskp at dprintf() level with optional prefix string.
  *
- * \param LEVEL defines dprintf() level to conditionally print at.
- * \param PREFIX is an optional string prefix (or NULL).
- * \param TASKP is the task which uuid is to be printed in "hex-dash" format
+ * \param level  defines dprintf() level to conditionally print at.
+ * \param prefix is an optional string prefix (or NULL).
+ * \param taskp  is the task which uuid is to be printed in "hex-dash" format
  */
-void task_print_uuid(uint32_t level, const char *prefix, const task_t *taskp);
+void task_print_id(uint32_t level, const char *prefix, const task_t *taskp);
+
+/*! Log the uuid at dprintf() level.
+ *
+ * \param level        defines dprintf() level to conditionally print at.
+ * \param uuid is an UUID to log.
+ */
+void task_print_uuid(uint32_t level, const te_service_id_t *uuid);
 
 status_t task_prepare(char *task_addr, u_int task_size, task_t *taskp,
                      Elf32_Shdr **bss_pad_shdr_p, task_type_t task_type);
@@ -206,6 +219,9 @@ status_t task_init_one_task(task_t *task);
  */
 status_t task_register(task_t **task_p);
 
+/*! return a const pointer to task_list header node */
+const struct list_node *task_get_task_list(void);
+
 /*! return the number of currently existing active tasks */
 u_int task_get_active_count(void);
 
index 4fdf5f6..d992f48 100644 (file)
@@ -52,8 +52,18 @@ void mon_mmu_map_uncached(uintptr_t vaddr, uint64_t paddr, uint32_t length);
 void mon_mmu_unmap(uintptr_t vaddr, uint32_t length);
 
 void mon_atomic_or(volatile uint32_t *ptr, uint32_t bits);
+void mon_atomic_and(volatile uint32_t *ptr, uint32_t bits);
 
 uint32_t mon_get_cpu_id(void);
+
+/*
+ * CPU power down sequence as per A57/A53 TRM
+ *
+ * l2_flush = indicates if L2 flush is required
+ *
+ */
+void mon_cpu_power_down(int l2_flush);
+
 #endif // !ASSEMBLY && WITH_MONITOR_BIN
 
 
index c24e150..df22de0 100644 (file)
@@ -34,7 +34,6 @@
 #include <common/ote_common.h>
 #include <common/ote_error.h>
 #include <service/ote_service.h>
-#include <service/ote_storage.h>
 #include <service/ote_manifest.h>
 #include <ext_nv/ote_ext_nv.h>
 #include <service/ote_task_load.h>
@@ -47,102 +46,6 @@ enum {
        OTE_PROP_DATA_TYPE_IDENTITY     = 2,
 };
 
-/*
- * The following describes the layout of the shared memory buffer
- * used for SS-related communication between the NS and S worlds.
- */
-#define TE_SHMEM_DNAME_SZ      (64)
-#define TE_SHMEM_FNAME_SZ      (128)
-#define TE_SHMEM_DATA_SZ       (2048)
-
-typedef struct {
-       char            dname[TE_SHMEM_DNAME_SZ];
-       char            fname[TE_SHMEM_FNAME_SZ];
-       uint32_t        flags;
-} te_ss_create_params_t;
-
-typedef struct {
-       char            dname[TE_SHMEM_DNAME_SZ];
-       char            fname[TE_SHMEM_FNAME_SZ];
-} te_ss_delete_params_t;
-
-typedef struct {
-       char            dname[TE_SHMEM_DNAME_SZ];
-       char            fname[TE_SHMEM_FNAME_SZ];
-       uint32_t        flags;
-       uint32_t        handle;
-} te_ss_open_params_t;
-
-typedef struct {
-       uint32_t        handle;
-} te_ss_close_params_t;
-
-typedef struct {
-       uint32_t        handle;
-       uint32_t        data_size;
-       char            data[TE_SHMEM_DATA_SZ];
-} te_ss_write_params_t;
-
-typedef struct {
-       uint32_t        handle;
-       uint32_t        data_size;
-       char            data[TE_SHMEM_DATA_SZ];
-} te_ss_read_params_t;
-
-typedef struct {
-       uint32_t        handle;
-       int32_t         offset;
-       uint32_t        whence;
-} te_ss_seek_params_t;
-
-typedef struct {
-       uint32_t        handle;
-       uint32_t        length;
-} te_ss_trunc_params_t;
-
-typedef struct {
-       uint32_t        handle;
-       uint32_t        size;
-} te_ss_get_size_params_t;
-
-#define RPMB_FRAME_SIZE        512
-
-typedef struct {
-       uint8_t         req_frame[RPMB_FRAME_SIZE];
-       uint8_t         req_resp_frame[RPMB_FRAME_SIZE];
-       uint8_t         resp_frame[RPMB_FRAME_SIZE];
-} te_ss_rpmb_write_params_t;
-
-typedef struct {
-       uint8_t         req_frame[RPMB_FRAME_SIZE];
-       uint8_t         resp_frame[RPMB_FRAME_SIZE];
-} te_ss_rpmb_read_params_t;
-
-typedef union {
-       te_ss_create_params_t           f_create;
-       te_ss_delete_params_t           f_delete;
-       te_ss_open_params_t             f_open;
-       te_ss_close_params_t            f_close;
-       te_ss_read_params_t             f_read;
-       te_ss_write_params_t            f_write;
-       te_ss_seek_params_t             f_seek;
-       te_ss_trunc_params_t            f_trunc;
-       te_ss_get_size_params_t         f_getsize;
-       te_ss_rpmb_write_params_t       f_rpmb_write;
-       te_ss_rpmb_read_params_t        f_rpmb_read;
-} te_ss_req_params_t;
-
-/*
- * Parameter block exchanged on each file system operation request.
- */
-typedef struct {
-       uint32_t                req_size;
-       uint32_t                type;
-       int32_t                 result;
-       uint32_t                params_size;
-       te_ss_req_params_t      params;
-} te_ss_op_t;
-
 #define DEVICE_UID_SIZE_WORDS  4
 
 typedef struct {
index ed353ab..c8fa6a8 100644 (file)
@@ -35,6 +35,7 @@ void *memalign(size_t boundary, size_t size) __MALLOC;
 void *calloc(size_t count, size_t size) __MALLOC;
 void *realloc(void *ptr, size_t size) __MALLOC;
 void free(void *ptr);
+void free_memalign(void *ptr);
 
 #if defined(__cplusplus)
 }
index 0beca2a..d9e1dd3 100644 (file)
@@ -26,6 +26,7 @@
 #include <assert.h>
 #include <kernel/boot_params.h>
 #include <platform/platform_p.h>
+#include <common/ote_nv_uuid.h>
 
 unsigned int coldboot_normal_os;
 unsigned int normal_os_coldboot_fn;
@@ -33,6 +34,7 @@ extern uint32_t debug_uart_id;
 unsigned int tf_key_addr;
 unsigned int tf_key_size;
 uint32_t device_uid[DEVICE_UID_SIZE_WORDS];
+paddr_t tsec_carveout_size, tsec_carveout_base;
 
 extern unsigned int __bootarg_addr;
 
@@ -115,6 +117,16 @@ void parse_cmdline(void)
 
                                tz_add_dram_range(base << 20, size << 20);
                                break;
+                       } else if (!strncmp(str, CMDLINE_TSEC_CARVEOUT, strlen(CMDLINE_TSEC_CARVEOUT))) {
+
+                               /* format is "tsec: <size>M@<base>M" in MBbytes */
+                               str += strlen(str) + 2;
+                               tsec_carveout_size = (paddr_t) atoui(str);
+                               tsec_carveout_base = (paddr_t) atoui(strchr(str, '@') + 1);
+                               tsec_carveout_size <<= 20;
+                               tsec_carveout_base <<= 20;
+                               cmdline_len--;
+                               break;
                        }
                }
 
@@ -128,3 +140,18 @@ done:
                str += strlen(str) + 1;
        }
 }
+
+int get_boot_args(task_t *task, uint32_t *argv)
+{
+       int i = 0;
+       te_service_id_t hdcp_uuid = SERVICE_SECURE_HDCP_UUID;
+
+       /* pass input params to hdcp service via argv */
+       if (!memcmp(&hdcp_uuid, &task->props.uuid, sizeof(te_service_id_t))) {
+               argv[i++] = 0x0;                /* argv[0] = progname (NULL) */
+               argv[i++] = tsec_carveout_base; /* argv[1] */
+               argv[i++] = tsec_carveout_size; /* argv[2] */
+       }
+
+       return i;
+}
index 5bf03a3..39bc440 100644 (file)
@@ -37,7 +37,6 @@
 
 #include <service/ote_manifest.h>
 
-#define MAX_SESSION_IDS                0xFFFF
 #define MAX_ARGS_PER_CMD       0x8
 
 #define PRINT_UUID(s,u)                                                           \
@@ -61,9 +60,16 @@ static struct list_node completion_list;
 
 typedef struct {
        struct list_node node;
+       bool active;
+       task_map_t *mptr;
+} persist_map_t;
+
+typedef struct {
+       struct list_node node;
        struct list_node cmd_node;
 
        unsigned int session_id;
+       struct list_node persist_maps;
        void *context;
        thread_t *thread;
 } session_t;
@@ -155,9 +161,6 @@ static session_t *te_get_session_from_id(uint32_t id)
 {
        session_t *session;
 
-       if (list_is_empty(&session_list))
-               goto exit;
-
        list_for_every_entry(&session_list, session, session_t, node) {
                if (session->session_id == id)
                        return session;
@@ -166,16 +169,83 @@ exit:
        return NULL;
 }
 
+static te_error_t te_add_persist_map(task_map_t *mptr, session_t *session)
+{
+       persist_map_t *persist_map = NULL;
+
+       persist_map = calloc(1, sizeof(persist_map_t));
+       if (persist_map == NULL) {
+               return OTE_ERROR_OUT_OF_MEMORY;
+       }
+
+       list_initialize(&persist_map->node);
+       persist_map->mptr = mptr;
+       persist_map->active = false;
+
+       enter_critical_section();
+       list_add_tail(&session->persist_maps, &persist_map->node);
+       exit_critical_section();
+
+       return OTE_SUCCESS;
+}
+
+static void te_release_persist_maps(session_t *session, task_t *task,
+                               bool only_inactive)
+{
+       persist_map_t *persist_map, *next;
+
+       list_for_every_entry_safe(&session->persist_maps,
+                               persist_map, next, persist_map_t, node) {
+
+               /* skip active mappings if desired */
+               if (only_inactive && persist_map->active)
+                       continue;
+
+               arch_task_unmap_memory(task, persist_map->mptr);
+               list_delete(&persist_map->node);
+               free(persist_map);
+       }
+}
+
+static void te_update_persist_maps(session_t *session, task_t *task)
+{
+       persist_map_t *persist_map, *next;
+
+       /* activate any pending persistent mappings */
+       list_for_every_entry_safe(&session->persist_maps,
+                               persist_map, next, persist_map_t, node) {
+               if (!persist_map->active)
+                       persist_map->active = true;
+       }
+}
+
 static te_error_t te_prepare_memref_param(task_t *task, struct te_command *cmd,
-                                          te_oper_param_t *params, bool writable)
+                                       te_oper_param_t *param)
 {
        task_map_t *mptr;
-       addr_t vaddr;
+       uint64_t vaddr;
        uint32_t size, flags;
+       te_error_t result;
+
+       /* set read/write flags */
+       if ((param->type == TE_PARAM_TYPE_MEM_RW) ||
+               (param->type == TE_PARAM_TYPE_PERSIST_MEM_RW)) {
+               flags = (TM_UR | TM_UW);
+       } else {
+               flags = TM_UR;
+       }
+
+       /* make sure we have room if it's a temporary memref */
+       if ((param->type == TE_PARAM_TYPE_MEM_RO) ||
+               (param->type == TE_PARAM_TYPE_MEM_RW)) {
+               if (cmd->maps == MAX_ARGS_PER_CMD) {
+                       dprintf(CRITICAL, "out of memref maps\n");
+                       return OTE_ERROR_OUT_OF_MEMORY;
+               }
+       }
 
-       vaddr = (addr_t)params->u.Mem.base;
-       size  = params->u.Mem.len;
-       flags = (writable) ? (TM_UR | TM_UW) : TM_UR;
+       vaddr = param->u.Mem.base;
+       size  = param->u.Mem.len;
 
        if (!cmd->requesting_task) {
                /* command (and memory) came from the NS world */
@@ -207,14 +277,25 @@ static te_error_t te_prepare_memref_param(task_t *task, struct te_command *cmd,
        if (mptr == NULL) {
                return OTE_ERROR_OUT_OF_MEMORY;
        }
-       cmd->mptr[cmd->maps++] = mptr;
+
+       if ((param->type == TE_PARAM_TYPE_PERSIST_MEM_RO) ||
+               (param->type == TE_PARAM_TYPE_PERSIST_MEM_RW)) {
+
+               result = te_add_persist_map(mptr, cmd->session);
+               if (result != OTE_SUCCESS) {
+                       arch_task_unmap_memory(task, mptr);
+                       return result;
+               }
+       } else {
+               cmd->mptr[cmd->maps++] = mptr;
+       }
 
        /* create new address w/ old page offset */
        vaddr &= PAGE_MASK;
        vaddr |= mptr->vaddr;
 
        /* rewrite param with this mapping */
-       params->u.Mem.base = vaddr;
+       param->u.Mem.base = vaddr;
 
        return OTE_SUCCESS;
 }
@@ -230,25 +311,27 @@ static te_error_t te_check_operation_params(task_t *task, struct te_command *cmd
        for (i = 0; i < cmd->msg.params_size; i++) {
                te_error_t result;
 
-               param_type = params[i].type;
-               if (param_type <= TE_PARAM_TYPE_INT_RW) {
-                       continue;       /* none or values */
-               }
-               if (param_type == TE_PARAM_TYPE_MEM_RO) {
-                       result = te_prepare_memref_param(task, cmd, &params[i], false);
-                       if (result != OTE_SUCCESS) {
-                               dprintf(CRITICAL, "%s: ro memref fail map:%d\n", __func__, cmd->maps);
-                               return result;
-                       }
-               } else if (param_type == TE_PARAM_TYPE_MEM_RW) {
-                       result = te_prepare_memref_param(task, cmd, &params[i], true);
-                       if (result != OTE_SUCCESS) {
-                               dprintf(CRITICAL, "%s: rw memref fail map:%d\n", __func__, cmd->maps);
-                               return result;
-                       }
-               } else {
+               switch (params[i].type) {
+               case TE_PARAM_TYPE_INT_RW:
+               case TE_PARAM_TYPE_INT_RO:
+                       continue;
+               case TE_PARAM_TYPE_MEM_RO:
+               case TE_PARAM_TYPE_MEM_RW:
+               case TE_PARAM_TYPE_PERSIST_MEM_RO:
+               case TE_PARAM_TYPE_PERSIST_MEM_RW:
+                       break;
+               default:
+                       dprintf(CRITICAL, "%s: unknown param type: 0x%x\n",
+                               __func__, params[i].type);
                        return OTE_ERROR_BAD_PARAMETERS;
                }
+
+               result = te_prepare_memref_param(task, cmd, &params[i]);
+               if (result != OTE_SUCCESS) {
+                       dprintf(CRITICAL, "%s: memref map failed: 0x%x\n",
+                               __func__, result);
+                       return result;
+               }
        }
        return OTE_SUCCESS;
 }
@@ -290,6 +373,15 @@ static te_error_t te_copyin_ta_params(te_request_t *req, struct te_command *cmd)
                        dprintf(SPEW, "%s: %d: MEM_RW: len 0x%x\n",
                                __func__, i, out_params[i].u.Mem.len);
                        break;
+               case TE_PARAM_TYPE_PERSIST_MEM_RO:
+                       dprintf(SPEW, "%s: %d: PERSIST_MEM_RO: len 0x%x\n",
+                               __func__, i, out_params[i].u.Mem.len);
+                       break;
+               case TE_PARAM_TYPE_PERSIST_MEM_RW:
+                       dprintf(SPEW, "%s: %d: PERSIST_MEM_RW: len 0x%x\n",
+                               __func__, i, out_params[i].u.Mem.len);
+                       break;
+
                default:
                        dprintf(INFO, "%s: unhandled param type 0x%x\n",
                                __func__, in_param->type);
@@ -344,6 +436,15 @@ static void te_copyout_ta_params(struct te_command *cmd, te_request_t *req)
                                __func__, i, in_params[i].u.Mem.len);
                        out_param->u.Mem.len = in_params[i].u.Mem.len;
                        break;
+               case TE_PARAM_TYPE_PERSIST_MEM_RO:
+                       dprintf(SPEW, "%s: %d: PERSIST_MEM_RO: len 0x%x\n",
+                               __func__, i, in_params[i].u.Mem.len);
+                       break;
+               case TE_PARAM_TYPE_PERSIST_MEM_RW:
+                       dprintf(SPEW, "%s: %d: PERSIST_MEM_RW: len 0x%x\n",
+                               __func__, i, in_params[i].u.Mem.len);
+                       out_param->u.Mem.len = in_params[i].u.Mem.len;
+                       break;
                default:
                        dprintf(INFO, "%s: %d: unhandled param type 0x%x\n",
                                __func__, i, out_param->type);
@@ -374,6 +475,7 @@ static session_t *te_create_thread_session(task_t *task)
 
        list_initialize(&session->node);
        list_initialize(&session->cmd_node);
+       list_initialize(&session->persist_maps);
 
        do {
                session_t *temp;
@@ -664,6 +766,10 @@ void te_get_completed_cmd(te_request_t *req, bool task_issued)
                /* unhook and free session on failure */
                if (cmd->msg.result != OTE_SUCCESS) {
                        ASSERT(session && next);
+
+                       /* release persistent mappings if any */
+                       te_release_persist_maps(session, task, false);
+
                        list_delete(&session->node);
                        free(session);
                        req->session_id = 0x0;
@@ -674,12 +780,18 @@ void te_get_completed_cmd(te_request_t *req, bool task_issued)
                        req->session_id = session->session_id;
                        if (task_issued)
                                te_copyout_ta_params(cmd, req);
+
+                       /* mark persistent mappings as active */
+                       te_update_persist_maps(session, task);
                }
                break;
        case DESTROY_INSTANCE:
        case CLOSE_SESSION:
                ASSERT(session && next);
 
+               /* release any persistent mappings */
+               te_release_persist_maps(session, task, false);
+
                /* unhook and free session */
                list_delete(&session->node);
                free(session);
@@ -687,8 +799,16 @@ void te_get_completed_cmd(te_request_t *req, bool task_issued)
                task->te_instances--;
                break;
        case LAUNCH_OPERATION:
-               if (task_issued)
-                       te_copyout_ta_params(cmd, req);
+               if (cmd->msg.result != OTE_SUCCESS) {
+                       /* release inactive persistent mappings if any */
+                       te_release_persist_maps(session, task, true);
+               } else {
+                       /* mark persistent mappings as active */
+                       te_update_persist_maps(session, task);
+
+                       if (task_issued)
+                               te_copyout_ta_params(cmd, req);
+               }
                break;
        }
 
@@ -846,6 +966,8 @@ static int te_handle_result_message(struct te_command *cmd, void *msg, bool read
                                sizeof(te_oper_param_t) * cmd->msg.params_size);
                }
                cmd->session->context = (void *)(uintptr_t)ep->context;
+
+               /* release non-persistent mappings */
                task = cmd->session->thread->arch.task;
                while (cmd->maps--) {
                        arch_task_unmap_memory(task, cmd->mptr[cmd->maps]);
@@ -859,6 +981,8 @@ static int te_handle_result_message(struct te_command *cmd, void *msg, bool read
                                (void *)(uintptr_t)ep->params,
                                sizeof(te_oper_param_t) * ep->params_size);
                }
+
+               /* release non-persistent mappings */
                task = cmd->session->thread->arch.task;
                while (cmd->maps--) {
                        arch_task_unmap_memory(task, cmd->mptr[cmd->maps]);
@@ -959,6 +1083,10 @@ int te_get_current_client_property(te_get_property_args_t *args)
        task_t *taskp;
        struct te_command *cmd;
 
+       /* determine which client property they're after */
+       ASSERT(args->data_type == OTE_PROP_DATA_TYPE_IDENTITY);
+       ASSERT(args->value_size == sizeof(te_identity_t));
+
        /* we expect to have a current command bound */
        if (!current_thread->arg) {
                args->result = OTE_ERROR_BAD_STATE;
@@ -967,23 +1095,18 @@ int te_get_current_client_property(te_get_property_args_t *args)
 
        cmd = (struct te_command *) current_thread->arg;
 
-       /* for now we only handle this query if client is another task */
-       if (!cmd->requesting_task) {
-               args->result = OTE_ERROR_NOT_IMPLEMENTED;
-               return -EINVAL;
+       /* set login type and uuid */
+       if (cmd->requesting_task) {
+               taskp = cmd->requesting_task;
+               memcpy(&args->value.identity.uuid, &taskp->props.uuid,
+                       sizeof(te_service_id_t));
+               args->value.identity.login = TE_LOGIN_TA;
+       } else {
+               /* no uuid available */
+               memset(&args->value.identity.uuid, 0, sizeof(te_service_id_t));
+               args->value.identity.login = TE_LOGIN_PUBLIC;
        }
 
-       taskp = cmd->requesting_task;
-
-       /* determine which client property they're after */
-       ASSERT(args->data_type == OTE_PROP_DATA_TYPE_IDENTITY);
-       ASSERT(args->value_size == sizeof(te_identity_t));
-
-       args->value.identity.login = 0;
-       memcpy(&args->value.identity.uuid,
-              &taskp->props.uuid,
-              sizeof(te_service_id_t));
-
        args->result = OTE_SUCCESS;
        return 0;
 }
@@ -1016,12 +1139,15 @@ void te_session_cancel_thread(thread_t *t)
                        list_for_every_entry_safe(&session->cmd_node, cmd, cmd_tmp,
                                                  te_command_t, node) {
                                while (cmd->maps--) {
-                                       arch_task_unmap_memory(task, cmd->mptr[cmd->maps]);
+                                       arch_task_unmap_memory(task,
+                                                       cmd->mptr[cmd->maps]);
                                }
                                list_delete(&cmd->node);
                                free(cmd);
                                cmd = NULL;
                        }
+
+                       te_release_persist_maps(session, task, false);
                        free(session);
                        session = NULL;
                }
index 2358309..5239f1f 100644 (file)
@@ -35,6 +35,8 @@
 #include <platform/platform_p.h>
 #include <kernel/task_load.h>
 
+#include "../lib/external/libc/include/syscall.h"
+
 struct timespec {
        long tv_sec;    /* seconds */
        long tv_nsec;   /* nanoseconds */
@@ -233,14 +235,7 @@ static int platform_ioctl_handler(u_int cmd, void *cmdbuf)
                }
                case OTE_IOCTL_SS_REQUEST:
                {
-                       te_storage_request_t *args = cmdbuf;
-
-                       /* validate command buffer */
-                       if (!task_valid_address((vaddr_t)args, sizeof(*args))) {
-                               return -EFAULT;
-                       }
-
-                       return platform_ss_request_handler(args);
+                       return platform_ss_request_handler();
                }
                case OTE_IOCTL_GET_DEVICE_ID:
                {
@@ -304,7 +299,7 @@ bool platform_syscall_handler(void *arg)
        task_t *task = current_thread->arch.task;
        uint32_t *r = arg;
 
-       if (r[7] == 0x3) {      /* read */
+       if (r[12] == __NR_read) {       /* read */
                /* only expect reads of the TA pipe fd */
                r[0] = te_handle_ta_message(r[0],
                                             (void *)(r[1]),
@@ -312,7 +307,7 @@ bool platform_syscall_handler(void *arg)
                                             true);
                return true;
        }
-       if (r[7] == 0x4) {      /* write */
+       if (r[12] == __NR_write) {      /* write */
                /* check buffer is in task's address space */
                if (task_valid_address(r[1], r[2]) == false) {
                        r[0] = -EFAULT;
@@ -334,12 +329,7 @@ bool platform_syscall_handler(void *arg)
                }
                return true;
        }
-       if (r[7] == 0x5) {      /* open */
-               /* for now, fail all open() attempts */
-               r[0] = -ENXIO;
-               return true;
-       }
-       if (r[7] == 0x2d) {     /* brk */
+       if (r[12] == __NR_brk) {        /* brk */
                u_int brk = r[0];
 
                /* update brk, if within range */
@@ -364,23 +354,7 @@ bool platform_syscall_handler(void *arg)
                r[0] = task->curr_brk;
                return true;
        }
-       if (r[7] == 0x4e) {     /* sys_gettimeofday */
-               r[0] = 0;
-               return true;
-       }
-       if (r[7] == 0x5b) {     /* munmap */
-               /* attempt to reclaim most recent alloc */
-               if ((r[0] + r[1]) == task->curr_brk) {
-                       task->curr_brk = r[0];
-               }
-               r[0] = 0;
-               return true;
-       }
-       if (r[7] == 0x7d) {     /* mprotect */
-               r[0] = 0;
-               return true;
-       }
-       if (r[7] == 0xa2) {     /* usleep */
+       if (r[12] == __NR_usleep) {     /* usleep */
                struct timespec *ts;
 
                /* check buffer is in task's address space */
@@ -400,60 +374,11 @@ bool platform_syscall_handler(void *arg)
                r[0] = 0;
                return true;
        }
-       if (r[7] == 0xc0) {     /* mmap2 */
-               u_int brk;
-
-               if (r[3] != (MAP_ANONYMOUS | MAP_PRIVATE)) {
-                       r[0] = -EINVAL;
-                       return true;
-               }
-
-               r[0] = ROUNDUP(task->curr_brk, PAGE_SIZE);
-               brk = r[0] + ROUNDUP(r[1], PAGE_SIZE);
-
-               /* update brk, if within range */
-               if ((brk >= task->start_brk) && (brk < task->end_brk)) {
-                       task->curr_brk = brk;
-                       return true;
-               } else {
-                       if (brk >= task->end_brk) {
-                               dprintf(CRITICAL,
-                                       "%s: task %d: mmap2: "
-                                       "no more heap (size 0x%lx bytes)\n",
-                                       __func__, task->task_index,
-                                       task->end_brk - task->start_brk);
-                       } else if (brk < task->start_brk) {
-                               dprintf(CRITICAL,
-                                       "%s: task %d: mmap2: "
-                                       "brk 0x%x < heap start 0x%lx\n",
-                                       __func__, task->task_index,
-                                       brk, task->start_brk);
-                       }
-               }
-               r[0] = -ENOMEM;
-               return true;
-       }
-       if (r[7] == 0xc5) {     /* fstat */
-               r[0] = -ENOENT;
-               return true;
-       }
-       if (r[7] == 0xdc) {     /* madvise */
-               r[0] = 0;
-               return true;
-       }
-       if (r[7] == 0xe0) {     /* gettid */
+       if (r[12] == __NR_gettid) {     /* gettid */
                r[0] = (u_int)current_thread;
                return true;
        }
-       if (r[7] == 0x14) {     /* getpid */
-               r[0] = -ENOENT;
-               return true;
-       }
-       if (r[7] == 0xc7) {     /* getuid */
-               r[0] = -ENOENT;
-               return true;
-       }
-       if (r[7] == 0xf8) {     /* exit_group */
+       if (r[12] == __NR_exit_group) { /* exit_group */
                /* terminate thread (and all task threads) */
                /* thread_exit(r[0]); */
 
@@ -461,28 +386,13 @@ bool platform_syscall_handler(void *arg)
                thread_suspend();
                return true;
        }
-       if (r[7] == 0x107) {    /* sys_clock_gettime */
-               r[0] = -EFAULT;
-               return true;
-       }
-       if (r[7] == 0x119){     /* socket */
-               r[0] = -ENOENT;
-               return true;
-       }
-       if (r[7] == 0xF0005) {  /* set_tls */
-               current_thread->arch.tp_value = r[0];
-               arch_set_tls(r[0]);
-
-               r[0] = 0x0;
-               return true;
-       }
-       if (r[7] == 0x36) {     /* ioctl */
+       if (r[12] == __NR_ioctl) {      /* ioctl */
                r[0] = platform_ioctl_handler(r[1], (void *)r[2]);
 
                return true;
        }
 
-       dprintf(CRITICAL, "%s: unhandled syscall: 0x%x\n", __func__, r[7]);
+       dprintf(CRITICAL, "%s: unhandled syscall: 0x%x\n", __func__, r[12]);
 
        return true;
 }
index 3f4b0ef..94f65b2 100644 (file)
@@ -37,6 +37,7 @@
 #include <platform.h>
 #include <platform/platform_p.h>
 #include <kernel/task_load.h>
+#include <common/ote_nv_uuid.h>
 
 /*! page aligned area for storing static task headers before heap is initialized */
 #define TASK_LIST_CARVEOUT_PAGES 1
@@ -64,12 +65,31 @@ extern int _heap_end;       /* heap ends here, adjusted by carve-outs below */
 /* memory carved off from the top (before heap_init) */
 #define carveout_taskmem       _heap_end
 
+void task_print_uuid(uint32_t level, const te_service_id_t *uuid)
+{
+       if (uuid) {
+               dprintf(level, "%08x-%04x-%04x-%02x%02x%02x%02x%02x%02x%02x%02x",
+                       uuid->time_low,
+                       uuid->time_mid,
+                       uuid->time_hi_and_version,
+                       uuid->clock_seq_and_node[0],    /* clock_seq_hi_and_reserved */
+                       uuid->clock_seq_and_node[1],    /* clock_seq_low */
+                       uuid->clock_seq_and_node[2],
+                       uuid->clock_seq_and_node[3],
+                       uuid->clock_seq_and_node[4],
+                       uuid->clock_seq_and_node[5],
+                       uuid->clock_seq_and_node[6],
+                       uuid->clock_seq_and_node[7]);
+       }
+}
+
 static status_t task_load_config_options(u_int task_image_addr, task_t *taskp, Elf32_Shdr *shdr)
 {
        status_t err = NO_ERROR;
        OTE_MANIFEST  *manifest;
        u_int *config_blob, config_blob_size;
        u_int i;
+       te_service_id_t null_uuid = NULL_UUID;
 
        if (shdr->sh_size < offsetof(OTE_MANIFEST, config_options)) {
                err = ERR_NOT_VALID;
@@ -87,6 +107,7 @@ static status_t task_load_config_options(u_int task_image_addr, task_t *taskp, E
         * Task loading may also override this field value.
         */
        memcpy(&taskp->task_name[0], &manifest->name[0], sizeof(taskp->task_name));
+       taskp->task_name[sizeof(taskp->task_name) - 1] = '\000';
 
        /*
         * Copy TA specific config data (optional field, define semantics per task).
@@ -96,9 +117,14 @@ static status_t task_load_config_options(u_int task_image_addr, task_t *taskp, E
        memcpy(&taskp->task_private_data[0], &manifest->private_data[0],
               sizeof(taskp->task_private_data));
 
+       /* reject all tasks with NULL UUID */
+       if (!memcmp(&manifest->uuid, &null_uuid, sizeof(te_service_id_t))) {
+               err = ERR_NOT_VALID;
+               goto exit;
+       }
        memcpy(&taskp->props.uuid, &manifest->uuid, sizeof(te_service_id_t));
 
-       task_print_uuid(SPEW, "task load uuid = ", taskp);
+       task_print_id(SPEW, "task load uuid = ", taskp);
 
        config_blob = (u_int *)((char *)manifest + offsetof(OTE_MANIFEST, config_options));
        config_blob_size = (shdr->sh_size - offsetof(OTE_MANIFEST, config_options));
@@ -355,7 +381,7 @@ static status_t task_init_stack(task_t *taskp)
        mptr->u_phys.contig = virtual_to_physical(mptr->u_phys.contig);
 
        mptr->vaddr = TASK_STACK_ADDR - mptr->size;
-       mptr->flags = (TM_UW | TM_UR | TM_PHYS_CONTIG);
+       mptr->flags = (TM_UW | TM_UR | TM_PHYS_CONTIG | TM_PHYS_ALLOCATED);
        mptr->offset = 0;
        mptr->map_attrs = NULL;
 
@@ -418,7 +444,7 @@ static status_t task_init_brk(u_int task_image_addr, task_t *taskp, Elf32_Ehdr *
                mptr->u_phys.contig = virtual_to_physical(mptr->u_phys.contig);
 
                mptr->vaddr = taskp->end_brk;
-               mptr->flags = (TM_UW | TM_UR | TM_PHYS_CONTIG);
+               mptr->flags = (TM_UW | TM_UR | TM_PHYS_CONTIG | TM_PHYS_ALLOCATED);
                mptr->offset = 0;
                mptr->map_attrs = NULL;
 
@@ -475,9 +501,8 @@ static status_t task_alloc_address_map(task_t *taskp)
                 * We're expecting to be able to execute the task in-place,
                 * meaning its PT_LOAD segments, should be page-aligned.
                 */
-               /* XXX TODO: convert this assert to error return later */
-               ASSERT(!(prg_hdr->p_vaddr & PAGE_MASK) &&
-                      !(prg_hdr->p_offset & PAGE_MASK));
+               if((prg_hdr->p_vaddr & PAGE_MASK) || (prg_hdr->p_offset & PAGE_MASK))
+                       return ERR_TASK_GENERIC;
 
                mptr = malloc(sizeof(task_map_t));
                if (mptr == NULL)
@@ -904,6 +929,8 @@ status_t task_init_one_task(task_t *task)
                goto exit;
        }
 
+       task->task_state = TASK_STATE_STARTING;
+
        if (arch_task_init(thread, task) == false) {
                dprintf(CRITICAL, "%s: arch thread/task init failed\n",
                        __func__);
@@ -986,6 +1013,11 @@ task_t *task_find_task_by_uuid(te_service_id_t *uuid)
 
        /* find task for this uuid */
        if (uuid) {
+               te_service_id_t null_uuid = NULL_UUID;
+
+               if (!memcmp(&null_uuid, uuid, sizeof(te_service_id_t)))
+                       return NULL;
+
                list_for_every_entry(&task_list, task, task_t, node) {
                        if (task->task_state != TASK_STATE_UNKNOWN) {
                                if (!memcmp(&task->props.uuid, uuid, sizeof(te_service_id_t))) {
@@ -1038,27 +1070,17 @@ const char *task_get_name_str(const task_t *task, const char *prefix, const char
        return buf;
 }
 
-void
-task_print_uuid(uint32_t level, const char *prefix, const task_t *taskp)
+void task_print_id(uint32_t level, const char *prefix, const task_t *taskp)
 {
+       te_service_id_t null_uuid = NULL_UUID;
+
        if (taskp) {
                char tp_name[OTE_TASK_NAME_MAX_LENGTH+3];
-               const te_service_id_t *uuid = &taskp->props.uuid;
 
-               dprintf(level, "%s%08x-%04x-%04x-%02x%02x%02x%02x%02x%02x%02x%02x%s\n",
-                       (prefix    ? prefix     : ""),
-                       uuid->time_low,
-                       uuid->time_mid,
-                       uuid->time_hi_and_version,
-                       uuid->clock_seq_and_node[0],    /* clock_seq_hi_and_reserved */
-                       uuid->clock_seq_and_node[1],    /* clock_seq_low */
-                       uuid->clock_seq_and_node[2],
-                       uuid->clock_seq_and_node[3],
-                       uuid->clock_seq_and_node[4],
-                       uuid->clock_seq_and_node[5],
-                       uuid->clock_seq_and_node[6],
-                       uuid->clock_seq_and_node[7],
-                       task_get_name_str(taskp, " (", ")", tp_name, sizeof(tp_name)));
+               dprintf(level, "%s", (prefix ? prefix : ""));
+               if (memcmp(&taskp->props.uuid, &null_uuid, sizeof(te_service_id_t)))
+                       task_print_uuid(level, &taskp->props.uuid);
+               dprintf(level, "%s\n", task_get_name_str(taskp, " (", ")", tp_name, sizeof(tp_name)));
        }
 }
 
@@ -1131,11 +1153,15 @@ u_int task_get_active_count()
        int count = 0;
 
        list_for_every_entry(&task_list, task, task_t, node) {
-               if ((task->task_state != TASK_STATE_UNKNOWN) &&
-                   (task->task_state != TASK_STATE_TERMINATED) &&
-                   (task->task_state != TASK_STATE_INIT)) {
+               if ((task->task_state == TASK_STATE_ACTIVE) ||
+                   (task->task_state == TASK_STATE_BLOCKED)) {
                        count++;
                }
        }
        return count;
 }
+
+const struct list_node *task_get_task_list()
+{
+       return &task_list;
+}
index 54d8d94..07cbfac 100644 (file)
@@ -678,12 +678,15 @@ static status_t task_parse_app(uint32_t handle, task_info_t *ti)
 
 /* @brief Start loaded application with manifest restrictions at step#3/3.
  */
-static status_t task_run_app(uint32_t handle, uint32_t reject_task, task_restrictions_t *tr)
+static status_t task_run_app(uint32_t handle, install_type_t install_type, task_restrictions_t *tr)
 {
        status_t err = NO_ERROR;
        task_pending_t *tp = NULL;
        task_t *taskp = NULL;
        int task_registered = 0;
+       task_t *update_task = NULL;
+       task_state_t update_task_state = TASK_STATE_UNKNOWN;
+       te_service_id_t update_task_uuid;
 
        tp = task_find_pending(handle);
        if (!tp) {
@@ -694,7 +697,7 @@ static status_t task_run_app(uint32_t handle, uint32_t reject_task, task_restric
        }
 
        /* a task can be rejected at any state; this triggers resource cleanup */
-       if (!tr || reject_task) {
+       if (!tr || (install_type == INSTALL_TYPE_REJECT)) {
                dprintf(INFO, "%s: task handle 0x%x rejected in state: %d\n",
                        __func__, handle, tp->tp_state);
 
@@ -744,6 +747,30 @@ static status_t task_run_app(uint32_t handle, uint32_t reject_task, task_restric
                        goto exit;
                }
 
+               if (install_type == INSTALL_TYPE_UPDATE) {
+                       update_task = task_find_task_by_uuid(&taskp->props.uuid);
+                       if (update_task) {
+                               if (update_task->props.initial_state & OTE_MANIFEST_TASK_ISTATE_STICKY) {
+                                       task_print_id(INFO, "Sticky task can not be updated ", update_task);
+                                       err = ERR_ALREADY_EXISTS;
+                                       goto exit;
+                               }
+
+                               task_print_id(INFO, "preparing to update ", update_task);
+
+                               /* Block existing task, no new connections allowed to it */
+                               update_task_state = update_task->task_state;
+                               update_task->task_state = TASK_STATE_BLOCKED;
+
+                               /* save UUID in case we need to restore task */
+                               memcpy(&update_task_uuid, &update_task->props.uuid,
+                                      sizeof(update_task->props.uuid));
+
+                               /* Clear existing task UUID to allow task updating */
+                               memset(&update_task->props.uuid, 0, sizeof(update_task->props.uuid));
+                       }
+               }
+
                /*
                 * Atomically commit task (and assign the index) to the known task_list
                 * unless there is an error. TASKP value swapped to track the registered
@@ -761,6 +788,8 @@ static status_t task_run_app(uint32_t handle, uint32_t reject_task, task_restric
 
                task_registered++;
 
+               arch_clean_cache_range((addr_t)tp->tp_task_tlk_addr, tp->tp_task_size);
+
                /*
                 * Init task and start it
                 */
@@ -795,6 +824,16 @@ static status_t task_run_app(uint32_t handle, uint32_t reject_task, task_restric
 
        if (0) {
        exit:
+               if (update_task) {
+                       /* The updated task must not exist in task list (UUID was cleared) */
+                       ASSERT(task_find_task_by_uuid(&update_task_uuid) == NULL);
+
+                       /* repair original task, loading replacement task failed */
+                       memcpy(&update_task->props.uuid, &update_task_uuid, sizeof(update_task->props.uuid));
+                       update_task->task_state = update_task_state;
+                       update_task = NULL;
+               }
+
                if (tp) {
                        if (!task_registered)
                                task_dealloc_app_load_memory_tp(tp);
@@ -805,6 +844,14 @@ static status_t task_run_app(uint32_t handle, uint32_t reject_task, task_restric
                if (err == NO_ERROR)
                        err = ERR_GENERIC;
        }
+
+       if (update_task) {
+               err = task_unload(&update_task);
+               if (err != NO_ERROR) {
+                       task_print_id(INFO, "replaced task unloading failed ", update_task);
+               }
+       }
+
        return err;
 }
 
@@ -880,16 +927,16 @@ static int tlk_handle_app_memory_request(te_app_load_memory_request_args_t *args
        dprintf(SPEW, "%s: mem request app size %d bytes\n",
                __func__, args->app_size);
 
-       task_print_uuid(INFO, "Map task memory request by ", taskp);
+       task_print_id(INFO, "Map task memory request by ", taskp);
 
        /*
         * Simple manifest based permission allowing a task to install
         * other tasks.
         */
        if (!task_allowed_to_load_tasks(taskp)) {
-               task_print_uuid(CRITICAL, "Client tried to perform "
-                               "an operation for which they are "
-                               "not permitted ", taskp);
+               task_print_id(CRITICAL, "Client tried to perform "
+                             "an operation for which they are "
+                             "not permitted ", taskp);
                return -EACCES;
        }
 
@@ -969,9 +1016,9 @@ static int tlk_handle_app_prepare(te_app_prepare_args_t *args)
        dprintf(INFO, "Parsing app handle 0x%x\n", args->app_handle);
 
        if (!task_allowed_to_load_tasks(taskp)) {
-               task_print_uuid(CRITICAL, "Client tried to perform "
-                               "an operation for which they are "
-                               "not permitted ", taskp);
+               task_print_id(CRITICAL, "Client tried to perform "
+                             "an operation for which they are "
+                             "not permitted ", taskp);
                return -EACCES;
        }
 
@@ -1057,9 +1104,9 @@ static int tlk_get_pending_mapping(te_get_pending_map_args_t *args)
                return -EINVAL;
 
        if (!task_allowed_to_load_tasks(taskp)) {
-               task_print_uuid(CRITICAL, "Client tried to perform "
-                               "an operation for which they are "
-                               "not permitted ", taskp);
+               task_print_id(CRITICAL, "Client tried to perform "
+                             "an operation for which they are "
+                             "not permitted ", taskp);
                rval = -EACCES;
                goto exit;
        }
@@ -1130,23 +1177,34 @@ static int tlk_handle_app_start(te_app_start_args_t *args)
                return -EINVAL;
 
        if (!task_allowed_to_load_tasks(taskp)) {
-               task_print_uuid(CRITICAL, "Client tried to perform "
-                               "an operation for which they are "
-                               "not permitted ", taskp);
+               task_print_id(CRITICAL, "Client tried to perform "
+                             "an operation for which they are "
+                             "not permitted ", taskp);
                return -EACCES;
        }
 
-       map_task_app_restrictions(&task_restrictions, &args->app_restrictions);
-
-       if (args->app_reject)
+       switch (args->app_install_type) {
+       case INSTALL_TYPE_REJECT:
                op_info = "reject";
+               break;
+       case INSTALL_TYPE_UPDATE:
+               op_info = "update";
+               break;
+       case INSTALL_TYPE_NORMAL:
+               op_info = "install";
+               break;
+       default:
+               return -EINVAL;
+       }
+
+       map_task_app_restrictions(&task_restrictions, &args->app_restrictions);
 
        dprintf(INFO, "%s app with handle 0x%x\n", op_info, args->app_handle);
 
-       err = task_run_app(args->app_handle, args->app_reject, &task_restrictions);
+       err = task_run_app(args->app_handle, args->app_install_type, &task_restrictions);
        if (err != NO_ERROR) {
                /* Do not log when rejecting a task that no longer exists */
-               if (!args->app_reject || (err != ERR_NOT_FOUND))
+               if ((args->app_install_type != INSTALL_TYPE_REJECT) || (err != ERR_NOT_FOUND))
                        dprintf(CRITICAL, "Could not %s loaded application (%d)\n",
                                op_info, err);
                return -EINVAL;
@@ -1172,9 +1230,9 @@ static int tlk_list_apps(te_app_list_args_t *args)
                return -EINVAL;
 
        if (!task_allowed_to_load_tasks(taskp)) {
-               task_print_uuid(CRITICAL, "Client tried to perform "
-                               "an operation for which they are "
-                               "not permitted ", taskp);
+               task_print_id(CRITICAL, "Client tried to perform "
+                             "an operation for which they are "
+                             "not permitted ", taskp);
                return -EACCES;
        }
 
@@ -1219,9 +1277,9 @@ static int tlk_task_get_info(te_get_task_info_t *args)
         */
        if (!task_allowed_to_load_tasks(taskp) &&
            (args->gti_request_type != OTE_GET_TASK_INFO_REQUEST_SELF)) {
-               task_print_uuid(CRITICAL, "Client tried to perform "
-                               "an operation for which they are "
-                               "not permitted ", taskp);
+               task_print_id(CRITICAL, "Client tried to perform "
+                             "an operation for which they are "
+                             "not permitted ", taskp);
                return -EACCES;
        }
 
@@ -1269,9 +1327,9 @@ static int tlk_task_get_mapping(te_get_task_mapping_t *args)
         */
        if (!task_allowed_to_load_tasks(taskp) &&
            (args->gmt_request_type != OTE_GET_TASK_INFO_REQUEST_SELF)) {
-               task_print_uuid(CRITICAL, "Client tried to perform "
-                               "an operation for which they are "
-                               "not permitted ", taskp);
+               task_print_id(CRITICAL, "Client tried to perform "
+                             "an operation for which they are "
+                             "not permitted ", taskp);
                return -EACCES;
        }
 
@@ -1310,9 +1368,9 @@ static int tlk_task_unload(te_app_unload_args_t *args)
                return -EINVAL;
 
        if (!task_allowed_to_load_tasks(taskp)) {
-               task_print_uuid(CRITICAL, "Client tried to perform "
-                               "an operation for which they are "
-                               "not permitted ", taskp);
+               task_print_id(CRITICAL, "Client tried to perform "
+                             "an operation for which they are "
+                             "not permitted ", taskp);
                return -EACCES;
        }
 
@@ -1334,7 +1392,7 @@ static int tlk_task_unload(te_app_unload_args_t *args)
        if (!target_task)
                return -ESRCH;
 
-       task_print_uuid(INFO, "Request to unload task ", target_task);
+       task_print_id(INFO, "Request to unload task ", target_task);
 
        err = task_unload(&target_task);
        if (err != NO_ERROR) {
@@ -1363,9 +1421,9 @@ static int tlk_task_block(te_app_block_args_t *args)
                return -EINVAL;
 
        if (!task_allowed_to_load_tasks(taskp)) {
-               task_print_uuid(CRITICAL, "Client tried to perform "
-                               "an operation for which they are "
-                               "not permitted ", taskp);
+               task_print_id(CRITICAL, "Client tried to perform "
+                             "an operation for which they are "
+                             "not permitted ", taskp);
                return -EACCES;
        }
 
@@ -1391,7 +1449,7 @@ static int tlk_task_block(te_app_block_args_t *args)
        case TASK_STATE_BLOCKED:
        case TASK_STATE_ACTIVE:
                target_task->task_state = TASK_STATE_BLOCKED;
-               task_print_uuid(INFO, "Blocked task ", target_task);
+               task_print_id(INFO, "Blocked task ", target_task);
                break;
        default:
                dprintf(INFO, "Request to block task#%d in state %d -- rejected\n",
@@ -1412,9 +1470,9 @@ static int tlk_task_unblock(te_app_block_args_t *args)
                return -EINVAL;
 
        if (!task_allowed_to_load_tasks(taskp)) {
-               task_print_uuid(CRITICAL, "Client tried to perform "
-                               "an operation for which they are "
-                               "not permitted ", taskp);
+               task_print_id(CRITICAL, "Client tried to perform "
+                             "an operation for which they are "
+                             "not permitted ", taskp);
                return -EACCES;
        }
 
@@ -1439,7 +1497,7 @@ static int tlk_task_unblock(te_app_block_args_t *args)
        switch(target_task->task_state) {
        case TASK_STATE_BLOCKED:
                target_task->task_state = TASK_STATE_ACTIVE;
-               task_print_uuid(INFO, "Unblocked task ", target_task);
+               task_print_id(INFO, "Unblocked task ", target_task);
                break;
        default:
                dprintf(INFO, "Request to unblock task#%d in state %d -- rejected\n",
index 824cfa5..ac2ce64 100644 (file)
@@ -26,6 +26,7 @@
 #include <string.h>
 #include <err.h>
 #include <malloc.h>
+#include <arch/arm/mmu.h>
 #include <kernel/task.h>
 #include <kernel/thread.h>
 #include <kernel/task_load.h>
@@ -52,10 +53,15 @@ static void task_free_resources(task_t **taskp_p)
                ASSERT(list_is_empty(&taskp->thread_node));
                ASSERT(list_in_list(&taskp->node));
 
+               memset(&taskp->props.uuid, 0, sizeof(te_service_id_t));
+
                list_for_every_entry_safe(&taskp->map_list, mptr, mptr_tmp, task_map_t, node) {
                        arch_task_unmap_memory(taskp, mptr);
                }
 
+               /* deallocate the task page tables */
+               arm_mmu_dealloc_upagetable(taskp);
+
                /* clear task image in tlk heap before deallocating it */
                memset(taskp->elf_hdr, 0, taskp->task_size);
 
@@ -68,6 +74,8 @@ static void task_free_resources(task_t **taskp_p)
                list_delete(&taskp->node);
                exit_critical_section();
 
+               arch_task_killed(taskp);
+
                /* Clear task header in task_list */
                memset(taskp, 0, sizeof(task_t));
 
@@ -172,6 +180,8 @@ void task_thread_killed(thread_t *thread)
        ASSERT(thread->arch.task);
        ASSERT(list_in_list(&thread->task_node));
 
+       arch_task_thread_killed(thread);
+
        /* remove the thread from TE session lists */
        te_session_cancel_thread(thread);
 
@@ -187,6 +197,7 @@ void task_thread_killed(thread_t *thread)
         */
        if (list_is_empty(&taskp->thread_node)) {
                taskp->task_state = TASK_STATE_TERMINATED;
+               memset(&taskp->props.uuid, 0, sizeof(te_service_id_t));
                event_signal(&task_reaper_event, false);
        }
 }
@@ -218,7 +229,7 @@ status_t task_unload(task_t **taskp_p)
        }
        taskp = *taskp_p;
 
-       task_print_uuid(INFO, "task unload request ", taskp);
+       task_print_id(INFO, "task unload request ", taskp);
 
 #if HAVE_UNLOAD_STATIC_TASKS == 0
        if (taskp->task_type != TASK_TYPE_LOADED) {
@@ -248,6 +259,12 @@ status_t task_unload(task_t **taskp_p)
                }
 
                taskp->task_state = TASK_STATE_BLOCKED;
+               /* FALLTHROUGH */
+
+       case TASK_STATE_STARTING:
+               /* Task starting, thread exist but not yet running; error case */
+               if (!ch_state)
+                       ch_state = "STARTING";
 
                /* The loop kills all kernel threads of the task which will wakeup
                 * task reaper which will reclaim resources when the task dies.
index bfa4692..c216702 100644 (file)
@@ -56,6 +56,11 @@ void *memalign(size_t boundary, size_t size)
        return heap_alloc(size, boundary);
 }
 
+void free_memalign(void *ptr)
+{
+       heap_free(ptr);
+}
+
 void *calloc(size_t count, size_t size)
 {
        void *ptr;
diff --git a/lib/monitor/arm64/monitor_cpu.S b/lib/monitor/arm64/monitor_cpu.S
deleted file mode 100644 (file)
index 3547261..0000000
+++ /dev/null
@@ -1,174 +0,0 @@
-/*
- * Copyright (c) 2014, NVIDIA CORPORATION. All rights reserved
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files
- * (the "Software"), to deal in the Software without restriction,
- * including without limitation the rights to use, copy, modify, merge,
- * publish, distribute, sublicense, and/or sell copies of the Software,
- * and to permit persons to whom the Software is furnished to do so,
- * subject to the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
- * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
- * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
- * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
- * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- */
-#include <config.h>
-#include <asm.h>
-#include <arch/arm.h>
-#include <arm64/asm.h>
-#include <psci.h>
-#include <arm64/monitor_macros.h>
-
-/* called both for cold reset and boot_secondary */
-FUNCTION(mon_init_cpu)
-       mrs     x4, currentel
-       cmp     x4, #MODE_EL(3)
-       b.ne    .               // error, if not EL3
-
-       /* initialize SCR to secure state */
-       mov     x3, #(MON_SCR_RESV1 | MON_SCR_64BIT)
-       msr     scr_el3, x3
-       isb
-
-       /* set vbar (with phys, to catch setup errors) */
-       adr     x3, _vector_el3
-       msr     vbar_el3, x3
-
-       /* enable I/D caches, disable MMU and alignment checks */
-       mrs     x4, sctlr_el3
-       bic     x4, x4, #(1 << 25)
-       orr     x4, x4, #(1 << 12)
-       orr     x4, x4, #(1 << 2)
-       bic     x4, x4, #((1 << 1) | (1 << 0))
-       msr     sctlr_el3, x4
-
-       /* set freq for arch general timer */
-       ldr     x0, =ARM_SYSTEM_COUNTER_FREQ
-       msr     cntfrq_el0, x0
-
-       /* enable the cycle count register */
-       mrs     x0, pmcr_el0
-       ubfx    x0, x0, #11, #5         // read PMCR.N field
-       mov     x4, #1
-       lsl     x0, x4, x0
-       sub     x0, x0, #1              // mask of event counters
-       orr     x0, x0, #0x80000000     // disable overflow intrs
-       msr     pmintenclr_el1, x0
-       msr     pmuserenr_el0, x4       // enable user mode access
-
-       /* mark per-CPU dist GROUP0 intrs non-secure */
-       ldr     x4, =ARM_GIC_DIST_BASE
-       mov     w3, #(~0)
-       str     w3, [x4, ARM_GIC_GICD_IGROUPR0]
-
-       /* enables GROUP0/GROUP1 intrs, signals GROUP0 with FIQ */
-       ldr     x4, =ARM_GIC_CPU_BASE
-       mov     w3, #((0xF << 4) | (0x1 << 3) | (0x3 << 0))
-       str     w3, [x4, ARM_GIC_GICC_CTLR]
-
-       /* init low pri mask, so NS can set its value */
-       mov     w3, #0xFF
-       str     w3, [x4, ARM_GIC_GICC_PMR]
-
-       /* disable copro traps to EL3 */
-       msr     cptr_el3, xzr
-
-       cpuidx  x12
-
-       /* setup per-cpu monitor stack (dividing up single 4K page) */
-       msr     spsel, #1
-       ldr     x3, =monitor_stack_top
-       lsl     x4, x12, #10    // each CPU gets a 1K stack
-       sub     x3, x3, x4
-       mov     sp, x3
-
-       ret
-
-/*
- * Return to address saved in __mon_cpu_return_addr, in
- * AARCH32 SVC (non-secure) mode.
- */
-FUNCTION(mon_return_aarch32_ns)
-       /* load return address */
-       cpuidx  x1
-       adr     x2, __mon_cpu_return_addr
-       ldr     x2, [x2, x1, lsl #3]
-
-       msr     elr_el3, x2
-       mov     x2, #(MON_SCR_RESV1 | MON_SCR_32BIT | MON_SCR_NS_MODE)
-       msr     scr_el3, x2
-       mov     x2, #(MON_SPSR_EXC_MASKED | MODE_SVC)
-       msr     spsr_el3, x2
-
-       eret
-
-/*
- * Return to address saved in __mon_cpu_return_addr, in
- * AARCH64 EL2 (non-secure) mode.
- */
-FUNCTION(mon_return_aarch64_ns)
-       /* load return address */
-       cpuidx  x1
-       adr     x2, __mon_cpu_return_addr
-       ldr     x2, [x2, x1, lsl #3]
-
-       msr     elr_el3, x2
-       mov     x2, #(MON_SCR_RESV1 | MON_SCR_64BIT | MON_SCR_NS_MODE)
-       msr     scr_el3, x2
-       mov     x2, #(MON_SPSR_EXC_MASKED | MODE_EL(2))
-       msr     spsr_el3, x2
-
-       eret
-
-/*
- * Routine to setup secondary CPU state and return, leaving
- * the primary CPU to initialize the secureos.
- */
-FUNCTION(boot_secondary)
-       bl      mon_init_cpu
-       bl      mon_enable_mmu
-
-       /* reload vbar with virt addr */
-       adr     x0, _vector_el3
-       msr     vbar_el3, x0
-       isb
-
-       cpuidx  x0
-       bl      platform_psci_cpu_has_reset
-       b       mon_return_aarch64_ns
-
-/* get the CPU ID */
-FUNCTION(mon_get_cpu_id)
-       mrs     x0, midr_el1
-       ubfx    x0, x0, #4, #12
-       ret
-
-.ltorg
-.align 3
-.global __mon_cpu_reset_vector
-__mon_cpu_reset_vector:
-       b       boot_secondary
-
-.ltorg
-.align 3
-.global __mon_cpu_return_addr
-__mon_cpu_return_addr:
-       .rept MONCPUS
-       .quad 0
-       .endr
-
-.ltorg
-.align 3
-.global __mon_cpu_return_mode
-__mon_cpu_return_mode:
-       .rept MONCPUS
-       .quad 0
-       .endr
diff --git a/lib/version/rules.mk b/lib/version/rules.mk
new file mode 100644 (file)
index 0000000..39628e3
--- /dev/null
@@ -0,0 +1,10 @@
+LOCAL_DIR := $(GET_LOCAL_DIR)
+
+MODULE := $(LOCAL_DIR)
+
+MODULE_SRCS += \
+       $(LOCAL_DIR)/version.c
+
+include make/module.mk
+
+EXTRA_BUILDRULES += lib/version/version.mk
diff --git a/lib/version/version.c b/lib/version/version.c
new file mode 100644 (file)
index 0000000..4ef1aea
--- /dev/null
@@ -0,0 +1 @@
+char *version = "built: " __DATE__ " " __TIME__;
diff --git a/lib/version/version.mk b/lib/version/version.mk
new file mode 100644 (file)
index 0000000..03fc2ed
--- /dev/null
@@ -0,0 +1,6 @@
+LOCAL_DIR := $(GET_LOCAL_DIR)
+
+MONITOR_OBJS := $(ALLMONITOR_OBJS) $(MON_LINKER_SCRIPT)
+SECUREOS_OBJS := $(ALLMODULE_OBJS) $(LINKER_SCRIPT) $(TASK_OBJ) $(EXTRA_OBJS)
+
+$(call TOBUILDDIR,$(LOCAL_DIR)/version.o): $(MONITOR_OBJS) $(SECUREOS_OBJS)
index b109337..24d4a97 100644 (file)
@@ -1,19 +1,15 @@
 # comment out or override if you want to see the full output of each command
 NOECHO ?= @
 
-$(OUTELF): $(ALLMODULE_OBJS) $(EXTRA_OBJS) $(LINKER_SCRIPT)
+$(OUTELF): $(ALLMODULE_OBJS) $(EXTRA_OBJS) $(LINKER_SCRIPT) $(MONLIB)
        @echo linking $@
        $(NOECHO)$(SIZE) -t $(ALLMODULE_OBJS)
-       $(NOECHO)$(LD) $(GLOBAL_LDFLAGS) -T $(LINKER_SCRIPT) $(ALLMODULE_OBJS) $(EXTRA_OBJS) $(LIBGCC) -o $@
+       $(NOECHO)$(LD) $(GLOBAL_LDFLAGS) -T $(LINKER_SCRIPT) $(ALLMODULE_OBJS) $(EXTRA_OBJS) $(LIBGCC) $(MONLIB) -o $@
 
 $(OUTTASK): $(OUTSYS) $(TASK_OBJ) $(LINKER_SCRIPT)
        @echo linking $@
        $(LD) $(GLOBAL_LDFLAGS) --no-warn-mismatch -T $(LINKER_SCRIPT) $(OUTSYS) $(TASK_OBJ) $(LIBGCC) -o $@
 
-$(MONBIN): $(MONELF)
-       @echo generating image: $@
-       $(NOECHO)$(MON_OBJCOPY) -O binary $< $@
-
 $(OUTBIN): $(OUTTASK)
        @echo generating image: $@
        $(NOECHO)$(OBJCOPY) -O binary $< $@
@@ -22,17 +18,13 @@ $(IMGBIN): $(MONBIN) $(OUTBIN)
        @echo combining monitor / task binaries
        cat $^ > $@
 
-$(LK_IMAGE): $(IMGBIN)
+$(TOSIMAGE): $(IMGBIN)
        @echo generating image: $@
        tools/gen_tos_part_img.py $< $@
 
-$(OUTSYS): $(ALLMODULE_OBJS) $(EXTRA_OBJS)
+$(OUTSYS): $(ALLMODULE_OBJS) $(EXTRA_OBJS) $(MONLIB)
        @echo partial linking $@
-       $(NOECHO)$(LD) -r $(ALLMODULE_OBJS) $(EXTRA_OBJS) -o $@
-
-$(MONELF): $(ALLMONITOR_OBJS) $(MON_LINKER_SCRIPT)
-       @echo linking $@
-       $(MON_LD) $(GLOBAL_LDFLAGS) -T $(MON_LINKER_SCRIPT) $(ALLMONITOR_OBJS) $(LIBGCC) -o $@
+       $(NOECHO)$(LD) -r $(ALLMODULE_OBJS) $(EXTRA_OBJS) $(MONLIB) -o $@
 
 $(OUTELF).sym: $(OUTELF)
        @echo generating symbols: $@
index a79d3d4..14aca4f 100644 (file)
--- a/makefile
+++ b/makefile
@@ -1,9 +1,12 @@
-#PREFIX ?= .
 PREFIX ?= ..
 
+ifeq ($(TARGET_ARCH),arm64)
+TOOLCHAIN_PREFIX ?= ../tools/aarch64-linux-android-4.8/bin/aarch64-linux-android-
+TOOLCHAIN_PREFIX64 ?= ../tools/aarch64-linux-android-4.8/bin/aarch64-linux-android-
+else
 TOOLCHAIN_PREFIX ?= ../tools/arm-eabi-4.7/bin/arm-eabi-
 TOOLCHAIN_PREFIX64 ?= ../tools/aarch64-linux-android-4.8/bin/aarch64-linux-android-
-PROJECT=tegra
+endif
 
 ifeq ($(MAKECMDGOALS),spotless)
 spotless:
@@ -44,10 +47,14 @@ OUTTASK := $(BUILDDIR)/lk.task
 CONFIGHEADER := $(BUILDDIR)/config.h
 IMGBIN := $(BUILDDIR)/img.bin
 LK_IMAGE ?= $(BUILDDIR)/tos.img
+MONLIB := $(BUILDDIR)/secure_monitor/libmonitor.a
 
-# conditionally built monitor files
-MONELF :=
-MONBIN :=
+ifneq ($(TARGET),t124)
+DEFINES += \
+       WITH_MONITOR_BIN=1
+MONLIB :=
+MONBIN := $(BUILDDIR)/secure_monitor/monitor.bin
+endif
 
 INCLUDES := -I$(BUILDDIR) -Iinclude -I../lib/include
 GLOBAL_OPTFLAGS ?= -Os
@@ -63,7 +70,7 @@ GLOBAL_COMPILEFLAGS += -ffunction-sections -fdata-sections
 GLOBAL_LDFLAGS += -gc-sections
 
 # top level rule
-all:: $(LK_IMAGE) $(OUTTASK) $(OUTELF).lst $(OUTELF).debug.lst $(OUTELF).sym $(OUTELF).size
+all:: $(TOSIMAGE) $(OUTTASK) $(OUTELF).lst $(OUTELF).debug.lst $(OUTELF).sym $(OUTELF).size
 
 # master module object list
 ALLOBJS_MODULE :=
@@ -79,7 +86,7 @@ MON_LINKER_SCRIPT :=
 GENERATED := $(CONFIGHEADER)
 
 # anything added to DEFINES will be put into $(BUILDDIR)/config.h
-DEFINES := LK=1
+DEFINES += LK=1
 
 # Anything added to SRCDEPS will become a dependency of every source file in the system.
 # Useful for header files that may be included by one or more source files.
@@ -108,6 +115,8 @@ include platform/$(PLATFORM)/rules.mk
 $(info PROJECT = $(PROJECT))
 $(info PLATFORM = $(PLATFORM))
 $(info TARGET = $(TARGET))
+$(info MONLIB = $(MONLIB))
+$(info TARGET_ARCH = $(TARGET_ARCH))
 
 include arch/$(ARCH)/rules.mk
 include platform/rules.mk
@@ -189,6 +198,8 @@ $(warning CPPFLAGS=$(CPPFLAGS))
 $(error CPPFLAGS is not empty, please use GLOBAL_CPPFLAGS or MODULE_CPPFLAGS)
 endif
 
+include lib/version/version.mk
+
 # the logic to compile and link stuff is in here
 include make/build.mk
 
index 6be7650..a958030 100644 (file)
@@ -212,6 +212,11 @@ go_virtual:
        mov     r0, #1
        mcr     p15, 0, r0, c9, c14, 0
 
+       /* enable user space CNTVCT access */
+       mrc     p15, 0, r0, c14, c1, 0
+       orr     r0, r0, #(1 << 1)
+       mcr     p15, 0, r0, c14, c1, 0
+
 1110:
        ldr     r0, =platform_config_interrupts
        blx     r0
index 6bd1d6b..1587d01 100644 (file)
@@ -112,9 +112,8 @@ status_t unmask_interrupt(unsigned int vector)
 
 enum handler_return platform_irq(struct arm_iframe *iframe)
 {
-       enum handler_return ret = INT_NO_RESCHEDULE;
        uint32_t vector;
-       struct tz_monitor_frame *smc_frame = NULL, frame;
+       struct tz_monitor_frame frame;
 
 #if DEBUG
        /*
@@ -129,28 +128,18 @@ enum handler_return platform_irq(struct arm_iframe *iframe)
 
        if (vector == 1023) {
                /* normal spurious intr, just return */
-               return ret;
+               return INT_NO_RESCHEDULE;
        } else {
                /* at the moment, NS owns all interrupts */
                ASSERT(vector == 1022);
        }
 
-#if defined(WITH_MONITOR_BIN)
        memset(&frame, 0, sizeof(struct tz_monitor_frame));
        frame.r[0] = SMC_ERR_PREEMPT_BY_IRQ;
 
-       smc_frame = tz_switch_to_ns(SMC_TOS_COMPLETION, &frame);
-       while (smc_frame->r[0] != SMC_TOS_RESTART) {
-               frame.r[0] = SMC_ERR_PREEMPT_BY_IRQ;
-               smc_frame = tz_switch_to_ns(SMC_TOS_COMPLETION, &frame);
-       }
-#else
-       smc_frame = tz_switch_to_ns(SMC_TOS_PREEMPT_BY_IRQ, NULL);
-       while (smc_frame)
-               smc_frame = tz_switch_to_ns(SMC_TOS_PREEMPT_BY_IRQ, NULL);
-#endif
+       (void)tz_switch_to_ns(SMC_TOS_PREEMPT_BY_IRQ, &frame);
 
-       return ret;
+       return INT_NO_RESCHEDULE;
 }
 
 void platform_fiq(struct arm_iframe *frame)
index f73cb23..0bce7b1 100644 (file)
@@ -42,6 +42,7 @@
 #include <arch/outercache.h>
 #endif
 #include <platform/platform_p.h>
+#include <platform/platform_monitor.h>
 
 #define        MB              (1024 * 1024)
 
@@ -58,9 +59,6 @@ extern uint32_t __jumpback_addr;
 
 uint32_t debug_uart_id = DEFAULT_DEBUG_PORT;
 
-static te_ss_op_t *ss_op_shmem;
-static te_ss_op_t *ns_ss_op_shmem;
-
 /* track available kernel VA space */
 vaddr_t platform_vaspace_ptr;
 vaddr_t platform_vaspace_end;
@@ -68,11 +66,16 @@ vaddr_t platform_vaspace_end;
 extern unsigned long cbstruct_addr;
 extern unsigned long cbuf_addr;
 
-static addr_t user_vector_page;
-
 void platform_early_init(void)
 {
+#if WITH_LIB_VERSION
+       extern char *version;
+#endif
        platform_init_debug_port(debug_uart_id);
+
+#if WITH_LIB_VERSION
+       dprintf(CRITICAL, "starting platform early init (TLK %s)\n", version);
+#endif
 }
 
 void platform_idle(void)
@@ -118,30 +121,10 @@ void platform_idle(void)
 
 void platform_init(void)
 {
-       task_map_t mptr;
-       arm_phys_attrs_t attrs;
        uint32_t reg = 0;
 
        platform_init_cpu();
 
-       /* map read-only user vector page in kernel */
-       arm_mmu_desc_set_default_kernel(&attrs);
-
-       mptr.map_attrs = &attrs;
-       mptr.size = PAGE_SIZE;
-       mptr.flags = TM_UR;
-
-       arm_mmu_map_kpage(0xFFFF0000, virtual_to_physical(user_vector_page), &mptr);
-       arm_invalidate_tlb();
-
-       memset((void *)user_vector_page, 0, mptr.size);
-
-       /* load user vectors (used by libc to get tls) */
-       memcpy((char *)user_vector_page + 0xFE0, arm_get_tls, 0x8);
-       memcpy((char *)user_vector_page + 0xFE8, arm_get_tls, 0x8);
-
-       platform_clean_invalidate_cache_range(user_vector_page, mptr.size);
-
        platform_setup_keys();
 
        /*
@@ -166,10 +149,6 @@ void platform_init_mmu_mappings(void)
        _heap_end = (VMEMBASE + __load_phys_size) - __early_heap_allocs;
        _heap_end &= ~PAGE_MASK;
 
-       /* reserve user vector page (before heap is initialized) */
-       _heap_end -= PAGE_SIZE;
-       user_vector_page = _heap_end;
-
        /* setup available vaspace (starts at end of carveout memory) */
        platform_vaspace_ptr = VMEMBASE + __load_phys_size;
        platform_vaspace_end = platform_vaspace_ptr + (VMEMSIZE - __load_phys_size);
@@ -201,14 +180,6 @@ uint32_t platform_get_time_us(void)
 
 status_t platform_ss_register_handler(struct tz_monitor_frame *frame)
 {
-       /* r[1] -> address of shared fs operation buffer */
-       ns_ss_op_shmem = (te_ss_op_t *)(uintptr_t)frame->r[1];
-
-       ss_op_shmem = (te_ss_op_t *)tz_map_shared_mem((nsaddr_t)frame->r[1],
-                                               sizeof(*ss_op_shmem));
-       if (!ss_op_shmem)
-               return ERR_GENERIC;
-
        return NO_ERROR;
 }
 
@@ -241,256 +212,14 @@ status_t set_log_phy_addr(nsaddr_t _ns_cb_struct_addr)
        return NO_ERROR;
 }
 
-static int validate_rpmb_frame_arg(te_storage_param_t *arg)
-{
-       /* validate frame length */
-       if (arg->mem.len != RPMB_FRAME_SIZE)
-               return -EINVAL;
-
-       /* validate frame memory range */
-       if (!task_valid_address((vaddr_t)arg->mem.base, arg->mem.len))
-               return -EFAULT;
-
-       return 0;
-}
-
-int platform_ss_request_handler(te_storage_request_t *req)
+int platform_ss_request_handler(void)
 {
-       struct tz_monitor_frame frame, *smc_frame;
-       int result;
-
-       ss_op_shmem->type = req->type;
-       ss_op_shmem->result = 0;
-
-       dprintf(INFO, "%s: type 0x%x\n", __func__, req->type);
-
-       switch (ss_op_shmem->type) {
-       case OTE_FILE_REQ_TYPE_CREATE:
-               /* input args: dirname, filename, flags */
-               strncpy(ss_op_shmem->params.f_create.dname,
-                       req->args[0].mem.base,
-                       sizeof(ss_op_shmem->params.f_create.dname));
-               strncpy(ss_op_shmem->params.f_create.fname,
-                       req->args[1].mem.base,
-                       sizeof(ss_op_shmem->params.f_create.fname));
-               ss_op_shmem->params.f_create.flags = req->args[2].val.a;
-
-               ss_op_shmem->params_size =
-                       sizeof(ss_op_shmem->params.f_create);
-               break;
-       case OTE_FILE_REQ_TYPE_DELETE:
-               /* input args: dirname, filename */
-               strncpy((char *)ss_op_shmem->params.f_delete.dname,
-                       req->args[0].mem.base,
-                       sizeof(ss_op_shmem->params.f_delete.dname));
-               strncpy((char *)ss_op_shmem->params.f_delete.fname,
-                       req->args[1].mem.base,
-                       sizeof(ss_op_shmem->params.f_delete.fname));
-
-               ss_op_shmem->params_size =
-                       sizeof(ss_op_shmem->params.f_delete);
-               break;
-       case OTE_FILE_REQ_TYPE_OPEN:
-               /* input args: dirname, filename, flags */
-               strncpy((char *)ss_op_shmem->params.f_open.dname,
-                       req->args[0].mem.base,
-                       sizeof(ss_op_shmem->params.f_open.dname));
-               strncpy((char *)ss_op_shmem->params.f_open.fname,
-                       req->args[1].mem.base,
-                       sizeof(ss_op_shmem->params.f_open.fname));
-               ss_op_shmem->params.f_open.flags = req->args[2].val.a;
-
-               ss_op_shmem->params_size = sizeof(ss_op_shmem->params.f_open);
-               break;
-       case OTE_FILE_REQ_TYPE_CLOSE:
-               /* input args: file handle */
-               ss_op_shmem->params.f_close.handle = req->args[0].val.a;
-
-               ss_op_shmem->params_size = sizeof(ss_op_shmem->params.f_close);
-               break;
-       case OTE_FILE_REQ_TYPE_READ:
-               /* validate read buffer */
-               if (!task_valid_address((vaddr_t)req->args[1].mem.base,
-                                       req->args[1].mem.len)) {
-                       return -EFAULT;
-               }
-
-               /* validate read buffer size */
-               if (req->args[1].mem.len >
-                       sizeof(ss_op_shmem->params.f_read.data)) {
-                       return -EINVAL;
-               }
-
-               /* input args: file_handle, read buffer */
-               ss_op_shmem->params.f_close.handle = req->args[0].val.a;
-               ss_op_shmem->params.f_read.data_size = req->args[1].mem.len;
-
-               ss_op_shmem->params_size = sizeof(ss_op_shmem->params.f_read);
-               break;
-       case OTE_FILE_REQ_TYPE_WRITE:
-               /* validate write buffer */
-               if (!task_valid_address((vaddr_t)req->args[1].mem.base,
-                                       req->args[1].mem.len)) {
-                       return -EFAULT;
-               }
-
-               /* validate write buffer size */
-               if (req->args[1].mem.len >
-                       sizeof(ss_op_shmem->params.f_write.data)) {
-                       return -EINVAL;
-               }
-
-               /* input args: file_handle, write buffer */
-               ss_op_shmem->params.f_write.handle = req->args[0].val.a;
-               ss_op_shmem->params.f_write.data_size = req->args[1].mem.len;
-               memcpy((void*)ss_op_shmem->params.f_write.data,
-                       req->args[1].mem.base,
-                       ss_op_shmem->params.f_write.data_size);
-
-               ss_op_shmem->params_size = sizeof(ss_op_shmem->params.f_write);
-               break;
-       case OTE_FILE_REQ_TYPE_GET_SIZE:
-               /* input arg: file_handle */
-               ss_op_shmem->params.f_getsize.handle = req->args[0].val.a;
-
-               ss_op_shmem->params_size =
-                       sizeof(ss_op_shmem->params.f_getsize);
-               break;
-       case OTE_FILE_REQ_TYPE_SEEK:
-               /* input args: file_handle, offset, whence */
-               ss_op_shmem->params.f_seek.handle = req->args[0].val.a;
-               ss_op_shmem->params.f_seek.offset = req->args[1].val.a;
-               ss_op_shmem->params.f_seek.whence = req->args[2].val.a;
-
-               ss_op_shmem->params_size = sizeof(ss_op_shmem->params.f_seek);
-               break;
-       case OTE_FILE_REQ_TYPE_TRUNC:
-               /* input args: file_handle, length */
-               ss_op_shmem->params.f_trunc.handle = req->args[0].val.a;
-               ss_op_shmem->params.f_trunc.length = req->args[1].val.a;
-
-               ss_op_shmem->params_size = sizeof(ss_op_shmem->params.f_trunc);
-               break;
-       case OTE_FILE_REQ_TYPE_RPMB_WRITE:
-               /* validate request frame */
-               result = validate_rpmb_frame_arg(&req->args[0]);
-               if (result) {
-                       dprintf(CRITICAL, "%s: write req frame invalid\n",
-                               __func__);
-                       return result;
-               }
-
-               /* validate request-response frame */
-               result = validate_rpmb_frame_arg(&req->args[1]);
-               if (result) {
-                       dprintf(CRITICAL, "%s: write req-resp frame invalid\n",
-                               __func__);
-                       return result;
-               }
-
-               /* validate response frame */
-               result = validate_rpmb_frame_arg(&req->args[2]);
-               if (result) {
-                       dprintf(CRITICAL, "%s: write resp frame invalid\n",
-                               __func__);
-                       return result;
-               }
-
-               /* input args: request frame, request-response frame */
-               memcpy((void*)ss_op_shmem->params.f_rpmb_write.req_frame,
-                       req->args[0].mem.base, req->args[0].mem.len);
-               memcpy((void*)ss_op_shmem->params.f_rpmb_write.req_resp_frame,
-                       req->args[1].mem.base, req->args[1].mem.len);
-
-               ss_op_shmem->params_size =
-                       sizeof(ss_op_shmem->params.f_rpmb_write);
-               break;
-       case OTE_FILE_REQ_TYPE_RPMB_READ:
-               /* validate request frame */
-               result = validate_rpmb_frame_arg(&req->args[0]);
-               if (result) {
-                       dprintf(CRITICAL, "%s: read req frame invalid\n",
-                               __func__);
-                       return result;
-               }
-
-               /* validate response frame */
-               result = validate_rpmb_frame_arg(&req->args[1]);
-               if (result) {
-                       dprintf(CRITICAL, "%s: read resp frame invalid\n",
-                               __func__);
-                       return result;
-               }
-
-               /* input arg: request frame */
-               memcpy((void*)ss_op_shmem->params.f_rpmb_read.req_frame,
-                       req->args[0].mem.base, req->args[0].mem.len);
-
-               ss_op_shmem->params_size =
-                       sizeof(ss_op_shmem->params.f_rpmb_read);
-               break;
-       default:
-               return -EINVAL;
-       }
-
-       /* adjust size down to only include required parameters */
-       ss_op_shmem->req_size = (sizeof(te_ss_op_t) - sizeof(uint32_t) -
-               sizeof(te_ss_req_params_t)) + ss_op_shmem->params_size;
+       struct tz_monitor_frame frame;
 
-#if defined(WITH_MONITOR_BIN)
        memset(&frame, 0, sizeof(struct tz_monitor_frame));
        frame.r[0] = SMC_ERR_PREEMPT_BY_FS;
 
-       smc_frame = tz_switch_to_ns(SMC_TOS_COMPLETION, &frame);
-       while (smc_frame->r[0] != SMC_TOS_RESTART) {
-               frame.r[0] = SMC_ERR_PREEMPT_BY_IRQ;
-               smc_frame = tz_switch_to_ns(SMC_TOS_COMPLETION, &frame);
-       }
-#else
-       smc_frame = tz_switch_to_ns(SMC_TOS_PREEMPT_BY_FS, NULL);
-       while (smc_frame)
-               smc_frame = tz_switch_to_ns(SMC_TOS_PREEMPT_BY_IRQ, NULL);
-#endif
-
-       req->result = ss_op_shmem->result;
-       if (req->result != 0) {
-               dprintf(CRITICAL, "%s: call to non-secure world failed 0x%x\n",
-                       __func__, req->result);
-               return req->result;
-       }
-
-       /* move any expected return data into request structure */
-       switch (ss_op_shmem->type) {
-       case OTE_FILE_REQ_TYPE_OPEN:
-               /* output arg: file_handle */
-               req->args[3].val.a = ss_op_shmem->params.f_open.handle;
-               break;
-       case OTE_FILE_REQ_TYPE_READ:
-               /* output args: amount of data read, data */
-               req->args[1].mem.len = ss_op_shmem->params.f_read.data_size;
-               memcpy(req->args[1].mem.base,
-                       (void *)ss_op_shmem->params.f_read.data,
-                       req->args[1].mem.len);
-               break;
-       case OTE_FILE_REQ_TYPE_GET_SIZE:
-               /* output arg: file size */
-               req->args[1].val.a = ss_op_shmem->params.f_getsize.size;
-               break;
-       case OTE_FILE_REQ_TYPE_RPMB_WRITE:
-               /* output arg: response frame */
-               memcpy(req->args[2].mem.base,
-                       (void *)ss_op_shmem->params.f_rpmb_write.resp_frame,
-                       req->args[2].mem.len);
-               break;
-       case OTE_FILE_REQ_TYPE_RPMB_READ:
-               /* output arg: response frame */
-               memcpy(req->args[1].mem.base,
-                       (void *)ss_op_shmem->params.f_rpmb_read.resp_frame,
-                       req->args[1].mem.len);
-               break;
-       default:
-               break;
-       }
+       (void)tz_switch_to_ns(SMC_TOS_PREEMPT_BY_FS, &frame);
 
        return 0;
 }
index beedc01..2c7f9b6 100644 (file)
@@ -38,6 +38,9 @@
 #include <arch/arm.h>
 #include <arch/arm/mmu.h>
 #include <platform/platform_p.h>
+#include <platform/platform_monitor.h>
+#include <platform/platform_cpu.h>
+#include <platform/platform_sip.h>
 #include <ote_intf.h>
 
 #define MONITOR_MODE_STACK_SZ  4096
index f967483..3d56e5b 100644 (file)
@@ -52,12 +52,12 @@ static const unsigned int system_timer_irq = 157;
 
 static inline void write_timer_reg(uint32_t reg, unsigned int data)
 {
-       *(volatile uint32_t *)(TEGRA_TMR10_BASE + (reg)) = data;
+       *(volatile uint32_t *)(TEGRA_TMR0_BASE + (reg)) = data;
 }
 
 static inline uint32_t read_timer_reg(uint32_t reg)
 {
-       return *(volatile uint32_t *)(TEGRA_TMR10_BASE + (reg));
+       return *(volatile uint32_t *)(TEGRA_TMR0_BASE + (reg));
 }
 
 status_t platform_set_periodic_timer(platform_timer_callback callback, void *arg, lk_time_t interval_ms)
index d3aad2a..2d158f5 100644 (file)
 #include <arch/arm.h>
 #include <arch/arm/mmu.h>
 #include <platform/platform_p.h>
+#include <platform/platform_ta.h>
+#include <platform/platform_tos.h>
+#include <platform/platform_monitor.h>
+#include <platform/platform_sip.h>
 #include <ote_intf.h>
 
 #define TZ_UNSUPPORTED_PARAM   0xDEADBEEF
@@ -325,6 +329,14 @@ static uint32_t tz_copyin_params(te_request_t *req, te_oper_param_t *in_params)
                        dprintf(SPEW, "%s: %d: MEM_RW: len 0x%x\n",
                                __func__, i, req_params[i].u.Mem.len);
                        break;
+               case TE_PARAM_TYPE_PERSIST_MEM_RO:
+                       dprintf(SPEW, "%s: %d: PERSIST_MEM_RO: len 0x%x\n",
+                               __func__, i, req_params[i].u.Mem.len);
+                       break;
+               case TE_PARAM_TYPE_PERSIST_MEM_RW:
+                       dprintf(SPEW, "%s: %d: PERSIST_MEM_RW: len 0x%x\n",
+                               __func__, i, req_params[i].u.Mem.len);
+                       break;
                default:
                        dprintf(INFO, "%s: unhandled param type 0x%x\n",
                                __func__, req_params[i].type);
@@ -364,6 +376,15 @@ static void tz_copyout_params(te_oper_param_t *out_params, te_request_t *req)
                                __func__, i, req_params[i].u.Mem.len);
                        out_params[i].u.Mem.len = req_params[i].u.Mem.len;
                        break;
+               case TE_PARAM_TYPE_PERSIST_MEM_RO:
+                       dprintf(SPEW, "%s: %d: PERSIST_MEM_RO: len 0x%x\n",
+                               __func__, i, req_params[i].u.Mem.len);
+                       break;
+               case TE_PARAM_TYPE_PERSIST_MEM_RW:
+                       dprintf(SPEW, "%s: %d: PERSIST_MEM_RW: len 0x%x\n",
+                               __func__, i, req_params[i].u.Mem.len);
+                       out_params[i].u.Mem.len = req_params[i].u.Mem.len;
+                       break;
                default:
                        dprintf(INFO, "%s: unhandled param type 0x%x\n",
                                __func__, out_params[i].type);
@@ -472,7 +493,9 @@ void tz_stdcall_handler(struct tz_monitor_frame *frame)
        case SMC_TOS_SS_REGISTER_HANDLER:
        case SMC_TOS_NS_REG_REQPARAM_BUF:
        case SMC_TOS_INIT_LOGGER:
+#if !defined(WITH_MONITOR_BIN)
        case SMC_TOS_PROGRAM_VPR:
+#endif
                tz_handle_system_smc(frame);
                break;
 
index bc2ebec..0e666a8 100644 (file)
@@ -79,8 +79,8 @@
 #define TEGRA_TMR9_BASE                        0x60005080
 #define TEGRA_TMR9_SIZE                        8
 
-#define TEGRA_TMR10_BASE               0x60005088
-#define TEGRA_TMR10_SIZE               8
+#define TEGRA_TMR0_BASE                        0x60005088
+#define TEGRA_TMR0_SIZE                        8
 
 #define TEGRA_WDT0_BASE                        0x60005100
 #define TEGRA_WDT0_SIZE                        32
similarity index 64%
copy from platform/tegra/tegra3/tz.c
copy to platform/tegra/include/platform/platform_cpu.h
index feadf78..f2c8ff5 100644 (file)
@@ -1,5 +1,6 @@
 /*
- * Copyright (c) 2013, NVIDIA CORPORATION. All rights reserved
+ * Copyright (c) 2008 Travis Geiselbrecht
+ * Copyright (c) 2012-2014, NVIDIA CORPORATION. All rights reserved
  *
  * Permission is hereby granted, free of charge, to any person obtaining
  * a copy of this software and associated documentation files
  * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
  * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
  */
+#ifndef __CPU_H
+#define __CPU_H
 
-#include <debug.h>
-#include <arch/outercache.h>
-#include <arch/arm.h>
-#include <platform/platform_p.h>
-#include <arch/arm/cache-l2x0.h>
-
-static int l2x0_init_done;
-
-void tz_handle_smc_l2(unsigned int smc)
-{
-       if (smc == 0x1) {
-               if (!l2x0_init_done) {
-                       outer_init();
-                       l2x0_init_done = 1;
-               } else {
-                       platform_init_outer();
-                       outer_enable();
-               }
-       } else if (smc == 0x2) {
-               outer_flush_all();
-               outer_disable(); /* disable */
-       } else {
-               dprintf(INFO, "invalid L2 SMC\n");
-       }
-}
-
-void tz_handle_smc_deep_sleep(void)
-{
-       l2x0_init_done = 0;
-}
+void cpu_save_context(void);
+void cpu_copy_context(void *dstptr);
+void flush_dcache_all(void);
+#endif
index 8b3d652..f0e4fc5 100644 (file)
 
 #include <lib/ote/ote_protocol.h>
 
-typedef enum {
-       /* Silicon Partner SMCs */
-       SMC_SIP_CPU_RESET_VECTOR_LEGACY = 0x82000001,
-       SMC_SIP_L2_MANAGEMENT           = 0x82000002,
-       SMC_SIP_PROGRAM_VPR             = 0x82000003,
-       SMC_SIP_DEVICE_SUSPEND          = 0x84000001,
-       SMC_SIP_CPU_RESET_VECTOR        = 0x84000003,
-
-       /* Trusted OS calls */
-       SMC_TOS_NS_FS_PARAMS            = 0x32000001,
-       SMC_TOS_NS_REG_REQPARAM_BUF     = 0x32000002,
-       SMC_TOS_PROGRAM_VPR             = 0x32000003,
-       SMC_TOS_NS_IRQ_PENDING_VECTOR   = 0x32000004,
-       SMC_TOS_NS_RETURN_FROM_IRQ      = 0x32000005,
-       SMC_TOS_FS_OP_DONE              = 0x32000006,
-       SMC_TOS_INIT_LOGGER             = 0x32000007,
-       SMC_TOS_SS_REQ_COMPLETE         = 0x32000009,
-       SMC_TOS_SS_REGISTER_HANDLER     = 0x32000010,
-
-       /* Trusted Application Calls */
-       SMC_TA_OPEN_SESSION             = 0x30000001,
-       SMC_TA_CLOSE_SESSION            = 0x30000002,
-       SMC_TA_LAUNCH_OPERATION         = 0x30000003,
-} smc_req_t;
-
 /*
  * Note: normal world sp/lr aren't kept in the tz_monitor_frame,
  * but instead are saved/restored from the global nonsecure_state
@@ -63,23 +38,17 @@ struct tz_monitor_frame {
 };
 typedef struct tz_monitor_frame tz_monitor_frame_t;
 
-void platform_init_interrupts(void);
-void platform_init_timer(void);
 void platform_init_memory(uint32_t sec_base, uint32_t sec_size);
-void platform_restore_memory();
-status_t platform_program_vpr(uint32_t vpr_base, uint32_t vpr_size);
 void platform_setup_keys(void);
 void platform_init_cpu(void);
-void platform_config_interrupts(void);
 void platform_disable_debug_intf(void);
 void platform_enable_debug_intf(void);
 void platform_set_intr_ready_state(bool, struct tz_monitor_frame *frame);
 status_t platform_ss_register_handler(struct tz_monitor_frame *frame);
-int platform_ss_request_handler(te_storage_request_t *req);
+int platform_ss_request_handler(void);
 void platform_get_device_id(te_device_id_args_t *args);
 uint32_t platform_get_time_us(void);
 void platform_clean_invalidate_cache_range(vaddr_t range, uint32_t size);
-void platform_secure_dram_aperture(void);
 
 void tz_init(void);
 struct tz_monitor_frame *tz_switch_to_ns(uint32_t smc_type, struct tz_monitor_frame *frame);
@@ -96,16 +65,10 @@ struct tz_monitor_frame *monitor_send_receive(uint32_t smc_type, struct tz_monit
 void pm_init(void);
 void pm_handle_platform_smc(struct tz_monitor_frame *frame);
 
-#if defined(WITH_MONITOR_BIN)
-void platform_monitor_init_cpu(void);
-#endif
-
 #if ARM_WITH_SCU
 void cpu_enable_scu(void);
 void cpu_enable_scu_access(void);
 #endif
-void cpu_save_context(void);
-void cpu_copy_context(void *dstptr);
 void cpu_gic_setup(void);
 
 status_t set_log_phy_addr(nsaddr_t _ns_cb_struct_addr);
similarity index 64%
copy from platform/tegra/tegra3/tz.c
copy to platform/tegra/include/platform/platform_ta.h
index feadf78..9192c46 100644 (file)
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013, NVIDIA CORPORATION. All rights reserved
+ * Copyright (c) 2012-2014, NVIDIA CORPORATION. All rights reserved
  *
  * Permission is hereby granted, free of charge, to any person obtaining
  * a copy of this software and associated documentation files
  * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
  */
 
-#include <debug.h>
-#include <arch/outercache.h>
-#include <arch/arm.h>
-#include <platform/platform_p.h>
-#include <arch/arm/cache-l2x0.h>
-
-static int l2x0_init_done;
-
-void tz_handle_smc_l2(unsigned int smc)
-{
-       if (smc == 0x1) {
-               if (!l2x0_init_done) {
-                       outer_init();
-                       l2x0_init_done = 1;
-               } else {
-                       platform_init_outer();
-                       outer_enable();
-               }
-       } else if (smc == 0x2) {
-               outer_flush_all();
-               outer_disable(); /* disable */
-       } else {
-               dprintf(INFO, "invalid L2 SMC\n");
-       }
-}
-
-void tz_handle_smc_deep_sleep(void)
-{
-       l2x0_init_done = 0;
-}
+/* Trusted Application Calls */
+#define SMC_TA_OPEN_SESSION                    0x30000001
+#define SMC_TA_CLOSE_SESSION                   0x30000002
+#define SMC_TA_LAUNCH_OPERATION                        0x30000003
similarity index 64%
copy from platform/tegra/tegra3/tz.c
copy to platform/tegra/include/platform/platform_tos.h
index feadf78..def6383 100644 (file)
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013, NVIDIA CORPORATION. All rights reserved
+ * Copyright (c) 2012-2014, NVIDIA CORPORATION. All rights reserved
  *
  * Permission is hereby granted, free of charge, to any person obtaining
  * a copy of this software and associated documentation files
  * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
  */
 
-#include <debug.h>
-#include <arch/outercache.h>
-#include <arch/arm.h>
-#include <platform/platform_p.h>
-#include <arch/arm/cache-l2x0.h>
-
-static int l2x0_init_done;
-
-void tz_handle_smc_l2(unsigned int smc)
-{
-       if (smc == 0x1) {
-               if (!l2x0_init_done) {
-                       outer_init();
-                       l2x0_init_done = 1;
-               } else {
-                       platform_init_outer();
-                       outer_enable();
-               }
-       } else if (smc == 0x2) {
-               outer_flush_all();
-               outer_disable(); /* disable */
-       } else {
-               dprintf(INFO, "invalid L2 SMC\n");
-       }
-}
-
-void tz_handle_smc_deep_sleep(void)
-{
-       l2x0_init_done = 0;
-}
+/* Trusted OS calls */
+#define SMC_TOS_NS_FS_PARAMS                   0x32000001
+#define SMC_TOS_NS_REG_REQPARAM_BUF            0x32000002
+#define SMC_TOS_PROGRAM_VPR                    0x32000003
+#define SMC_TOS_NS_IRQ_PENDING_VECTOR          0x32000004
+#define SMC_TOS_NS_RETURN_FROM_IRQ             0x32000005
+#define SMC_TOS_FS_OP_DONE                     0x32000006
+#define SMC_TOS_INIT_LOGGER                    0x32000007
+#define SMC_TOS_SS_REQ_COMPLETE                        0x32000009
+#define SMC_TOS_SS_REGISTER_HANDLER            0x32000010
index 4a85b96..a26c982 100644 (file)
@@ -11,7 +11,8 @@ INCLUDES += \
        -I$(LOCAL_DIR)/include \
        -I$(LOCAL_DIR)/include/platform/$(PLATFORM_SOC) \
        -I$(LOCAL_DIR)/common \
-       -I../lib
+       -I../lib \
+        -Isecure_monitor/platform/tegra/include
 
 COMMON_DIR := $(LOCAL_DIR)/common
 PLATFORM_SOC_DIR := $(LOCAL_DIR)/$(PLATFORM_SOC)
@@ -26,6 +27,9 @@ MODULE_SRCS += \
        $(COMMON_DIR)/memory.c          \
        $(COMMON_DIR)/debug.c           \
 
+MODULE_DEPS += \
+       lib/version
+
 # The code within the monitor dir builds to a lib that's either
 # linked into a mon.bin (when MONITOR_BIN is true) or into the
 # secureos when it's not.
@@ -38,9 +42,6 @@ MODULE_SRCS += \
 # routines, but they're only called for secureos handling
 # (i.e. aren't part of the monitor or for restoring HW state).
 
-MODULE_DEPS += \
-       $(LOCAL_DIR)/monitor
-
 # Add power management into the secureos build if
 # there's not a separate monitor being built.
 ifeq ($(MONITOR_BIN),)
diff --git a/platform/tegra/tegra3/platform.c b/platform/tegra/tegra3/platform.c
deleted file mode 100644 (file)
index 407eb0a..0000000
+++ /dev/null
@@ -1,96 +0,0 @@
-/*
- * Copyright (c) 2013, NVIDIA CORPORATION. All rights reserved
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files
- * (the "Software"), to deal in the Software without restriction,
- * including without limitation the rights to use, copy, modify, merge,
- * publish, distribute, sublicense, and/or sell copies of the Software,
- * and to permit persons to whom the Software is furnished to do so,
- * subject to the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
- * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
- * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
- * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
- * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- */
-
-#include <debug.h>
-#include <arch/arm.h>
-#include <platform/memmap.h>
-#include <arch/arm/cache-l2x0.h>
-#include <platform/platform_p.h>
-
-static unsigned int lp_tag_latency = 0x221;
-static unsigned int lp_data_latency = 0x221;
-static unsigned int g_tag_latency = 0x441;
-static unsigned int g_data_latency = 0x551;
-
-static bool platform_is_lp_cluster(void)
-{
-       uint32_t mpidr;
-
-       __asm__ volatile("mrc p15, 0, %0, c0, c0, 5": "=r" (mpidr));
-
-       return (((mpidr >> 8) & 0xF) != 0);     /* 0 == G, 1 == LP*/
-}
-
-uint32_t platform_l2x0_base
-{
-       return TEGRA_ARM_PL310_BASE;
-}
-
-void platform_init_outer(void)
-{
-       uint32_t base = TEGRA_ARM_PL310_BASE;
-       uint32_t tag_latency_ctrl = base + L2X0_TAG_LATENCY_CTRL;
-       uint32_t data_latency_ctrl = base + L2X0_DATA_LATENCY_CTRL;
-       uint32_t aux_ctrl;
-
-       if (*(volatile uint32_t *)(base + L2X0_CTRL) & 1) {
-               dprintf(INFO, "L2 cache already enabled\n");
-                       return;
-       }
-
-       /* determine cluster ID to set latencies */
-       if (platform_is_lp_cluster()) {
-               // LP cluster
-               *(volatile uint32_t *)tag_latency_ctrl = lp_tag_latency;
-               *(volatile uint32_t *)data_latency_ctrl = lp_data_latency;
-       } else {
-               // G cluster
-               *(volatile uint32_t *)tag_latency_ctrl = g_tag_latency;
-               *(volatile uint32_t *)data_latency_ctrl = g_data_latency;
-       }
-
-       *(volatile uint32_t *)(base + L2X0_PREFETCH_CTRL) = 7;
-       *(volatile uint32_t *)(base + L2X0_POWER_CTRL) =
-               L2X0_DYNAMIC_CLK_GATING_EN | L2X0_STNDBY_MODE_EN;
-
-       aux_ctrl = *(volatile uint32_t *)(base + L2X0_AUX_CTRL);
-       aux_ctrl |= (uint32_t) ((1 << 0) | // Full line of zeros
-               (1 << 22) |  // Shared attribute override enable
-               (1 << 26) |  // NS lockdown enable
-               (1 << 27) |  // NS int access ctrl
-               (1 << 28) |  // data prefetch enable
-               (1 << 29) |  // instn prefetch enable
-               (1 << 30));  // early BRESP enable
-       *(volatile uint32_t *)(base + L2X0_AUX_CTRL) = aux_ctrl;
-}
-
-void platform_init_cpu(void)
-{
-       l2x0_setup();
-
-        cpu_enable_scu();
-        cpu_enable_scu_access();
-
-       tz_init();
-       cpu_gic_setup();
-}
diff --git a/platform/tegra/tegra3/rules.mk b/platform/tegra/tegra3/rules.mk
deleted file mode 100644 (file)
index 22972ae..0000000
+++ /dev/null
@@ -1,12 +0,0 @@
-# ROMBASE, VMEMBASE, and VMEMSIZE are required for the linker script
-VMEMBASE := 0x48000000
-
-ARM_CPU := cortex-a9
-
-DEFINES += \
-       ARM_WITH_L2X0=1         \
-       ARM_WITH_OUTER_CACHE=1
-
-MODULE_SRCS += \
-       $(LOCAL_DIR)/tegra3/platform.c \
-       $(LOCAL_DIR)/tegra3/tz.c
index 47d67a0..7f0f9c3 100644 (file)
@@ -22,6 +22,7 @@
  */
 
 #include <platform/platform_p.h>
+#include <platform/platform_cpu.h>
 
 void platform_init_cpu(void)
 {
diff --git a/secure_monitor/Android.mk b/secure_monitor/Android.mk
new file mode 100644 (file)
index 0000000..22ea408
--- /dev/null
@@ -0,0 +1,155 @@
+#
+# Copyright (c) 2013-2014, NVIDIA CORPORATION. All rights reserved
+#
+# Permission is hereby granted, free of charge, to any person obtaining
+# a copy of this software and associated documentation files
+# (the "Software"), to deal in the Software without restriction,
+# including without limitation the rights to use, copy, modify, merge,
+# publish, distribute, sublicense, and/or sell copies of the Software,
+# and to permit persons to whom the Software is furnished to do so,
+# subject to the following conditions:
+#
+# The above copyright notice and this permission notice shall be
+# included in all copies or substantial portions of the Software.
+#
+# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+# EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+# MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
+# IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
+# CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
+# TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
+# SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+#
+
+LOCAL_PATH := $(call my-dir)
+include $(CLEAR_VARS)
+
+# tos.img is considered to be 32-bit
+ifneq (,$(TARGET_2ND_ARCH))
+LOCAL_2ND_ARCH_VAR_PREFIX := $(TARGET_2ND_ARCH_VAR_PREFIX)
+endif
+
+ifeq (tlk,$(SECURE_OS_BUILD))
+
+ifeq (t124,$(TARGET_TEGRA_VERSION))
+
+$(warning SECURE_OS_BUILD. Making libmonitor.a)
+# building a monitor library
+LOCAL_MODULE := libmonitor
+LOCAL_MODULE_CLASS := STATIC_LIBRARIES
+LOCAL_UNINSTALLABLE_MODULE := true
+LOCAL_BUILT_MODULE_STEM := libmonitor.a
+STANDALONE_MONITOR := false
+MONITOR_LIBRARY := true
+OUTFILE_EXTENSION := .a
+
+else # TARGET_TEGRA_VERSION != t124
+
+$(warning SECURE_OS_BUILD. Making monitor.bin)
+# building a monitor binary
+LOCAL_MODULE := monitor.bin
+LOCAL_MODULE_CLASS := EXECUTABLES
+LOCAL_UNINSTALLABLE_MODULE := true
+LOCAL_BUILT_MODULE_STEM := monitor.bin
+STANDALONE_MONITOR := false
+MONITOR_LIBRARY := false
+
+endif # TARGET_TEGRA_VERSION == t124
+
+else # SECURE_OS_BUILD != tlk
+
+ifeq (t124,$(TARGET_TEGRA_VERSION))
+
+$(warning Non SECURE_OS_BUILD for T124 - Nothing to do)
+# t124, non secure: No nothing
+LOCAL_MODULE :=
+LOCAL_MODULE_CLASS :=
+LOCAL_UNINSTALLABLE_MODULE :=
+LOCAL_BUILT_MODULE_STEM :=
+STANDALONE_MONITOR := false
+MONITOR_LIBRARY := false
+
+else # TARGET_TEGRA_VERSION != t124
+
+$(warning Non SECURE_OS_BUILD. Making monitor.bin and tos.img)
+# building a monitor binary and tos.img
+LOCAL_MODULE := monitor.bin
+LOCAL_MODULE_CLASS := EXECUTABLES
+LOCAL_UNINSTALLABLE_MODULE := true
+LOCAL_BUILT_MODULE_STEM := monitor.bin
+STANDALONE_MONITOR := true
+MONITOR_LIBRARY := false
+
+endif # TARGET_TEGRA_VERSION == t124
+
+endif # SECURE_OS_BUILD == tlk
+
+ifneq (,$(LOCAL_BUILT_MODULE_STEM))
+
+ifeq ($(LOCAL_MODULE_CLASS),EXECUTABLES)
+# monitor.bin_intermediates
+MODULE_INTERMEDIATES := $(call intermediates-dir-for,$(LOCAL_MODULE_CLASS),$(LOCAL_BUILT_MODULE_STEM),,,$(LOCAL_2ND_ARCH_VAR_PREFIX))
+else
+# libmonitor_intermediates
+MODULE_INTERMEDIATES := $(call intermediates-dir-for,$(LOCAL_MODULE_CLASS),$(LOCAL_MODULE),,,$(LOCAL_2ND_ARCH_VAR_PREFIX))
+endif
+
+PROJECT := tegra
+OUTFILE := $(MODULE_INTERMEDIATES)/$(LOCAL_BUILT_MODULE_STEM)
+
+ifeq ($(STANDALONE_MONITOR),true)
+TOSIMAGE := $(PRODUCT_OUT)/tos.img
+ALL_MODULES.$(LOCAL_MODULE).INSTALLED := $(TOSIMAGE)
+endif
+
+ifeq ($(TARGET_ARCH),arm64)
+LK_TOOLCHAIN_PREFIX := prebuilts/gcc/$(HOST_PREBUILT_TAG)/arm/arm-eabi-4.8/bin/arm-eabi-
+LK_TOOLCHAIN_PREFIX64 := $(TARGET_TOOLS_PREFIX)
+else
+LK_TOOLCHAIN_PREFIX := $(ARM_EABI_TOOLCHAIN)/arm-eabi-
+LK_TOOLCHAIN_PREFIX64 := $(ARM_EABI_TOOLCHAIN)/../../../aarch64/aarch64-linux-android-4.8/bin/aarch64-linux-android-
+endif
+
+$(OUTFILE): PRIVATE_CUSTOM_TOOL_ARGS := PROJECT=$(PROJECT) \
+               TARGET=$(TARGET_TEGRA_VERSION) \
+               TOOLCHAIN_PREFIX=$(abspath $(LK_TOOLCHAIN_PREFIX)) \
+               TOOLCHAIN_PREFIX64=$(abspath $(LK_TOOLCHAIN_PREFIX64)) \
+               PREFIX=$(abspath $(MODULE_INTERMEDIATES)) \
+               STANDALONE_MONITOR=$(STANDALONE_MONITOR) \
+               MONITOR_LIBRARY=$(MONITOR_LIBRARY) \
+               TOSIMAGE=$(abspath $(TOSIMAGE)) \
+               -C $(LOCAL_PATH)
+
+$(OUTFILE): PRIVATE_MODULE := $(LOCAL_MODULE)
+# Depend on tasks when we are doing a full build.
+# For one shot builds, (mm, mmm) do not.
+$(OUTFILE):
+       @echo "target Generated: $(PRIVATE_MODULE)"
+       @mkdir -p $(dir $@)
+       $(hide) $(MAKE) $(PRIVATE_CUSTOM_TOOL_ARGS)
+
+$(TOSIMAGE): $(OUTFILE)
+
+.PHONY: $(OUTFILE)
+
+# Needed to clean tos.img
+PRIVATE_CLEAN_FILES := $(TOSIMAGE)
+
+ifeq ($(LOCAL_2ND_ARCH_VAR_PREFIX),)
+ALL_NVIDIA_MODULES += $(LOCAL_MODULE)
+else
+ALL_NVIDIA_MODULES += $(LOCAL_MODULE)_32
+endif
+include $(BUILD_SYSTEM)/base_rules.mk
+
+# Clean variables
+PROJECT :=
+OUTFILE :=
+TOSIMAGE :=
+LK_TOOLCHAIN_PREFIX :=
+LK_TOOLCHAIN_PREFIX64 :=
+STANDALONE_MONITOR :=
+MONITOR_LIBRARY :=
+OUTFILE_EXTENSION :=
+
+endif
diff --git a/secure_monitor/arch/arm/include/arch/arm.h b/secure_monitor/arch/arm/include/arch/arm.h
new file mode 100644 (file)
index 0000000..c470f17
--- /dev/null
@@ -0,0 +1,182 @@
+/*
+ * Copyright (c) 2008 Travis Geiselbrecht
+ * Copyright (c) 2012-2013, NVIDIA CORPORATION. All rights reserved
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining
+ * a copy of this software and associated documentation files
+ * (the "Software"), to deal in the Software without restriction,
+ * including without limitation the rights to use, copy, modify, merge,
+ * publish, distribute, sublicense, and/or sell copies of the Software,
+ * and to permit persons to whom the Software is furnished to do so,
+ * subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
+ * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
+ * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
+ * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
+ * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ */
+#ifndef __ARCH_ARM_H
+#define __ARCH_ARM_H
+
+/* defines used in asm */
+#define MODE_USR       0x10
+#define MODE_FIQ       0x11
+#define MODE_IRQ       0x12
+#define MODE_SVC       0x13
+#define MODE_MON       0x16
+#define MODE_ABT       0x17
+#define MODE_UND       0x1b
+#define MODE_SYS       0x1f
+#define MODE_MASK      0x1f
+
+#define EXC_ARM                (0 << 5)
+#define EXC_THUMB      (1 << 5)
+
+/* offsets in context_switch_frame */
+#define CSF_OFFSET_R0  0x0
+#define CSF_OFFSET_R1  0x4
+#define CSF_OFFSET_R2  0x8
+#define CSF_OFFSET_R3  0xc
+#define CSF_OFFSET_R4  0x10
+#define CSF_OFFSET_R5  0x14
+#define CSF_OFFSET_R6  0x18
+#define CSF_OFFSET_R7  0x1c
+#define CSF_OFFSET_R8  0x20
+#define CSF_OFFSET_R9  0x24
+#define CSF_OFFSET_R10 0x28
+#define CSF_OFFSET_R11 0x2c
+#define CSF_OFFSET_R12 0x30
+#define CSF_OFFSET_SP  0x34
+#define CSF_OFFSET_LR  0x38
+#define CSF_OFFSET_PC  0x3c
+#define CSF_OFFSET_PSR 0x40
+#define CSF_SIZE       (CSF_OFFSET_PSR + 0x4)
+
+#ifndef ASSEMBLY
+
+#include <sys/types.h>
+#include <arch/arm/cores.h>
+#include <kernel/thread.h>
+
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+#define DSB __asm__ volatile("dsb" ::: "memory")
+#define ISB __asm__ volatile("isb" ::: "memory")
+
+void arm_context_switch(thread_t *old_sp, thread_t *new_sp);
+
+static inline uint32_t read_cpsr() {
+       uint32_t cpsr;
+
+       __asm__ volatile("mrs   %0, cpsr" : "=r" (cpsr));
+       return cpsr;
+}
+
+struct arm_iframe {
+       uint32_t r[13];
+       uint32_t lr;    /* lr_svc */
+       uint32_t usp;   /* sp_usr */
+       uint32_t ulr;   /* lr_usr */
+       uint32_t pc;
+       uint32_t spsr;  /* spsr_irq */
+};
+
+struct arm_fault_frame {
+       uint32_t spsr;
+       uint32_t usp;
+       uint32_t ulr;
+       uint32_t r[13];
+       uint32_t pc;
+};
+
+struct context_switch_frame {
+       uint32_t r0;
+       uint32_t r1;
+       uint32_t r2;
+       uint32_t r3;
+       uint32_t r4;
+       uint32_t r5;
+       uint32_t r6;
+       uint32_t r7;
+       uint32_t r8;
+       uint32_t r9;
+       uint32_t r10;
+       uint32_t r11;
+       uint32_t r12;
+       uint32_t sp;    /* sp_usr or sp_svc */
+       uint32_t lr;    /* lr_usr or lr_svc */
+       uint32_t pc;    /* restart pc */
+       uint32_t psr;   /* previous mode */
+};
+
+struct arm_mode_regs {
+       uint32_t fiq_r13, fiq_r14;
+       uint32_t irq_r13, irq_r14;
+       uint32_t svc_r13, svc_r14;
+       uint32_t abt_r13, abt_r14;
+       uint32_t und_r13, und_r14;
+       uint32_t sys_r13, sys_r14;
+};
+
+void arm_save_mode_regs(struct arm_mode_regs *regs);
+
+uint32_t arm_read_sctlr(void);
+void arm_write_sctlr(uint32_t val);
+uint32_t arm_read_actlr(void);
+void arm_write_actlr(uint32_t val);
+uint32_t arm_read_ttbr0(void);
+void arm_write_ttbr0(uint32_t val);
+uint32_t arm_read_contextidr(void);
+void arm_write_contextidr(uint32_t val);
+uint32_t arm_read_ttbr1(void);
+void arm_write_ttbr1(uint32_t val);
+uint32_t arm_read_ttbcr(void);
+void arm_write_ttbcr(uint32_t val);
+uint32_t arm_read_dacr(void);
+void arm_write_dacr(uint32_t val);
+void arm_invalidate_tlb(void);
+void arm_invalidate_tlb_byaddr(addr_t addr);
+void arm_invalidate_tlb_byaddr_asid(addr_t addr, uint32_t asid);
+
+uint32_t arm_get_tls(void);
+void arm_set_tls(uint32_t val);
+uint32_t arm_read_vbar(void);
+void arm_write_vbar(uint32_t val);
+
+/* virt -> phys address translation args */
+enum {
+       V2PCWPR,
+       V2PCWPW,
+       V2PCWUR,
+       V2PCWUW,
+       V2POWPR,
+       V2POWPW,
+       V2POWUR,
+       V2POWUW
+};
+void arm_write_v2p(uint32_t vaddr, uint32_t type);
+uint64_t arm_read_par(void);
+
+#if ARM_WITH_NEON
+uint32_t arm_get_vfp_fpexc(void);
+void arm_set_vfp_fpexc(uint32_t val);
+uint32_t arm_get_vfp_fpscr(void);
+void arm_set_vfp_fpscr(uint32_t val);
+void arm_save_vfp_dregs(addr_t ctx);
+void arm_restore_vfp_dregs(addr_t ctx);
+#endif
+
+#if defined(__cplusplus)
+}
+#endif
+#endif
+
+#endif
diff --git a/secure_monitor/arch/arm/include/arch/arm/ops.h b/secure_monitor/arch/arm/include/arch/arm/ops.h
new file mode 100644 (file)
index 0000000..7f84223
--- /dev/null
@@ -0,0 +1,165 @@
+/*
+ * Copyright (c) 2008-2012 Travis Geiselbrecht
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining
+ * a copy of this software and associated documentation files
+ * (the "Software"), to deal in the Software without restriction,
+ * including without limitation the rights to use, copy, modify, merge,
+ * publish, distribute, sublicense, and/or sell copies of the Software,
+ * and to permit persons to whom the Software is furnished to do so,
+ * subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
+ * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
+ * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
+ * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
+ * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ */
+#ifndef __ARCH_ARM_OPS_H
+#define __ARCH_ARM_OPS_H
+
+#ifndef ASSEMBLY
+
+#include <compiler.h>
+#include <reg.h>
+
+#if ARM_ISA_ARMV7 || (ARM_ISA_ARMV6 && !__thumb__)
+// override of some routines
+__GNU_INLINE __ALWAYS_INLINE extern inline void arch_enable_ints(void)
+{
+       __asm__("cpsie i");
+       CF;
+}
+
+__GNU_INLINE __ALWAYS_INLINE extern inline void arch_disable_ints(void)
+{
+       __asm__("cpsid i");
+       CF;
+}
+
+__GNU_INLINE __ALWAYS_INLINE extern inline int atomic_add(volatile int *ptr, int val)
+{
+       int old;
+       int temp;
+       int test;
+
+       do {
+               __asm__ volatile(
+                   "ldrex      %[old], [%[ptr]]\n"
+                   "add        %[temp], %[old], %[val]\n"
+                   "strex      %[test], %[temp], [%[ptr]]\n"
+                   : [old]"=&r" (old), [temp]"=&r" (temp), [test]"=&r" (test)
+                   : [ptr]"r" (ptr), [val]"r" (val)
+                   : "memory");
+
+       } while (test != 0);
+
+       return old;
+}
+
+__GNU_INLINE __ALWAYS_INLINE extern inline int atomic_or(volatile int *ptr, int val)
+{
+       int old;
+       int temp;
+       int test;
+
+       do {
+               __asm__ volatile(
+                   "ldrex      %[old], [%[ptr]]\n"
+                   "orr        %[temp], %[old], %[val]\n"
+                   "strex      %[test], %[temp], [%[ptr]]\n"
+                   : [old]"=&r" (old), [temp]"=&r" (temp), [test]"=&r" (test)
+                   : [ptr]"r" (ptr), [val]"r" (val)
+                   : "memory");
+
+       } while (test != 0);
+
+       return old;
+}
+
+__GNU_INLINE __ALWAYS_INLINE extern inline int atomic_and(volatile int *ptr, int val)
+{
+       int old;
+       int temp;
+       int test;
+
+       do {
+               __asm__ volatile(
+                   "ldrex      %[old], [%[ptr]]\n"
+                   "and        %[temp], %[old], %[val]\n"
+                   "strex      %[test], %[temp], [%[ptr]]\n"
+                   : [old]"=&r" (old), [temp]"=&r" (temp), [test]"=&r" (test)
+                   : [ptr]"r" (ptr), [val]"r" (val)
+                   : "memory");
+
+       } while (test != 0);
+
+       return old;
+}
+
+__GNU_INLINE __ALWAYS_INLINE extern inline int atomic_swap(volatile int *ptr, int val)
+{
+       int old;
+       int test;
+
+       do {
+               __asm__ volatile(
+                   "ldrex      %[old], [%[ptr]]\n"
+                   "strex      %[test], %[val], [%[ptr]]\n"
+                   : [old]"=&r" (old), [test]"=&r" (test)
+                   : [ptr]"r" (ptr), [val]"r" (val)
+                   : "memory");
+
+       } while (test != 0);
+
+       return old;
+}
+
+__GNU_INLINE __ALWAYS_INLINE extern inline int atomic_cmpxhg(volatile int *ptr, int oldval, int newval)
+{
+       int old;
+       int test;
+
+       do {
+               __asm__ volatile(
+                   "ldrex      %[old], [%[ptr]]\n"
+                   "mov        %[test], #0\n"
+                   "teq        %[old], %[oldval]\n"
+#if ARM_ISA_ARMV7M
+                   "bne        0f\n"
+                   "strex      %[test], %[newval], [%[ptr]]\n"
+                   "0:\n"
+#else
+                   "strexeq %[test], %[newval], [%[ptr]]\n"
+#endif
+                   : [old]"=&r" (old), [test]"=&r" (test)
+                   : [ptr]"r" (ptr), [oldval]"Ir" (oldval), [newval]"r" (newval)
+                   : "cc");
+
+       } while (test != 0);
+
+       return old;
+}
+
+__GNU_INLINE __ALWAYS_INLINE extern inline uint32_t arch_cycle_count(void)
+{
+#if ARM_CPU_CORTEX_M3
+#define DWT_CYCCNT (0xE0001004)
+    return *REG32(DWT_CYCCNT);
+#else
+       return 0;
+#endif
+}
+
+
+#endif
+
+#endif
+
+#endif
+
similarity index 64%
copy from platform/tegra/tegra3/tz.c
copy to secure_monitor/arch/arm/include/arch/defines.h
index feadf78..10b1952 100644 (file)
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013, NVIDIA CORPORATION. All rights reserved
+ * Copyright (c) 2008 Travis Geiselbrecht
  *
  * Permission is hereby granted, free of charge, to any person obtaining
  * a copy of this software and associated documentation files
  * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
  * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
  */
+#ifndef __ARCH_CPU_H
+#define __ARCH_CPU_H
 
-#include <debug.h>
-#include <arch/outercache.h>
-#include <arch/arm.h>
-#include <platform/platform_p.h>
-#include <arch/arm/cache-l2x0.h>
+/* arm specific stuff */
+#define PAGE_SIZE 4096
+#define PAGE_MASK (PAGE_SIZE - 1)
 
-static int l2x0_init_done;
+#if ARM_CPU_ARM7
+/* irrelevant, no consistent cache */
+#define CACHE_LINE 32
+#elif ARM_CPU_ARM926
+#define CACHE_LINE 32
+#elif ARM_CPU_ARM1136
+#define CACHE_LINE 32
+#elif ARM_CPU_CORTEX_A8
+#define CACHE_LINE 64
+#elif ARM_CPU_CORTEX_M3
+#define CACHE_LINE 32 /* doesn't actually matter */
+#elif ARM_CPU_CORTEX_A9
+#define CACHE_LINE 32
+#elif ARM_CPU_CORTEX_A15
+#define CACHE_LINE 64
+#else
+ #error unknown cpu
+#endif
 
-void tz_handle_smc_l2(unsigned int smc)
-{
-       if (smc == 0x1) {
-               if (!l2x0_init_done) {
-                       outer_init();
-                       l2x0_init_done = 1;
-               } else {
-                       platform_init_outer();
-                       outer_enable();
-               }
-       } else if (smc == 0x2) {
-               outer_flush_all();
-               outer_disable(); /* disable */
-       } else {
-               dprintf(INFO, "invalid L2 SMC\n");
-       }
-}
+#endif
 
-void tz_handle_smc_deep_sleep(void)
-{
-       l2x0_init_done = 0;
-}
diff --git a/secure_monitor/arch/arm/rules.mk b/secure_monitor/arch/arm/rules.mk
new file mode 100644 (file)
index 0000000..76f6e09
--- /dev/null
@@ -0,0 +1,125 @@
+LOCAL_DIR := $(GET_LOCAL_DIR)
+
+MODULE := $(LOCAL_DIR)
+
+# default to the regular arm subarch
+SUBARCH := arm
+
+DEFINES += \
+       ARM_CPU_$(ARM_CPU)=1
+
+# do set some options based on the cpu core
+HANDLED_CORE := false
+
+ifeq ($(ARM_CPU),cortex-a15)
+DEFINES += \
+       ARM_WITH_CP15=1         \
+       ARM_WITH_MMU=1          \
+       ARM_ISA_ARMv7=1         \
+       ARM_ISA_ARMv7A=1        \
+       ARM_WITH_VFP=1          \
+       ARM_WITH_NEON=1         \
+       ARM_WITH_THUMB=1        \
+       ARM_WITH_THUMB2=1       \
+       ARM_WITH_CACHE=1        \
+       ARM_WITH_SCU=0          \
+       ARM_WITH_L2=0
+HANDLED_CORE := true
+#CFLAGS += -mfpu=neon -mfloat-abi=softfp
+MODULE_DEPS += $(LOCAL_DIR)/arm/neon
+endif
+ifeq ($(ARM_CPU),cortex-a9)
+DEFINES += \
+       ARM_WITH_CP15=1         \
+       ARM_WITH_MMU=1          \
+       ARM_ISA_ARMv7=1         \
+       ARM_ISA_ARMv7A=1        \
+       ARM_WITH_VFP=1          \
+       ARM_WITH_NEON=1         \
+       ARM_WITH_THUMB=1        \
+       ARM_WITH_THUMB2=1       \
+       ARM_WITH_CACHE=1        \
+       ARM_WITH_SCU=1          \
+       ARM_WITH_L2=0
+HANDLED_CORE := true
+#CFLAGS += -mfpu=neon -mfloat-abi=softfp
+MODULE_DEPS += $(LOCAL_DIR)/arm/neon
+endif
+
+ifeq ($(ARM_CPU),arm926ej-s)
+DEFINES += \
+       ARM_WITH_CP15=1 \
+       ARM_WITH_MMU=1 \
+       ARM_ISA_ARMv5E=1 \
+       ARM_WITH_THUMB=1 \
+       ARM_WITH_CACHE=1 \
+       ARM_CPU_ARM9=1 \
+       ARM_CPU_ARM926=1
+HANDLED_CORE := true
+endif
+
+ifneq ($(HANDLED_CORE),true)
+$(warning $(LOCAL_DIR)/rules.mk doesnt have logic for arm core $(ARM_CPU))
+$(warning this is likely to be broken)
+endif
+
+INCLUDES += \
+       -I$(LOCAL_DIR)/include \
+       -I$(LOCAL_DIR)/$(SUBARCH)/include
+
+ifeq ($(SUBARCH),arm)
+
+# using either long / short MMU desc support
+ifeq ($(ARM_WITH_LPAE),true)
+DEFINES += \
+       ARM_WITH_LPAE=1
+endif
+
+DEFINES += \
+       ARCH_DEFAULT_STACK_SIZE=4096
+endif
+
+# If platform sets ARM_USE_MMU_RELOC the image will be built based on
+# VMEMBASE and will create page table entries in start.S to the physmem
+# it's been given (avoiding relocation by copying the image).
+
+ifeq ($(ARM_USE_MMU_RELOC),true)
+DEFINES += \
+       ARM_USE_MMU_RELOC=1
+endif
+
+ifeq ($(ARM_USE_CPU_CACHING),true)
+DEFINES += \
+       ARM_USE_CPU_CACHING=1
+endif
+
+# make sure some bits were set up
+MEMVARS_SET := 0
+ifeq ($(ARM_USE_MMU_RELOC),true)
+ifneq ($(VMEMBASE),)
+MEMVARS_SET := 1
+endif
+ifneq ($(VMEMSIZE),)
+MEMVARS_SET := 1
+endif
+ifeq ($(MEMVARS_SET),0)
+$(error missing VMEMBASE or VMEMSIZE variable, please set in target rules.mk)
+endif
+else
+ifneq ($(MEMBASE),)
+MEMVARS_SET := 1
+endif
+ifneq ($(MEMSIZE),)
+MEMVARS_SET := 1
+endif
+DEFINES += \
+        VMEMBASE=$(MEMBASE)
+endif
+ifeq ($(MEMVARS_SET),0)
+$(error missing MEMBASE or MEMSIZE variable, please set in target rules.mk)
+endif
+
+LIBGCC := $(shell $(TOOLCHAIN_PREFIX)gcc $(MODULE_COMPILEFLAGS) -print-libgcc-file-name)
+$(info LIBGCC = $(LIBGCC))
+
+$(info ARCH_COMPILEFLAGS = $(MODULE_COMPILEFLAGS))
diff --git a/secure_monitor/build/Makefile.package b/secure_monitor/build/Makefile.package
new file mode 100644 (file)
index 0000000..dfd2cce
--- /dev/null
@@ -0,0 +1,152 @@
+################################### tell Emacs this is a -*- makefile-gmake -*-
+#
+# Copyright (c) 2014, NVIDIA CORPORATION.  All Rights Reserved.
+#
+# NVIDIA CORPORATION and its licensors retain all intellectual property
+# and proprietary rights in and to this software, related documentation
+# and any modifications thereto.  Any use, reproduction, disclosure or
+# distribution of this software and related documentation without an express
+# license agreement from NVIDIA CORPORATION is strictly prohibited.
+#
+# tmake for SW Mobile
+#
+# Wrapper makefile to build all variants of the "secure_monitor" parts umbrella
+#
+###############################################################################
+#
+# Default targets
+#
+.PHONY: default build install clean distclean
+
+# NOTE: this needs to be the *FIRST* rule in the makefile!
+default: build
+
+
+###############################################################################
+#
+# Various constants
+#
+ifndef NV_SOURCE
+NV_SOURCE := $(CURDIR)
+endif
+ifndef NV_OUTDIR
+NV_OUTDIR := $(CURDIR)/out
+endif
+
+
+###############################################################################
+#
+# Macro to call component parts umbrella
+#
+define _build
+       +$(MAKE) \
+               -C $(NV_SOURCE) \
+               -f secure_monitor/build/Makefile.secure_monitor \
+               NV_OUTDIR=$(NV_BUILD_COMPONENT_OUTDIR)
+endef
+
+###############################################################################
+#
+# Macro to generate one build configuration
+#
+# $(1): target name
+# $(2): same as $(1) but split into words
+define _generate_config
+
+# configuration dependent variables
+$(eval NV_BUILD_COMPONENT_OUTDIR      := $(NV_OUTDIR)/$(1))
+$(eval NV_BUILD_COMPONENT_INSTALL_DIR := $(NV_OUTDIR)/install/$(1))
+$(eval NV_BUILD_COMPONENT_SYSTEM      := $(word 1,$(2)))
+$(eval NV_BUILD_COMPONENT_BOARD       := $(word 2,$(2)))
+
+# forces re-execution of component parts umbrella to check for build changes
+.PHONY: $(1)
+_directories += $(1)
+$(1): NV_BUILD_COMPONENT_CONFIG := \
+       NV_TARGET_BOARD=$$(NV_BUILD_COMPONENT_BOARD) \
+       NV_BUILD_SYSTEM_TYPE=$$(NV_BUILD_COMPONENT_SYSTEM)
+$(1): | $(NV_BUILD_COMPONENT_OUTDIR)
+       $(_build) $$(NV_BUILD_COMPONENT_CONFIG)
+
+$(NV_BUILD_COMPONENT_OUTDIR): | $(NV_OUTDIR)
+       mkdir -p $$@
+
+.PHONY: $(NV_BUILD_COMPONENT_INSTALL_DIR)
+$(NV_BUILD_COMPONENT_INSTALL_DIR): NV_BUILD_COMPONENT_BUILD_DIR := $(NV_OUTDIR)/$(1)/nvidia
+$(NV_BUILD_COMPONENT_INSTALL_DIR):
+       mkdir -p $$@
+       cp \
+               $$(NV_BUILD_COMPONENT_BUILD_DIR)/secure_monitor/tos.img \
+               $$@
+
+clean distclean::
+       $(_build) $$@
+endef
+
+
+###############################################################################
+#
+# Build configuration
+#
+# Configuration naming scheme
+#
+#     <system>@<board>
+#
+#  system:  value for $(NV_BUILD_SYSTEM_TYPE)
+#  board:   value for $(NV_TARGET_BOARD)
+#
+###############################################################################
+_configurations :=
+
+###############################################################################
+#
+# Android
+#
+# None
+#
+###############################################################################
+#
+# L4T
+#
+# T132
+_configurations += l4t@t132ref
+# T210
+_configurations += l4t@t210ref
+#
+###############################################################################
+#
+# Embedded-Linux
+#
+# None
+#
+###############################################################################
+#
+# Embedded-QNX
+#
+# None
+#
+###############################################################################
+
+_directories :=
+$(foreach c,$(_configurations),$(eval $(call _generate_config,$(subst @,_,$(c)),$(subst @, ,$(c)))))
+
+build: $(_directories)
+
+NV_BUILD_COMPONENT_INSTALLS := $(addprefix $(NV_OUTDIR)/install/,$(_directories))
+
+install: $(NV_BUILD_COMPONENT_INSTALLS) | $(NV_OUTDIR)/install
+
+
+###############################################################################
+#
+# Intermediate directory creation
+#
+$(NV_OUTDIR) $(NV_OUTDIR)/install:
+       mkdir -p $@
+
+
+# Local Variables:
+# indent-tabs-mode: t
+# tab-width: 8
+# End:
+# vi: set tabstop=8 noexpandtab:
diff --git a/secure_monitor/build/Makefile.secure_monitor b/secure_monitor/build/Makefile.secure_monitor
new file mode 100644 (file)
index 0000000..51efe29
--- /dev/null
@@ -0,0 +1,126 @@
+################################### tell Emacs this is a -*- makefile-gmake -*-
+#
+# Copyright (c) 2014, NVIDIA CORPORATION.  All rights reserved.
+#
+# NVIDIA CORPORATION and its licensors retain all intellectual property
+# and proprietary rights in and to this software, related documentation
+# and any modifications thereto.  Any use, reproduction, disclosure or
+# distribution of this software and related documentation without an express
+# license agreement from NVIDIA CORPORATION is strictly prohibited.
+#
+# tmake for SW Mobile
+#
+# Umbrella parts adaptor to secure_monitor build system (LK based)
+#
+###############################################################################
+#
+# Umbrella build is always started from top-level of the source tree
+#
+ifndef NV_SOURCE
+NV_SOURCE := $(CURDIR)
+endif
+
+#
+# Macro for checking that each variable given in list $(1) is both defined
+# and has a non empty value in it.
+define NV_BUILD_VARIABLES_SANITY_CHECK
+$(foreach var,$(1),$(eval \
+ifndef $(var)
+_missing_vars := 1 $$(info ERROR: variable not set or empty: $(var))
+endif))\
+$(if $(_missing_vars),$(error Environment sanity check failed))
+endef
+
+$(call NV_BUILD_VARIABLES_SANITY_CHECK, NV_BUILD_SYSTEM_TYPE NV_TARGET_BOARD)
+
+#
+# Default targets
+#
+# Define them here to prevent component makefiles from messing with them.
+#
+.PHONY: default build clean distclean systemimage release-info
+.PHONY: build-tools clean-tools distclean-tools # not implemented, but needed
+
+# NOTE: this needs to be the *FIRST* rule in the makefile!
+default: build
+
+#
+# Common bits
+#
+NV_PATH := tmake
+include $(NV_SOURCE)/$(NV_PATH)/umbrella/common.tmk
+include $(NV_SOURCE)/$(NV_PATH)/umbrella/board_soc.tmk
+
+#
+# Cross-compilation toolchain
+#
+NV_BUILD_SECURE_MONITOR_SOURCE    := $(NV_SOURCE)/secure_monitor
+
+ifneq ($(filter l4t mods embedded-linux,$(NV_BUILD_SYSTEM_TYPE)),)
+NV_BUILD_SECURE_MONITOR_TOOLCHAIN := $(NV_SOURCE)/prebuilts/gcc/linux-x86/aarch64/aarch64-linux-android-4.8/bin/aarch64-linux-android-
+else
+$(error umbrella: secure_monitor part not supported for build type "$(NV_BUILD_SYSTEM_TYPE)")
+endif
+
+#
+# monitor build
+#
+NV_BUILD_SECURE_MONITOR_OUTDIR    := $(NV_INTERMEDIATES_TOP)/secure_monitor
+NV_BUILD_SECURE_MONITOR_IMAGE     := $(NV_BUILD_SECURE_MONITOR_OUTDIR)/tos.img
+
+# translate our verbosity and build type to monitor build
+ifeq ($(NV_BUILD_CONFIGURATION_IS_VERBOSE),1)
+_secure_monitor_build_verbosity :=
+else
+_secure_monitor_build_verbosity := @
+endif
+ifeq ($(NV_BUILD_CONFIGURATION_IS_DEBUG),1)
+_secure_monitor_build_type := debug
+else
+_secure_monitor_build_type := release
+endif
+
+# macro to call monitor build
+define _secure_monitor_build
+       +$(MAKE) -C $(NV_BUILD_SECURE_MONITOR_SOURCE) \
+                               PROJECT=tegra \
+                               TARGET=$(NV_TARGET_SOC) \
+                               TOOLCHAIN_PREFIX=$(NV_BUILD_SECURE_MONITOR_TOOLCHAIN) \
+                               TOOLCHAIN_PREFIX64=$(NV_BUILD_SECURE_MONITOR_TOOLCHAIN) \
+                               TARGET_BUILD_TYPE=$(_secure_monitor_build_type) \
+                               NOECHO=$(_secure_monitor_build_verbosity) \
+                               PREFIX=$(NV_BUILD_SECURE_MONITOR_OUTDIR) \
+                               STANDALONE_MONITOR=true \
+                               MONITOR_LIBRARY=false \
+                               TOSIMAGE=$(NV_BUILD_SECURE_MONITOR_IMAGE)
+endef
+
+# standard build: build every component
+ifndef NV_BUILD_COMPONENTS
+build: $(NV_BUILD_SECURE_MONITOR_IMAGE)
+
+# forces re-execution of monitor build system to check for source changes
+.PHONY: $(NV_BUILD_SECURE_MONITOR_IMAGE)
+$(NV_BUILD_SECURE_MONITOR_IMAGE): | $(NV_BUILD_SECURE_MONITOR_OUTDIR)
+       $(_secure_monitor_build)
+
+clean distclean::
+       $(_secure_monitor_build) $@
+
+else
+# user has requested build of specific components -> skip secure_monitor build
+endif
+
+#
+# Intermediate directory creation
+#
+$(NV_BUILD_SECURE_MONITOR_OUTDIR): | $(NV_INTERMEDIATES_TOP)
+$(NV_INTERMEDIATES_TOP) $(NV_BUILD_SECURE_MONITOR_OUTDIR):
+       $(MKDIR_P) $@
+
+
+# Local Variables:
+# indent-tabs-mode: t
+# tab-width: 8
+# End:
+# vi: set tabstop=8 noexpandtab:
diff --git a/secure_monitor/include/arch/ops.h b/secure_monitor/include/arch/ops.h
new file mode 100644 (file)
index 0000000..1fb6ecf
--- /dev/null
@@ -0,0 +1,76 @@
+/*
+ * Copyright (c) 2008 Travis Geiselbrecht
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining
+ * a copy of this software and associated documentation files
+ * (the "Software"), to deal in the Software without restriction,
+ * including without limitation the rights to use, copy, modify, merge,
+ * publish, distribute, sublicense, and/or sell copies of the Software,
+ * and to permit persons to whom the Software is furnished to do so,
+ * subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
+ * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
+ * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
+ * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
+ * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ */
+#ifndef __ARCH_OPS_H
+#define __ARCH_OPS_H
+
+#ifndef ASSEMBLY
+
+#include <sys/types.h>
+#include <stddef.h>
+#include <compiler.h>
+
+#if defined(__cplusplus)
+extern "C" {
+#endif
+
+void arch_enable_ints(void);
+void arch_disable_ints(void);
+
+int atomic_swap(volatile int *ptr, int val);
+int atomic_add(volatile int *ptr, int val);
+int atomic_and(volatile int *ptr, int val);
+int atomic_or(volatile int *ptr, int val);
+
+#endif // !ASSEMBLY
+#define ICACHE 1
+#define DCACHE 2
+#define UCACHE (ICACHE|DCACHE)
+#ifndef ASSEMBLY
+
+void arch_disable_cache(uint flags);
+void arch_enable_cache(uint flags);
+
+void arch_clean_cache_range(addr_t start, size_t len);
+void arch_clean_invalidate_cache_range(addr_t start, size_t len);
+void arch_invalidate_cache_range(addr_t start, size_t len);
+void arch_sync_cache_range(addr_t start, size_t len);
+       
+void arch_idle(void);
+
+void arch_disable_mmu(void);
+
+void arch_switch_stacks_and_call(addr_t call, addr_t stack) __NO_RETURN;
+
+uint32_t arch_cycle_count(void);
+
+#if defined(__cplusplus)
+}
+#endif
+
+#endif // !ASSEMBLY
+
+#if ARCH_ARM
+#include <arch/arm/ops.h>
+#endif
+
+#endif
similarity index 64%
copy from platform/tegra/tegra3/tz.c
copy to secure_monitor/include/asm.h
index feadf78..dadf2c4 100644 (file)
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013, NVIDIA CORPORATION. All rights reserved
+ * Copyright (c) 2008 Travis Geiselbrecht
  *
  * Permission is hereby granted, free of charge, to any person obtaining
  * a copy of this software and associated documentation files
  * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
  * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
  */
+#ifndef __ASM_H
+#define __ASM_H
 
-#include <debug.h>
-#include <arch/outercache.h>
-#include <arch/arm.h>
-#include <platform/platform_p.h>
-#include <arch/arm/cache-l2x0.h>
+//#define FUNCTION(x) .global x; .type x,@function; x:
+#define FUNCTION(x) .global x; x:
 
-static int l2x0_init_done;
+#endif
 
-void tz_handle_smc_l2(unsigned int smc)
-{
-       if (smc == 0x1) {
-               if (!l2x0_init_done) {
-                       outer_init();
-                       l2x0_init_done = 1;
-               } else {
-                       platform_init_outer();
-                       outer_enable();
-               }
-       } else if (smc == 0x2) {
-               outer_flush_all();
-               outer_disable(); /* disable */
-       } else {
-               dprintf(INFO, "invalid L2 SMC\n");
-       }
-}
-
-void tz_handle_smc_deep_sleep(void)
-{
-       l2x0_init_done = 0;
-}
similarity index 65%
copy from platform/tegra/tegra3/tz.c
copy to secure_monitor/include/assert.h
index feadf78..332dfdb 100644 (file)
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013, NVIDIA CORPORATION. All rights reserved
+ * Copyright (c) 2008 Travis Geiselbrecht
  *
  * Permission is hereby granted, free of charge, to any person obtaining
  * a copy of this software and associated documentation files
  * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
  * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
  */
+#ifndef __ASSERT_H
+#define __ASSERT_H
 
+#include <compiler.h>
 #include <debug.h>
-#include <arch/outercache.h>
-#include <arch/arm.h>
-#include <platform/platform_p.h>
-#include <arch/arm/cache-l2x0.h>
 
-static int l2x0_init_done;
+#define ASSERT(x) \
+       do { if (unlikely(!(x))) { panic("ASSERT FAILED at (%s:%d): %s\n", __FILE__, __LINE__, #x); } } while (0)
 
-void tz_handle_smc_l2(unsigned int smc)
-{
-       if (smc == 0x1) {
-               if (!l2x0_init_done) {
-                       outer_init();
-                       l2x0_init_done = 1;
-               } else {
-                       platform_init_outer();
-                       outer_enable();
-               }
-       } else if (smc == 0x2) {
-               outer_flush_all();
-               outer_disable(); /* disable */
-       } else {
-               dprintf(INFO, "invalid L2 SMC\n");
-       }
-}
+#if DEBUGLEVEL > 1
+#define DEBUG_ASSERT(x) \
+       do { if (unlikely(!(x))) { panic("DEBUG ASSERT FAILED at (%s:%d): %s\n", __FILE__, __LINE__, #x); } } while (0)
+#else
+#define DEBUG_ASSERT(x) \
+       do { } while(0)
+#endif
 
-void tz_handle_smc_deep_sleep(void)
-{
-       l2x0_init_done = 0;
-}
+#endif
diff --git a/secure_monitor/include/compiler.h b/secure_monitor/include/compiler.h
new file mode 100644 (file)
index 0000000..cc96002
--- /dev/null
@@ -0,0 +1,155 @@
+/*
+ * Copyright (c) 2008 Travis Geiselbrecht
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining
+ * a copy of this software and associated documentation files
+ * (the "Software"), to deal in the Software without restriction,
+ * including without limitation the rights to use, copy, modify, merge,
+ * publish, distribute, sublicense, and/or sell copies of the Software,
+ * and to permit persons to whom the Software is furnished to do so,
+ * subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
+ * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
+ * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
+ * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
+ * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ */
+#ifndef __COMPILER_H
+#define __COMPILER_H
+
+#ifndef __ASSEMBLY__
+
+#if __GNUC__
+#define likely(x)       __builtin_expect(!!(x), 1)
+#define unlikely(x)     __builtin_expect(!!(x), 0)
+#define __UNUSED __attribute__((__unused__))
+#define __PACKED __attribute__((packed))
+#define __ALIGNED(x) __attribute__((aligned(x)))
+#define __PRINTFLIKE(__fmt,__varargs) __attribute__((__format__ (__printf__, __fmt, __varargs)))
+#define __SCANFLIKE(__fmt,__varargs) __attribute__((__format__ (__scanf__, __fmt, __varargs)))
+#define __SECTION(x) __attribute((section(x)))
+#define __PURE __attribute((pure))
+#define __CONST __attribute((const))
+#define __NO_RETURN __attribute__((noreturn)) 
+#define __MALLOC __attribute__((malloc))
+#define __WEAK __attribute__((weak))
+#define __GNU_INLINE __attribute__((gnu_inline))
+#define __GET_CALLER(x) __builtin_return_address(0)
+#define __GET_FRAME(x) __builtin_frame_address(0)
+#define __NAKED __attribute__((naked))
+#define __ISCONSTANT(x) __builtin_constant_p(x)
+
+#define INCBIN(symname, sizename, filename, section)                                   \
+       __asm__ (".section " section "; .align 4; .globl "#symname);            \
+       __asm__ (""#symname ":\n.incbin \"" filename "\"");                                     \
+       __asm__ (".section " section "; .align 1;");                                            \
+       __asm__ (""#symname "_end:");                                                                           \
+       __asm__ (".section " section "; .align 4; .globl "#sizename);           \
+       __asm__ (""#sizename ": .long "#symname "_end - "#symname " - 1");      \
+       extern unsigned char symname[];                                                                         \
+       extern unsigned int sizename
+
+#define INCFILE(symname, sizename, filename) INCBIN(symname, sizename, filename, ".rodata")
+
+/* look for gcc 3.0 and above */
+#if (__GNUC__ > 3) || (__GNUC__ == 3 && __GNUC_MINOR__ >= 0)
+#define __ALWAYS_INLINE __attribute__((always_inline))
+#else
+#define __ALWAYS_INLINE
+#endif
+
+/* look for gcc 3.1 and above */
+#if !defined(__DEPRECATED) // seems to be built in in some versions of the compiler
+#if (__GNUC__ > 3) || (__GNUC__ == 3 && __GNUC_MINOR__ >= 1)
+#define __DEPRECATED __attribute((deprecated))
+#else
+#define __DEPRECATED
+#endif
+#endif
+
+/* look for gcc 3.3 and above */
+#if (__GNUC__ > 3) || (__GNUC__ == 3 && __GNUC_MINOR__ >= 3)
+/* the may_alias attribute was introduced in gcc 3.3; before that, there
+ * was no way to specify aliasiang rules on a type-by-type basis */
+#define __MAY_ALIAS __attribute__((may_alias)) 
+
+/* nonnull was added in gcc 3.3 as well */
+#define __NONNULL(x) __attribute((nonnull x))
+#else
+#define __MAY_ALIAS
+#define __NONNULL(x)
+#endif
+
+/* look for gcc 3.4 and above */
+#if (__GNUC__ > 3) || (__GNUC__ == 3 && __GNUC_MINOR__ >= 4)
+#define __WARN_UNUSED_RESULT __attribute((warn_unused_result))
+#else
+#define __WARN_UNUSED_RESULT
+#endif
+
+#if (__GNUC__ > 4) || (__GNUC__ == 4 && __GNUC_MINOR__ >= 1)
+#define __EXTERNALLY_VISIBLE __attribute__((externally_visible))
+#else
+#define __EXTERNALLY_VISIBLE
+#endif
+
+#if (__GNUC__ > 4) || (__GNUC__ == 4 && __GNUC_MINOR__ >= 5)
+#define __UNREACHABLE __builtin_unreachable()
+#else
+#define __UNREACHABLE
+#endif
+
+/* compiler fence */
+#define CF do { __asm__ volatile("" ::: "memory"); } while(0)
+
+#define __WEAK_ALIAS(x) __attribute__((weak, alias(x)))
+#define __ALIAS(x) __attribute__((alias(x)))
+
+#define __EXPORT __attribute__ ((visibility("default")))
+#define __LOCAL  __attribute__ ((visibility("hidden")))
+
+#define __THREAD __thread
+
+#define __offsetof(type, field) __builtin_offsetof(type, field)
+
+#else
+
+#define likely(x)       (x)
+#define unlikely(x)     (x)
+#define __UNUSED 
+#define __PACKED 
+#define __ALIGNED(x)
+#define __PRINTFLIKE(__fmt,__varargs)
+#define __SCANFLIKE(__fmt,__varargs)
+#define __SECTION(x)
+#define __PURE
+#define __CONST
+#define __NONNULL(x)
+#define __DEPRECATED
+#define __WARN_UNUSED_RESULT
+#define __ALWAYS_INLINE
+#define __MAY_ALIAS
+#define __NO_RETURN
+#endif
+
+#endif
+
+/* TODO: add type check */
+#define countof(a) (sizeof(a) / sizeof((a)[0]))
+
+/* CPP header guards */
+#ifdef __cplusplus
+#define __BEGIN_CDECLS  extern "C" {
+#define __END_CDECLS    }
+#else
+#define __BEGIN_CDECLS
+#define __END_CDECLS
+#endif
+
+#endif
diff --git a/secure_monitor/include/debug.h b/secure_monitor/include/debug.h
new file mode 100644 (file)
index 0000000..4554717
--- /dev/null
@@ -0,0 +1,124 @@
+/*
+ * Copyright (c) 2008-2012 Travis Geiselbrecht
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining
+ * a copy of this software and associated documentation files
+ * (the "Software"), to deal in the Software without restriction,
+ * including without limitation the rights to use, copy, modify, merge,
+ * publish, distribute, sublicense, and/or sell copies of the Software,
+ * and to permit persons to whom the Software is furnished to do so,
+ * subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
+ * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
+ * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
+ * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
+ * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ */
+#ifndef __DEBUG_H
+#define __DEBUG_H
+
+#include <stdarg.h>
+#include <stddef.h>
+#include <compiler.h>
+#include <platform/debug.h>
+#include <printf.h>
+
+__BEGIN_CDECLS
+
+/*
+ * It defines the debug level and restricts the number of prints that
+ * is to be printed in release or debug builds.
+ */
+#if defined(DEBUG)
+#define DEBUGLEVEL DEBUG
+#else
+#define DEBUGLEVEL 2
+#endif
+
+/* Various logging output mechanisms */
+
+/* debug levels */
+#define CRITICAL 0
+#define ALWAYS 0
+#define INFO 1
+#define SPEW 2
+
+/* Shared buffer size */
+#define EARLYBUF_SIZE 4096
+
+struct circular_buffer {
+       uint32_t size; /* Indicates the total size of the buffer */
+       uint32_t start; /* Starting point of valid data in buffer */
+       uint32_t end; /* First character which is empty (can be written to) */
+       uint32_t overflow; /* Indicator whether buffer has overflown or not */
+       nsaddr_t buf;
+};
+
+extern char early_logbuf[EARLYBUF_SIZE];
+extern int early_char_count;
+
+#if !DISABLE_DEBUG_OUTPUT
+
+/* input/output */
+#define _dputc(c) platform_dputc(c)
+int _dputs(const char *str);
+int _dprintf(const char *fmt, ...) __PRINTFLIKE(1, 2);
+int _dvprintf(const char *fmt, va_list ap);
+
+/* dump memory */
+void hexdump(const void *ptr, size_t len);
+void hexdump8(const void *ptr, size_t len);
+
+#else
+
+/* input/output */
+static inline void _dputc(char c) { }
+static inline int _dputs(const char *str) { return 0; }
+static inline int __PRINTFLIKE(1, 2) _dprintf(const char *fmt, ...) { return 0; }
+static inline int _dvprintf(const char *fmt, va_list ap) { return 0; }
+
+/* dump memory */
+static inline void hexdump(const void *ptr, size_t len) { }
+static inline void hexdump8(const void *ptr, size_t len) { }
+
+#endif /* DISABLE_DEBUG_OUTPUT */
+
+#define dputc(level, str) do { if ((level) <= DEBUGLEVEL) { _dputc(str); } } while (0)
+#define dputs(level, str) do { if ((level) <= DEBUGLEVEL) { _dputs(str); } } while (0)
+#define dprintf(level, x...) do { if ((level) <= DEBUGLEVEL) { _dprintf(x); } } while (0)
+#define dvprintf(level, x...) do { if ((level) <= DEBUGLEVEL) { _dvprintf(x); } } while (0)
+
+/* trace routines */
+#define TRACE_ENTRY printf("%s: entry\n", __PRETTY_FUNCTION__)
+#define TRACE_EXIT printf("%s: exit\n", __PRETTY_FUNCTION__)
+#define TRACE_ENTRY_OBJ printf("%s: entry obj %p\n", __PRETTY_FUNCTION__, this)
+#define TRACE_EXIT_OBJ printf("%s: exit obj %p\n", __PRETTY_FUNCTION__, this)
+#define TRACE printf("%s:%d\n", __PRETTY_FUNCTION__, __LINE__)
+#define TRACEF(str, x...) do { printf("%s:%d: " str, __PRETTY_FUNCTION__, __LINE__, ## x); } while (0)
+
+/* trace routines that work if LOCAL_TRACE is set */
+#define LTRACE_ENTRY do { if (LOCAL_TRACE) { TRACE_ENTRY; } } while (0)
+#define LTRACE_EXIT do { if (LOCAL_TRACE) { TRACE_EXIT; } } while (0)
+#define LTRACE do { if (LOCAL_TRACE) { TRACE; } } while (0)
+#define LTRACEF(x...) do { if (LOCAL_TRACE) { TRACEF(x); } } while (0)
+
+/* systemwide halts */
+void halt(void) __NO_RETURN;
+
+void _panic(void *caller, const char *fmt, ...) __PRINTFLIKE(2, 3) __NO_RETURN;
+#define panic(x...) _panic(__GET_CALLER(), x)
+
+#define PANIC_UNIMPLEMENTED panic("%s unimplemented\n", __PRETTY_FUNCTION__)
+
+/* spin the cpu for a period of (short) time */
+void spin(uint32_t usecs);
+
+__END_CDECLS
+
+#endif
diff --git a/secure_monitor/include/endian.h b/secure_monitor/include/endian.h
new file mode 100644 (file)
index 0000000..34bef6e
--- /dev/null
@@ -0,0 +1,99 @@
+/*
+ * Copyright (c) 2008 Travis Geiselbrecht
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining
+ * a copy of this software and associated documentation files
+ * (the "Software"), to deal in the Software without restriction,
+ * including without limitation the rights to use, copy, modify, merge,
+ * publish, distribute, sublicense, and/or sell copies of the Software,
+ * and to permit persons to whom the Software is furnished to do so,
+ * subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
+ * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
+ * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
+ * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
+ * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ */
+#ifndef __ENDIAN_H
+#define __ENDIAN_H
+
+#include <sys/types.h>
+
+#ifndef LITTLE_ENDIAN
+#define LITTLE_ENDIAN 1234
+#endif
+#ifndef BIG_ENDIAN
+#define BIG_ENDIAN 4321
+#endif
+
+#if __POWERPC__
+#include <ppc_intrinsics.h>
+#endif
+
+#if defined(ARCH_ARM)
+#define BYTE_ORDER LITTLE_ENDIAN
+#endif
+
+#if defined(__i386__) || defined(_X86_)
+#define BYTE_ORDER LITTLE_ENDIAN
+#endif
+
+#ifndef BYTE_ORDER
+#error "need to get the BYTE_ORDER define from somewhere"
+#endif
+
+// define a macro that unconditionally swaps
+#define SWAP_32(x) \
+       (((uint32_t)(x) << 24) | (((uint32_t)(x) & 0xff00) << 8) |(((uint32_t)(x) & 0x00ff0000) >> 8) | ((uint32_t)(x) >> 24))
+#define SWAP_16(x) \
+       ((((uint16_t)(x) & 0xff) << 8) | ((uint16_t)(x) >> 8))
+
+// standard swap macros
+#if BYTE_ORDER == BIG_ENDIAN
+#define LE32(val) SWAP_32(val)
+#define LE16(val) SWAP_16(val)
+#define BE32(val) (val)
+#define BE16(val) (val)
+#else
+#define LE32(val) (val)
+#define LE16(val) (val)
+#define BE32(val) SWAP_32(val)
+#define BE16(val) SWAP_16(val)
+#endif
+
+#define LE32SWAP(var) (var) = LE32(var);
+#define LE16SWAP(var) (var) = LE16(var);
+#define BE32SWAP(var) (var) = BE32(var);
+#define BE16SWAP(var) (var) = BE16(var);
+
+/* classic network byte swap stuff */
+#define ntohs(n) BE16(n)
+#define htons(h) BE16(h)
+#define ntohl(n) BE32(n)
+#define htonl(h) BE32(h)
+
+// some memory access macros
+#if __POWERPC__
+#define READ_MEM_WORD(ptr)             __lwbrx((word *)(ptr), 0)
+#define READ_MEM_HALFWORD(ptr)         __lhbrx((halfword *)(ptr), 0)
+#define READ_MEM_BYTE(ptr)             (*(byte *)(ptr))
+#define WRITE_MEM_WORD(ptr, data)      __stwbrx(data, (word *)(ptr), 0)
+#define WRITE_MEM_HALFWORD(ptr, data)  __sthbrx(data, (halfword *)(ptr), 0)
+#define WRITE_MEM_BYTE(ptr, data)      (*(byte *)(ptr) = (data))
+#else
+#define READ_MEM_WORD(ptr)             SWAPIT_32(*(word *)(ptr))
+#define READ_MEM_HALFWORD(ptr)         SWAPIT_16(*(halfword *)(ptr))
+#define READ_MEM_BYTE(ptr)             (*(byte *)(ptr))
+#define WRITE_MEM_WORD(ptr, data)      (*(word *)(ptr) = SWAPIT_32(data))
+#define WRITE_MEM_HALFWORD(ptr, data)  (*(halfword *)(ptr) = SWAPIT_16(data))
+#define WRITE_MEM_BYTE(ptr, data)      (*(byte *)(ptr) = (data))
+#endif
+
+
+#endif
similarity index 55%
copy from lib/monitor/arm64/include/psci.h
copy to secure_monitor/include/err.h
index 3bb219b..7f6eaf2 100644 (file)
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014, NVIDIA CORPORATION. All rights reserved
+ * Copyright (c) 2008 Travis Geiselbrecht
  *
  * Permission is hereby granted, free of charge, to any person obtaining
  * a copy of this software and associated documentation files
  * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
  * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
  */
-#ifndef __PSCI_H
-#define __PSCI_H
+#ifndef __ERR_H
+#define __ERR_H
 
-#define PSCI_FUNC_ID_VERSION           0x84000000
-#define PSCI_FUNC_ID_CPU_SUSPEND_LEGACY        0x84000001
-#define PSCI_FUNC_ID_CPU_SUSPEND       0xC4000001
-#define PSCI_FUNC_ID_CPU_OFF           0xC4000002
-#define PSCI_FUNC_ID_CPU_ON            0xC4000003
-#define PSCI_FUNC_ID_AFFINITY_INFO     0xC4000004
-#define PSCI_FUNC_ID_MIGRATE           0xC4000005
+#include <sys/types.h> // for status_t
 
-#define PSCI_RETURN_SUCCESS            (0)
-#define PSCI_RETURN_NOT_SUPPORTED      (-1)
-#define PSCI_RETURN_INVALID_PARAMS     (-2)
-#define PSCI_RETURN_DENIED             (-3)
-#define PSCI_RETURN_ALREADY_ON         (-4)
-#define PSCI_RETURN_ON_PENDING         (-5)
-#define PSCI_RETURN_INTERNAL_FAILURE   (-6)
-#define PSCI_RETURN_NOT_PRESENT                (-7)
-#define PSCI_RETURN_DISABLED           (-8)
+#define NO_ERROR 0
+#define ERR_GENERIC -1
+#define ERR_NOT_FOUND -2
+#define ERR_NOT_READY -3
+#define ERR_NO_MSG -4
+#define ERR_NO_MEMORY -5
+#define ERR_ALREADY_STARTED -6
+#define ERR_NOT_VALID -7
+#define ERR_INVALID_ARGS -8
+#define ERR_NOT_ENOUGH_BUFFER -9
+#define ERR_NOT_SUSPENDED -10
+#define ERR_OBJECT_DESTROYED -11
+#define ERR_NOT_BLOCKED -12
+#define ERR_TIMED_OUT -13
+#define ERR_ALREADY_EXISTS -14
+#define ERR_CHANNEL_CLOSED -15
+#define ERR_OFFLINE -16
+#define ERR_NOT_ALLOWED -17
+#define ERR_BAD_PATH -18
+#define ERR_ALREADY_MOUNTED -19
+#define ERR_IO -20
+#define ERR_NOT_DIR -21
+#define ERR_NOT_FILE -22
+#define ERR_RECURSE_TOO_DEEP -23
+#define ERR_NOT_SUPPORTED -24
+#define ERR_TOO_BIG -25
+
+#define ERR_TOO_MANY_TASKS -26
+#define ERR_TASK_GENERIC -27
 
 #endif
diff --git a/secure_monitor/include/lib/monitor/monitor_vector.h b/secure_monitor/include/lib/monitor/monitor_vector.h
new file mode 100644 (file)
index 0000000..2844e44
--- /dev/null
@@ -0,0 +1,135 @@
+/*
+ * Copyright (c) 2014, NVIDIA CORPORATION. All rights reserved
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining
+ * a copy of this software and associated documentation files
+ * (the "Software"), to deal in the Software without restriction,
+ * including without limitation the rights to use, copy, modify, merge,
+ * publish, distribute, sublicense, and/or sell copies of the Software,
+ * and to permit persons to whom the Software is furnished to do so,
+ * subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
+ * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
+ * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
+ * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
+ * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ */
+#ifndef __MONITOR_VECTOR_H
+#define __MONITOR_VECTOR_H
+
+#ifndef ASSEMBLY
+#define UL(x)  (x##UL)
+#else
+#define UL(x)  (x)
+#endif
+
+#if !defined(ASSEMBLY) && defined(WITH_MONITOR_BIN)
+/*
+ * Exported monitor data structures and functions which can be
+ * referenced by routines also linked into the monitor binary.
+ */
+extern uintptr_t __mon_cpu_return_addr;
+extern uintptr_t __mon_cpu_reset_vector;
+extern uintptr_t __mon_phys_base;
+extern uintptr_t __mon_phys_size;
+
+/* holds arguments/return value during fastcalls */
+struct fastcall_frame {
+       uint64_t r[8];  /* r0-r7 */
+};
+
+paddr_t mon_virt_to_phys(void *vaddr);
+void *mon_phys_to_virt(uint64_t paddr);
+
+int mon_mmu_map_mmio(uintptr_t vaddr, uint64_t paddr, uint32_t length);
+void mon_mmu_map_uncached(uintptr_t vaddr, uint64_t paddr, uint32_t length);
+void mon_mmu_unmap(uintptr_t vaddr, uint32_t length);
+
+void mon_atomic_or(volatile uint32_t *ptr, uint32_t bits);
+void mon_atomic_and(volatile uint32_t *ptr, uint32_t bits);
+
+uint32_t mon_get_cpu_id(void);
+
+/*
+ * CPU power down sequence as per A57/A53 TRM
+ *
+ * l2_flush = indicates if L2 flush is required
+ *
+ */
+void mon_cpu_power_down(int l2_flush);
+
+#endif // !ASSEMBLY && WITH_MONITOR_BIN
+
+
+#define SMC_STDCALL                    (UL(0) << 31)
+#define SMC_FASTCALL                   (UL(1) << 31)
+
+#define SMC_CALLING_CONVENTION_32      (UL(0) << 30)
+#define SMC_CALLING_CONVENTION_64      (UL(1) << 30)
+
+#define SMC_OWNER_MASK                 0x3F
+#define SMC_OWNER_SHIFT                        24
+
+#define SMC_OWNER_ARM_ARCH             0x0
+#define SMC_OWNER_CPU_SERVICE          0x1
+#define SMC_OWNER_SIP_SERVICE          0x2
+#define SMC_OWNER_OEM_SERVICE          0x3
+#define SMC_OWNER_ARM_STD              0x4
+
+#define SMC_OWNER_TRUSTED_BASE         0x30
+#define SMC_OWNER_TRUSTED_SERVICE      0x5
+
+#define SMC_MUST_BE_ZERO_MASK          0xFF
+#define SMC_MUST_BE_ZERO_SHIFT         16
+
+/* legacy when fastcall & MBZ field is all 1s */
+#define SMC_IS_LEGACY  \
+       (SMC_FASTCALL | (SMC_MUST_BE_ZERO_MASK << SMC_MUST_BE_ZERO_SHIFT))
+
+/* Silicon Partner issued SMCs */
+#define SMC_SIP_CALL                   (SMC_OWNER_SIP_SERVICE << SMC_OWNER_SHIFT)
+#define SMC_SIP_AARCH_SWITCH           (SMC_FASTCALL | SMC_SIP_CALL | 0x4)
+#define SMC_SIP_GET_FIQ_REGS           (SMC_FASTCALL | SMC_SIP_CALL | 0x6)
+
+/* Trusted OS issued SMC (i.e. generated from the TLK kernel) */
+#define SMC_TOS_CALL                   (0x32 << SMC_OWNER_SHIFT)
+#define SMC_TOS_FROM_SECURE            (1 << 15)
+#define SMC_TOS_PREEMPT                        (1 << 12)
+
+#if ARCH_ARM
+/* TOS 32bit secure fastcalls */
+#define SMC_TOS_SECURE (SMC_FASTCALL | SMC_TOS_CALL | \
+                        SMC_TOS_FROM_SECURE | SMC_CALLING_CONVENTION_32)
+#endif
+#if ARCH_ARM64
+/* TOS 64bit secure fastcalls */
+#define SMC_TOS_SECURE (SMC_FASTCALL | SMC_TOS_CALL | \
+                        SMC_TOS_FROM_SECURE | SMC_CALLING_CONVENTION_64)
+#endif
+
+/* low byte used as jump table idx */
+#define        SMC_TOS_FUNC_ID_MASK            0xFF
+
+/* TOS issued SMCs (update MAX_FUNC_IDX when adding new calls) */
+#define        SMC_TOS_COMPLETION              (SMC_TOS_SECURE | 0x1)
+#define        SMC_TOS_PREEMPT_BY_IRQ          (SMC_TOS_SECURE | SMC_TOS_PREEMPT | 0x2)
+#define        SMC_TOS_PREEMPT_BY_FS           (SMC_TOS_SECURE | SMC_TOS_PREEMPT | 0x3)
+#define        SMC_TOS_INITIAL_NS_RETURN       (SMC_TOS_SECURE | 0x4)
+#define        SMC_TOS_ADDR_TRANSLATE          (SMC_TOS_SECURE | 0x5)
+#define        SMC_TOS_INIT_SHARED_ADDR        (SMC_TOS_SECURE | 0x6)
+#define        SMC_TOS_MAX_FUNC_IDX            0x6
+
+/* restart pre-empted SMC handling */
+#define SMC_TOS_RESTART                        (60 << 24)
+
+/* informs the NS world that we were pre-empted by an irq */
+#define SMC_ERR_PREEMPT_BY_IRQ         0xFFFFFFFD
+#define SMC_ERR_PREEMPT_BY_FS          0xFFFFFFFE
+
+#endif
similarity index 64%
copy from platform/tegra/tegra3/tz.c
copy to secure_monitor/include/malloc.h
index feadf78..c8fa6a8 100644 (file)
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013, NVIDIA CORPORATION. All rights reserved
+ * Copyright (c) 2008 Travis Geiselbrecht
  *
  * Permission is hereby granted, free of charge, to any person obtaining
  * a copy of this software and associated documentation files
  * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
  * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
  */
+#ifndef __MALLOC_H
+#define __MALLOC_H
 
-#include <debug.h>
-#include <arch/outercache.h>
-#include <arch/arm.h>
-#include <platform/platform_p.h>
-#include <arch/arm/cache-l2x0.h>
+#include <sys/types.h>
+#include <compiler.h>
 
-static int l2x0_init_done;
+#if defined(__cplusplus)
+extern "C" {
+#endif
 
-void tz_handle_smc_l2(unsigned int smc)
-{
-       if (smc == 0x1) {
-               if (!l2x0_init_done) {
-                       outer_init();
-                       l2x0_init_done = 1;
-               } else {
-                       platform_init_outer();
-                       outer_enable();
-               }
-       } else if (smc == 0x2) {
-               outer_flush_all();
-               outer_disable(); /* disable */
-       } else {
-               dprintf(INFO, "invalid L2 SMC\n");
-       }
-}
+void *malloc(size_t size) __MALLOC;
+void *memalign(size_t boundary, size_t size) __MALLOC;
+void *calloc(size_t count, size_t size) __MALLOC;
+void *realloc(void *ptr, size_t size) __MALLOC;
+void free(void *ptr);
+void free_memalign(void *ptr);
 
-void tz_handle_smc_deep_sleep(void)
-{
-       l2x0_init_done = 0;
+#if defined(__cplusplus)
 }
+#endif
+
+#endif
+
similarity index 54%
copy from lib/monitor/common/debug.c
copy to secure_monitor/include/platform.h
index c51d1d2..a62c76e 100644 (file)
@@ -1,5 +1,6 @@
 /*
- * Copyright (c) 2008-2012 Travis Geiselbrecht
+ * Copyright (c) 2008 Travis Geiselbrecht
+ * Copyright (c) 2012-2014, NVIDIA CORPORATION. All rights reserved
  *
  * Permission is hereby granted, free of charge, to any person obtaining
  * a copy of this software and associated documentation files
  * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
  * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
  */
-#include <debug.h>
+#ifndef __PLATFORM_H
+#define __PLATFORM_H
 
-void halt(void)
-{
-       platform_halt();
-}
+#include <sys/types.h>
 
-void _panic(void *caller, const char *fmt, ...)
-{
-       dprintf(ALWAYS, "panic (caller %p): ", caller);
+lk_time_t current_time(void);
+lk_bigtime_t current_time_hires(void);
 
-       va_list ap;
-       va_start(ap, fmt);
-       _dvprintf(fmt, ap);
-       va_end(ap);
+/* super early platform initialization, before almost everything */
+void platform_early_init(void);
 
-       halt();
-}
+/* later init, after the kernel has come up */
+void platform_init(void);
 
-#if !DISABLE_DEBUG_OUTPUT
+/* called by the arch init code to get the platform to set up any mmu mappings it may need */
+void platform_init_mmu_mappings(void);
 
-int _dputs(const char *str)
-{
-       while(*str != 0) {
-               _dputc(*str++);
-       }
+/* used by platforms to implement their own idle routine */
+void platform_idle(void);
 
-       return 0;
-}
+/* return l2x0 base address */
+uint32_t platform_l2x0_base(void);
 
-static int _dprintf_output_func(char c, void *state)
-{
-       _dputc(c);
-       return INT_MAX;
-}
+/* init outer cache */
+void platform_init_outer(void);
 
-int _dprintf(const char *fmt, ...)
-{
-       int err;
+/* handle syscall */
+bool platform_syscall_handler(void *arg);
 
-       va_list ap;
-       va_start(ap, fmt);
-       err = _printf_engine(&_dprintf_output_func, NULL, fmt, ap);
-       va_end(ap);
+/* Get a random number */
+uint32_t platform_get_rand32(void);
 
-       return err;
-}
-
-int _dvprintf(const char *fmt, va_list ap)
-{
-       int err;
-
-       err = _printf_engine(&_dprintf_output_func, NULL, fmt, ap);
-
-       return err;
-}
-
-#endif // !DISABLE_DEBUG_OUTPUT
+void platform_monitor_init_cpu(void);
+#endif
similarity index 64%
copy from platform/tegra/tegra3/tz.c
copy to secure_monitor/include/platform/debug.h
index feadf78..42e9fc6 100644 (file)
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013, NVIDIA CORPORATION. All rights reserved
+ * Copyright (c) 2008 Travis Geiselbrecht
  *
  * Permission is hereby granted, free of charge, to any person obtaining
  * a copy of this software and associated documentation files
  * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
  * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
  */
+#ifndef __PLATFORM_DEBUG_H
+#define __PLATFORM_DEBUG_H
 
-#include <debug.h>
-#include <arch/outercache.h>
-#include <arch/arm.h>
-#include <platform/platform_p.h>
-#include <arch/arm/cache-l2x0.h>
+#include <sys/types.h>
+#include <stdbool.h>
+#include <stdarg.h>
+#include <compiler.h>
 
-static int l2x0_init_done;
+__BEGIN_CDECLS
 
-void tz_handle_smc_l2(unsigned int smc)
-{
-       if (smc == 0x1) {
-               if (!l2x0_init_done) {
-                       outer_init();
-                       l2x0_init_done = 1;
-               } else {
-                       platform_init_outer();
-                       outer_enable();
-               }
-       } else if (smc == 0x2) {
-               outer_flush_all();
-               outer_disable(); /* disable */
-       } else {
-               dprintf(INFO, "invalid L2 SMC\n");
-       }
-}
+void platform_halt(void) __NO_RETURN;
+void platform_init_debug_port(unsigned int dbg_port);
+void platform_dputc(char c);
+int platform_dgetc(char *c, bool wait);
+
+__END_CDECLS
+
+#endif
 
-void tz_handle_smc_deep_sleep(void)
-{
-       l2x0_init_done = 0;
-}
similarity index 64%
copy from platform/tegra/tegra3/tz.c
copy to secure_monitor/include/platform/interrupts.h
index feadf78..7ee25bc 100644 (file)
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013, NVIDIA CORPORATION. All rights reserved
+ * Copyright (c) 2008 Travis Geiselbrecht
  *
  * Permission is hereby granted, free of charge, to any person obtaining
  * a copy of this software and associated documentation files
  * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
  * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
  */
+#ifndef __PLATFORM_INTERRUPTS_H
+#define __PLATFORM_INTERRUPTS_H
 
-#include <debug.h>
-#include <arch/outercache.h>
-#include <arch/arm.h>
-#include <platform/platform_p.h>
-#include <arch/arm/cache-l2x0.h>
+#include <sys/types.h>
 
-static int l2x0_init_done;
+status_t mask_interrupt(unsigned int vector);
+status_t unmask_interrupt(unsigned int vector);
 
-void tz_handle_smc_l2(unsigned int smc)
-{
-       if (smc == 0x1) {
-               if (!l2x0_init_done) {
-                       outer_init();
-                       l2x0_init_done = 1;
-               } else {
-                       platform_init_outer();
-                       outer_enable();
-               }
-       } else if (smc == 0x2) {
-               outer_flush_all();
-               outer_disable(); /* disable */
-       } else {
-               dprintf(INFO, "invalid L2 SMC\n");
-       }
-}
+typedef enum handler_return (*int_handler)(void *arg);
 
-void tz_handle_smc_deep_sleep(void)
-{
-       l2x0_init_done = 0;
-}
+void register_int_handler(unsigned int vector, int_handler handler, void *arg);
+
+#endif
similarity index 52%
copy from lib/monitor/common/debug.c
copy to secure_monitor/include/printf.h
index c51d1d2..1e237c5 100644 (file)
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2008-2012 Travis Geiselbrecht
+ * Copyright (c) 2008 Travis Geiselbrecht
  *
  * Permission is hereby granted, free of charge, to any person obtaining
  * a copy of this software and associated documentation files
  * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
  * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
  */
-#include <debug.h>
-
-void halt(void)
-{
-       platform_halt();
-}
-
-void _panic(void *caller, const char *fmt, ...)
-{
-       dprintf(ALWAYS, "panic (caller %p): ", caller);
+#ifndef __LIB_PRINTF_H
+#define __LIB_PRINTF_H
 
-       va_list ap;
-       va_start(ap, fmt);
-       _dvprintf(fmt, ap);
-       va_end(ap);
+#include <stdarg.h>
+#include <compiler.h>
+#include <debug.h>
+#include <stddef.h>
 
-       halt();
-}
+#if defined(__cplusplus)
+extern "C" {
+#endif
 
 #if !DISABLE_DEBUG_OUTPUT
+#define printf(x...) _printf(x)
+#else
+static inline int __PRINTFLIKE(1, 2) printf(const char *fmt, ...) { return 0; }
+#endif
 
-int _dputs(const char *str)
-{
-       while(*str != 0) {
-               _dputc(*str++);
-       }
-
-       return 0;
-}
-
-static int _dprintf_output_func(char c, void *state)
-{
-       _dputc(c);
-       return INT_MAX;
-}
-
-int _dprintf(const char *fmt, ...)
-{
-       int err;
+int _printf(const char *fmt, ...) __PRINTFLIKE(1, 2);
+int sprintf(char *str, const char *fmt, ...) __PRINTFLIKE(2, 3);
+int snprintf(char *str, size_t len, const char *fmt, ...) __PRINTFLIKE(3, 4);
+int vsprintf(char *str, const char *fmt, va_list ap);
+int vsnprintf(char *str, size_t len, const char *fmt, va_list ap);
 
-       va_list ap;
-       va_start(ap, fmt);
-       err = _printf_engine(&_dprintf_output_func, NULL, fmt, ap);
-       va_end(ap);
+/* printf engine that parses the format string and generates output */
 
-       return err;
-}
-
-int _dvprintf(const char *fmt, va_list ap)
-{
-       int err;
+/* function pointer to pass the engine, 
+ * return code is remaining characters in destination (or INT_MAX for infinity)
+ */
+typedef int (*_printf_engine_output_func)(char c, void *state);
 
-       err = _printf_engine(&_dprintf_output_func, NULL, fmt, ap);
+int _printf_engine(_printf_engine_output_func out, void *state, const char *fmt, va_list ap);
 
-       return err;
+#if defined(__cplusplus)
 }
+#endif
 
-#endif // !DISABLE_DEBUG_OUTPUT
+#endif
similarity index 52%
copy from lib/monitor/arm64/include/psci.h
copy to secure_monitor/include/reg.h
index 3bb219b..d04d4ea 100644 (file)
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014, NVIDIA CORPORATION. All rights reserved
+ * Copyright (c) 2008 Travis Geiselbrecht
  *
  * Permission is hereby granted, free of charge, to any person obtaining
  * a copy of this software and associated documentation files
  * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
  * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
  */
-#ifndef __PSCI_H
-#define __PSCI_H
+#ifndef __REG_H
+#define __REG_H
 
-#define PSCI_FUNC_ID_VERSION           0x84000000
-#define PSCI_FUNC_ID_CPU_SUSPEND_LEGACY        0x84000001
-#define PSCI_FUNC_ID_CPU_SUSPEND       0xC4000001
-#define PSCI_FUNC_ID_CPU_OFF           0xC4000002
-#define PSCI_FUNC_ID_CPU_ON            0xC4000003
-#define PSCI_FUNC_ID_AFFINITY_INFO     0xC4000004
-#define PSCI_FUNC_ID_MIGRATE           0xC4000005
+#include <sys/types.h>
 
-#define PSCI_RETURN_SUCCESS            (0)
-#define PSCI_RETURN_NOT_SUPPORTED      (-1)
-#define PSCI_RETURN_INVALID_PARAMS     (-2)
-#define PSCI_RETURN_DENIED             (-3)
-#define PSCI_RETURN_ALREADY_ON         (-4)
-#define PSCI_RETURN_ON_PENDING         (-5)
-#define PSCI_RETURN_INTERNAL_FAILURE   (-6)
-#define PSCI_RETURN_NOT_PRESENT                (-7)
-#define PSCI_RETURN_DISABLED           (-8)
+/* low level macros for accessing memory mapped hardware registers */
+#define REG64(addr) ((volatile uint64_t *)(addr))
+#define REG32(addr) ((volatile uint32_t *)(addr))
+#define REG16(addr) ((volatile uint16_t *)(addr))
+#define REG8(addr) ((volatile uint8_t *)(addr))
+
+#define RMWREG64(addr, startbit, width, val) *REG64(addr) = (*REG64(addr) & ~(((1<<(width)) - 1) << (startbit))) | ((val) << (startbit))
+#define RMWREG32(addr, startbit, width, val) *REG32(addr) = (*REG32(addr) & ~(((1<<(width)) - 1) << (startbit))) | ((val) << (startbit))
+#define RMWREG16(addr, startbit, width, val) *REG16(addr) = (*REG16(addr) & ~(((1<<(width)) - 1) << (startbit))) | ((val) << (startbit))
+#define RMWREG8(addr, startbit, width, val) *REG8(addr) = (*REG8(addr) & ~(((1<<(width)) - 1) << (startbit))) | ((val) << (startbit))
+
+#define writel(v, a) (*REG32(a) = (v))
+#define readl(a) (*REG32(a))
 
 #endif
similarity index 64%
copy from platform/tegra/tegra3/tz.c
copy to secure_monitor/include/stdbool.h
index feadf78..ba83e84 100644 (file)
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013, NVIDIA CORPORATION. All rights reserved
+ * Copyright (c) 2012 Travis Geiselbrecht
  *
  * Permission is hereby granted, free of charge, to any person obtaining
  * a copy of this software and associated documentation files
  * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
  * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
  */
+#ifndef __STDBOOL_H
+#define __STDBOOL_H
 
-#include <debug.h>
-#include <arch/outercache.h>
-#include <arch/arm.h>
-#include <platform/platform_p.h>
-#include <arch/arm/cache-l2x0.h>
+#ifndef __cplusplus
 
-static int l2x0_init_done;
+#define bool _Bool
+#define true 1
+#define false 0
 
-void tz_handle_smc_l2(unsigned int smc)
-{
-       if (smc == 0x1) {
-               if (!l2x0_init_done) {
-                       outer_init();
-                       l2x0_init_done = 1;
-               } else {
-                       platform_init_outer();
-                       outer_enable();
-               }
-       } else if (smc == 0x2) {
-               outer_flush_all();
-               outer_disable(); /* disable */
-       } else {
-               dprintf(INFO, "invalid L2 SMC\n");
-       }
-}
+#endif
 
-void tz_handle_smc_deep_sleep(void)
-{
-       l2x0_init_done = 0;
-}
+#define __bool_true_false_are_defined 1
+
+#endif
similarity index 64%
copy from platform/tegra/tegra3/tz.c
copy to secure_monitor/include/stddef.h
index feadf78..a19c3db 100644 (file)
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013, NVIDIA CORPORATION. All rights reserved
+ * Copyright (c) 2012 Travis Geiselbrecht
  *
  * Permission is hereby granted, free of charge, to any person obtaining
  * a copy of this software and associated documentation files
  * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
  * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
  */
+#ifndef __STDDEF_H
+#define __STDDEF_H
 
-#include <debug.h>
-#include <arch/outercache.h>
-#include <arch/arm.h>
-#include <platform/platform_p.h>
-#include <arch/arm/cache-l2x0.h>
+#include <compiler.h> // for __offsetof()
 
-static int l2x0_init_done;
+#define offsetof(x, y) __offsetof(x, y)
 
-void tz_handle_smc_l2(unsigned int smc)
-{
-       if (smc == 0x1) {
-               if (!l2x0_init_done) {
-                       outer_init();
-                       l2x0_init_done = 1;
-               } else {
-                       platform_init_outer();
-                       outer_enable();
-               }
-       } else if (smc == 0x2) {
-               outer_flush_all();
-               outer_disable(); /* disable */
-       } else {
-               dprintf(INFO, "invalid L2 SMC\n");
-       }
-}
+typedef long ptrdiff_t;
 
-void tz_handle_smc_deep_sleep(void)
-{
-       l2x0_init_done = 0;
-}
+#ifndef _SIZE_T_DEFINED_
+typedef unsigned long size_t;
+#endif
+typedef long          ssize_t;
+
+#define NULL 0
+
+#endif
similarity index 51%
copy from lib/monitor/arm64/include/psci.h
copy to secure_monitor/include/stdint.h
index 3bb219b..7655059 100644 (file)
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014, NVIDIA CORPORATION. All rights reserved
+ * Copyright (c) 2008 Travis Geiselbrecht
  *
  * Permission is hereby granted, free of charge, to any person obtaining
  * a copy of this software and associated documentation files
  * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
  * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
  */
-#ifndef __PSCI_H
-#define __PSCI_H
-
-#define PSCI_FUNC_ID_VERSION           0x84000000
-#define PSCI_FUNC_ID_CPU_SUSPEND_LEGACY        0x84000001
-#define PSCI_FUNC_ID_CPU_SUSPEND       0xC4000001
-#define PSCI_FUNC_ID_CPU_OFF           0xC4000002
-#define PSCI_FUNC_ID_CPU_ON            0xC4000003
-#define PSCI_FUNC_ID_AFFINITY_INFO     0xC4000004
-#define PSCI_FUNC_ID_MIGRATE           0xC4000005
-
-#define PSCI_RETURN_SUCCESS            (0)
-#define PSCI_RETURN_NOT_SUPPORTED      (-1)
-#define PSCI_RETURN_INVALID_PARAMS     (-2)
-#define PSCI_RETURN_DENIED             (-3)
-#define PSCI_RETURN_ALREADY_ON         (-4)
-#define PSCI_RETURN_ON_PENDING         (-5)
-#define PSCI_RETURN_INTERNAL_FAILURE   (-6)
-#define PSCI_RETURN_NOT_PRESENT                (-7)
-#define PSCI_RETURN_DISABLED           (-8)
+#ifndef __STDINT_H
+#define __STDINT_H
+
+#include <sys/types.h> // for ULONG_MAX
+
+typedef unsigned char      uint8_t;
+typedef unsigned short     uint16_t;
+typedef unsigned int       uint32_t;
+typedef unsigned long long uint64_t;
+typedef signed char int8_t;
+typedef short     int16_t;
+typedef int       int32_t;
+typedef long long int64_t;
+
+typedef int8_t int_least8_t;
+typedef int16_t int_least16_t;
+typedef int32_t int_least32_t;
+typedef int64_t int_least64_t;
+typedef uint8_t uint_least8_t;
+typedef uint16_t uint_least16_t;
+typedef uint32_t uint_least32_t;
+typedef uint64_t uint_least64_t;
+
+typedef int8_t int_fast8_t;
+typedef int16_t int_fast16_t;
+typedef int32_t int_fast32_t;
+typedef int64_t int_fast64_t;
+typedef uint8_t uint_fast8_t;
+typedef uint16_t uint_fast16_t;
+typedef uint32_t uint_fast32_t;
+typedef uint64_t uint_fast64_t;
+
+typedef long intptr_t;
+typedef unsigned long uintptr_t;
+
+typedef long long intmax_t;
+typedef unsigned long long uintmax_t;
+
+#define SIZE_MAX ULONG_MAX
 
 #endif
+
similarity index 59%
copy from lib/monitor/arm64/include/psci.h
copy to secure_monitor/include/stdlib.h
index 3bb219b..fb1e1de 100644 (file)
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014, NVIDIA CORPORATION. All rights reserved
+ * Copyright (c) 2008 Travis Geiselbrecht
  *
  * Permission is hereby granted, free of charge, to any person obtaining
  * a copy of this software and associated documentation files
  * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
  * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
  */
-#ifndef __PSCI_H
-#define __PSCI_H
+#ifndef __STDLIB_H
+#define __STDLIB_H
 
-#define PSCI_FUNC_ID_VERSION           0x84000000
-#define PSCI_FUNC_ID_CPU_SUSPEND_LEGACY        0x84000001
-#define PSCI_FUNC_ID_CPU_SUSPEND       0xC4000001
-#define PSCI_FUNC_ID_CPU_OFF           0xC4000002
-#define PSCI_FUNC_ID_CPU_ON            0xC4000003
-#define PSCI_FUNC_ID_AFFINITY_INFO     0xC4000004
-#define PSCI_FUNC_ID_MIGRATE           0xC4000005
+#include <sys/types.h>
+#include <stddef.h>
+#include <malloc.h>
+#include <printf.h>
+#include <endian.h>
+#include <arch/defines.h>
 
-#define PSCI_RETURN_SUCCESS            (0)
-#define PSCI_RETURN_NOT_SUPPORTED      (-1)
-#define PSCI_RETURN_INVALID_PARAMS     (-2)
-#define PSCI_RETURN_DENIED             (-3)
-#define PSCI_RETURN_ALREADY_ON         (-4)
-#define PSCI_RETURN_ON_PENDING         (-5)
-#define PSCI_RETURN_INTERNAL_FAILURE   (-6)
-#define PSCI_RETURN_NOT_PRESENT                (-7)
-#define PSCI_RETURN_DISABLED           (-8)
+int atoi(const char *num);
+unsigned int atoui(const char *num);
+long atol(const char *num);
+unsigned long atoul(const char *num);
+
+#define MIN(a, b) (((a) < (b)) ? (a) : (b))
+#define MAX(a, b) (((a) > (b)) ? (a) : (b))
+
+#define ROUNDUP(a, b) (((a) + ((b)-1)) & ~((b)-1))
+#define ROUNDDOWN(a, b) ((a) & ~((b)-1))
+
+/* allocate a buffer on the stack aligned and padded to the cpu's cache line size */
+#define STACKBUF_DMA_ALIGN(var, size) \
+       uint8_t __##var[(size) + CACHE_LINE]; uint8_t *var = (uint8_t *)(ROUNDUP((addr_t)__##var, CACHE_LINE))
 
 #endif
+
diff --git a/secure_monitor/include/string.h b/secure_monitor/include/string.h
new file mode 100644 (file)
index 0000000..b95895b
--- /dev/null
@@ -0,0 +1,80 @@
+/*
+ * Copyright (c) 2008 Travis Geiselbrecht
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining
+ * a copy of this software and associated documentation files
+ * (the "Software"), to deal in the Software without restriction,
+ * including without limitation the rights to use, copy, modify, merge,
+ * publish, distribute, sublicense, and/or sell copies of the Software,
+ * and to permit persons to whom the Software is furnished to do so,
+ * subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
+ * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
+ * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
+ * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
+ * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ */
+#ifndef __LIB_STRING_H
+#define __LIB_STRING_H
+
+#include <stddef.h>
+#include <compiler.h>
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+void *memchr (void const *, int, size_t) __PURE;
+int   memcmp (void const *, const void *, size_t) __PURE;
+void *memcpy (void *, void const *, size_t);
+void *memmove(void *, void const *, size_t);
+void *memset (void *, int, size_t);
+
+char       *strcat(char *, char const *);
+char       *strchr(char const *, int) __PURE;
+int         strcmp(char const *, char const *) __PURE;
+char       *strcpy(char *, char const *);
+char const *strerror(int) __CONST;
+size_t      strlen(char const *) __PURE;
+char       *strncat(char *, char const *, size_t);
+int         strncmp(char const *, char const *, size_t) __PURE;
+char       *strncpy(char *, char const *, size_t);
+char       *strpbrk(char const *, char const *) __PURE;
+char       *strrchr(char const *, int) __PURE;
+size_t      strspn(char const *, char const *) __PURE;
+size_t      strcspn(const char *s, const char *) __PURE;
+char       *strstr(char const *, char const *) __PURE;
+char       *strtok(char *, char const *);
+int         strcoll(const char *s1, const char *s2) __PURE;
+size_t      strxfrm(char *dest, const char *src, size_t n) __PURE;
+char       *strdup(const char *str) __MALLOC;
+
+#ifdef __cplusplus
+} /* extern "C" */
+#endif
+
+#ifdef __cplusplus
+extern "C"
+{
+#endif
+
+/* non standard */
+void  *bcopy(void const *, void *, size_t);
+void   bzero(void *, size_t);
+size_t strlcat(char *, char const *, size_t);
+size_t strlcpy(char *, char const *, size_t);
+int    strncasecmp(char const *, char const *, size_t)  __PURE;
+int    strnicmp(char const *, char const *, size_t) __PURE;
+size_t strnlen(char const *s, size_t count) __PURE;
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif
diff --git a/secure_monitor/include/sys/types.h b/secure_monitor/include/sys/types.h
new file mode 100644 (file)
index 0000000..ae60b5c
--- /dev/null
@@ -0,0 +1,87 @@
+/*
+ * Copyright (c) 2008-2012 Travis Geiselbrecht
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining
+ * a copy of this software and associated documentation files
+ * (the "Software"), to deal in the Software without restriction,
+ * including without limitation the rights to use, copy, modify, merge,
+ * publish, distribute, sublicense, and/or sell copies of the Software,
+ * and to permit persons to whom the Software is furnished to do so,
+ * subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
+ * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
+ * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
+ * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
+ * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ */
+#ifndef __SYS_TYPES_H
+#define __SYS_TYPES_H
+
+#ifndef __cplusplus
+#define false 0
+#define true 1
+typedef int bool;
+#endif
+
+#include <stddef.h>
+#include <stdint.h>
+
+typedef unsigned char uchar;
+typedef unsigned short ushort;
+typedef unsigned int uint;
+typedef unsigned long ulong;
+typedef unsigned char u_char;
+typedef unsigned short u_short;
+typedef unsigned int u_int;
+typedef unsigned long u_long;
+
+typedef long long     off_t;
+
+typedef int status_t;
+
+typedef uintptr_t addr_t;
+typedef uintptr_t vaddr_t;
+typedef uint64_t nsaddr_t;
+
+#ifdef WITH_PADDR_T_64BIT
+typedef uint64_t paddr_t;
+#else
+typedef uintptr_t paddr_t;
+#endif
+
+typedef int kobj_id;
+
+#define USHRT_MAX      ((u16)(~0U))
+#define SHRT_MAX       ((s16)(USHRT_MAX>>1))
+#define SHRT_MIN       ((s16)(-SHRT_MAX - 1))
+#define INT_MAX                ((int)(~0U>>1))
+#define INT_MIN                (-INT_MAX - 1)
+#define UINT_MAX       (~0U)
+#define LONG_MAX       ((long)(~0UL>>1))
+#define LONG_MIN       (-LONG_MAX - 1)
+#define ULONG_MAX      (~0UL)
+#define LLONG_MAX      ((long long)(~0ULL>>1))
+#define LLONG_MIN      (-LLONG_MAX - 1)
+#define ULLONG_MAX     (~0ULL)
+#define INFINITE_TIME  ULONG_MAX
+typedef unsigned long lk_time_t;
+typedef unsigned long long lk_bigtime_t;
+
+#define TIME_GTE(a, b) ((long)((a) - (b)) >= 0)
+#define TIME_LTE(a, b) ((long)((a) - (b)) <= 0)
+#define TIME_GT(a, b) ((long)((a) - (b)) > 0)
+#define TIME_LT(a, b) ((long)((a) - (b)) < 0)
+#define ARRAY_SIZE(x) (sizeof(x)/sizeof((x)[0]))
+
+enum handler_return {
+       INT_NO_RESCHEDULE = 0,
+       INT_RESCHEDULE,
+};
+
+#endif
diff --git a/secure_monitor/lib/libc/string/arch/arm/rules.mk b/secure_monitor/lib/libc/string/arch/arm/rules.mk
new file mode 100644 (file)
index 0000000..0494205
--- /dev/null
@@ -0,0 +1,14 @@
+LOCAL_DIR := $(GET_LOCAL_DIR)
+
+ifeq ($(SUBARCH),arm)
+
+ASM_STRING_OPS := bcopy bzero memcpy memmove memset
+
+MODULE_SRCS += \
+       $(LOCAL_DIR)/memcpy.S \
+       $(LOCAL_DIR)/memset.S
+
+# filter out the C implementation
+C_STRING_OPS := $(filter-out $(ASM_STRING_OPS),$(C_STRING_OPS))
+endif
+
diff --git a/secure_monitor/lib/monitor/arm64/cache_helpers.S b/secure_monitor/lib/monitor/arm64/cache_helpers.S
new file mode 100644 (file)
index 0000000..ba1c2fc
--- /dev/null
@@ -0,0 +1,174 @@
+/*
+ * Copyright (c) 2013-2014, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2014, NVIDIA CORPORATION. All rights reserved
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are met:
+ *
+ * Redistributions of source code must retain the above copyright notice, this
+ * list of conditions and the following disclaimer.
+ *
+ * Redistributions in binary form must reproduce the above copyright notice,
+ * this list of conditions and the following disclaimer in the documentation
+ * and/or other materials provided with the distribution.
+ *
+ * Neither the name of ARM nor the names of its contributors may be used
+ * to endorse or promote products derived from this software without specific
+ * prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
+ * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
+ * POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include <asm.h>
+
+/* CLIDR definitions */
+#define LOUIS_SHIFT            21
+#define LOC_SHIFT              24
+#define CLIDR_FIELD_WIDTH      3
+
+/* CSSELR definitions */
+#define LEVEL_SHIFT            1
+
+.macro dcache_line_size  reg, tmp
+       mrs     \tmp, ctr_el0
+       ubfx    \tmp, \tmp, #16, #4
+       mov     \reg, #4
+       lsl     \reg, \reg, \tmp
+.endm
+
+       /* ------------------------------------------
+        * Clean+Invalidate from base address till
+        * size. 'x0' = addr, 'x1' = size
+        * ------------------------------------------
+        */
+FUNCTION(flush_dcache_range)
+       dcache_line_size x2, x3
+       add     x1, x0, x1
+       sub     x3, x2, #1
+       bic     x0, x0, x3
+flush_loop:
+       dc      civac, x0
+       add     x0, x0, x2
+       cmp     x0, x1
+       b.lo    flush_loop
+       dsb     sy
+       ret
+
+
+       /* ------------------------------------------
+        * Invalidate from base address till
+        * size. 'x0' = addr, 'x1' = size
+        * ------------------------------------------
+        */
+FUNCTION(inv_dcache_range)
+       dcache_line_size x2, x3
+       add     x1, x0, x1
+       sub     x3, x2, #1
+       bic     x0, x0, x3
+inv_loop:
+       dc      ivac, x0
+       add     x0, x0, x2
+       cmp     x0, x1
+       b.lo    inv_loop
+       dsb     sy
+       ret
+
+
+       /* ---------------------------------------------------------------
+        * Data cache operations by set/way to the level specified
+        *
+        * The main function, do_dcsw_op requires:
+        * x0: The operation type (0-2), as defined in arch.h
+        * x3: The last cache level to operate on
+        * x9: clidr_el1
+        * and will carry out the operation on each data cache from level 0
+        * to the level in x3 in sequence
+        *
+        * The dcsw_op macro sets up the x3 and x9 parameters based on
+        * clidr_el1 cache information before invoking the main function
+        * ---------------------------------------------------------------
+        */
+
+.macro dcsw_op shift, fw, ls
+       mrs     x9, clidr_el1
+       ubfx    x3, x9, \shift, \fw
+       lsl     x3, x3, \ls
+       b       do_dcsw_op
+.endm
+
+do_dcsw_op:
+       cbz     x3, exit
+       mov     x10, xzr
+       adr     x14, dcsw_loop_table    // compute inner loop address
+       add     x14, x14, x0, lsl #5    // inner loop is 8x32-bit instructions
+       mov     x0, x9
+       mov     w8, #1
+loop1:
+       add     x2, x10, x10, lsr #1    // work out 3x current cache level
+       lsr     x1, x0, x2              // extract cache type bits from clidr
+       and     x1, x1, #7              // mask the bits for current cache only
+       cmp     x1, #2                  // see what cache we have at this level
+       b.lt    level_done              // nothing to do if no cache or icache
+
+       msr     csselr_el1, x10         // select current cache level in csselr
+       isb                             // isb to sych the new cssr&csidr
+       mrs     x1, ccsidr_el1          // read the new ccsidr
+       and     x2, x1, #7              // extract the length of the cache lines
+       add     x2, x2, #4              // add 4 (line length offset)
+       ubfx    x4, x1, #3, #10         // maximum way number
+       clz     w5, w4                  // bit position of way size increment
+       lsl     w9, w4, w5              // w9 = aligned max way number
+       lsl     w16, w8, w5             // w16 = way number loop decrement
+       orr     w9, w10, w9             // w9 = combine way and cache number
+       ubfx    w6, w1, #13, #15        // w6 = max set number
+       lsl     w17, w8, w2             // w17 = set number loop decrement
+       dsb     sy                      // barrier before we start this level
+       br      x14                     // jump to DC operation specific loop
+
+level_done:
+       add     x10, x10, #2            // increment cache number
+       cmp     x3, x10
+       b.gt    loop1
+       msr     csselr_el1, xzr         // select cache level 0 in csselr
+       dsb     sy                      // barrier to complete final cache operation
+       isb
+exit:
+       ret
+
+.macro dcsw_loop _op
+loop2_\_op:
+       lsl     w7, w6, w2              // w7 = aligned max set number
+
+loop3_\_op:
+       orr     w11, w9, w7             // combine cache, way and set number
+       dc      \_op, x11
+       subs    w7, w7, w17             // decrement set number
+       b.ge    loop3_\_op
+
+       subs    x9, x9, x16             // decrement way number
+       b.ge    loop2_\_op
+
+       b       level_done
+.endm
+
+dcsw_loop_table:
+       dcsw_loop isw
+       dcsw_loop cisw
+       dcsw_loop csw
+
+FUNCTION(dcsw_op_louis)
+       dcsw_op #LOUIS_SHIFT, #CLIDR_FIELD_WIDTH, #LEVEL_SHIFT
+
+
+FUNCTION(dcsw_op_all)
+       dcsw_op #LOC_SHIFT, #CLIDR_FIELD_WIDTH, #LEVEL_SHIFT
similarity index 90%
rename from lib/monitor/arm64/include/arm64/asm.h
rename to secure_monitor/lib/monitor/arm64/include/arm64/asm.h
index e71bf31..c7968ef 100644 (file)
 #ifndef __ARCH_ARM64_ASM_H
 #define __ARCH_ARM64_ASM_H
 
+/* Cortex A57/A53 CPU IDs */
+#define CORTEX_A57_MP  0xd07
+#define CORTEX_A53_MP  0xd03
+
+/* SMP enable bit */
+#define CPUECTLR_SMP_BIT       (1 << 6)
+
+/* Double lock control bit */
+#define OSDLR_DBL_LOCK_BIT     1
+
 #define MODE_EL(x)     ((x) << 2)
 
 /* flag indicating in which mode CPU is returned */
@@ -34,6 +44,7 @@
 
 /* SCR_EL3 register fields/settings */
 #define MON_SCR_NS_MODE                (0x1 << 0)
+#define MON_SCR_EL3FIQ_EN      (0x1 << 2)
 #define MON_SCR_RESV1          (0x3 << 4)
 #define MON_SCR_32BIT          (0x0 << 10)
 #define MON_SCR_64BIT          (0x1 << 10)
similarity index 72%
rename from lib/monitor/arm64/include/psci.h
rename to secure_monitor/lib/monitor/arm64/include/psci.h
index 3bb219b..377111b 100644 (file)
 #ifndef __PSCI_H
 #define __PSCI_H
 
+#ifndef ASSEMBLY
+#include <sys/types.h>
+#endif
+
 #define PSCI_FUNC_ID_VERSION           0x84000000
 #define PSCI_FUNC_ID_CPU_SUSPEND_LEGACY        0x84000001
 #define PSCI_FUNC_ID_CPU_SUSPEND       0xC4000001
-#define PSCI_FUNC_ID_CPU_OFF           0xC4000002
+#define PSCI_FUNC_ID_CPU_OFF           0x84000002
 #define PSCI_FUNC_ID_CPU_ON            0xC4000003
 #define PSCI_FUNC_ID_AFFINITY_INFO     0xC4000004
 #define PSCI_FUNC_ID_MIGRATE           0xC4000005
 #define PSCI_RETURN_NOT_PRESENT                (-7)
 #define PSCI_RETURN_DISABLED           (-8)
 
+#define PSCI_POWER_STATE_TYPE_STANDBY          0
+#define PSCI_POWER_STATE_TYPE_POWER_DOWN       1
+
+#define PSCI_POWER_STATE_ID_MASK       0xffff
+#define PSCI_POWER_STATE_ID_SHIFT      0
+#define PSCI_POWER_STATE_TYPE_MASK     0x1
+#define PSCI_POWER_STATE_TYPE_SHIFT    16
+#define PSCI_POWER_STATE_AFFL_MASK     0x3
+#define PSCI_POWER_STATE_AFFL_SHIFT    24
+
+#ifndef ASSEMBLY
+void platform_psci_start(int cpu_id);
+int platform_psci_cpu_suspend(int cpu, uint32_t pwr_state);
+void platform_psci_cpu_resume(int cpu);
+void platform_psci_cpu_off(int cpu, uint32_t pwr_state);
+int platform_psci_cpu_on(int cpu);
+#endif
+
 #endif
diff --git a/secure_monitor/lib/monitor/arm64/monitor_cpu.S b/secure_monitor/lib/monitor/arm64/monitor_cpu.S
new file mode 100644 (file)
index 0000000..19c1e47
--- /dev/null
@@ -0,0 +1,352 @@
+/*
+ * Copyright (c) 2014, NVIDIA CORPORATION. All rights reserved
+ *
+ * Permission is hereby granted, free of charge, to any person obtaining
+ * a copy of this software and associated documentation files
+ * (the "Software"), to deal in the Software without restriction,
+ * including without limitation the rights to use, copy, modify, merge,
+ * publish, distribute, sublicense, and/or sell copies of the Software,
+ * and to permit persons to whom the Software is furnished to do so,
+ * subject to the following conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+ * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
+ * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
+ * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
+ * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
+ * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ */
+#include <config.h>
+#include <asm.h>
+#include <arch/arm.h>
+#include <arm64/asm.h>
+#include <psci.h>
+#include <arm64/monitor_macros.h>
+
+#define CORTEX_A53_MP_R0       0x410fd03
+#define DCCISW                 1
+
+/* called both for cold reset and boot_secondary */
+FUNCTION(mon_init_cpu)
+       mrs     x4, currentel
+       cmp     x4, #MODE_EL(3)
+       b.ne    .               // error, if not EL3
+
+       /* initialize SCR to secure state */
+       mov     x3, #(MON_SCR_RESV1 | MON_SCR_64BIT)
+       msr     scr_el3, x3
+       isb
+
+       /* set vbar (with phys, to catch setup errors) */
+       adr     x3, _vector_el3
+       msr     vbar_el3, x3
+
+       /* Check if ARM Cortex-A53 with revisions R0P0, R0P1, R0P2 */
+       mrs     x3, MIDR_EL1
+       lsr     x4, x3, #4
+       ldr     x12, =CORTEX_A53_MP_R0
+       cmp     x4, x12
+
+       b.ne    post_a53_erratum
+       and     x4, x3, #0xf
+       cmp     x4, #2
+       b.gt    post_a53_erratum
+
+       /*
+        * Cortex-A53 erratum 826319: disable evict and writeevict
+        * transactions
+        */
+       mrs     x3, s3_1_c15_c0_0
+       orr     x3, x3, #8              // disable clean/evict
+       mov     x4, #0x4000
+       bic     x3, x3, x4              // enable UniqueClean eviction
+       msr     s3_1_c15_c0_0, x3
+
+post_a53_erratum:
+#if !defined(MONTARGET_DENVER)
+       /* set SMPEN for A57/A53 */
+       mrs     x0, s3_1_c15_c2_1
+       orr     x0, x0, #CPUECTLR_SMP_BIT
+       msr     s3_1_c15_c2_1, x0
+#endif
+
+       /* enable I cache, disable MMU and alignment checks */
+       mrs     x4, sctlr_el3
+       bic     x4, x4, #(1 << 25)
+       orr     x4, x4, #(1 << 12)
+       bic     x4, x4, #((1 << 2) | (1 << 1) | (1 << 0))
+       msr     sctlr_el3, x4
+
+       /* set freq for arch general timer */
+       ldr     x0, =ARM_SYSTEM_COUNTER_FREQ
+       msr     cntfrq_el0, x0
+
+       /* allow non-privileged access to CNTVCT */
+       mrs     x0, cntkctl_el1
+       orr     x0, x0, #(1 << 1)
+       msr     cntkctl_el1, x0
+
+       /* enable the cycle count register */
+       mrs     x0, pmcr_el0
+       ubfx    x0, x0, #11, #5         // read PMCR.N field
+       mov     x4, #1
+       lsl     x0, x4, x0
+       sub     x0, x0, #1              // mask of event counters
+       orr     x0, x0, #0x80000000     // disable overflow intrs
+       msr     pmintenclr_el1, x0
+       msr     pmuserenr_el0, x4       // enable user mode access
+
+       /* mark per-CPU dist GROUP0 intrs non-secure */
+       ldr     x4, =ARM_GIC_DIST_BASE
+       mov     w3, #(~0)
+       str     w3, [x4, ARM_GIC_GICD_IGROUPR0]
+
+       /* enables GROUP0/GROUP1 intrs, signals GROUP0 with FIQ */
+       ldr     x4, =ARM_GIC_CPU_BASE
+       mov     w3, #((0xF << 5) | (0x1 << 3) | (0x3 << 0))
+       str     w3, [x4, ARM_GIC_GICC_CTLR]
+
+       /* init low pri mask, so NS can set its value */
+       mov     w3, #0xFF
+       str     w3, [x4, ARM_GIC_GICC_PMR]
+
+       /* disable copro traps to EL3 */
+       msr     cptr_el3, xzr
+
+       cpuidx  x12
+
+       /* setup per-cpu monitor stack (dividing up single 4K page) */
+       msr     spsel, #1
+       ldr     x3, =monitor_stack_top
+       lsl     x4, x12, #10    // each CPU gets a 1K stack
+       sub     x3, x3, x4
+       mov     sp, x3
+
+       ret
+
+/*
+ * Return to address saved in __mon_cpu_return_addr, in
+ * AARCH32 SVC (non-secure) mode.
+ */
+FUNCTION(mon_return_aarch32_ns)
+       /* load return address */
+       cpuidx  x1
+       adr     x2, __mon_cpu_return_addr
+       ldr     x2, [x2, x1, lsl #3]
+
+       msr     elr_el3, x2
+       mov     x2, #(MON_SCR_RESV1 | MON_SCR_32BIT | MON_SCR_NS_MODE)
+       msr     scr_el3, x2
+       mov     x2, #(MON_SPSR_EXC_MASKED | MODE_SVC)
+       msr     spsr_el3, x2
+
+       eret
+
+/*
+ * Return to address saved in __mon_cpu_return_addr, in
+ * AARCH64 EL2 (non-secure) mode.
+ */
+FUNCTION(mon_return_aarch64_ns)
+       /* load return address */
+       cpuidx  x1
+       adr     x2, __mon_cpu_return_addr
+       ldr     x2, [x2, x1, lsl #3]
+
+       msr     elr_el3, x2
+       mov     x2, #(MON_SCR_RESV1 | MON_SCR_64BIT | MON_SCR_NS_MODE)
+       orr     x2, x2, #MON_SCR_EL3FIQ_EN
+       msr     scr_el3, x2
+       mov     x2, #(MON_SPSR_EXC_MASKED | MODE_EL(2))
+       msr     spsr_el3, x2
+
+       eret
+
+/*
+ * Routine to setup secondary CPU state and return, leaving
+ * the primary CPU to initialize the secureos.
+ */
+FUNCTION(boot_secondary)
+       bl      mon_init_cpu
+       bl      mon_enable_mmu
+
+       /* reload vbar with virt addr */
+       adr     x0, _vector_el3
+       msr     vbar_el3, x0
+       isb
+
+       cpuidx  x0
+       bl      platform_psci_cpu_has_reset
+       b       mon_return_aarch64_ns
+
+/* get the CPU ID */
+FUNCTION(mon_get_cpu_id)
+       mrs     x0, midr_el1
+       ubfx    x0, x0, #4, #12
+       ret
+
+.ltorg
+.align 6
+.global __mon_cpu_reset_vector
+__mon_cpu_reset_vector:
+#if !defined(MONTARGET_DENVER)
+       /*
+        * code in this #if block are approved by HW and recommended
+        * by ARM. do NOT touch it.
+        */
+       mrs     x4, s3_1_c15_c2_0
+       orr     x4, x4, #1
+       msr     s3_1_c15_c2_0, x4      /* inv BTB when invalidating icache */
+       dsb     sy
+       isb
+       ic      iallu                  /* really invalidating icache & BTB */
+       dsb     sy
+       isb
+       bic     x4, x4, #1
+       msr     s3_1_c15_c2_0, x4      /* restore original cpuactlr_el1 */
+       dsb     sy
+       isb
+       .rept 7
+       nop                            /* wait */
+       .endr
+
+       mrs     x0, oslsr_el1
+       and     x0, x0, #2             /* extract oslk bit */
+       mrs     x1, mpidr_el1
+       bics    xzr, x0, x1, lsr #7    /* 0 if slow cluster or warm reset */
+       b.eq    __restore_oslock
+       mov     x0, xzr
+       msr     oslar_el1, x0          /* os lock stays off across warm reset */
+       mov     x3, #3
+       movz    x4, #0x8000, lsl #48
+       msr     s3_1_c15_c2_0, x4      /* turn off RCG */
+       isb
+       msr     rmr_el3, x3            /* request warm reset */
+       isb
+       dsb     sy
+       wfi
+       .rept 65
+       nop     /* these nops are here so that speculative execution */
+               /* won't do harm before we are done warm reset */
+               /* do not insert instructions here */
+       .endr
+__restore_oslock:
+       mov     x0, #1
+       msr     oslar_el1, x0
+#endif
+       b       boot_secondary
+
+.ltorg
+.align 3
+.global __mon_cpu_return_addr
+__mon_cpu_return_addr:
+       .rept MONCPUS
+       .quad 0
+       .endr
+
+.ltorg
+.align 3
+.global __mon_cpu_return_mode
+__mon_cpu_return_mode:
+       .rept MONCPUS
+       .quad 0
+       .endr
+
+/*
+ * CPU power down sequence as per A57/A53 TRM
+ *
+ * x0 - L2 flush?
+ *
+ */
+FUNCTION(mon_cpu_power_down)
+       /* Store L2 cache flush request */
+       mov     x13, x0
+
+       /* 1. Stop allocations to our data cache */
+       mrs     x0, sctlr_el1
+       bic     x0, x0, #1 << 2         // clear SCTLR.C
+       msr     sctlr_el1, x0
+       isb
+
+       mrs     x0, sctlr_el3
+       bic     x0, x0, #1 << 2         // clear SCTLR.C
+       msr     sctlr_el3, x0
+       isb
+
+       mrs     x0, midr_el1
+       ubfx    x0, x0, #4, #12
+       cmp     x0, #CORTEX_A57_MP
+       b.ne    not_a57
+
+       /* 2. Disable L2 prefetch */
+       mrs     x0, s3_1_c15_c2_1       // CPUECTLR_EL1
+       /* CPUECTLR[38], disable table walk descriptor access L2 prefetch */
+       orr     x0, x0, #1 << 38
+       /*
+        * CPUECTLR[36:35] L2 instruction fetch prefetch distance
+        * 0 => disable instruction prefetch
+        */
+       bic     x0, x0, #3 << 35
+       /*
+        * CPUECTLR[33:32] L2 load/store prefetch distance
+        * 0 => disable instruction prefetch
+        */
+       bic     x0, x0, #3 << 32
+       msr     s3_1_c15_c2_1, x0
+
+       /* 3. ISB to ensure ectlr write is complete */
+       isb
+
+       /* 4. DSB to ensure prior prefetches are complete */
+       dsb     sy
+
+not_a57:
+       /* 5. Clean and invalidate L1 and L2 if X13 == 1 */
+       mov     x0, #DCCISW
+       cmp     x13, #1
+       bne     1f
+       bl      dcsw_op_all
+       b       2f
+1:
+       bl      dcsw_op_louis
+2:
+
+       /* 6. Leave coherency, clear SMPEN */
+       mrs     x0, s3_1_c15_c2_1
+       bic     x0, x0, #CPUECTLR_SMP_BIT
+       msr     s3_1_c15_c2_1, x0
+
+       /* 7. Ensure that the system does not send interrupts to us */
+       ldr     x1, =ARM_GIC_CPU_BASE
+       mov     w0, #0x1E0
+       str     w0, [x1]
+
+       /* 8. Set the DBGOSDLR.DLK, Double lock control bit */
+       mrs     x0, osdlr_el1
+       orr     x0, x0, #OSDLR_DBL_LOCK_BIT
+       msr     osdlr_el1, x0
+
+       /*
+        * 9. Execute an ISB instruction to ensure that all of the
+        * System register changes from the previous steps have
+        * been committed.
+        */
+       isb
+
+       /*
+        * 10. Execute a DSB instruction to ensure that all
+        * instruction cache, TLB, and branch predictor
+        * maintenance operations issued by any processor in the
+        * multiprocessor before the SMPEN bit was cleared have
+        * completed.
+        */
+       dsb     sy
+
+       /* 11. wfi */
+3:     wfi
+
+       /* we never return here */
+       b       3b
similarity index 97%
rename from lib/monitor/arm64/monitor_fastcall.S
rename to secure_monitor/lib/monitor/arm64/monitor_fastcall.S
index f76221e..4934594 100644 (file)
@@ -44,9 +44,8 @@ FUNCTION(monitor_fastcall)
        mov     x6, #SMC_OWNER_TRUSTED_SERVICE
        csel    x10, x6, x10, ge
 
-       /* args for fastcall handler (frame, cpu) */
+       /* args for fastcall handler (frame) */
        mov     x0, sp
-       cpuidx  x1
 
        /* call fastcall handler */
        adr     x9, fastcall_table
similarity index 92%
rename from lib/monitor/arm64/monitor_lib.S
rename to secure_monitor/lib/monitor/arm64/monitor_lib.S
index ccc96ba..713f69c 100644 (file)
@@ -32,6 +32,15 @@ FUNCTION(mon_atomic_or)
        cbnz    w3, 1b
        ret
 
+/* void mon_atomic_and(uint32_t *ptr, uint32_t bits); */
+FUNCTION(mon_atomic_and)
+1:
+       ldxr    w2, [x0]
+       and     w2, w2, w1
+       stxr    w3, w2, [x0]
+       cbnz    w3, 1b
+       ret
+
 /* void *memset(void *s, int c, size_t n); */
 FUNCTION(memset)
        cbz     x0, done
similarity index 99%
rename from lib/monitor/arm64/monitor_mmu.S
rename to secure_monitor/lib/monitor/arm64/monitor_mmu.S
index 50b166a..fa8725c 100644 (file)
@@ -241,7 +241,8 @@ spin_wait:
 
        mrs     x1, sctlr_el3
        orr     x1, x1, #1
-       msr     sctlr_el3, x1           // enable MMU
+       orr     x1, x1, #(1 << 2)
+       msr     sctlr_el3, x1           // enable MMU and D cache
        isb
 
        ret
similarity index 81%
rename from lib/monitor/arm64/monitor_start.S
rename to secure_monitor/lib/monitor/arm64/monitor_start.S
index 4f02d20..7062cd0 100644 (file)
@@ -70,11 +70,11 @@ FUNCTION(_vector_el3)
        /* EL1 exception to EL3 (AArch64) */
        vec_entry       handle_exc_aarch64
        vec_entry_null                  /* IRQ exc aarch64  - unexpected in EL3 */
-       vec_entry_null                  /* FIQ exc aarch64  - unexpected in EL3 */
+       vec_entry       handle_fiq_aarch64      /* FIQ exc aarch64 */
        vec_entry_null                  /* SERR exc aarch64 - unexpected in EL3 */
 
 /*
- * Vector offset 0x600 - 0x580 (from Lower EL, using AArch32)
+ * Vector offset 0x600 - 0x680 (from Lower EL, using AArch32)
  */
 .align 9
        /* EL1 exception to EL3 (AArch32) */
@@ -97,44 +97,6 @@ FUNCTION(mon_clear_bss)
        ret
 
 /*
- * Set up initial registers and transition to EL1 to start the
- * secureos (no args are passed to this routine and it does not
- * return).
- */
-FUNCTION(mon_start_tlk_el1)
-        /*
-        * Save EL1 entry state before secureos init (which modifies
-        * the same EL1 arch state), so on return to the BL, it can
-        * be restored.
-        */
-       adr     x3, el1_non_secure_context
-       mon_save_el1_regs x3
-
-       /* entry into EL1 is at _end of monitor binary */
-       ldr     x6, __mon_phys_offset
-       adr     x4, _end
-       sub     x5, x4, x6      // phys addr of _end
-
-       /* adjust carveout (reduced by what monitor's used) */
-       adr     x3, __mon_phys_size
-       ldr     w0, [x3]
-       adr     x4, _start
-       sub     x7, x4, x6      // phys addr of _start
-       sub     x3, x5, x7      // amount used by monitor
-       sub     w0, w0, w3      // reduced size
-
-       /* size and bootarg passed as 32bit args */
-       adr     x3, __mon_bootarg_addr
-       ldr     w1, [x3]
-
-       mon_scr_secure_32 x3
-
-       mov     x3, #(MON_SPSR_EXC_MASKED | MODE_SVC)
-       msr     spsr_el3, x3
-       msr     elr_el3, x5
-       eret
-
-/*
  * Entry from the bootloader.
  *
  * Assuming for now the BL will jump to our _start rather than exception
@@ -196,7 +158,13 @@ _reset:
 
        cpuidx  x0
        bl      platform_psci_init
+
+#if defined(WITH_EL3_MONITOR_ONLY)
+       bl      platform_secure_dram_aperture
+       b       mon_return_aarch64_ns
+#else
        b       mon_start_tlk_el1
+#endif
 
 .ltorg
 .align 3
@@ -212,6 +180,7 @@ __mon_phys_base:
 __mon_phys_size:
        .quad 0
 
+.global __mon_bootarg_addr
 __mon_bootarg_addr:
        .quad 0
 
similarity index 51%
copy from lib/monitor/arm64/monitor_vector.S
copy to secure_monitor/lib/monitor/arm64/monitor_vector.S
index 3df92c7..01f8edc 100644 (file)
 #define        EC_SMC_AARCH32          0x13
 #define        EC_SMC_AARCH64          0x17
 
+#define FIQ_STATE_ELR_SPSR     0
+#define FIQ_STATE_SP_EL0_SP_EL1        16
+#define FIQ_STATE_PC_CPSR      32
+
 .macro mon_handle_aarch_switch, scr, scr2
        ldr     \scr, =SMC_SIP_AARCH_SWITCH
        cmp     \scr, x0
 1:
 .endm
 
+.macro mon_handle_get_fiq_regs, scr, scr2
+       ldr     \scr, =SMC_SIP_GET_FIQ_REGS
+       cmp     \scr, x0
+       b.ne    1f      // continue, not SMC_SIP_GET_FIQ_REGS
+
+       /* regs saved during a fiq exception */
+       adr     \scr, __fiq_state
+       ldp     x0, x1, [\scr, #FIQ_STATE_PC_CPSR]
+       ldp     x2, x3, [\scr, #FIQ_STATE_SP_EL0_SP_EL1]
+
+       /* switch non-secure for return */
+       mon_scr_non_secure_64 \scr
+
+       ldp     \scr, \scr2, [sp], #16  // restore scratch
+       eret
+1:
+.endm
+
 /*
  * Occurs from either non-secure/secure EL1.
  *
@@ -84,137 +106,48 @@ FUNCTION(handle_exc_aarch32)
        mon_handle_aarch_switch x9, x10
        b       .               // unrecognized aarch32 SMC
 
+.weak handle_trusted_os_call
 handle_trusted_os_call:
-       /* SMC expected from secureos in EL1(S) */
-       mrs     x9, scr_el3
-       tst     x9, #MON_SCR_NS_MODE
-       b.ne    .               // not in secure mode
-
-       and     x0, x0, #SMC_TOS_FUNC_ID_MASK
-       cmp     x0, #SMC_TOS_MAX_FUNC_IDX
-       b.gt    .               // too large an index
-
-       /* call function at tos_table[idx] */
-       adr     x9, tos_table
-       ldr     x10, [x9, x0, lsl #3]
-       br      x10
-
-tos_completion:
-       ldp     x9, x10, [sp], #16      // restore scratch
-
-       /* save secure EL1 state */
-       adr     x3, el1_secure_context
-       mon_save_el1_regs x3
-
-       /* restore NS EL1 state (loads spsr_el3/elr_el3) */
-       adr     x3, el1_non_secure_context
-       mon_restore_el1_regs x3
-
-       /* switch non-secure for return */
-       mon_scr_non_secure_64 x3
-
-       /* load SMC results into registers */
-       ldr     x3, el1_smc_args_results
-       ldp     x0, x1, [x3], #16
-       ldp     x2, x3, [x3], #16
-
-       eret
-
-tos_initial_ns_return:
-       ldp     x9, x10, [sp], #16      // restore scratch
-
-       /* save S EL1 state */
-       adr     x3, el1_secure_context
-       mon_save_el1_regs x3
-
-       /* restore NS EL1 state (from monitor entry point) */
-       adr     x3, el1_non_secure_context
-       mon_restore_el1_regs x3
-
-       bl      platform_psci_coldboot_epilog
-       b       mon_return_aarch64_ns
-
-tos_init_shared_addr:
-       ldp     x9, x10, [sp], #16      // restore scratch
-
-       /* save shared mem address (in x1) and return */
-       adr     x3, el1_smc_args_results
-       str     x1, [x3]
-
+fail:
+       mvn     x0, xzr         // return -1
        eret
 
 /*
- * This TOS call is serviced entirely within the monitor and returns
- * to secure EL1. If the virt->phys translation is for the normal world,
- * then make that MMU state current.
+ * FIQ exception handler for the monitor mode.
+ *
+ * We service the FIQ exceptions in the secure world and then jump to the NS
+ * world. The NS world has already registered its handler with us during
+ * boot. We store the necessary FIQ context before returning to the NS world
+ * handler. The saved FIQ context is requested by the NS world as a response to
+ * SMC_SIP_GET_FIQ_REGS function ID.
  */
-tos_addr_translation:
-       /* get virt address and type */
-       ldr     x9, el1_smc_args_results
-       ldp     x0, x1, [x9]
-
-       /* translate in current or non-secure world */
-       tst     x1, 0x4
-       b.eq    write_vreg      // current: no need to change state */
-
-       /* make non-secure MMU state current (corrupts x0, x1) */
-       adr     x3, el1_secure_context
-       mon_save_el1_mmu x3
-       adr     x3, el1_non_secure_context
-       mon_restore_el1_mmu x3
-
-       /* switch non-secure for translation */
-       mon_scr_non_secure_64 x3
-
-       /* reload args */
-       ldp     x0, x1, [x9]
-
-write_vreg:
-       mov     x10, x1
-       and     x10, x10, #3
-       adr     x2, v2p_table
-       add     x2, x2, x10, lsl #3     // each type is 2 instrs
-       br      x2
-
-v2p_table:
-       at      s12e1r, x0      // S12 priv read
-       b       read_par
-       at      s12e1w, x0      // S12 priv write
-       b       read_par
-       at      s12e0r, x0      // S12 user read
-       b       read_par
-       at      s12e0w, x0      // S12 user write
-
-read_par:
-       mrs     x0, par_el1
-       str     x0, [x9]        // return par in x0
-
-       /* translate in current or non-secure world */
-       tst     x1, 0x4
-       b.eq    do_return       // current: no need to restore state */
-
-       /* restore secure MMU state */
-       adr     x3, el1_secure_context
-       mon_restore_el1_mmu x3
-
-       /* go back to secure mode */
-       mon_scr_secure_32 x3
-
-do_return:
+FUNCTION(handle_fiq_aarch64)
+       stp     x9, x10, [sp, #-16]!    // create scratch
+       stp     x11, x12, [sp, #-16]!   // create scratch
+
+       adr     x11, __fiq_state
+       mrs     x9, elr_el1
+       mrs     x10, spsr_el1
+       stp     x9, x10, [x11, #FIQ_STATE_ELR_SPSR]
+       mrs     x9, sp_el0
+       mrs     x10, sp_el1
+       stp     x9, x10, [x11, #FIQ_STATE_SP_EL0_SP_EL1]
+       mrs     x9, elr_el3
+       mrs     x10, spsr_el3
+       stp     x9, x10, [x11, #FIQ_STATE_PC_CPSR]
+
+       adr     x9, __mon_cpu_fiq_glue
+       ldr     x9, [x9]
+       cbz     x9, .                   // NS world's handler not present
+       msr     elr_el3, x9
+       mov     x9, #(MON_SCR_RESV1 | MON_SCR_64BIT | MON_SCR_NS_MODE)
+       msr     scr_el3, x9
+
+       ldp     x11, x12, [sp], #16     // restore scratch
        ldp     x9, x10, [sp], #16      // restore scratch
        eret
 
 /*
- * Callbacks from secure->non-secure (not ready yet)
- */
-tos_callback:
-       b       .
-
-fail:
-       movn    x0, #0
-       eret
-
-/*
  * SMCs from 64bit non-secure world.
  *
  * This would be the path for PSCI calls and Trusted OS SMCs interfacing
@@ -255,6 +188,9 @@ secure_el1_smc64:
         * secure TAs (which call the secureos in EL1 for handling).
         */
 non_secure_el1_smc64:
+       /* service NS SIP call to get regs saved during FIQ excptn */
+       mon_handle_get_fiq_regs x9, x10
+
        /* service NS SIP call to switch aarch */
        mon_handle_aarch_switch x9, x10
 
@@ -262,66 +198,21 @@ non_secure_el1_smc64:
        tst     x0, #SMC_FASTCALL
        b.ne    monitor_fastcall
 
-non_secure_stdcall:
-       /* save incoming SMC args from registers */
-       ldr     x9, el1_smc_args_results
-       stp     x0, x1, [x9], #16
-       stp     x2, x3, [x9], #16
-       stp     x4, x5, [x9], #16
-       stp     x6, x7, [x9], #16
-
-       ldp     x9, x10, [sp], #16      // restore scratch
-
-       /*
-        * Some SMCs (besides PSCI) don't transition to the secureos.
-        * For instance, the registration of IRQ and FS callback handlers.
-        *
-        * It does mean we're not supporting this functionality at the
-        * moment, but the intent is to change the implementation, to not
-        * require returning to a different PC than where we were called.
-        */
-       ldr     w3, =0x32000004         // SMC_TOS_NS_IRQ_PENDING_VECTOR
-       cmp     w0, w3
-       b.ne    call_secureos
+       b non_secure_stdcall
 
-       mov     x0, #0
+.weak non_secure_stdcall
+non_secure_stdcall:
+       mvn     x0, xzr         // return -1
        eret
 
-call_secureos:
-       /* save NS EL1 state */
-       adr     x3, el1_non_secure_context
-       mon_save_el1_regs x3
-
-       /* restore S EL1 state (including spsr_el3/elr_el3) */
-       adr     x3, el1_secure_context
-       mon_restore_el1_regs x3
+.align 3
+.global __mon_cpu_fiq_glue
+__mon_cpu_fiq_glue:
+       .quad 0
 
-       /* set scr to secure32 */
-       mon_scr_secure_32 x3
-       eret
+.global __mon_cpu_fiq_ns_stack
+__mon_cpu_fiq_ns_stack:
+       .quad 0
 
-.align 3
-el1_secure_context:
-       .rept   NUM_CTX_REGS
-       .quad   0
-       .endr
-
-.global el1_non_secure_context
-el1_non_secure_context:
-       .rept   NUM_CTX_REGS
-       .quad   0
-       .endr
-
-/* SMCs issued from the Trusted OS */
-tos_table:
-       .quad   -1
-       .quad   tos_completion
-       .quad   tos_callback            /* IRQ */
-       .quad   tos_callback            /* filesystem */
-       .quad   tos_initial_ns_return
-       .quad   tos_addr_translation
-       .quad   tos_init_shared_addr
-
-/* address of shared mem for passing SMC args/results */
-el1_smc_args_results:
-       .quad   0
+__fiq_state:
+       .quad 0, 0, 0, 0, 0, 0
similarity index 64%
rename from lib/monitor/arm64/monitor_vector.S
rename to secure_monitor/lib/monitor/arm64/secure_callback.S
index 3df92c7..e9ea5b5 100644 (file)
  * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
  * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
  */
+#include <config.h>
 #include <asm.h>
+#include <arch/arm.h>
 #include <arm64/asm.h>
 #include <arm64/monitor_macros.h>
 #include <lib/monitor/monitor_vector.h>
 
-#define EC_BIT_POS             26
-#define EC_WIDTH               6
-
-#define        EC_SMC_AARCH32          0x13
-#define        EC_SMC_AARCH64          0x17
-
-.macro mon_handle_aarch_switch, scr, scr2
-       ldr     \scr, =SMC_SIP_AARCH_SWITCH
-       cmp     \scr, x0
-       b.ne    1f      // continue, not SMC_SIP_AARCH_SWITCH
-
-       /* save address/mode and use during return */
-       cpuidx  \scr
-       adr     \scr2, __mon_cpu_return_addr
-       str     x1, [\scr2, \scr, lsl #3]
-       adr     \scr2, __mon_cpu_return_mode
-       str     x2, [\scr2, \scr, lsl #3]
-
-       ldp     \scr, \scr2, [sp], #16  // restore scratch
-       mov     x0, xzr                 // return success
-
-       cbz     x2, mon_return_aarch64_ns
-       b       mon_return_aarch32_ns
-1:
-.endm
-
 /*
- * Occurs from either non-secure/secure EL1.
- *
- * If coming from the non-secure world, we may have to save more state
- * depending on if we're going to transition to EL1 in secure mode. This
- * is needed if passing along a standard call SMC, which launches a
- * separate thread.
- *
- * If coming from S-EL1, detectable by NS=0 already, then just need to
- * save the GP regs (all the other NS-EL1 state has been saved already).
- *
- * Args are passed in x0-x6 and x18-x30 are callee saved.
+ * Set up initial registers and transition to EL1 to start the
+ * secureos (no args are passed to this routine and it does not
+ * return).
  */
-FUNCTION(handle_exc_aarch32)
-       stp     x9, x10, [sp, #-16]!    // create scratch
+FUNCTION(mon_start_tlk_el1)
+        /*
+        * Save EL1 entry state before secureos init (which modifies
+        * the same EL1 arch state), so on return to the BL, it can
+        * be restored.
+        */
+       adr     x3, el1_non_secure_context
+       mon_save_el1_regs x3
 
-       /* get exception code */
-       mrs     x9, esr_el3
-       ubfx    x9, x9, #EC_BIT_POS, #EC_WIDTH
+       /* entry into EL1 is at _end of monitor binary */
+       ldr     x6, __mon_phys_offset
+       adr     x4, _end
+       sub     x5, x4, x6      // phys addr of _end
 
-       cmp     x9, #EC_SMC_AARCH32
-       b.ne    .               // fail
+       /* adjust carveout (reduced by what monitor's used) */
+       adr     x3, __mon_phys_size
+       ldr     w0, [x3]
+       adr     x4, _start
+       sub     x7, x4, x6      // phys addr of _start
+       sub     x3, x5, x7      // amount used by monitor
+       sub     w0, w0, w3      // reduced size
 
-       /* check for 32bit Trusted OS (TOS) calls */
-       and     x9, x0, #(SMC_OWNER_MASK << SMC_OWNER_SHIFT)
-       ldr     x10, =SMC_TOS_CALL
-       cmp     x9, x10
-       b.eq    handle_trusted_os_call
+       /* size and bootarg passed as 32bit args */
+       adr     x3, __mon_bootarg_addr
+       ldr     w1, [x3]
 
-       /* service NS SIP call to switch aarch */
-       mon_handle_aarch_switch x9, x10
-       b       .               // unrecognized aarch32 SMC
+       mon_scr_secure_32 x3
+
+       mov     x3, #(MON_SPSR_EXC_MASKED | MODE_SVC)
+       msr     spsr_el3, x3
+       msr     elr_el3, x5
+       eret
 
+.global handle_trusted_os_call
 handle_trusted_os_call:
        /* SMC expected from secureos in EL1(S) */
        mrs     x9, scr_el3
@@ -120,6 +102,7 @@ tos_completion:
 
        eret
 
+// Is this the first SMC we receive (from the bootloader) on boot?
 tos_initial_ns_return:
        ldp     x9, x10, [sp], #16      // restore scratch
 
@@ -210,58 +193,7 @@ do_return:
 tos_callback:
        b       .
 
-fail:
-       movn    x0, #0
-       eret
-
-/*
- * SMCs from 64bit non-secure world.
- *
- * This would be the path for PSCI calls and Trusted OS SMCs interfacing
- * with secure TAs. For PSCI, they'd be serviced here, but Trusted OS
- * SMCs need to transition to the secureos in EL1.
- */
-FUNCTION(handle_exc_aarch64)
-       stp     x9, x10, [sp, #-16]!    // create scratch
-
-       /* get exception code */
-       mrs     x9, esr_el3
-       ubfx    x10, x9, #EC_BIT_POS, #EC_WIDTH
-
-       cmp     x10, #EC_SMC_AARCH64
-       b.ne    .                       // fail
-
-       /* for now, only expect non-secure EL1 */
-       mrs     x9, scr_el3
-       tst     x9, #1
-       b.eq    secure_el1_smc64        // fail
-       b       non_secure_el1_smc64
-
-       /*
-        * SMCs from 64bit secure world.
-        * Currently these are unexpected as secureos runs in a 32bit mode.
-        */
-secure_el1_smc64:
-       b       .
-       ldp     x9, x10, [sp], #16      // restore scratch
-       movn    x0, #0
-       eret
-
-       /*
-        * SMCs from 64bit non-secure world.
-        *
-        * This is the path for both monitor fastcalls (i.e. those serviced
-        * entirely within the monitor) and Trusted OS SMCs interfacing with
-        * secure TAs (which call the secureos in EL1 for handling).
-        */
-non_secure_el1_smc64:
-       /* service NS SIP call to switch aarch */
-       mon_handle_aarch_switch x9, x10
-
-       /* handle fastcall SMCs */
-       tst     x0, #SMC_FASTCALL
-       b.ne    monitor_fastcall
-
+.global non_secure_stdcall
 non_secure_stdcall:
        /* save incoming SMC args from registers */
        ldr     x9, el1_smc_args_results
@@ -284,9 +216,7 @@ non_secure_stdcall:
        cmp     w0, w3
        b.ne    call_secureos
 
-       mov     x0, #0
-       eret
-
+.global call_secureos
 call_secureos:
        /* save NS EL1 state */
        adr     x3, el1_non_secure_context
@@ -306,7 +236,7 @@ el1_secure_context:
        .quad   0
        .endr
 
-.global el1_non_secure_context
+;.global el1_non_secure_context // Not needed anymore?
 el1_non_secure_context:
        .rept   NUM_CTX_REGS
        .quad   0
@@ -316,8 +246,8 @@ el1_non_secure_context:
 tos_table:
        .quad   -1
        .quad   tos_completion
-       .quad   tos_callback            /* IRQ */
-       .quad   tos_callback            /* filesystem */
+       .quad   tos_completion          /* IRQ */
+       .quad   tos_completion          /* filesystem */
        .quad   tos_initial_ns_return
        .quad   tos_addr_translation
        .quad   tos_init_shared_addr
similarity index 77%
rename from lib/monitor/rules.mk
rename to secure_monitor/lib/monitor/rules.mk
index 2e2aa45..8be2af3 100644 (file)
@@ -2,7 +2,7 @@
 # This builds either into a library that's linked with the TLK kernel
 # (when MONITOR_MODULE = false, in the case of MODULE_ARCH = arm).
 #
-# Or, generates a separate mon.bin binary with its own address space
+# Or, generates a separate monitor.bin binary with its own address space
 # (when MONITOR_MODULE = true, in the case of MODULE_ARCH = arm64).
 #
 LOCAL_DIR := $(GET_LOCAL_DIR)
@@ -31,29 +31,34 @@ MODULE_SRCS += \
        $(LOCAL_DIR)/arm64/monitor_cpu.S \
        $(LOCAL_DIR)/arm64/monitor_fastcall.S \
        $(LOCAL_DIR)/arm64/monitor_lib.S \
-       $(LOCAL_DIR)/arm64/monitor_mmu.S
+       $(LOCAL_DIR)/arm64/monitor_mmu.S \
+       $(LOCAL_DIR)/arm64/cache_helpers.S
 
 MODULE_CC := $(TOOLCHAIN_PREFIX64)gcc
 MODULE_LD := $(TOOLCHAIN_PREFIX64)ld
 MON_OBJCOPY := $(TOOLCHAIN_PREFIX64)objcopy
-endif
+#
+# If we're building a secure build include the secure world callbacks
+ifeq ($(STANDALONE_MONITOR),false)
+MODULE_SRCS += \
+       $(LOCAL_DIR)/arm64/secure_callback.S
+endif # STANDALONE_MONITOR == false
+endif # MONARCH == arm64
 
-# generating separate $(MONARCH) mon.bin
+# generating separate $(MONARCH) monitor.bin
 ifeq ($(MONITOR_BIN),true)
 DEFINES += \
        WITH_MONITOR_BIN=1 \
        MONBITS=$(MONBITS) \
        MONBASE=$(MONBASE) \
-       MONCPUS=$(MONCPUS)
+       MONCPUS=$(MONCPUS) \
+       MONTARGET_$(MONTARGET)=1
 
 MONITOR_MODULE := true
 MON_LD := $(MODULE_LD)
 MON_LINKER_SCRIPT += \
         $(BUILDDIR)/monitor-onesegment.ld
 
-MONELF := $(BUILDDIR)/mon.elf
-MONBIN := $(BUILDDIR)/mon.bin
-
 ifeq ($(MONBASE),)
 $(error missing MONBASE variable, please set in target rules.mk)
 endif
diff --git a/secure_monitor/make/build.mk b/secure_monitor/make/build.mk
new file mode 100644 (file)
index 0000000..f26a8ff
--- /dev/null
@@ -0,0 +1,20 @@
+# comment out or override if you want to see the full output of each command
+NOECHO ?= @
+
+$(MONBIN): $(MONELF)
+       @echo generating image: $@
+       $(NOECHO)$(MON_OBJCOPY) -O binary $< $@
+
+# This target builds the barebones tos.img from monitor.bin
+$(TOSIMAGE): $(MONBIN)
+       @echo generating image: $@
+       tools/gen_tos_part_img.py $< $@
+
+$(MONELF): $(ALLMONITOR_OBJS) $(MON_LINKER_SCRIPT)
+       @echo linking $@
+       $(NOECHO)$(MON_LD) $(GLOBAL_LDFLAGS) -T $(MON_LINKER_SCRIPT) $(ALLMONITOR_OBJS) $(LIBGCC) -o $@
+
+# This builds a static library from platform/monitor for ote/tlk to link in
+$(MONLIB): $(ALLMODULE_OBJS)
+       @echo building platform monitor static library $@
+       $(AR) $(GLOBAL_ARFLAGS) $@ $<
diff --git a/secure_monitor/make/compile.mk b/secure_monitor/make/compile.mk
new file mode 100644 (file)
index 0000000..a1198d0
--- /dev/null
@@ -0,0 +1,79 @@
+# create a separate list of objects per source type
+MODULE_CSRCS := $(filter %.c,$(MODULE_SRCS))
+MODULE_CPPSRCS := $(filter %.cpp,$(MODULE_SRCS))
+MODULE_ASMSRCS := $(filter %.S,$(MODULE_SRCS))
+
+MODULE_COBJS := $(call TOBUILDDIR,$(patsubst %.c,%.o,$(MODULE_CSRCS)))
+MODULE_CPPOBJS := $(call TOBUILDDIR,$(patsubst %.cpp,%.o,$(MODULE_CPPSRCS)))
+MODULE_ASMOBJS := $(call TOBUILDDIR,$(patsubst %.S,%.o,$(MODULE_ASMSRCS)))
+
+# do the same thing for files specified in arm override mode
+MODULE_ARM_CSRCS := $(filter %.c,$(MODULE_ARM_OVERRIDE_SRCS))
+MODULE_ARM_CPPSRCS := $(filter %.cpp,$(MODULE_ARM_OVERRIDE_SRCS))
+MODULE_ARM_ASMSRCS := $(filter %.S,$(MODULE_ARM_OVERRIDE_SRCS))
+
+MODULE_ARM_COBJS := $(call TOBUILDDIR,$(patsubst %.c,%.o,$(MODULE_ARM_CSRCS)))
+MODULE_ARM_CPPOBJS := $(call TOBUILDDIR,$(patsubst %.cpp,%.o,$(MODULE_ARM_CPPSRCS)))
+MODULE_ARM_ASMOBJS := $(call TOBUILDDIR,$(patsubst %.S,%.o,$(MODULE_ARM_ASMSRCS)))
+
+MODULE_OBJS := $(MODULE_COBJS) $(MODULE_CPPOBJS) $(MODULE_ASMOBJS) $(MODULE_ARM_COBJS) $(MODULE_ARM_CPPOBJS) $(MODULE_ARM_ASMOBJS)
+
+#$(info MODULE_SRCS = $(MODULE_SRCS))
+#$(info MODULE_CSRCS = $(MODULE_CSRCS))
+#$(info MODULE_CPPSRCS = $(MODULE_CPPSRCS))
+#$(info MODULE_ASMSRCS = $(MODULE_ASMSRCS))
+
+#$(info MODULE_OBJS = $(MODULE_OBJS))
+#$(info MODULE_COBJS = $(MODULE_COBJS))
+#$(info MODULE_CPPOBJS = $(MODULE_CPPOBJS))
+#$(info MODULE_ASMOBJS = $(MODULE_ASMOBJS))
+
+$(MODULE_OBJS): MODULE_CC:=$(MODULE_CC)
+$(MODULE_OBJS): MODULE_OPTFLAGS:=$(MODULE_OPTFLAGS)
+$(MODULE_OBJS): MODULE_COMPILEFLAGS:=$(MODULE_COMPILEFLAGS)
+$(MODULE_OBJS): MODULE_CFLAGS:=$(MODULE_CFLAGS)
+$(MODULE_OBJS): MODULE_CPPFLAGS:=$(MODULE_CPPFLAGS)
+$(MODULE_OBJS): MODULE_ASMFLAGS:=$(MODULE_ASMFLAGS)
+$(MODULE_OBJS): MODULE_SRCDEPS:=$(MODULE_SRCDEPS)
+$(MODULE_OBJS): SRCDEPS:=$(SRCDEPS)
+
+$(MODULE_OBJS): $(MODULE_SRCDEPS) $(SRCDEPS)
+
+$(MODULE_COBJS): $(BUILDDIR)/%.o: %.c $(SRCDEPS)
+       @$(MKDIR)
+       @echo compiling $<
+       $(NOECHO)$(MODULE_CC) $(GLOBAL_OPTFLAGS) $(MODULE_OPTFLAGS) $(GLOBAL_COMPILEFLAGS) $(MODULE_COMPILEFLAGS) $(GLOBAL_CFLAGS) $(MODULE_CFLAGS) $(THUMBCFLAGS) $(INCLUDES) $(MODULE_INCLUDES) -c $< -MD -MT $@ -MF $(@:%o=%d) -o $@
+
+$(MODULE_CPPOBJS): $(BUILDDIR)/%.o: %.cpp $(SRCDEPS)
+       @$(MKDIR)
+       @echo compiling $<
+       $(NOECHO)$(MODULE_CC) $(GLOBAL_OPTFLAGS) $(MODULE_OPTFLAGS) $(GLOBAL_COMPILEFLAGS) $(MODULE_COMPILEFLAGS) $(GLOBAL_CPPFLAGS) $(MODULE_CPPFLAGS) $(THUMBCFLAGS) $(INCLUDES) $(MODULE_INCLUDES) -c $< -MD -MT $@ -MF $(@:%o=%d) -o $@
+
+$(MODULE_ASMOBJS): $(BUILDDIR)/%.o: %.S $(SRCDEPS)
+       @$(MKDIR)
+       @echo compiling $<
+       $(NOECHO)$(MODULE_CC) $(GLOBAL_OPTFLAGS) $(MODULE_OPTFLAGS) $(GLOBAL_COMPILEFLAGS) $(MODULE_COMPILEFLAGS) $(GLOBAL_ASMFLAGS) $(MODULE_ASMFLAGS) $(THUMBCFLAGS) $(INCLUDES) $(MODULE_INCLUDES) -c $< -MD -MT $@ -MF $(@:%o=%d) -o $@
+
+# overridden arm versions
+$(MODULE_ARM_COBJS): $(BUILDDIR)/%.o: %.c $(SRCDEPS)
+       @$(MKDIR)
+       @echo compiling $<
+       $(NOECHO)$(MODULE_CC) $(GLOBAL_OPTFLAGS) $(MODULE_OPTFLAGS) $(GLOBAL_COMPILEFLAGS) $(MODULE_COMPILEFLAGS) $(GLOBAL_CFLAGS) $(MODULE_CFLAGS) $(INCLUDES) $(MODULE_INCLUDES) -c $< -MD -MT $@ -MF $(@:%o=%d) -o $@
+
+$(MODULE_ARM_CPPOBJS): $(BUILDDIR)/%.o: %.cpp $(SRCDEPS)
+       @$(MKDIR)
+       @echo compiling $<
+       $(NOECHO)$(MODULE_CC) $(GLOBAL_OPTFLAGS) $(MODULE_OPTFLAGS) $(GLOBAL_COMPILEFLAGS) $(MODULE_COMPILEFLAGS) $(GLOBAL_CPPFLAGS) $(MODULE_CPPFLAGS) $(INCLUDES) $(MODULE_INCLUDES) -c $< -MD -MT $@ -MF $(@:%o=%d) -o $@
+
+$(MODULE_ARM_ASMOBJS): $(BUILDDIR)/%.o: %.S $(SRCDEPS)
+       @$(MKDIR)
+       @echo compiling $<
+       $(NOECHO)$(MODULE_CC) $(GLOBAL_OPTFLAGS) $(MODULE_OPTFLAGS) $(GLOBAL_COMPILEFLAGS) $(MODULE_COMPILEFLAGS) $(GLOBAL_ASMFLAGS) $(MODULE_ASMFLAGS) $(INCLUDES) $(MODULE_INCLUDES) -c $< -MD -MT $@ -MF $(@:%o=%d) -o $@
+
+# clear some variables we set here
+MODULE_CSRCS :=
+MODULE_CPPSRCS :=
+MODULE_ASMSRCS :=
+MODULE_COBJS :=
+MODULE_CPPOBJS :=
+MODULE_ASMOBJS :=
diff --git a/secure_monitor/make/macros.mk b/secure_monitor/make/macros.mk
new file mode 100644 (file)
index 0000000..e23715e
--- /dev/null
@@ -0,0 +1,35 @@
+# Find the local dir of the make file
+GET_LOCAL_DIR    = $(patsubst %/,%,$(dir $(word $(words $(MAKEFILE_LIST)),$(MAKEFILE_LIST))))
+
+# makes sure the target dir exists
+MKDIR = if [ ! -d $(dir $@) ]; then mkdir -p $(dir $@); fi
+
+# prepends the BUILD_DIR var to each item in the list
+TOBUILDDIR = $(addprefix $(BUILDDIR)/,$(1))
+
+COMMA := ,
+SPACE :=
+SPACE +=
+
+# generate a header file at $1 with an expanded variable in $2
+define MAKECONFIGHEADER
+       @$(MKDIR)
+       @echo generating $1
+       @rm -f $1.tmp; \
+       LDEF=`echo $1 | tr '/\\.-' '_'`; \
+       echo \#ifndef __$${LDEF}_H > $1.tmp; \
+       echo \#define __$${LDEF}_H >> $1.tmp; \
+       for d in `echo $($2) | tr '[:lower:]' '[:upper:]'`; do \
+               echo "#define $$d" | sed "s/=/\ /g;s/-/_/g;s/\//_/g" >> $1.tmp; \
+       done; \
+       echo \#endif >> $1.tmp; \
+       if [ -f "$1" ]; then \
+               if cmp "$1.tmp" "$1"; then \
+                       rm -f $1.tmp; \
+               else \