Merge pull request #1373 from jeenu-arm/ras-support

RAS support
diff --git a/.checkpatch.conf b/.checkpatch.conf
index e92b96f..63bdf7b 100644
--- a/.checkpatch.conf
+++ b/.checkpatch.conf
@@ -36,6 +36,10 @@
 # This is not Linux so don't expect a Linux tree!
 --no-tree
 
+# The Linux kernel expects the SPDX license tag in the first line of each file.
+# We don't follow this in the Trusted Firmware.
+--ignore SPDX_LICENSE_TAG
+
 # This clarifes the lines indications in the report.
 #
 # E.g.:
diff --git a/.editorconfig b/.editorconfig
new file mode 100644
index 0000000..0e7a5c3
--- /dev/null
+++ b/.editorconfig
@@ -0,0 +1,62 @@
+#
+# Copyright (c) 2017, ARM Limited and Contributors. All rights reserved.
+#
+# SPDX-License-Identifier: BSD-3-Clause
+#
+
+# ARM Trusted Firmware Coding style spec for editors.
+
+# References:
+# [EC]          http://editorconfig.org/
+# [CONT]        contributing.rst
+# [LCS]         Linux Coding Style
+#               (https://www.kernel.org/doc/html/v4.10/process/coding-style.html)
+
+
+root = true
+
+# set default to match [LCS] .c/.h settings.
+# This will also apply to .S, .mk, .sh, Makefile, .dts, etc.
+[*]
+# Not specified, but fits current ARM-TF sources.
+charset = utf-8
+
+# Not specified, but implicit for "LINUX coding style".
+end_of_line = lf
+
+# [LCS] Chapter 1: Indentation
+#       "and thus indentations are also 8 characters"
+indent_size = 8
+
+# [LCS] Chapter 1: Indentation
+#       "Outside of comments,...spaces are never used for indentation"
+indent_style = tab
+
+# Not specified by [LCS], but sensible
+insert_final_newline = true
+
+# [LCS] Chapter 2: Breaking long lines and strings
+#       "The limit on the length of lines is 80 columns"
+#   This is a "soft" requirement for Arm-TF, and should not be the sole
+#   reason for changes.
+max_line_length = 80
+
+# [LCS] Chapter 1: Indentation
+#       "Tabs are 8 characters"
+tab_width = 8
+
+# [LCS] Chapter 1: Indentation
+#       "Get a decent editor and don't leave whitespace at the end of lines."
+# [LCS] Chapter 3.1: Spaces
+#       "Do not leave trailing whitespace at the ends of lines."
+trim_trailing_whitespace = true
+
+
+# Adjustment for existing .rst files with different format
+[*.{rst,md}]
+indent_size = 4
+indent_style = space
+max_line_length = 180
+# 180 only selected to prevent changes to existing text.
+tab_width = 4
+
diff --git a/Makefile b/Makefile
index 5132701..b7116a7 100644
--- a/Makefile
+++ b/Makefile
@@ -90,7 +90,6 @@
         LOG_LEVEL	:=	40
 else
         BUILD_TYPE	:=	release
-        $(eval $(call add_define,NDEBUG))
         # Use LOG_LEVEL_NOTICE by default for release builds
         LOG_LEVEL	:=	20
 endif
diff --git a/bl2/bl2_main.c b/bl2/bl2_main.c
index 41d1745..101eb33 100644
--- a/bl2/bl2_main.c
+++ b/bl2/bl2_main.c
@@ -46,6 +46,7 @@
 	/* Load the subsequent bootloader images. */
 	next_bl_ep_info = bl2_load_images();
 
+#if !BL2_AT_EL3
 #ifdef AARCH32
 	/*
 	 * For AArch32 state BL1 and BL2 share the MMU setup.
@@ -55,8 +56,6 @@
 	disable_mmu_icache_secure();
 #endif /* AARCH32 */
 
