Merge pull request #643 from sandrine-bailleux-arm/sb/checkpatch-conf-file

Move checkpatch options in a configuration file
diff --git a/Makefile b/Makefile
index 74bbe42..ab9b1ad 100644
--- a/Makefile
+++ b/Makefile
@@ -62,6 +62,9 @@
 RESET_TO_BL31			:= 0
 # Include FP registers in cpu context
 CTX_INCLUDE_FPREGS		:= 0
+# Build flag to include AArch32 registers in cpu context save and restore
+# during world switch. This flag must be set to 0 for AArch64-only platforms.
+CTX_INCLUDE_AARCH32_REGS	:= 1
 # Determine the version of ARM GIC architecture to use for interrupt management
 # in EL3. The platform port can change this value if needed.
 ARM_GIC_ARCH			:= 2
@@ -392,6 +395,7 @@
 $(eval $(call assert_boolean,NS_TIMER_SWITCH))
 $(eval $(call assert_boolean,RESET_TO_BL31))
 $(eval $(call assert_boolean,CTX_INCLUDE_FPREGS))
+$(eval $(call assert_boolean,CTX_INCLUDE_AARCH32_REGS))
 $(eval $(call assert_boolean,ASM_ASSERTION))
 $(eval $(call assert_boolean,USE_COHERENT_MEM))
 $(eval $(call assert_boolean,DISABLE_PEDANTIC))
@@ -419,6 +423,7 @@
 $(eval $(call add_define,NS_TIMER_SWITCH))
 $(eval $(call add_define,RESET_TO_BL31))
 $(eval $(call add_define,CTX_INCLUDE_FPREGS))
+$(eval $(call add_define,CTX_INCLUDE_AARCH32_REGS))
 $(eval $(call add_define,ARM_GIC_ARCH))
 $(eval $(call add_define,ARM_CCI_PRODUCT_ID))
 $(eval $(call add_define,ASM_ASSERTION))
diff --git a/bl1/bl1_context_mgmt.c b/bl1/bl1_context_mgmt.c
index bd40608..972c7f6 100644
--- a/bl1/bl1_context_mgmt.c
+++ b/bl1/bl1_context_mgmt.c
@@ -32,6 +32,7 @@
 #include <assert.h>
 #include <context.h>
 #include <context_mgmt.h>
+#include <debug.h>
 #include <platform.h>
 
 /*
@@ -66,6 +67,19 @@
 	image_desc_t *image_desc;
 	entry_point_info_t *next_bl_ep;
 
+#if CTX_INCLUDE_AARCH32_REGS
+	/*
+	 * Ensure that the build flag to save AArch32 system registers in CPU
+	 * context is not set for AArch64-only platforms.
+	 */
+	if (((read_id_aa64pfr0_el1() >> ID_AA64PFR0_EL1_SHIFT)
+			& ID_AA64PFR0_ELX_MASK) == 0x1) {
+		ERROR("EL1 supports AArch64-only. Please set build flag "
+				"CTX_INCLUDE_AARCH32_REGS = 0");
+		panic();
+	}
+#endif
+
 	/* Get the image descriptor. */
 	image_desc = bl1_plat_get_image_desc(image_id);
 	assert(image_desc);
diff --git a/bl31/bl31_main.c b/bl31/bl31_main.c
index 835d41e..7f04d21 100644
--- a/bl31/bl31_main.c
+++ b/bl31/bl31_main.c
@@ -145,6 +145,19 @@
 	entry_point_info_t *next_image_info;
 	uint32_t image_type;
 
+#if CTX_INCLUDE_AARCH32_REGS
+	/*
+	 * Ensure that the build flag to save AArch32 system registers in CPU
+	 * context is not set for AArch64-only platforms.
+	 */
+	if (((read_id_aa64pfr0_el1() >> ID_AA64PFR0_EL1_SHIFT)
+			& ID_AA64PFR0_ELX_MASK) == 0x1) {
+		ERROR("EL1 supports AArch64-only. Please set build flag "
+				"CTX_INCLUDE_AARCH32_REGS = 0");
+		panic();
+	}
+#endif
+
 	/* Determine which image to execute next */
 	image_type = bl31_get_next_image_type();
 