-
-#if !BL2_AT_EL3
 	console_flush();
 
 	/*
diff --git a/drivers/console/aarch64/multi_console.S b/drivers/console/aarch64/multi_console.S
index 15c3ba4..a85a6a5 100644
--- a/drivers/console/aarch64/multi_console.S
+++ b/drivers/console/aarch64/multi_console.S
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2017, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2018, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -10,7 +10,8 @@
 
 	.globl	console_register
 	.globl	console_unregister
-	.globl  console_set_scope
+	.globl	console_is_registered
+	.globl	console_set_scope
 	.globl	console_switch_state
 	.globl	console_putc
 	.globl	console_getc
@@ -38,13 +39,15 @@
 	 * persistent memory (e.g. the data section).
 	 * In : x0 - address of console_t structure
 	 * Out: x0 - Always 1 (for easier tail calling)
-	 * Clobber list: x0, x1, x14
+	 * Clobber list: x0, x1, x14, x15
 	 * -----------------------------------------------
 	 */
 func console_register
 #if ENABLE_ASSERTIONS
+	/* Assert that x0 isn't a NULL pointer */
 	cmp	x0, #0
 	ASM_ASSERT(ne)
+	/* Assert that the struct isn't in the stack */
 	adrp	x1, __STACKS_START__
 	add	x1, x1, :lo12:__STACKS_START__
 	cmp	x0, x1
@@ -54,6 +57,14 @@
 	cmp	x0, x1
 	ASM_ASSERT(hs)
 not_on_stack:
+	/* Assert that this struct isn't in the list */
+	mov	x1, x0 /* Preserve x0 and x30 */
+	mov	x15, x30
+	bl	console_is_registered
+	cmp	x0, #0
+	ASM_ASSERT(eq)
+	mov	x30, x15
+	mov	x0, x1
 #endif /* ENABLE_ASSERTIONS */
 	adrp	x14, console_list
 	ldr	x1, [x14, :lo12:console_list]	/* X1 = first struct in list */
@@ -73,6 +84,11 @@
 	 * -----------------------------------------------
 	 */
 func console_unregister
+#if ENABLE_ASSERTIONS
+	/* Assert that x0 isn't a NULL pointer */
+	cmp	x0, #0
+	ASM_ASSERT(ne)
+#endif /* ENABLE_ASSERTIONS */
 	adrp	x14, console_list
 	add	x14, x14, :lo12:console_list	/* X14 = ptr to first struct */
 	ldr	x1, [x14]			/* X1 = first struct */
@@ -96,6 +112,37 @@
 endfunc console_unregister
 
 	/* -----------------------------------------------
+	 * int console_is_registered(console_t *console)
+	 * Function to detect if a specific console is
+	 * registered or not.
+	 * In: x0 - address of console_t struct to remove
+	 * Out: x0 - 1 if it is registered, 0 if not.
+	 * Clobber list: x0, x14
+	 * -----------------------------------------------
+	 */
+func console_is_registered
+#if ENABLE_ASSERTIONS
+	/* Assert that x0 isn't a NULL pointer */
+	cmp	x0, #0
+	ASM_ASSERT(ne)
+#endif /* ENABLE_ASSERTIONS */
+	adrp	x14, console_list
+	ldr	x14, [x14, :lo12:console_list]	/* X14 = first console struct */
+check_registered_loop:
+	cbz	x14, console_not_registered /* Check if end of list */
+	cmp	x0, x14		/* Check if the pointers are different */
+	b.eq	console_registered
+	ldr	x14, [x14, #CONSOLE_T_NEXT]	/* Get pointer to next struct */
+	b	check_registered_loop
+console_not_registered:
+	mov	x0, #0
+	ret
+console_registered:
+	mov	x0, #1
+	ret
+endfunc console_is_registered
+
+	/* -----------------------------------------------
 	 * void console_switch_state(unsigned int new_state)
 	 * Function to switch the current console state.
 	 * The console state determines which of the
diff --git a/include/drivers/console.h b/include/drivers/console.h
index f8ec83d..0855170 100644
--- a/include/drivers/console.h
+++ b/include/drivers/console.h
@@ -50,7 +50,12 @@
  */
 /* Remove a single console_t instance from the console list. */
 int console_unregister(console_t *console);
-/* Set scope mask of a console that determines in what states it is active. */
+/* Returns 1 if this console is already registered, 0 if not */
+int console_is_registered(console_t *console);
+/*
+ * Set scope mask of a console that determines in what states it is active.
+ * By default they are registered with (CONSOLE_FLAG_BOOT|CONSOLE_FLAG_CRASH).
+ */
 void console_set_scope(console_t *console, unsigned int scope);
 
 /* Switch to a new global console state (CONSOLE_FLAG_BOOT/RUNTIME/CRASH). */
diff --git a/include/lib/utils.h b/include/lib/utils.h
index 3d215c3..f367a1f 100644
--- a/include/lib/utils.h
+++ b/include/lib/utils.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2017, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2016-2018, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -29,6 +29,18 @@
  */
 void clear_mem_regions(mem_region_t *tbl, size_t nregions);
 
+/*
+ * zero_normalmem all the regions defined in region. It dynamically
+ * maps chunks of 'chunk_size' in 'va' virtual address and clears them.
+ * For this reason memory regions must be multiple of chunk_size and
+ * must be aligned to it as well. chunk_size and va can be selected
+ * in a way that they minimize the number of entries used in the
+ * translation tables.
+ */
+void clear_map_dyn_mem_regions(mem_region_t *region,
+			       size_t nregions,
+			       uintptr_t va,
+			       size_t chunk_size);
 
 /*
  * checks that a region (addr + nbytes-1) of memory is totally covered by
diff --git a/include/lib/xlat_tables/xlat_tables_arch.h b/include/lib/xlat_tables/xlat_tables_arch.h
index 165b161d..af8c463 100644
--- a/include/lib/xlat_tables/xlat_tables_arch.h
+++ b/include/lib/xlat_tables/xlat_tables_arch.h
@@ -21,8 +21,8 @@
  * limits. Not that these limits are different for AArch32 and AArch64.
  */
 #define CHECK_VIRT_ADDR_SPACE_SIZE(size)			\
-	(((size) >= MIN_VIRT_ADDR_SPACE_SIZE) &&		\
-	((size) <= MAX_VIRT_ADDR_SPACE_SIZE) &&			\
+	(((unsigned long long)(size) >= MIN_VIRT_ADDR_SPACE_SIZE) &&		\
+	((unsigned long long)(size) <= MAX_VIRT_ADDR_SPACE_SIZE) &&		\
 	IS_POWER_OF_TWO(size))
 
 /*
diff --git a/include/plat/arm/board/common/board_arm_def.h b/include/plat/arm/board/common/board_arm_def.h
index 12a21fb..845f140 100644
--- a/include/plat/arm/board/common/board_arm_def.h
+++ b/include/plat/arm/board/common/board_arm_def.h
@@ -30,7 +30,11 @@
 #elif defined(IMAGE_BL2U)
 # define PLATFORM_STACK_SIZE 0x200
 #elif defined(IMAGE_BL31)
+#ifdef PLAT_XLAT_TABLES_DYNAMIC
+# define PLATFORM_STACK_SIZE 0x800
+#else
 # define PLATFORM_STACK_SIZE 0x400
+#endif
 #elif defined(IMAGE_BL32)
 # define PLATFORM_STACK_SIZE 0x440
 #endif
@@ -59,11 +63,11 @@
 #  define PLAT_SP_IMAGE_MMAP_REGIONS	7
 #  define PLAT_SP_IMAGE_MAX_XLAT_TABLES	10
 # else
-#  define PLAT_ARM_MMAP_ENTRIES		7
+#  define PLAT_ARM_MMAP_ENTRIES		8
 #  define MAX_XLAT_TABLES		5
 # endif
 #elif defined(IMAGE_BL32)
-# define PLAT_ARM_MMAP_ENTRIES		7
+# define PLAT_ARM_MMAP_ENTRIES		8
 # define MAX_XLAT_TABLES		5
 #else
 # define PLAT_ARM_MMAP_ENTRIES		11
diff --git a/include/plat/arm/common/plat_arm.h b/include/plat/arm/common/plat_arm.h
index f79450c..612a63a 100644
--- a/include/plat/arm/common/plat_arm.h
+++ b/include/plat/arm/common/plat_arm.h
@@ -166,7 +166,8 @@
 void arm_program_trusted_mailbox(uintptr_t address);
 int arm_psci_read_mem_protect(int *enabled);
 int arm_nor_psci_write_mem_protect(int val);
-void arm_nor_psci_do_mem_protect(void);
+void arm_nor_psci_do_static_mem_protect(void);
+void arm_nor_psci_do_dyn_mem_protect(void);
 int arm_psci_mem_protect_chk(uintptr_t base, u_register_t length);
 
 /* Topology utility function */
diff --git a/include/plat/arm/css/common/css_def.h b/include/plat/arm/css/common/css_def.h
index a2c0b4e..deea1bb 100644
--- a/include/plat/arm/css/common/css_def.h
+++ b/include/plat/arm/css/common/css_def.h
@@ -172,7 +172,7 @@
 #endif /* CSS_LOAD_SCP_IMAGES */
 
 /* Load address of Non-Secure Image for CSS platform ports */
-#define PLAT_ARM_NS_IMAGE_OFFSET	0xE0000000
+#define PLAT_ARM_NS_IMAGE_OFFSET	U(0xE0000000)
 
 /* TZC related constants */
 #define PLAT_ARM_TZC_FILTERS		TZC_400_REGION_ATTR_FILTER_BIT_ALL
diff --git a/lib/utils/mem_region.c b/lib/utils/mem_region.c
index 31c6231..24c2c1d 100644
--- a/lib/utils/mem_region.c
+++ b/lib/utils/mem_region.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2018, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -40,6 +40,59 @@
 	}
 }
 