diff --git a/common/aarch64/context.S b/common/aarch64/context.S
index 0baa9b2..d51daa7 100644
--- a/common/aarch64/context.S
+++ b/common/aarch64/context.S
@@ -57,14 +57,6 @@
 	mrs	x10, elr_el1
 	stp	x9, x10, [x0, #CTX_SPSR_EL1]
 
-	mrs	x11, spsr_abt
-	mrs	x12, spsr_und
-	stp	x11, x12, [x0, #CTX_SPSR_ABT]
-
-	mrs	x13, spsr_irq
-	mrs	x14, spsr_fiq
-	stp	x13, x14, [x0, #CTX_SPSR_IRQ]
-
 	mrs	x15, sctlr_el1
 	mrs	x16, actlr_el1
 	stp	x15, x16, [x0, #CTX_SCTLR_EL1]
@@ -93,10 +85,6 @@
 	mrs	x10, tpidrro_el0
 	stp	x9, x10, [x0, #CTX_TPIDR_EL0]
 
-	mrs	x11, dacr32_el2
-	mrs	x12, ifsr32_el2
-	stp	x11, x12, [x0, #CTX_DACR32_EL2]
-
 	mrs	x13, par_el1
 	mrs	x14, far_el1
 	stp	x13, x14, [x0, #CTX_PAR_EL1]
@@ -109,6 +97,24 @@
 	mrs	x9, vbar_el1
 	stp	x17, x9, [x0, #CTX_CONTEXTIDR_EL1]
 
+	/* Save AArch32 system registers if the build has instructed so */
+#if CTX_INCLUDE_AARCH32_REGS
+	mrs	x11, spsr_abt
+	mrs	x12, spsr_und
+	stp	x11, x12, [x0, #CTX_SPSR_ABT]
+
+	mrs	x13, spsr_irq
+	mrs	x14, spsr_fiq
+	stp	x13, x14, [x0, #CTX_SPSR_IRQ]
+
+	mrs	x15, dacr32_el2
+	mrs	x16, ifsr32_el2
+	stp	x15, x16, [x0, #CTX_DACR32_EL2]
+
+	mrs	x17, fpexc32_el2
+	str	x17, [x0, #CTX_FP_FPEXC32_EL2]
+#endif
+
 	/* Save NS timer registers if the build has instructed so */
 #if NS_TIMER_SWITCH
 	mrs	x10, cntp_ctl_el0
@@ -123,9 +129,6 @@
 	str	x14, [x0, #CTX_CNTKCTL_EL1]
 #endif
 
-	mrs	x15, fpexc32_el2
-	str	x15, [x0, #CTX_FP_FPEXC32_EL2]
-
 	ret
 endfunc el1_sysregs_context_save
 
@@ -143,14 +146,6 @@
 	msr	spsr_el1, x9
 	msr	elr_el1, x10
 
-	ldp	x11, x12, [x0, #CTX_SPSR_ABT]
-	msr	spsr_abt, x11
-	msr	spsr_und, x12
-
-	ldp	x13, x14, [x0, #CTX_SPSR_IRQ]
-	msr	spsr_irq, x13
-	msr	spsr_fiq, x14
-
 	ldp	x15, x16, [x0, #CTX_SCTLR_EL1]
 	msr	sctlr_el1, x15
 	msr	actlr_el1, x16
@@ -179,10 +174,6 @@
 	msr	tpidr_el0, x9
 	msr	tpidrro_el0, x10
 
-	ldp	x11, x12, [x0, #CTX_DACR32_EL2]
-	msr	dacr32_el2, x11
-	msr	ifsr32_el2, x12
-
 	ldp	x13, x14, [x0, #CTX_PAR_EL1]
 	msr	par_el1, x13
 	msr	far_el1, x14
@@ -195,6 +186,23 @@
 	msr	contextidr_el1, x17
 	msr	vbar_el1, x9
 
+	/* Restore AArch32 system registers if the build has instructed so */
+#if CTX_INCLUDE_AARCH32_REGS
+	ldp	x11, x12, [x0, #CTX_SPSR_ABT]
+	msr	spsr_abt, x11
+	msr	spsr_und, x12
+
+	ldp	x13, x14, [x0, #CTX_SPSR_IRQ]
+	msr	spsr_irq, x13
+	msr	spsr_fiq, x14
+
+	ldp	x15, x16, [x0, #CTX_DACR32_EL2]
+	msr	dacr32_el2, x15
+	msr	ifsr32_el2, x16
+
+	ldr	x17, [x0, #CTX_FP_FPEXC32_EL2]
+	msr	fpexc32_el2, x17
+#endif
 	/* Restore NS timer registers if the build has instructed so */
 #if NS_TIMER_SWITCH
 	ldp	x10, x11, [x0, #CTX_CNTP_CTL_EL0]
@@ -209,11 +217,7 @@
 	msr	cntkctl_el1, x14
 #endif
 
-	ldr	x15, [x0, #CTX_FP_FPEXC32_EL2]
-	msr	fpexc32_el2, x15
-
 	/* No explict ISB required here as ERET covers it */
-
 	ret
 endfunc el1_sysregs_context_restore
 
diff --git a/common/bl_common.c b/common/bl_common.c
index 2e23fbf..7cafe63 100644
--- a/common/bl_common.c
+++ b/common/bl_common.c
@@ -189,12 +189,20 @@
 }
 
 /*******************************************************************************
- * Generic function to load an image at a specific address given a name and
- * extents of free memory. It updates the memory layout if the load is
- * successful, as well as the image information and the entry point information.
- * The caller might pass a NULL pointer for the entry point if it is not
- * interested in this information, e.g. because the image just needs to be
- * loaded in memory but won't ever be executed.
+ * Generic function to load an image at a specific address given an image ID and
+ * extents of free memory.
+ *
+ * If the load is successful then the image information is updated.
+ *
+ * If the entry_point_info argument is not NULL then this function also updates:
+ * - the memory layout to mark the memory as reserved;
+ * - the entry point information.
+ *
+ * The caller might pass a NULL pointer for the entry point if they are not
+ * interested in this information. This is typically the case for non-executable
+ * images (e.g. certificates) and executable images that won't ever be executed
+ * on the application processor (e.g. additional microcontroller firmware).
+ *
  * Returns 0 on success, a negative error code otherwise.
  ******************************************************************************/
 int load_image(meminfo_t *mem_layout,
@@ -259,6 +267,9 @@
 		goto exit;
 	}
 
+	image_data->image_base = image_base;
+	image_data->image_size = image_size;
+
 	/*
 	 * Update the memory usage info.
 	 * This is done after the actual loading so that it is not updated when
@@ -269,20 +280,16 @@
 	if (entry_point_info != NULL) {
 		reserve_mem(&mem_layout->free_base, &mem_layout->free_size,
 				image_base, image_size);
+		entry_point_info->pc = image_base;
 	} else {
 		INFO("Skip reserving memory: %p - %p\n", (void *) image_base,
 		     (void *) (image_base + image_size));
 	}
 
-	image_data->image_base = image_base;
-	image_data->image_size = image_size;
-
-	if (entry_point_info != NULL)
-		entry_point_info->pc = image_base;
-
 	/*
 	 * File has been successfully loaded.
-	 * Flush the image in TZRAM so that the next EL can see it.
+	 * Flush the image in Trusted SRAM so that the next exception level can
+	 * see it.
 	 */
 	flush_dcache_range(image_base, image_size);
 
diff --git a/docs/user-guide.md b/docs/user-guide.md
index ce0390d..0bdedf9 100644
--- a/docs/user-guide.md
+++ b/docs/user-guide.md
@@ -380,6 +380,12 @@
     any register that is not part of the SBSA generic UART specification.
     Default value is 0 (a full PL011 compliant UART is present).
 
+*   `CTX_INCLUDE_AARCH32_REGS` : Boolean option that, when set to 1, will cause
+    the AArch32 system registers to be included when saving and restoring the
+    CPU context. The option must be set to 0 for AArch64-only platforms (that
+    is on hardware that does not implement AArch32, or at least not at EL1 and
+    higher ELs). Default value is 1.
+
 *   `CTX_INCLUDE_FPREGS`: Boolean option that, when set to 1, will cause the FP
     registers to be included when saving and restoring the CPU context. Default
     is 0.
diff --git a/include/common/context.h b/include/common/context.h
index 0dfebe0..ec47f2a 100644
--- a/include/common/context.h
+++ b/include/common/context.h
@@ -91,48 +91,58 @@
 #define CTX_SYSREGS_OFFSET	(CTX_EL3STATE_OFFSET + CTX_EL3STATE_END)
 #define CTX_SPSR_EL1		0x0
 #define CTX_ELR_EL1		0x8
-#define CTX_SPSR_ABT		0x10
-#define CTX_SPSR_UND		0x18
-#define CTX_SPSR_IRQ		0x20
-#define CTX_SPSR_FIQ		0x28
-#define CTX_SCTLR_EL1		0x30
-#define CTX_ACTLR_EL1		0x38
-#define CTX_CPACR_EL1		0x40
-#define CTX_CSSELR_EL1		0x48
-#define CTX_SP_EL1		0x50
-#define CTX_ESR_EL1		0x58
-#define CTX_TTBR0_EL1		0x60
-#define CTX_TTBR1_EL1		0x68
-#define CTX_MAIR_EL1		0x70
-#define CTX_AMAIR_EL1		0x78
-#define CTX_TCR_EL1		0x80
-#define CTX_TPIDR_EL1		0x88
-#define CTX_TPIDR_EL0		0x90
-#define CTX_TPIDRRO_EL0		0x98
-#define CTX_DACR32_EL2		0xa0
-#define CTX_IFSR32_EL2		0xa8
-#define CTX_PAR_EL1		0xb0
-#define CTX_FAR_EL1		0xb8
-#define CTX_AFSR0_EL1		0xc0
-#define CTX_AFSR1_EL1		0xc8
-#define CTX_CONTEXTIDR_EL1	0xd0
-#define CTX_VBAR_EL1		0xd8
+#define CTX_SCTLR_EL1		0x10
+#define CTX_ACTLR_EL1		0x18
+#define CTX_CPACR_EL1		0x20
+#define CTX_CSSELR_EL1		0x28
+#define CTX_SP_EL1		0x30
+#define CTX_ESR_EL1		0x38
+#define CTX_TTBR0_EL1		0x40
+#define CTX_TTBR1_EL1		0x48
+#define CTX_MAIR_EL1		0x50
+#define CTX_AMAIR_EL1		0x58
+#define CTX_TCR_EL1		0x60
+#define CTX_TPIDR_EL1		0x68
+#define CTX_TPIDR_EL0		0x70
+#define CTX_TPIDRRO_EL0		0x78
+#define CTX_PAR_EL1		0x80
+#define CTX_FAR_EL1		0x88
+#define CTX_AFSR0_EL1		0x90
+#define CTX_AFSR1_EL1		0x98
+#define CTX_CONTEXTIDR_EL1	0xa0
+#define CTX_VBAR_EL1		0xa8
+
+/*
+ * If the platform is AArch64-only, there is no need to save and restore these
+ * AArch32 registers.
+ */
+#if CTX_INCLUDE_AARCH32_REGS
+#define CTX_SPSR_ABT		0xb0
+#define CTX_SPSR_UND		0xb8
+#define CTX_SPSR_IRQ		0xc0
+#define CTX_SPSR_FIQ		0xc8
+#define CTX_DACR32_EL2		0xd0
+#define CTX_IFSR32_EL2		0xd8
+#define CTX_FP_FPEXC32_EL2	0xe0
+#define CTX_TIMER_SYSREGS_OFF		0xf0 /* Align to the next 16 byte boundary */
+#else
+#define CTX_TIMER_SYSREGS_OFF		0xb0
+#endif /* __CTX_INCLUDE_AARCH32_REGS__ */
+
 /*
  * If the timer registers aren't saved and restored, we don't have to reserve
  * space for them in the context
  */
 #if NS_TIMER_SWITCH
-#define CTX_CNTP_CTL_EL0	0xe0
-#define CTX_CNTP_CVAL_EL0	0xe8
-#define CTX_CNTV_CTL_EL0	0xf0
-#define CTX_CNTV_CVAL_EL0	0xf8
-#define CTX_CNTKCTL_EL1		0x100
-#define CTX_FP_FPEXC32_EL2	0x108
-#define CTX_SYSREGS_END		0x110
+#define CTX_CNTP_CTL_EL0	(CTX_TIMER_SYSREGS_OFF + 0x0)
+#define CTX_CNTP_CVAL_EL0	(CTX_TIMER_SYSREGS_OFF + 0x8)
+#define CTX_CNTV_CTL_EL0	(CTX_TIMER_SYSREGS_OFF + 0x10)
+#define CTX_CNTV_CVAL_EL0	(CTX_TIMER_SYSREGS_OFF + 0x18)
+#define CTX_CNTKCTL_EL1		(CTX_TIMER_SYSREGS_OFF + 0x20)
+#define CTX_SYSREGS_END		(CTX_TIMER_SYSREGS_OFF + 0x30) /* Align to the next 16 byte boundary */
 #else
-#define CTX_FP_FPEXC32_EL2	0xe0
-#define CTX_SYSREGS_END		0xf0
-#endif
+#define CTX_SYSREGS_END		CTX_TIMER_SYSREGS_OFF
+#endif /* __NS_TIMER_SWITCH__ */
 
 /*******************************************************************************
  * Constants that allow assembler code to access members of and the 'fp_regs'
diff --git a/include/lib/cpus/aarch64/cortex_a73.h b/include/lib/cpus/aarch64/cortex_a73.h
new file mode 100644
index 0000000..2ad0467
--- /dev/null
+++ b/include/lib/cpus/aarch64/cortex_a73.h
@@ -0,0 +1,44 @@
+/*
+ * Copyright (c) 2016, ARM Limited and Contributors. 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.
+ */
+
+#ifndef __CORTEX_A73_H__
+#define __CORTEX_A73_H__
+
+/* Cortex-A73 midr for revision 0 */
+#define CORTEX_A73_MIDR	0x410FD090
+
+/*******************************************************************************
+ * CPU Extended Control register specific definitions.
+ ******************************************************************************/
+#define CORTEX_A73_CPUECTLR_EL1		S3_1_C15_C2_1	/* Instruction def. */
+
+#define CORTEX_A73_CPUECTLR_SMP_BIT	(1 << 6)
+
+#endif /* __CORTEX_A73_H__ */
diff --git a/include/lib/xlat_tables.h b/include/lib/xlat_tables.h
index abe46ed..7d57521 100644
--- a/include/lib/xlat_tables.h
+++ b/include/lib/xlat_tables.h
@@ -150,12 +150,6 @@
 	MT_MEMORY,
 	/* Values up to 7 are reserved to add new memory types in the future */
 
-	/*
-	 * The following values are organised so that a clear bit gives a more
-	 * restrictive mapping than a set bit, that way a bitwise-and of two
-	 * sets of attributes will never give an attribute which has greater
-	 * access rights than any of the original attributes.
-	 */
 	MT_RO		= 0 << MT_PERM_SHIFT,
 	MT_RW		= 1 << MT_PERM_SHIFT,
 
diff --git a/lib/cpus/aarch64/cortex_a73.S b/lib/cpus/aarch64/cortex_a73.S
new file mode 100644
index 0000000..70b4c6a
--- /dev/null
+++ b/lib/cpus/aarch64/cortex_a73.S
@@ -0,0 +1,155 @@
+/*
+ * Copyright (c) 2016, ARM Limited and Contributors. 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 <arch.h>
+#include <asm_macros.S>
+#include <bl_common.h>
+#include <cortex_a73.h>
+#include <cpu_macros.S>
+#include <plat_macros.S>
+
+	/* ---------------------------------------------
+	 * Disable L1 data cache
+	 * ---------------------------------------------
+	 */
+func cortex_a73_disable_dcache
+	mrs	x1, sctlr_el3
+	bic	x1, x1, #SCTLR_C_BIT
+	msr	sctlr_el3, x1
+	isb
+	ret
+endfunc cortex_a73_disable_dcache
+
+	/* ---------------------------------------------
+	 * Disable intra-cluster coherency
+	 * ---------------------------------------------
+	 */
+func cortex_a73_disable_smp
+	mrs	x0, CORTEX_A73_CPUECTLR_EL1
+	bic	x0, x0, #CORTEX_A73_CPUECTLR_SMP_BIT
+	msr	CORTEX_A73_CPUECTLR_EL1, x0
+	isb
+	dsb	sy
+	ret
+endfunc cortex_a73_disable_smp
+
+func cortex_a73_reset_func
+	/* ---------------------------------------------
+	 * Enable the SMP bit.
+	 * Clobbers : x0
+	 * ---------------------------------------------
+	 */
+	mrs	x0, CORTEX_A73_CPUECTLR_EL1
+	orr	x0, x0, #CORTEX_A73_CPUECTLR_SMP_BIT
+	msr	CORTEX_A73_CPUECTLR_EL1, x0
+	isb
+	ret
+endfunc cortex_a73_reset_func
+
+func cortex_a73_core_pwr_dwn
+	mov	x18, x30
+
+	/* ---------------------------------------------
+	 * Turn off caches.
+	 * ---------------------------------------------
+	 */
+	bl	cortex_a73_disable_dcache
+
+	/* ---------------------------------------------
+	 * Flush L1 caches.
+	 * ---------------------------------------------
+	 */
+	mov	x0, #DCCISW
+	bl	dcsw_op_level1
+
+	/* ---------------------------------------------
+	 * Come out of intra cluster coherency
+	 * ---------------------------------------------
+	 */
+	mov	x30, x18
+	b	cortex_a73_disable_smp
+endfunc cortex_a73_core_pwr_dwn
+
+func cortex_a73_cluster_pwr_dwn
+	mov	x18, x30
+
+	/* ---------------------------------------------
+	 * Turn off caches.
+	 * ---------------------------------------------
+	 */
+	bl	cortex_a73_disable_dcache
+
+	/* ---------------------------------------------
+	 * Flush L1 caches.
+	 * ---------------------------------------------
+	 */
+	mov	x0, #DCCISW
+	bl	dcsw_op_level1
+
+	/* ---------------------------------------------
+	 * Disable the optional ACP.
+	 * ---------------------------------------------
+	 */
+	bl	plat_disable_acp
+
+	/* ---------------------------------------------
+	 * Flush L2 caches.
+	 * ---------------------------------------------
+	 */
+	mov	x0, #DCCISW
+	bl	dcsw_op_level2
+
+	/* ---------------------------------------------
+	 * Come out of intra cluster coherency
+	 * ---------------------------------------------
+	 */
+	mov	x30, x18
+	b	cortex_a73_disable_smp
+endfunc cortex_a73_cluster_pwr_dwn
+
+	/* ---------------------------------------------
+	 * This function provides cortex_a73 specific
+	 * register information for crash reporting.
+	 * It needs to return with x6 pointing to
+	 * a list of register names in ascii and
+	 * x8 - x15 having values of registers to be
+	 * reported.
+	 * ---------------------------------------------
+	 */
+.section .rodata.cortex_a73_regs, "aS"
+cortex_a73_regs:  /* The ascii list of register names to be reported */
+	.asciz	"cpuectlr_el1", ""
+
+func cortex_a73_cpu_reg_dump
+	adr	x6, cortex_a73_regs
+	mrs	x8, CORTEX_A73_CPUECTLR_EL1
+	ret
+endfunc cortex_a73_cpu_reg_dump
+
+declare_cpu_ops cortex_a73, CORTEX_A73_MIDR
diff --git a/plat/arm/board/common/board_arm_trusted_boot.c b/plat/arm/board/common/board_arm_trusted_boot.c
index 7ae00cc..fd9e9f6 100644
--- a/plat/arm/board/common/board_arm_trusted_boot.c
+++ b/plat/arm/board/common/board_arm_trusted_boot.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2016, ARM Limited and Contributors. All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
  * modification, are permitted provided that the following conditions are met:
@@ -180,10 +180,10 @@
 }
 
 /*
- * Store a new non-volatile counter value. On Juno and FVP, the non-volatile
- * counters are RO and cannot be modified. We expect the values in the
- * certificates to always match the RO values so that this function is never
- * called.
+ * Store a new non-volatile counter value. By default on ARM development
+ * platforms, the non-volatile counters are RO and cannot be modified. We expect
+ * the values in the certificates to always match the RO values so that this
+ * function is never called.
  *
  * Return: 0 = success, Otherwise = error
  */
diff --git a/plat/arm/board/fvp/fvp_common.c b/plat/arm/board/fvp/fvp_common.c
index eb67dab..0f557af 100644
--- a/plat/arm/board/fvp/fvp_common.c
+++ b/plat/arm/board/fvp/fvp_common.c
@@ -62,7 +62,7 @@
 
 #define MAP_DEVICE2	MAP_REGION_FLAT(DEVICE2_BASE,			\
 					DEVICE2_SIZE,			\
-					MT_DEVICE | MT_RO | MT_SECURE)
+					MT_DEVICE | MT_RW | MT_SECURE)
 
 
 /*
diff --git a/plat/arm/board/fvp/fvp_trusted_boot.c b/plat/arm/board/fvp/fvp_trusted_boot.c
new file mode 100644
index 0000000..7db5051
--- /dev/null
+++ b/plat/arm/board/fvp/fvp_trusted_boot.c
@@ -0,0 +1,68 @@
+/*
+ * Copyright (c) 2016, ARM Limited and Contributors. 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 <assert.h>
+#include <platform_oid.h>
+#include <stdint.h>
+#include <string.h>
+#include "fvp_def.h"
+
+/*
+ * Store a new non-volatile counter value. On some FVP versions, the
+ * non-volatile counters are RO. On these versions we expect the values in the
+ * certificates to always match the RO values so that this function is never
+ * called.
+ *
+ * Return: 0 = success, Otherwise = error
+ */
+int plat_set_nv_ctr(void *cookie, unsigned int nv_ctr)
+{
+	const char *oid;
+	uint32_t *nv_ctr_addr;
+
+	assert(cookie != NULL);
+
+	oid = (const char *)cookie;
+	if (strcmp(oid, TRUSTED_FW_NVCOUNTER_OID) == 0) {
+		nv_ctr_addr = (uint32_t *)TFW_NVCTR_BASE;
+	} else if (strcmp(oid, NON_TRUSTED_FW_NVCOUNTER_OID) == 0) {
+		nv_ctr_addr = (uint32_t *)NTFW_CTR_BASE;
+	} else {
+		return 1;
+	}
+
+	*(unsigned int *)nv_ctr_addr = nv_ctr;
+
+	/* Verify that the current value is the one we just wrote. */
+	if (nv_ctr != (unsigned int)(*nv_ctr_addr))
+		return 1;
+
+	return 0;
+}
diff --git a/plat/arm/board/fvp/platform.mk b/plat/arm/board/fvp/platform.mk
index 6456cde..1ea9822 100644
--- a/plat/arm/board/fvp/platform.mk
+++ b/plat/arm/board/fvp/platform.mk
@@ -102,7 +102,8 @@
 				lib/cpus/aarch64/cortex_a35.S			\
 				lib/cpus/aarch64/cortex_a53.S			\
 				lib/cpus/aarch64/cortex_a57.S			\
-				lib/cpus/aarch64/cortex_a72.S
+				lib/cpus/aarch64/cortex_a72.S			\
+				lib/cpus/aarch64/cortex_a73.S
 
 BL1_SOURCES		+=	drivers/io/io_semihosting.c			\
 				lib/semihosting/semihosting.c			\
@@ -111,6 +112,7 @@
 				plat/arm/board/fvp/fvp_bl1_setup.c		\
 				plat/arm/board/fvp/fvp_err.c			\
 				plat/arm/board/fvp/fvp_io_storage.c		\
+				plat/arm/board/fvp/fvp_trusted_boot.c		\
 				${FVP_CPU_LIBS}					\
 				${FVP_INTERCONNECT_SOURCES}
 
@@ -122,6 +124,7 @@
 				plat/arm/board/fvp/fvp_bl2_setup.c		\
 				plat/arm/board/fvp/fvp_err.c			\
 				plat/arm/board/fvp/fvp_io_storage.c		\
+				plat/arm/board/fvp/fvp_trusted_boot.c		\
 				${FVP_SECURITY_SOURCES}
 
 ifeq (${FVP_USE_SP804_TIMER},1)
diff --git a/plat/arm/common/aarch64/arm_common.c b/plat/arm/common/aarch64/arm_common.c
index 616edc9..c4cc80e 100644
--- a/plat/arm/common/aarch64/arm_common.c
+++ b/plat/arm/common/aarch64/arm_common.c
@@ -176,7 +176,7 @@
 #if ERROR_DEPRECATED
 unsigned int plat_get_syscnt_freq2(void)
 {
-	unsigned int counter_base_frequency
+	unsigned int counter_base_frequency;
 #else
 unsigned long long plat_get_syscnt_freq(void)
 {