+#if defined(PLAT_XLAT_TABLES_DYNAMIC)
+/*
+ * zero_normalmem all the regions defined in regions.
+ * It assumes that MMU is enabled and the memory is Normal memory.
+ * regions must be a valid pointer to a memory mem_region_t array,
+ * nregions is the size of the array. va is the virtual address
+ * where we want to map the physical pages that are going to
+ * be cleared, and chunk is the amount of memory mapped and
+ * cleared in every iteration.
+ */
+void clear_map_dyn_mem_regions(mem_region_t *regions,
+			       size_t nregions,
+			       uintptr_t va,
+			       size_t chunk)
+{
+	uintptr_t begin;
+	int r;
+	size_t size;
+	const mmap_attr_t attr = MT_MEMORY|MT_RW|MT_NS;
+
+	assert(regions != NULL);
+	assert(nregions > 0 && chunk > 0);
+
+	for ( ; nregions--; regions++) {
+		begin = regions->base;
+		size = regions->nbytes;
+		if ((begin & (chunk-1)) != 0 || (size & (chunk-1)) != 0) {
+			INFO("PSCI: Not correctly aligned region\n");
+			panic();
+		}
+
+		while (size > 0) {
+			r = mmap_add_dynamic_region(begin, va, chunk, attr);
+			if (r != 0) {
+				INFO("PSCI: mmap_add_dynamic_region failed with %d\n", r);
+				panic();
+			}
+
+			zero_normalmem((void *) va, chunk);
+
+			r = mmap_remove_dynamic_region(va, chunk);
+			if (r != 0) {
+				INFO("PSCI: mmap_remove_dynamic_region failed with %d\n", r);
+				panic();
+			}
+
+			begin += chunk;
+			size -= chunk;
+		}
+	}
+}
+#endif
+
 /*
  * This function checks that a region (addr + nbytes-1) of memory is totally
  * covered by one of the regions defined in tbl.
diff --git a/lib/xlat_tables/aarch64/xlat_tables.c b/lib/xlat_tables/aarch64/xlat_tables.c
index eabc3df..a72c645 100644
--- a/lib/xlat_tables/aarch64/xlat_tables.c
+++ b/lib/xlat_tables/aarch64/xlat_tables.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2014-2017, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2014-2018, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -57,13 +57,13 @@
 }
 
 #if ENABLE_ASSERTIONS
-/* Physical Address ranges supported in the AArch64 Memory Model */
+/*
+ * Physical Address ranges supported in the AArch64 Memory Model. Value 0b110 is
+ * supported in ARMv8.2 onwards.
+ */
 static const unsigned int pa_range_bits_arr[] = {
 	PARANGE_0000, PARANGE_0001, PARANGE_0010, PARANGE_0011, PARANGE_0100,
-	PARANGE_0101,
-#if ARM_ARCH_AT_LEAST(8, 2)
-	PARANGE_0110,
-#endif
+	PARANGE_0101, PARANGE_0110
 };
 
 static unsigned long long get_max_supported_pa(void)
diff --git a/lib/xlat_tables_v2/aarch64/xlat_tables_arch.c b/lib/xlat_tables_v2/aarch64/xlat_tables_arch.c
index ffbc665..b3504e1 100644
--- a/lib/xlat_tables_v2/aarch64/xlat_tables_arch.c
+++ b/lib/xlat_tables_v2/aarch64/xlat_tables_arch.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2017-2018, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -45,13 +45,13 @@
 }
 
 #if ENABLE_ASSERTIONS
-/* Physical Address ranges supported in the AArch64 Memory Model */
+/*
+ * Physical Address ranges supported in the AArch64 Memory Model. Value 0b110 is
+ * supported in ARMv8.2 onwards.
+ */
 static const unsigned int pa_range_bits_arr[] = {
 	PARANGE_0000, PARANGE_0001, PARANGE_0010, PARANGE_0011, PARANGE_0100,
-	PARANGE_0101,
-#if ARM_ARCH_AT_LEAST(8, 2)
-	PARANGE_0110,
-#endif
+	PARANGE_0101, PARANGE_0110
 };
 
 unsigned long long xlat_arch_get_max_supported_pa(void)
diff --git a/lib/xlat_tables_v2/xlat_tables_internal.c b/lib/xlat_tables_v2/xlat_tables_internal.c
index 584d7c4..8be6d94 100644
--- a/lib/xlat_tables_v2/xlat_tables_internal.c
+++ b/lib/xlat_tables_v2/xlat_tables_internal.c
@@ -1066,18 +1066,19 @@
 
 	if (xlat_regime == EL3_REGIME) {
 		/* For EL3, the AP[2] bit is all what matters */
-		tf_printf((desc & LOWER_ATTRS(AP_RO)) ? ro_str : rw_str);
+		tf_printf("%s", (desc & LOWER_ATTRS(AP_RO)) ? ro_str : rw_str);
 	} else {
 		const char *ap_str = (desc & LOWER_ATTRS(AP_RO)) ? ro_str : rw_str;
-		tf_printf(ap_str);
-		tf_printf(priv_str);
+		tf_printf("%s", ap_str);
+		tf_printf("%s", priv_str);
 		/*
 		 * EL0 can only have the same permissions as EL1 or no
 		 * permissions at all.
 		 */
-		tf_printf((desc & LOWER_ATTRS(AP_ACCESS_UNPRIVILEGED))
+		tf_printf("%s",
+			  (desc & LOWER_ATTRS(AP_ACCESS_UNPRIVILEGED))
 			  ? ap_str : no_access_str);
-		tf_printf(user_str);
+		tf_printf("%s", user_str);
 	}
 
 	const char *xn_str = "-XN";
@@ -1085,14 +1086,14 @@
 
 	if (xlat_regime == EL3_REGIME) {
 		/* For EL3, the XN bit is all what matters */
-		tf_printf(LOWER_ATTRS(XN) & desc ? xn_str : exec_str);
+		tf_printf("%s", LOWER_ATTRS(XN) & desc ? xn_str : exec_str);
 	} else {
 		/* For EL0 and EL1, we need to know who has which rights */
-		tf_printf(LOWER_ATTRS(PXN) & desc ? xn_str : exec_str);
-		tf_printf(priv_str);
+		tf_printf("%s", LOWER_ATTRS(PXN) & desc ? xn_str : exec_str);
+		tf_printf("%s", priv_str);
 
-		tf_printf(LOWER_ATTRS(UXN) & desc ? xn_str : exec_str);
-		tf_printf(user_str);
+		tf_printf("%s", LOWER_ATTRS(UXN) & desc ? xn_str : exec_str);
+		tf_printf("%s", user_str);
 	}
 
 	tf_printf(LOWER_ATTRS(NS) & desc ? "-NS" : "-S");
diff --git a/plat/arm/board/common/board_css_common.c b/plat/arm/board/common/board_css_common.c
index c1c3e66..c4e83a4 100644
--- a/plat/arm/board/common/board_css_common.c
+++ b/plat/arm/board/common/board_css_common.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2017, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2018, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -73,6 +73,9 @@
 const mmap_region_t plat_arm_mmap[] = {
 #ifdef AARCH32
 	ARM_MAP_SHARED_RAM,
+#ifdef PLAT_ARM_MEM_PROT_ADDR
+	ARM_V2M_MAP_MEM_PROTECT,
+#endif
 #endif
 	V2M_MAP_IOFPGA,
 	CSS_MAP_DEVICE,
diff --git a/plat/arm/board/fvp/fvp_pm.c b/plat/arm/board/fvp/fvp_pm.c
index 0fa83a5..065ecc1 100644
--- a/plat/arm/board/fvp/fvp_pm.c
+++ b/plat/arm/board/fvp/fvp_pm.c
@@ -412,13 +412,7 @@
 	 */
 	.get_sys_suspend_power_state = fvp_get_sys_suspend_power_state,
 #endif
-#if !RESET_TO_BL31 && !RESET_TO_SP_MIN
-	/*
-	 * mem_protect is not supported in RESET_TO_BL31 and RESET_TO_SP_MIN,
-	 * as that would require mapping in all of NS DRAM into BL31 or BL32.
-	 */
 	.mem_protect_chk	= arm_psci_mem_protect_chk,
 	.read_mem_protect	= arm_psci_read_mem_protect,
 	.write_mem_protect	= arm_nor_psci_write_mem_protect,
-#endif
 };
diff --git a/plat/arm/board/fvp/include/platform_def.h b/plat/arm/board/fvp/include/platform_def.h
index 2d01490..b1adbee 100644
--- a/plat/arm/board/fvp/include/platform_def.h
+++ b/plat/arm/board/fvp/include/platform_def.h
@@ -7,6 +7,17 @@
 #ifndef __PLATFORM_DEF_H__
 #define __PLATFORM_DEF_H__
 
+/* Enable the dynamic translation tables library. */
+#ifdef AARCH32
+# if defined(IMAGE_BL32) && RESET_TO_SP_MIN
+#  define PLAT_XLAT_TABLES_DYNAMIC     1
+# endif
+#else
+# if defined(IMAGE_BL31) && RESET_TO_BL31
+#  define PLAT_XLAT_TABLES_DYNAMIC     1
+# endif
+#endif /* AARCH32 */
+
 #include <arm_def.h>
 #include <arm_spm_def.h>
 #include <board_arm_def.h>
@@ -40,6 +51,9 @@
 #define PLAT_ARM_TRUSTED_DRAM_BASE	0x06000000
 #define PLAT_ARM_TRUSTED_DRAM_SIZE	0x02000000	/* 32 MB */
 
+/* virtual address used by dynamic mem_protect for chunk_base */
+#define PLAT_ARM_MEM_PROTEC_VA_FRAME	0xc0000000
+
 /* No SCP in FVP */
 #define PLAT_ARM_SCP_TZC_DRAM1_SIZE	ULL(0x0)
 
@@ -48,7 +62,7 @@
 /*
  * Load address of BL33 for this platform port
  */
-#define PLAT_ARM_NS_IMAGE_OFFSET	(ARM_DRAM1_BASE + 0x8000000)
+#define PLAT_ARM_NS_IMAGE_OFFSET	(ARM_DRAM1_BASE + U(0x8000000))
 
 
 /*
diff --git a/plat/arm/board/juno/include/platform_def.h b/plat/arm/board/juno/include/platform_def.h
index b422398..c834941 100644
--- a/plat/arm/board/juno/include/platform_def.h
+++ b/plat/arm/board/juno/include/platform_def.h
@@ -7,6 +7,18 @@
 #ifndef __PLATFORM_DEF_H__
 #define __PLATFORM_DEF_H__
 
+/* Enable the dynamic translation tables library. */
+#ifdef AARCH32
+# if defined(IMAGE_BL32) && RESET_TO_SP_MIN
+#  define PLAT_XLAT_TABLES_DYNAMIC     1
+# endif
+#else
+# if defined(IMAGE_BL31) && RESET_TO_BL31
+#  define PLAT_XLAT_TABLES_DYNAMIC     1
+# endif
+#endif /* AARCH32 */
+
+
 #include <arm_def.h>
 #include <board_arm_def.h>
 #include <board_css_def.h>
@@ -44,6 +56,9 @@
 /* Use the bypass address */
 #define PLAT_ARM_TRUSTED_ROM_BASE	V2M_FLASH0_BASE + BL1_ROM_BYPASS_OFFSET
 
+/* virtual address used by dynamic mem_protect for chunk_base */
+#define PLAT_ARM_MEM_PROTEC_VA_FRAME	0xc0000000
+
 /*
  * Actual ROM size on Juno is 64 KB, but TBB currently requires at least 80 KB
  * in debug mode. We can test TBB on Juno bypassing the ROM and using 128 KB of
@@ -90,7 +105,7 @@
 #endif
 
 #ifdef IMAGE_BL32
-# define PLAT_ARM_MMAP_ENTRIES		5
+# define PLAT_ARM_MMAP_ENTRIES		6
 # define MAX_XLAT_TABLES		4
 #endif
 
diff --git a/plat/arm/common/arm_bl2_setup.c b/plat/arm/common/arm_bl2_setup.c
index 8a6c768..dc7cd68 100644
--- a/plat/arm/common/arm_bl2_setup.c
+++ b/plat/arm/common/arm_bl2_setup.c
@@ -219,7 +219,7 @@
 	plat_arm_security_setup();
 
 #if defined(PLAT_ARM_MEM_PROT_ADDR)
-	arm_nor_psci_do_mem_protect();
+	arm_nor_psci_do_static_mem_protect();
 #endif
 }
 
diff --git a/plat/arm/common/arm_bl31_setup.c b/plat/arm/common/arm_bl31_setup.c
index 16ab3d7..b483f0c 100644
--- a/plat/arm/common/arm_bl31_setup.c
+++ b/plat/arm/common/arm_bl31_setup.c
@@ -207,6 +207,10 @@
 	 */
 	plat_arm_security_setup();
 
+#if defined(PLAT_ARM_MEM_PROT_ADDR)
+	arm_nor_psci_do_dyn_mem_protect();
+#endif /* PLAT_ARM_MEM_PROT_ADDR */
+
 #endif /* RESET_TO_BL31 */
 
 	/* Enable and initialize the System level generic timer */
diff --git a/plat/arm/common/arm_nor_psci_mem_protect.c b/plat/arm/common/arm_nor_psci_mem_protect.c
index 3167a42..c01e4ed 100644
--- a/plat/arm/common/arm_nor_psci_mem_protect.c
+++ b/plat/arm/common/arm_nor_psci_mem_protect.c
@@ -12,10 +12,22 @@
 #include <psci.h>
 #include <utils.h>
 
+
+/*
+ * DRAM1 is used also to load the NS boot loader. For this reason we
+ * cannot clear the full DRAM1, because in that case we would clear
+ * the NS images (especially for RESET_TO_BL31 and RESET_TO_SPMIN cases).
+ * For this reason we reserve 64 MB for the NS images and protect the RAM
+ * until the end of DRAM1.
+ * We limit the size of DRAM2 to 1 GB to avoid big delays while booting
+ */
+#define DRAM1_NS_IMAGE_LIMIT  (PLAT_ARM_NS_IMAGE_OFFSET + (32 << TWO_MB_SHIFT))
+#define DRAM1_PROTECTED_SIZE  (ARM_NS_DRAM1_END+1u - DRAM1_NS_IMAGE_LIMIT)
+
 static mem_region_t arm_ram_ranges[] = {
-	{ARM_NS_DRAM1_BASE, ARM_NS_DRAM1_SIZE},
+	{DRAM1_NS_IMAGE_LIMIT, DRAM1_PROTECTED_SIZE},
 #ifdef AARCH64
-	{ARM_DRAM2_BASE, ARM_DRAM2_SIZE},
+	{ARM_DRAM2_BASE, 1u << ONE_GB_SHIFT},
 #endif
 };
 
@@ -29,7 +41,7 @@
 	int tmp;
 
 	tmp = *(int *) PLAT_ARM_MEM_PROT_ADDR;
-	*enabled = (tmp == 1);
+	*enabled = (tmp == 1) ? 1 : 0;
 	return 0;
 }
 
@@ -46,7 +58,7 @@
 		return -1;
 	}
 
-	if (enable) {
+	if (enable != 0) {
 		/*
 		 * If we want to write a value different than 0
 		 * then we have to erase the full block because
@@ -71,15 +83,47 @@
  * Function used for required psci operations performed when
  * system boots
  ******************************************************************************/
-void arm_nor_psci_do_mem_protect(void)
+/*
+ * PLAT_MEM_PROTECT_VA_FRAME is a address specifically
+ * selected in a way that is not needed an additional
+ * translation table for memprotect. It happens because
+ * we use a chunk of size 2MB and it means that it can
+ * be mapped in a level 2 table and the level 2 table
+ * for 0xc0000000 is already used and the entry for
+ * 0xc0000000 is not used.
+ */
+#if defined(PLAT_XLAT_TABLES_DYNAMIC)
+void arm_nor_psci_do_dyn_mem_protect(void)
 {
 	int enable;
 
 	arm_psci_read_mem_protect(&enable);
-	if (!enable)
+	if (enable == 0)
 		return;
-	INFO("PSCI: Overwritting non secure memory\n");
-	clear_mem_regions(arm_ram_ranges, ARRAY_SIZE(arm_ram_ranges));
+
+	INFO("PSCI: Overwriting non secure memory\n");
+	clear_map_dyn_mem_regions(arm_ram_ranges,
+				  ARRAY_SIZE(arm_ram_ranges),
+				  PLAT_ARM_MEM_PROTEC_VA_FRAME,
+				  1 << TWO_MB_SHIFT);
+}
+#endif
+
+/*******************************************************************************
+ * Function used for required psci operations performed when
+ * system boots and dynamic memory is not used.
+ ******************************************************************************/
+void arm_nor_psci_do_static_mem_protect(void)
+{
+	int enable;
+
+	arm_psci_read_mem_protect(&enable);
+	if (enable == 0)
+		return;
+
+	INFO("PSCI: Overwriting non secure memory\n");
+	clear_mem_regions(arm_ram_ranges,
+			  ARRAY_SIZE(arm_ram_ranges));
 	arm_nor_psci_write_mem_protect(0);
 }
 
diff --git a/plat/arm/common/sp_min/arm_sp_min_setup.c b/plat/arm/common/sp_min/arm_sp_min_setup.c
index 7b5477e..9a6c074 100644
--- a/plat/arm/common/sp_min/arm_sp_min_setup.c
+++ b/plat/arm/common/sp_min/arm_sp_min_setup.c
@@ -162,6 +162,11 @@
 	 */
 #if RESET_TO_SP_MIN
 	plat_arm_security_setup();
+
+#if defined(PLAT_ARM_MEM_PROT_ADDR)
+	arm_nor_psci_do_dyn_mem_protect();
+#endif /* PLAT_ARM_MEM_PROT_ADDR */
+
 #endif
 
 	/* Enable and initialize the System level generic timer */
diff --git a/plat/arm/css/common/css_pm.c b/plat/arm/css/common/css_pm.c
index 4a615e1..3df5b78 100644
--- a/plat/arm/css/common/css_pm.c
+++ b/plat/arm/css/common/css_pm.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2015-2017, ARM Limited and Contributors. All rights reserved.
+ * Copyright (c) 2015-2018, ARM Limited and Contributors. All rights reserved.
  *
  * SPDX-License-Identifier: BSD-3-Clause
  */
@@ -303,11 +303,8 @@
 	.translate_power_state_by_mpidr = css_translate_power_state_by_mpidr,
 	.get_node_hw_state	= css_node_hw_state,
 	.get_sys_suspend_power_state = css_get_sys_suspend_power_state,
-/*
- * mem_protect is not supported in RESET_TO_BL31 and RESET_TO_SP_MIN,
- * as that would require mapping in all of NS DRAM into BL31 or BL32.
- */
-#if defined(PLAT_ARM_MEM_PROT_ADDR) && !RESET_TO_BL31 && !RESET_TO_SP_MIN
+
+#if defined(PLAT_ARM_MEM_PROT_ADDR)
 	.mem_protect_chk	= arm_psci_mem_protect_chk,
 	.read_mem_protect	= arm_psci_read_mem_protect,
 	.write_mem_protect	= arm_nor_psci_write_mem_protect,
diff --git a/tools/cert_create/Makefile b/tools/cert_create/Makefile
index b0994b8..8a1958f 100644
--- a/tools/cert_create/Makefile
+++ b/tools/cert_create/Makefile
@@ -86,5 +86,5 @@
 	$(call SHELL_DELETE_ALL, src/build_msg.o ${OBJECTS})
 
 realclean: clean
-	$(call SHELL_DELETE, ${BINARY})
+	$(call SHELL_DELETE,${BINARY})
 
diff --git a/tools/fiptool/fiptool.c b/tools/fiptool/fiptool.c
index e70ff36..e4348ee 100644
--- a/tools/fiptool/fiptool.c
+++ b/tools/fiptool/fiptool.c
@@ -169,7 +169,10 @@
 	free(desc->name);
 	free(desc->cmdline_name);
 	free(desc->action_arg);
-	free(desc->image);
+	if (desc->image) {
+		free(desc->image->buffer);
+		free(desc->image);
+	}
 	free(desc);
 }